Race condition detecting graphical devices
@bor
Submitted by Andrey Borzenkov Assigned to Ray Strode @halfline
Link to original bug (#105141)
Description
This is long standing problem reported by many users on openSUSE - sporadically Plymouth starts with text mode splash instead of graphical one. I can reliably reproduce it on openSUSE Tumbleweed with plymouth 6e9e95dc starting VM with cold caches (after "echo 3 > /proc/sys/vm/drop_caches" on host). Restarting the same VM again will result in graphical splash.
This is apparently race condition when looking for graphical devices. Here is plymouth trace for both cases:
- Text mode splash:
[ply-device-manager.c:815] create_devices_from_udev:Timeout elapsed, looking for devices from udev [ply-device-manager.c:302] create_devices_for_subsystem:creating objects for drm devices [ply-device-manager.c:319] create_devices_for_subsystem:found device /sys/devices/pci0000:00/0000:00:01.0/drm/card0 [ply-device-manager.c:342] create_devices_for_subsystem:it's not initialized [ply-device-manager.c:319] create_devices_for_subsystem:found device /sys/devices/pci0000:00/0000:00:01.0/drm/card0/card0-Virtual-1 [ply-device-manager.c:342] create_devices_for_subsystem:it's not initialized [ply-device-manager.c:319] create_devices_for_subsystem:found device /sys/devices/virtual/drm/ttm [ply-device-manager.c:342] create_devices_for_subsystem:it's not initialized [ply-device-manager.c:302] create_devices_for_subsystem:creating objects for frame buffer devices [ply-device-manager.c:319] create_devices_for_subsystem:found device /sys/devices/pci0000:00/0000:00:01.0/graphics/fb0 [ply-device-manager.c:342] create_devices_for_subsystem:it's not initialized [ply-device-manager.c:319] create_devices_for_subsystem:found device /sys/devices/virtual/graphics/fbcon [ply-device-manager.c:342] create_devices_for_subsystem:it's not initialized [ply-device-manager.c:823] create_devices_from_udev:Creating non-graphical devices, since there's no suitable graphics hardware ... [ply-device-manager.c:365] on_udev_event:got add event for device card0 [ply-device-manager.c:377] on_udev_event:ignoring since we're already using text splash for local console [ply-device-manager.c:365] on_udev_event:got add event for device fb0 [ply-device-manager.c:381] on_udev_event:ignoring since we only handle subsystem graphics devices after timeout [ply-device-manager.c:365] on_udev_event:got add event for device card0-Virtual-1 [ply-device-manager.c:377] on_udev_event:ignoring since we're already using text splash for local console
- Frame-buffer splash: [ply-device-manager.c:815] create_devices_from_udev:Timeout elapsed, looking for devices from udev [ply-device-manager.c:302] create_devices_for_subsystem:creating objects for drm devices [ply-device-manager.c:319] create_devices_for_subsystem:found device /sys/devices/pci0000:00/0000:00:01.0/drm/card0 [ply-device-manager.c:326] create_devices_for_subsystem:device is initialized [ply-device-manager.c:335] create_devices_for_subsystem:found node /dev/dri/card0 [ply-device-manager.c:229] create_devices_for_udev_device:device subsystem is drm [ply-device-manager.c:244] create_devices_for_udev_device:found DRM device /dev/dri/card0 [ply-device-manager.c:247] create_devices_for_udev_device:forcing use of framebuffer for cirrusdrmfb [ply-device-manager.c:319] create_devices_for_subsystem:found device /sys/devices/pci0000:00/0000:00:01.0/drm/card0/card0-Virtual-1 [ply-device-manager.c:326] create_devices_for_subsystem:device is initialized [ply-device-manager.c:319] create_devices_for_subsystem:found device /sys/devices/virtual/drm/ttm [ply-device-manager.c:342] create_devices_for_subsystem:it's not initialized [ply-device-manager.c:302] create_devices_for_subsystem:creating objects for frame buffer devices [ply-device-manager.c:319] create_devices_for_subsystem:found device /sys/devices/pci0000:00/0000:00:01.0/graphics/fb0 [ply-device-manager.c:326] create_devices_for_subsystem:device is initialized [ply-device-manager.c:335] create_devices_for_subsystem:found node /dev/fb0 [ply-device-manager.c:229] create_devices_for_udev_device:device subsystem is graphics [ply-device-manager.c:251] create_devices_for_udev_device:found frame buffer device /dev/fb0 [ply-device-manager.c:699] create_devices_for_terminal_and_renderer_type:creating devices for /dev/fb0 (renderer type: 2) (terminal: /dev/tty7)
"it's not initialized" means that udev has not yet finished device processing. Comment in src/libply-splash-core/ply-device-manager.c:create_devices_for_subsystem() suggests that we should get event later which is true but as we already selected text mode when even arrived it is ignored.
If plymouth sees non-initalized device it must wait for udev to finish. Example of this handling (wait_for_initialize):
https://github.com/systemd/systemd/blob/master/src/rfkill/rfkill.c#L108