]> git.ipfire.org Git - thirdparty/kernel/stable-queue.git/commitdiff
3.0 patches
authorGreg Kroah-Hartman <gregkh@suse.de>
Tue, 6 Dec 2011 22:04:35 +0000 (14:04 -0800)
committerGreg Kroah-Hartman <gregkh@suse.de>
Tue, 6 Dec 2011 22:04:35 +0000 (14:04 -0800)
added patches:
add-missing-.set-function-for-nt_s390_last_break-regset.patch
cfg80211-amend-regulatory-null-dereference-fix.patch
cfg80211-fix-race-on-init-and-driver-registration.patch
genirq-fix-race-condition-when-stopping-the-irq-thread.patch
mac80211-fill-rate-filter-for-internal-scan-requests.patch
nfs-prevent-3.0-from-crashing-if-it-receives-a-partial-layout.patch
oprofile-x86-fix-crash-when-unloading-module-nmi-timer-mode.patch
perf-x86-fix-pebs-instruction-unwind.patch
sched-x86-avoid-unnecessary-overflow-in-sched_clock.patch
x86-fix-acer-aspire-1-reboot-hang.patch
x86-mpparse-account-for-bus-types-other-than-isa-and-pci.patch
x86-paravirt-pte-updates-in-k-un-map_atomic-need-to-be-synchronous-regardless-of-lazy_mmu-mode.patch
xfs-fix-attr2-vs-large-data-fork-assert.patch
xfs-force-buffer-writeback-before-blocking-on-the-ilock-in-inode-reclaim.patch
xfs-validate-acl-count.patch

16 files changed:
queue-3.0/add-missing-.set-function-for-nt_s390_last_break-regset.patch [new file with mode: 0644]
queue-3.0/cfg80211-amend-regulatory-null-dereference-fix.patch [new file with mode: 0644]
queue-3.0/cfg80211-fix-race-on-init-and-driver-registration.patch [new file with mode: 0644]
queue-3.0/genirq-fix-race-condition-when-stopping-the-irq-thread.patch [new file with mode: 0644]
queue-3.0/mac80211-fill-rate-filter-for-internal-scan-requests.patch [new file with mode: 0644]
queue-3.0/nfs-prevent-3.0-from-crashing-if-it-receives-a-partial-layout.patch [new file with mode: 0644]
queue-3.0/oprofile-x86-fix-crash-when-unloading-module-nmi-timer-mode.patch [new file with mode: 0644]
queue-3.0/perf-x86-fix-pebs-instruction-unwind.patch [new file with mode: 0644]
queue-3.0/sched-x86-avoid-unnecessary-overflow-in-sched_clock.patch [new file with mode: 0644]
queue-3.0/series
queue-3.0/x86-fix-acer-aspire-1-reboot-hang.patch [new file with mode: 0644]
queue-3.0/x86-mpparse-account-for-bus-types-other-than-isa-and-pci.patch [new file with mode: 0644]
queue-3.0/x86-paravirt-pte-updates-in-k-un-map_atomic-need-to-be-synchronous-regardless-of-lazy_mmu-mode.patch [new file with mode: 0644]
queue-3.0/xfs-fix-attr2-vs-large-data-fork-assert.patch [new file with mode: 0644]
queue-3.0/xfs-force-buffer-writeback-before-blocking-on-the-ilock-in-inode-reclaim.patch [new file with mode: 0644]
queue-3.0/xfs-validate-acl-count.patch [new file with mode: 0644]

diff --git a/queue-3.0/add-missing-.set-function-for-nt_s390_last_break-regset.patch b/queue-3.0/add-missing-.set-function-for-nt_s390_last_break-regset.patch
new file mode 100644 (file)
index 0000000..7a09181
--- /dev/null
@@ -0,0 +1,83 @@
+From b934069c991355d27a053a932591c77960f4e414 Mon Sep 17 00:00:00 2001
+From: Martin Schwidefsky <schwidefsky@de.ibm.com>
+Date: Thu, 1 Dec 2011 13:32:17 +0100
+Subject: [S390] add missing .set function for NT_S390_LAST_BREAK regset
+
+From: Martin Schwidefsky <schwidefsky@de.ibm.com>
+
+commit b934069c991355d27a053a932591c77960f4e414 upstream.
+
+The last breaking event address is a read-only value, the regset misses the
+.set function. If a PTRACE_SETREGSET is done for NT_S390_LAST_BREAK we
+get an oops due to a branch to zero:
+
+Kernel BUG at 0000000000000002 verbose debug info unavailable
+illegal operation: 0001 #1 SMP
+...
+Call Trace:
+(<0000000000158294> ptrace_regset+0x184/0x188)
+ <00000000001595b6> ptrace_request+0x37a/0x4fc
+ <0000000000109a78> arch_ptrace+0x108/0x1fc
+ <00000000001590d6> SyS_ptrace+0xaa/0x12c
+ <00000000005c7a42> sysc_noemu+0x16/0x1c
+ <000003fffd5ec10c> 0x3fffd5ec10c
+Last Breaking-Event-Address:
+ <0000000000158242> ptrace_regset+0x132/0x188
+
+Add a nop .set function to prevent the branch to zero.
+
+Signed-off-by: Martin Schwidefsky <schwidefsky@de.ibm.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ arch/s390/kernel/ptrace.c |   18 ++++++++++++++++++
+ 1 file changed, 18 insertions(+)
+
+--- a/arch/s390/kernel/ptrace.c
++++ b/arch/s390/kernel/ptrace.c
+@@ -897,6 +897,14 @@ static int s390_last_break_get(struct ta
+       return 0;
+ }
++static int s390_last_break_set(struct task_struct *target,
++                             const struct user_regset *regset,
++                             unsigned int pos, unsigned int count,
++                             const void *kbuf, const void __user *ubuf)
++{
++      return 0;
++}
++
+ #endif
+ static const struct user_regset s390_regsets[] = {
+@@ -923,6 +931,7 @@ static const struct user_regset s390_reg
+               .size = sizeof(long),
+               .align = sizeof(long),
+               .get = s390_last_break_get,
++              .set = s390_last_break_set,
+       },
+ #endif
+ };
+@@ -1080,6 +1089,14 @@ static int s390_compat_last_break_get(st
+       return 0;
+ }
++static int s390_compat_last_break_set(struct task_struct *target,
++                                    const struct user_regset *regset,
++                                    unsigned int pos, unsigned int count,
++                                    const void *kbuf, const void __user *ubuf)
++{
++      return 0;
++}
++
+ static const struct user_regset s390_compat_regsets[] = {
+       [REGSET_GENERAL] = {
+               .core_note_type = NT_PRSTATUS,
+@@ -1103,6 +1120,7 @@ static const struct user_regset s390_com
+               .size = sizeof(long),
+               .align = sizeof(long),
+               .get = s390_compat_last_break_get,
++              .set = s390_compat_last_break_set,
+       },
+       [REGSET_GENERAL_EXTENDED] = {
+               .core_note_type = NT_S390_HIGH_GPRS,
diff --git a/queue-3.0/cfg80211-amend-regulatory-null-dereference-fix.patch b/queue-3.0/cfg80211-amend-regulatory-null-dereference-fix.patch
new file mode 100644 (file)
index 0000000..5ce7f54
--- /dev/null
@@ -0,0 +1,46 @@
+From 0bac71af6e66dc798bf07d0c0dd14ee5503362f9 Mon Sep 17 00:00:00 2001
+From: "Luis R. Rodriguez" <mcgrof@qca.qualcomm.com>
+Date: Mon, 28 Nov 2011 16:47:16 -0500
+Subject: cfg80211: amend regulatory NULL dereference fix
+
+From: "Luis R. Rodriguez" <mcgrof@qca.qualcomm.com>
+
+commit 0bac71af6e66dc798bf07d0c0dd14ee5503362f9 upstream.
+
+Johannes' patch for "cfg80211: fix regulatory NULL dereference"
+broke user regulaotry hints and it did not address the fact that
+last_request was left populated even if the previous regulatory
+hint was stale due to the wiphy disappearing.
+
+Fix user reguluatory hints by only bailing out if for those
+regulatory hints where a request_wiphy is expected. The stale last_request
+considerations are addressed through the previous fixes on last_request
+where we reset the last_request to a static world regdom request upon
+reset_regdomains(). In this case though we further enhance the effect
+by simply restoring reguluatory settings completely.
+
+Cc: Johannes Berg <johannes.berg@intel.com>
+Signed-off-by: Luis R. Rodriguez <mcgrof@qca.qualcomm.com>
+Reviewed-by: Johannes Berg <johannes@sipsolutions.net>
+Signed-off-by: John W. Linville <linville@tuxdriver.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ net/wireless/reg.c |    6 ++++--
+ 1 file changed, 4 insertions(+), 2 deletions(-)
+
+--- a/net/wireless/reg.c
++++ b/net/wireless/reg.c
+@@ -2040,8 +2040,10 @@ static int __set_regdom(const struct iee
+       }
+       request_wiphy = wiphy_idx_to_wiphy(last_request->wiphy_idx);
+-      if (!request_wiphy) {
+-              reg_set_request_processed();
++      if (!request_wiphy &&
++          (last_request->initiator == NL80211_REGDOM_SET_BY_DRIVER ||
++           last_request->initiator == NL80211_REGDOM_SET_BY_COUNTRY_IE)) {
++              schedule_delayed_work(&reg_timeout, 0);
+               return -ENODEV;
+       }
diff --git a/queue-3.0/cfg80211-fix-race-on-init-and-driver-registration.patch b/queue-3.0/cfg80211-fix-race-on-init-and-driver-registration.patch
new file mode 100644 (file)
index 0000000..0275c83
--- /dev/null
@@ -0,0 +1,160 @@
+From a042994dd377d86bff9446ee76151ceb6267c9ba Mon Sep 17 00:00:00 2001
+From: "Luis R. Rodriguez" <mcgrof@qca.qualcomm.com>
+Date: Mon, 28 Nov 2011 16:47:15 -0500
+Subject: cfg80211: fix race on init and driver registration
+
+From: "Luis R. Rodriguez" <mcgrof@qca.qualcomm.com>
+
+commit a042994dd377d86bff9446ee76151ceb6267c9ba upstream.
+
+There is a theoretical race that if hit will trigger
+a crash. The race is between when we issue the first
+regulatory hint, regulatory_hint_core(), gets processed
+by the workqueue and between when the first device
+gets registered to the wireless core. This is not easy
+to reproduce but it was easy to do so through the
+regulatory simulator I have been working on. This
+is a port of the fix I implemented there [1].
+
+[1] https://github.com/mcgrof/regsim/commit/a246ccf81f059cb662eee288aa13100f631e4cc8
+
+Cc: Johannes Berg <johannes.berg@intel.com>
+Signed-off-by: Luis R. Rodriguez <mcgrof@qca.qualcomm.com>
+Signed-off-by: John W. Linville <linville@tuxdriver.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ net/wireless/reg.c |   43 +++++++++++++++++++++++++++----------------
+ 1 file changed, 27 insertions(+), 16 deletions(-)
+
+--- a/net/wireless/reg.c
++++ b/net/wireless/reg.c
+@@ -57,8 +57,17 @@
+ #define REG_DBG_PRINT(args...)
+ #endif
++static struct regulatory_request core_request_world = {
++      .initiator = NL80211_REGDOM_SET_BY_CORE,
++      .alpha2[0] = '0',
++      .alpha2[1] = '0',
++      .intersect = false,
++      .processed = true,
++      .country_ie_env = ENVIRON_ANY,
++};
++
+ /* Receipt of information from last regulatory request */
+-static struct regulatory_request *last_request;
++static struct regulatory_request *last_request = &core_request_world;
+ /* To trigger userspace events */
+ static struct platform_device *reg_pdev;
+@@ -150,7 +159,7 @@ static char user_alpha2[2];
+ module_param(ieee80211_regdom, charp, 0444);
+ MODULE_PARM_DESC(ieee80211_regdom, "IEEE 802.11 regulatory domain code");
+-static void reset_regdomains(void)
++static void reset_regdomains(bool full_reset)
+ {
+       /* avoid freeing static information or freeing something twice */
+       if (cfg80211_regdomain == cfg80211_world_regdom)
+@@ -165,6 +174,13 @@ static void reset_regdomains(void)
+       cfg80211_world_regdom = &world_regdom;
+       cfg80211_regdomain = NULL;
++
++      if (!full_reset)
++              return;
++
++      if (last_request != &core_request_world)
++              kfree(last_request);
++      last_request = &core_request_world;
+ }
+ /*
+@@ -175,7 +191,7 @@ static void update_world_regdomain(const
+ {
+       BUG_ON(!last_request);
+-      reset_regdomains();
++      reset_regdomains(false);
+       cfg80211_world_regdom = rd;
+       cfg80211_regdomain = rd;
+@@ -1396,7 +1412,8 @@ static int __regulatory_hint(struct wiph
+       }
+ new_request:
+-      kfree(last_request);
++      if (last_request != &core_request_world)
++              kfree(last_request);
+       last_request = pending_request;
+       last_request->intersect = intersect;
+@@ -1566,9 +1583,6 @@ static int regulatory_hint_core(const ch
+ {
+       struct regulatory_request *request;
+-      kfree(last_request);
+-      last_request = NULL;
+-
+       request = kzalloc(sizeof(struct regulatory_request),
+                         GFP_KERNEL);
+       if (!request)
+@@ -1766,7 +1780,7 @@ static void restore_regulatory_settings(
+       mutex_lock(&cfg80211_mutex);
+       mutex_lock(&reg_mutex);
+-      reset_regdomains();
++      reset_regdomains(true);
+       restore_alpha2(alpha2, reset_user);
+       /*
+@@ -2035,7 +2049,7 @@ static int __set_regdom(const struct iee
+               int r;
+               if (last_request->initiator != NL80211_REGDOM_SET_BY_DRIVER) {
+-                      reset_regdomains();
++                      reset_regdomains(false);
+                       cfg80211_regdomain = rd;
+                       return 0;
+               }
+@@ -2056,7 +2070,7 @@ static int __set_regdom(const struct iee
+               if (r)
+                       return r;
+-              reset_regdomains();
++              reset_regdomains(false);
+               cfg80211_regdomain = rd;
+               return 0;
+       }
+@@ -2081,7 +2095,7 @@ static int __set_regdom(const struct iee
+               rd = NULL;
+-              reset_regdomains();
++              reset_regdomains(false);
+               cfg80211_regdomain = intersected_rd;
+               return 0;
+@@ -2101,7 +2115,7 @@ static int __set_regdom(const struct iee
+       kfree(rd);
+       rd = NULL;
+-      reset_regdomains();
++      reset_regdomains(false);
+       cfg80211_regdomain = intersected_rd;
+       return 0;
+@@ -2254,11 +2268,8 @@ void /* __init_or_exit */ regulatory_exi
+       mutex_lock(&cfg80211_mutex);
+       mutex_lock(&reg_mutex);
+-      reset_regdomains();
+-
+-      kfree(last_request);
++      reset_regdomains(true);
+-      last_request = NULL;
+       dev_set_uevent_suppress(&reg_pdev->dev, true);
+       platform_device_unregister(reg_pdev);
diff --git a/queue-3.0/genirq-fix-race-condition-when-stopping-the-irq-thread.patch b/queue-3.0/genirq-fix-race-condition-when-stopping-the-irq-thread.patch
new file mode 100644 (file)
index 0000000..e92ced8
--- /dev/null
@@ -0,0 +1,68 @@
+From 550acb19269d65f32e9ac4ddb26c2b2070e37f1c Mon Sep 17 00:00:00 2001
+From: Ido Yariv <ido@wizery.com>
+Date: Thu, 1 Dec 2011 13:55:08 +0200
+Subject: genirq: Fix race condition when stopping the irq thread
+
+From: Ido Yariv <ido@wizery.com>
+
+commit 550acb19269d65f32e9ac4ddb26c2b2070e37f1c upstream.
+
+In irq_wait_for_interrupt(), the should_stop member is verified before
+setting the task's state to TASK_INTERRUPTIBLE and calling schedule().
+In case kthread_stop sets should_stop and wakes up the process after
+should_stop is checked by the irq thread but before the task's state
+is changed, the irq thread might never exit:
+
+kthread_stop                    irq_wait_for_interrupt
+------------                    ----------------------
+
+                                 ...
+...                              while (!kthread_should_stop()) {
+kthread->should_stop = 1;
+wake_up_process(k);
+wait_for_completion(&kthread->exited);
+...
+                                     set_current_state(TASK_INTERRUPTIBLE);
+
+                                     ...
+
+                                     schedule();
+                                 }
+
+Fix this by checking if the thread should stop after modifying the
+task's state.
+
+[ tglx: Simplified it a bit ]
+
+Signed-off-by: Ido Yariv <ido@wizery.com>
+Link: http://lkml.kernel.org/r/1322740508-22640-1-git-send-email-ido@wizery.com
+Signed-off-by: Thomas Gleixner <tglx@linutronix.de>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ kernel/irq/manage.c |    5 ++++-
+ 1 file changed, 4 insertions(+), 1 deletion(-)
+
+--- a/kernel/irq/manage.c
++++ b/kernel/irq/manage.c
+@@ -620,8 +620,9 @@ static irqreturn_t irq_nested_primary_ha
+ static int irq_wait_for_interrupt(struct irqaction *action)
+ {
++      set_current_state(TASK_INTERRUPTIBLE);
++
+       while (!kthread_should_stop()) {
+-              set_current_state(TASK_INTERRUPTIBLE);
+               if (test_and_clear_bit(IRQTF_RUNTHREAD,
+                                      &action->thread_flags)) {
+@@ -629,7 +630,9 @@ static int irq_wait_for_interrupt(struct
+                       return 0;
+               }
+               schedule();
++              set_current_state(TASK_INTERRUPTIBLE);
+       }
++      __set_current_state(TASK_RUNNING);
+       return -1;
+ }
diff --git a/queue-3.0/mac80211-fill-rate-filter-for-internal-scan-requests.patch b/queue-3.0/mac80211-fill-rate-filter-for-internal-scan-requests.patch
new file mode 100644 (file)
index 0000000..4920cd9
--- /dev/null
@@ -0,0 +1,36 @@
+From c72e8d335e2c6a309b6281f2abcf491f37b8b92b Mon Sep 17 00:00:00 2001
+From: Simon Wunderlich <simon.wunderlich@s2003.tu-chemnitz.de>
+Date: Wed, 30 Nov 2011 16:56:30 +0100
+Subject: mac80211: fill rate filter for internal scan requests
+
+From: Simon Wunderlich <simon.wunderlich@s2003.tu-chemnitz.de>
+
+commit c72e8d335e2c6a309b6281f2abcf491f37b8b92b upstream.
+
+The rates bitmap for internal scan requests shoud be filled,
+otherwise there will be probe requests with zero rates supported.
+
+Signed-off-by: Simon Wunderlich <siwu@hrz.tu-chemnitz.de>
+Signed-off-by: Mathias Kretschmer <mathias.kretschmer@fokus.fraunhofer.de>
+Signed-off-by: John W. Linville <linville@tuxdriver.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ net/mac80211/main.c |    6 ++++++
+ 1 file changed, 6 insertions(+)
+
+--- a/net/mac80211/main.c
++++ b/net/mac80211/main.c
+@@ -742,6 +742,12 @@ int ieee80211_register_hw(struct ieee802
+       if (!local->int_scan_req)
+               return -ENOMEM;
++      for (band = 0; band < IEEE80211_NUM_BANDS; band++) {
++              if (!local->hw.wiphy->bands[band])
++                      continue;
++              local->int_scan_req->rates[band] = (u32) -1;
++      }
++
+       /* if low-level driver supports AP, we also support VLAN */
+       if (local->hw.wiphy->interface_modes & BIT(NL80211_IFTYPE_AP)) {
+               hw->wiphy->interface_modes |= BIT(NL80211_IFTYPE_AP_VLAN);
diff --git a/queue-3.0/nfs-prevent-3.0-from-crashing-if-it-receives-a-partial-layout.patch b/queue-3.0/nfs-prevent-3.0-from-crashing-if-it-receives-a-partial-layout.patch
new file mode 100644 (file)
index 0000000..5a6b134
--- /dev/null
@@ -0,0 +1,56 @@
+From Trond.Myklebust@netapp.com  Tue Dec  6 13:58:55 2011
+From: Trond Myklebust <Trond.Myklebust@netapp.com>
+Date: Tue, 18 Oct 2011 10:11:07 -0700
+Subject: NFS: Prevent 3.0 from crashing if it receives a partial layout
+To: stable@kernel.org
+Cc: "Fred Isaman , Trond Myklebust" <iisaman@netapp.com>
+Message-ID: <1318957867-19760-1-git-send-email-Trond.Myklebust@netapp.com>
+
+From: Trond Myklebust <Trond.Myklebust@netapp.com>
+
+This is a backport of critical parts of
+commit 7c24d9489f "NFSv4.1: File layout only supports whole file layouts"
+
+It prevents the file layout driver from (incorrectly) using
+partial layouts, but ignores the part of the referenced commmit that
+relies on additional machinery to change the LAYOUTGET request
+based on layout driver.
+
+Signed-off-by: Fred Isaman <iisaman@netapp.com>
+Acked-by: Trond Myklebust <Trond.Myklebust@netapp.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ fs/nfs/nfs4filelayout.c |    8 ++++++++
+ fs/nfs/pnfs.c           |    3 ++-
+ 2 files changed, 10 insertions(+), 1 deletion(-)
+
+--- a/fs/nfs/nfs4filelayout.c
++++ b/fs/nfs/nfs4filelayout.c
+@@ -428,6 +428,14 @@ filelayout_check_layout(struct pnfs_layo
+       dprintk("--> %s\n", __func__);
++      /* FIXME: remove this check when layout segment support is added */
++      if (lgr->range.offset != 0 ||
++          lgr->range.length != NFS4_MAX_UINT64) {
++              dprintk("%s Only whole file layouts supported. Use MDS i/o\n",
++                      __func__);
++              goto out;
++      }
++
+       if (fl->pattern_offset > lgr->range.offset) {
+               dprintk("%s pattern_offset %lld too large\n",
+                               __func__, fl->pattern_offset);
+--- a/fs/nfs/pnfs.c
++++ b/fs/nfs/pnfs.c
+@@ -980,7 +980,8 @@ pnfs_update_layout(struct inode *ino,
+               arg.offset -= pg_offset;
+               arg.length += pg_offset;
+       }
+-      arg.length = PAGE_CACHE_ALIGN(arg.length);
++      if (arg.length != NFS4_MAX_UINT64)
++              arg.length = PAGE_CACHE_ALIGN(arg.length);
+       lseg = send_layoutget(lo, ctx, &arg, gfp_flags);
+       if (!lseg && first) {
diff --git a/queue-3.0/oprofile-x86-fix-crash-when-unloading-module-nmi-timer-mode.patch b/queue-3.0/oprofile-x86-fix-crash-when-unloading-module-nmi-timer-mode.patch
new file mode 100644 (file)
index 0000000..bc0e3f2
--- /dev/null
@@ -0,0 +1,90 @@
+From 97f7f8189fe54e3cfe324ef9ad35064f3d2d3bff Mon Sep 17 00:00:00 2001
+From: Robert Richter <robert.richter@amd.com>
+Date: Mon, 10 Oct 2011 16:21:10 +0200
+Subject: oprofile, x86: Fix crash when unloading module (nmi timer mode)
+
+From: Robert Richter <robert.richter@amd.com>
+
+commit 97f7f8189fe54e3cfe324ef9ad35064f3d2d3bff upstream.
+
+If oprofile uses the nmi timer interrupt there is a crash while
+unloading the module. The bug can be triggered with oprofile build as
+module and kernel parameter nolapic set. This patch fixes this.
+
+oprofile: using NMI timer interrupt.
+BUG: unable to handle kernel NULL pointer dereference at 0000000000000008
+IP: [<ffffffff8123c226>] unregister_syscore_ops+0x41/0x58
+PGD 42dbca067 PUD 41da6a067 PMD 0
+Oops: 0002 [#1] PREEMPT SMP
+CPU 5
+Modules linked in: oprofile(-) [last unloaded: oprofile]
+
+Pid: 2518, comm: modprobe Not tainted 3.1.0-rc7-00019-gb2fb49d #19 Advanced Micro Device Anaheim/Anaheim
+RIP: 0010:[<ffffffff8123c226>]  [<ffffffff8123c226>] unregister_syscore_ops+0x41/0x58
+RSP: 0018:ffff88041ef71e98  EFLAGS: 00010296
+RAX: 0000000000000000 RBX: ffffffffa0017100 RCX: dead000000200200
+RDX: 0000000000000000 RSI: dead000000100100 RDI: ffffffff8178c620
+RBP: ffff88041ef71ea8 R08: 0000000000000001 R09: 0000000000000082
+R10: 0000000000000000 R11: ffff88041ef71de8 R12: 0000000000000080
+R13: fffffffffffffff5 R14: 0000000000000001 R15: 0000000000610210
+FS:  00007fc902f20700(0000) GS:ffff88042fd40000(0000) knlGS:0000000000000000
+CS:  0010 DS: 0000 ES: 0000 CR0: 000000008005003b
+CR2: 0000000000000008 CR3: 000000041cdb6000 CR4: 00000000000006e0
+DR0: 0000000000000000 DR1: 0000000000000000 DR2: 0000000000000000
+DR3: 0000000000000000 DR6: 00000000ffff0ff0 DR7: 0000000000000400
+Process modprobe (pid: 2518, threadinfo ffff88041ef70000, task ffff88041d348040)
+Stack:
+ ffff88041ef71eb8 ffffffffa0017790 ffff88041ef71eb8 ffffffffa0013532
+ ffff88041ef71ec8 ffffffffa00132d6 ffff88041ef71ed8 ffffffffa00159b2
+ ffff88041ef71f78 ffffffff81073115 656c69666f72706f 0000000000610200
+Call Trace:
+ [<ffffffffa0013532>] op_nmi_exit+0x15/0x17 [oprofile]
+ [<ffffffffa00132d6>] oprofile_arch_exit+0xe/0x10 [oprofile]
+ [<ffffffffa00159b2>] oprofile_exit+0x1e/0x20 [oprofile]
+ [<ffffffff81073115>] sys_delete_module+0x1c3/0x22f
+ [<ffffffff811bf09e>] ? trace_hardirqs_on_thunk+0x3a/0x3f
+ [<ffffffff8148070b>] system_call_fastpath+0x16/0x1b
+Code: 20 c6 78 81 e8 c5 cc 23 00 48 8b 13 48 8b 43 08 48 be 00 01 10 00 00 00 ad de 48 b9 00 02 20 00 00 00 ad de 48 c7 c7 20 c6 78 81
+ 89 42 08 48 89 10 48 89 33 48 89 4b 08 e8 a6 c0 23 00 5a 5b
+RIP  [<ffffffff8123c226>] unregister_syscore_ops+0x41/0x58
+ RSP <ffff88041ef71e98>
+CR2: 0000000000000008
+---[ end trace 43a541a52956b7b0 ]---
+
+Signed-off-by: Robert Richter <robert.richter@amd.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ arch/x86/oprofile/init.c |    7 +++++--
+ 1 file changed, 5 insertions(+), 2 deletions(-)
+
+--- a/arch/x86/oprofile/init.c
++++ b/arch/x86/oprofile/init.c
+@@ -21,6 +21,7 @@ extern int op_nmi_timer_init(struct opro
+ extern void op_nmi_exit(void);
+ extern void x86_backtrace(struct pt_regs * const regs, unsigned int depth);
++static int nmi_timer;
+ int __init oprofile_arch_init(struct oprofile_operations *ops)
+ {
+@@ -31,8 +32,9 @@ int __init oprofile_arch_init(struct opr
+ #ifdef CONFIG_X86_LOCAL_APIC
+       ret = op_nmi_init(ops);
+ #endif
++      nmi_timer = (ret != 0);
+ #ifdef CONFIG_X86_IO_APIC
+-      if (ret < 0)
++      if (nmi_timer)
+               ret = op_nmi_timer_init(ops);
+ #endif
+       ops->backtrace = x86_backtrace;
+@@ -44,6 +46,7 @@ int __init oprofile_arch_init(struct opr
+ void oprofile_arch_exit(void)
+ {
+ #ifdef CONFIG_X86_LOCAL_APIC
+-      op_nmi_exit();
++      if (!nmi_timer)
++              op_nmi_exit();
+ #endif
+ }
diff --git a/queue-3.0/perf-x86-fix-pebs-instruction-unwind.patch b/queue-3.0/perf-x86-fix-pebs-instruction-unwind.patch
new file mode 100644 (file)
index 0000000..6f4ef94
--- /dev/null
@@ -0,0 +1,47 @@
+From 57d1c0c03c6b48b2b96870d831b9ce6b917f53ac Mon Sep 17 00:00:00 2001
+From: Peter Zijlstra <a.p.zijlstra@chello.nl>
+Date: Fri, 7 Oct 2011 13:36:40 +0200
+Subject: perf/x86: Fix PEBS instruction unwind
+
+From: Peter Zijlstra <a.p.zijlstra@chello.nl>
+
+commit 57d1c0c03c6b48b2b96870d831b9ce6b917f53ac upstream.
+
+Masami spotted that we always try to decode the instruction stream as
+64bit instructions when running a 64bit kernel, this doesn't work for
+ia32-compat proglets.
+
+Use TIF_IA32 to detect if we need to use the 32bit instruction
+decoder.
+
+Reported-by: Masami Hiramatsu <masami.hiramatsu.pt@hitachi.com>
+Signed-off-by: Peter Zijlstra <a.p.zijlstra@chello.nl>
+Signed-off-by: Ingo Molnar <mingo@elte.hu>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ arch/x86/kernel/cpu/perf_event_intel_ds.c |    6 +++++-
+ 1 file changed, 5 insertions(+), 1 deletion(-)
+
+--- a/arch/x86/kernel/cpu/perf_event_intel_ds.c
++++ b/arch/x86/kernel/cpu/perf_event_intel_ds.c
+@@ -508,6 +508,7 @@ static int intel_pmu_pebs_fixup_ip(struc
+       unsigned long from = cpuc->lbr_entries[0].from;
+       unsigned long old_to, to = cpuc->lbr_entries[0].to;
+       unsigned long ip = regs->ip;
++      int is_64bit = 0;
+       /*
+        * We don't need to fixup if the PEBS assist is fault like
+@@ -559,7 +560,10 @@ static int intel_pmu_pebs_fixup_ip(struc
+               } else
+                       kaddr = (void *)to;
+-              kernel_insn_init(&insn, kaddr);
++#ifdef CONFIG_X86_64
++              is_64bit = kernel_ip(to) || !test_thread_flag(TIF_IA32);
++#endif
++              insn_init(&insn, kaddr, is_64bit);
+               insn_get_length(&insn);
+               to += insn.length;
+       } while (to < ip);
diff --git a/queue-3.0/sched-x86-avoid-unnecessary-overflow-in-sched_clock.patch b/queue-3.0/sched-x86-avoid-unnecessary-overflow-in-sched_clock.patch
new file mode 100644 (file)
index 0000000..c05f2d6
--- /dev/null
@@ -0,0 +1,72 @@
+From 4cecf6d401a01d054afc1e5f605bcbfe553cb9b9 Mon Sep 17 00:00:00 2001
+From: Salman Qazi <sqazi@google.com>
+Date: Tue, 15 Nov 2011 14:12:06 -0800
+Subject: sched, x86: Avoid unnecessary overflow in sched_clock
+
+From: Salman Qazi <sqazi@google.com>
+
+commit 4cecf6d401a01d054afc1e5f605bcbfe553cb9b9 upstream.
+
+(Added the missing signed-off-by line)
+
+In hundreds of days, the __cycles_2_ns calculation in sched_clock
+has an overflow.  cyc * per_cpu(cyc2ns, cpu) exceeds 64 bits, causing
+the final value to become zero.  We can solve this without losing
+any precision.
+
+We can decompose TSC into quotient and remainder of division by the
+scale factor, and then use this to convert TSC into nanoseconds.
+
+Signed-off-by: Salman Qazi <sqazi@google.com>
+Acked-by: John Stultz <johnstul@us.ibm.com>
+Reviewed-by: Paul Turner <pjt@google.com>
+Signed-off-by: Peter Zijlstra <a.p.zijlstra@chello.nl>
+Link: http://lkml.kernel.org/r/20111115221121.7262.88871.stgit@dungbeetle.mtv.corp.google.com
+Signed-off-by: Ingo Molnar <mingo@elte.hu>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ arch/x86/include/asm/timer.h |   23 ++++++++++++++++++++++-
+ 1 file changed, 22 insertions(+), 1 deletion(-)
+
+--- a/arch/x86/include/asm/timer.h
++++ b/arch/x86/include/asm/timer.h
+@@ -32,6 +32,22 @@ extern int no_timer_check;
+  *  (mathieu.desnoyers@polymtl.ca)
+  *
+  *                    -johnstul@us.ibm.com "math is hard, lets go shopping!"
++ *
++ * In:
++ *
++ * ns = cycles * cyc2ns_scale / SC
++ *
++ * Although we may still have enough bits to store the value of ns,
++ * in some cases, we may not have enough bits to store cycles * cyc2ns_scale,
++ * leading to an incorrect result.
++ *
++ * To avoid this, we can decompose 'cycles' into quotient and remainder
++ * of division by SC.  Then,
++ *
++ * ns = (quot * SC + rem) * cyc2ns_scale / SC
++ *    = quot * cyc2ns_scale + (rem * cyc2ns_scale) / SC
++ *
++ *                    - sqazi@google.com
+  */
+ DECLARE_PER_CPU(unsigned long, cyc2ns);
+@@ -41,9 +57,14 @@ DECLARE_PER_CPU(unsigned long long, cyc2
+ static inline unsigned long long __cycles_2_ns(unsigned long long cyc)
+ {
++      unsigned long long quot;
++      unsigned long long rem;
+       int cpu = smp_processor_id();
+       unsigned long long ns = per_cpu(cyc2ns_offset, cpu);
+-      ns += cyc * per_cpu(cyc2ns, cpu) >> CYC2NS_SCALE_FACTOR;
++      quot = (cyc >> CYC2NS_SCALE_FACTOR);
++      rem = cyc & ((1ULL << CYC2NS_SCALE_FACTOR) - 1);
++      ns += quot * per_cpu(cyc2ns, cpu) +
++              ((rem * per_cpu(cyc2ns, cpu)) >> CYC2NS_SCALE_FACTOR);
+       return ns;
+ }
index 1613c5a69baedb1460c0a6cb59d6e7985a4f9cab..b65d8394984b794b5f45f9966de296773076d5cd 100644 (file)
@@ -55,3 +55,18 @@ usb-usb-storage-unusual_devs-entry-for-kingston-dt-101-g2.patch
 usb-ehci-fix-hub-tt-scheduling-issue-with-iso-transfer.patch
 ehci-fix-a-regression-in-the-iso-scheduler.patch
 xhci-fix-bug-in-xhci_clear_command_ring.patch
+sched-x86-avoid-unnecessary-overflow-in-sched_clock.patch
+x86-mpparse-account-for-bus-types-other-than-isa-and-pci.patch
+x86-fix-acer-aspire-1-reboot-hang.patch
+x86-paravirt-pte-updates-in-k-un-map_atomic-need-to-be-synchronous-regardless-of-lazy_mmu-mode.patch
+perf-x86-fix-pebs-instruction-unwind.patch
+oprofile-x86-fix-crash-when-unloading-module-nmi-timer-mode.patch
+add-missing-.set-function-for-nt_s390_last_break-regset.patch
+mac80211-fill-rate-filter-for-internal-scan-requests.patch
+cfg80211-fix-race-on-init-and-driver-registration.patch
+cfg80211-amend-regulatory-null-dereference-fix.patch
+genirq-fix-race-condition-when-stopping-the-irq-thread.patch
+nfs-prevent-3.0-from-crashing-if-it-receives-a-partial-layout.patch
+xfs-validate-acl-count.patch
+xfs-force-buffer-writeback-before-blocking-on-the-ilock-in-inode-reclaim.patch
+xfs-fix-attr2-vs-large-data-fork-assert.patch
diff --git a/queue-3.0/x86-fix-acer-aspire-1-reboot-hang.patch b/queue-3.0/x86-fix-acer-aspire-1-reboot-hang.patch
new file mode 100644 (file)
index 0000000..ae925e1
--- /dev/null
@@ -0,0 +1,72 @@
+From 1ef03890969932e9359b9a4c658f7f87771910ac Mon Sep 17 00:00:00 2001
+From: Peter Chubb <peter.chubb@nicta.com.au>
+Date: Mon, 5 Dec 2011 16:53:53 +0300
+Subject: x86: Fix "Acer Aspire 1" reboot hang
+MIME-Version: 1.0
+Content-Type: text/plain; charset=UTF-8
+Content-Transfer-Encoding: 8bit
+
+From: Peter Chubb <peter.chubb@nicta.com.au>
+
+commit 1ef03890969932e9359b9a4c658f7f87771910ac upstream.
+
+Looks like on some Acer Aspire 1s with older bioses, reboot via bios
+fails.  It works on my machine, (with BIOS version 0.3310) but
+not on some others (BIOS version 0.3309).
+
+There's a log of problems at:
+
+  https://bbs.archlinux.org/viewtopic.php?id=124136
+
+This patch adds a different callback to the reboot quirk table,
+to allow rebooting via keybaord controller.
+
+Reported-by: Uroš Vampl <mobile.leecher@gmail.com>
+Tested-by: Vasily Khoruzhick <anarsoul@gmail.com>
+Signed-off-by: Peter Chubb <peter.chubb@nicta.com.au>
+Cc: Don Zickus <dzickus@redhat.com>
+Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
+Link: http://lkml.kernel.org/r/1323093233-9481-1-git-send-email-anarsoul@gmail.com
+Signed-off-by: Ingo Molnar <mingo@elte.hu>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ arch/x86/kernel/reboot.c |   13 +++++++++++--
+ 1 file changed, 11 insertions(+), 2 deletions(-)
+
+--- a/arch/x86/kernel/reboot.c
++++ b/arch/x86/kernel/reboot.c
+@@ -124,7 +124,7 @@ __setup("reboot=", reboot_setup);
+  */
+ /*
+- * Some machines require the "reboot=b"  commandline option,
++ * Some machines require the "reboot=b" or "reboot=k"  commandline options,
+  * this quirk makes that automatic.
+  */
+ static int __init set_bios_reboot(const struct dmi_system_id *d)
+@@ -136,6 +136,15 @@ static int __init set_bios_reboot(const
+       return 0;
+ }
++static int __init set_kbd_reboot(const struct dmi_system_id *d)
++{
++      if (reboot_type != BOOT_KBD) {
++              reboot_type = BOOT_KBD;
++              printk(KERN_INFO "%s series board detected. Selecting KBD-method for reboot.\n", d->ident);
++      }
++      return 0;
++}
++
+ static struct dmi_system_id __initdata reboot_dmi_table[] = {
+       {       /* Handle problems with rebooting on Dell E520's */
+               .callback = set_bios_reboot,
+@@ -295,7 +304,7 @@ static struct dmi_system_id __initdata r
+               },
+       },
+       { /* Handle reboot issue on Acer Aspire one */
+-              .callback = set_bios_reboot,
++              .callback = set_kbd_reboot,
+               .ident = "Acer Aspire One A110",
+               .matches = {
+                       DMI_MATCH(DMI_SYS_VENDOR, "Acer"),
diff --git a/queue-3.0/x86-mpparse-account-for-bus-types-other-than-isa-and-pci.patch b/queue-3.0/x86-mpparse-account-for-bus-types-other-than-isa-and-pci.patch
new file mode 100644 (file)
index 0000000..81658e3
--- /dev/null
@@ -0,0 +1,54 @@
+From 9e6866686bdf2dcf3aeb0838076237ede532dcc8 Mon Sep 17 00:00:00 2001
+From: Bjorn Helgaas <bhelgaas@google.com>
+Date: Sun, 25 Sep 2011 15:29:00 -0600
+Subject: x86/mpparse: Account for bus types other than ISA and PCI
+
+From: Bjorn Helgaas <bhelgaas@google.com>
+
+commit 9e6866686bdf2dcf3aeb0838076237ede532dcc8 upstream.
+
+In commit f8924e770e04 ("x86: unify mp_bus_info"), the 32-bit
+and 64-bit versions of MP_bus_info were rearranged to match each
+other better.  Unfortunately it introduced a regression: prior
+to that change we used to always set the mp_bus_not_pci bit,
+then clear it if we found a PCI bus.  After it, we set
+mp_bus_not_pci for ISA buses, clear it for PCI buses, and leave
+it alone otherwise.
+
+In the cases of ISA and PCI, there's not much difference.  But
+ISA is not the only non-PCI bus, so it's better to always set
+mp_bus_not_pci and clear it only for PCI.
+
+Without this change, Dan's Dell PowerEdge 4200 panics on boot
+with a log indicating interrupt routing trouble unless the
+"noapic" option is supplied.  With this change, the machine
+boots reliably without "noapic".
+
+Fixes http://bugs.debian.org/586494
+
+Reported-bisected-and-tested-by: Dan McGrath <troubledaemon@gmail.com>
+Signed-off-by: Bjorn Helgaas <bhelgaas@google.com>
+Cc: Dan McGrath <troubledaemon@gmail.com>
+Cc: Alexey Starikovskiy <aystarik@gmail.com>
+[jrnieder@gmail.com: clarified commit message]
+Signed-off-by: Jonathan Nieder <jrnieder@gmail.com>
+Link: http://lkml.kernel.org/r/20111122215000.GA9151@elie.hsd1.il.comcast.net
+Signed-off-by: Ingo Molnar <mingo@elte.hu>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ arch/x86/kernel/mpparse.c |    2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+--- a/arch/x86/kernel/mpparse.c
++++ b/arch/x86/kernel/mpparse.c
+@@ -95,8 +95,8 @@ static void __init MP_bus_info(struct mp
+       }
+ #endif
++      set_bit(m->busid, mp_bus_not_pci);
+       if (strncmp(str, BUSTYPE_ISA, sizeof(BUSTYPE_ISA) - 1) == 0) {
+-              set_bit(m->busid, mp_bus_not_pci);
+ #if defined(CONFIG_EISA) || defined(CONFIG_MCA)
+               mp_bus_id_to_type[m->busid] = MP_BUS_ISA;
+ #endif
diff --git a/queue-3.0/x86-paravirt-pte-updates-in-k-un-map_atomic-need-to-be-synchronous-regardless-of-lazy_mmu-mode.patch b/queue-3.0/x86-paravirt-pte-updates-in-k-un-map_atomic-need-to-be-synchronous-regardless-of-lazy_mmu-mode.patch
new file mode 100644 (file)
index 0000000..a3ed707
--- /dev/null
@@ -0,0 +1,87 @@
+From 2cd1c8d4dc7ecca9e9431e2dabe41ae9c7d89e51 Mon Sep 17 00:00:00 2001
+From: Konrad Rzeszutek Wilk <konrad.wilk@oracle.com>
+Date: Tue, 15 Nov 2011 14:49:09 -0800
+Subject: x86/paravirt: PTE updates in k(un)map_atomic need to be synchronous, regardless of lazy_mmu mode
+
+From: Konrad Rzeszutek Wilk <konrad.wilk@oracle.com>
+
+commit 2cd1c8d4dc7ecca9e9431e2dabe41ae9c7d89e51 upstream.
+
+Fix an outstanding issue that has been reported since 2.6.37.
+Under a heavy loaded machine processing "fork()" calls could
+crash with:
+
+BUG: unable to handle kernel paging request at f573fc8c
+IP: [<c01abc54>] swap_count_continued+0x104/0x180
+*pdpt = 000000002a3b9027 *pde = 0000000001bed067 *pte = 0000000000000000 Oops: 0000 [#1] SMP
+Modules linked in:
+Pid: 1638, comm: apache2 Not tainted 3.0.4-linode37 #1
+EIP: 0061:[<c01abc54>] EFLAGS: 00210246 CPU: 3
+EIP is at swap_count_continued+0x104/0x180
+.. snip..
+Call Trace:
+ [<c01ac222>] ? __swap_duplicate+0xc2/0x160
+ [<c01040f7>] ? pte_mfn_to_pfn+0x87/0xe0
+ [<c01ac2e4>] ? swap_duplicate+0x14/0x40
+ [<c01a0a6b>] ? copy_pte_range+0x45b/0x500
+ [<c01a0ca5>] ? copy_page_range+0x195/0x200
+ [<c01328c6>] ? dup_mmap+0x1c6/0x2c0
+ [<c0132cf8>] ? dup_mm+0xa8/0x130
+ [<c013376a>] ? copy_process+0x98a/0xb30
+ [<c013395f>] ? do_fork+0x4f/0x280
+ [<c01573b3>] ? getnstimeofday+0x43/0x100
+ [<c010f770>] ? sys_clone+0x30/0x40
+ [<c06c048d>] ? ptregs_clone+0x15/0x48
+ [<c06bfb71>] ? syscall_call+0x7/0xb
+
+The problem is that in copy_page_range() we turn lazy mode on,
+and then in swap_entry_free() we call swap_count_continued()
+which ends up in:
+
+         map = kmap_atomic(page, KM_USER0) + offset;
+
+and then later we touch *map.
+
+Since we are running in batched mode (lazy) we don't actually
+set up the PTE mappings and the kmap_atomic is not done
+synchronously and ends up trying to dereference a page that has
+not been set.
+
+Looking at kmap_atomic_prot_pfn(), it uses
+'arch_flush_lazy_mmu_mode' and doing the same in
+kmap_atomic_prot() and __kunmap_atomic() makes the problem go
+away.
+
+Interestingly, commit b8bcfe997e4615 ("x86/paravirt: remove lazy
+mode in interrupts") removed part of this to fix an interrupt
+issue - but it went to far and did not consider this scenario.
+
+Signed-off-by: Konrad Rzeszutek Wilk <konrad.wilk@oracle.com>
+Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
+Cc: Jeremy Fitzhardinge <jeremy.fitzhardinge@citrix.com>
+Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
+Signed-off-by: Ingo Molnar <mingo@elte.hu>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ arch/x86/mm/highmem_32.c |    2 ++
+ 1 file changed, 2 insertions(+)
+
+--- a/arch/x86/mm/highmem_32.c
++++ b/arch/x86/mm/highmem_32.c
+@@ -45,6 +45,7 @@ void *kmap_atomic_prot(struct page *page
+       vaddr = __fix_to_virt(FIX_KMAP_BEGIN + idx);
+       BUG_ON(!pte_none(*(kmap_pte-idx)));
+       set_pte(kmap_pte-idx, mk_pte(page, prot));
++      arch_flush_lazy_mmu_mode();
+       return (void *)vaddr;
+ }
+@@ -88,6 +89,7 @@ void __kunmap_atomic(void *kvaddr)
+                */
+               kpte_clear_flush(kmap_pte-idx, vaddr);
+               kmap_atomic_idx_pop();
++              arch_flush_lazy_mmu_mode();
+       }
+ #ifdef CONFIG_DEBUG_HIGHMEM
+       else {
diff --git a/queue-3.0/xfs-fix-attr2-vs-large-data-fork-assert.patch b/queue-3.0/xfs-fix-attr2-vs-large-data-fork-assert.patch
new file mode 100644 (file)
index 0000000..d2555a3
--- /dev/null
@@ -0,0 +1,154 @@
+From hch@infradead.org  Tue Dec  6 14:02:17 2011
+From: Christoph Hellwig <hch@infradead.org>
+Date: Tue, 6 Dec 2011 16:21:30 -0500
+Subject: xfs: fix attr2 vs large data fork assert
+To: stable@vger.kernel.org
+Cc: xfs@oss.sgi.com
+Message-ID: <20111206212130.GC28459@infradead.org>
+Content-Disposition: inline
+
+From: Christoph Hellwig <hch@infradead.org>
+
+commit 4c393a6059f8442a70512a48ce4639b882b6f6ad upstream.
+
+With Dmitry fsstress updates I've seen very reproducible crashes in
+xfs_attr_shortform_remove because xfs_attr_shortform_bytesfit claims that
+the attributes would not fit inline into the inode after removing an
+attribute.  It turns out that we were operating on an inode with lots
+of delalloc extents, and thus an if_bytes values for the data fork that
+is larger than biggest possible on-disk storage for it which utterly
+confuses the code near the end of xfs_attr_shortform_bytesfit.
+
+Fix this by always allowing the current attribute fork, like we already
+do for the attr1 format, given that delalloc conversion will take care
+for moving either the data or attribute area out of line if it doesn't
+fit at that point - or making the point moot by merging extents at this
+point.
+
+Also document the function better, and clean up some loose bits.
+
+Reviewed-by: Dave Chinner <dchinner@redhat.com>
+Signed-off-by: Christoph Hellwig <hch@lst.de>
+Signed-off-by: Ben Myers <bpm@sgi.com>
+Acked-by: Dave Chinner <dchinner@redhat.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ fs/xfs/xfs_attr_leaf.c |   64 +++++++++++++++++++++++++++++--------------------
+ 1 file changed, 39 insertions(+), 25 deletions(-)
+
+--- a/fs/xfs/xfs_attr_leaf.c
++++ b/fs/xfs/xfs_attr_leaf.c
+@@ -110,6 +110,7 @@ xfs_attr_namesp_match(int arg_flags, int
+ /*
+  * Query whether the requested number of additional bytes of extended
+  * attribute space will be able to fit inline.
++ *
+  * Returns zero if not, else the di_forkoff fork offset to be used in the
+  * literal area for attribute data once the new bytes have been added.
+  *
+@@ -122,7 +123,7 @@ xfs_attr_shortform_bytesfit(xfs_inode_t
+       int offset;
+       int minforkoff; /* lower limit on valid forkoff locations */
+       int maxforkoff; /* upper limit on valid forkoff locations */
+-      int dsize;      
++      int dsize;
+       xfs_mount_t *mp = dp->i_mount;
+       offset = (XFS_LITINO(mp) - bytes) >> 3; /* rounded down */
+@@ -136,47 +137,60 @@ xfs_attr_shortform_bytesfit(xfs_inode_t
+               return (offset >= minforkoff) ? minforkoff : 0;
+       }
+-      if (!(mp->m_flags & XFS_MOUNT_ATTR2)) {
+-              if (bytes <= XFS_IFORK_ASIZE(dp))
+-                      return dp->i_d.di_forkoff;
++      /*
++       * If the requested numbers of bytes is smaller or equal to the
++       * current attribute fork size we can always proceed.
++       *
++       * Note that if_bytes in the data fork might actually be larger than
++       * the current data fork size is due to delalloc extents. In that
++       * case either the extent count will go down when they are converted
++       * to real extents, or the delalloc conversion will take care of the
++       * literal area rebalancing.
++       */
++      if (bytes <= XFS_IFORK_ASIZE(dp))
++              return dp->i_d.di_forkoff;
++
++      /*
++       * For attr2 we can try to move the forkoff if there is space in the
++       * literal area, but for the old format we are done if there is no
++       * space in the fixed attribute fork.
++       */
++      if (!(mp->m_flags & XFS_MOUNT_ATTR2))
+               return 0;
+-      }
+       dsize = dp->i_df.if_bytes;
+-      
++
+       switch (dp->i_d.di_format) {
+       case XFS_DINODE_FMT_EXTENTS:
+-              /* 
++              /*
+                * If there is no attr fork and the data fork is extents, 
+-               * determine if creating the default attr fork will result 
+-               * in the extents form migrating to btree. If so, the 
+-               * minimum offset only needs to be the space required for 
++               * determine if creating the default attr fork will result
++               * in the extents form migrating to btree. If so, the
++               * minimum offset only needs to be the space required for
+                * the btree root.
+-               */ 
++               */
+               if (!dp->i_d.di_forkoff && dp->i_df.if_bytes >
+                   xfs_default_attroffset(dp))
+                       dsize = XFS_BMDR_SPACE_CALC(MINDBTPTRS);
+               break;
+-              
+       case XFS_DINODE_FMT_BTREE:
+               /*
+-               * If have data btree then keep forkoff if we have one,
+-               * otherwise we are adding a new attr, so then we set 
+-               * minforkoff to where the btree root can finish so we have 
++               * If we have a data btree then keep forkoff if we have one,
++               * otherwise we are adding a new attr, so then we set
++               * minforkoff to where the btree root can finish so we have
+                * plenty of room for attrs
+                */
+               if (dp->i_d.di_forkoff) {
+-                      if (offset < dp->i_d.di_forkoff) 
++                      if (offset < dp->i_d.di_forkoff)
+                               return 0;
+-                      else 
+-                              return dp->i_d.di_forkoff;
+-              } else
+-                      dsize = XFS_BMAP_BROOT_SPACE(dp->i_df.if_broot);
++                      return dp->i_d.di_forkoff;
++              }
++              dsize = XFS_BMAP_BROOT_SPACE(dp->i_df.if_broot);
+               break;
+       }
+-      
+-      /* 
+-       * A data fork btree root must have space for at least 
++
++      /*
++       * A data fork btree root must have space for at least
+        * MINDBTPTRS key/ptr pairs if the data fork is small or empty.
+        */
+       minforkoff = MAX(dsize, XFS_BMDR_SPACE_CALC(MINDBTPTRS));
+@@ -186,10 +200,10 @@ xfs_attr_shortform_bytesfit(xfs_inode_t
+       maxforkoff = XFS_LITINO(mp) - XFS_BMDR_SPACE_CALC(MINABTPTRS);
+       maxforkoff = maxforkoff >> 3;   /* rounded down */
+-      if (offset >= minforkoff && offset < maxforkoff)
+-              return offset;
+       if (offset >= maxforkoff)
+               return maxforkoff;
++      if (offset >= minforkoff)
++              return offset;
+       return 0;
+ }
diff --git a/queue-3.0/xfs-force-buffer-writeback-before-blocking-on-the-ilock-in-inode-reclaim.patch b/queue-3.0/xfs-force-buffer-writeback-before-blocking-on-the-ilock-in-inode-reclaim.patch
new file mode 100644 (file)
index 0000000..4d5037c
--- /dev/null
@@ -0,0 +1,94 @@
+From hch@infradead.org  Tue Dec  6 14:01:57 2011
+From: Christoph Hellwig <hch@infradead.org>
+Date: Tue, 6 Dec 2011 16:21:15 -0500
+Subject: xfs: force buffer writeback before blocking on the ilock in inode reclaim
+To: stable@vger.kernel.org
+Cc: xfs@oss.sgi.com
+Message-ID: <20111206212115.GB28459@infradead.org>
+Content-Disposition: inline
+
+From: Christoph Hellwig <hch@infradead.org>
+
+commit 4dd2cb4a28b7ab1f37163a4eba280926a13a8749 upstream.
+
+If we are doing synchronous inode reclaim we block the VM from making
+progress in memory reclaim.  So if we encouter a flush locked inode
+promote it in the delwri list and wake up xfsbufd to write it out now.
+Without this we can get hangs of up to 30 seconds during workloads hitting
+synchronous inode reclaim.
+
+The scheme is copied from what we do for dquot reclaims.
+
+Reported-by: Simon Kirby <sim@hostway.ca>
+Signed-off-by: Christoph Hellwig <hch@lst.de>
+Tested-by: Simon Kirby <sim@hostway.ca>
+Signed-off-by: Ben Myers <bpm@sgi.com>
+Acked-by: Dave Chinner <dchinner@redhat.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ fs/xfs/linux-2.6/xfs_sync.c |   11 +++++++++++
+ fs/xfs/xfs_inode.c          |   21 +++++++++++++++++++++
+ fs/xfs/xfs_inode.h          |    1 +
+ 3 files changed, 33 insertions(+)
+
+--- a/fs/xfs/linux-2.6/xfs_sync.c
++++ b/fs/xfs/linux-2.6/xfs_sync.c
+@@ -772,6 +772,17 @@ restart:
+       if (!xfs_iflock_nowait(ip)) {
+               if (!(sync_mode & SYNC_WAIT))
+                       goto out;
++
++              /*
++               * If we only have a single dirty inode in a cluster there is
++               * a fair chance that the AIL push may have pushed it into
++               * the buffer, but xfsbufd won't touch it until 30 seconds
++               * from now, and thus we will lock up here.
++               *
++               * Promote the inode buffer to the front of the delwri list
++               * and wake up xfsbufd now.
++               */
++              xfs_promote_inode(ip);
+               xfs_iflock(ip);
+       }
+--- a/fs/xfs/xfs_inode.c
++++ b/fs/xfs/xfs_inode.c
+@@ -3099,6 +3099,27 @@ corrupt_out:
+       return XFS_ERROR(EFSCORRUPTED);
+ }
++void
++xfs_promote_inode(
++      struct xfs_inode        *ip)
++{
++      struct xfs_buf          *bp;
++
++      ASSERT(xfs_isilocked(ip, XFS_ILOCK_EXCL|XFS_ILOCK_SHARED));
++
++      bp = xfs_incore(ip->i_mount->m_ddev_targp, ip->i_imap.im_blkno,
++                      ip->i_imap.im_len, XBF_TRYLOCK);
++      if (!bp)
++              return;
++
++      if (XFS_BUF_ISDELAYWRITE(bp)) {
++              xfs_buf_delwri_promote(bp);
++              wake_up_process(ip->i_mount->m_ddev_targp->bt_task);
++      }
++
++      xfs_buf_relse(bp);
++}
++
+ /*
+  * Return a pointer to the extent record at file index idx.
+  */
+--- a/fs/xfs/xfs_inode.h
++++ b/fs/xfs/xfs_inode.h
+@@ -509,6 +509,7 @@ int                xfs_iunlink(struct xfs_trans *, xfs
+ void          xfs_iext_realloc(xfs_inode_t *, int, int);
+ void          xfs_iunpin_wait(xfs_inode_t *);
+ int           xfs_iflush(xfs_inode_t *, uint);
++void          xfs_promote_inode(struct xfs_inode *);
+ void          xfs_lock_inodes(xfs_inode_t **, int, uint);
+ void          xfs_lock_two_inodes(xfs_inode_t *, xfs_inode_t *, uint);
diff --git a/queue-3.0/xfs-validate-acl-count.patch b/queue-3.0/xfs-validate-acl-count.patch
new file mode 100644 (file)
index 0000000..bd1d691
--- /dev/null
@@ -0,0 +1,36 @@
+From hch@infradead.org  Tue Dec  6 14:00:24 2011
+From: Christoph Hellwig <hch@infradead.org>
+Date: Tue, 6 Dec 2011 16:21:05 -0500
+Subject: xfs: validate acl count
+To: stable@vger.kernel.org
+Cc: xfs@oss.sgi.com
+Message-ID: <20111206212105.GA28459@infradead.org>
+Content-Disposition: inline
+
+From: Christoph Hellwig <hch@infradead.org>
+
+commit fa8b18edd752a8b4e9d1ee2cd615b82c93cf8bba upstream.
+
+This prevents in-memory corruption and possible panics if the on-disk
+ACL is badly corrupted.
+
+Signed-off-by: Christoph Hellwig <hch@lst.de>
+Signed-off-by: Ben Myers <bpm@sgi.com>
+Acked-by: Dave Chinner <dchinner@redhat.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ fs/xfs/linux-2.6/xfs_acl.c |    2 ++
+ 1 file changed, 2 insertions(+)
+
+--- a/fs/xfs/linux-2.6/xfs_acl.c
++++ b/fs/xfs/linux-2.6/xfs_acl.c
+@@ -42,6 +42,8 @@ xfs_acl_from_disk(struct xfs_acl *aclp)
+       int count, i;
+       count = be32_to_cpu(aclp->acl_cnt);
++      if (count > XFS_ACL_MAX_ENTRIES)
++              return ERR_PTR(-EFSCORRUPTED);
+       acl = posix_acl_alloc(count, GFP_KERNEL);
+       if (!acl)