2018-01-09 21:35 GMT-03:00 Laurent Bercot: > > What it looks like is the kernel not assigning a major and a minor > to the device before you manually trigger the "add". I suspect it's > just that the relevant module is not loaded, but why would that be > different from any other hardware managing to make mdevd autoload the > appropriate module? > [...] > Well I certainly don't want people to need to write their own > trigger-uevents service, so I'll make sure your hardware is properly > found by mdevd-coldplug. I'd just like to understand what is happening > and add the proper fix rather than take a big hammer and scan all of > /sys/devices just to be sure.
It might be worth to look at what systemd [1] and eudev [2] do here. When 'udevadm trigger --type=devices --action=add' is performed after the udev daemon starts executing, it looks like what happens is basically this: * If /sys/subsystem exists, an 'add' string is written to every /sys/subsystem/*/devices/*/uevent file. * If /sys/subsystem does not exist, an 'add' string is written to every /sys/class/*/*/uevent and /sys/bus/*/devices/*/uevent file. I have a 4.9-series kernel and no /sys/subsystem, but I do have /sys/class/*/* and /sys/bus/*/devices/* files indeed, and they are in all cases symbolic links to subdirectories of /sys/devices with 'uevent' files. So it kind of looks like a big hammer is used, but with an easy to generate set of pathnames instead of actually traversing the /sys/devices hierarchy. Maybe this can be taken to be the currently agreed sysfs interface for device managers (or else systemd breaks). On the other hand it looks like mdevd-coldplug and BusyBox' 'mdev -s' want to access the /sys/dev/block/${major}:${minor} and /sys/dev/char/${major}:${minor} symlinks. If it is the case that some of these won't exist until the relevant kernel modules are loaded, and if the device manager is expected to load them, it would mean it can't reliably use /sys/dev. For testing purposes, with mdevd-netlink running, either this: #/bin/execlineb -P elglob syssubsystem /sys/subsystem/*/devices/*/uevent forx f { $syssubsystem } importas -u ueventfile f redirfd -w 1 $ueventfile echo add or this: #/bin/execlineb -P elglob sysclass /sys/class/*/*/uevent elglob sysbus /sys/bus/*/devices/*/uevent forx f { $sysclass $sysbus } importas -u ueventfile f redirfd -w 1 $ueventfile echo add could be used to see what happens, depending on the case. I don't have mdevd installed with a suitable /etc/mdev.conf file at the moment, but I tried executing the script while eudev's udevd was running (as a replacement for udevadm trigger), and I did get all kernel modules to load, and did see new /sys/dev/*/* symlinks after that. G. [1] * https://github.com/systemd/systemd/blob/master/src/udev/udevadm-trigger.c adm_trigger(), exec_list() * https://github.com/systemd/systemd/blob/master/src/libudev/libudev-enumerate.c udev_enumerate_scan_devices() * https://github.com/systemd/systemd/blob/master/src/libsystemd/sd-device/device-enumerator.c device_enumerator_scan_devices(), enumerator_scan_devices_all(), enumerator_scan_dir(), enumerator_scan_dir_and_add_devices() * https://github.com/systemd/systemd/blob/master/src/libsystemd/sd-device/sd-device.c sd_device_new_from_syspath() [2] * https://github.com/gentoo/eudev/blob/master/src/udev/udevadm-trigger.c adm_trigger(), exec_list() * https://github.com/gentoo/eudev/blob/master/src/libudev/libudev-enumerate.c udev_enumerate_scan_devices(), scan_devices_all(), scan_dir(), scan_dir_and_add_devices(), syspath_add()