]> git.ipfire.org Git - thirdparty/kernel/stable-queue.git/commitdiff
3.1 patches
authorGreg Kroah-Hartman <gregkh@suse.de>
Thu, 3 Nov 2011 19:35:34 +0000 (12:35 -0700)
committerGreg Kroah-Hartman <gregkh@suse.de>
Thu, 3 Nov 2011 19:35:34 +0000 (12:35 -0700)
queue-3.1/drivers-power-ds2780_battery.c-add-a-nolock-function-to-w1-interface.patch [new file with mode: 0644]
queue-3.1/drivers-power-ds2780_battery.c-create-central-point-for-calling-w1-interface.patch [new file with mode: 0644]
queue-3.1/drivers-power-ds2780_battery.c-fix-deadlock-upon-insertion-and-removal.patch [new file with mode: 0644]
queue-3.1/ext2-ext3-ext4-don-t-inherit-append_fl-or-immutable_fl-for-new-inodes.patch [new file with mode: 0644]
queue-3.1/ext4-call-ext4_handle_dirty_metadata-with-correct-inode-in-ext4_dx_add_entry.patch [new file with mode: 0644]
queue-3.1/ext4-ext4_mkdir-should-dirty-dir_block-with-newly-created-directory-inode.patch [new file with mode: 0644]
queue-3.1/ext4-ext4_rename-should-dirty-dir_bh-with-the-correct-directory.patch [new file with mode: 0644]
queue-3.1/ext4-fix-race-in-xattr-block-allocation-path.patch [new file with mode: 0644]
queue-3.1/ext4-let-ext4_page_mkwrite-stop-started-handle-in-failure.patch [new file with mode: 0644]
queue-3.1/hwspinlock-core-use-a-mutex-to-protect-the-radix-tree.patch [new file with mode: 0644]
queue-3.1/series

diff --git a/queue-3.1/drivers-power-ds2780_battery.c-add-a-nolock-function-to-w1-interface.patch b/queue-3.1/drivers-power-ds2780_battery.c-add-a-nolock-function-to-w1-interface.patch
new file mode 100644 (file)
index 0000000..122c990
--- /dev/null
@@ -0,0 +1,114 @@
+From 9fe678fa2feb4aaac0b4220de63e1b7f8ccebae6 Mon Sep 17 00:00:00 2001
+From: Clifton Barnes <cabarnes@indesign-llc.com>
+Date: Wed, 2 Nov 2011 13:39:52 -0700
+Subject: drivers/power/ds2780_battery.c: add a nolock function to w1 interface
+
+From: Clifton Barnes <cabarnes@indesign-llc.com>
+
+commit 9fe678fa2feb4aaac0b4220de63e1b7f8ccebae6 upstream.
+
+Adds a nolock function to the w1 interface to avoid locking the
+mutex if needed.
+
+Signed-off-by: Clifton Barnes <cabarnes@indesign-llc.com>
+Cc: Evgeniy Polyakov <zbr@ioremap.net>
+Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
+Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ drivers/w1/slaves/w1_ds2780.c |   48 ++++++++++++++++++++++++++++++------------
+ drivers/w1/slaves/w1_ds2780.h |    2 +
+ 2 files changed, 37 insertions(+), 13 deletions(-)
+
+--- a/drivers/w1/slaves/w1_ds2780.c
++++ b/drivers/w1/slaves/w1_ds2780.c
+@@ -26,20 +26,14 @@
+ #include "../w1_family.h"
+ #include "w1_ds2780.h"
+-int w1_ds2780_io(struct device *dev, char *buf, int addr, size_t count,
+-                      int io)
++static int w1_ds2780_do_io(struct device *dev, char *buf, int addr,
++                      size_t count, int io)
+ {
+       struct w1_slave *sl = container_of(dev, struct w1_slave, dev);
+-      if (!dev)
+-              return -ENODEV;
+-
+-      mutex_lock(&sl->master->mutex);
++      if (addr > DS2780_DATA_SIZE || addr < 0)
++              return 0;
+-      if (addr > DS2780_DATA_SIZE || addr < 0) {
+-              count = 0;
+-              goto out;
+-      }
+       count = min_t(int, count, DS2780_DATA_SIZE - addr);
+       if (w1_reset_select_slave(sl) == 0) {
+@@ -47,7 +41,6 @@ int w1_ds2780_io(struct device *dev, cha
+                       w1_write_8(sl->master, W1_DS2780_WRITE_DATA);
+                       w1_write_8(sl->master, addr);
+                       w1_write_block(sl->master, buf, count);
+-                      /* XXX w1_write_block returns void, not n_written */
+               } else {
+                       w1_write_8(sl->master, W1_DS2780_READ_DATA);
+                       w1_write_8(sl->master, addr);
+@@ -55,13 +48,42 @@ int w1_ds2780_io(struct device *dev, cha
+               }
+       }
+-out:
++      return count;
++}
++
++int w1_ds2780_io(struct device *dev, char *buf, int addr, size_t count,
++                      int io)
++{
++      struct w1_slave *sl = container_of(dev, struct w1_slave, dev);
++      int ret;
++
++      if (!dev)
++              return -ENODEV;
++
++      mutex_lock(&sl->master->mutex);
++
++      ret = w1_ds2780_do_io(dev, buf, addr, count, io);
++
+       mutex_unlock(&sl->master->mutex);
+-      return count;
++      return ret;
+ }
+ EXPORT_SYMBOL(w1_ds2780_io);
++int w1_ds2780_io_nolock(struct device *dev, char *buf, int addr, size_t count,
++                      int io)
++{
++      int ret;
++
++      if (!dev)
++              return -ENODEV;
++
++      ret = w1_ds2780_do_io(dev, buf, addr, count, io);
++
++      return ret;
++}
++EXPORT_SYMBOL(w1_ds2780_io_nolock);
++
+ int w1_ds2780_eeprom_cmd(struct device *dev, int addr, int cmd)
+ {
+       struct w1_slave *sl = container_of(dev, struct w1_slave, dev);
+--- a/drivers/w1/slaves/w1_ds2780.h
++++ b/drivers/w1/slaves/w1_ds2780.h
+@@ -124,6 +124,8 @@
+ extern int w1_ds2780_io(struct device *dev, char *buf, int addr, size_t count,
+                       int io);
++extern int w1_ds2780_io_nolock(struct device *dev, char *buf, int addr,
++                      size_t count, int io);
+ extern int w1_ds2780_eeprom_cmd(struct device *dev, int addr, int cmd);
+ #endif /* !_W1_DS2780_H */
diff --git a/queue-3.1/drivers-power-ds2780_battery.c-create-central-point-for-calling-w1-interface.patch b/queue-3.1/drivers-power-ds2780_battery.c-create-central-point-for-calling-w1-interface.patch
new file mode 100644 (file)
index 0000000..8c5edea
--- /dev/null
@@ -0,0 +1,278 @@
+From 853eee72f74f449797f0500ea19fc1bf497428d8 Mon Sep 17 00:00:00 2001
+From: Clifton Barnes <cabarnes@indesign-llc.com>
+Date: Wed, 2 Nov 2011 13:39:50 -0700
+Subject: drivers/power/ds2780_battery.c: create central point for calling w1 interface
+
+From: Clifton Barnes <cabarnes@indesign-llc.com>
+
+commit 853eee72f74f449797f0500ea19fc1bf497428d8 upstream.
+
+Simply creates one point to call the w1 interface.
+
+Signed-off-by: Clifton Barnes <cabarnes@indesign-llc.com>
+Cc: Evgeniy Polyakov <zbr@ioremap.net>
+Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
+Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ drivers/power/ds2780_battery.c |   77 ++++++++++++++++++++++-------------------
+ 1 file changed, 42 insertions(+), 35 deletions(-)
+
+--- a/drivers/power/ds2780_battery.c
++++ b/drivers/power/ds2780_battery.c
+@@ -49,8 +49,8 @@ enum current_types {
+ static const char model[] = "DS2780";
+ static const char manufacturer[] = "Maxim/Dallas";
+-static inline struct ds2780_device_info *to_ds2780_device_info(
+-      struct power_supply *psy)
++static inline struct ds2780_device_info *
++to_ds2780_device_info(struct power_supply *psy)
+ {
+       return container_of(psy, struct ds2780_device_info, bat);
+ }
+@@ -60,17 +60,25 @@ static inline struct power_supply *to_po
+       return dev_get_drvdata(dev);
+ }
+-static inline int ds2780_read8(struct device *dev, u8 *val, int addr)
++static inline int ds2780_battery_io(struct ds2780_device_info *dev_info,
++      char *buf, int addr, size_t count, int io)
+ {
+-      return w1_ds2780_io(dev, val, addr, sizeof(u8), 0);
++              return w1_ds2780_io(dev_info->w1_dev, buf, addr, count, io);
+ }
+-static int ds2780_read16(struct device *dev, s16 *val, int addr)
++static inline int ds2780_read8(struct ds2780_device_info *dev_info, u8 *val,
++      int addr)
++{
++      return ds2780_battery_io(dev_info, val, addr, sizeof(u8), 0);
++}
++
++static int ds2780_read16(struct ds2780_device_info *dev_info, s16 *val,
++      int addr)
+ {
+       int ret;
+       u8 raw[2];
+-      ret = w1_ds2780_io(dev, raw, addr, sizeof(u8) * 2, 0);
++      ret = ds2780_battery_io(dev_info, raw, addr, sizeof(raw), 0);
+       if (ret < 0)
+               return ret;
+@@ -79,16 +87,16 @@ static int ds2780_read16(struct device *
+       return 0;
+ }
+-static inline int ds2780_read_block(struct device *dev, u8 *val, int addr,
+-      size_t count)
++static inline int ds2780_read_block(struct ds2780_device_info *dev_info,
++      u8 *val, int addr, size_t count)
+ {
+-      return w1_ds2780_io(dev, val, addr, count, 0);
++      return ds2780_battery_io(dev_info, val, addr, count, 0);
+ }
+-static inline int ds2780_write(struct device *dev, u8 *val, int addr,
+-      size_t count)
++static inline int ds2780_write(struct ds2780_device_info *dev_info, u8 *val,
++      int addr, size_t count)
+ {
+-      return w1_ds2780_io(dev, val, addr, count, 1);
++      return ds2780_battery_io(dev_info, val, addr, count, 1);
+ }
+ static inline int ds2780_store_eeprom(struct device *dev, int addr)
+@@ -122,7 +130,7 @@ static int ds2780_set_sense_register(str
+ {
+       int ret;
+-      ret = ds2780_write(dev_info->w1_dev, &conductance,
++      ret = ds2780_write(dev_info, &conductance,
+                               DS2780_RSNSP_REG, sizeof(u8));
+       if (ret < 0)
+               return ret;
+@@ -134,7 +142,7 @@ static int ds2780_set_sense_register(str
+ static int ds2780_get_rsgain_register(struct ds2780_device_info *dev_info,
+       u16 *rsgain)
+ {
+-      return ds2780_read16(dev_info->w1_dev, rsgain, DS2780_RSGAIN_MSB_REG);
++      return ds2780_read16(dev_info, rsgain, DS2780_RSGAIN_MSB_REG);
+ }
+ /* Set RSGAIN value from 0 to 1.999 in steps of 0.001 */
+@@ -144,8 +152,8 @@ static int ds2780_set_rsgain_register(st
+       int ret;
+       u8 raw[] = {rsgain >> 8, rsgain & 0xFF};
+-      ret = ds2780_write(dev_info->w1_dev, raw,
+-                              DS2780_RSGAIN_MSB_REG, sizeof(u8) * 2);
++      ret = ds2780_write(dev_info, raw,
++                              DS2780_RSGAIN_MSB_REG, sizeof(raw));
+       if (ret < 0)
+               return ret;
+@@ -167,7 +175,7 @@ static int ds2780_get_voltage(struct ds2
+        * Bits 2 - 0 of the voltage value are in bits 7 - 5 of the
+        * voltage LSB register
+        */
+-      ret = ds2780_read16(dev_info->w1_dev, &voltage_raw,
++      ret = ds2780_read16(dev_info, &voltage_raw,
+                               DS2780_VOLT_MSB_REG);
+       if (ret < 0)
+               return ret;
+@@ -196,7 +204,7 @@ static int ds2780_get_temperature(struct
+        * Bits 2 - 0 of the temperature value are in bits 7 - 5 of the
+        * temperature LSB register
+        */
+-      ret = ds2780_read16(dev_info->w1_dev, &temperature_raw,
++      ret = ds2780_read16(dev_info, &temperature_raw,
+                               DS2780_TEMP_MSB_REG);
+       if (ret < 0)
+               return ret;
+@@ -222,13 +230,13 @@ static int ds2780_get_current(struct ds2
+        * The units of measurement for current are dependent on the value of
+        * the sense resistor.
+        */
+-      ret = ds2780_read8(dev_info->w1_dev, &sense_res_raw, DS2780_RSNSP_REG);
++      ret = ds2780_read8(dev_info, &sense_res_raw, DS2780_RSNSP_REG);
+       if (ret < 0)
+               return ret;
+       if (sense_res_raw == 0) {
+               dev_err(dev_info->dev, "sense resistor value is 0\n");
+-              return -ENXIO;
++              return -EINVAL;
+       }
+       sense_res = 1000 / sense_res_raw;
+@@ -248,7 +256,7 @@ static int ds2780_get_current(struct ds2
+        * Bits 7 - 0 of the current value are in bits 7 - 0 of the current
+        * LSB register
+        */
+-      ret = ds2780_read16(dev_info->w1_dev, &current_raw, reg_msb);
++      ret = ds2780_read16(dev_info, &current_raw, reg_msb);
+       if (ret < 0)
+               return ret;
+@@ -267,7 +275,7 @@ static int ds2780_get_accumulated_curren
+        * The units of measurement for accumulated current are dependent on
+        * the value of the sense resistor.
+        */
+-      ret = ds2780_read8(dev_info->w1_dev, &sense_res_raw, DS2780_RSNSP_REG);
++      ret = ds2780_read8(dev_info, &sense_res_raw, DS2780_RSNSP_REG);
+       if (ret < 0)
+               return ret;
+@@ -285,7 +293,7 @@ static int ds2780_get_accumulated_curren
+        * Bits 7 - 0 of the ACR value are in bits 7 - 0 of the ACR
+        * LSB register
+        */
+-      ret = ds2780_read16(dev_info->w1_dev, &current_raw, DS2780_ACR_MSB_REG);
++      ret = ds2780_read16(dev_info, &current_raw, DS2780_ACR_MSB_REG);
+       if (ret < 0)
+               return ret;
+@@ -299,7 +307,7 @@ static int ds2780_get_capacity(struct ds
+       int ret;
+       u8 raw;
+-      ret = ds2780_read8(dev_info->w1_dev, &raw, DS2780_RARC_REG);
++      ret = ds2780_read8(dev_info, &raw, DS2780_RARC_REG);
+       if (ret < 0)
+               return ret;
+@@ -345,7 +353,7 @@ static int ds2780_get_charge_now(struct
+        * Bits 7 - 0 of the RAAC value are in bits 7 - 0 of the RAAC
+        * LSB register
+        */
+-      ret = ds2780_read16(dev_info->w1_dev, &charge_raw, DS2780_RAAC_MSB_REG);
++      ret = ds2780_read16(dev_info, &charge_raw, DS2780_RAAC_MSB_REG);
+       if (ret < 0)
+               return ret;
+@@ -356,7 +364,7 @@ static int ds2780_get_charge_now(struct
+ static int ds2780_get_control_register(struct ds2780_device_info *dev_info,
+       u8 *control_reg)
+ {
+-      return ds2780_read8(dev_info->w1_dev, control_reg, DS2780_CONTROL_REG);
++      return ds2780_read8(dev_info, control_reg, DS2780_CONTROL_REG);
+ }
+ static int ds2780_set_control_register(struct ds2780_device_info *dev_info,
+@@ -364,7 +372,7 @@ static int ds2780_set_control_register(s
+ {
+       int ret;
+-      ret = ds2780_write(dev_info->w1_dev, &control_reg,
++      ret = ds2780_write(dev_info, &control_reg,
+                               DS2780_CONTROL_REG, sizeof(u8));
+       if (ret < 0)
+               return ret;
+@@ -503,7 +511,7 @@ static ssize_t ds2780_get_sense_resistor
+       struct power_supply *psy = to_power_supply(dev);
+       struct ds2780_device_info *dev_info = to_ds2780_device_info(psy);
+-      ret = ds2780_read8(dev_info->w1_dev, &sense_resistor, DS2780_RSNSP_REG);
++      ret = ds2780_read8(dev_info, &sense_resistor, DS2780_RSNSP_REG);
+       if (ret < 0)
+               return ret;
+@@ -584,7 +592,7 @@ static ssize_t ds2780_get_pio_pin(struct
+       struct power_supply *psy = to_power_supply(dev);
+       struct ds2780_device_info *dev_info = to_ds2780_device_info(psy);
+-      ret = ds2780_read8(dev_info->w1_dev, &sfr, DS2780_SFR_REG);
++      ret = ds2780_read8(dev_info, &sfr, DS2780_SFR_REG);
+       if (ret < 0)
+               return ret;
+@@ -611,7 +619,7 @@ static ssize_t ds2780_set_pio_pin(struct
+               return -EINVAL;
+       }
+-      ret = ds2780_write(dev_info->w1_dev, &new_setting,
++      ret = ds2780_write(dev_info, &new_setting,
+                               DS2780_SFR_REG, sizeof(u8));
+       if (ret < 0)
+               return ret;
+@@ -632,7 +640,7 @@ static ssize_t ds2780_read_param_eeprom_
+               DS2780_EEPROM_BLOCK1_END -
+               DS2780_EEPROM_BLOCK1_START + 1 - off);
+-      return ds2780_read_block(dev_info->w1_dev, buf,
++      return ds2780_read_block(dev_info, buf,
+                               DS2780_EEPROM_BLOCK1_START + off, count);
+ }
+@@ -650,7 +658,7 @@ static ssize_t ds2780_write_param_eeprom
+               DS2780_EEPROM_BLOCK1_END -
+               DS2780_EEPROM_BLOCK1_START + 1 - off);
+-      ret = ds2780_write(dev_info->w1_dev, buf,
++      ret = ds2780_write(dev_info, buf,
+                               DS2780_EEPROM_BLOCK1_START + off, count);
+       if (ret < 0)
+               return ret;
+@@ -685,9 +693,8 @@ static ssize_t ds2780_read_user_eeprom_b
+               DS2780_EEPROM_BLOCK0_END -
+               DS2780_EEPROM_BLOCK0_START + 1 - off);
+-      return ds2780_read_block(dev_info->w1_dev, buf,
++      return ds2780_read_block(dev_info, buf,
+                               DS2780_EEPROM_BLOCK0_START + off, count);
+-
+ }
+ static ssize_t ds2780_write_user_eeprom_bin(struct file *filp,
+@@ -704,7 +711,7 @@ static ssize_t ds2780_write_user_eeprom_
+               DS2780_EEPROM_BLOCK0_END -
+               DS2780_EEPROM_BLOCK0_START + 1 - off);
+-      ret = ds2780_write(dev_info->w1_dev, buf,
++      ret = ds2780_write(dev_info, buf,
+                               DS2780_EEPROM_BLOCK0_START + off, count);
+       if (ret < 0)
+               return ret;
diff --git a/queue-3.1/drivers-power-ds2780_battery.c-fix-deadlock-upon-insertion-and-removal.patch b/queue-3.1/drivers-power-ds2780_battery.c-fix-deadlock-upon-insertion-and-removal.patch
new file mode 100644 (file)
index 0000000..4992566
--- /dev/null
@@ -0,0 +1,67 @@
+From 0e053fcbbbc4d945247cb32cad2767b483cb65f8 Mon Sep 17 00:00:00 2001
+From: Clifton Barnes <cabarnes@indesign-llc.com>
+Date: Wed, 2 Nov 2011 13:39:55 -0700
+Subject: drivers/power/ds2780_battery.c: fix deadlock upon insertion and removal
+
+From: Clifton Barnes <cabarnes@indesign-llc.com>
+
+commit 0e053fcbbbc4d945247cb32cad2767b483cb65f8 upstream.
+
+Fixes the deadlock when inserting and removing the ds2780.
+
+Signed-off-by: Clifton Barnes <cabarnes@indesign-llc.com>
+Cc: Evgeniy Polyakov <zbr@ioremap.net>
+Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
+Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ drivers/power/ds2780_battery.c |    9 +++++++++
+ 1 file changed, 9 insertions(+)
+
+--- a/drivers/power/ds2780_battery.c
++++ b/drivers/power/ds2780_battery.c
+@@ -39,6 +39,7 @@ struct ds2780_device_info {
+       struct device *dev;
+       struct power_supply bat;
+       struct device *w1_dev;
++      struct task_struct *mutex_holder;
+ };
+ enum current_types {
+@@ -63,6 +64,9 @@ static inline struct power_supply *to_po
+ static inline int ds2780_battery_io(struct ds2780_device_info *dev_info,
+       char *buf, int addr, size_t count, int io)
+ {
++      if (dev_info->mutex_holder == current)
++              return w1_ds2780_io_nolock(dev_info->w1_dev, buf, addr, count, io);
++      else
+               return w1_ds2780_io(dev_info->w1_dev, buf, addr, count, io);
+ }
+@@ -775,6 +779,7 @@ static int __devinit ds2780_battery_prob
+       dev_info->bat.properties        = ds2780_battery_props;
+       dev_info->bat.num_properties    = ARRAY_SIZE(ds2780_battery_props);
+       dev_info->bat.get_property      = ds2780_battery_get_property;
++      dev_info->mutex_holder          = current;
+       ret = power_supply_register(&pdev->dev, &dev_info->bat);
+       if (ret) {
+@@ -804,6 +809,8 @@ static int __devinit ds2780_battery_prob
+               goto fail_remove_bin_file;
+       }
++      dev_info->mutex_holder = NULL;
++
+       return 0;
+ fail_remove_bin_file:
+@@ -823,6 +830,8 @@ static int __devexit ds2780_battery_remo
+ {
+       struct ds2780_device_info *dev_info = platform_get_drvdata(pdev);
++      dev_info->mutex_holder = current;
++
+       /* remove attributes */
+       sysfs_remove_group(&dev_info->bat.dev->kobj, &ds2780_attr_group);
diff --git a/queue-3.1/ext2-ext3-ext4-don-t-inherit-append_fl-or-immutable_fl-for-new-inodes.patch b/queue-3.1/ext2-ext3-ext4-don-t-inherit-append_fl-or-immutable_fl-for-new-inodes.patch
new file mode 100644 (file)
index 0000000..646709e
--- /dev/null
@@ -0,0 +1,62 @@
+From 1cd9f0976aa4606db8d6e3dc3edd0aca8019372a Mon Sep 17 00:00:00 2001
+From: Theodore Ts'o <tytso@mit.edu>
+Date: Wed, 31 Aug 2011 11:54:51 -0400
+Subject: ext2,ext3,ext4: don't inherit APPEND_FL or IMMUTABLE_FL for new inodes
+
+From: Theodore Ts'o <tytso@mit.edu>
+
+commit 1cd9f0976aa4606db8d6e3dc3edd0aca8019372a upstream.
+
+This doesn't make much sense, and it exposes a bug in the kernel where
+attempts to create a new file in an append-only directory using
+O_CREAT will fail (but still leave a zero-length file).  This was
+discovered when xfstests #79 was generalized so it could run on all
+file systems.
+
+Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ fs/ext4/ext4.h          |    3 +--
+ include/linux/ext2_fs.h |    4 ++--
+ include/linux/ext3_fs.h |    4 ++--
+ 3 files changed, 5 insertions(+), 6 deletions(-)
+
+--- a/fs/ext4/ext4.h
++++ b/fs/ext4/ext4.h
+@@ -358,8 +358,7 @@ struct flex_groups {
+ /* Flags that should be inherited by new inodes from their parent. */
+ #define EXT4_FL_INHERITED (EXT4_SECRM_FL | EXT4_UNRM_FL | EXT4_COMPR_FL |\
+-                         EXT4_SYNC_FL | EXT4_IMMUTABLE_FL | EXT4_APPEND_FL |\
+-                         EXT4_NODUMP_FL | EXT4_NOATIME_FL |\
++                         EXT4_SYNC_FL | EXT4_NODUMP_FL | EXT4_NOATIME_FL |\
+                          EXT4_NOCOMPR_FL | EXT4_JOURNAL_DATA_FL |\
+                          EXT4_NOTAIL_FL | EXT4_DIRSYNC_FL)
+--- a/include/linux/ext2_fs.h
++++ b/include/linux/ext2_fs.h
+@@ -197,8 +197,8 @@ struct ext2_group_desc
+ /* Flags that should be inherited by new inodes from their parent. */
+ #define EXT2_FL_INHERITED (EXT2_SECRM_FL | EXT2_UNRM_FL | EXT2_COMPR_FL |\
+-                         EXT2_SYNC_FL | EXT2_IMMUTABLE_FL | EXT2_APPEND_FL |\
+-                         EXT2_NODUMP_FL | EXT2_NOATIME_FL | EXT2_COMPRBLK_FL|\
++                         EXT2_SYNC_FL | EXT2_NODUMP_FL |\
++                         EXT2_NOATIME_FL | EXT2_COMPRBLK_FL |\
+                          EXT2_NOCOMP_FL | EXT2_JOURNAL_DATA_FL |\
+                          EXT2_NOTAIL_FL | EXT2_DIRSYNC_FL)
+--- a/include/linux/ext3_fs.h
++++ b/include/linux/ext3_fs.h
+@@ -180,8 +180,8 @@ struct ext3_group_desc
+ /* Flags that should be inherited by new inodes from their parent. */
+ #define EXT3_FL_INHERITED (EXT3_SECRM_FL | EXT3_UNRM_FL | EXT3_COMPR_FL |\
+-                         EXT3_SYNC_FL | EXT3_IMMUTABLE_FL | EXT3_APPEND_FL |\
+-                         EXT3_NODUMP_FL | EXT3_NOATIME_FL | EXT3_COMPRBLK_FL|\
++                         EXT3_SYNC_FL | EXT3_NODUMP_FL |\
++                         EXT3_NOATIME_FL | EXT3_COMPRBLK_FL |\
+                          EXT3_NOCOMPR_FL | EXT3_JOURNAL_DATA_FL |\
+                          EXT3_NOTAIL_FL | EXT3_DIRSYNC_FL)
diff --git a/queue-3.1/ext4-call-ext4_handle_dirty_metadata-with-correct-inode-in-ext4_dx_add_entry.patch b/queue-3.1/ext4-call-ext4_handle_dirty_metadata-with-correct-inode-in-ext4_dx_add_entry.patch
new file mode 100644 (file)
index 0000000..1d12a29
--- /dev/null
@@ -0,0 +1,44 @@
+From 5930ea643805feb50a2f8383ae12eb6f10935e49 Mon Sep 17 00:00:00 2001
+From: Theodore Ts'o <tytso@mit.edu>
+Date: Wed, 31 Aug 2011 12:02:51 -0400
+Subject: ext4: call ext4_handle_dirty_metadata with correct inode in ext4_dx_add_entry
+
+From: Theodore Ts'o <tytso@mit.edu>
+
+commit 5930ea643805feb50a2f8383ae12eb6f10935e49 upstream.
+
+ext4_dx_add_entry manipulates bh2 and frames[0].bh, which are two buffer_heads
+that point to directory blocks assigned to the directory inode.  However, the
+function calls ext4_handle_dirty_metadata with the inode of the file that's
+being added to the directory, not the directory inode itself.  Therefore,
+correct the code to dirty the directory buffers with the directory inode, not
+the file inode.
+
+Signed-off-by: Darrick J. Wong <djwong@us.ibm.com>
+Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ fs/ext4/namei.c |    4 ++--
+ 1 file changed, 2 insertions(+), 2 deletions(-)
+
+--- a/fs/ext4/namei.c
++++ b/fs/ext4/namei.c
+@@ -1586,7 +1586,7 @@ static int ext4_dx_add_entry(handle_t *h
+                       dxtrace(dx_show_index("node", frames[1].entries));
+                       dxtrace(dx_show_index("node",
+                              ((struct dx_node *) bh2->b_data)->entries));
+-                      err = ext4_handle_dirty_metadata(handle, inode, bh2);
++                      err = ext4_handle_dirty_metadata(handle, dir, bh2);
+                       if (err)
+                               goto journal_error;
+                       brelse (bh2);
+@@ -1612,7 +1612,7 @@ static int ext4_dx_add_entry(handle_t *h
+                       if (err)
+                               goto journal_error;
+               }
+-              err = ext4_handle_dirty_metadata(handle, inode, frames[0].bh);
++              err = ext4_handle_dirty_metadata(handle, dir, frames[0].bh);
+               if (err) {
+                       ext4_std_error(inode->i_sb, err);
+                       goto cleanup;
diff --git a/queue-3.1/ext4-ext4_mkdir-should-dirty-dir_block-with-newly-created-directory-inode.patch b/queue-3.1/ext4-ext4_mkdir-should-dirty-dir_block-with-newly-created-directory-inode.patch
new file mode 100644 (file)
index 0000000..441087d
--- /dev/null
@@ -0,0 +1,33 @@
+From f9287c1f2d329f4d78a3bbc9cf0db0ebae6f146a Mon Sep 17 00:00:00 2001
+From: "Darrick J. Wong" <djwong@us.ibm.com>
+Date: Wed, 31 Aug 2011 12:00:51 -0400
+Subject: ext4: ext4_mkdir should dirty dir_block with newly created directory inode
+
+From: "Darrick J. Wong" <djwong@us.ibm.com>
+
+commit f9287c1f2d329f4d78a3bbc9cf0db0ebae6f146a upstream.
+
+ext4_mkdir calls ext4_handle_dirty_metadata with dir_block and the inode "dir".
+Unfortunately, dir_block belongs to the newly created directory (which is
+"inode"), not the parent directory (which is "dir").  Fix the incorrect
+association.
+
+Signed-off-by: Darrick J. Wong <djwong@us.ibm.com>
+Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ fs/ext4/namei.c |    2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+--- a/fs/ext4/namei.c
++++ b/fs/ext4/namei.c
+@@ -1863,7 +1863,7 @@ retry:
+       ext4_set_de_type(dir->i_sb, de, S_IFDIR);
+       inode->i_nlink = 2;
+       BUFFER_TRACE(dir_block, "call ext4_handle_dirty_metadata");
+-      err = ext4_handle_dirty_metadata(handle, dir, dir_block);
++      err = ext4_handle_dirty_metadata(handle, inode, dir_block);
+       if (err)
+               goto out_clear_inode;
+       err = ext4_mark_inode_dirty(handle, inode);
diff --git a/queue-3.1/ext4-ext4_rename-should-dirty-dir_bh-with-the-correct-directory.patch b/queue-3.1/ext4-ext4_rename-should-dirty-dir_bh-with-the-correct-directory.patch
new file mode 100644 (file)
index 0000000..7307ff9
--- /dev/null
@@ -0,0 +1,35 @@
+From bcaa992975041e40449be8c010c26192b8c8b409 Mon Sep 17 00:00:00 2001
+From: "Darrick J. Wong" <djwong@us.ibm.com>
+Date: Wed, 31 Aug 2011 11:58:51 -0400
+Subject: ext4: ext4_rename should dirty dir_bh with the correct directory
+
+From: "Darrick J. Wong" <djwong@us.ibm.com>
+
+commit bcaa992975041e40449be8c010c26192b8c8b409 upstream.
+
+When ext4_rename performs a directory rename (move), dir_bh is a
+buffer that is modified to update the '..' link in the directory being
+moved (old_inode).  However, ext4_handle_dirty_metadata is called with
+the old parent directory inode (old_dir) and dir_bh, which is
+incorrect because dir_bh does not belong to the parent inode.  Fix
+this error.
+
+Signed-off-by: Darrick J. Wong <djwong@us.ibm.com>
+Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ fs/ext4/namei.c |    2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+--- a/fs/ext4/namei.c
++++ b/fs/ext4/namei.c
+@@ -2530,7 +2530,7 @@ static int ext4_rename(struct inode *old
+               PARENT_INO(dir_bh->b_data, new_dir->i_sb->s_blocksize) =
+                                               cpu_to_le32(new_dir->i_ino);
+               BUFFER_TRACE(dir_bh, "call ext4_handle_dirty_metadata");
+-              retval = ext4_handle_dirty_metadata(handle, old_dir, dir_bh);
++              retval = ext4_handle_dirty_metadata(handle, old_inode, dir_bh);
+               if (retval) {
+                       ext4_std_error(old_dir->i_sb, retval);
+                       goto end_rename;
diff --git a/queue-3.1/ext4-fix-race-in-xattr-block-allocation-path.patch b/queue-3.1/ext4-fix-race-in-xattr-block-allocation-path.patch
new file mode 100644 (file)
index 0000000..67ee218
--- /dev/null
@@ -0,0 +1,78 @@
+From 6d6a435190bdf2e04c9465cde5bdc3ac68cf11a4 Mon Sep 17 00:00:00 2001
+From: Eric Sandeen <sandeen@redhat.com>
+Date: Sat, 29 Oct 2011 10:15:35 -0400
+Subject: ext4: fix race in xattr block allocation path
+
+From: Eric Sandeen <sandeen@redhat.com>
+
+commit 6d6a435190bdf2e04c9465cde5bdc3ac68cf11a4 upstream.
+
+Ceph users reported that when using Ceph on ext4, the filesystem
+would often become corrupted, containing inodes with incorrect
+i_blocks counters.
+
+I managed to reproduce this with a very hacked-up "streamtest"
+binary from the Ceph tree.
+
+Ceph is doing a lot of xattr writes, to out-of-inode blocks.
+There is also another thread which does sync_file_range and close,
+of the same files.  The problem appears to happen due to this race:
+
+sync/flush thread               xattr-set thread
+-----------------               ----------------
+
+do_writepages                   ext4_xattr_set
+ext4_da_writepages              ext4_xattr_set_handle
+mpage_da_map_blocks             ext4_xattr_block_set
+        set DELALLOC_RESERVE
+                                ext4_new_meta_blocks
+                                        ext4_mb_new_blocks
+                                                if (!i_delalloc_reserved_flag)
+                                                        vfs_dq_alloc_block
+ext4_get_blocks
+       down_write(i_data_sem)
+        set i_delalloc_reserved_flag
+       ...
+       up_write(i_data_sem)
+                                        if (i_delalloc_reserved_flag)
+                                                vfs_dq_alloc_block_nofail
+
+
+In other words, the sync/flush thread pops in and sets
+i_delalloc_reserved_flag on the inode, which makes the xattr thread
+think that it's in a delalloc path in ext4_new_meta_blocks(),
+and add the block for a second time, after already having added
+it once in the !i_delalloc_reserved_flag case in ext4_mb_new_blocks
+
+The real problem is that we shouldn't be using the DELALLOC_RESERVED
+state flag, and instead we should be passing
+EXT4_GET_BLOCKS_DELALLOC_RESERVE down to ext4_map_blocks() instead of
+using an inode state flag.  We'll fix this for now with using
+i_data_sem to prevent this race, but this is really not the right way
+to fix things.
+
+Signed-off-by: Eric Sandeen <sandeen@redhat.com>
+Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ fs/ext4/xattr.c |    6 ++++++
+ 1 file changed, 6 insertions(+)
+
+--- a/fs/ext4/xattr.c
++++ b/fs/ext4/xattr.c
+@@ -820,8 +820,14 @@ inserted:
+                       if (!(ext4_test_inode_flag(inode, EXT4_INODE_EXTENTS)))
+                               goal = goal & EXT4_MAX_BLOCK_FILE_PHYS;
++                      /*
++                       * take i_data_sem because we will test
++                       * i_delalloc_reserved_flag in ext4_mb_new_blocks
++                       */
++                      down_read((&EXT4_I(inode)->i_data_sem));
+                       block = ext4_new_meta_blocks(handle, inode, goal, 0,
+                                                    NULL, &error);
++                      up_read((&EXT4_I(inode)->i_data_sem));
+                       if (error)
+                               goto cleanup;
diff --git a/queue-3.1/ext4-let-ext4_page_mkwrite-stop-started-handle-in-failure.patch b/queue-3.1/ext4-let-ext4_page_mkwrite-stop-started-handle-in-failure.patch
new file mode 100644 (file)
index 0000000..37d7bd4
--- /dev/null
@@ -0,0 +1,30 @@
+From fcbb5515825f1bb20b7a6f75ec48bee61416f879 Mon Sep 17 00:00:00 2001
+From: Yongqiang Yang <xiaoqiangnk@gmail.com>
+Date: Wed, 26 Oct 2011 05:00:19 -0400
+Subject: ext4: let ext4_page_mkwrite stop started handle in failure
+
+From: Yongqiang Yang <xiaoqiangnk@gmail.com>
+
+commit fcbb5515825f1bb20b7a6f75ec48bee61416f879 upstream.
+
+The started journal handle should be stopped in failure case.
+
+Signed-off-by: Yongqiang Yang <xiaoqiangnk@gmail.com>
+Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>
+Acked-by: Jan Kara <jack@suse.cz>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ fs/ext4/inode.c |    1 +
+ 1 file changed, 1 insertion(+)
+
+--- a/fs/ext4/inode.c
++++ b/fs/ext4/inode.c
+@@ -4416,6 +4416,7 @@ retry_alloc:
+                         PAGE_CACHE_SIZE, NULL, do_journal_get_write_access)) {
+                       unlock_page(page);
+                       ret = VM_FAULT_SIGBUS;
++                      ext4_journal_stop(handle);
+                       goto out;
+               }
+               ext4_set_inode_state(inode, EXT4_STATE_JDATA);
diff --git a/queue-3.1/hwspinlock-core-use-a-mutex-to-protect-the-radix-tree.patch b/queue-3.1/hwspinlock-core-use-a-mutex-to-protect-the-radix-tree.patch
new file mode 100644 (file)
index 0000000..99bb8f9
--- /dev/null
@@ -0,0 +1,249 @@
+From 93b465c2e186d96fb90012ba0f9372eb9952e732 Mon Sep 17 00:00:00 2001
+From: Juan Gutierrez <jgutierrez@ti.com>
+Date: Tue, 6 Sep 2011 09:30:16 +0300
+Subject: hwspinlock/core: use a mutex to protect the radix tree
+
+From: Juan Gutierrez <jgutierrez@ti.com>
+
+commit 93b465c2e186d96fb90012ba0f9372eb9952e732 upstream.
+
+Since we're using non-atomic radix tree allocations, we
+should be protecting the tree using a mutex and not a
+spinlock.
+
+Non-atomic allocations and process context locking is good enough,
+as the tree is manipulated only when locks are registered/
+unregistered/requested/freed.
+
+The locks themselves are still protected by spinlocks of course,
+and mutexes are not involved in the locking/unlocking paths.
+
+Signed-off-by: Juan Gutierrez <jgutierrez@ti.com>
+[ohad@wizery.com: rewrite the commit log, #include mutex.h, add minor
+commentary]
+[ohad@wizery.com: update register/unregister parts in hwspinlock.txt]
+Signed-off-by: Ohad Ben-Cohen <ohad@wizery.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ Documentation/hwspinlock.txt         |   18 +++++---------
+ drivers/hwspinlock/hwspinlock_core.c |   45 +++++++++++++++--------------------
+ 2 files changed, 27 insertions(+), 36 deletions(-)
+
+--- a/Documentation/hwspinlock.txt
++++ b/Documentation/hwspinlock.txt
+@@ -39,23 +39,20 @@ independent, drivers.
+      in case an unused hwspinlock isn't available. Users of this
+      API will usually want to communicate the lock's id to the remote core
+      before it can be used to achieve synchronization.
+-     Can be called from an atomic context (this function will not sleep) but
+-     not from within interrupt context.
++     Should be called from a process context (might sleep).
+   struct hwspinlock *hwspin_lock_request_specific(unsigned int id);
+    - assign a specific hwspinlock id and return its address, or NULL
+      if that hwspinlock is already in use. Usually board code will
+      be calling this function in order to reserve specific hwspinlock
+      ids for predefined purposes.
+-     Can be called from an atomic context (this function will not sleep) but
+-     not from within interrupt context.
++     Should be called from a process context (might sleep).
+   int hwspin_lock_free(struct hwspinlock *hwlock);
+    - free a previously-assigned hwspinlock; returns 0 on success, or an
+      appropriate error code on failure (e.g. -EINVAL if the hwspinlock
+      is already free).
+-     Can be called from an atomic context (this function will not sleep) but
+-     not from within interrupt context.
++     Should be called from a process context (might sleep).
+   int hwspin_lock_timeout(struct hwspinlock *hwlock, unsigned int timeout);
+    - lock a previously-assigned hwspinlock with a timeout limit (specified in
+@@ -232,15 +229,14 @@ int hwspinlock_example2(void)
+   int hwspin_lock_register(struct hwspinlock *hwlock);
+    - to be called from the underlying platform-specific implementation, in
+-     order to register a new hwspinlock instance. Can be called from an atomic
+-     context (this function will not sleep) but not from within interrupt
+-     context. Returns 0 on success, or appropriate error code on failure.
++     order to register a new hwspinlock instance. Should be called from
++     a process context (this function might sleep).
++     Returns 0 on success, or appropriate error code on failure.
+   struct hwspinlock *hwspin_lock_unregister(unsigned int id);
+    - to be called from the underlying vendor-specific implementation, in order
+      to unregister an existing (and unused) hwspinlock instance.
+-     Can be called from an atomic context (will not sleep) but not from
+-     within interrupt context.
++     Should be called from a process context (this function might sleep).
+      Returns the address of hwspinlock on success, or NULL on error (e.g.
+      if the hwspinlock is sill in use).
+--- a/drivers/hwspinlock/hwspinlock_core.c
++++ b/drivers/hwspinlock/hwspinlock_core.c
+@@ -26,6 +26,7 @@
+ #include <linux/radix-tree.h>
+ #include <linux/hwspinlock.h>
+ #include <linux/pm_runtime.h>
++#include <linux/mutex.h>
+ #include "hwspinlock_internal.h"
+@@ -52,10 +53,12 @@
+ static RADIX_TREE(hwspinlock_tree, GFP_KERNEL);
+ /*
+- * Synchronization of access to the tree is achieved using this spinlock,
++ * Synchronization of access to the tree is achieved using this mutex,
+  * as the radix-tree API requires that users provide all synchronisation.
++ * A mutex is needed because we're using non-atomic radix tree allocations.
+  */
+-static DEFINE_SPINLOCK(hwspinlock_tree_lock);
++static DEFINE_MUTEX(hwspinlock_tree_lock);
++
+ /**
+  * __hwspin_trylock() - attempt to lock a specific hwspinlock
+@@ -261,8 +264,7 @@ EXPORT_SYMBOL_GPL(__hwspin_unlock);
+  * This function should be called from the underlying platform-specific
+  * implementation, to register a new hwspinlock instance.
+  *
+- * Can be called from an atomic context (will not sleep) but not from
+- * within interrupt context.
++ * Should be called from a process context (might sleep)
+  *
+  * Returns 0 on success, or an appropriate error code on failure
+  */
+@@ -279,7 +281,7 @@ int hwspin_lock_register(struct hwspinlo
+       spin_lock_init(&hwlock->lock);
+-      spin_lock(&hwspinlock_tree_lock);
++      mutex_lock(&hwspinlock_tree_lock);
+       ret = radix_tree_insert(&hwspinlock_tree, hwlock->id, hwlock);
+       if (ret)
+@@ -293,7 +295,7 @@ int hwspin_lock_register(struct hwspinlo
+       WARN_ON(tmp != hwlock);
+ out:
+-      spin_unlock(&hwspinlock_tree_lock);
++      mutex_unlock(&hwspinlock_tree_lock);
+       return ret;
+ }
+ EXPORT_SYMBOL_GPL(hwspin_lock_register);
+@@ -305,8 +307,7 @@ EXPORT_SYMBOL_GPL(hwspin_lock_register);
+  * This function should be called from the underlying platform-specific
+  * implementation, to unregister an existing (and unused) hwspinlock.
+  *
+- * Can be called from an atomic context (will not sleep) but not from
+- * within interrupt context.
++ * Should be called from a process context (might sleep)
+  *
+  * Returns the address of hwspinlock @id on success, or NULL on failure
+  */
+@@ -315,7 +316,7 @@ struct hwspinlock *hwspin_lock_unregiste
+       struct hwspinlock *hwlock = NULL;
+       int ret;
+-      spin_lock(&hwspinlock_tree_lock);
++      mutex_lock(&hwspinlock_tree_lock);
+       /* make sure the hwspinlock is not in use (tag is set) */
+       ret = radix_tree_tag_get(&hwspinlock_tree, id, HWSPINLOCK_UNUSED);
+@@ -331,7 +332,7 @@ struct hwspinlock *hwspin_lock_unregiste
+       }
+ out:
+-      spin_unlock(&hwspinlock_tree_lock);
++      mutex_unlock(&hwspinlock_tree_lock);
+       return hwlock;
+ }
+ EXPORT_SYMBOL_GPL(hwspin_lock_unregister);
+@@ -400,9 +401,7 @@ EXPORT_SYMBOL_GPL(hwspin_lock_get_id);
+  * to the remote core before it can be used for synchronization (to get the
+  * id of a given hwlock, use hwspin_lock_get_id()).
+  *
+- * Can be called from an atomic context (will not sleep) but not from
+- * within interrupt context (simply because there is no use case for
+- * that yet).
++ * Should be called from a process context (might sleep)
+  *
+  * Returns the address of the assigned hwspinlock, or NULL on error
+  */
+@@ -411,7 +410,7 @@ struct hwspinlock *hwspin_lock_request(v
+       struct hwspinlock *hwlock;
+       int ret;
+-      spin_lock(&hwspinlock_tree_lock);
++      mutex_lock(&hwspinlock_tree_lock);
+       /* look for an unused lock */
+       ret = radix_tree_gang_lookup_tag(&hwspinlock_tree, (void **)&hwlock,
+@@ -431,7 +430,7 @@ struct hwspinlock *hwspin_lock_request(v
+               hwlock = NULL;
+ out:
+-      spin_unlock(&hwspinlock_tree_lock);
++      mutex_unlock(&hwspinlock_tree_lock);
+       return hwlock;
+ }
+ EXPORT_SYMBOL_GPL(hwspin_lock_request);
+@@ -445,9 +444,7 @@ EXPORT_SYMBOL_GPL(hwspin_lock_request);
+  * Usually early board code will be calling this function in order to
+  * reserve specific hwspinlock ids for predefined purposes.
+  *
+- * Can be called from an atomic context (will not sleep) but not from
+- * within interrupt context (simply because there is no use case for
+- * that yet).
++ * Should be called from a process context (might sleep)
+  *
+  * Returns the address of the assigned hwspinlock, or NULL on error
+  */
+@@ -456,7 +453,7 @@ struct hwspinlock *hwspin_lock_request_s
+       struct hwspinlock *hwlock;
+       int ret;
+-      spin_lock(&hwspinlock_tree_lock);
++      mutex_lock(&hwspinlock_tree_lock);
+       /* make sure this hwspinlock exists */
+       hwlock = radix_tree_lookup(&hwspinlock_tree, id);
+@@ -482,7 +479,7 @@ struct hwspinlock *hwspin_lock_request_s
+               hwlock = NULL;
+ out:
+-      spin_unlock(&hwspinlock_tree_lock);
++      mutex_unlock(&hwspinlock_tree_lock);
+       return hwlock;
+ }
+ EXPORT_SYMBOL_GPL(hwspin_lock_request_specific);
+@@ -495,9 +492,7 @@ EXPORT_SYMBOL_GPL(hwspin_lock_request_sp
+  * Should only be called with an @hwlock that was retrieved from
+  * an earlier call to omap_hwspin_lock_request{_specific}.
+  *
+- * Can be called from an atomic context (will not sleep) but not from
+- * within interrupt context (simply because there is no use case for
+- * that yet).
++ * Should be called from a process context (might sleep)
+  *
+  * Returns 0 on success, or an appropriate error code on failure
+  */
+@@ -511,7 +506,7 @@ int hwspin_lock_free(struct hwspinlock *
+               return -EINVAL;
+       }
+-      spin_lock(&hwspinlock_tree_lock);
++      mutex_lock(&hwspinlock_tree_lock);
+       /* make sure the hwspinlock is used */
+       ret = radix_tree_tag_get(&hwspinlock_tree, hwlock->id,
+@@ -538,7 +533,7 @@ int hwspin_lock_free(struct hwspinlock *
+       module_put(hwlock->owner);
+ out:
+-      spin_unlock(&hwspinlock_tree_lock);
++      mutex_unlock(&hwspinlock_tree_lock);
+       return ret;
+ }
+ EXPORT_SYMBOL_GPL(hwspin_lock_free);
index 66a781bd5f2a01775b54a4b08ae41e956048764e..8f243a0ff57465ac230e9c810a94456606beca1a 100644 (file)
@@ -163,3 +163,13 @@ binfmt_elf-fix-pie-execution-with-randomization-disabled.patch
 proc-fix-races-against-execve-of-proc-pid-fd.patch
 alsa-hda-add-missing-static-adc-tables-for-alc269-quirks.patch
 drivers-net-rionet.c-fix-ethernet-address-macros-for-le-platforms.patch
+hwspinlock-core-use-a-mutex-to-protect-the-radix-tree.patch
+drivers-power-ds2780_battery.c-create-central-point-for-calling-w1-interface.patch
+drivers-power-ds2780_battery.c-add-a-nolock-function-to-w1-interface.patch
+drivers-power-ds2780_battery.c-fix-deadlock-upon-insertion-and-removal.patch
+ext2-ext3-ext4-don-t-inherit-append_fl-or-immutable_fl-for-new-inodes.patch
+ext4-ext4_rename-should-dirty-dir_bh-with-the-correct-directory.patch
+ext4-ext4_mkdir-should-dirty-dir_block-with-newly-created-directory-inode.patch
+ext4-call-ext4_handle_dirty_metadata-with-correct-inode-in-ext4_dx_add_entry.patch
+ext4-let-ext4_page_mkwrite-stop-started-handle-in-failure.patch
+ext4-fix-race-in-xattr-block-allocation-path.patch