Page MenuHomeFreeBSD

D7496.diff
No OneTemporary

D7496.diff

Index: sys/dev/drm2/drmP.h
===================================================================
--- sys/dev/drm2/drmP.h
+++ sys/dev/drm2/drmP.h
@@ -418,6 +418,9 @@
int event_space;
struct drm_prime_file_private prime;
+
+ struct selinfo kevent_selinfo;
+ struct mtx kevent_mtx;
};
/**
@@ -1195,6 +1198,7 @@
int drm_mmap_single(struct cdev *kdev, vm_ooffset_t *offset,
vm_size_t size, struct vm_object **obj_res, int nprot);
d_poll_t drm_poll;
+int drm_kqfilter(struct cdev *kdev, struct knote *kn);
/* Memory management support (drm_memory.h) */
extern void drm_free_agp(DRM_AGP_MEM * handle, int pages);
Index: sys/dev/drm2/drm_fops.c
===================================================================
--- sys/dev/drm2/drm_fops.c
+++ sys/dev/drm2/drm_fops.c
@@ -207,6 +207,9 @@
INIT_LIST_HEAD(&priv->event_list);
priv->event_space = 4096; /* set aside 4k for event buffer */
+ mtx_init(&priv->kevent_mtx, "drm kevent lock", NULL, MTX_DEF);
+ knlist_init_mtx(&priv->kevent_selinfo.si_note, &priv->kevent_mtx);
+
if (dev->driver->driver_features & DRIVER_GEM)
drm_gem_open(dev, priv);
@@ -552,6 +555,10 @@
wakeup(&file_priv->event_space);
selwakeup(&file_priv->event_poll);
+
+ mtx_lock(&file_priv->kevent_mtx);
+ KNOTE_LOCKED(&file_priv->kevent_selinfo.si_note, 1);
+ mtx_unlock(&file_priv->kevent_mtx);
}
int
@@ -601,3 +608,69 @@
return (ENODEV);
}
}
+
+static void
+drm_kqfilter_detach(struct knote *kn)
+{
+ struct drm_file *file_priv = kn->kn_hook;
+ knlist_remove(&file_priv->kevent_selinfo.si_note, kn, 0);
+}
+
+static int
+drm_kqfilter_read(struct knote *kn, long hint)
+{
+ struct drm_file *file_priv = kn->kn_hook;
+ struct drm_device *dev = file_priv->minor->dev;
+ struct drm_pending_event *e = NULL;
+ struct drm_pending_event *et = NULL;
+ ssize_t ret = 0;
+ mtx_lock(&dev->event_lock);
+ list_for_each_entry_safe(e, et, &file_priv->event_list, link) {
+ ret += e->event->length;
+ }
+ mtx_unlock(&dev->event_lock);
+ kn->kn_data = ret;
+ return (ret > 0);
+}
+
+static struct filterops drm_kqfiltops_read = {
+ .f_isfd = 1,
+ .f_detach = drm_kqfilter_detach,
+ .f_event = drm_kqfilter_read,
+};
+
+int
+drm_kqfilter(struct cdev *kdev, struct knote *kn)
+{
+ struct drm_file *file_priv;
+ struct drm_device *dev;
+ int error;
+
+ error = devfs_get_cdevpriv((void **)&file_priv);
+ if (error != 0) {
+ DRM_ERROR("can't find authenticator\n");
+ return (EINVAL);
+ }
+
+ dev = drm_get_device_from_kdev(kdev);
+
+ switch (kn->kn_filter) {
+ case EVFILT_READ:
+ kn->kn_fop = &drm_kqfiltops_read;
+ error = 0;
+ break;
+ default:
+ error = EOPNOTSUPP;
+ break;
+ }
+
+ if (error == 0) {
+ mtx_lock(&file_priv->kevent_mtx);
+ kn->kn_hook = file_priv;
+ knlist_add(&file_priv->kevent_selinfo.si_note, kn, 1);
+ mtx_unlock(&file_priv->kevent_mtx);
+ }
+
+ return (error);
+}
+EXPORT_SYMBOL(drm_kqfilter);
Index: sys/dev/drm2/drm_stub.c
===================================================================
--- sys/dev/drm2/drm_stub.c
+++ sys/dev/drm2/drm_stub.c
@@ -80,7 +80,8 @@
.d_poll = drm_poll,
.d_mmap_single = drm_mmap_single,
.d_name = "drm",
- .d_flags = D_TRACKCLOSE
+ .d_flags = D_TRACKCLOSE,
+ .d_kqfilter = drm_kqfilter,
};
static int drm_minor_get_id(struct drm_device *dev, int type)

File Metadata

Mime Type
text/plain
Expires
Wed, Mar 12, 3:44 PM (10 h, 56 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
17122105
Default Alt Text
D7496.diff (3 KB)

Event Timeline