add kqueue support to drm(4) by making the drm_sysfs_hotplug_event()
authorrobert <robert@openbsd.org>
Sat, 13 Jan 2018 13:03:42 +0000 (13:03 +0000)
committerrobert <robert@openbsd.org>
Sat, 13 Jan 2018 13:03:42 +0000 (13:03 +0000)
available on OpenBSD well and by notifying listeners of a device
state change using EVFILT_DEVICE and NOTE_CHANGE.

drm_sysfs_hotplug_event() gets called when a state change of the device
occured, like an hdmi cable has been plugged, this in the future will
be used by the modesetting xorg driver to notify desktop environments
via randr events to update their screen configuration

ok kettenis@

sys/dev/pci/drm/drmP.h
sys/dev/pci/drm/drm_drv.c
sys/dev/pci/drm/drm_linux.c
sys/sys/conf.h

index f04240a..78e9f97 100644 (file)
@@ -1,4 +1,4 @@
-/* $OpenBSD: drmP.h,v 1.215 2017/07/22 14:33:45 kettenis Exp $ */
+/* $OpenBSD: drmP.h,v 1.216 2018/01/13 13:03:42 robert Exp $ */
 /* drmP.h -- Private header for Direct Rendering Manager -*- linux-c -*-
  * Created: Mon Jan  4 10:05:05 1999 by faith@precisioninsight.com
  */
@@ -735,6 +735,8 @@ struct drm_device {
 
        struct drm_driver *driver;
 
+       struct klist     note;
+
        struct pci_dev  _pdev;
        struct pci_dev  *pdev;
        u_int16_t        pci_device;
@@ -1014,6 +1016,9 @@ int       drm_agp_free_ioctl(struct drm_device *, void *, struct drm_file *);
 int    drm_agp_unbind_ioctl(struct drm_device *, void *, struct drm_file *);
 int    drm_agp_bind_ioctl(struct drm_device *, void *, struct drm_file *);
 
+/* hotplug support */
+void   drm_sysfs_hotplug_event(struct drm_device *);
+
 static inline int
 drm_sysfs_connector_add(struct drm_connector *connector)
 {
@@ -1025,11 +1030,6 @@ drm_sysfs_connector_remove(struct drm_connector *connector)
 {
 }
 
-static inline void
-drm_sysfs_hotplug_event(struct drm_device *dev)
-{
-}
-
 /* Graphics Execution Manager library functions (drm_gem.c) */
 int drm_gem_init(struct drm_device *dev);
 void drm_gem_destroy(struct drm_device *dev);
index 523ccfe..065691a 100644 (file)
@@ -1,4 +1,4 @@
-/* $OpenBSD: drm_drv.c,v 1.154 2017/07/19 22:05:58 kettenis Exp $ */
+/* $OpenBSD: drm_drv.c,v 1.155 2018/01/13 13:03:42 robert Exp $ */
 /*-
  * Copyright 2007-2009 Owain G. Ainsworth <oga@openbsd.org>
  * Copyright © 2008 Intel Corporation
@@ -50,6 +50,7 @@
 #include <sys/systm.h>
 #include <sys/ttycom.h> /* for TIOCSGRP */
 #include <sys/vnode.h>
+#include <sys/event.h>
 
 #include <uvm/uvm.h>
 #include <uvm/uvm_device.h>
@@ -633,6 +634,55 @@ drm_lastclose(struct drm_device *dev)
        return 0;
 }
 
+void
+filt_drmdetach(struct knote *kn)
+{
+       struct drm_device *dev = kn->kn_hook;
+       int s;
+
+       s = spltty();
+       SLIST_REMOVE(&dev->note, kn, knote, kn_selnext);
+       splx(s);
+}
+
+int
+filt_drmkms(struct knote *kn, long hint)
+{
+       if (kn->kn_sfflags & hint)
+               kn->kn_fflags |= hint;
+       return (kn->kn_fflags != 0);
+}
+
+struct filterops drm_filtops =
+       { 1, NULL, filt_drmdetach, filt_drmkms };
+
+int
+drmkqfilter(dev_t kdev, struct knote *kn)
+{
+       struct drm_device       *dev = NULL;
+       int s;
+
+       dev = drm_get_device_from_kdev(kdev);
+       if (dev == NULL || dev->dev_private == NULL)
+               return (ENXIO);
+
+       switch (kn->kn_filter) {
+       case EVFILT_DEVICE:
+               kn->kn_fop = &drm_filtops;
+               break;
+       default:
+               return (EINVAL);
+       }
+
+       kn->kn_hook = dev;
+
+       s = spltty();
+       SLIST_INSERT_HEAD(&dev->note, kn, kn_selnext);
+       splx(s);
+
+       return (0);
+}
+
 int
 drmopen(dev_t kdev, int flags, int fmt, struct proc *p)
 {
index 4c4498b..40141b8 100644 (file)
@@ -1,4 +1,4 @@
-/*     $OpenBSD: drm_linux.c,v 1.16 2018/01/12 11:03:15 jsg Exp $      */
+/*     $OpenBSD: drm_linux.c,v 1.17 2018/01/13 13:03:42 robert Exp $   */
 /*
  * Copyright (c) 2013 Jonathan Gray <jsg@openbsd.org>
  * Copyright (c) 2015, 2016 Mark Kettenis <kettenis@openbsd.org>
@@ -18,6 +18,7 @@
 
 #include <dev/pci/drm/drmP.h>
 #include <dev/pci/ppbreg.h>
+#include <sys/event.h>
 
 void
 flush_barrier(void *arg)
@@ -730,3 +731,9 @@ backlight_schedule_update_status(struct backlight_device *bd)
 {
        task_add(systq, &bd->task);
 }
+
+void
+drm_sysfs_hotplug_event(struct drm_device *dev)
+{
+       KNOTE(&dev->note, NOTE_CHANGE);
+}
index 79c5f6c..6967ffb 100644 (file)
@@ -1,4 +1,4 @@
-/*     $OpenBSD: conf.h,v 1.143 2016/09/04 10:51:24 naddy Exp $        */
+/*     $OpenBSD: conf.h,v 1.144 2018/01/13 13:03:42 robert Exp $       */
 /*     $NetBSD: conf.h,v 1.33 1996/05/03 20:03:32 christos Exp $       */
 
 /*-
@@ -444,7 +444,7 @@ extern struct cdevsw cdevsw[];
        dev_init(c,n,open), dev_init(c,n,close), dev_init(c, n, read), \
        (dev_type_write((*))) enodev, dev_init(c,n,ioctl), \
        (dev_type_stop((*))) enodev, 0,  dev_init(c,n,poll), \
-       dev_init(c,n,mmap), 0, D_CLONE }
+       dev_init(c,n,mmap), 0, D_CLONE, dev_init(c,n,kqfilter) }
 
 /* open, close, ioctl */
 #define cdev_amdmsr_init(c,n) { \