drivers/staging/media/imx/imx-media-capture.c

Source file repositories/reference/linux-study-clean/drivers/staging/media/imx/imx-media-capture.c

File Facts

System
Linux kernel
Corpus path
drivers/staging/media/imx/imx-media-capture.c
Extension
.c
Size
27479 bytes
Lines
1056
Domain
Driver Families
Bucket
drivers/staging
Inferred role
Driver Families: exported/initcall integration point
Status
integration implementation candidate

Why This File Exists

Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.

Dependency Surface

Detected Declarations

Annotated Snippet

struct capture_priv {
	struct imx_media_dev *md;		/* Media device */
	struct device *dev;			/* Physical device */

	struct imx_media_video_dev vdev;	/* Video device */
	struct media_pad vdev_pad;		/* Video device pad */

	struct v4l2_subdev *src_sd;		/* Source subdev */
	int src_sd_pad;				/* Source subdev pad */

	struct mutex mutex;			/* Protect vdev operations */

	struct vb2_queue q;			/* The videobuf2 queue */
	struct list_head ready_q;		/* List of queued buffers */
	spinlock_t q_lock;			/* Protect ready_q */

	struct v4l2_ctrl_handler ctrl_hdlr;	/* Controls inherited from subdevs */

	bool legacy_api;			/* Use the legacy (pre-MC) API */
};

#define to_capture_priv(v) container_of(v, struct capture_priv, vdev)

/* In bytes, per queue */
#define VID_MEM_LIMIT	SZ_64M

/* -----------------------------------------------------------------------------
 * MC-Centric Video IOCTLs
 */

static const struct imx_media_pixfmt *capture_find_format(u32 code, u32 fourcc)
{
	const struct imx_media_pixfmt *cc;

	cc = imx_media_find_ipu_format(code, PIXFMT_SEL_YUV_RGB);
	if (cc) {
		enum imx_pixfmt_sel fmt_sel = cc->cs == IPUV3_COLORSPACE_YUV
					    ? PIXFMT_SEL_YUV : PIXFMT_SEL_RGB;

		cc = imx_media_find_pixel_format(fourcc, fmt_sel);
		if (!cc) {
			imx_media_enum_pixel_formats(&fourcc, 0, fmt_sel, 0);
			cc = imx_media_find_pixel_format(fourcc, fmt_sel);
		}

		return cc;
	}

	return imx_media_find_mbus_format(code, PIXFMT_SEL_ANY);
}

static int capture_querycap(struct file *file, void *fh,
			    struct v4l2_capability *cap)
{
	struct capture_priv *priv = video_drvdata(file);

	strscpy(cap->driver, IMX_CAPTURE_NAME, sizeof(cap->driver));
	strscpy(cap->card, IMX_CAPTURE_NAME, sizeof(cap->card));
	snprintf(cap->bus_info, sizeof(cap->bus_info),
		 "platform:%s", dev_name(priv->dev));

	return 0;
}

static int capture_enum_fmt_vid_cap(struct file *file, void *fh,
				    struct v4l2_fmtdesc *f)
{
	return imx_media_enum_pixel_formats(&f->pixelformat, f->index,
					    PIXFMT_SEL_ANY, f->mbus_code);
}

static int capture_enum_framesizes(struct file *file, void *fh,
				   struct v4l2_frmsizeenum *fsize)
{
	const struct imx_media_pixfmt *cc;

	if (fsize->index > 0)
		return -EINVAL;

	cc = imx_media_find_pixel_format(fsize->pixel_format, PIXFMT_SEL_ANY);
	if (!cc)
		return -EINVAL;

	/*
	 * TODO: The constraints are hardware-specific and may depend on the
	 * pixel format. This should come from the driver using
	 * imx_media_capture.
	 */
	fsize->type = V4L2_FRMSIZE_TYPE_CONTINUOUS;
	fsize->stepwise.min_width = 1;

Annotation

Implementation Notes