diff options
author | Kay Sievers <kay.sievers@vrfy.org> | 2012-01-17 17:13:41 +0100 |
---|---|---|
committer | Kay Sievers <kay.sievers@vrfy.org> | 2012-01-17 17:13:41 +0100 |
commit | b4e0af938d92107de48ca520045121e482e63cec (patch) | |
tree | ef007857a1e45b7d5cec9ce14f776c35882ee009 | |
parent | 118d375cbcf90c2d9f41fee4adb324a5852dbb30 (diff) | |
download | patches-b4e0af938d92107de48ca520045121e482e63cec.tar.gz |
add udlfb patch
-rw-r--r-- | prctl-child_reaper.patch | 2 | ||||
-rw-r--r-- | series | 1 | ||||
-rw-r--r-- | udlfb.patch | 94 |
3 files changed, 96 insertions, 1 deletions
diff --git a/prctl-child_reaper.patch b/prctl-child_reaper.patch index 6ab5561..dc04f17 100644 --- a/prctl-child_reaper.patch +++ b/prctl-child_reaper.patch @@ -146,7 +146,7 @@ Signed-off-by: Kay Sievers <kay.sievers@vrfy.org> return pid_ns->child_reaper; --- a/kernel/fork.c +++ b/kernel/fork.c -@@ -982,6 +982,9 @@ static int copy_signal(unsigned long clo +@@ -984,6 +984,9 @@ static int copy_signal(unsigned long clo sig->oom_score_adj = current->signal->oom_score_adj; sig->oom_score_adj_min = current->signal->oom_score_adj_min; @@ -1 +1,2 @@ prctl-child_reaper.patch +udlfb.patch diff --git a/udlfb.patch b/udlfb.patch new file mode 100644 index 0000000..200aaf4 --- /dev/null +++ b/udlfb.patch @@ -0,0 +1,94 @@ +From: Kay Sievers <kay.sievers@vrfy.org> +Subject: udlfb: remove sysfs frambuffer device with USB .disconnect() + +The USB graphics card driver delays the unregistering of the framebuffer +device to a workqueue, which breaks the userspace visible remove event +sequence. + +The framebuffer device is a direct child of the USB interface which is +removed immedeately after the USB .disconnect() callback. But the fb device +stay around until its final cleanup, at a time where all the parent devices +are already gone. + +To work around that, we remove the sysfs fb device directly in the USB +.disconnect() callback and leave only the cleanup of the internal fb +data to the delayed work. + +Before: + add /devices/pci0000:00/0000:00:1d.0/usb2/2-1/2-1.2 (usb) + add /devices/pci0000:00/0000:00:1d.0/usb2/2-1/2-1.2/2-1.2:1.0 (usb) + add /devices/pci0000:00/0000:00:1d.0/usb2/2-1/2-1.2/2-1.2:1.0/graphics/fb0 (graphics) + remove /devices/pci0000:00/0000:00:1d.0/usb2/2-1/2-1.2/2-1.2:1.0 (usb) + remove /devices/pci0000:00/0000:00:1d.0/usb2/2-1/2-1.2 (usb) + remove /2-1.2:1.0/graphics/fb0 (graphics) + +After: + add /devices/pci0000:00/0000:00:1d.0/usb2/2-1/2-1.2 (usb) + add /devices/pci0000:00/0000:00:1d.0/usb2/2-1/2-1.2/2-1.2:1.0 (usb) + add /devices/pci0000:00/0000:00:1d.0/usb2/2-1/2-1.2/2-1.2:1.0/graphics/fb1 (graphics) + remove /devices/pci0000:00/0000:00:1d.0/usb2/2-1/2-1.2/2-1.2:1.0/graphics/fb1 (graphics) + remove /devices/pci0000:00/0000:00:1d.0/usb2/2-1/2-1.2/2-1.2:1.0 (usb) + remove /devices/pci0000:00/0000:00:1d.0/usb2/2-1/2-1.2 (usb) + +Signed-off-by: Kay Sievers <kay.sievers@vrfy.org> +--- + drivers/video/fbmem.c | 18 +++++++++++++++++- + drivers/video/udlfb.c | 2 +- + include/linux/fb.h | 1 + + 3 files changed, 19 insertions(+), 2 deletions(-) + +--- a/drivers/video/fbmem.c ++++ b/drivers/video/fbmem.c +@@ -1672,7 +1672,7 @@ static int do_unregister_framebuffer(str + registered_fb[i] = NULL; + num_registered_fb--; + fb_cleanup_device(fb_info); +- device_destroy(fb_class, MKDEV(FB_MAJOR, i)); ++ unlink_framebuffer(fb_info); + event.info = fb_info; + fb_notifier_call_chain(FB_EVENT_FB_UNREGISTERED, &event); + +@@ -1681,6 +1681,22 @@ static int do_unregister_framebuffer(str + return 0; + } + ++int unlink_framebuffer(struct fb_info *fb_info) ++{ ++ int i; ++ ++ i = fb_info->node; ++ if (i < 0 || i >= FB_MAX || registered_fb[i] != fb_info) ++ return -EINVAL; ++ ++ if (fb_info->dev) { ++ device_destroy(fb_class, MKDEV(FB_MAJOR, i)); ++ fb_info->dev = NULL; ++ } ++ return 0; ++} ++EXPORT_SYMBOL(unlink_framebuffer); ++ + void remove_conflicting_framebuffers(struct apertures_struct *a, + const char *name, bool primary) + { +--- a/drivers/video/udlfb.c ++++ b/drivers/video/udlfb.c +@@ -1739,7 +1739,7 @@ static void dlfb_usb_disconnect(struct u + for (i = 0; i < ARRAY_SIZE(fb_device_attrs); i++) + device_remove_file(info->dev, &fb_device_attrs[i]); + device_remove_bin_file(info->dev, &edid_attr); +- ++ unlink_framebuffer(info); + usb_set_intfdata(interface, NULL); + + /* if clients still have us open, will be freed on last close */ +--- a/include/linux/fb.h ++++ b/include/linux/fb.h +@@ -1003,6 +1003,7 @@ extern ssize_t fb_sys_write(struct fb_in + /* drivers/video/fbmem.c */ + extern int register_framebuffer(struct fb_info *fb_info); + extern int unregister_framebuffer(struct fb_info *fb_info); ++extern int unlink_framebuffer(struct fb_info *fb_info); + extern void remove_conflicting_framebuffers(struct apertures_struct *a, + const char *name, bool primary); + extern int fb_prepare_logo(struct fb_info *fb_info, int rotate); |