[kernel] Linux 3.3-rc1-git6 (upstream 6bc2b95ee602659c1be6fac0f6aadeb0c5c29a5d)

Josh Boyer jwboyer at fedoraproject.org
Mon Jan 30 21:38:08 UTC 2012


commit cf9048c9c41c8838f628174e090de937212d57d7
Author: Josh Boyer <jwboyer at redhat.com>
Date:   Mon Jan 30 16:37:49 2012 -0500

    Linux 3.3-rc1-git6 (upstream 6bc2b95ee602659c1be6fac0f6aadeb0c5c29a5d)
    
    - Add patch from Kay Sievers for udlfb device removal
    - utrace patch to allow calling internal functions from atomic context from
      Oleg Nesterov

 kernel.spec                                        |   12 ++-
 ...fs-framebuffer-device-with-USB-disconnect.patch |  118 ++++++++++++++++++++
 utrace.patch                                       |   70 ++++++++++++
 3 files changed, 199 insertions(+), 1 deletions(-)
---
diff --git a/kernel.spec b/kernel.spec
index bf55811..273631f 100644
--- a/kernel.spec
+++ b/kernel.spec
@@ -87,7 +87,7 @@ Summary: The Linux kernel
 # The rc snapshot level
 %define rcrev 1
 # The git snapshot level
-%define gitrev 5
+%define gitrev 6
 # Set rpm version accordingly
 %define rpmversion 3.%{upstream_sublevel}.0
 %endif
@@ -741,6 +741,8 @@ Patch21087: fs-Inval-cache-for-parent-block-device-if-fsync-called-on-part.patch
 
 Patch21091: kmemleak.patch
 
+Patch21092: udlfb-remove-sysfs-framebuffer-device-with-USB-disconnect.patch
+
 # compat-wireless patches
 Patch50000: compat-wireless-config-fixups.patch
 Patch50001: compat-wireless-pr_fmt-warning-avoidance.patch
@@ -1432,6 +1434,8 @@ ApplyPatch KVM-x86-fix-missing-checks-in-syscall-emulation.patch
 
 ApplyPatch kmemleak.patch
 
+ApplyPatch udlfb-remove-sysfs-framebuffer-device-with-USB-disconnect.patch
+
 #rhbz 783211
 ApplyPatch fs-Inval-cache-for-parent-block-device-if-fsync-called-on-part.patch
 
@@ -2281,6 +2285,12 @@ fi
 #                 ||----w |
 #                 ||     ||
 %changelog
+* Mon Jan 30 2012 Josh Boyer <jwboyer at redhat.com> - 3.3.0-0.rc1.git6.1
+- Linux 3.3-rc1-git6 (upstream 6bc2b95ee602659c1be6fac0f6aadeb0c5c29a5d)
+- Add patch from Kay Sievers for udlfb device removal
+- utrace patch to allow calling internal functions from atomic context from
+  Oleg Nesterov
+
 * Mon Jan 30 2012 John W. Linville <linville at redhat.com>
 - ath9k: use WARN_ON_ONCE in ath_rc_get_highest_rix
 
diff --git a/udlfb-remove-sysfs-framebuffer-device-with-USB-disconnect.patch b/udlfb-remove-sysfs-framebuffer-device-with-USB-disconnect.patch
new file mode 100644
index 0000000..c304713
--- /dev/null
+++ b/udlfb-remove-sysfs-framebuffer-device-with-USB-disconnect.patch
@@ -0,0 +1,118 @@
+From 92a9c19a89af2ca219fbb040a0059f414a4b7223 Mon Sep 17 00:00:00 2001
+From: Kay Sievers <kay.sievers at vrfy.org>
+Date: Sat, 28 Jan 2012 19:57:46 +0000
+Subject: [PATCH] udlfb: remove sysfs framebuffer 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 uevent
+sequence. Recent userspace tools started to support USB graphics card
+hotplug out-of-the-box and rely on proper events sent by the kernel.
+
+The framebuffer device is a direct child of the USB interface which is
+removed immediately after the USB .disconnect() callback. But the fb device
+in /sys stays around until its final cleanup, at a time where all the parent
+devices have been removed already.
+
+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)
+
+Cc: stable at vger.kernel.org
+Tested-by: Bernie Thompson <bernie at plugable.com>
+Acked-by: Bernie Thompson <bernie at plugable.com>
+Signed-off-by: Kay Sievers <kay.sievers at vrfy.org>
+Signed-off-by: Florian Tobias Schandinat <FlorianSchandinat at gmx.de>
+---
+ drivers/video/fbmem.c |   18 +++++++++++++++++-
+ drivers/video/udlfb.c |    2 +-
+ include/linux/fb.h    |    1 +
+ 3 files changed, 19 insertions(+), 2 deletions(-)
+
+diff --git a/drivers/video/fbmem.c b/drivers/video/fbmem.c
+index ac9141b..c6ce416 100644
+--- a/drivers/video/fbmem.c
++++ b/drivers/video/fbmem.c
+@@ -1665,6 +1665,7 @@ static int do_unregister_framebuffer(struct fb_info *fb_info)
+ 	if (ret)
+ 		return -EINVAL;
+ 
++	unlink_framebuffer(fb_info);
+ 	if (fb_info->pixmap.addr &&
+ 	    (fb_info->pixmap.flags & FB_PIXMAP_DEFAULT))
+ 		kfree(fb_info->pixmap.addr);
+@@ -1672,7 +1673,6 @@ static int do_unregister_framebuffer(struct fb_info *fb_info)
+ 	registered_fb[i] = NULL;
+ 	num_registered_fb--;
+ 	fb_cleanup_device(fb_info);
+-	device_destroy(fb_class, MKDEV(FB_MAJOR, i));
+ 	event.info = fb_info;
+ 	fb_notifier_call_chain(FB_EVENT_FB_UNREGISTERED, &event);
+ 
+@@ -1681,6 +1681,22 @@ static int do_unregister_framebuffer(struct fb_info *fb_info)
+ 	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)
+ {
+diff --git a/drivers/video/udlfb.c b/drivers/video/udlfb.c
+index a197731..a40c05e 100644
+--- a/drivers/video/udlfb.c
++++ b/drivers/video/udlfb.c
+@@ -1739,7 +1739,7 @@ static void dlfb_usb_disconnect(struct usb_interface *interface)
+ 	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 */
+diff --git a/include/linux/fb.h b/include/linux/fb.h
+index c18122f..a395b8c 100644
+--- a/include/linux/fb.h
++++ b/include/linux/fb.h
+@@ -1003,6 +1003,7 @@ extern ssize_t fb_sys_write(struct fb_info *info, const char __user *buf,
+ /* 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);
+-- 
+1.7.6.5
+
diff --git a/utrace.patch b/utrace.patch
index 0e34971..556188a 100644
--- a/utrace.patch
+++ b/utrace.patch
@@ -4683,3 +4683,73 @@ index 0000000..c817a46
 +	seq_printf(m, "Utrace:\t%lx\n", p->utrace_flags);
 +}
 
+Add the new UTRACE_ATTACH_ATOMIC flag for utrace_attach_task().
+If it is set, UTRACE_ATTACH_CREATE uses GFP_ATOMIC for memory
+allocations and thus it can be used in atomic context.
+
+Suggested-by: Mark Wielaard <mjw at redhat.com>
+Signed-off-by: Oleg Nesterov <oleg at redhat.com>
+---
+ include/linux/utrace.h |    1 +
+ kernel/utrace.c        |   12 ++++++++----
+ 2 files changed, 9 insertions(+), 4 deletions(-)
+
+diff --git a/include/linux/utrace.h b/include/linux/utrace.h
+index f37373b..46959af 100644
+--- a/include/linux/utrace.h
++++ b/include/linux/utrace.h
+@@ -317,6 +317,7 @@ static inline enum utrace_syscall_action utrace_syscall_action(u32 action)
+ #define UTRACE_ATTACH_MATCH_MASK	0x000f
+ #define UTRACE_ATTACH_CREATE		0x0010 /* Attach a new engine.  */
+ #define UTRACE_ATTACH_EXCLUSIVE		0x0020 /* Refuse if existing match.  */
++#define UTRACE_ATTACH_ATOMIC		0x0040 /* For _CREATE, don't sleep  */
+ 
+ /**
+  * struct utrace_engine - per-engine structure
+diff --git a/kernel/utrace.c b/kernel/utrace.c
+index c817a46..a169e1b 100644
+--- a/kernel/utrace.c
++++ b/kernel/utrace.c
+@@ -113,9 +113,9 @@ void task_utrace_unlock(struct task_struct *task)
+  *
+  * This returns false only in case of a memory allocation failure.
+  */
+-static bool utrace_task_alloc(struct task_struct *task)
++static bool utrace_task_alloc(struct task_struct *task, gfp_t gfp_flags)
+ {
+-	struct utrace *utrace = kmem_cache_zalloc(utrace_cachep, GFP_KERNEL);
++	struct utrace *utrace = kmem_cache_zalloc(utrace_cachep, gfp_flags);
+ 	if (unlikely(!utrace))
+ 		return false;
+ 	spin_lock_init(&utrace->lock);
+@@ -295,6 +295,7 @@ struct utrace_engine *utrace_attach_task(
+ {
+ 	struct utrace *utrace = task_utrace_struct(target);
+ 	struct utrace_engine *engine;
++	gfp_t gfp_flags;
+ 	int ret;
+ 
+ 	if (!(flags & UTRACE_ATTACH_CREATE)) {
+@@ -317,13 +318,16 @@ struct utrace_engine *utrace_attach_task(
+ 		 */
+ 		return ERR_PTR(-EPERM);
+ 
++	gfp_flags = (flags & UTRACE_ATTACH_ATOMIC)
++				? GFP_ATOMIC : GFP_KERNEL;
++
+ 	if (!utrace) {
+-		if (unlikely(!utrace_task_alloc(target)))
++		if (unlikely(!utrace_task_alloc(target, gfp_flags)))
+ 			return ERR_PTR(-ENOMEM);
+ 		utrace = task_utrace_struct(target);
+ 	}
+ 
+-	engine = kmem_cache_alloc(utrace_engine_cachep, GFP_KERNEL);
++	engine = kmem_cache_alloc(utrace_engine_cachep, gfp_flags);
+ 	if (unlikely(!engine))
+ 		return ERR_PTR(-ENOMEM);
+ 
+-- 
+1.5.5.1
+
+


More information about the scm-commits mailing list