return 0;
 }
 EXPORT_SYMBOL(v4l2_ctrl_log_status);
+
+int v4l2_ctrl_subscribe_event(struct v4l2_fh *fh,
+                               struct v4l2_event_subscription *sub)
+{
+       if (sub->type == V4L2_EVENT_CTRL)
+               return v4l2_event_subscribe(fh, sub, 0);
+       return -EINVAL;
+}
+EXPORT_SYMBOL(v4l2_ctrl_subscribe_event);
+
+unsigned int v4l2_ctrl_poll(struct file *file, struct poll_table_struct *wait)
+{
+       struct v4l2_fh *fh = file->private_data;
+
+       if (v4l2_event_pending(fh))
+               return POLLPRI;
+       poll_wait(file, &fh->wait, wait);
+       return 0;
+}
+EXPORT_SYMBOL(v4l2_ctrl_poll);
 
 struct v4l2_subdev;
 struct v4l2_subscribed_event;
 struct v4l2_fh;
+struct poll_table_struct;
 
 /** struct v4l2_ctrl_ops - The control operations that the driver has to provide.
   * @g_volatile_ctrl: Get a new value for this control. Generally only relevant
    associated with the filehandle. */
 int v4l2_ctrl_log_status(struct file *file, void *fh);
 
+/* Can be used as a vidioc_subscribe_event function that just subscribes
+   control events. */
+int v4l2_ctrl_subscribe_event(struct v4l2_fh *fh,
+                               struct v4l2_event_subscription *sub);
+
+/* Can be used as a poll function that just polls for control events. */
+unsigned int v4l2_ctrl_poll(struct file *file, struct poll_table_struct *wait);
+
 /* Helpers for ioctl_ops. If hdl == NULL then they will all return -EINVAL. */
 int v4l2_queryctrl(struct v4l2_ctrl_handler *hdl, struct v4l2_queryctrl *qc);
 int v4l2_querymenu(struct v4l2_ctrl_handler *hdl, struct v4l2_querymenu *qm);