]> git.ipfire.org Git - thirdparty/kernel/stable-queue.git/commitdiff
more .28 patches
authorGreg Kroah-Hartman <gregkh@suse.de>
Fri, 13 Mar 2009 06:20:29 +0000 (23:20 -0700)
committerGreg Kroah-Hartman <gregkh@suse.de>
Fri, 13 Mar 2009 06:20:29 +0000 (23:20 -0700)
25 files changed:
queue-2.6.28/acpi-fix-broken-usage-of-acpi_ut_get_node_name.patch [new file with mode: 0644]
queue-2.6.28/acpi-fix-broken-usage-of-name.ascii.patch [new file with mode: 0644]
queue-2.6.28/arm-add-i2c_board_info-for-riscpc-pcf8583.patch [new file with mode: 0644]
queue-2.6.28/crypto-api-fix-algorithm-test-race-that-broke-aead-initialisation.patch [new file with mode: 0644]
queue-2.6.28/drm-i915-add-missing-userland-definitions-for-gem-init-execbuffer.patch [new file with mode: 0644]
queue-2.6.28/ext4-add-fallback-for-find_group_flex.patch [new file with mode: 0644]
queue-2.6.28/ext4-fix-deadlock-in-ext4_write_begin-and-ext4_da_write_begin.patch [new file with mode: 0644]
queue-2.6.28/ext4-fix-lockdep-warning.patch [new file with mode: 0644]
queue-2.6.28/ext4-fix-null-dereference-in-ext4_ext_migrate-s-error-handling.patch [new file with mode: 0644]
queue-2.6.28/ext4-fix-to-read-empty-directory-blocks-correctly-in-64k.patch [new file with mode: 0644]
queue-2.6.28/ext4-implement-range_cyclic-in-ext4_da_writepages-instead-of-write_cache_pages.patch [new file with mode: 0644]
queue-2.6.28/ext4-initialize-preallocation-list_head-s-properly.patch [new file with mode: 0644]
queue-2.6.28/hid-move-tmff-and-zpff-devices-from-ignore_list-to-blacklist.patch [new file with mode: 0644]
queue-2.6.28/hwmon-hide-misleading-error-message.patch [new file with mode: 0644]
queue-2.6.28/i2c-fix-misplaced-parentheses.patch [new file with mode: 0644]
queue-2.6.28/i2c-timeouts-reach-1.patch [new file with mode: 0644]
queue-2.6.28/ide-iops-fix-odd-length-atapi-pio-transfers.patch [new file with mode: 0644]
queue-2.6.28/jbd2-avoid-possible-null-dereference-in-jbd2_journal_begin_ordered_truncate.patch [new file with mode: 0644]
queue-2.6.28/jbd2-fix-return-value-of-jbd2_journal_start_commit.patch [new file with mode: 0644]
queue-2.6.28/revert-ext4-wait-on-all-pending-commits-in-ext4_sync_fs.patch [new file with mode: 0644]
queue-2.6.28/series
queue-2.6.28/x86-fix-math_emu-register-frame-access.patch [new file with mode: 0644]
queue-2.6.28/x86-hpet-fix-for-ls21-hpet-boot-hang.patch [new file with mode: 0644]
queue-2.6.28/x86-math_emu-info-cleanup.patch [new file with mode: 0644]
queue-2.6.28/x86-paravirt-make-arch_flush_lazy_mmu-cpu-disable-preemption.patch [new file with mode: 0644]

diff --git a/queue-2.6.28/acpi-fix-broken-usage-of-acpi_ut_get_node_name.patch b/queue-2.6.28/acpi-fix-broken-usage-of-acpi_ut_get_node_name.patch
new file mode 100644 (file)
index 0000000..c462b93
--- /dev/null
@@ -0,0 +1,39 @@
+From hmh@hmh.eng.br  Thu Mar 12 23:12:43 2009
+From: Henrique de Moraes Holschuh <hmh@hmh.eng.br>
+Date: Tue, 24 Feb 2009 11:48:18 -0300
+Subject: ACPI: fix broken usage of acpi_ut_get_node_name()
+To: Len Brown <lenb@kernel.org>
+Cc: linux-acpi@vger.kernel.org, Lin Ming <ming.m.lin@intel.com>, stable@kernel.org, Henrique de Moraes Holschuh <hmh@hmh.eng.br>
+Message-ID: <1235486898-27756-2-git-send-email-hmh@hmh.eng.br>
+
+From: Henrique de Moraes Holschuh <hmh@hmh.eng.br>
+
+This issue was fixed indirectly in mainline by commit
+60a4ce7f4148155d3f28eea4a213f7ee47cd57b7.
+
+acpi_ut_get_node_name() returns a four char fixed-size array, not
+NULL-terminated.
+
+This is the minimal fix for stable 2.6.28.
+
+Signed-off-by: Henrique de Moraes Holschuh <hmh@hmh.eng.br>
+Cc: stable@kernel.org
+Acked-by: Lin Ming <ming.m.lin@intel.com>
+Cc: Len Brown <lenb@kernel.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ drivers/acpi/power.c |    2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+--- a/drivers/acpi/power.c
++++ b/drivers/acpi/power.c
+@@ -151,7 +151,7 @@ static int acpi_power_get_state(acpi_han
+       *state = (sta & 0x01)?ACPI_POWER_RESOURCE_STATE_ON:
+                             ACPI_POWER_RESOURCE_STATE_OFF;
+-      ACPI_DEBUG_PRINT((ACPI_DB_INFO, "Resource [%s] is %s\n",
++      ACPI_DEBUG_PRINT((ACPI_DB_INFO, "Resource [%4.4s] is %s\n",
+                         acpi_ut_get_node_name(handle),
+                               *state ? "on" : "off"));
diff --git a/queue-2.6.28/acpi-fix-broken-usage-of-name.ascii.patch b/queue-2.6.28/acpi-fix-broken-usage-of-name.ascii.patch
new file mode 100644 (file)
index 0000000..8c28ac5
--- /dev/null
@@ -0,0 +1,43 @@
+From hmh@hmh.eng.br  Thu Mar 12 23:11:32 2009
+From: Henrique de Moraes Holschuh <hmh@hmh.eng.br>
+Date: Tue, 24 Feb 2009 11:48:17 -0300
+Subject: ACPI: fix broken usage of name.ascii
+To: Len Brown <lenb@kernel.org>
+Cc: linux-acpi@vger.kernel.org, Lin Ming <ming.m.lin@intel.com>, stable@kernel.org, Henrique de Moraes Holschuh <hmh@hmh.eng.br>
+Message-ID: <1235486898-27756-1-git-send-email-hmh@hmh.eng.br>
+
+From: Henrique de Moraes Holschuh <hmh@hmh.eng.br>
+
+This issue was fixed indirectly in mainline by commit
+0175d562a29ad052c510782c7e76bc63d5155b9b.
+
+acpi_namespace_node's name.ascii field is four chars, and not NULL-
+terminated except by pure luck.  So, it cannot be used by sscanf() without
+a length restriction.
+
+This is the minimal fix for both stable 2.6.27 and 2.6.28.
+
+Signed-off-by: Henrique de Moraes Holschuh <hmh@hmh.eng.br>
+Cc: Lin Ming <ming.m.lin@intel.com>
+Cc: Len Brown <lenb@kernel.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ drivers/acpi/ec.c |    5 +++--
+ 1 file changed, 3 insertions(+), 2 deletions(-)
+
+--- a/drivers/acpi/ec.c
++++ b/drivers/acpi/ec.c
+@@ -759,9 +759,10 @@ acpi_ec_register_query_methods(acpi_hand
+       struct acpi_namespace_node *node = handle;
+       struct acpi_ec *ec = context;
+       int value = 0;
+-      if (sscanf(node->name.ascii, "_Q%x", &value) == 1) {
++
++      if (sscanf(node->name.ascii, "_Q%2x", &value) == 1)
+               acpi_ec_add_query_handler(ec, value, handle, NULL, NULL);
+-      }
++
+       return AE_OK;
+ }
diff --git a/queue-2.6.28/arm-add-i2c_board_info-for-riscpc-pcf8583.patch b/queue-2.6.28/arm-add-i2c_board_info-for-riscpc-pcf8583.patch
new file mode 100644 (file)
index 0000000..1ee076b
--- /dev/null
@@ -0,0 +1,69 @@
+From khali@linux-fr.org  Thu Mar 12 23:08:53 2009
+From: Jean Delvare <khali@linux-fr.org>
+Date: Wed, 25 Feb 2009 21:34:07 +0100
+Subject: ARM: Add i2c_board_info for RiscPC PCF8583
+To: stable@kernel.org
+Cc: Russell King <rmk+kernel@arm.linux.org.uk>
+Message-ID: <20090225213407.4a932f92@hyperion.delvare>
+
+
+From: Russell King <rmk+kernel@arm.linux.org.uk>
+
+commit 531660ef5604c75de6fdead9da1304051af17c09 upstream
+
+Add the necessary i2c_board_info structure to fix the lack of PCF8583
+RTC on RiscPC.
+
+Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
+Signed-off-by: Jean Delvare <khali@linux-fr.org>
+Cc: Alessandro Zummo <a.zummo@towertech.it>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ arch/arm/mach-rpc/riscpc.c     |    6 ++++++
+ drivers/i2c/busses/i2c-acorn.c |    3 ++-
+ 2 files changed, 8 insertions(+), 1 deletion(-)
+
+--- a/arch/arm/mach-rpc/riscpc.c
++++ b/arch/arm/mach-rpc/riscpc.c
+@@ -19,6 +19,7 @@
+ #include <linux/serial_8250.h>
+ #include <linux/ata_platform.h>
+ #include <linux/io.h>
++#include <linux/i2c.h>
+ #include <asm/elf.h>
+ #include <asm/mach-types.h>
+@@ -201,8 +202,13 @@ static struct platform_device *devs[] __
+       &pata_device,
+ };
++static struct i2c_board_info i2c_rtc = {
++      I2C_BOARD_INFO("pcf8583", 0x50)
++};
++
+ static int __init rpc_init(void)
+ {
++      i2c_register_board_info(0, &i2c_rtc, 1);
+       return platform_add_devices(devs, ARRAY_SIZE(devs));
+ }
+--- a/drivers/i2c/busses/i2c-acorn.c
++++ b/drivers/i2c/busses/i2c-acorn.c
+@@ -84,6 +84,7 @@ static struct i2c_algo_bit_data ioc_data
+ static struct i2c_adapter ioc_ops = {
+       .id                     = I2C_HW_B_IOC,
++      .nr                     = 0,
+       .algo_data              = &ioc_data,
+ };
+@@ -91,7 +92,7 @@ static int __init i2c_ioc_init(void)
+ {
+       force_ones = FORCE_ONES | SCL | SDA;
+-      return i2c_bit_add_bus(&ioc_ops);
++      return i2c_bit_add_numbered_bus(&ioc_ops);
+ }
+ module_init(i2c_ioc_init);
diff --git a/queue-2.6.28/crypto-api-fix-algorithm-test-race-that-broke-aead-initialisation.patch b/queue-2.6.28/crypto-api-fix-algorithm-test-race-that-broke-aead-initialisation.patch
new file mode 100644 (file)
index 0000000..77b349f
--- /dev/null
@@ -0,0 +1,62 @@
+From b8e15992b420d09dae831125a623c474c8637cee Mon Sep 17 00:00:00 2001
+From: Herbert Xu <herbert@gondor.apana.org.au>
+Date: Wed, 28 Jan 2009 14:09:59 +1100
+Subject: crypto: api - Fix algorithm test race that broke aead initialisation
+
+From: Herbert Xu <herbert@gondor.apana.org.au>
+
+commit b8e15992b420d09dae831125a623c474c8637cee upstream.
+
+When we complete a test we'll notify everyone waiting on it, drop
+the mutex, and then remove the test larval (after reacquiring the
+mutex).  If one of the notified parties tries to register another
+algorithm with the same driver name prior to the removal of the
+test larval, they will fail with EEXIST as only one algorithm of
+a given name can be tested at any time.
+
+This broke the initialisation of aead and givcipher algorithms as
+they will register two algorithms with the same driver name, in
+sequence.
+
+This patch fixes the problem by marking the larval as dead before
+we drop the mutex, and also ignoring all dead or dying algorithms
+on the registration path.
+
+Tested-by: Andreas Steffen <andreas.steffen@strongswan.org>
+Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>
+Cc: Kerin Millar <kerframil@gmail.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ crypto/algapi.c |    6 +++++-
+ 1 file changed, 5 insertions(+), 1 deletion(-)
+
+--- a/crypto/algapi.c
++++ b/crypto/algapi.c
+@@ -149,6 +149,9 @@ static struct crypto_larval *__crypto_re
+               if (q == alg)
+                       goto err;
++              if (crypto_is_moribund(q))
++                      continue;
++
+               if (crypto_is_larval(q)) {
+                       if (!strcmp(alg->cra_driver_name, q->cra_driver_name))
+                               goto err;
+@@ -197,7 +200,7 @@ void crypto_alg_tested(const char *name,
+       down_write(&crypto_alg_sem);
+       list_for_each_entry(q, &crypto_alg_list, cra_list) {
+-              if (!crypto_is_larval(q))
++              if (crypto_is_moribund(q) || !crypto_is_larval(q))
+                       continue;
+               test = (struct crypto_larval *)q;
+@@ -210,6 +213,7 @@ void crypto_alg_tested(const char *name,
+       goto unlock;
+ found:
++      q->cra_flags |= CRYPTO_ALG_DEAD;
+       alg = test->adult;
+       if (err || list_empty(&alg->cra_list))
+               goto complete;
diff --git a/queue-2.6.28/drm-i915-add-missing-userland-definitions-for-gem-init-execbuffer.patch b/queue-2.6.28/drm-i915-add-missing-userland-definitions-for-gem-init-execbuffer.patch
new file mode 100644 (file)
index 0000000..01b5099
--- /dev/null
@@ -0,0 +1,30 @@
+From 8d391aa410ecb230fc4c3147b94eec25b9f3c20f Mon Sep 17 00:00:00 2001
+From: Eric Anholt <eric@anholt.net>
+Date: Wed, 17 Dec 2008 22:32:14 -0800
+Subject: drm/i915: Add missing userland definitions for gem init/execbuffer.
+
+From: Eric Anholt <eric@anholt.net>
+
+commit 8d391aa410ecb230fc4c3147b94eec25b9f3c20f upstream.
+
+fdo bug #19132.
+
+Signed-off-by: Eric Anholt <eric@anholt.net>
+Signed-off-by: Dave Airlie <airlied@redhat.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ include/drm/i915_drm.h |    2 ++
+ 1 file changed, 2 insertions(+)
+
+--- a/include/drm/i915_drm.h
++++ b/include/drm/i915_drm.h
+@@ -177,6 +177,8 @@ typedef struct _drm_i915_sarea {
+ #define DRM_IOCTL_I915_SET_VBLANK_PIPE        DRM_IOW( DRM_COMMAND_BASE + DRM_I915_SET_VBLANK_PIPE, drm_i915_vblank_pipe_t)
+ #define DRM_IOCTL_I915_GET_VBLANK_PIPE        DRM_IOR( DRM_COMMAND_BASE + DRM_I915_GET_VBLANK_PIPE, drm_i915_vblank_pipe_t)
+ #define DRM_IOCTL_I915_VBLANK_SWAP    DRM_IOWR(DRM_COMMAND_BASE + DRM_I915_VBLANK_SWAP, drm_i915_vblank_swap_t)
++#define DRM_IOCTL_I915_GEM_INIT               DRM_IOW(DRM_COMMAND_BASE + DRM_I915_GEM_INIT, struct drm_i915_gem_init)
++#define DRM_IOCTL_I915_GEM_EXECBUFFER DRM_IOW(DRM_COMMAND_BASE + DRM_I915_GEM_EXECBUFFER, struct drm_i915_gem_execbuffer)
+ #define DRM_IOCTL_I915_GEM_PIN                DRM_IOWR(DRM_COMMAND_BASE + DRM_I915_GEM_PIN, struct drm_i915_gem_pin)
+ #define DRM_IOCTL_I915_GEM_UNPIN      DRM_IOW(DRM_COMMAND_BASE + DRM_I915_GEM_UNPIN, struct drm_i915_gem_unpin)
+ #define DRM_IOCTL_I915_GEM_BUSY               DRM_IOWR(DRM_COMMAND_BASE + DRM_I915_GEM_BUSY, struct drm_i915_gem_busy)
diff --git a/queue-2.6.28/ext4-add-fallback-for-find_group_flex.patch b/queue-2.6.28/ext4-add-fallback-for-find_group_flex.patch
new file mode 100644 (file)
index 0000000..3d52d29
--- /dev/null
@@ -0,0 +1,49 @@
+From tytso@mit.edu  Thu Mar 12 22:52:01 2009
+From: "Theodore Ts'o" <tytso@mit.edu>
+Date: Thu,  5 Mar 2009 02:35:14 -0500
+Subject: ext4: Add fallback for find_group_flex
+To: stable@kernel.org
+Cc: Ext4 Developers List <linux-ext4@vger.kernel.org>, "Theodore Ts'o" <tytso@mit.edu>
+Message-ID: <1236238515-8479-1-git-send-email-tytso@mit.edu>
+
+From: "Theodore Ts'o" <tytso@mit.edu>
+
+(cherry picked from commit 05bf9e839d9de4e8a094274a0a2fd07beb47eaf1)
+
+This is a workaround for find_group_flex() which badly needs to be
+replaced.  One of its problems (besides ignoring the Orlov algorithm)
+is that it is a bit hyperactive about returning failure under
+suspicious circumstances.  This can lead to spurious ENOSPC failures
+even when there are inodes still available.
+
+Work around this for now by retrying the search using
+find_group_other() if find_group_flex() returns -1.  If
+find_group_other() succeeds when find_group_flex() has failed, log a
+warning message.
+
+A better block/inode allocator that will fix this problem for real has
+been queued up for the next merge window.
+
+Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ fs/ext4/ialloc.c |    7 +++++++
+ 1 file changed, 7 insertions(+)
+
+--- a/fs/ext4/ialloc.c
++++ b/fs/ext4/ialloc.c
+@@ -703,6 +703,13 @@ struct inode *ext4_new_inode(handle_t *h
+       if (sbi->s_log_groups_per_flex) {
+               ret2 = find_group_flex(sb, dir, &group);
++              if (ret2 == -1) {
++                      ret2 = find_group_other(sb, dir, &group);
++                      if (ret2 == 0 && printk_ratelimit())
++                              printk(KERN_NOTICE "ext4: find_group_flex "
++                                     "failed, fallback succeeded dir %lu\n",
++                                     dir->i_ino);
++              }
+               goto got_group;
+       }
diff --git a/queue-2.6.28/ext4-fix-deadlock-in-ext4_write_begin-and-ext4_da_write_begin.patch b/queue-2.6.28/ext4-fix-deadlock-in-ext4_write_begin-and-ext4_da_write_begin.patch
new file mode 100644 (file)
index 0000000..4084a3e
--- /dev/null
@@ -0,0 +1,62 @@
+From tytso@mit.edu  Thu Mar 12 22:52:20 2009
+From: "Theodore Ts'o" <tytso@mit.edu>
+Date: Thu,  5 Mar 2009 02:35:15 -0500
+Subject: ext4: Fix deadlock in ext4_write_begin() and ext4_da_write_begin()
+To: stable@kernel.org
+Cc: "Theodore Ts'o" <tytso@mit.edu>, Ext4 Developers List <linux-ext4@vger.kernel.org>, Jan Kara <jack@suse.cz>
+Message-ID: <1236238515-8479-2-git-send-email-tytso@mit.edu>
+
+
+From: Jan Kara <jack@suse.cz>
+
+(cherry picked from commit ebd3610b110bbb18ea6f9f2aeed1e1068c537227)
+
+Functions ext4_write_begin() and ext4_da_write_begin() call
+grab_cache_page_write_begin() without AOP_FLAG_NOFS. Thus it
+can happen that page reclaim is triggered in that function
+and it recurses back into the filesystem (or some other filesystem).
+But this can lead to various problems as a transaction is already
+started at that point. Add the necessary flag.
+
+http://bugzilla.kernel.org/show_bug.cgi?id=11688
+
+Signed-off-by: Jan Kara <jack@suse.cz>
+Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ fs/ext4/inode.c |    9 ++++++++-
+ 1 file changed, 8 insertions(+), 1 deletion(-)
+
+--- a/fs/ext4/inode.c
++++ b/fs/ext4/inode.c
+@@ -1347,6 +1347,10 @@ retry:
+               goto out;
+       }
++      /* We cannot recurse into the filesystem as the transaction is already
++       * started */
++      flags |= AOP_FLAG_NOFS;
++
+       page = grab_cache_page_write_begin(mapping, index, flags);
+       if (!page) {
+               ext4_journal_stop(handle);
+@@ -1356,7 +1360,7 @@ retry:
+       *pagep = page;
+       ret = block_write_begin(file, mapping, pos, len, flags, pagep, fsdata,
+-                                                      ext4_get_block);
++                              ext4_get_block);
+       if (!ret && ext4_should_journal_data(inode)) {
+               ret = walk_page_buffers(handle, page_buffers(page),
+@@ -2603,6 +2607,9 @@ retry:
+               ret = PTR_ERR(handle);
+               goto out;
+       }
++      /* We cannot recurse into the filesystem as the transaction is already
++       * started */
++      flags |= AOP_FLAG_NOFS;
+       page = grab_cache_page_write_begin(mapping, index, flags);
+       if (!page) {
diff --git a/queue-2.6.28/ext4-fix-lockdep-warning.patch b/queue-2.6.28/ext4-fix-lockdep-warning.patch
new file mode 100644 (file)
index 0000000..6769713
--- /dev/null
@@ -0,0 +1,79 @@
+From tytso@mit.edu  Thu Mar 12 22:50:38 2009
+From: Aneesh Kumar K.V <aneesh.kumar@linux.vnet.ibm.com>
+Date: Tue, 24 Feb 2009 12:14:45 -0500
+Subject: ext4: Fix lockdep warning
+To: stable@kernel.org
+Cc: "Theodore Ts'o" <tytso@mit.edu>, "Aneesh Kumar K.V" <aneesh.kumar@linux.vnet.ibm.com>
+Message-ID: <1235495688-8044-5-git-send-email-tytso@mit.edu>
+
+
+From: Aneesh Kumar K.V <aneesh.kumar@linux.vnet.ibm.com>
+
+(cherry picked from commit ba4439165f0f0d25b2fe065cf0c1ff8130b802eb)
+
+We should not call ext4_mb_add_n_trim while holding alloc_semp.
+
+    =============================================
+    [ INFO: possible recursive locking detected ]
+    2.6.29-rc4-git1-dirty #124
+    ---------------------------------------------
+    ffsb/3116 is trying to acquire lock:
+     (&meta_group_info[i]->alloc_sem){----}, at: [<ffffffff8035a6e8>]
+     ext4_mb_load_buddy+0xd2/0x343
+
+    but task is already holding lock:
+     (&meta_group_info[i]->alloc_sem){----}, at: [<ffffffff8035a6e8>]
+     ext4_mb_load_buddy+0xd2/0x343
+
+http://bugzilla.kernel.org/show_bug.cgi?id=12672
+
+Signed-off-by: Aneesh Kumar K.V <aneesh.kumar@linux.vnet.ibm.com>
+Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ fs/ext4/mballoc.c |   29 ++++++++++++++++-------------
+ 1 file changed, 16 insertions(+), 13 deletions(-)
+
+--- a/fs/ext4/mballoc.c
++++ b/fs/ext4/mballoc.c
+@@ -4456,23 +4456,26 @@ static int ext4_mb_release_context(struc
+                       pa->pa_free -= ac->ac_b_ex.fe_len;
+                       pa->pa_len -= ac->ac_b_ex.fe_len;
+                       spin_unlock(&pa->pa_lock);
+-                      /*
+-                       * We want to add the pa to the right bucket.
+-                       * Remove it from the list and while adding
+-                       * make sure the list to which we are adding
+-                       * doesn't grow big.
+-                       */
+-                      if (likely(pa->pa_free)) {
+-                              spin_lock(pa->pa_obj_lock);
+-                              list_del_rcu(&pa->pa_inode_list);
+-                              spin_unlock(pa->pa_obj_lock);
+-                              ext4_mb_add_n_trim(ac);
+-                      }
+               }
+-              ext4_mb_put_pa(ac, ac->ac_sb, pa);
+       }
+       if (ac->alloc_semp)
+               up_read(ac->alloc_semp);
++      if (pa) {
++              /*
++               * We want to add the pa to the right bucket.
++               * Remove it from the list and while adding
++               * make sure the list to which we are adding
++               * doesn't grow big.  We need to release
++               * alloc_semp before calling ext4_mb_add_n_trim()
++               */
++              if (pa->pa_linear && likely(pa->pa_free)) {
++                      spin_lock(pa->pa_obj_lock);
++                      list_del_rcu(&pa->pa_inode_list);
++                      spin_unlock(pa->pa_obj_lock);
++                      ext4_mb_add_n_trim(ac);
++              }
++              ext4_mb_put_pa(ac, ac->ac_sb, pa);
++      }
+       if (ac->ac_bitmap_page)
+               page_cache_release(ac->ac_bitmap_page);
+       if (ac->ac_buddy_page)
diff --git a/queue-2.6.28/ext4-fix-null-dereference-in-ext4_ext_migrate-s-error-handling.patch b/queue-2.6.28/ext4-fix-null-dereference-in-ext4_ext_migrate-s-error-handling.patch
new file mode 100644 (file)
index 0000000..a8e5ff0
--- /dev/null
@@ -0,0 +1,56 @@
+From tytso@mit.edu  Thu Mar 12 22:51:42 2009
+From: Dan Carpenter <error27@gmail.com>
+Date: Tue, 24 Feb 2009 12:14:48 -0500
+Subject: ext4: Fix NULL dereference in ext4_ext_migrate()'s error handling
+To: stable@kernel.org
+Cc: "Theodore Ts'o" <tytso@mit.edu>, Dan Carpenter <error27@gmail.com>
+Message-ID: <1235495688-8044-8-git-send-email-tytso@mit.edu>
+
+
+From: Dan Carpenter <error27@gmail.com>
+
+(cherry picked from commit 090542641de833c6f756895fc2f139f046e298f9)
+
+This was found through a code checker (http://repo.or.cz/w/smatch.git/).
+It looks like you might be able to trigger the error by trying to migrate
+a readonly file system.
+
+Signed-off-by: Dan Carpenter <error27@gmail.com>
+Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ fs/ext4/migrate.c |    8 +++-----
+ 1 file changed, 3 insertions(+), 5 deletions(-)
+
+--- a/fs/ext4/migrate.c
++++ b/fs/ext4/migrate.c
+@@ -480,7 +480,7 @@ int ext4_ext_migrate(struct inode *inode
+                                       + 1);
+       if (IS_ERR(handle)) {
+               retval = PTR_ERR(handle);
+-              goto err_out;
++              return retval;
+       }
+       tmp_inode = ext4_new_inode(handle,
+                               inode->i_sb->s_root->d_inode,
+@@ -488,8 +488,7 @@ int ext4_ext_migrate(struct inode *inode
+       if (IS_ERR(tmp_inode)) {
+               retval = -ENOMEM;
+               ext4_journal_stop(handle);
+-              tmp_inode = NULL;
+-              goto err_out;
++              return retval;
+       }
+       i_size_write(tmp_inode, i_size_read(inode));
+       /*
+@@ -617,8 +616,7 @@ err_out:
+       ext4_journal_stop(handle);
+-      if (tmp_inode)
+-              iput(tmp_inode);
++      iput(tmp_inode);
+       return retval;
+ }
diff --git a/queue-2.6.28/ext4-fix-to-read-empty-directory-blocks-correctly-in-64k.patch b/queue-2.6.28/ext4-fix-to-read-empty-directory-blocks-correctly-in-64k.patch
new file mode 100644 (file)
index 0000000..6fe137b
--- /dev/null
@@ -0,0 +1,47 @@
+From tytso@mit.edu  Thu Mar 12 22:50:20 2009
+From: Wei Yongjun <yjwei@cn.fujitsu.com>
+Date: Tue, 24 Feb 2009 12:14:44 -0500
+Subject: ext4: Fix to read empty directory blocks correctly in 64k
+To: stable@kernel.org
+Cc: "Theodore Ts'o" <tytso@mit.edu>, Wei Yongjun <yjwei@cn.fujitsu.com>
+Message-ID: <1235495688-8044-4-git-send-email-tytso@mit.edu>
+
+
+From: Wei Yongjun <yjwei@cn.fujitsu.com>
+
+(cherry picked from commit 7be2baaa0322c59ba888aa5260a8c130666acd41)
+
+The rec_len field in the directory entry is 16 bits, so there was a
+problem representing rec_len for filesystems with a 64k block size in
+the case where the directory entry takes the entire 64k block.
+Unfortunately, there were two schemes that were proposed; one where
+all zeros meant 65536 and one where all ones (65535) meant 65536.
+E2fsprogs used 0, whereas the kernel used 65535.  Oops.  Fortunately
+this case happens extremely rarely, with the most common case being
+the lost+found directory, created by mke2fs.
+
+So we will be liberal in what we accept, and accept both encodings,
+but we will continue to encode 65536 as 65535.  This will require a
+change in e2fsprogs, but with fortunately ext4 filesystems normally
+have the dir_index feature enabled, which precludes having a
+completely empty directory block.
+
+Signed-off-by: Wei Yongjun <yjwei@cn.fujitsu.com>
+Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ fs/ext4/ext4.h |    2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+--- a/fs/ext4/ext4.h
++++ b/fs/ext4/ext4.h
+@@ -862,7 +862,7 @@ static inline unsigned ext4_rec_len_from
+ {
+       unsigned len = le16_to_cpu(dlen);
+-      if (len == EXT4_MAX_REC_LEN)
++      if (len == EXT4_MAX_REC_LEN || len == 0)
+               return 1 << 16;
+       return len;
+ }
diff --git a/queue-2.6.28/ext4-implement-range_cyclic-in-ext4_da_writepages-instead-of-write_cache_pages.patch b/queue-2.6.28/ext4-implement-range_cyclic-in-ext4_da_writepages-instead-of-write_cache_pages.patch
new file mode 100644 (file)
index 0000000..dfc1bf4
--- /dev/null
@@ -0,0 +1,101 @@
+From tytso@mit.edu  Thu Mar 12 22:51:22 2009
+From: Aneesh Kumar K.V <aneesh.kumar@linux.vnet.ibm.com>
+Date: Tue, 24 Feb 2009 12:14:47 -0500
+Subject: ext4: Implement range_cyclic in ext4_da_writepages instead of write_cache_pages
+To: stable@kernel.org
+Cc: "Theodore Ts'o" <tytso@mit.edu>, "Aneesh Kumar K.V" <aneesh.kumar@linux.vnet.ibm.com>
+Message-ID: <1235495688-8044-7-git-send-email-tytso@mit.edu>
+
+
+From: Aneesh Kumar K.V <aneesh.kumar@linux.vnet.ibm.com>
+
+(cherry picked from commit 2acf2c261b823d9d9ed954f348b97620297a36b5)
+
+With delayed allocation we lock the page in write_cache_pages() and
+try to build an in memory extent of contiguous blocks.  This is needed
+so that we can get large contiguous blocks request.  If range_cyclic
+mode is enabled, write_cache_pages() will loop back to the 0 index if
+no I/O has been done yet, and try to start writing from the beginning
+of the range.  That causes an attempt to take the page lock of lower
+index page while holding the page lock of higher index page, which can
+cause a dead lock with another writeback thread.
+
+The solution is to implement the range_cyclic behavior in
+ext4_da_writepages() instead.
+
+http://bugzilla.kernel.org/show_bug.cgi?id=12579
+
+Signed-off-by: Aneesh Kumar K.V <aneesh.kumar@linux.vnet.ibm.com>
+Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ fs/ext4/inode.c |   21 +++++++++++++++++++--
+ 1 file changed, 19 insertions(+), 2 deletions(-)
+
+--- a/fs/ext4/inode.c
++++ b/fs/ext4/inode.c
+@@ -2402,6 +2402,7 @@ static int ext4_da_writepages(struct add
+       struct inode *inode = mapping->host;
+       int no_nrwrite_index_update;
+       long pages_written = 0, pages_skipped;
++      int range_cyclic, cycled = 1, io_done = 0;
+       int needed_blocks, ret = 0, nr_to_writebump = 0;
+       struct ext4_sb_info *sbi = EXT4_SB(mapping->host->i_sb);
+@@ -2439,9 +2440,15 @@ static int ext4_da_writepages(struct add
+       if (wbc->range_start == 0 && wbc->range_end == LLONG_MAX)
+               range_whole = 1;
+-      if (wbc->range_cyclic)
++      range_cyclic = wbc->range_cyclic;
++      if (wbc->range_cyclic) {
+               index = mapping->writeback_index;
+-      else
++              if (index)
++                      cycled = 0;
++              wbc->range_start = index << PAGE_CACHE_SHIFT;
++              wbc->range_end  = LLONG_MAX;
++              wbc->range_cyclic = 0;
++      } else
+               index = wbc->range_start >> PAGE_CACHE_SHIFT;
+       mpd.wbc = wbc;
+@@ -2455,6 +2462,7 @@ static int ext4_da_writepages(struct add
+       wbc->no_nrwrite_index_update = 1;
+       pages_skipped = wbc->pages_skipped;
++retry:
+       while (!ret && wbc->nr_to_write > 0) {
+               /*
+@@ -2497,6 +2505,7 @@ static int ext4_da_writepages(struct add
+                       pages_written += mpd.pages_written;
+                       wbc->pages_skipped = pages_skipped;
+                       ret = 0;
++                      io_done = 1;
+               } else if (wbc->nr_to_write)
+                       /*
+                        * There is no more writeout needed
+@@ -2505,6 +2514,13 @@ static int ext4_da_writepages(struct add
+                        */
+                       break;
+       }
++      if (!io_done && !cycled) {
++              cycled = 1;
++              index = 0;
++              wbc->range_start = index << PAGE_CACHE_SHIFT;
++              wbc->range_end  = mapping->writeback_index - 1;
++              goto retry;
++      }
+       if (pages_skipped != wbc->pages_skipped)
+               printk(KERN_EMERG "This should not happen leaving %s "
+                               "with nr_to_write = %ld ret = %d\n",
+@@ -2512,6 +2528,7 @@ static int ext4_da_writepages(struct add
+       /* Update index */
+       index += pages_written;
++      wbc->range_cyclic = range_cyclic;
+       if (wbc->range_cyclic || (range_whole && wbc->nr_to_write > 0))
+               /*
+                * set the writeback_index so that range_cyclic
diff --git a/queue-2.6.28/ext4-initialize-preallocation-list_head-s-properly.patch b/queue-2.6.28/ext4-initialize-preallocation-list_head-s-properly.patch
new file mode 100644 (file)
index 0000000..ffefe3f
--- /dev/null
@@ -0,0 +1,45 @@
+From tytso@mit.edu  Thu Mar 12 22:51:02 2009
+From: Aneesh Kumar K.V <aneesh.kumar@linux.vnet.ibm.com>
+Date: Tue, 24 Feb 2009 12:14:46 -0500
+Subject: ext4: Initialize preallocation list_head's properly
+To: stable@kernel.org
+Cc: "Theodore Ts'o" <tytso@mit.edu>, "Aneesh Kumar K.V" <aneesh.kumar@linux.vnet.ibm.com>
+Message-ID: <1235495688-8044-6-git-send-email-tytso@mit.edu>
+
+
+From: Aneesh Kumar K.V <aneesh.kumar@linux.vnet.ibm.com>
+
+(cherry picked from commit d794bf8e0936dce45104565cd48c571061f4c1e3)
+
+When creating a new ext4_prealloc_space structure, we have to
+initialize its list_head pointers before we add them to any prealloc
+lists.  Otherwise, with list debug enabled, we will get list
+corruption warnings.
+
+Signed-off-by: Aneesh Kumar K.V <aneesh.kumar@linux.vnet.ibm.com>
+Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ fs/ext4/mballoc.c |    3 +++
+ 1 file changed, 3 insertions(+)
+
+--- a/fs/ext4/mballoc.c
++++ b/fs/ext4/mballoc.c
+@@ -3690,6 +3690,8 @@ ext4_mb_new_inode_pa(struct ext4_allocat
+       pa->pa_free = pa->pa_len;
+       atomic_set(&pa->pa_count, 1);
+       spin_lock_init(&pa->pa_lock);
++      INIT_LIST_HEAD(&pa->pa_inode_list);
++      INIT_LIST_HEAD(&pa->pa_group_list);
+       pa->pa_deleted = 0;
+       pa->pa_linear = 0;
+@@ -3748,6 +3750,7 @@ ext4_mb_new_group_pa(struct ext4_allocat
+       atomic_set(&pa->pa_count, 1);
+       spin_lock_init(&pa->pa_lock);
+       INIT_LIST_HEAD(&pa->pa_inode_list);
++      INIT_LIST_HEAD(&pa->pa_group_list);
+       pa->pa_deleted = 0;
+       pa->pa_linear = 1;
diff --git a/queue-2.6.28/hid-move-tmff-and-zpff-devices-from-ignore_list-to-blacklist.patch b/queue-2.6.28/hid-move-tmff-and-zpff-devices-from-ignore_list-to-blacklist.patch
new file mode 100644 (file)
index 0000000..3012f01
--- /dev/null
@@ -0,0 +1,68 @@
+From jkosina@suse.cz  Thu Mar 12 23:07:31 2009
+From: Jiri Kosina <jkosina@suse.cz>
+Date: Mon, 2 Mar 2009 16:16:10 +0100 (CET)
+Subject: HID: move tmff and zpff devices from ignore_list to blacklist
+To: stable@kernel.org
+Cc: Anssi Hannula <anssi.hannula@gmail.com>
+Message-ID: <alpine.LNX.1.10.0903021614570.11667@jikos.suse.cz>
+
+
+From: Jiri Kosina <jkosina@suse.cz>
+
+[ upstream commit daedb3d6a91f9626ab4c921378ac52e44de833d5 ]
+
+From: Anssi Hannula <anssi.hannula@gmail.com>
+Subject: HID: move tmff and zpff devices from ignore_list to blacklist
+
+The devices handled by hid-tmff and hid-zpff were added in the
+hid_ignore_list[] instead of hid_blacklist[] in hid-core.c, thus
+disabling them completely.
+
+hid_ignore_list[] causes hid layer to skip the device, while
+hid_blacklist[] indicates there is a specific driver in hid bus.
+
+Re-enable the devices by moving them to the correct list.
+
+Signed-off-by: Anssi Hannula <anssi.hannula@gmail.com>
+Signed-off-by: Jiri Kosina <jkosina@suse.cz>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ drivers/hid/hid-core.c |   12 ++++++------
+ 1 file changed, 6 insertions(+), 6 deletions(-)
+
+--- a/drivers/hid/hid-core.c
++++ b/drivers/hid/hid-core.c
+@@ -1302,6 +1302,12 @@ static const struct hid_device_id hid_bl
+       { HID_USB_DEVICE(USB_VENDOR_ID_SONY, USB_DEVICE_ID_SONY_PS3_CONTROLLER) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_SONY, USB_DEVICE_ID_SONY_VAIO_VGX_MOUSE) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_SUNPLUS, USB_DEVICE_ID_SUNPLUS_WDESKTOP) },
++      { HID_USB_DEVICE(USB_VENDOR_ID_THRUSTMASTER, 0xb300) },
++      { HID_USB_DEVICE(USB_VENDOR_ID_THRUSTMASTER, 0xb304) },
++      { HID_USB_DEVICE(USB_VENDOR_ID_THRUSTMASTER, 0xb651) },
++      { HID_USB_DEVICE(USB_VENDOR_ID_THRUSTMASTER, 0xb654) },
++      { HID_USB_DEVICE(USB_VENDOR_ID_ZEROPLUS, 0x0005) },
++      { HID_USB_DEVICE(USB_VENDOR_ID_ZEROPLUS, 0x0030) },
+       { HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_APPLE, 0x030c) },
+       { HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_MICROSOFT, USB_DEVICE_ID_MS_PRESENTER_8K_BT) },
+@@ -1529,10 +1535,6 @@ static const struct hid_device_id hid_ig
+       { HID_USB_DEVICE(USB_VENDOR_ID_SOUNDGRAPH, USB_DEVICE_ID_SOUNDGRAPH_IMON_LCD3) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_TENX, USB_DEVICE_ID_TENX_IBUDDY1) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_TENX, USB_DEVICE_ID_TENX_IBUDDY2) },
+-      { HID_USB_DEVICE(USB_VENDOR_ID_THRUSTMASTER, 0xb300) },
+-      { HID_USB_DEVICE(USB_VENDOR_ID_THRUSTMASTER, 0xb304) },
+-      { HID_USB_DEVICE(USB_VENDOR_ID_THRUSTMASTER, 0xb651) },
+-      { HID_USB_DEVICE(USB_VENDOR_ID_THRUSTMASTER, 0xb654) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_VERNIER, USB_DEVICE_ID_VERNIER_LABPRO) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_VERNIER, USB_DEVICE_ID_VERNIER_GOTEMP) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_VERNIER, USB_DEVICE_ID_VERNIER_SKIP) },
+@@ -1543,8 +1545,6 @@ static const struct hid_device_id hid_ig
+       { HID_USB_DEVICE(USB_VENDOR_ID_WISEGROUP, USB_DEVICE_ID_1_PHIDGETSERVO_20) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_WISEGROUP, USB_DEVICE_ID_8_8_4_IF_KIT) },
+       { HID_USB_DEVICE(USB_VENDOR_ID_YEALINK, USB_DEVICE_ID_YEALINK_P1K_P4K_B2K) },
+-      { HID_USB_DEVICE(USB_VENDOR_ID_ZEROPLUS, 0x0005) },
+-      { HID_USB_DEVICE(USB_VENDOR_ID_ZEROPLUS, 0x0030) },
+       { }
+ };
diff --git a/queue-2.6.28/hwmon-hide-misleading-error-message.patch b/queue-2.6.28/hwmon-hide-misleading-error-message.patch
new file mode 100644 (file)
index 0000000..f69d625
--- /dev/null
@@ -0,0 +1,38 @@
+From khali@linux-fr.org  Thu Mar 12 23:16:17 2009
+From: Jean Delvare <khali@linux-fr.org>
+Date: Sat, 21 Feb 2009 12:00:20 +0100
+Subject: hwmon: (f71882fg) Hide misleading error message
+To: stable@kernel.org
+Message-ID: <20090221120020.35dafe74@hyperion.delvare>
+
+From: Jean Delvare <khali@linux-fr.org>
+
+commit 603eaa1bdd3e0402085e815cc531bb0a32827a9e upstream
+
+If the F71882FG chip is at address 0x4e, then the probe at 0x2e will
+fail with the following message in the logs:
+f71882fg: Not a Fintek device
+
+This is misleading because there is a Fintek device, just at a
+different address. So I propose to degrade this message to a debug
+message.
+
+Signed-off-by: Jean Delvare <khali@linux-fr.org>
+Acked-by: Hans de Goede <hdegoede@redhat.com>
+
+
+---
+ drivers/hwmon/f71882fg.c |    2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+--- a/drivers/hwmon/f71882fg.c
++++ b/drivers/hwmon/f71882fg.c
+@@ -837,7 +837,7 @@ static int __init f71882fg_find(int sioa
+       devid = superio_inw(sioaddr, SIO_REG_MANID);
+       if (devid != SIO_FINTEK_ID) {
+-              printk(KERN_INFO DRVNAME ": Not a Fintek device\n");
++              pr_debug(DRVNAME ": Not a Fintek device\n");
+               goto exit;
+       }
diff --git a/queue-2.6.28/i2c-fix-misplaced-parentheses.patch b/queue-2.6.28/i2c-fix-misplaced-parentheses.patch
new file mode 100644 (file)
index 0000000..60e9d85
--- /dev/null
@@ -0,0 +1,35 @@
+From khali@linux-fr.org  Thu Mar 12 23:10:15 2009
+From: Roel Kluin <roel.kluin@gmail.com>
+Date: Wed, 25 Feb 2009 21:24:40 +0100
+Subject: i2c: Fix misplaced parentheses
+To: stable@kernel.org
+Message-ID: <20090225212440.3b6d0001@hyperion.delvare>
+
+
+From: Roel Kluin <roel.kluin@gmail.com>
+
+commit f29d2e0275a4f03ef2fd158e484508dcb0c64efb upstream
+
+Fix misplaced parentheses.
+
+Signed-off-by: Roel Kluin <roel.kluin@gmail.com>
+Signed-off-by: Jean Delvare <khali@linux-fr.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+
+---
+ drivers/i2c/i2c-core.c |    3 ++-
+ 1 file changed, 2 insertions(+), 1 deletion(-)
+
+--- a/drivers/i2c/i2c-core.c
++++ b/drivers/i2c/i2c-core.c
+@@ -1831,7 +1831,8 @@ static s32 i2c_smbus_xfer_emulated(struc
+       case I2C_SMBUS_QUICK:
+               msg[0].len = 0;
+               /* Special case: The read/write field is used as data */
+-              msg[0].flags = flags | (read_write==I2C_SMBUS_READ)?I2C_M_RD:0;
++              msg[0].flags = flags | (read_write == I2C_SMBUS_READ ?
++                                      I2C_M_RD : 0);
+               num = 1;
+               break;
+       case I2C_SMBUS_BYTE:
diff --git a/queue-2.6.28/i2c-timeouts-reach-1.patch b/queue-2.6.28/i2c-timeouts-reach-1.patch
new file mode 100644 (file)
index 0000000..a682bab
--- /dev/null
@@ -0,0 +1,60 @@
+From khali@linux-fr.org  Thu Mar 12 23:09:33 2009
+From: Roel Kluin <roel.kluin@gmail.com>
+Date: Wed, 25 Feb 2009 21:26:21 +0100
+Subject: i2c: Timeouts reach -1
+To: stable@kernel.org
+Message-ID: <20090225212621.4714ef35@hyperion.delvare>
+
+
+From: Roel Kluin <roel.kluin@gmail.com>
+
+commit a746b578d8406b2db0e9f0d040061bc1f78433cf upstream
+
+With a postfix decrement these timeouts reach -1 rather than 0, but
+after the loop it is tested whether they have become 0.
+
+As pointed out by Jean Delvare, the condition we are waiting for should
+also be tested before the timeout. With the current order, you could
+exit with a timeout error while the job is actually done.
+
+Signed-off-by: Roel Kluin <roel.kluin@gmail.com>
+Signed-off-by: Jean Delvare <khali@linux-fr.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+
+---
+ drivers/i2c/busses/i2c-amd8111.c |    4 ++--
+ drivers/i2c/busses/i2c-pxa.c     |    2 +-
+ 2 files changed, 3 insertions(+), 3 deletions(-)
+
+--- a/drivers/i2c/busses/i2c-amd8111.c
++++ b/drivers/i2c/busses/i2c-amd8111.c
+@@ -72,7 +72,7 @@ static unsigned int amd_ec_wait_write(st
+ {
+       int timeout = 500;
+-      while (timeout-- && (inb(smbus->base + AMD_EC_SC) & AMD_EC_SC_IBF))
++      while ((inb(smbus->base + AMD_EC_SC) & AMD_EC_SC_IBF) && --timeout)
+               udelay(1);
+       if (!timeout) {
+@@ -88,7 +88,7 @@ static unsigned int amd_ec_wait_read(str
+ {
+       int timeout = 500;
+-      while (timeout-- && (~inb(smbus->base + AMD_EC_SC) & AMD_EC_SC_OBF))
++      while ((~inb(smbus->base + AMD_EC_SC) & AMD_EC_SC_OBF) && --timeout)
+               udelay(1);
+       if (!timeout) {
+--- a/drivers/i2c/busses/i2c-pxa.c
++++ b/drivers/i2c/busses/i2c-pxa.c
+@@ -644,7 +644,7 @@ static int i2c_pxa_do_pio_xfer(struct px
+       i2c_pxa_start_message(i2c);
+-      while (timeout-- && i2c->msg_num > 0) {
++      while (i2c->msg_num > 0 && --timeout) {
+               i2c_pxa_handler(0, i2c);
+               udelay(10);
+       }
diff --git a/queue-2.6.28/ide-iops-fix-odd-length-atapi-pio-transfers.patch b/queue-2.6.28/ide-iops-fix-odd-length-atapi-pio-transfers.patch
new file mode 100644 (file)
index 0000000..98f0d48
--- /dev/null
@@ -0,0 +1,32 @@
+From a509538d4fb4f99cdf0a095213d57cc3b2347615 Mon Sep 17 00:00:00 2001
+From: Sergei Shtylyov <sshtylyov@ru.mvista.com>
+Date: Thu, 5 Mar 2009 16:10:56 +0100
+Subject: ide-iops: fix odd-length ATAPI PIO transfers
+
+From: Sergei Shtylyov <sshtylyov@ru.mvista.com>
+
+commit a509538d4fb4f99cdf0a095213d57cc3b2347615 upstream.
+
+Commit 9567b349f7e7dd7e2483db99ee8e4a6fe0caca38 (ide: merge ->atapi_*put_bytes
+and ->ata_*put_data methods) introduced a regression  WRT the odd-length ATAPI
+PIO transfers -- the final word didn't get written (causing command timeouts).
+
+Signed-off-by: Sergei Shtylyov <sshtylyov@ru.mvista.com>
+Signed-off-by: Bartlomiej Zolnierkiewicz <bzolnier@gmail.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ drivers/ide/ide-iops.c |    2 ++
+ 1 file changed, 2 insertions(+)
+
+--- a/drivers/ide/ide-iops.c
++++ b/drivers/ide/ide-iops.c
+@@ -324,6 +324,8 @@ void ide_output_data(ide_drive_t *drive,
+       u8 io_32bit = drive->io_32bit;
+       u8 mmio = (hwif->host_flags & IDE_HFLAG_MMIO) ? 1 : 0;
++      len++;
++
+       if (io_32bit) {
+               unsigned long uninitialized_var(flags);
diff --git a/queue-2.6.28/jbd2-avoid-possible-null-dereference-in-jbd2_journal_begin_ordered_truncate.patch b/queue-2.6.28/jbd2-avoid-possible-null-dereference-in-jbd2_journal_begin_ordered_truncate.patch
new file mode 100644 (file)
index 0000000..6d20602
--- /dev/null
@@ -0,0 +1,142 @@
+From tytso@mit.edu  Thu Mar 12 22:49:54 2009
+From: Jan Kara <jack@suse.cz>
+Date: Tue, 24 Feb 2009 12:14:43 -0500
+Subject: jbd2: Avoid possible NULL dereference in jbd2_journal_begin_ordered_truncate()
+To: stable@kernel.org
+Cc: "Theodore Ts'o" <tytso@mit.edu>, Dan Carpenter <error27@gmail.com>, mfasheh@suse.de, Jan Kara <jack@suse.cz>, linux-ext4@vger.kernel.org, ocfs2-devel@oss.oracle.com
+Message-ID: <1235495688-8044-3-git-send-email-tytso@mit.edu>
+
+
+From: Jan Kara <jack@suse.cz>
+
+(cherry picked from commit 7f5aa215088b817add9c71914b83650bdd49f8a9)
+
+If we race with commit code setting i_transaction to NULL, we could
+possibly dereference it.  Proper locking requires the journal pointer
+(to access journal->j_list_lock), which we don't have.  So we have to
+change the prototype of the function so that filesystem passes us the
+journal pointer.  Also add a more detailed comment about why the
+function jbd2_journal_begin_ordered_truncate() does what it does and
+how it should be used.
+
+Thanks to Dan Carpenter <error27@gmail.com> for pointing to the
+suspitious code.
+
+Signed-off-by: Jan Kara <jack@suse.cz>
+Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>
+Acked-by: Joel Becker <joel.becker@oracle.com>
+CC: linux-ext4@vger.kernel.org
+CC: ocfs2-devel@oss.oracle.com
+CC: mfasheh@suse.de
+CC: Dan Carpenter <error27@gmail.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ fs/ext4/inode.c       |    6 ++++--
+ fs/jbd2/transaction.c |   42 +++++++++++++++++++++++++++++++-----------
+ fs/ocfs2/journal.h    |    6 ++++--
+ include/linux/jbd2.h  |    3 ++-
+ 4 files changed, 41 insertions(+), 16 deletions(-)
+
+--- a/fs/ext4/inode.c
++++ b/fs/ext4/inode.c
+@@ -46,8 +46,10 @@
+ static inline int ext4_begin_ordered_truncate(struct inode *inode,
+                                             loff_t new_size)
+ {
+-      return jbd2_journal_begin_ordered_truncate(&EXT4_I(inode)->jinode,
+-                                                 new_size);
++      return jbd2_journal_begin_ordered_truncate(
++                                      EXT4_SB(inode->i_sb)->s_journal,
++                                      &EXT4_I(inode)->jinode,
++                                      new_size);
+ }
+ static void ext4_invalidatepage(struct page *page, unsigned long offset);
+--- a/fs/jbd2/transaction.c
++++ b/fs/jbd2/transaction.c
+@@ -2050,26 +2050,46 @@ done:
+ }
+ /*
+- * This function must be called when inode is journaled in ordered mode
+- * before truncation happens. It starts writeout of truncated part in
+- * case it is in the committing transaction so that we stand to ordered
+- * mode consistency guarantees.
++ * File truncate and transaction commit interact with each other in a
++ * non-trivial way.  If a transaction writing data block A is
++ * committing, we cannot discard the data by truncate until we have
++ * written them.  Otherwise if we crashed after the transaction with
++ * write has committed but before the transaction with truncate has
++ * committed, we could see stale data in block A.  This function is a
++ * helper to solve this problem.  It starts writeout of the truncated
++ * part in case it is in the committing transaction.
++ *
++ * Filesystem code must call this function when inode is journaled in
++ * ordered mode before truncation happens and after the inode has been
++ * placed on orphan list with the new inode size. The second condition
++ * avoids the race that someone writes new data and we start
++ * committing the transaction after this function has been called but
++ * before a transaction for truncate is started (and furthermore it
++ * allows us to optimize the case where the addition to orphan list
++ * happens in the same transaction as write --- we don't have to write
++ * any data in such case).
+  */
+-int jbd2_journal_begin_ordered_truncate(struct jbd2_inode *inode,
++int jbd2_journal_begin_ordered_truncate(journal_t *journal,
++                                      struct jbd2_inode *jinode,
+                                       loff_t new_size)
+ {
+-      journal_t *journal;
+-      transaction_t *commit_trans;
++      transaction_t *inode_trans, *commit_trans;
+       int ret = 0;
+-      if (!inode->i_transaction && !inode->i_next_transaction)
++      /* This is a quick check to avoid locking if not necessary */
++      if (!jinode->i_transaction)
+               goto out;
+-      journal = inode->i_transaction->t_journal;
++      /* Locks are here just to force reading of recent values, it is
++       * enough that the transaction was not committing before we started
++       * a transaction adding the inode to orphan list */
+       spin_lock(&journal->j_state_lock);
+       commit_trans = journal->j_committing_transaction;
+       spin_unlock(&journal->j_state_lock);
+-      if (inode->i_transaction == commit_trans) {
+-              ret = filemap_fdatawrite_range(inode->i_vfs_inode->i_mapping,
++      spin_lock(&journal->j_list_lock);
++      inode_trans = jinode->i_transaction;
++      spin_unlock(&journal->j_list_lock);
++      if (inode_trans == commit_trans) {
++              ret = filemap_fdatawrite_range(jinode->i_vfs_inode->i_mapping,
+                       new_size, LLONG_MAX);
+               if (ret)
+                       jbd2_journal_abort(journal, ret);
+--- a/fs/ocfs2/journal.h
++++ b/fs/ocfs2/journal.h
+@@ -445,8 +445,10 @@ static inline int ocfs2_jbd2_file_inode(
+ static inline int ocfs2_begin_ordered_truncate(struct inode *inode,
+                                              loff_t new_size)
+ {
+-      return jbd2_journal_begin_ordered_truncate(&OCFS2_I(inode)->ip_jinode,
+-                                                 new_size);
++      return jbd2_journal_begin_ordered_truncate(
++                              OCFS2_SB(inode->i_sb)->journal->j_journal,
++                              &OCFS2_I(inode)->ip_jinode,
++                              new_size);
+ }
+ #endif /* OCFS2_JOURNAL_H */
+--- a/include/linux/jbd2.h
++++ b/include/linux/jbd2.h
+@@ -1087,7 +1087,8 @@ extern int          jbd2_journal_clear_err  (j
+ extern int       jbd2_journal_bmap(journal_t *, unsigned long, unsigned long long *);
+ extern int       jbd2_journal_force_commit(journal_t *);
+ extern int       jbd2_journal_file_inode(handle_t *handle, struct jbd2_inode *inode);
+-extern int       jbd2_journal_begin_ordered_truncate(struct jbd2_inode *inode, loff_t new_size);
++extern int       jbd2_journal_begin_ordered_truncate(journal_t *journal,
++                              struct jbd2_inode *inode, loff_t new_size);
+ extern void      jbd2_journal_init_jbd_inode(struct jbd2_inode *jinode, struct inode *inode);
+ extern void      jbd2_journal_release_jbd_inode(journal_t *journal, struct jbd2_inode *jinode);
diff --git a/queue-2.6.28/jbd2-fix-return-value-of-jbd2_journal_start_commit.patch b/queue-2.6.28/jbd2-fix-return-value-of-jbd2_journal_start_commit.patch
new file mode 100644 (file)
index 0000000..d5c3d34
--- /dev/null
@@ -0,0 +1,103 @@
+From tytso@mit.edu  Thu Mar 12 22:49:00 2009
+From: Jan Kara <jack@suse.cz>
+Date: Tue, 24 Feb 2009 12:14:41 -0500
+Subject: jbd2: Fix return value of jbd2_journal_start_commit()
+To: stable@kernel.org
+Cc: "Theodore Ts'o" <tytso@mit.edu>, linux-ext4@vger.kernel.org, Jan Kara <jack@suse.cz>, Eric Sandeen <sandeen@redhat.com>
+Message-ID: <1235495688-8044-1-git-send-email-tytso@mit.edu>
+
+
+From: Jan Kara <jack@suse.cz>
+
+(cherry picked from commit c88ccea3143975294f5a52097546bcbb75975f52)
+
+The function jbd2_journal_start_commit() returns 1 if either a
+transaction is committing or the function has queued a transaction
+commit. But it returns 0 if we raced with somebody queueing the
+transaction commit as well. This resulted in ext4_sync_fs() not
+functioning correctly (description from Arthur Jones):
+
+   In the case of a data=ordered umount with pending long symlinks
+   which are delayed due to a long list of other I/O on the backing
+   block device, this causes the buffer associated with the long
+   symlinks to not be moved to the inode dirty list in the second
+   phase of fsync_super.  Then, before they can be dirtied again,
+   kjournald exits, seeing the UMOUNT flag and the dirty pages are
+   never written to the backing block device, causing long symlink
+   corruption and exposing new or previously freed block data to
+   userspace.
+
+This can be reproduced with a script created by Eric Sandeen
+<sandeen@redhat.com>:
+
+        #!/bin/bash
+
+        umount /mnt/test2
+        mount /dev/sdb4 /mnt/test2
+        rm -f /mnt/test2/*
+        dd if=/dev/zero of=/mnt/test2/bigfile bs=1M count=512
+        touch /mnt/test2/thisisveryveryveryveryveryveryveryveryveryveryveryveryveryveryveryverylongfilename
+        ln -s /mnt/test2/thisisveryveryveryveryveryveryveryveryveryveryveryveryveryveryveryverylongfilename
+        /mnt/test2/link
+        umount /mnt/test2
+        mount /dev/sdb4 /mnt/test2
+        ls /mnt/test2/
+
+This patch fixes jbd2_journal_start_commit() to always return 1 when
+there's a transaction committing or queued for commit.
+
+Signed-off-by: Jan Kara <jack@suse.cz>
+Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>
+CC: Eric Sandeen <sandeen@redhat.com>
+CC: linux-ext4@vger.kernel.org
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ fs/jbd2/journal.c |   17 +++++++++++------
+ 1 file changed, 11 insertions(+), 6 deletions(-)
+
+--- a/fs/jbd2/journal.c
++++ b/fs/jbd2/journal.c
+@@ -430,7 +430,7 @@ int __jbd2_log_space_left(journal_t *jou
+ }
+ /*
+- * Called under j_state_lock.  Returns true if a transaction was started.
++ * Called under j_state_lock.  Returns true if a transaction commit was started.
+  */
+ int __jbd2_log_start_commit(journal_t *journal, tid_t target)
+ {
+@@ -498,7 +498,8 @@ int jbd2_journal_force_commit_nested(jou
+ /*
+  * Start a commit of the current running transaction (if any).  Returns true
+- * if a transaction was started, and fills its tid in at *ptid
++ * if a transaction is going to be committed (or is currently already
++ * committing), and fills its tid in at *ptid
+  */
+ int jbd2_journal_start_commit(journal_t *journal, tid_t *ptid)
+ {
+@@ -508,15 +509,19 @@ int jbd2_journal_start_commit(journal_t 
+       if (journal->j_running_transaction) {
+               tid_t tid = journal->j_running_transaction->t_tid;
+-              ret = __jbd2_log_start_commit(journal, tid);
+-              if (ret && ptid)
++              __jbd2_log_start_commit(journal, tid);
++              /* There's a running transaction and we've just made sure
++               * it's commit has been scheduled. */
++              if (ptid)
+                       *ptid = tid;
+-      } else if (journal->j_committing_transaction && ptid) {
++              ret = 1;
++      } else if (journal->j_committing_transaction) {
+               /*
+                * If ext3_write_super() recently started a commit, then we
+                * have to wait for completion of that transaction
+                */
+-              *ptid = journal->j_committing_transaction->t_tid;
++              if (ptid)
++                      *ptid = journal->j_committing_transaction->t_tid;
+               ret = 1;
+       }
+       spin_unlock(&journal->j_state_lock);
diff --git a/queue-2.6.28/revert-ext4-wait-on-all-pending-commits-in-ext4_sync_fs.patch b/queue-2.6.28/revert-ext4-wait-on-all-pending-commits-in-ext4_sync_fs.patch
new file mode 100644 (file)
index 0000000..4dd70d7
--- /dev/null
@@ -0,0 +1,58 @@
+From tytso@mit.edu  Thu Mar 12 22:49:29 2009
+From: Jan Kara <jack@suse.cz>
+Date: Tue, 24 Feb 2009 12:14:42 -0500
+Subject: Revert "ext4: wait on all pending commits in ext4_sync_fs()"
+To: stable@kernel.org
+Cc: "Theodore Ts'o" <tytso@mit.edu>, linux-ext4@vger.kernel.org, Jan Kara <jack@suse.cz>, Eric Sandeen <sandeen@redhat.com>
+Message-ID: <1235495688-8044-2-git-send-email-tytso@mit.edu>
+
+
+From: Jan Kara <jack@suse.cz>
+
+(cherry picked from commit 9eddacf9e9c03578ef2c07c9534423e823d677f8)
+
+This undoes commit 14ce0cb411c88681ab8f3a4c9caa7f42e97a3184.
+
+Since jbd2_journal_start_commit() is now fixed to return 1 when we
+started a transaction commit, there's some transaction waiting to be
+committed or there's a transaction already committing, we don't
+need to call ext4_force_commit() in ext4_sync_fs(). Furthermore
+ext4_force_commit() can unnecessarily create sync transaction which is
+expensive so it's worthwhile to remove it when we can.
+
+http://bugzilla.kernel.org/show_bug.cgi?id=12224
+
+Signed-off-by: Jan Kara <jack@suse.cz>
+Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>
+Cc: Eric Sandeen <sandeen@redhat.com>
+Cc: linux-ext4@vger.kernel.org
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ fs/ext4/super.c |   12 ++++++------
+ 1 file changed, 6 insertions(+), 6 deletions(-)
+
+--- a/fs/ext4/super.c
++++ b/fs/ext4/super.c
+@@ -2914,15 +2914,15 @@ static void ext4_write_super(struct supe
+ static int ext4_sync_fs(struct super_block *sb, int wait)
+ {
+-      int ret = 0;
++      tid_t target;
+       trace_mark(ext4_sync_fs, "dev %s wait %d", sb->s_id, wait);
+       sb->s_dirt = 0;
+-      if (wait)
+-              ret = ext4_force_commit(sb);
+-      else
+-              jbd2_journal_start_commit(EXT4_SB(sb)->s_journal, NULL);
+-      return ret;
++      if (jbd2_journal_start_commit(EXT4_SB(sb)->s_journal, &target)) {
++              if (wait)
++                      jbd2_log_wait_commit(EXT4_SB(sb)->s_journal, target);
++      }
++      return 0;
+ }
+ /*
index de774bac5d5cade4cb029459ae1f8a25680f8282..e4d1c0db3bb0cbb1171d7d335106b6daab712232 100644 (file)
@@ -85,3 +85,27 @@ pipe_rdwr_fasync-fix-the-error-handling-to-prevent-the-leak-crash.patch
 0002-V4L-tda8290-fix-TDA8290-TDA18271-initialization.patch
 0003-V4L-saa7127-fix-broken-S-Video-with-saa7129.patch
 0004-V4L-ivtv-fix-decoder-crash-regression.patch
+jbd2-fix-return-value-of-jbd2_journal_start_commit.patch
+revert-ext4-wait-on-all-pending-commits-in-ext4_sync_fs.patch
+jbd2-avoid-possible-null-dereference-in-jbd2_journal_begin_ordered_truncate.patch
+ext4-fix-to-read-empty-directory-blocks-correctly-in-64k.patch
+ext4-fix-lockdep-warning.patch
+ext4-initialize-preallocation-list_head-s-properly.patch
+ext4-implement-range_cyclic-in-ext4_da_writepages-instead-of-write_cache_pages.patch
+ext4-fix-null-dereference-in-ext4_ext_migrate-s-error-handling.patch
+ext4-add-fallback-for-find_group_flex.patch
+ext4-fix-deadlock-in-ext4_write_begin-and-ext4_da_write_begin.patch
+x86-paravirt-make-arch_flush_lazy_mmu-cpu-disable-preemption.patch
+x86-hpet-fix-for-ls21-hpet-boot-hang.patch
+x86-math_emu-info-cleanup.patch
+x86-fix-math_emu-register-frame-access.patch
+ide-iops-fix-odd-length-atapi-pio-transfers.patch
+hid-move-tmff-and-zpff-devices-from-ignore_list-to-blacklist.patch
+arm-add-i2c_board_info-for-riscpc-pcf8583.patch
+i2c-timeouts-reach-1.patch
+i2c-fix-misplaced-parentheses.patch
+acpi-fix-broken-usage-of-name.ascii.patch
+acpi-fix-broken-usage-of-acpi_ut_get_node_name.patch
+crypto-api-fix-algorithm-test-race-that-broke-aead-initialisation.patch
+hwmon-hide-misleading-error-message.patch
+drm-i915-add-missing-userland-definitions-for-gem-init-execbuffer.patch
diff --git a/queue-2.6.28/x86-fix-math_emu-register-frame-access.patch b/queue-2.6.28/x86-fix-math_emu-register-frame-access.patch
new file mode 100644 (file)
index 0000000..da0cf13
--- /dev/null
@@ -0,0 +1,287 @@
+From d315760ffa261c15ff92699ac6f514112543d7ca Mon Sep 17 00:00:00 2001
+From: Tejun Heo <tj@kernel.org>
+Date: Mon, 9 Feb 2009 22:17:39 +0900
+Subject: x86: fix math_emu register frame access
+
+From: Tejun Heo <tj@kernel.org>
+
+commit d315760ffa261c15ff92699ac6f514112543d7ca upstream.
+
+do_device_not_available() is the handler for #NM and it declares that
+it takes a unsigned long and calls math_emu(), which takes a long
+argument and surprisingly expects the stack frame starting at the zero
+argument would match struct math_emu_info, which isn't true regardless
+of configuration in the current code.
+
+This patch makes do_device_not_available() take struct pt_regs like
+other exception handlers and initialize struct math_emu_info with
+pointer to it and pass pointer to the math_emu_info to math_emulate()
+like normal C functions do.  This way, unless gcc makes a copy of
+struct pt_regs in do_device_not_available(), the register frame is
+correctly accessed regardless of kernel configuration or compiler
+used.
+
+This doesn't fix all math_emu problems but it at least gets it
+somewhat working.
+
+Signed-off-by: Tejun Heo <tj@kernel.org>
+Signed-off-by: Ingo Molnar <mingo@elte.hu>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ arch/x86/include/asm/math_emu.h |    4 +-
+ arch/x86/include/asm/traps.h    |    4 +-
+ arch/x86/kernel/traps.c         |   15 +++++----
+ arch/x86/math-emu/fpu_entry.c   |    4 +-
+ arch/x86/math-emu/fpu_proto.h   |    2 -
+ arch/x86/math-emu/fpu_system.h  |   16 +++------
+ arch/x86/math-emu/get_address.c |   66 ++++++++++++++++++++--------------------
+ 7 files changed, 55 insertions(+), 56 deletions(-)
+
+--- a/arch/x86/include/asm/math_emu.h
++++ b/arch/x86/include/asm/math_emu.h
+@@ -11,8 +11,8 @@
+ struct math_emu_info {
+       long ___orig_eip;
+       union {
+-              struct pt_regs regs;
+-              struct kernel_vm86_regs vm86;
++              struct pt_regs *regs;
++              struct kernel_vm86_regs *vm86;
+       };
+ };
+ #endif /* _ASM_X86_MATH_EMU_H */
+--- a/arch/x86/include/asm/traps.h
++++ b/arch/x86/include/asm/traps.h
+@@ -41,7 +41,7 @@ dotraplinkage void do_int3(struct pt_reg
+ dotraplinkage void do_overflow(struct pt_regs *, long);
+ dotraplinkage void do_bounds(struct pt_regs *, long);
+ dotraplinkage void do_invalid_op(struct pt_regs *, long);
+-dotraplinkage void do_device_not_available(struct pt_regs *, long);
++dotraplinkage void do_device_not_available(struct pt_regs);
+ dotraplinkage void do_coprocessor_segment_overrun(struct pt_regs *, long);
+ dotraplinkage void do_invalid_TSS(struct pt_regs *, long);
+ dotraplinkage void do_segment_not_present(struct pt_regs *, long);
+@@ -74,8 +74,8 @@ extern int kstack_depth_to_print;
+ #ifdef CONFIG_X86_32
+ void math_error(void __user *);
++void math_emulate(struct math_emu_info *);
+ unsigned long patch_espfix_desc(unsigned long, unsigned long);
+-asmlinkage void math_emulate(long);
+ #endif
+ #endif /* _ASM_X86_TRAPS_H */
+--- a/arch/x86/kernel/traps.c
++++ b/arch/x86/kernel/traps.c
+@@ -912,7 +912,7 @@ asmlinkage void math_state_restore(void)
+ EXPORT_SYMBOL_GPL(math_state_restore);
+ #ifndef CONFIG_MATH_EMULATION
+-asmlinkage void math_emulate(long arg)
++void math_emulate(struct math_emu_info *info)
+ {
+       printk(KERN_EMERG
+               "math-emulation not enabled and no coprocessor found.\n");
+@@ -922,16 +922,19 @@ asmlinkage void math_emulate(long arg)
+ }
+ #endif /* CONFIG_MATH_EMULATION */
+-dotraplinkage void __kprobes
+-do_device_not_available(struct pt_regs *regs, long error)
++dotraplinkage void __kprobes do_device_not_available(struct pt_regs regs)
+ {
+ #ifdef CONFIG_X86_32
+       if (read_cr0() & X86_CR0_EM) {
+-              conditional_sti(regs);
+-              math_emulate(0);
++              struct math_emu_info info = { };
++
++              conditional_sti(&regs);
++
++              info.regs = &regs;
++              math_emulate(&info);
+       } else {
+               math_state_restore(); /* interrupts still off */
+-              conditional_sti(regs);
++              conditional_sti(&regs);
+       }
+ #else
+       math_state_restore();
+--- a/arch/x86/math-emu/fpu_entry.c
++++ b/arch/x86/math-emu/fpu_entry.c
+@@ -131,7 +131,7 @@ u_char emulating = 0;
+ static int valid_prefix(u_char *Byte, u_char __user ** fpu_eip,
+                       overrides * override);
+-asmlinkage void math_emulate(long arg)
++void math_emulate(struct math_emu_info *info)
+ {
+       u_char FPU_modrm, byte1;
+       unsigned short code;
+@@ -161,7 +161,7 @@ asmlinkage void math_emulate(long arg)
+       RE_ENTRANT_CHECK_ON;
+ #endif /* RE_ENTRANT_CHECKING */
+-      SETUP_DATA_AREA(arg);
++      FPU_info = info;
+       FPU_ORIG_EIP = FPU_EIP;
+--- a/arch/x86/math-emu/fpu_proto.h
++++ b/arch/x86/math-emu/fpu_proto.h
+@@ -51,7 +51,7 @@ extern void ffreep(void);
+ extern void fst_i_(void);
+ extern void fstp_i(void);
+ /* fpu_entry.c */
+-asmlinkage extern void math_emulate(long arg);
++extern void math_emulate(struct math_emu_info *info);
+ extern void math_abort(struct math_emu_info *info, unsigned int signal);
+ /* fpu_etc.c */
+ extern void FPU_etc(void);
+--- a/arch/x86/math-emu/fpu_system.h
++++ b/arch/x86/math-emu/fpu_system.h
+@@ -16,10 +16,6 @@
+ #include <linux/kernel.h>
+ #include <linux/mm.h>
+-/* This sets the pointer FPU_info to point to the argument part
+-   of the stack frame of math_emulate() */
+-#define SETUP_DATA_AREA(arg)  FPU_info = (struct math_emu_info *) &arg
+-
+ /* s is always from a cpu register, and the cpu does bounds checking
+  * during register load --> no further bounds checks needed */
+ #define LDT_DESCRIPTOR(s)     (((struct desc_struct *)current->mm->context.ldt)[(s) >> 3])
+@@ -38,12 +34,12 @@
+ #define I387                  (current->thread.xstate)
+ #define FPU_info              (I387->soft.info)
+-#define FPU_CS                        (*(unsigned short *) &(FPU_info->regs.cs))
+-#define FPU_SS                        (*(unsigned short *) &(FPU_info->regs.ss))
+-#define FPU_DS                        (*(unsigned short *) &(FPU_info->regs.ds))
+-#define FPU_EAX                       (FPU_info->regs.ax)
+-#define FPU_EFLAGS            (FPU_info->regs.flags)
+-#define FPU_EIP                       (FPU_info->regs.ip)
++#define FPU_CS                        (*(unsigned short *) &(FPU_info->regs->cs))
++#define FPU_SS                        (*(unsigned short *) &(FPU_info->regs->ss))
++#define FPU_DS                        (*(unsigned short *) &(FPU_info->regs->ds))
++#define FPU_EAX                       (FPU_info->regs->ax)
++#define FPU_EFLAGS            (FPU_info->regs->flags)
++#define FPU_EIP                       (FPU_info->regs->ip)
+ #define FPU_ORIG_EIP          (FPU_info->___orig_eip)
+ #define FPU_lookahead           (I387->soft.lookahead)
+--- a/arch/x86/math-emu/get_address.c
++++ b/arch/x86/math-emu/get_address.c
+@@ -29,43 +29,43 @@
+ #define FPU_WRITE_BIT 0x10
+ static int reg_offset[] = {
+-      offsetof(struct math_emu_info, regs.ax),
+-      offsetof(struct math_emu_info, regs.cx),
+-      offsetof(struct math_emu_info, regs.dx),
+-      offsetof(struct math_emu_info, regs.bx),
+-      offsetof(struct math_emu_info, regs.sp),
+-      offsetof(struct math_emu_info, regs.bp),
+-      offsetof(struct math_emu_info, regs.si),
+-      offsetof(struct math_emu_info, regs.di)
++      offsetof(struct pt_regs, ax),
++      offsetof(struct pt_regs, cx),
++      offsetof(struct pt_regs, dx),
++      offsetof(struct pt_regs, bx),
++      offsetof(struct pt_regs, sp),
++      offsetof(struct pt_regs, bp),
++      offsetof(struct pt_regs, si),
++      offsetof(struct pt_regs, di)
+ };
+-#define REG_(x) (*(long *)(reg_offset[(x)]+(u_char *) FPU_info))
++#define REG_(x) (*(long *)(reg_offset[(x)] + (u_char *)FPU_info->regs))
+ static int reg_offset_vm86[] = {
+-      offsetof(struct math_emu_info, regs.cs),
+-      offsetof(struct math_emu_info, vm86.ds),
+-      offsetof(struct math_emu_info, vm86.es),
+-      offsetof(struct math_emu_info, vm86.fs),
+-      offsetof(struct math_emu_info, vm86.gs),
+-      offsetof(struct math_emu_info, regs.ss),
+-      offsetof(struct math_emu_info, vm86.ds)
++      offsetof(struct pt_regs, cs),
++      offsetof(struct kernel_vm86_regs, ds),
++      offsetof(struct kernel_vm86_regs, es),
++      offsetof(struct kernel_vm86_regs, fs),
++      offsetof(struct kernel_vm86_regs, gs),
++      offsetof(struct pt_regs, ss),
++      offsetof(struct kernel_vm86_regs, ds)
+ };
+ #define VM86_REG_(x) (*(unsigned short *) \
+-                    (reg_offset_vm86[((unsigned)x)]+(u_char *) FPU_info))
++              (reg_offset_vm86[((unsigned)x)] + (u_char *)FPU_info->regs))
+ static int reg_offset_pm[] = {
+-      offsetof(struct math_emu_info, regs.cs),
+-      offsetof(struct math_emu_info, regs.ds),
+-      offsetof(struct math_emu_info, regs.es),
+-      offsetof(struct math_emu_info, regs.fs),
+-      offsetof(struct math_emu_info, regs.ds), /* dummy, not saved on stack */
+-      offsetof(struct math_emu_info, regs.ss),
+-      offsetof(struct math_emu_info, regs.ds)
++      offsetof(struct pt_regs, cs),
++      offsetof(struct pt_regs, ds),
++      offsetof(struct pt_regs, es),
++      offsetof(struct pt_regs, fs),
++      offsetof(struct pt_regs, ds),   /* dummy, not saved on stack */
++      offsetof(struct pt_regs, ss),
++      offsetof(struct pt_regs, ds)
+ };
+ #define PM_REG_(x) (*(unsigned short *) \
+-                    (reg_offset_pm[((unsigned)x)]+(u_char *) FPU_info))
++              (reg_offset_pm[((unsigned)x)] + (u_char *)FPU_info->regs))
+ /* Decode the SIB byte. This function assumes mod != 0 */
+ static int sib(int mod, unsigned long *fpu_eip)
+@@ -346,34 +346,34 @@ void __user *FPU_get_address_16(u_char F
+       }
+       switch (rm) {
+       case 0:
+-              address += FPU_info->regs.bx + FPU_info->regs.si;
++              address += FPU_info->regs->bx + FPU_info->regs->si;
+               break;
+       case 1:
+-              address += FPU_info->regs.bx + FPU_info->regs.di;
++              address += FPU_info->regs->bx + FPU_info->regs->di;
+               break;
+       case 2:
+-              address += FPU_info->regs.bp + FPU_info->regs.si;
++              address += FPU_info->regs->bp + FPU_info->regs->si;
+               if (addr_modes.override.segment == PREFIX_DEFAULT)
+                       addr_modes.override.segment = PREFIX_SS_;
+               break;
+       case 3:
+-              address += FPU_info->regs.bp + FPU_info->regs.di;
++              address += FPU_info->regs->bp + FPU_info->regs->di;
+               if (addr_modes.override.segment == PREFIX_DEFAULT)
+                       addr_modes.override.segment = PREFIX_SS_;
+               break;
+       case 4:
+-              address += FPU_info->regs.si;
++              address += FPU_info->regs->si;
+               break;
+       case 5:
+-              address += FPU_info->regs.di;
++              address += FPU_info->regs->di;
+               break;
+       case 6:
+-              address += FPU_info->regs.bp;
++              address += FPU_info->regs->bp;
+               if (addr_modes.override.segment == PREFIX_DEFAULT)
+                       addr_modes.override.segment = PREFIX_SS_;
+               break;
+       case 7:
+-              address += FPU_info->regs.bx;
++              address += FPU_info->regs->bx;
+               break;
+       }
diff --git a/queue-2.6.28/x86-hpet-fix-for-ls21-hpet-boot-hang.patch b/queue-2.6.28/x86-hpet-fix-for-ls21-hpet-boot-hang.patch
new file mode 100644 (file)
index 0000000..f31c9ec
--- /dev/null
@@ -0,0 +1,55 @@
+From b13e24644c138d0ddbc451403c30a96b09bfd556 Mon Sep 17 00:00:00 2001
+From: john stultz <johnstul@us.ibm.com>
+Date: Thu, 12 Feb 2009 18:48:53 -0800
+Subject: x86, hpet: fix for LS21 + HPET = boot hang
+
+From: john stultz <johnstul@us.ibm.com>
+
+commit b13e24644c138d0ddbc451403c30a96b09bfd556 upstream.
+
+Between 2.6.23 and 2.6.24-rc1 a change was made that broke IBM LS21
+systems that had the HPET enabled in the BIOS, resulting in boot hangs
+for x86_64.
+
+Specifically commit b8ce33590687888ebb900d09557b8807c4539022, which
+merges the i386 and x86_64 HPET code.
+
+Prior to this commit, when we setup the HPET timers in x86_64, we did
+the following:
+
+       hpet_writel(HPET_TN_ENABLE | HPET_TN_PERIODIC | HPET_TN_SETVAL |
+                    HPET_TN_32BIT, HPET_T0_CFG);
+
+However after the i386/x86_64 HPET merge, we do the following:
+
+       cfg = hpet_readl(HPET_Tn_CFG(timer));
+       cfg |= HPET_TN_ENABLE | HPET_TN_PERIODIC |
+                       HPET_TN_SETVAL | HPET_TN_32BIT;
+       hpet_writel(cfg, HPET_Tn_CFG(timer));
+
+However on LS21s with HPET enabled in the BIOS, the HPET_T0_CFG register
+boots with Level triggered interrupts (HPET_TN_LEVEL) enabled. This
+causes the periodic interrupt to be not so periodic, and that results in
+the boot time hang I reported earlier in the delay calibration.
+
+My fix: Always disable HPET_TN_LEVEL when setting up periodic mode.
+
+Signed-off-by: John Stultz <johnstul@us.ibm.com>
+Signed-off-by: Ingo Molnar <mingo@elte.hu>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ arch/x86/kernel/hpet.c |    2 ++
+ 1 file changed, 2 insertions(+)
+
+--- a/arch/x86/kernel/hpet.c
++++ b/arch/x86/kernel/hpet.c
+@@ -267,6 +267,8 @@ static void hpet_set_mode(enum clock_eve
+               now = hpet_readl(HPET_COUNTER);
+               cmp = now + (unsigned long) delta;
+               cfg = hpet_readl(HPET_Tn_CFG(timer));
++              /* Make sure we use edge triggered interrupts */
++              cfg &= ~HPET_TN_LEVEL;
+               cfg |= HPET_TN_ENABLE | HPET_TN_PERIODIC |
+                      HPET_TN_SETVAL | HPET_TN_32BIT;
+               hpet_writel(cfg, HPET_Tn_CFG(timer));
diff --git a/queue-2.6.28/x86-math_emu-info-cleanup.patch b/queue-2.6.28/x86-math_emu-info-cleanup.patch
new file mode 100644 (file)
index 0000000..f05f112
--- /dev/null
@@ -0,0 +1,244 @@
+From ae6af41f5a4841f06eb92bc86ad020ad44ae2a30 Mon Sep 17 00:00:00 2001
+From: Tejun Heo <tj@kernel.org>
+Date: Mon, 9 Feb 2009 22:17:39 +0900
+Subject: x86: math_emu info cleanup
+
+From: Tejun Heo <tj@kernel.org>
+
+commit ae6af41f5a4841f06eb92bc86ad020ad44ae2a30 upstream.
+
+Impact: cleanup
+
+* Come on, struct info?  s/struct info/struct math_emu_info/
+
+* Use struct pt_regs and kernel_vm86_regs instead of defining its own
+  register frame structure.
+
+Signed-off-by: Tejun Heo <tj@kernel.org>
+Signed-off-by: Ingo Molnar <mingo@elte.hu>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ arch/x86/include/asm/math_emu.h  |   29 ++++-------------
+ arch/x86/include/asm/processor.h |    2 -
+ arch/x86/math-emu/fpu_entry.c    |    2 -
+ arch/x86/math-emu/fpu_proto.h    |    2 -
+ arch/x86/math-emu/fpu_system.h   |   14 ++++----
+ arch/x86/math-emu/get_address.c  |   63 ++++++++++++++++++---------------------
+ 6 files changed, 48 insertions(+), 64 deletions(-)
+
+--- a/arch/x86/include/asm/math_emu.h
++++ b/arch/x86/include/asm/math_emu.h
+@@ -1,31 +1,18 @@
+ #ifndef _ASM_X86_MATH_EMU_H
+ #define _ASM_X86_MATH_EMU_H
++#include <asm/ptrace.h>
++#include <asm/vm86.h>
++
+ /* This structure matches the layout of the data saved to the stack
+    following a device-not-present interrupt, part of it saved
+    automatically by the 80386/80486.
+    */
+-struct info {
++struct math_emu_info {
+       long ___orig_eip;
+-      long ___ebx;
+-      long ___ecx;
+-      long ___edx;
+-      long ___esi;
+-      long ___edi;
+-      long ___ebp;
+-      long ___eax;
+-      long ___ds;
+-      long ___es;
+-      long ___fs;
+-      long ___orig_eax;
+-      long ___eip;
+-      long ___cs;
+-      long ___eflags;
+-      long ___esp;
+-      long ___ss;
+-      long ___vm86_es; /* This and the following only in vm86 mode */
+-      long ___vm86_ds;
+-      long ___vm86_fs;
+-      long ___vm86_gs;
++      union {
++              struct pt_regs regs;
++              struct kernel_vm86_regs vm86;
++      };
+ };
+ #endif /* _ASM_X86_MATH_EMU_H */
+--- a/arch/x86/include/asm/processor.h
++++ b/arch/x86/include/asm/processor.h
+@@ -349,7 +349,7 @@ struct i387_soft_struct {
+       u8                      no_update;
+       u8                      rm;
+       u8                      alimit;
+-      struct info             *info;
++      struct math_emu_info    *info;
+       u32                     entry_eip;
+ };
+--- a/arch/x86/math-emu/fpu_entry.c
++++ b/arch/x86/math-emu/fpu_entry.c
+@@ -659,7 +659,7 @@ static int valid_prefix(u_char *Byte, u_
+       }
+ }
+-void math_abort(struct info *info, unsigned int signal)
++void math_abort(struct math_emu_info *info, unsigned int signal)
+ {
+       FPU_EIP = FPU_ORIG_EIP;
+       current->thread.trap_no = 16;
+--- a/arch/x86/math-emu/fpu_proto.h
++++ b/arch/x86/math-emu/fpu_proto.h
+@@ -52,7 +52,7 @@ extern void fst_i_(void);
+ extern void fstp_i(void);
+ /* fpu_entry.c */
+ asmlinkage extern void math_emulate(long arg);
+-extern void math_abort(struct info *info, unsigned int signal);
++extern void math_abort(struct math_emu_info *info, unsigned int signal);
+ /* fpu_etc.c */
+ extern void FPU_etc(void);
+ /* fpu_tags.c */
+--- a/arch/x86/math-emu/fpu_system.h
++++ b/arch/x86/math-emu/fpu_system.h
+@@ -18,7 +18,7 @@
+ /* This sets the pointer FPU_info to point to the argument part
+    of the stack frame of math_emulate() */
+-#define SETUP_DATA_AREA(arg)  FPU_info = (struct info *) &arg
++#define SETUP_DATA_AREA(arg)  FPU_info = (struct math_emu_info *) &arg
+ /* s is always from a cpu register, and the cpu does bounds checking
+  * during register load --> no further bounds checks needed */
+@@ -38,12 +38,12 @@
+ #define I387                  (current->thread.xstate)
+ #define FPU_info              (I387->soft.info)
+-#define FPU_CS                        (*(unsigned short *) &(FPU_info->___cs))
+-#define FPU_SS                        (*(unsigned short *) &(FPU_info->___ss))
+-#define FPU_DS                        (*(unsigned short *) &(FPU_info->___ds))
+-#define FPU_EAX                       (FPU_info->___eax)
+-#define FPU_EFLAGS            (FPU_info->___eflags)
+-#define FPU_EIP                       (FPU_info->___eip)
++#define FPU_CS                        (*(unsigned short *) &(FPU_info->regs.cs))
++#define FPU_SS                        (*(unsigned short *) &(FPU_info->regs.ss))
++#define FPU_DS                        (*(unsigned short *) &(FPU_info->regs.ds))
++#define FPU_EAX                       (FPU_info->regs.ax)
++#define FPU_EFLAGS            (FPU_info->regs.flags)
++#define FPU_EIP                       (FPU_info->regs.ip)
+ #define FPU_ORIG_EIP          (FPU_info->___orig_eip)
+ #define FPU_lookahead           (I387->soft.lookahead)
+--- a/arch/x86/math-emu/get_address.c
++++ b/arch/x86/math-emu/get_address.c
+@@ -29,42 +29,39 @@
+ #define FPU_WRITE_BIT 0x10
+ static int reg_offset[] = {
+-      offsetof(struct info, ___eax),
+-      offsetof(struct info, ___ecx),
+-      offsetof(struct info, ___edx),
+-      offsetof(struct info, ___ebx),
+-      offsetof(struct info, ___esp),
+-      offsetof(struct info, ___ebp),
+-      offsetof(struct info, ___esi),
+-      offsetof(struct info, ___edi)
++      offsetof(struct math_emu_info, regs.ax),
++      offsetof(struct math_emu_info, regs.cx),
++      offsetof(struct math_emu_info, regs.dx),
++      offsetof(struct math_emu_info, regs.bx),
++      offsetof(struct math_emu_info, regs.sp),
++      offsetof(struct math_emu_info, regs.bp),
++      offsetof(struct math_emu_info, regs.si),
++      offsetof(struct math_emu_info, regs.di)
+ };
+ #define REG_(x) (*(long *)(reg_offset[(x)]+(u_char *) FPU_info))
+ static int reg_offset_vm86[] = {
+-      offsetof(struct info, ___cs),
+-      offsetof(struct info, ___vm86_ds),
+-      offsetof(struct info, ___vm86_es),
+-      offsetof(struct info, ___vm86_fs),
+-      offsetof(struct info, ___vm86_gs),
+-      offsetof(struct info, ___ss),
+-      offsetof(struct info, ___vm86_ds)
++      offsetof(struct math_emu_info, regs.cs),
++      offsetof(struct math_emu_info, vm86.ds),
++      offsetof(struct math_emu_info, vm86.es),
++      offsetof(struct math_emu_info, vm86.fs),
++      offsetof(struct math_emu_info, vm86.gs),
++      offsetof(struct math_emu_info, regs.ss),
++      offsetof(struct math_emu_info, vm86.ds)
+ };
+ #define VM86_REG_(x) (*(unsigned short *) \
+                     (reg_offset_vm86[((unsigned)x)]+(u_char *) FPU_info))
+-/* This dummy, gs is not saved on the stack. */
+-#define ___GS ___ds
+-
+ static int reg_offset_pm[] = {
+-      offsetof(struct info, ___cs),
+-      offsetof(struct info, ___ds),
+-      offsetof(struct info, ___es),
+-      offsetof(struct info, ___fs),
+-      offsetof(struct info, ___GS),
+-      offsetof(struct info, ___ss),
+-      offsetof(struct info, ___ds)
++      offsetof(struct math_emu_info, regs.cs),
++      offsetof(struct math_emu_info, regs.ds),
++      offsetof(struct math_emu_info, regs.es),
++      offsetof(struct math_emu_info, regs.fs),
++      offsetof(struct math_emu_info, regs.ds), /* dummy, not saved on stack */
++      offsetof(struct math_emu_info, regs.ss),
++      offsetof(struct math_emu_info, regs.ds)
+ };
+ #define PM_REG_(x) (*(unsigned short *) \
+@@ -349,34 +346,34 @@ void __user *FPU_get_address_16(u_char F
+       }
+       switch (rm) {
+       case 0:
+-              address += FPU_info->___ebx + FPU_info->___esi;
++              address += FPU_info->regs.bx + FPU_info->regs.si;
+               break;
+       case 1:
+-              address += FPU_info->___ebx + FPU_info->___edi;
++              address += FPU_info->regs.bx + FPU_info->regs.di;
+               break;
+       case 2:
+-              address += FPU_info->___ebp + FPU_info->___esi;
++              address += FPU_info->regs.bp + FPU_info->regs.si;
+               if (addr_modes.override.segment == PREFIX_DEFAULT)
+                       addr_modes.override.segment = PREFIX_SS_;
+               break;
+       case 3:
+-              address += FPU_info->___ebp + FPU_info->___edi;
++              address += FPU_info->regs.bp + FPU_info->regs.di;
+               if (addr_modes.override.segment == PREFIX_DEFAULT)
+                       addr_modes.override.segment = PREFIX_SS_;
+               break;
+       case 4:
+-              address += FPU_info->___esi;
++              address += FPU_info->regs.si;
+               break;
+       case 5:
+-              address += FPU_info->___edi;
++              address += FPU_info->regs.di;
+               break;
+       case 6:
+-              address += FPU_info->___ebp;
++              address += FPU_info->regs.bp;
+               if (addr_modes.override.segment == PREFIX_DEFAULT)
+                       addr_modes.override.segment = PREFIX_SS_;
+               break;
+       case 7:
+-              address += FPU_info->___ebx;
++              address += FPU_info->regs.bx;
+               break;
+       }
diff --git a/queue-2.6.28/x86-paravirt-make-arch_flush_lazy_mmu-cpu-disable-preemption.patch b/queue-2.6.28/x86-paravirt-make-arch_flush_lazy_mmu-cpu-disable-preemption.patch
new file mode 100644 (file)
index 0000000..e90276e
--- /dev/null
@@ -0,0 +1,97 @@
+From d85cf93da66977dbc645352be1b2084a659d8a0b Mon Sep 17 00:00:00 2001
+From: Jeremy Fitzhardinge <jeremy@goop.org>
+Date: Thu, 12 Feb 2009 10:02:56 -0800
+Subject: x86/paravirt: make arch_flush_lazy_mmu/cpu disable preemption
+
+From: Jeremy Fitzhardinge <jeremy@goop.org>
+
+commit d85cf93da66977dbc645352be1b2084a659d8a0b upstream.
+
+Impact: avoid access to percpu vars in preempible context
+
+They are intended to be used whenever there's the possibility
+that there's some stale state which is going to be overwritten
+with a queued update, or to force a state change when we may be
+in lazy mode.  Either way, we could end up calling it with
+preemption enabled, so wrap the functions in their own little
+preempt-disable section so they can be safely called in any
+context (though preemption should never be enabled if we're actually
+in a lazy state).
+
+(Move out of line to avoid #include dependencies.)
+
+Signed-off-by: Jeremy Fitzhardinge <jeremy.fitzhardinge@citrix.com>
+Signed-off-by: Thomas Gleixner <tglx@linutronix.de>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ arch/x86/include/asm/paravirt.h |   17 ++---------------
+ arch/x86/kernel/paravirt.c      |   24 ++++++++++++++++++++++++
+ 2 files changed, 26 insertions(+), 15 deletions(-)
+
+--- a/arch/x86/include/asm/paravirt.h
++++ b/arch/x86/include/asm/paravirt.h
+@@ -1352,14 +1352,7 @@ static inline void arch_leave_lazy_cpu_m
+       PVOP_VCALL0(pv_cpu_ops.lazy_mode.leave);
+ }
+-static inline void arch_flush_lazy_cpu_mode(void)
+-{
+-      if (unlikely(paravirt_get_lazy_mode() == PARAVIRT_LAZY_CPU)) {
+-              arch_leave_lazy_cpu_mode();
+-              arch_enter_lazy_cpu_mode();
+-      }
+-}
+-
++void arch_flush_lazy_cpu_mode(void);
+ #define  __HAVE_ARCH_ENTER_LAZY_MMU_MODE
+ static inline void arch_enter_lazy_mmu_mode(void)
+@@ -1372,13 +1365,7 @@ static inline void arch_leave_lazy_mmu_m
+       PVOP_VCALL0(pv_mmu_ops.lazy_mode.leave);
+ }
+-static inline void arch_flush_lazy_mmu_mode(void)
+-{
+-      if (unlikely(paravirt_get_lazy_mode() == PARAVIRT_LAZY_MMU)) {
+-              arch_leave_lazy_mmu_mode();
+-              arch_enter_lazy_mmu_mode();
+-      }
+-}
++void arch_flush_lazy_mmu_mode(void);
+ static inline void __set_fixmap(unsigned /* enum fixed_addresses */ idx,
+                               unsigned long phys, pgprot_t flags)
+--- a/arch/x86/kernel/paravirt.c
++++ b/arch/x86/kernel/paravirt.c
+@@ -268,6 +268,30 @@ enum paravirt_lazy_mode paravirt_get_laz
+       return __get_cpu_var(paravirt_lazy_mode);
+ }
++void arch_flush_lazy_mmu_mode(void)
++{
++      preempt_disable();
++
++      if (paravirt_get_lazy_mode() == PARAVIRT_LAZY_MMU) {
++              arch_leave_lazy_mmu_mode();
++              arch_enter_lazy_mmu_mode();
++      }
++
++      preempt_enable();
++}
++
++void arch_flush_lazy_cpu_mode(void)
++{
++      preempt_disable();
++
++      if (paravirt_get_lazy_mode() == PARAVIRT_LAZY_CPU) {
++              arch_leave_lazy_cpu_mode();
++              arch_enter_lazy_cpu_mode();
++      }
++
++      preempt_enable();
++}
++
+ struct pv_info pv_info = {
+       .name = "bare hardware",
+       .paravirt_enabled = 0,