From eb895a988d1531c7ede0f7b983db61f38770d929 Mon Sep 17 00:00:00 2001 From: Laurent Pinchart Date: Fri, 20 Apr 2012 11:48:45 +0200 Subject: omap3isp: Add ISP crop support If the sensor doesn't support cropping, crop the image on the first ISP entity that supports cropping on its source pad. Signed-off-by: Laurent Pinchart --- isp/omap3isp.c | 50 ++++++++++++++++++++++++++------------------------ 1 file changed, 26 insertions(+), 24 deletions(-) diff --git a/isp/omap3isp.c b/isp/omap3isp.c index 0bbba2c..d1c74c1 100644 --- a/isp/omap3isp.c +++ b/isp/omap3isp.c @@ -627,7 +627,6 @@ static int omap3_isp_pipeline_try_format(struct omap3_isp_device *isp, struct omap3_isp_entity *sink; struct omap3_isp_video *video; struct media_entity_pad *pad; - struct v4l2_rect rect; int ret; /* Configure formats. Start from the sensor output and propagate the @@ -642,22 +641,6 @@ static int omap3_isp_pipeline_try_format(struct omap3_isp_device *isp, else format = *ofmt; - if (crop) { - ret = v4l2_subdev_set_crop(isp->sensor.entity, crop, 0, - V4L2_SUBDEV_FORMAT_TRY); - if (ret < 0 && ret != -ENOTTY && ret != -EINVAL) { - printf("error: set crop on sensor output failed.\n"); - return ret; - } - } else { - ret = v4l2_subdev_get_crop(isp->sensor.entity, &rect, 0, - V4L2_SUBDEV_FORMAT_TRY); - if (ret < 0 && ret != -ENOTTY && ret != -EINVAL) { - printf("error: get crop on sensor output failed.\n"); - return ret; - } - } - ret = v4l2_subdev_set_format(isp->sensor.entity, &format, 0, V4L2_SUBDEV_FORMAT_TRY); if (ret < 0) { @@ -668,18 +651,37 @@ static int omap3_isp_pipeline_try_format(struct omap3_isp_device *isp, list_for_each_entry(sink, &pipe->entities, list) { if (source == NULL) { source = sink; - - if (crop) - source->source.crop = *crop; - else - source->source.crop = rect; continue; } if (source->type == OMAP3_ISP_ENTITY_ENTITY) { - /* Try to force the output format code onto the source pad. */ pad = source->source.link->source; + /* Crop on the first subdev that supports cropping. */ + source->source.crop.width = 0; + source->source.crop.height = 0; + + if (crop) { + ret = v4l2_subdev_set_crop(pad->entity, crop, pad->index, + V4L2_SUBDEV_FORMAT_TRY); + if (ret < 0 && ret != -ENOTTY && ret != -EINVAL) { + printf("error: set crop on sensor output failed.\n"); + return ret; + } else if (ret >= 0) { + format.width = crop->width; + format.height = crop->height; + source->source.crop = *crop; + crop = NULL; + } + } else if (source->entity == isp->sensor.entity) { + /* If crop is not requested, reset the crop rectangle on the + * sensor to its default value. + */ + source->source.crop.width = format.width; + source->source.crop.height = format.height; + } + + /* Try to force the output format code onto the source pad. */ ret = v4l2_subdev_get_format(pad->entity, &format, pad->index, V4L2_SUBDEV_FORMAT_TRY); if (ret < 0) { @@ -800,7 +802,7 @@ static int omap3_isp_pipeline_activate(struct omap3_isp_device *isp, if (source->type == OMAP3_ISP_ENTITY_ENTITY) { pad = source->source.link->source; - if (first) { + if (source->source.crop.width && source->source.crop.height) { struct v4l2_rect crop = source->source.crop; ret = v4l2_subdev_set_crop(pad->entity, &crop, pad->index, -- cgit v1.2.3