media: rcar-vin: Add support for RAW10
authorNiklas Söderlund <niklas.soderlund+renesas@ragnatech.se>
Wed, 4 Sep 2024 15:06:56 +0000 (17:06 +0200)
committerMauro Carvalho Chehab <mchehab+huawei@kernel.org>
Wed, 16 Oct 2024 07:32:39 +0000 (09:32 +0200)
Some R-Car SoCs are capable of capturing RAW10. Extend the format
enumeration, validation and setup to expose and configure for this
format if the particular device supports it.

The VIN is usually capable of converting from most media bus formats to
a range of different pixel formats. However if the input media bus
format is a RAW10 format this is not possible so the corresponding pixel
output format is forced.

Signed-off-by: Niklas Söderlund <niklas.soderlund+renesas@ragnatech.se>
Signed-off-by: Sakari Ailus <sakari.ailus@linux.intel.com>
Signed-off-by: Mauro Carvalho Chehab <mchehab+huawei@kernel.org>
drivers/media/platform/renesas/rcar-vin/rcar-core.c
drivers/media/platform/renesas/rcar-vin/rcar-dma.c
drivers/media/platform/renesas/rcar-vin/rcar-v4l2.c
drivers/media/platform/renesas/rcar-vin/rcar-vin.h

index b738b19ed900719264edef53d5e69b1e9bc4b8b9..ddfb18e6e7a400f1b5c73807c51bcef6e534f4d9 100644 (file)
@@ -1279,6 +1279,7 @@ static const struct rvin_info rcar_info_gen4 = {
        .use_mc = true,
        .use_isp = true,
        .nv12 = true,
+       .raw10 = true,
        .max_width = 4096,
        .max_height = 4096,
 };
index 21d5b2815e86a66a1786901586f18f5474b94ad0..a6e79d47408deb47d689e7adeb387e95808dee4c 100644 (file)
 /* Video n Data Mode Register bits */
 #define VNDMR_A8BIT(n)         (((n) & 0xff) << 24)
 #define VNDMR_A8BIT_MASK       (0xff << 24)
+#define VNDMR_RMODE_RAW10      (2 << 19)
 #define VNDMR_YMODE_Y8         (1 << 12)
+#define VNDMR_YC_THR           (1 << 11)
 #define VNDMR_EXRGB            (1 << 8)
 #define VNDMR_BPSM             (1 << 4)
 #define VNDMR_ABIT             (1 << 2)
@@ -790,6 +792,12 @@ static int rvin_setup(struct rvin_dev *vin)
        case MEDIA_BUS_FMT_Y8_1X8:
                vnmc |= VNMC_INF_RAW8;
                break;
+       case MEDIA_BUS_FMT_SBGGR10_1X10:
+       case MEDIA_BUS_FMT_SGBRG10_1X10:
+       case MEDIA_BUS_FMT_SGRBG10_1X10:
+       case MEDIA_BUS_FMT_SRGGB10_1X10:
+               vnmc |= VNMC_INF_RGB666;
+               break;
        default:
                break;
        }
@@ -898,6 +906,12 @@ static int rvin_setup(struct rvin_dev *vin)
                        dmr = 0;
                }
                break;
+       case V4L2_PIX_FMT_SBGGR10:
+       case V4L2_PIX_FMT_SGBRG10:
+       case V4L2_PIX_FMT_SGRBG10:
+       case V4L2_PIX_FMT_SRGGB10:
+               dmr = VNDMR_RMODE_RAW10 | VNDMR_YC_THR;
+               break;
        default:
                vin_err(vin, "Invalid pixelformat (0x%x)\n",
                        vin->format.pixelformat);
@@ -1280,6 +1294,22 @@ static int rvin_mc_validate_format(struct rvin_dev *vin, struct v4l2_subdev *sd,
                if (vin->format.pixelformat != V4L2_PIX_FMT_GREY)
                        return -EPIPE;
                break;
+       case MEDIA_BUS_FMT_SBGGR10_1X10:
+               if (vin->format.pixelformat != V4L2_PIX_FMT_SBGGR10)
+                       return -EPIPE;
+               break;
+       case MEDIA_BUS_FMT_SGBRG10_1X10:
+               if (vin->format.pixelformat != V4L2_PIX_FMT_SGBRG10)
+                       return -EPIPE;
+               break;
+       case MEDIA_BUS_FMT_SGRBG10_1X10:
+               if (vin->format.pixelformat != V4L2_PIX_FMT_SGRBG10)
+                       return -EPIPE;
+               break;
+       case MEDIA_BUS_FMT_SRGGB10_1X10:
+               if (vin->format.pixelformat != V4L2_PIX_FMT_SRGGB10)
+                       return -EPIPE;
+               break;
        default:
                return -EPIPE;
        }
index bb4b07bed28dd343854b7b041ae9a69a821ecc62..756fdfdbce616ce54cc3ba7f4758ec51a738e3da 100644 (file)
@@ -86,6 +86,22 @@ static const struct rvin_video_format rvin_formats[] = {
                .fourcc                 = V4L2_PIX_FMT_GREY,
                .bpp                    = 1,
        },
+       {
+               .fourcc                 = V4L2_PIX_FMT_SBGGR10,
+               .bpp                    = 4,
+       },
+       {
+               .fourcc                 = V4L2_PIX_FMT_SGBRG10,
+               .bpp                    = 4,
+       },
+       {
+               .fourcc                 = V4L2_PIX_FMT_SGRBG10,
+               .bpp                    = 4,
+       },
+       {
+               .fourcc                 = V4L2_PIX_FMT_SRGGB10,
+               .bpp                    = 4,
+       },
 };
 
 const struct rvin_video_format *rvin_format_from_pixel(struct rvin_dev *vin,
@@ -106,6 +122,13 @@ const struct rvin_video_format *rvin_format_from_pixel(struct rvin_dev *vin,
                if (!vin->info->nv12 || !(BIT(vin->id) & 0x3333))
                        return NULL;
                break;
+       case V4L2_PIX_FMT_SBGGR10:
+       case V4L2_PIX_FMT_SGBRG10:
+       case V4L2_PIX_FMT_SGRBG10:
+       case V4L2_PIX_FMT_SRGGB10:
+               if (!vin->info->raw10)
+                       return NULL;
+               break;
        default:
                break;
        }
@@ -407,6 +430,26 @@ static int rvin_enum_fmt_vid_cap(struct file *file, void *priv,
                        return -EINVAL;
                f->pixelformat = V4L2_PIX_FMT_SRGGB8;
                return 0;
+       case MEDIA_BUS_FMT_SBGGR10_1X10:
+               if (f->index)
+                       return -EINVAL;
+               f->pixelformat = V4L2_PIX_FMT_SBGGR10;
+               return 0;
+       case MEDIA_BUS_FMT_SGBRG10_1X10:
+               if (f->index)
+                       return -EINVAL;
+               f->pixelformat = V4L2_PIX_FMT_SGBRG10;
+               return 0;
+       case MEDIA_BUS_FMT_SGRBG10_1X10:
+               if (f->index)
+                       return -EINVAL;
+               f->pixelformat = V4L2_PIX_FMT_SGRBG10;
+               return 0;
+       case MEDIA_BUS_FMT_SRGGB10_1X10:
+               if (f->index)
+                       return -EINVAL;
+               f->pixelformat = V4L2_PIX_FMT_SRGGB10;
+               return 0;
        default:
                return -EINVAL;
        }
index 997a66318a2931fbc282166505593de44ad0bfd3..f87d4bc9e53ed3dab20818bfeaf2ae283fb1558b 100644 (file)
@@ -151,7 +151,8 @@ struct rvin_group_route {
  * @model:             VIN model
  * @use_mc:            use media controller instead of controlling subdevice
  * @use_isp:           the VIN is connected to the ISP and not to the CSI-2
- * @nv12:              support outputing NV12 pixel format
+ * @nv12:              support outputting NV12 pixel format
+ * @raw10:             support outputting RAW10 pixel format
  * @max_width:         max input width the VIN supports
  * @max_height:                max input height the VIN supports
  * @routes:            list of possible routes from the CSI-2 recivers to
@@ -163,6 +164,7 @@ struct rvin_info {
        bool use_mc;
        bool use_isp;
        bool nv12;
+       bool raw10;
 
        unsigned int max_width;
        unsigned int max_height;