`drmread_filtops' conversion is easy, because `event_lock' mutex(9) is
already to protect events list, so use to protect `drmread_filtops' too.

`drm_filtops' is little bit difficult. It only requires to protect
knote(9) data, but it's not clean to me which existing lock to use. I
introduces new `note_mtx' mutex(9) to 'drm_device' structure for
protection.

klist_invalidate() seems not be required for `drm_filtops', but I could
be wrong here.

Kernel events layer is not synchronized with Linux, so I see no reason
to use custom klistops with spinlock wrappers.

I have no radeondrm(4), tested only with inteldrm(4). Please test this
diff with radeondrm(4) too.

Index: sys/dev/pci/drm/drm_connector.c
===================================================================
RCS file: /cvs/src/sys/dev/pci/drm/drm_connector.c,v
retrieving revision 1.10
diff -u -p -r1.10 drm_connector.c
--- sys/dev/pci/drm/drm_connector.c     10 Feb 2023 14:34:16 -0000      1.10
+++ sys/dev/pci/drm/drm_connector.c     7 Oct 2023 13:41:40 -0000
@@ -2590,7 +2590,7 @@ int drm_connector_set_obj_prop(struct dr
        } else if (property == connector->backlight_property) {
                connector->backlight_device->props.brightness = value;
                backlight_schedule_update_status(connector->backlight_device);
-               knote_locked(&connector->dev->note, NOTE_CHANGE);
+               knote(&connector->dev->note, NOTE_CHANGE);
                ret = 0;
 #endif
        } else if (connector->funcs->set_property)
Index: sys/dev/pci/drm/drm_drv.c
===================================================================
RCS file: /cvs/src/sys/dev/pci/drm/drm_drv.c,v
retrieving revision 1.187
diff -u -p -r1.187 drm_drv.c
--- sys/dev/pci/drm/drm_drv.c   26 Jul 2023 11:04:07 -0000      1.187
+++ sys/dev/pci/drm/drm_drv.c   7 Oct 2023 13:41:40 -0000
@@ -1366,6 +1366,9 @@ drm_attach(struct device *parent, struct
 #endif
        }
 
+       mtx_init(&dev->note_mtx, IPL_MPFLOOR);
+       klist_init_mutex(&dev->note, &dev->note_mtx);
+
        mtx_init(&dev->quiesce_mtx, IPL_NONE);
        mtx_init(&dev->event_lock, IPL_TTY);
        rw_init(&dev->struct_mutex, "drmdevlk");
@@ -1577,11 +1580,8 @@ void
 filt_drmdetach(struct knote *kn)
 {
        struct drm_device *dev = kn->kn_hook;
-       int s;
 
-       s = spltty();
-       klist_remove_locked(&dev->note, kn);
-       splx(s);
+       klist_remove(&dev->note, kn);
 }
 
 int
@@ -1592,43 +1592,90 @@ filt_drmkms(struct knote *kn, long hint)
        return (kn->kn_fflags != 0);
 }
 
+int
+filt_drmmodify(struct kevent *kev, struct knote *kn)
+{
+       struct drm_device *dev = kn->kn_hook;
+       int active;
+
+       mtx_enter(&dev->note_mtx);
+       active = knote_modify(kev, kn);
+       mtx_leave(&dev->note_mtx);
+
+       return (active);
+}
+
+int
+filt_drmprocess(struct knote *kn, struct kevent *kev)
+{
+       struct drm_device *dev = kn->kn_hook;
+       int active;
+
+       mtx_enter(&dev->note_mtx);
+       active = knote_process(kn, kev); 
+       mtx_leave(&dev->note_mtx);
+
+       return (active);
+}
+
 void
 filt_drmreaddetach(struct knote *kn)
 {
        struct drm_file         *file_priv = kn->kn_hook;
-       int s;
 
-       s = spltty();
-       klist_remove_locked(&file_priv->rsel.si_note, kn);
-       splx(s);
+       klist_remove(&file_priv->rklist, kn);
 }
 
 int
 filt_drmread(struct knote *kn, long hint)
 {
        struct drm_file         *file_priv = kn->kn_hook;
-       int                      val = 0;
 
-       if ((hint & NOTE_SUBMIT) == 0)
-               mtx_enter(&file_priv->minor->dev->event_lock);
-       val = !list_empty(&file_priv->event_list);
-       if ((hint & NOTE_SUBMIT) == 0)
-               mtx_leave(&file_priv->minor->dev->event_lock);
-       return (val);
+       return (!list_empty(&file_priv->event_list));
+}
+
+int
+filt_drmreadmodify(struct kevent *kev, struct knote *kn)
+{
+       struct drm_file         *file_priv = kn->kn_hook;
+       int                      active;
+
+       mtx_enter(&file_priv->minor->dev->event_lock);
+       active = knote_modify(kev, kn);
+       mtx_leave(&file_priv->minor->dev->event_lock);
+
+       return (active);
+}
+
+int
+filt_drmreadprocess(struct knote *kn, struct kevent *kev)
+{
+       struct drm_file         *file_priv = kn->kn_hook;
+       int                      active;
+
+       mtx_enter(&file_priv->minor->dev->event_lock);
+       active = knote_process(kn, kev); 
+       mtx_leave(&file_priv->minor->dev->event_lock);
+
+       return (active);
 }
 
 const struct filterops drm_filtops = {
-       .f_flags        = FILTEROP_ISFD,
+       .f_flags        = FILTEROP_ISFD | FILTEROP_MPSAFE,
        .f_attach       = NULL,
        .f_detach       = filt_drmdetach,
        .f_event        = filt_drmkms,
+       .f_modify       = filt_drmmodify,
+       .f_process      = filt_drmprocess,
 };
 
 const struct filterops drmread_filtops = {
-       .f_flags        = FILTEROP_ISFD,
+       .f_flags        = FILTEROP_ISFD | FILTEROP_MPSAFE,
        .f_attach       = NULL,
        .f_detach       = filt_drmreaddetach,
        .f_event        = filt_drmread,
+       .f_modify       = filt_drmreadmodify,
+       .f_process      = filt_drmreadprocess,
 };
 
 int
@@ -1653,17 +1700,13 @@ drmkqfilter(dev_t kdev, struct knote *kn
                kn->kn_fop = &drmread_filtops;
                kn->kn_hook = file_priv;
 
-               s = spltty();
-               klist_insert_locked(&file_priv->rsel.si_note, kn);
-               splx(s);
+               klist_insert(&file_priv->rklist, kn);
                break;
        case EVFILT_DEVICE:
                kn->kn_fop = &drm_filtops;
                kn->kn_hook = dev;
 
-               s = spltty();
-               klist_insert_locked(&dev->note, kn);
-               splx(s);
+               klist_insert(&dev->note, kn);
                break;
        default:
                return (EINVAL);
Index: sys/dev/pci/drm/drm_file.c
===================================================================
RCS file: /cvs/src/sys/dev/pci/drm/drm_file.c,v
retrieving revision 1.9
diff -u -p -r1.9 drm_file.c
--- sys/dev/pci/drm/drm_file.c  1 Jan 2023 01:34:33 -0000       1.9
+++ sys/dev/pci/drm/drm_file.c  7 Oct 2023 13:41:40 -0000
@@ -176,6 +176,8 @@ struct drm_file *drm_file_alloc(struct d
        mtx_init(&file->master_lookup_lock, IPL_NONE);
        rw_init(&file->event_read_lock, "evread");
 
+       klist_init_mutex(&file->rklist, &dev->event_lock);
+
        if (drm_core_check_feature(dev, DRIVER_GEM))
                drm_gem_open(dev, file);
 
@@ -272,6 +274,9 @@ void drm_file_free(struct drm_file *file
 
        drm_events_release(file);
 
+       klist_invalidate(&file->rklist);
+       klist_free(&file->rklist);
+
        if (drm_core_check_feature(dev, DRIVER_MODESET)) {
                drm_fb_release(file);
                drm_property_destroy_user_blobs(dev, file);
@@ -829,7 +834,7 @@ static void drm_send_event_helper(struct
        wake_up_interruptible_poll(&e->file_priv->event_wait,
                EPOLLIN | EPOLLRDNORM);
 #ifdef __OpenBSD__
-       selwakeup(&e->file_priv->rsel);
+       knote_locked(&e->file_priv->rklist, 0);
 #endif
 }
 
Index: sys/dev/pci/drm/drm_linux.c
===================================================================
RCS file: /cvs/src/sys/dev/pci/drm/drm_linux.c,v
retrieving revision 1.103
diff -u -p -r1.103 drm_linux.c
--- sys/dev/pci/drm/drm_linux.c 4 Aug 2023 09:36:28 -0000       1.103
+++ sys/dev/pci/drm/drm_linux.c 7 Oct 2023 13:41:40 -0000
@@ -1569,13 +1569,13 @@ backlight_disable(struct backlight_devic
 void
 drm_sysfs_hotplug_event(struct drm_device *dev)
 {
-       knote_locked(&dev->note, NOTE_CHANGE);
+       knote(&dev->note, NOTE_CHANGE);
 }
 
 void
 drm_sysfs_connector_hotplug_event(struct drm_connector *connector)
 {
-       knote_locked(&connector->dev->note, NOTE_CHANGE);
+       knote(&connector->dev->note, NOTE_CHANGE);
 }
 
 void
Index: sys/dev/pci/drm/drm_mode_object.c
===================================================================
RCS file: /cvs/src/sys/dev/pci/drm/drm_mode_object.c,v
retrieving revision 1.7
diff -u -p -r1.7 drm_mode_object.c
--- sys/dev/pci/drm/drm_mode_object.c   10 Feb 2023 14:34:17 -0000      1.7
+++ sys/dev/pci/drm/drm_mode_object.c   7 Oct 2023 13:41:40 -0000
@@ -561,7 +561,7 @@ retry:
                struct drm_connector *connector = obj_to_connector(obj);
                connector->backlight_device->props.brightness = prop_value;
                backlight_schedule_update_status(connector->backlight_device);
-               knote_locked(&connector->dev->note, NOTE_CHANGE);
+               knote(&connector->dev->note, NOTE_CHANGE);
                ret = 0;
 #endif
        } else {
Index: sys/dev/pci/drm/amd/amdgpu/amdgpu_drv.c
===================================================================
RCS file: /cvs/src/sys/dev/pci/drm/amd/amdgpu/amdgpu_drv.c,v
retrieving revision 1.34
diff -u -p -r1.34 amdgpu_drv.c
--- sys/dev/pci/drm/amd/amdgpu/amdgpu_drv.c     10 Sep 2023 06:25:09 -0000      
1.34
+++ sys/dev/pci/drm/amd/amdgpu/amdgpu_drv.c     7 Oct 2023 13:41:40 -0000
@@ -3345,7 +3345,7 @@ amdgpu_wsioctl(void *v, u_long cmd, cadd
                case WSDISPLAYIO_PARAM_BRIGHTNESS:
                        bd->props.brightness = dp->curval;
                        backlight_update_status(bd);
-                       knote_locked(&adev->ddev.note, NOTE_CHANGE);
+                       knote(&adev->ddev.note, NOTE_CHANGE);
                        return 0;
                }
                break;
Index: sys/dev/pci/drm/i915/i915_driver.c
===================================================================
RCS file: /cvs/src/sys/dev/pci/drm/i915/i915_driver.c,v
retrieving revision 1.6
diff -u -p -r1.6 i915_driver.c
--- sys/dev/pci/drm/i915/i915_driver.c  10 Sep 2023 06:25:09 -0000      1.6
+++ sys/dev/pci/drm/i915/i915_driver.c  7 Oct 2023 13:41:41 -0000
@@ -2252,7 +2252,7 @@ inteldrm_wsioctl(void *v, u_long cmd, ca
                case WSDISPLAYIO_PARAM_BRIGHTNESS:
                        bd->props.brightness = dp->curval;
                        backlight_update_status(bd);
-                       knote_locked(&dev_priv->drm.note, NOTE_CHANGE);
+                       knote(&dev_priv->drm.note, NOTE_CHANGE);
                        return 0;
                }
                break;
Index: sys/dev/pci/drm/include/drm/drm_device.h
===================================================================
RCS file: /cvs/src/sys/dev/pci/drm/include/drm/drm_device.h,v
retrieving revision 1.9
diff -u -p -r1.9 drm_device.h
--- sys/dev/pci/drm/include/drm/drm_device.h    13 Sep 2023 14:24:37 -0000      
1.9
+++ sys/dev/pci/drm/include/drm/drm_device.h    7 Oct 2023 13:41:41 -0000
@@ -88,6 +88,7 @@ struct drm_device {
        bus_dma_tag_t           dmat;
        bus_space_tag_t         bst;
 
+       struct mutex note_mtx;
        struct klist note;
        struct pci_dev  _pdev;
        struct pci_dev *pdev;
Index: sys/dev/pci/drm/include/drm/drm_file.h
===================================================================
RCS file: /cvs/src/sys/dev/pci/drm/include/drm/drm_file.h,v
retrieving revision 1.7
diff -u -p -r1.7 drm_file.h
--- sys/dev/pci/drm/include/drm/drm_file.h      1 Jan 2023 01:34:58 -0000       
1.7
+++ sys/dev/pci/drm/include/drm/drm_file.h      7 Oct 2023 13:41:41 -0000
@@ -38,7 +38,7 @@
 
 #include <drm/drm_prime.h>
 
-#include <sys/selinfo.h>
+#include <sys/event.h>
 
 struct dma_fence;
 struct drm_file;
@@ -373,7 +373,7 @@ struct drm_file {
        unsigned long lock_count; /* DRI1 legacy lock count */
 #endif
 
-       struct selinfo rsel;
+       struct klist rklist;
        SPLAY_ENTRY(drm_file) link;
 };
 

Reply via email to