Back to home page

OSCL-LXR

 
 

    


0001 /* SPDX-License-Identifier: GPL-2.0+ */
0002 /*
0003  * V4L2 Media Controller Driver for Freescale i.MX5/6 SOC
0004  *
0005  * Copyright (c) 2016 Mentor Graphics Inc.
0006  */
0007 #ifndef _IMX_MEDIA_H
0008 #define _IMX_MEDIA_H
0009 
0010 #include <linux/platform_device.h>
0011 #include <media/v4l2-ctrls.h>
0012 #include <media/v4l2-device.h>
0013 #include <media/v4l2-fwnode.h>
0014 #include <media/v4l2-subdev.h>
0015 #include <media/videobuf2-dma-contig.h>
0016 #include <video/imx-ipu-v3.h>
0017 
0018 #define IMX_MEDIA_DEF_PIX_WIDTH     640
0019 #define IMX_MEDIA_DEF_PIX_HEIGHT    480
0020 
0021 /*
0022  * Enumeration of the IPU internal sub-devices
0023  */
0024 enum {
0025     IPU_CSI0 = 0,
0026     IPU_CSI1,
0027     IPU_VDIC,
0028     IPU_IC_PRP,
0029     IPU_IC_PRPENC,
0030     IPU_IC_PRPVF,
0031     NUM_IPU_SUBDEVS,
0032 };
0033 
0034 /*
0035  * Pad definitions for the subdevs with multiple source or
0036  * sink pads
0037  */
0038 
0039 /* ipu_csi */
0040 enum {
0041     CSI_SINK_PAD = 0,
0042     CSI_SRC_PAD_DIRECT,
0043     CSI_SRC_PAD_IDMAC,
0044     CSI_NUM_PADS,
0045 };
0046 
0047 /* ipu_vdic */
0048 enum {
0049     VDIC_SINK_PAD_DIRECT = 0,
0050     VDIC_SINK_PAD_IDMAC,
0051     VDIC_SRC_PAD_DIRECT,
0052     VDIC_NUM_PADS,
0053 };
0054 
0055 /* ipu_ic_prp */
0056 enum {
0057     PRP_SINK_PAD = 0,
0058     PRP_SRC_PAD_PRPENC,
0059     PRP_SRC_PAD_PRPVF,
0060     PRP_NUM_PADS,
0061 };
0062 
0063 /* ipu_ic_prpencvf */
0064 enum {
0065     PRPENCVF_SINK_PAD = 0,
0066     PRPENCVF_SRC_PAD,
0067     PRPENCVF_NUM_PADS,
0068 };
0069 
0070 /* How long to wait for EOF interrupts in the buffer-capture subdevs */
0071 #define IMX_MEDIA_EOF_TIMEOUT       2000
0072 
0073 struct imx_media_pixfmt {
0074     /* the in-memory FourCC pixel format */
0075     u32     fourcc;
0076     /*
0077      * the set of equivalent media bus codes for the fourcc.
0078      * NOTE! codes pointer is NULL for in-memory-only formats.
0079      */
0080     const u32 *codes;
0081     int     bpp;     /* total bpp */
0082     /* cycles per pixel for generic (bayer) formats for the parallel bus */
0083     int cycles;
0084     enum ipu_color_space cs;
0085     bool    planar;  /* is a planar format */
0086     bool    bayer;   /* is a raw bayer format */
0087     bool    ipufmt;  /* is one of the IPU internal formats */
0088 };
0089 
0090 enum imx_pixfmt_sel {
0091     PIXFMT_SEL_YUV   = BIT(0), /* select YUV formats */
0092     PIXFMT_SEL_RGB   = BIT(1), /* select RGB formats */
0093     PIXFMT_SEL_BAYER = BIT(2), /* select BAYER formats */
0094     PIXFMT_SEL_IPU   = BIT(3), /* select IPU-internal formats */
0095     PIXFMT_SEL_YUV_RGB = PIXFMT_SEL_YUV | PIXFMT_SEL_RGB,
0096     PIXFMT_SEL_ANY = PIXFMT_SEL_YUV | PIXFMT_SEL_RGB | PIXFMT_SEL_BAYER,
0097 };
0098 
0099 struct imx_media_buffer {
0100     struct vb2_v4l2_buffer vbuf; /* v4l buffer must be first */
0101     struct list_head  list;
0102 };
0103 
0104 struct imx_media_video_dev {
0105     struct video_device *vfd;
0106 
0107     /* the user format */
0108     struct v4l2_pix_format fmt;
0109     /* the compose rectangle */
0110     struct v4l2_rect compose;
0111     const struct imx_media_pixfmt *cc;
0112 
0113     /* links this vdev to master list */
0114     struct list_head list;
0115 };
0116 
0117 static inline struct imx_media_buffer *to_imx_media_vb(struct vb2_buffer *vb)
0118 {
0119     struct vb2_v4l2_buffer *vbuf = to_vb2_v4l2_buffer(vb);
0120 
0121     return container_of(vbuf, struct imx_media_buffer, vbuf);
0122 }
0123 
0124 /*
0125  * to support control inheritance to video devices, this
0126  * retrieves a pad's list_head of video devices that can
0127  * be reached from the pad. Note that only the lists in
0128  * source pads get populated, sink pads have empty lists.
0129  */
0130 static inline struct list_head *
0131 to_pad_vdev_list(struct v4l2_subdev *sd, int pad_index)
0132 {
0133     struct list_head *vdev_list = sd->host_priv;
0134 
0135     return vdev_list ? &vdev_list[pad_index] : NULL;
0136 }
0137 
0138 /* an entry in a pad's video device list */
0139 struct imx_media_pad_vdev {
0140     struct imx_media_video_dev *vdev;
0141     struct list_head list;
0142 };
0143 
0144 struct imx_media_dev {
0145     struct media_device md;
0146     struct v4l2_device  v4l2_dev;
0147 
0148     /* the pipeline object */
0149     struct media_pipeline pipe;
0150 
0151     struct mutex mutex; /* protect elements below */
0152 
0153     /* master video device list */
0154     struct list_head vdev_list;
0155 
0156     /* IPUs this media driver control, valid after subdevs bound */
0157     struct ipu_soc *ipu[2];
0158 
0159     /* for async subdev registration */
0160     struct v4l2_async_notifier notifier;
0161 
0162     /* IC scaler/CSC mem2mem video device */
0163     struct imx_media_video_dev *m2m_vdev;
0164 
0165     /* the IPU internal subdev's registered synchronously */
0166     struct v4l2_subdev *sync_sd[2][NUM_IPU_SUBDEVS];
0167 };
0168 
0169 /* imx-media-utils.c */
0170 const struct imx_media_pixfmt *
0171 imx_media_find_pixel_format(u32 fourcc, enum imx_pixfmt_sel sel);
0172 int imx_media_enum_pixel_formats(u32 *fourcc, u32 index,
0173                  enum imx_pixfmt_sel sel, u32 code);
0174 const struct imx_media_pixfmt *
0175 imx_media_find_mbus_format(u32 code, enum imx_pixfmt_sel sel);
0176 int imx_media_enum_mbus_formats(u32 *code, u32 index,
0177                 enum imx_pixfmt_sel sel);
0178 
0179 static inline const struct imx_media_pixfmt *
0180 imx_media_find_ipu_format(u32 code, enum imx_pixfmt_sel fmt_sel)
0181 {
0182     return imx_media_find_mbus_format(code, fmt_sel | PIXFMT_SEL_IPU);
0183 }
0184 
0185 static inline int imx_media_enum_ipu_formats(u32 *code, u32 index,
0186                          enum imx_pixfmt_sel fmt_sel)
0187 {
0188     return imx_media_enum_mbus_formats(code, index,
0189                       fmt_sel | PIXFMT_SEL_IPU);
0190 }
0191 
0192 int imx_media_init_mbus_fmt(struct v4l2_mbus_framefmt *mbus,
0193                 u32 width, u32 height, u32 code, u32 field,
0194                 const struct imx_media_pixfmt **cc);
0195 int imx_media_init_cfg(struct v4l2_subdev *sd,
0196                struct v4l2_subdev_state *sd_state);
0197 void imx_media_try_colorimetry(struct v4l2_mbus_framefmt *tryfmt,
0198                    bool ic_route);
0199 int imx_media_mbus_fmt_to_pix_fmt(struct v4l2_pix_format *pix,
0200                   const struct v4l2_mbus_framefmt *mbus,
0201                   const struct imx_media_pixfmt *cc);
0202 void imx_media_grp_id_to_sd_name(char *sd_name, int sz,
0203                  u32 grp_id, int ipu_id);
0204 struct v4l2_subdev *
0205 imx_media_find_subdev_by_fwnode(struct imx_media_dev *imxmd,
0206                 struct fwnode_handle *fwnode);
0207 struct v4l2_subdev *
0208 imx_media_find_subdev_by_devname(struct imx_media_dev *imxmd,
0209                  const char *devname);
0210 void imx_media_add_video_device(struct imx_media_dev *imxmd,
0211                 struct imx_media_video_dev *vdev);
0212 int imx_media_pipeline_csi2_channel(struct media_entity *start_entity);
0213 struct media_pad *
0214 imx_media_pipeline_pad(struct media_entity *start_entity, u32 grp_id,
0215                enum v4l2_buf_type buftype, bool upstream);
0216 struct v4l2_subdev *
0217 imx_media_pipeline_subdev(struct media_entity *start_entity, u32 grp_id,
0218               bool upstream);
0219 struct video_device *
0220 imx_media_pipeline_video_device(struct media_entity *start_entity,
0221                 enum v4l2_buf_type buftype, bool upstream);
0222 struct fwnode_handle *imx_media_get_pad_fwnode(struct media_pad *pad);
0223 
0224 struct imx_media_dma_buf {
0225     void          *virt;
0226     dma_addr_t     phys;
0227     unsigned long  len;
0228 };
0229 
0230 void imx_media_free_dma_buf(struct device *dev,
0231                 struct imx_media_dma_buf *buf);
0232 int imx_media_alloc_dma_buf(struct device *dev,
0233                 struct imx_media_dma_buf *buf,
0234                 int size);
0235 
0236 int imx_media_pipeline_set_stream(struct imx_media_dev *imxmd,
0237                   struct media_entity *entity,
0238                   bool on);
0239 
0240 /* imx-media-dev-common.c */
0241 int imx_media_probe_complete(struct v4l2_async_notifier *notifier);
0242 struct imx_media_dev *imx_media_dev_init(struct device *dev,
0243                      const struct media_device_ops *ops);
0244 int imx_media_dev_notifier_register(struct imx_media_dev *imxmd,
0245                 const struct v4l2_async_notifier_operations *ops);
0246 
0247 /* imx-media-fim.c */
0248 struct imx_media_fim;
0249 void imx_media_fim_eof_monitor(struct imx_media_fim *fim, ktime_t timestamp);
0250 int imx_media_fim_set_stream(struct imx_media_fim *fim,
0251                  const struct v4l2_fract *frame_interval,
0252                  bool on);
0253 int imx_media_fim_add_controls(struct imx_media_fim *fim);
0254 struct imx_media_fim *imx_media_fim_init(struct v4l2_subdev *sd);
0255 void imx_media_fim_free(struct imx_media_fim *fim);
0256 
0257 /* imx-media-internal-sd.c */
0258 int imx_media_register_ipu_internal_subdevs(struct imx_media_dev *imxmd,
0259                         struct v4l2_subdev *csi);
0260 void imx_media_unregister_ipu_internal_subdevs(struct imx_media_dev *imxmd);
0261 
0262 /* imx-media-of.c */
0263 int imx_media_add_of_subdevs(struct imx_media_dev *dev,
0264                  struct device_node *np);
0265 int imx_media_of_add_csi(struct imx_media_dev *imxmd,
0266              struct device_node *csi_np);
0267 
0268 /* imx-media-vdic.c */
0269 struct v4l2_subdev *imx_media_vdic_register(struct v4l2_device *v4l2_dev,
0270                         struct device *ipu_dev,
0271                         struct ipu_soc *ipu,
0272                         u32 grp_id);
0273 int imx_media_vdic_unregister(struct v4l2_subdev *sd);
0274 
0275 /* imx-ic-common.c */
0276 struct v4l2_subdev *imx_media_ic_register(struct v4l2_device *v4l2_dev,
0277                       struct device *ipu_dev,
0278                       struct ipu_soc *ipu,
0279                       u32 grp_id);
0280 int imx_media_ic_unregister(struct v4l2_subdev *sd);
0281 
0282 /* imx-media-capture.c */
0283 struct imx_media_video_dev *
0284 imx_media_capture_device_init(struct device *dev, struct v4l2_subdev *src_sd,
0285                   int pad, bool legacy_api);
0286 void imx_media_capture_device_remove(struct imx_media_video_dev *vdev);
0287 int imx_media_capture_device_register(struct imx_media_video_dev *vdev,
0288                       u32 link_flags);
0289 void imx_media_capture_device_unregister(struct imx_media_video_dev *vdev);
0290 struct imx_media_buffer *
0291 imx_media_capture_device_next_buf(struct imx_media_video_dev *vdev);
0292 void imx_media_capture_device_error(struct imx_media_video_dev *vdev);
0293 
0294 /* imx-media-csc-scaler.c */
0295 struct imx_media_video_dev *
0296 imx_media_csc_scaler_device_init(struct imx_media_dev *dev);
0297 int imx_media_csc_scaler_device_register(struct imx_media_video_dev *vdev);
0298 void imx_media_csc_scaler_device_unregister(struct imx_media_video_dev *vdev);
0299 
0300 /* subdev group ids */
0301 #define IMX_MEDIA_GRP_ID_CSI2          BIT(8)
0302 #define IMX_MEDIA_GRP_ID_CSI           BIT(9)
0303 #define IMX_MEDIA_GRP_ID_IPU_CSI_BIT   10
0304 #define IMX_MEDIA_GRP_ID_IPU_CSI       (0x3 << IMX_MEDIA_GRP_ID_IPU_CSI_BIT)
0305 #define IMX_MEDIA_GRP_ID_IPU_CSI0      BIT(IMX_MEDIA_GRP_ID_IPU_CSI_BIT)
0306 #define IMX_MEDIA_GRP_ID_IPU_CSI1      (2 << IMX_MEDIA_GRP_ID_IPU_CSI_BIT)
0307 #define IMX_MEDIA_GRP_ID_IPU_VDIC      BIT(12)
0308 #define IMX_MEDIA_GRP_ID_IPU_IC_PRP    BIT(13)
0309 #define IMX_MEDIA_GRP_ID_IPU_IC_PRPENC BIT(14)
0310 #define IMX_MEDIA_GRP_ID_IPU_IC_PRPVF  BIT(15)
0311 #define IMX_MEDIA_GRP_ID_CSI_MUX       BIT(16)
0312 
0313 #endif