cachepc-linux

Fork of AMDESE/linux with modifications for CachePC side-channel attack
git clone https://git.sinitax.com/sinitax/cachepc-linux
Log | Files | Refs | README | LICENSE | sfeed.txt

v4l2-subdev.c (28257B)


      1// SPDX-License-Identifier: GPL-2.0-only
      2/*
      3 * V4L2 sub-device
      4 *
      5 * Copyright (C) 2010 Nokia Corporation
      6 *
      7 * Contact: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
      8 *	    Sakari Ailus <sakari.ailus@iki.fi>
      9 */
     10
     11#include <linux/ioctl.h>
     12#include <linux/mm.h>
     13#include <linux/module.h>
     14#include <linux/slab.h>
     15#include <linux/types.h>
     16#include <linux/videodev2.h>
     17#include <linux/export.h>
     18#include <linux/version.h>
     19
     20#include <media/v4l2-ctrls.h>
     21#include <media/v4l2-device.h>
     22#include <media/v4l2-ioctl.h>
     23#include <media/v4l2-fh.h>
     24#include <media/v4l2-event.h>
     25
     26#if defined(CONFIG_VIDEO_V4L2_SUBDEV_API)
     27static int subdev_fh_init(struct v4l2_subdev_fh *fh, struct v4l2_subdev *sd)
     28{
     29	struct v4l2_subdev_state *state;
     30	static struct lock_class_key key;
     31
     32	state = __v4l2_subdev_state_alloc(sd, "fh->state->lock", &key);
     33	if (IS_ERR(state))
     34		return PTR_ERR(state);
     35
     36	fh->state = state;
     37
     38	return 0;
     39}
     40
     41static void subdev_fh_free(struct v4l2_subdev_fh *fh)
     42{
     43	__v4l2_subdev_state_free(fh->state);
     44	fh->state = NULL;
     45}
     46
     47static int subdev_open(struct file *file)
     48{
     49	struct video_device *vdev = video_devdata(file);
     50	struct v4l2_subdev *sd = vdev_to_v4l2_subdev(vdev);
     51	struct v4l2_subdev_fh *subdev_fh;
     52	int ret;
     53
     54	subdev_fh = kzalloc(sizeof(*subdev_fh), GFP_KERNEL);
     55	if (subdev_fh == NULL)
     56		return -ENOMEM;
     57
     58	ret = subdev_fh_init(subdev_fh, sd);
     59	if (ret) {
     60		kfree(subdev_fh);
     61		return ret;
     62	}
     63
     64	v4l2_fh_init(&subdev_fh->vfh, vdev);
     65	v4l2_fh_add(&subdev_fh->vfh);
     66	file->private_data = &subdev_fh->vfh;
     67
     68	if (sd->v4l2_dev->mdev && sd->entity.graph_obj.mdev->dev) {
     69		struct module *owner;
     70
     71		owner = sd->entity.graph_obj.mdev->dev->driver->owner;
     72		if (!try_module_get(owner)) {
     73			ret = -EBUSY;
     74			goto err;
     75		}
     76		subdev_fh->owner = owner;
     77	}
     78
     79	if (sd->internal_ops && sd->internal_ops->open) {
     80		ret = sd->internal_ops->open(sd, subdev_fh);
     81		if (ret < 0)
     82			goto err;
     83	}
     84
     85	return 0;
     86
     87err:
     88	module_put(subdev_fh->owner);
     89	v4l2_fh_del(&subdev_fh->vfh);
     90	v4l2_fh_exit(&subdev_fh->vfh);
     91	subdev_fh_free(subdev_fh);
     92	kfree(subdev_fh);
     93
     94	return ret;
     95}
     96
     97static int subdev_close(struct file *file)
     98{
     99	struct video_device *vdev = video_devdata(file);
    100	struct v4l2_subdev *sd = vdev_to_v4l2_subdev(vdev);
    101	struct v4l2_fh *vfh = file->private_data;
    102	struct v4l2_subdev_fh *subdev_fh = to_v4l2_subdev_fh(vfh);
    103
    104	if (sd->internal_ops && sd->internal_ops->close)
    105		sd->internal_ops->close(sd, subdev_fh);
    106	module_put(subdev_fh->owner);
    107	v4l2_fh_del(vfh);
    108	v4l2_fh_exit(vfh);
    109	subdev_fh_free(subdev_fh);
    110	kfree(subdev_fh);
    111	file->private_data = NULL;
    112
    113	return 0;
    114}
    115#else /* CONFIG_VIDEO_V4L2_SUBDEV_API */
    116static int subdev_open(struct file *file)
    117{
    118	return -ENODEV;
    119}
    120
    121static int subdev_close(struct file *file)
    122{
    123	return -ENODEV;
    124}
    125#endif /* CONFIG_VIDEO_V4L2_SUBDEV_API */
    126
    127static inline int check_which(u32 which)
    128{
    129	if (which != V4L2_SUBDEV_FORMAT_TRY &&
    130	    which != V4L2_SUBDEV_FORMAT_ACTIVE)
    131		return -EINVAL;
    132
    133	return 0;
    134}
    135
    136static inline int check_pad(struct v4l2_subdev *sd, u32 pad)
    137{
    138#if defined(CONFIG_MEDIA_CONTROLLER)
    139	if (sd->entity.num_pads) {
    140		if (pad >= sd->entity.num_pads)
    141			return -EINVAL;
    142		return 0;
    143	}
    144#endif
    145	/* allow pad 0 on subdevices not registered as media entities */
    146	if (pad > 0)
    147		return -EINVAL;
    148	return 0;
    149}
    150
    151static int check_state_pads(u32 which, struct v4l2_subdev_state *state)
    152{
    153	if (which == V4L2_SUBDEV_FORMAT_TRY && (!state || !state->pads))
    154		return -EINVAL;
    155
    156	return 0;
    157}
    158
    159static inline int check_format(struct v4l2_subdev *sd,
    160			       struct v4l2_subdev_state *state,
    161			       struct v4l2_subdev_format *format)
    162{
    163	if (!format)
    164		return -EINVAL;
    165
    166	return check_which(format->which) ? : check_pad(sd, format->pad) ? :
    167	       check_state_pads(format->which, state);
    168}
    169
    170static int call_get_fmt(struct v4l2_subdev *sd,
    171			struct v4l2_subdev_state *state,
    172			struct v4l2_subdev_format *format)
    173{
    174	return check_format(sd, state, format) ? :
    175	       sd->ops->pad->get_fmt(sd, state, format);
    176}
    177
    178static int call_set_fmt(struct v4l2_subdev *sd,
    179			struct v4l2_subdev_state *state,
    180			struct v4l2_subdev_format *format)
    181{
    182	return check_format(sd, state, format) ? :
    183	       sd->ops->pad->set_fmt(sd, state, format);
    184}
    185
    186static int call_enum_mbus_code(struct v4l2_subdev *sd,
    187			       struct v4l2_subdev_state *state,
    188			       struct v4l2_subdev_mbus_code_enum *code)
    189{
    190	if (!code)
    191		return -EINVAL;
    192
    193	return check_which(code->which) ? : check_pad(sd, code->pad) ? :
    194	       check_state_pads(code->which, state) ? :
    195	       sd->ops->pad->enum_mbus_code(sd, state, code);
    196}
    197
    198static int call_enum_frame_size(struct v4l2_subdev *sd,
    199				struct v4l2_subdev_state *state,
    200				struct v4l2_subdev_frame_size_enum *fse)
    201{
    202	if (!fse)
    203		return -EINVAL;
    204
    205	return check_which(fse->which) ? : check_pad(sd, fse->pad) ? :
    206	       check_state_pads(fse->which, state) ? :
    207	       sd->ops->pad->enum_frame_size(sd, state, fse);
    208}
    209
    210static inline int check_frame_interval(struct v4l2_subdev *sd,
    211				       struct v4l2_subdev_frame_interval *fi)
    212{
    213	if (!fi)
    214		return -EINVAL;
    215
    216	return check_pad(sd, fi->pad);
    217}
    218
    219static int call_g_frame_interval(struct v4l2_subdev *sd,
    220				 struct v4l2_subdev_frame_interval *fi)
    221{
    222	return check_frame_interval(sd, fi) ? :
    223	       sd->ops->video->g_frame_interval(sd, fi);
    224}
    225
    226static int call_s_frame_interval(struct v4l2_subdev *sd,
    227				 struct v4l2_subdev_frame_interval *fi)
    228{
    229	return check_frame_interval(sd, fi) ? :
    230	       sd->ops->video->s_frame_interval(sd, fi);
    231}
    232
    233static int call_enum_frame_interval(struct v4l2_subdev *sd,
    234				    struct v4l2_subdev_state *state,
    235				    struct v4l2_subdev_frame_interval_enum *fie)
    236{
    237	if (!fie)
    238		return -EINVAL;
    239
    240	return check_which(fie->which) ? : check_pad(sd, fie->pad) ? :
    241	       check_state_pads(fie->which, state) ? :
    242	       sd->ops->pad->enum_frame_interval(sd, state, fie);
    243}
    244
    245static inline int check_selection(struct v4l2_subdev *sd,
    246				  struct v4l2_subdev_state *state,
    247				  struct v4l2_subdev_selection *sel)
    248{
    249	if (!sel)
    250		return -EINVAL;
    251
    252	return check_which(sel->which) ? : check_pad(sd, sel->pad) ? :
    253	       check_state_pads(sel->which, state);
    254}
    255
    256static int call_get_selection(struct v4l2_subdev *sd,
    257			      struct v4l2_subdev_state *state,
    258			      struct v4l2_subdev_selection *sel)
    259{
    260	return check_selection(sd, state, sel) ? :
    261	       sd->ops->pad->get_selection(sd, state, sel);
    262}
    263
    264static int call_set_selection(struct v4l2_subdev *sd,
    265			      struct v4l2_subdev_state *state,
    266			      struct v4l2_subdev_selection *sel)
    267{
    268	return check_selection(sd, state, sel) ? :
    269	       sd->ops->pad->set_selection(sd, state, sel);
    270}
    271
    272static inline int check_edid(struct v4l2_subdev *sd,
    273			     struct v4l2_subdev_edid *edid)
    274{
    275	if (!edid)
    276		return -EINVAL;
    277
    278	if (edid->blocks && edid->edid == NULL)
    279		return -EINVAL;
    280
    281	return check_pad(sd, edid->pad);
    282}
    283
    284static int call_get_edid(struct v4l2_subdev *sd, struct v4l2_subdev_edid *edid)
    285{
    286	return check_edid(sd, edid) ? : sd->ops->pad->get_edid(sd, edid);
    287}
    288
    289static int call_set_edid(struct v4l2_subdev *sd, struct v4l2_subdev_edid *edid)
    290{
    291	return check_edid(sd, edid) ? : sd->ops->pad->set_edid(sd, edid);
    292}
    293
    294static int call_dv_timings_cap(struct v4l2_subdev *sd,
    295			       struct v4l2_dv_timings_cap *cap)
    296{
    297	if (!cap)
    298		return -EINVAL;
    299
    300	return check_pad(sd, cap->pad) ? :
    301	       sd->ops->pad->dv_timings_cap(sd, cap);
    302}
    303
    304static int call_enum_dv_timings(struct v4l2_subdev *sd,
    305				struct v4l2_enum_dv_timings *dvt)
    306{
    307	if (!dvt)
    308		return -EINVAL;
    309
    310	return check_pad(sd, dvt->pad) ? :
    311	       sd->ops->pad->enum_dv_timings(sd, dvt);
    312}
    313
    314static int call_get_mbus_config(struct v4l2_subdev *sd, unsigned int pad,
    315				struct v4l2_mbus_config *config)
    316{
    317	return check_pad(sd, pad) ? :
    318	       sd->ops->pad->get_mbus_config(sd, pad, config);
    319}
    320
    321#ifdef CONFIG_MEDIA_CONTROLLER
    322/*
    323 * Create state-management wrapper for pad ops dealing with subdev state. The
    324 * wrapper handles the case where the caller does not provide the called
    325 * subdev's state. This should be removed when all the callers are fixed.
    326 */
    327#define DEFINE_STATE_WRAPPER(f, arg_type)                                  \
    328	static int call_##f##_state(struct v4l2_subdev *sd,                \
    329				    struct v4l2_subdev_state *_state,      \
    330				    arg_type *arg)                         \
    331	{                                                                  \
    332		struct v4l2_subdev_state *state = _state;                  \
    333		int ret;                                                   \
    334		if (!_state)                                               \
    335			state = v4l2_subdev_lock_and_get_active_state(sd); \
    336		ret = call_##f(sd, state, arg);                            \
    337		if (!_state && state)                                      \
    338			v4l2_subdev_unlock_state(state);                   \
    339		return ret;                                                \
    340	}
    341
    342#else /* CONFIG_MEDIA_CONTROLLER */
    343
    344#define DEFINE_STATE_WRAPPER(f, arg_type)                            \
    345	static int call_##f##_state(struct v4l2_subdev *sd,          \
    346				    struct v4l2_subdev_state *state, \
    347				    arg_type *arg)                   \
    348	{                                                            \
    349		return call_##f(sd, state, arg);                     \
    350	}
    351
    352#endif /* CONFIG_MEDIA_CONTROLLER */
    353
    354DEFINE_STATE_WRAPPER(get_fmt, struct v4l2_subdev_format);
    355DEFINE_STATE_WRAPPER(set_fmt, struct v4l2_subdev_format);
    356DEFINE_STATE_WRAPPER(enum_mbus_code, struct v4l2_subdev_mbus_code_enum);
    357DEFINE_STATE_WRAPPER(enum_frame_size, struct v4l2_subdev_frame_size_enum);
    358DEFINE_STATE_WRAPPER(enum_frame_interval, struct v4l2_subdev_frame_interval_enum);
    359DEFINE_STATE_WRAPPER(get_selection, struct v4l2_subdev_selection);
    360DEFINE_STATE_WRAPPER(set_selection, struct v4l2_subdev_selection);
    361
    362static const struct v4l2_subdev_pad_ops v4l2_subdev_call_pad_wrappers = {
    363	.get_fmt		= call_get_fmt_state,
    364	.set_fmt		= call_set_fmt_state,
    365	.enum_mbus_code		= call_enum_mbus_code_state,
    366	.enum_frame_size	= call_enum_frame_size_state,
    367	.enum_frame_interval	= call_enum_frame_interval_state,
    368	.get_selection		= call_get_selection_state,
    369	.set_selection		= call_set_selection_state,
    370	.get_edid		= call_get_edid,
    371	.set_edid		= call_set_edid,
    372	.dv_timings_cap		= call_dv_timings_cap,
    373	.enum_dv_timings	= call_enum_dv_timings,
    374	.get_mbus_config	= call_get_mbus_config,
    375};
    376
    377static const struct v4l2_subdev_video_ops v4l2_subdev_call_video_wrappers = {
    378	.g_frame_interval	= call_g_frame_interval,
    379	.s_frame_interval	= call_s_frame_interval,
    380};
    381
    382const struct v4l2_subdev_ops v4l2_subdev_call_wrappers = {
    383	.pad	= &v4l2_subdev_call_pad_wrappers,
    384	.video	= &v4l2_subdev_call_video_wrappers,
    385};
    386EXPORT_SYMBOL(v4l2_subdev_call_wrappers);
    387
    388#if defined(CONFIG_VIDEO_V4L2_SUBDEV_API)
    389
    390static struct v4l2_subdev_state *
    391subdev_ioctl_get_state(struct v4l2_subdev *sd, struct v4l2_subdev_fh *subdev_fh,
    392		       unsigned int cmd, void *arg)
    393{
    394	u32 which;
    395
    396	switch (cmd) {
    397	default:
    398		return NULL;
    399	case VIDIOC_SUBDEV_G_FMT:
    400	case VIDIOC_SUBDEV_S_FMT:
    401		which = ((struct v4l2_subdev_format *)arg)->which;
    402		break;
    403	case VIDIOC_SUBDEV_G_CROP:
    404	case VIDIOC_SUBDEV_S_CROP:
    405		which = ((struct v4l2_subdev_crop *)arg)->which;
    406		break;
    407	case VIDIOC_SUBDEV_ENUM_MBUS_CODE:
    408		which = ((struct v4l2_subdev_mbus_code_enum *)arg)->which;
    409		break;
    410	case VIDIOC_SUBDEV_ENUM_FRAME_SIZE:
    411		which = ((struct v4l2_subdev_frame_size_enum *)arg)->which;
    412		break;
    413	case VIDIOC_SUBDEV_ENUM_FRAME_INTERVAL:
    414		which = ((struct v4l2_subdev_frame_interval_enum *)arg)->which;
    415		break;
    416	case VIDIOC_SUBDEV_G_SELECTION:
    417	case VIDIOC_SUBDEV_S_SELECTION:
    418		which = ((struct v4l2_subdev_selection *)arg)->which;
    419		break;
    420	}
    421
    422	return which == V4L2_SUBDEV_FORMAT_TRY ?
    423			     subdev_fh->state :
    424			     v4l2_subdev_get_unlocked_active_state(sd);
    425}
    426
    427static long subdev_do_ioctl(struct file *file, unsigned int cmd, void *arg,
    428			    struct v4l2_subdev_state *state)
    429{
    430	struct video_device *vdev = video_devdata(file);
    431	struct v4l2_subdev *sd = vdev_to_v4l2_subdev(vdev);
    432	struct v4l2_fh *vfh = file->private_data;
    433	bool ro_subdev = test_bit(V4L2_FL_SUBDEV_RO_DEVNODE, &vdev->flags);
    434	int rval;
    435
    436	switch (cmd) {
    437	case VIDIOC_SUBDEV_QUERYCAP: {
    438		struct v4l2_subdev_capability *cap = arg;
    439
    440		memset(cap->reserved, 0, sizeof(cap->reserved));
    441		cap->version = LINUX_VERSION_CODE;
    442		cap->capabilities = ro_subdev ? V4L2_SUBDEV_CAP_RO_SUBDEV : 0;
    443
    444		return 0;
    445	}
    446
    447	case VIDIOC_QUERYCTRL:
    448		/*
    449		 * TODO: this really should be folded into v4l2_queryctrl (this
    450		 * currently returns -EINVAL for NULL control handlers).
    451		 * However, v4l2_queryctrl() is still called directly by
    452		 * drivers as well and until that has been addressed I believe
    453		 * it is safer to do the check here. The same is true for the
    454		 * other control ioctls below.
    455		 */
    456		if (!vfh->ctrl_handler)
    457			return -ENOTTY;
    458		return v4l2_queryctrl(vfh->ctrl_handler, arg);
    459
    460	case VIDIOC_QUERY_EXT_CTRL:
    461		if (!vfh->ctrl_handler)
    462			return -ENOTTY;
    463		return v4l2_query_ext_ctrl(vfh->ctrl_handler, arg);
    464
    465	case VIDIOC_QUERYMENU:
    466		if (!vfh->ctrl_handler)
    467			return -ENOTTY;
    468		return v4l2_querymenu(vfh->ctrl_handler, arg);
    469
    470	case VIDIOC_G_CTRL:
    471		if (!vfh->ctrl_handler)
    472			return -ENOTTY;
    473		return v4l2_g_ctrl(vfh->ctrl_handler, arg);
    474
    475	case VIDIOC_S_CTRL:
    476		if (!vfh->ctrl_handler)
    477			return -ENOTTY;
    478		return v4l2_s_ctrl(vfh, vfh->ctrl_handler, arg);
    479
    480	case VIDIOC_G_EXT_CTRLS:
    481		if (!vfh->ctrl_handler)
    482			return -ENOTTY;
    483		return v4l2_g_ext_ctrls(vfh->ctrl_handler,
    484					vdev, sd->v4l2_dev->mdev, arg);
    485
    486	case VIDIOC_S_EXT_CTRLS:
    487		if (!vfh->ctrl_handler)
    488			return -ENOTTY;
    489		return v4l2_s_ext_ctrls(vfh, vfh->ctrl_handler,
    490					vdev, sd->v4l2_dev->mdev, arg);
    491
    492	case VIDIOC_TRY_EXT_CTRLS:
    493		if (!vfh->ctrl_handler)
    494			return -ENOTTY;
    495		return v4l2_try_ext_ctrls(vfh->ctrl_handler,
    496					  vdev, sd->v4l2_dev->mdev, arg);
    497
    498	case VIDIOC_DQEVENT:
    499		if (!(sd->flags & V4L2_SUBDEV_FL_HAS_EVENTS))
    500			return -ENOIOCTLCMD;
    501
    502		return v4l2_event_dequeue(vfh, arg, file->f_flags & O_NONBLOCK);
    503
    504	case VIDIOC_SUBSCRIBE_EVENT:
    505		return v4l2_subdev_call(sd, core, subscribe_event, vfh, arg);
    506
    507	case VIDIOC_UNSUBSCRIBE_EVENT:
    508		return v4l2_subdev_call(sd, core, unsubscribe_event, vfh, arg);
    509
    510#ifdef CONFIG_VIDEO_ADV_DEBUG
    511	case VIDIOC_DBG_G_REGISTER:
    512	{
    513		struct v4l2_dbg_register *p = arg;
    514
    515		if (!capable(CAP_SYS_ADMIN))
    516			return -EPERM;
    517		return v4l2_subdev_call(sd, core, g_register, p);
    518	}
    519	case VIDIOC_DBG_S_REGISTER:
    520	{
    521		struct v4l2_dbg_register *p = arg;
    522
    523		if (!capable(CAP_SYS_ADMIN))
    524			return -EPERM;
    525		return v4l2_subdev_call(sd, core, s_register, p);
    526	}
    527	case VIDIOC_DBG_G_CHIP_INFO:
    528	{
    529		struct v4l2_dbg_chip_info *p = arg;
    530
    531		if (p->match.type != V4L2_CHIP_MATCH_SUBDEV || p->match.addr)
    532			return -EINVAL;
    533		if (sd->ops->core && sd->ops->core->s_register)
    534			p->flags |= V4L2_CHIP_FL_WRITABLE;
    535		if (sd->ops->core && sd->ops->core->g_register)
    536			p->flags |= V4L2_CHIP_FL_READABLE;
    537		strscpy(p->name, sd->name, sizeof(p->name));
    538		return 0;
    539	}
    540#endif
    541
    542	case VIDIOC_LOG_STATUS: {
    543		int ret;
    544
    545		pr_info("%s: =================  START STATUS  =================\n",
    546			sd->name);
    547		ret = v4l2_subdev_call(sd, core, log_status);
    548		pr_info("%s: ==================  END STATUS  ==================\n",
    549			sd->name);
    550		return ret;
    551	}
    552
    553	case VIDIOC_SUBDEV_G_FMT: {
    554		struct v4l2_subdev_format *format = arg;
    555
    556		memset(format->reserved, 0, sizeof(format->reserved));
    557		memset(format->format.reserved, 0, sizeof(format->format.reserved));
    558		return v4l2_subdev_call(sd, pad, get_fmt, state, format);
    559	}
    560
    561	case VIDIOC_SUBDEV_S_FMT: {
    562		struct v4l2_subdev_format *format = arg;
    563
    564		if (format->which != V4L2_SUBDEV_FORMAT_TRY && ro_subdev)
    565			return -EPERM;
    566
    567		memset(format->reserved, 0, sizeof(format->reserved));
    568		memset(format->format.reserved, 0, sizeof(format->format.reserved));
    569		return v4l2_subdev_call(sd, pad, set_fmt, state, format);
    570	}
    571
    572	case VIDIOC_SUBDEV_G_CROP: {
    573		struct v4l2_subdev_crop *crop = arg;
    574		struct v4l2_subdev_selection sel;
    575
    576		memset(crop->reserved, 0, sizeof(crop->reserved));
    577		memset(&sel, 0, sizeof(sel));
    578		sel.which = crop->which;
    579		sel.pad = crop->pad;
    580		sel.target = V4L2_SEL_TGT_CROP;
    581
    582		rval = v4l2_subdev_call(
    583			sd, pad, get_selection, state, &sel);
    584
    585		crop->rect = sel.r;
    586
    587		return rval;
    588	}
    589
    590	case VIDIOC_SUBDEV_S_CROP: {
    591		struct v4l2_subdev_crop *crop = arg;
    592		struct v4l2_subdev_selection sel;
    593
    594		if (crop->which != V4L2_SUBDEV_FORMAT_TRY && ro_subdev)
    595			return -EPERM;
    596
    597		memset(crop->reserved, 0, sizeof(crop->reserved));
    598		memset(&sel, 0, sizeof(sel));
    599		sel.which = crop->which;
    600		sel.pad = crop->pad;
    601		sel.target = V4L2_SEL_TGT_CROP;
    602		sel.r = crop->rect;
    603
    604		rval = v4l2_subdev_call(
    605			sd, pad, set_selection, state, &sel);
    606
    607		crop->rect = sel.r;
    608
    609		return rval;
    610	}
    611
    612	case VIDIOC_SUBDEV_ENUM_MBUS_CODE: {
    613		struct v4l2_subdev_mbus_code_enum *code = arg;
    614
    615		memset(code->reserved, 0, sizeof(code->reserved));
    616		return v4l2_subdev_call(sd, pad, enum_mbus_code, state,
    617					code);
    618	}
    619
    620	case VIDIOC_SUBDEV_ENUM_FRAME_SIZE: {
    621		struct v4l2_subdev_frame_size_enum *fse = arg;
    622
    623		memset(fse->reserved, 0, sizeof(fse->reserved));
    624		return v4l2_subdev_call(sd, pad, enum_frame_size, state,
    625					fse);
    626	}
    627
    628	case VIDIOC_SUBDEV_G_FRAME_INTERVAL: {
    629		struct v4l2_subdev_frame_interval *fi = arg;
    630
    631		memset(fi->reserved, 0, sizeof(fi->reserved));
    632		return v4l2_subdev_call(sd, video, g_frame_interval, arg);
    633	}
    634
    635	case VIDIOC_SUBDEV_S_FRAME_INTERVAL: {
    636		struct v4l2_subdev_frame_interval *fi = arg;
    637
    638		if (ro_subdev)
    639			return -EPERM;
    640
    641		memset(fi->reserved, 0, sizeof(fi->reserved));
    642		return v4l2_subdev_call(sd, video, s_frame_interval, arg);
    643	}
    644
    645	case VIDIOC_SUBDEV_ENUM_FRAME_INTERVAL: {
    646		struct v4l2_subdev_frame_interval_enum *fie = arg;
    647
    648		memset(fie->reserved, 0, sizeof(fie->reserved));
    649		return v4l2_subdev_call(sd, pad, enum_frame_interval, state,
    650					fie);
    651	}
    652
    653	case VIDIOC_SUBDEV_G_SELECTION: {
    654		struct v4l2_subdev_selection *sel = arg;
    655
    656		memset(sel->reserved, 0, sizeof(sel->reserved));
    657		return v4l2_subdev_call(
    658			sd, pad, get_selection, state, sel);
    659	}
    660
    661	case VIDIOC_SUBDEV_S_SELECTION: {
    662		struct v4l2_subdev_selection *sel = arg;
    663
    664		if (sel->which != V4L2_SUBDEV_FORMAT_TRY && ro_subdev)
    665			return -EPERM;
    666
    667		memset(sel->reserved, 0, sizeof(sel->reserved));
    668		return v4l2_subdev_call(
    669			sd, pad, set_selection, state, sel);
    670	}
    671
    672	case VIDIOC_G_EDID: {
    673		struct v4l2_subdev_edid *edid = arg;
    674
    675		return v4l2_subdev_call(sd, pad, get_edid, edid);
    676	}
    677
    678	case VIDIOC_S_EDID: {
    679		struct v4l2_subdev_edid *edid = arg;
    680
    681		return v4l2_subdev_call(sd, pad, set_edid, edid);
    682	}
    683
    684	case VIDIOC_SUBDEV_DV_TIMINGS_CAP: {
    685		struct v4l2_dv_timings_cap *cap = arg;
    686
    687		return v4l2_subdev_call(sd, pad, dv_timings_cap, cap);
    688	}
    689
    690	case VIDIOC_SUBDEV_ENUM_DV_TIMINGS: {
    691		struct v4l2_enum_dv_timings *dvt = arg;
    692
    693		return v4l2_subdev_call(sd, pad, enum_dv_timings, dvt);
    694	}
    695
    696	case VIDIOC_SUBDEV_QUERY_DV_TIMINGS:
    697		return v4l2_subdev_call(sd, video, query_dv_timings, arg);
    698
    699	case VIDIOC_SUBDEV_G_DV_TIMINGS:
    700		return v4l2_subdev_call(sd, video, g_dv_timings, arg);
    701
    702	case VIDIOC_SUBDEV_S_DV_TIMINGS:
    703		if (ro_subdev)
    704			return -EPERM;
    705
    706		return v4l2_subdev_call(sd, video, s_dv_timings, arg);
    707
    708	case VIDIOC_SUBDEV_G_STD:
    709		return v4l2_subdev_call(sd, video, g_std, arg);
    710
    711	case VIDIOC_SUBDEV_S_STD: {
    712		v4l2_std_id *std = arg;
    713
    714		if (ro_subdev)
    715			return -EPERM;
    716
    717		return v4l2_subdev_call(sd, video, s_std, *std);
    718	}
    719
    720	case VIDIOC_SUBDEV_ENUMSTD: {
    721		struct v4l2_standard *p = arg;
    722		v4l2_std_id id;
    723
    724		if (v4l2_subdev_call(sd, video, g_tvnorms, &id))
    725			return -EINVAL;
    726
    727		return v4l_video_std_enumstd(p, id);
    728	}
    729
    730	case VIDIOC_SUBDEV_QUERYSTD:
    731		return v4l2_subdev_call(sd, video, querystd, arg);
    732
    733	default:
    734		return v4l2_subdev_call(sd, core, ioctl, cmd, arg);
    735	}
    736
    737	return 0;
    738}
    739
    740static long subdev_do_ioctl_lock(struct file *file, unsigned int cmd, void *arg)
    741{
    742	struct video_device *vdev = video_devdata(file);
    743	struct mutex *lock = vdev->lock;
    744	long ret = -ENODEV;
    745
    746	if (lock && mutex_lock_interruptible(lock))
    747		return -ERESTARTSYS;
    748
    749	if (video_is_registered(vdev)) {
    750		struct v4l2_subdev *sd = vdev_to_v4l2_subdev(vdev);
    751		struct v4l2_fh *vfh = file->private_data;
    752		struct v4l2_subdev_fh *subdev_fh = to_v4l2_subdev_fh(vfh);
    753		struct v4l2_subdev_state *state;
    754
    755		state = subdev_ioctl_get_state(sd, subdev_fh, cmd, arg);
    756
    757		if (state)
    758			v4l2_subdev_lock_state(state);
    759
    760		ret = subdev_do_ioctl(file, cmd, arg, state);
    761
    762		if (state)
    763			v4l2_subdev_unlock_state(state);
    764	}
    765
    766	if (lock)
    767		mutex_unlock(lock);
    768	return ret;
    769}
    770
    771static long subdev_ioctl(struct file *file, unsigned int cmd,
    772	unsigned long arg)
    773{
    774	return video_usercopy(file, cmd, arg, subdev_do_ioctl_lock);
    775}
    776
    777#ifdef CONFIG_COMPAT
    778static long subdev_compat_ioctl32(struct file *file, unsigned int cmd,
    779	unsigned long arg)
    780{
    781	struct video_device *vdev = video_devdata(file);
    782	struct v4l2_subdev *sd = vdev_to_v4l2_subdev(vdev);
    783
    784	return v4l2_subdev_call(sd, core, compat_ioctl32, cmd, arg);
    785}
    786#endif
    787
    788#else /* CONFIG_VIDEO_V4L2_SUBDEV_API */
    789static long subdev_ioctl(struct file *file, unsigned int cmd,
    790			 unsigned long arg)
    791{
    792	return -ENODEV;
    793}
    794
    795#ifdef CONFIG_COMPAT
    796static long subdev_compat_ioctl32(struct file *file, unsigned int cmd,
    797				  unsigned long arg)
    798{
    799	return -ENODEV;
    800}
    801#endif
    802#endif /* CONFIG_VIDEO_V4L2_SUBDEV_API */
    803
    804static __poll_t subdev_poll(struct file *file, poll_table *wait)
    805{
    806	struct video_device *vdev = video_devdata(file);
    807	struct v4l2_subdev *sd = vdev_to_v4l2_subdev(vdev);
    808	struct v4l2_fh *fh = file->private_data;
    809
    810	if (!(sd->flags & V4L2_SUBDEV_FL_HAS_EVENTS))
    811		return EPOLLERR;
    812
    813	poll_wait(file, &fh->wait, wait);
    814
    815	if (v4l2_event_pending(fh))
    816		return EPOLLPRI;
    817
    818	return 0;
    819}
    820
    821const struct v4l2_file_operations v4l2_subdev_fops = {
    822	.owner = THIS_MODULE,
    823	.open = subdev_open,
    824	.unlocked_ioctl = subdev_ioctl,
    825#ifdef CONFIG_COMPAT
    826	.compat_ioctl32 = subdev_compat_ioctl32,
    827#endif
    828	.release = subdev_close,
    829	.poll = subdev_poll,
    830};
    831
    832#ifdef CONFIG_MEDIA_CONTROLLER
    833
    834int v4l2_subdev_get_fwnode_pad_1_to_1(struct media_entity *entity,
    835				      struct fwnode_endpoint *endpoint)
    836{
    837	struct fwnode_handle *fwnode;
    838	struct v4l2_subdev *sd;
    839
    840	if (!is_media_entity_v4l2_subdev(entity))
    841		return -EINVAL;
    842
    843	sd = media_entity_to_v4l2_subdev(entity);
    844
    845	fwnode = fwnode_graph_get_port_parent(endpoint->local_fwnode);
    846	fwnode_handle_put(fwnode);
    847
    848	if (dev_fwnode(sd->dev) == fwnode)
    849		return endpoint->port;
    850
    851	return -ENXIO;
    852}
    853EXPORT_SYMBOL_GPL(v4l2_subdev_get_fwnode_pad_1_to_1);
    854
    855int v4l2_subdev_link_validate_default(struct v4l2_subdev *sd,
    856				      struct media_link *link,
    857				      struct v4l2_subdev_format *source_fmt,
    858				      struct v4l2_subdev_format *sink_fmt)
    859{
    860	bool pass = true;
    861
    862	/* The width, height and code must match. */
    863	if (source_fmt->format.width != sink_fmt->format.width) {
    864		dev_dbg(sd->entity.graph_obj.mdev->dev,
    865			"%s: width does not match (source %u, sink %u)\n",
    866			__func__,
    867			source_fmt->format.width, sink_fmt->format.width);
    868		pass = false;
    869	}
    870
    871	if (source_fmt->format.height != sink_fmt->format.height) {
    872		dev_dbg(sd->entity.graph_obj.mdev->dev,
    873			"%s: height does not match (source %u, sink %u)\n",
    874			__func__,
    875			source_fmt->format.height, sink_fmt->format.height);
    876		pass = false;
    877	}
    878
    879	if (source_fmt->format.code != sink_fmt->format.code) {
    880		dev_dbg(sd->entity.graph_obj.mdev->dev,
    881			"%s: media bus code does not match (source 0x%8.8x, sink 0x%8.8x)\n",
    882			__func__,
    883			source_fmt->format.code, sink_fmt->format.code);
    884		pass = false;
    885	}
    886
    887	/* The field order must match, or the sink field order must be NONE
    888	 * to support interlaced hardware connected to bridges that support
    889	 * progressive formats only.
    890	 */
    891	if (source_fmt->format.field != sink_fmt->format.field &&
    892	    sink_fmt->format.field != V4L2_FIELD_NONE) {
    893		dev_dbg(sd->entity.graph_obj.mdev->dev,
    894			"%s: field does not match (source %u, sink %u)\n",
    895			__func__,
    896			source_fmt->format.field, sink_fmt->format.field);
    897		pass = false;
    898	}
    899
    900	if (pass)
    901		return 0;
    902
    903	dev_dbg(sd->entity.graph_obj.mdev->dev,
    904		"%s: link was \"%s\":%u -> \"%s\":%u\n", __func__,
    905		link->source->entity->name, link->source->index,
    906		link->sink->entity->name, link->sink->index);
    907
    908	return -EPIPE;
    909}
    910EXPORT_SYMBOL_GPL(v4l2_subdev_link_validate_default);
    911
    912static int
    913v4l2_subdev_link_validate_get_format(struct media_pad *pad,
    914				     struct v4l2_subdev_format *fmt)
    915{
    916	if (is_media_entity_v4l2_subdev(pad->entity)) {
    917		struct v4l2_subdev *sd =
    918			media_entity_to_v4l2_subdev(pad->entity);
    919
    920		fmt->which = V4L2_SUBDEV_FORMAT_ACTIVE;
    921		fmt->pad = pad->index;
    922		return v4l2_subdev_call_state_active(sd, pad, get_fmt, fmt);
    923	}
    924
    925	WARN(pad->entity->function != MEDIA_ENT_F_IO_V4L,
    926	     "Driver bug! Wrong media entity type 0x%08x, entity %s\n",
    927	     pad->entity->function, pad->entity->name);
    928
    929	return -EINVAL;
    930}
    931
    932int v4l2_subdev_link_validate(struct media_link *link)
    933{
    934	struct v4l2_subdev *sink;
    935	struct v4l2_subdev_format sink_fmt, source_fmt;
    936	int rval;
    937
    938	rval = v4l2_subdev_link_validate_get_format(
    939		link->source, &source_fmt);
    940	if (rval < 0)
    941		return 0;
    942
    943	rval = v4l2_subdev_link_validate_get_format(
    944		link->sink, &sink_fmt);
    945	if (rval < 0)
    946		return 0;
    947
    948	sink = media_entity_to_v4l2_subdev(link->sink->entity);
    949
    950	rval = v4l2_subdev_call(sink, pad, link_validate, link,
    951				&source_fmt, &sink_fmt);
    952	if (rval != -ENOIOCTLCMD)
    953		return rval;
    954
    955	return v4l2_subdev_link_validate_default(
    956		sink, link, &source_fmt, &sink_fmt);
    957}
    958EXPORT_SYMBOL_GPL(v4l2_subdev_link_validate);
    959
    960struct v4l2_subdev_state *
    961__v4l2_subdev_state_alloc(struct v4l2_subdev *sd, const char *lock_name,
    962			  struct lock_class_key *lock_key)
    963{
    964	struct v4l2_subdev_state *state;
    965	int ret;
    966
    967	state = kzalloc(sizeof(*state), GFP_KERNEL);
    968	if (!state)
    969		return ERR_PTR(-ENOMEM);
    970
    971	__mutex_init(&state->_lock, lock_name, lock_key);
    972	if (sd->state_lock)
    973		state->lock = sd->state_lock;
    974	else
    975		state->lock = &state->_lock;
    976
    977	if (sd->entity.num_pads) {
    978		state->pads = kvcalloc(sd->entity.num_pads,
    979				       sizeof(*state->pads), GFP_KERNEL);
    980		if (!state->pads) {
    981			ret = -ENOMEM;
    982			goto err;
    983		}
    984	}
    985
    986	/*
    987	 * There can be no race at this point, but we lock the state anyway to
    988	 * satisfy lockdep checks.
    989	 */
    990	v4l2_subdev_lock_state(state);
    991	ret = v4l2_subdev_call(sd, pad, init_cfg, state);
    992	v4l2_subdev_unlock_state(state);
    993
    994	if (ret < 0 && ret != -ENOIOCTLCMD)
    995		goto err;
    996
    997	return state;
    998
    999err:
   1000	if (state && state->pads)
   1001		kvfree(state->pads);
   1002
   1003	kfree(state);
   1004
   1005	return ERR_PTR(ret);
   1006}
   1007EXPORT_SYMBOL_GPL(__v4l2_subdev_state_alloc);
   1008
   1009void __v4l2_subdev_state_free(struct v4l2_subdev_state *state)
   1010{
   1011	if (!state)
   1012		return;
   1013
   1014	mutex_destroy(&state->_lock);
   1015
   1016	kvfree(state->pads);
   1017	kfree(state);
   1018}
   1019EXPORT_SYMBOL_GPL(__v4l2_subdev_state_free);
   1020
   1021int __v4l2_subdev_init_finalize(struct v4l2_subdev *sd, const char *name,
   1022				struct lock_class_key *key)
   1023{
   1024	struct v4l2_subdev_state *state;
   1025
   1026	state = __v4l2_subdev_state_alloc(sd, name, key);
   1027	if (IS_ERR(state))
   1028		return PTR_ERR(state);
   1029
   1030	sd->active_state = state;
   1031
   1032	return 0;
   1033}
   1034EXPORT_SYMBOL_GPL(__v4l2_subdev_init_finalize);
   1035
   1036void v4l2_subdev_cleanup(struct v4l2_subdev *sd)
   1037{
   1038	__v4l2_subdev_state_free(sd->active_state);
   1039	sd->active_state = NULL;
   1040}
   1041EXPORT_SYMBOL_GPL(v4l2_subdev_cleanup);
   1042
   1043#if defined(CONFIG_VIDEO_V4L2_SUBDEV_API)
   1044
   1045int v4l2_subdev_get_fmt(struct v4l2_subdev *sd, struct v4l2_subdev_state *state,
   1046			struct v4l2_subdev_format *format)
   1047{
   1048	struct v4l2_mbus_framefmt *fmt;
   1049
   1050	if (format->pad >= sd->entity.num_pads)
   1051		return -EINVAL;
   1052
   1053	fmt = v4l2_subdev_get_pad_format(sd, state, format->pad);
   1054	if (!fmt)
   1055		return -EINVAL;
   1056
   1057	format->format = *fmt;
   1058
   1059	return 0;
   1060}
   1061EXPORT_SYMBOL_GPL(v4l2_subdev_get_fmt);
   1062
   1063#endif /* CONFIG_VIDEO_V4L2_SUBDEV_API */
   1064
   1065#endif /* CONFIG_MEDIA_CONTROLLER */
   1066
   1067void v4l2_subdev_init(struct v4l2_subdev *sd, const struct v4l2_subdev_ops *ops)
   1068{
   1069	INIT_LIST_HEAD(&sd->list);
   1070	BUG_ON(!ops);
   1071	sd->ops = ops;
   1072	sd->v4l2_dev = NULL;
   1073	sd->flags = 0;
   1074	sd->name[0] = '\0';
   1075	sd->grp_id = 0;
   1076	sd->dev_priv = NULL;
   1077	sd->host_priv = NULL;
   1078#if defined(CONFIG_MEDIA_CONTROLLER)
   1079	sd->entity.name = sd->name;
   1080	sd->entity.obj_type = MEDIA_ENTITY_TYPE_V4L2_SUBDEV;
   1081	sd->entity.function = MEDIA_ENT_F_V4L2_SUBDEV_UNKNOWN;
   1082#endif
   1083}
   1084EXPORT_SYMBOL(v4l2_subdev_init);
   1085
   1086void v4l2_subdev_notify_event(struct v4l2_subdev *sd,
   1087			      const struct v4l2_event *ev)
   1088{
   1089	v4l2_event_queue(sd->devnode, ev);
   1090	v4l2_subdev_notify(sd, V4L2_DEVICE_NOTIFY_EVENT, (void *)ev);
   1091}
   1092EXPORT_SYMBOL_GPL(v4l2_subdev_notify_event);