Weston中的检测

drm_backend_create在创建时,会创建一个循环获取热拔插事件。

b->udev_drm_source =
    wl_event_loop_add_fd(loop,
             udev_monitor_get_fd(b->udev_monitor),
             WL_EVENT_READABLE, udev_drm_event, b);
static int
udev_drm_event(int fd, uint32_t mask, void *data)
{
  struct drm_backend *b = data;
  struct udev_device *event;
  uint32_t conn_id, prop_id;
​
  event = udev_monitor_receive_device(b->udev_monitor);
​
  if (udev_event_is_hotplug(b, event)) {
    if (udev_event_is_conn_prop_change(b, event, &conn_id, &prop_id))
      drm_backend_update_conn_props(b, conn_id, prop_id);
    else
      drm_backend_update_heads(b, event);
  }
​
  udev_device_unref(event);
​
  return 1;
}

udev_device_get_property_value(device, "HOTPLUG")检测drm驱动中“HOTPLUG”属性的值,产生热拔插后,驱动层。

我们使用udevadm monitor --property命令来检测热拔插事件。

monitor will print the received events for:
UDEV - the event which udev sends out after rule processing
KERNEL - the kernel uevent
KERNEL[4940.661886] change   /devices/platform/display-subsystem/drm/card1 (drm)
ACTION=change
DEVPATH=/devices/platform/display-subsystem/drm/card1
SUBSYSTEM=drm
HOTPLUG=1
DEVNAME=/dev/dri/card1
DEVTYPE=drm_minor
SEQNUM=4255
MAJOR=226
MINOR=1
Bridge驱动的检测

驱动层通过devm_request_threaded_irq来开辟一个中断检测线程,检测到irq后,需要通过drm_helper_hpd_irq_event和drm_bridge_hpd_notify函数才能将irq事件发送给drm设备。

第一步:drm_helper_hpd_irq_event

drm_helper_hpd_irq_event此时来修改connector的状态,然后drm_kms_helper_hotplug_event会在用户空间触发uevent事件。也就是刚才我们之前使用udevadm命令所看到uevent的信息。

第二步:drm_bridge_hpd_notify

drm_bridge_hpd_notify将drm_connector_status值传给bridge设备,通知bridge驱动来处理热拔插事件。