aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/media/platform/vsp1/vsp1_video.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/media/platform/vsp1/vsp1_video.c')
-rw-r--r--drivers/media/platform/vsp1/vsp1_video.c117
1 files changed, 55 insertions, 62 deletions
diff --git a/drivers/media/platform/vsp1/vsp1_video.c b/drivers/media/platform/vsp1/vsp1_video.c
index 5ce88e1f5d71..637d0d6f79fb 100644
--- a/drivers/media/platform/vsp1/vsp1_video.c
+++ b/drivers/media/platform/vsp1/vsp1_video.c
@@ -160,8 +160,7 @@ vsp1_video_remote_subdev(struct media_pad *local, u32 *pad)
struct media_pad *remote;
remote = media_entity_remote_pad(local);
- if (remote == NULL ||
- media_entity_type(remote->entity) != MEDIA_ENT_T_V4L2_SUBDEV)
+ if (!remote || !is_media_entity_v4l2_subdev(remote->entity))
return NULL;
if (pad)
@@ -274,35 +273,6 @@ static int __vsp1_video_try_format(struct vsp1_video *video,
return 0;
}
-static bool
-vsp1_video_format_adjust(struct vsp1_video *video,
- const struct v4l2_pix_format_mplane *format,
- struct v4l2_pix_format_mplane *adjust)
-{
- unsigned int i;
-
- *adjust = *format;
- __vsp1_video_try_format(video, adjust, NULL);
-
- if (format->width != adjust->width ||
- format->height != adjust->height ||
- format->pixelformat != adjust->pixelformat ||
- format->num_planes != adjust->num_planes)
- return false;
-
- for (i = 0; i < format->num_planes; ++i) {
- if (format->plane_fmt[i].bytesperline !=
- adjust->plane_fmt[i].bytesperline)
- return false;
-
- adjust->plane_fmt[i].sizeimage =
- max(adjust->plane_fmt[i].sizeimage,
- format->plane_fmt[i].sizeimage);
- }
-
- return true;
-}
-
/* -----------------------------------------------------------------------------
* Pipeline Management
*/
@@ -312,24 +282,35 @@ static int vsp1_pipeline_validate_branch(struct vsp1_pipeline *pipe,
struct vsp1_rwpf *output)
{
struct vsp1_entity *entity;
- unsigned int entities = 0;
+ struct media_entity_enum ent_enum;
struct media_pad *pad;
+ int rval;
bool bru_found = false;
input->location.left = 0;
input->location.top = 0;
+ rval = media_entity_enum_init(
+ &ent_enum, input->entity.pads[RWPF_PAD_SOURCE].graph_obj.mdev);
+ if (rval)
+ return rval;
+
pad = media_entity_remote_pad(&input->entity.pads[RWPF_PAD_SOURCE]);
while (1) {
- if (pad == NULL)
- return -EPIPE;
+ if (pad == NULL) {
+ rval = -EPIPE;
+ goto out;
+ }
/* We've reached a video node, that shouldn't have happened. */
- if (media_entity_type(pad->entity) != MEDIA_ENT_T_V4L2_SUBDEV)
- return -EPIPE;
+ if (!is_media_entity_v4l2_subdev(pad->entity)) {
+ rval = -EPIPE;
+ goto out;
+ }
- entity = to_vsp1_entity(media_entity_to_v4l2_subdev(pad->entity));
+ entity = to_vsp1_entity(
+ media_entity_to_v4l2_subdev(pad->entity));
/* A BRU is present in the pipeline, store the compose rectangle
* location in the input RPF for use when configuring the RPF.
@@ -352,15 +333,18 @@ static int vsp1_pipeline_validate_branch(struct vsp1_pipeline *pipe,
break;
/* Ensure the branch has no loop. */
- if (entities & (1 << entity->subdev.entity.id))
- return -EPIPE;
-
- entities |= 1 << entity->subdev.entity.id;
+ if (media_entity_enum_test_and_set(&ent_enum,
+ &entity->subdev.entity)) {
+ rval = -EPIPE;
+ goto out;
+ }
/* UDS can't be chained. */
if (entity->type == VSP1_ENTITY_UDS) {
- if (pipe->uds)
- return -EPIPE;
+ if (pipe->uds) {
+ rval = -EPIPE;
+ goto out;
+ }
pipe->uds = entity;
pipe->uds_input = bru_found ? pipe->bru
@@ -378,9 +362,12 @@ static int vsp1_pipeline_validate_branch(struct vsp1_pipeline *pipe,
/* The last entity must be the output WPF. */
if (entity != &output->entity)
- return -EPIPE;
+ rval = -EPIPE;
- return 0;
+out:
+ media_entity_enum_cleanup(&ent_enum);
+
+ return rval;
}
static void __vsp1_pipeline_cleanup(struct vsp1_pipeline *pipe)
@@ -409,13 +396,19 @@ static int vsp1_pipeline_validate(struct vsp1_pipeline *pipe,
{
struct media_entity_graph graph;
struct media_entity *entity = &video->video.entity;
- struct media_device *mdev = entity->parent;
+ struct media_device *mdev = entity->graph_obj.mdev;
unsigned int i;
int ret;
mutex_lock(&mdev->graph_mutex);
/* Walk the graph to locate the entities and video nodes. */
+ ret = media_entity_graph_walk_init(&graph, mdev);
+ if (ret) {
+ mutex_unlock(&mdev->graph_mutex);
+ return ret;
+ }
+
media_entity_graph_walk_start(&graph, entity);
while ((entity = media_entity_graph_walk_next(&graph))) {
@@ -423,7 +416,7 @@ static int vsp1_pipeline_validate(struct vsp1_pipeline *pipe,
struct vsp1_rwpf *rwpf;
struct vsp1_entity *e;
- if (media_entity_type(entity) != MEDIA_ENT_T_V4L2_SUBDEV) {
+ if (is_media_entity_v4l2_io(entity)) {
pipe->num_video++;
continue;
}
@@ -449,6 +442,8 @@ static int vsp1_pipeline_validate(struct vsp1_pipeline *pipe,
mutex_unlock(&mdev->graph_mutex);
+ media_entity_graph_walk_cleanup(&graph);
+
/* We need one output and at least one input. */
if (pipe->num_inputs == 0 || !pipe->output) {
ret = -EPIPE;
@@ -611,7 +606,7 @@ vsp1_video_complete_buffer(struct vsp1_video *video)
spin_unlock_irqrestore(&video->irqlock, flags);
done->buf.sequence = video->sequence++;
- v4l2_get_timestamp(&done->buf.timestamp);
+ done->buf.vb2_buf.timestamp = ktime_get_ns();
for (i = 0; i < done->buf.vb2_buf.num_planes; ++i)
vb2_set_plane_payload(&done->buf.vb2_buf, i, done->length[i]);
vb2_buffer_done(&done->buf.vb2_buf, VB2_BUF_STATE_DONE);
@@ -692,7 +687,7 @@ void vsp1_pipeline_propagate_alpha(struct vsp1_pipeline *pipe,
pad = media_entity_remote_pad(&input->pads[RWPF_PAD_SOURCE]);
while (pad) {
- if (media_entity_type(pad->entity) != MEDIA_ENT_T_V4L2_SUBDEV)
+ if (!is_media_entity_v4l2_subdev(pad->entity))
break;
entity = to_vsp1_entity(media_entity_to_v4l2_subdev(pad->entity));
@@ -787,26 +782,24 @@ void vsp1_pipelines_resume(struct vsp1_device *vsp1)
*/
static int
-vsp1_video_queue_setup(struct vb2_queue *vq, const void *parg,
+vsp1_video_queue_setup(struct vb2_queue *vq,
unsigned int *nbuffers, unsigned int *nplanes,
unsigned int sizes[], void *alloc_ctxs[])
{
- const struct v4l2_format *fmt = parg;
struct vsp1_video *video = vb2_get_drv_priv(vq);
- const struct v4l2_pix_format_mplane *format;
- struct v4l2_pix_format_mplane pix_mp;
+ const struct v4l2_pix_format_mplane *format = &video->format;
unsigned int i;
- if (fmt) {
- /* Make sure the format is valid and adjust the sizeimage field
- * if needed.
- */
- if (!vsp1_video_format_adjust(video, &fmt->fmt.pix_mp, &pix_mp))
+ if (*nplanes) {
+ if (*nplanes != format->num_planes)
return -EINVAL;
- format = &pix_mp;
- } else {
- format = &video->format;
+ for (i = 0; i < *nplanes; i++) {
+ if (sizes[i] < format->plane_fmt[i].sizeimage)
+ return -EINVAL;
+ alloc_ctxs[i] = video->alloc_ctx;
+ }
+ return 0;
}
*nplanes = format->num_planes;
@@ -1224,7 +1217,7 @@ int vsp1_video_init(struct vsp1_video *video, struct vsp1_entity *rwpf)
video->pipe.state = VSP1_PIPELINE_STOPPED;
/* Initialize the media entity... */
- ret = media_entity_init(&video->video.entity, 1, &video->pad, 0);
+ ret = media_entity_pads_init(&video->video.entity, 1, &video->pad);
if (ret < 0)
return ret;