mirror of
https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git
synced 2024-09-12 13:55:32 +00:00
media: sun6i-csi: Introduce bridge format structure, list and helper
Introduce a more informative format list for the bridge, with information about how to configure the input. This separation will later be useful when using the bridge standalone (without capture) for the isp workflow. Signed-off-by: Paul Kocialkowski <paul.kocialkowski@bootlin.com> Acked-by: Jernej Skrabec <jernej.skrabec@gmail.com> Signed-off-by: Sakari Ailus <sakari.ailus@linux.intel.com> Signed-off-by: Mauro Carvalho Chehab <mchehab@kernel.org>
This commit is contained in:
parent
2ed385697b
commit
21818a2905
2 changed files with 145 additions and 36 deletions
|
@ -11,6 +11,7 @@
|
|||
|
||||
#include "sun6i_csi.h"
|
||||
#include "sun6i_csi_bridge.h"
|
||||
#include "sun6i_csi_reg.h"
|
||||
|
||||
/* Helpers */
|
||||
|
||||
|
@ -34,47 +35,143 @@ void sun6i_csi_bridge_format(struct sun6i_csi_device *csi_dev,
|
|||
|
||||
/* Format */
|
||||
|
||||
static const u32 sun6i_csi_bridge_mbus_codes[] = {
|
||||
static const struct sun6i_csi_bridge_format sun6i_csi_bridge_formats[] = {
|
||||
/* Bayer */
|
||||
MEDIA_BUS_FMT_SBGGR8_1X8,
|
||||
MEDIA_BUS_FMT_SGBRG8_1X8,
|
||||
MEDIA_BUS_FMT_SGRBG8_1X8,
|
||||
MEDIA_BUS_FMT_SRGGB8_1X8,
|
||||
MEDIA_BUS_FMT_SBGGR10_1X10,
|
||||
MEDIA_BUS_FMT_SGBRG10_1X10,
|
||||
MEDIA_BUS_FMT_SGRBG10_1X10,
|
||||
MEDIA_BUS_FMT_SRGGB10_1X10,
|
||||
MEDIA_BUS_FMT_SBGGR12_1X12,
|
||||
MEDIA_BUS_FMT_SGBRG12_1X12,
|
||||
MEDIA_BUS_FMT_SGRBG12_1X12,
|
||||
MEDIA_BUS_FMT_SRGGB12_1X12,
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_SBGGR8_1X8,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_RAW,
|
||||
},
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_SGBRG8_1X8,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_RAW,
|
||||
},
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_SGRBG8_1X8,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_RAW,
|
||||
},
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_SRGGB8_1X8,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_RAW,
|
||||
},
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_SBGGR10_1X10,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_RAW,
|
||||
},
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_SGBRG10_1X10,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_RAW,
|
||||
},
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_SGRBG10_1X10,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_RAW,
|
||||
},
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_SRGGB10_1X10,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_RAW,
|
||||
},
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_SBGGR12_1X12,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_RAW,
|
||||
},
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_SGBRG12_1X12,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_RAW,
|
||||
},
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_SGRBG12_1X12,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_RAW,
|
||||
},
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_SRGGB12_1X12,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_RAW,
|
||||
},
|
||||
/* RGB */
|
||||
MEDIA_BUS_FMT_RGB565_2X8_LE,
|
||||
MEDIA_BUS_FMT_RGB565_2X8_BE,
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_RGB565_2X8_LE,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_RAW,
|
||||
},
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_RGB565_2X8_BE,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_RAW,
|
||||
},
|
||||
/* YUV422 */
|
||||
MEDIA_BUS_FMT_YUYV8_2X8,
|
||||
MEDIA_BUS_FMT_UYVY8_2X8,
|
||||
MEDIA_BUS_FMT_YVYU8_2X8,
|
||||
MEDIA_BUS_FMT_UYVY8_2X8,
|
||||
MEDIA_BUS_FMT_VYUY8_2X8,
|
||||
MEDIA_BUS_FMT_YUYV8_1X16,
|
||||
MEDIA_BUS_FMT_UYVY8_1X16,
|
||||
MEDIA_BUS_FMT_YVYU8_1X16,
|
||||
MEDIA_BUS_FMT_UYVY8_1X16,
|
||||
MEDIA_BUS_FMT_VYUY8_1X16,
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_YUYV8_2X8,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_YUV422,
|
||||
.input_yuv_seq = SUN6I_CSI_INPUT_YUV_SEQ_YUYV,
|
||||
.input_yuv_seq_invert = SUN6I_CSI_INPUT_YUV_SEQ_YVYU,
|
||||
},
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_UYVY8_2X8,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_YUV422,
|
||||
.input_yuv_seq = SUN6I_CSI_INPUT_YUV_SEQ_UYVY,
|
||||
.input_yuv_seq_invert = SUN6I_CSI_INPUT_YUV_SEQ_VYUY,
|
||||
},
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_YVYU8_2X8,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_YUV422,
|
||||
.input_yuv_seq = SUN6I_CSI_INPUT_YUV_SEQ_YVYU,
|
||||
.input_yuv_seq_invert = SUN6I_CSI_INPUT_YUV_SEQ_YUYV,
|
||||
},
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_UYVY8_2X8,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_YUV422,
|
||||
.input_yuv_seq = SUN6I_CSI_INPUT_YUV_SEQ_UYVY,
|
||||
.input_yuv_seq_invert = SUN6I_CSI_INPUT_YUV_SEQ_VYUY,
|
||||
},
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_VYUY8_2X8,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_YUV422,
|
||||
.input_yuv_seq = SUN6I_CSI_INPUT_YUV_SEQ_VYUY,
|
||||
.input_yuv_seq_invert = SUN6I_CSI_INPUT_YUV_SEQ_UYVY,
|
||||
},
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_YUYV8_1X16,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_YUV422,
|
||||
.input_yuv_seq = SUN6I_CSI_INPUT_YUV_SEQ_YUYV,
|
||||
.input_yuv_seq_invert = SUN6I_CSI_INPUT_YUV_SEQ_YVYU,
|
||||
},
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_UYVY8_1X16,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_YUV422,
|
||||
.input_yuv_seq = SUN6I_CSI_INPUT_YUV_SEQ_UYVY,
|
||||
.input_yuv_seq_invert = SUN6I_CSI_INPUT_YUV_SEQ_VYUY,
|
||||
},
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_YVYU8_1X16,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_YUV422,
|
||||
.input_yuv_seq = SUN6I_CSI_INPUT_YUV_SEQ_YVYU,
|
||||
.input_yuv_seq_invert = SUN6I_CSI_INPUT_YUV_SEQ_YUYV,
|
||||
},
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_UYVY8_1X16,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_YUV422,
|
||||
.input_yuv_seq = SUN6I_CSI_INPUT_YUV_SEQ_UYVY,
|
||||
.input_yuv_seq_invert = SUN6I_CSI_INPUT_YUV_SEQ_VYUY,
|
||||
},
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_VYUY8_1X16,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_YUV422,
|
||||
.input_yuv_seq = SUN6I_CSI_INPUT_YUV_SEQ_VYUY,
|
||||
.input_yuv_seq_invert = SUN6I_CSI_INPUT_YUV_SEQ_UYVY,
|
||||
},
|
||||
/* Compressed */
|
||||
MEDIA_BUS_FMT_JPEG_1X8,
|
||||
{
|
||||
.mbus_code = MEDIA_BUS_FMT_JPEG_1X8,
|
||||
.input_format = SUN6I_CSI_INPUT_FMT_RAW,
|
||||
},
|
||||
};
|
||||
|
||||
static bool sun6i_csi_bridge_mbus_code_check(u32 mbus_code)
|
||||
const struct sun6i_csi_bridge_format *
|
||||
sun6i_csi_bridge_format_find(u32 mbus_code)
|
||||
{
|
||||
unsigned int i;
|
||||
|
||||
for (i = 0; i < ARRAY_SIZE(sun6i_csi_bridge_mbus_codes); i++)
|
||||
if (sun6i_csi_bridge_mbus_codes[i] == mbus_code)
|
||||
return true;
|
||||
for (i = 0; i < ARRAY_SIZE(sun6i_csi_bridge_formats); i++)
|
||||
if (sun6i_csi_bridge_formats[i].mbus_code == mbus_code)
|
||||
return &sun6i_csi_bridge_formats[i];
|
||||
|
||||
return false;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/* V4L2 Subdev */
|
||||
|
@ -124,8 +221,8 @@ static const struct v4l2_subdev_video_ops sun6i_csi_bridge_video_ops = {
|
|||
static void
|
||||
sun6i_csi_bridge_mbus_format_prepare(struct v4l2_mbus_framefmt *mbus_format)
|
||||
{
|
||||
if (!sun6i_csi_bridge_mbus_code_check(mbus_format->code))
|
||||
mbus_format->code = sun6i_csi_bridge_mbus_codes[0];
|
||||
if (!sun6i_csi_bridge_format_find(mbus_format->code))
|
||||
mbus_format->code = sun6i_csi_bridge_formats[0].mbus_code;
|
||||
|
||||
mbus_format->field = V4L2_FIELD_NONE;
|
||||
mbus_format->colorspace = V4L2_COLORSPACE_RAW;
|
||||
|
@ -144,7 +241,7 @@ static int sun6i_csi_bridge_init_cfg(struct v4l2_subdev *subdev,
|
|||
|
||||
mutex_lock(lock);
|
||||
|
||||
mbus_format->code = sun6i_csi_bridge_mbus_codes[0];
|
||||
mbus_format->code = sun6i_csi_bridge_formats[0].mbus_code;
|
||||
mbus_format->width = 1280;
|
||||
mbus_format->height = 720;
|
||||
|
||||
|
@ -160,10 +257,10 @@ sun6i_csi_bridge_enum_mbus_code(struct v4l2_subdev *subdev,
|
|||
struct v4l2_subdev_state *state,
|
||||
struct v4l2_subdev_mbus_code_enum *code_enum)
|
||||
{
|
||||
if (code_enum->index >= ARRAY_SIZE(sun6i_csi_bridge_mbus_codes))
|
||||
if (code_enum->index >= ARRAY_SIZE(sun6i_csi_bridge_formats))
|
||||
return -EINVAL;
|
||||
|
||||
code_enum->code = sun6i_csi_bridge_mbus_codes[code_enum->index];
|
||||
code_enum->code = sun6i_csi_bridge_formats[code_enum->index].mbus_code;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -20,6 +20,13 @@ enum sun6i_csi_bridge_pad {
|
|||
|
||||
struct sun6i_csi_device;
|
||||
|
||||
struct sun6i_csi_bridge_format {
|
||||
u32 mbus_code;
|
||||
u8 input_format;
|
||||
u8 input_yuv_seq;
|
||||
u8 input_yuv_seq_invert;
|
||||
};
|
||||
|
||||
struct sun6i_csi_bridge_source {
|
||||
struct v4l2_subdev *subdev;
|
||||
struct v4l2_fwnode_endpoint endpoint;
|
||||
|
@ -48,6 +55,11 @@ void sun6i_csi_bridge_dimensions(struct sun6i_csi_device *csi_dev,
|
|||
void sun6i_csi_bridge_format(struct sun6i_csi_device *csi_dev,
|
||||
u32 *mbus_code, u32 *field);
|
||||
|
||||
/* Format */
|
||||
|
||||
const struct sun6i_csi_bridge_format *
|
||||
sun6i_csi_bridge_format_find(u32 mbus_code);
|
||||
|
||||
/* Bridge */
|
||||
|
||||
int sun6i_csi_bridge_setup(struct sun6i_csi_device *csi_dev);
|
||||
|
|
Loading…
Reference in a new issue