Patchwork Change struct flchip_shared spinlock locking into mutex

login
register
mail settings
Submitter Stefani Seibold
Date Aug. 2, 2010, 7:40 p.m.
Message ID <1280778048-6208-1-git-send-email-stefani@seibold.net>
Download mbox | patch
Permalink /patch/60565/
State New
Headers show

Comments

Stefani Seibold - Aug. 2, 2010, 7:40 p.m.
From: Stefani Seibold <stefani@seibold.net>

This patch prevent to schedule while atomic by changing the
flchip_shared spinlock into a mutex. This should be save since no atomic
path will use this lock.

This patch is based on linux kernel 2.6.35. Please apply.

It was requested by Arnd Bergmann and Vasiliy Kulikov.

- Stefani

shared->

Signed-off-by: Stefani Seibold <stefani@seibold.net>
---
 drivers/mtd/chips/cfi_cmdset_0001.c |   20 ++++++++++----------
 include/linux/mtd/flashchip.h       |    2 +-
 2 files changed, 11 insertions(+), 11 deletions(-)
Arnd Bergmann - Aug. 3, 2010, 8:25 a.m.
On Monday 02 August 2010, stefani@seibold.net wrote:
> From: Stefani Seibold <stefani@seibold.net>
> 
> This patch prevent to schedule while atomic by changing the
> flchip_shared spinlock into a mutex. This should be save since no atomic
> path will use this lock.

I don't know this code well, but the patch looks correct and seems
to be needed.

Acked-by: Arnd Bergmann <arnd@arndb.de>
Artem Bityutskiy - Aug. 5, 2010, 4:58 a.m.
On Mon, 2010-08-02 at 21:40 +0200, stefani@seibold.net wrote:
> From: Stefani Seibold <stefani@seibold.net>
> 
> This patch prevent to schedule while atomic by changing the
> flchip_shared spinlock into a mutex. This should be save since no atomic
> path will use this lock.
> 
> This patch is based on linux kernel 2.6.35. Please apply.
> 
> It was requested by Arnd Bergmann and Vasiliy Kulikov.

Taken to my l2-mtd-2.6.git / master
Artem Bityutskiy - Aug. 5, 2010, 5:30 a.m.
On Thu, 2010-08-05 at 07:58 +0300, Artem Bityutskiy wrote:
> On Mon, 2010-08-02 at 21:40 +0200, stefani@seibold.net wrote:
> > From: Stefani Seibold <stefani@seibold.net>
> > 
> > This patch prevent to schedule while atomic by changing the
> > flchip_shared spinlock into a mutex. This should be save since no atomic
> > path will use this lock.
> > 
> > This patch is based on linux kernel 2.6.35. Please apply.
> > 
> > It was requested by Arnd Bergmann and Vasiliy Kulikov.
> 
> Taken to my l2-mtd-2.6.git / master

This patch causes the following compilation error:

drivers/mtd/lpddr/lpddr_cmds.c: In function ‘lpddr_cmdset’:
drivers/mtd/lpddr/lpddr_cmds.c:101: warning: passing argument 1 of ‘spinlock_check’ from incompatible pointer type
include/linux/spinlock.h:271: note: expected ‘struct spinlock_t *’ but argument is of type ‘struct mutex *’
drivers/mtd/lpddr/lpddr_cmds.c:101: error: ‘struct mutex’ has no member named ‘rlock’
drivers/mtd/lpddr/lpddr_cmds.c: In function ‘get_chip’:
drivers/mtd/lpddr/lpddr_cmds.c:220: warning: passing argument 1 of ‘spin_lock’ from incompatible pointer type
include/linux/spinlock.h:282: note: expected ‘struct spinlock_t *’ but argument is of type ‘struct mutex *’
drivers/mtd/lpddr/lpddr_cmds.c:233: warning: passing argument 1 of ‘spin_unlock’ from incompatible pointer type
include/linux/spinlock.h:322: note: expected ‘struct spinlock_t *’ but argument is of type ‘struct mutex *’
drivers/mtd/lpddr/lpddr_cmds.c:248: warning: passing argument 1 of ‘spin_lock’ from incompatible pointer type
include/linux/spinlock.h:282: note: expected ‘struct spinlock_t *’ but argument is of type ‘struct mutex *’
drivers/mtd/lpddr/lpddr_cmds.c:264: warning: passing argument 1 of ‘spin_unlock’ from incompatible pointer type
include/linux/spinlock.h:322: note: expected ‘struct spinlock_t *’ but argument is of type ‘struct mutex *’
drivers/mtd/lpddr/lpddr_cmds.c:278: warning: passing argument 1 of ‘spin_unlock’ from incompatible pointer type
include/linux/spinlock.h:322: note: expected ‘struct spinlock_t *’ but argument is of type ‘struct mutex *’
drivers/mtd/lpddr/lpddr_cmds.c: In function ‘put_chip’:
drivers/mtd/lpddr/lpddr_cmds.c:351: warning: passing argument 1 of ‘spin_lock’ from incompatible pointer type
include/linux/spinlock.h:282: note: expected ‘struct spinlock_t *’ but argument is of type ‘struct mutex *’
drivers/mtd/lpddr/lpddr_cmds.c:359: warning: passing argument 1 of ‘spin_unlock’ from incompatible pointer type
include/linux/spinlock.h:322: note: expected ‘struct spinlock_t *’ but argument is of type ‘struct mutex *’
drivers/mtd/lpddr/lpddr_cmds.c:377: warning: passing argument 1 of ‘spin_unlock’ from incompatible pointer type
include/linux/spinlock.h:322: note: expected ‘struct spinlock_t *’ but argument is of type ‘struct mutex *’
drivers/mtd/lpddr/lpddr_cmds.c:381: warning: passing argument 1 of ‘spin_unlock’ from incompatible pointer type
include/linux/spinlock.h:322: note: expected ‘struct spinlock_t *’ but argument is of type ‘struct mutex *’

Removed from my tree.

Patch

diff --git a/drivers/mtd/chips/cfi_cmdset_0001.c b/drivers/mtd/chips/cfi_cmdset_0001.c
index 62f3ea9..3364061 100644
--- a/drivers/mtd/chips/cfi_cmdset_0001.c
+++ b/drivers/mtd/chips/cfi_cmdset_0001.c
@@ -717,7 +717,7 @@  static int cfi_intelext_partition_fixup(struct mtd_info *mtd,
 		chip = &newcfi->chips[0];
 		for (i = 0; i < cfi->numchips; i++) {
 			shared[i].writing = shared[i].erasing = NULL;
-			spin_lock_init(&shared[i].lock);
+			mutex_init(&shared[i].lock);
 			for (j = 0; j < numparts; j++) {
 				*chip = cfi->chips[i];
 				chip->start += j << partshift;
@@ -886,7 +886,7 @@  static int get_chip(struct map_info *map, struct flchip *chip, unsigned long adr
 		 */
 		struct flchip_shared *shared = chip->priv;
 		struct flchip *contender;
-		spin_lock(&shared->lock);
+		mutex_lock(&shared->lock);
 		contender = shared->writing;
 		if (contender && contender != chip) {
 			/*
@@ -899,7 +899,7 @@  static int get_chip(struct map_info *map, struct flchip *chip, unsigned long adr
 			 * get_chip returns success we're clear to go ahead.
 			 */
 			ret = mutex_trylock(&contender->mutex);
-			spin_unlock(&shared->lock);
+			mutex_unlock(&shared->lock);
 			if (!ret)
 				goto retry;
 			mutex_unlock(&chip->mutex);
@@ -914,7 +914,7 @@  static int get_chip(struct map_info *map, struct flchip *chip, unsigned long adr
 				mutex_unlock(&contender->mutex);
 				return ret;
 			}
-			spin_lock(&shared->lock);
+			mutex_lock(&shared->lock);
 
 			/* We should not own chip if it is already
 			 * in FL_SYNCING state. Put contender and retry. */
@@ -930,7 +930,7 @@  static int get_chip(struct map_info *map, struct flchip *chip, unsigned long adr
 		 * on this chip. Sleep. */
 		if (mode == FL_ERASING && shared->erasing
 		    && shared->erasing->oldstate == FL_ERASING) {
-			spin_unlock(&shared->lock);
+			mutex_unlock(&shared->lock);
 			set_current_state(TASK_UNINTERRUPTIBLE);
 			add_wait_queue(&chip->wq, &wait);
 			mutex_unlock(&chip->mutex);
@@ -944,7 +944,7 @@  static int get_chip(struct map_info *map, struct flchip *chip, unsigned long adr
 		shared->writing = chip;
 		if (mode == FL_ERASING)
 			shared->erasing = chip;
-		spin_unlock(&shared->lock);
+		mutex_unlock(&shared->lock);
 	}
 	ret = chip_ready(map, chip, adr, mode);
 	if (ret == -EAGAIN)
@@ -959,7 +959,7 @@  static void put_chip(struct map_info *map, struct flchip *chip, unsigned long ad
 
 	if (chip->priv) {
 		struct flchip_shared *shared = chip->priv;
-		spin_lock(&shared->lock);
+		mutex_lock(&shared->lock);
 		if (shared->writing == chip && chip->oldstate == FL_READY) {
 			/* We own the ability to write, but we're done */
 			shared->writing = shared->erasing;
@@ -967,7 +967,7 @@  static void put_chip(struct map_info *map, struct flchip *chip, unsigned long ad
 				/* give back ownership to who we loaned it from */
 				struct flchip *loaner = shared->writing;
 				mutex_lock(&loaner->mutex);
-				spin_unlock(&shared->lock);
+				mutex_unlock(&shared->lock);
 				mutex_unlock(&chip->mutex);
 				put_chip(map, loaner, loaner->start);
 				mutex_lock(&chip->mutex);
@@ -985,11 +985,11 @@  static void put_chip(struct map_info *map, struct flchip *chip, unsigned long ad
 			 * Don't let the switch below mess things up since
 			 * we don't have ownership to resume anything.
 			 */
-			spin_unlock(&shared->lock);
+			mutex_unlock(&shared->lock);
 			wake_up(&chip->wq);
 			return;
 		}
-		spin_unlock(&shared->lock);
+		mutex_unlock(&shared->lock);
 	}
 
 	switch(chip->oldstate) {
diff --git a/include/linux/mtd/flashchip.h b/include/linux/mtd/flashchip.h
index f43e9b4..23cc10f 100644
--- a/include/linux/mtd/flashchip.h
+++ b/include/linux/mtd/flashchip.h
@@ -92,7 +92,7 @@  struct flchip {
 /* This is used to handle contention on write/erase operations
    between partitions of the same physical chip. */
 struct flchip_shared {
-	spinlock_t lock;
+	struct mutex lock;
 	struct flchip *writing;
 	struct flchip *erasing;
 };