diff options
author | Linus Torvalds <torvalds@linux-foundation.org> | 2010-08-10 18:22:42 -0400 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2010-08-10 18:22:42 -0400 |
commit | 2f9e825d3e0e2b407ae8f082de5c00afcf7378fb (patch) | |
tree | f8b3ee40674ce4acd5508a0a0bf52a30904caf6c | |
parent | 7ae0dea900b027cd90e8a3e14deca9a19e17638b (diff) | |
parent | de75d60d5ea235e6e09f4962ab22541ce0fe176a (diff) |
Merge branch 'for-2.6.36' of git://git.kernel.dk/linux-2.6-block
* 'for-2.6.36' of git://git.kernel.dk/linux-2.6-block: (149 commits)
block: make sure that REQ_* types are seen even with CONFIG_BLOCK=n
xen-blkfront: fix missing out label
blkdev: fix blkdev_issue_zeroout return value
block: update request stacking methods to support discards
block: fix missing export of blk_types.h
writeback: fix bad _bh spinlock nesting
drbd: revert "delay probes", feature is being re-implemented differently
drbd: Initialize all members of sync_conf to their defaults [Bugz 315]
drbd: Disable delay probes for the upcomming release
writeback: cleanup bdi_register
writeback: add new tracepoints
writeback: remove unnecessary init_timer call
writeback: optimize periodic bdi thread wakeups
writeback: prevent unnecessary bdi threads wakeups
writeback: move bdi threads exiting logic to the forker thread
writeback: restructure bdi forker loop a little
writeback: move last_active to bdi
writeback: do not remove bdi from bdi_list
writeback: simplify bdi code a little
writeback: do not lose wake-ups in bdi threads
...
Fixed up pretty trivial conflicts in drivers/block/virtio_blk.c and
drivers/scsi/scsi_error.c as per Jens.
154 files changed, 4286 insertions, 3211 deletions
diff --git a/arch/alpha/include/asm/scatterlist.h b/arch/alpha/include/asm/scatterlist.h index 5728c52a7412..017d7471c3c4 100644 --- a/arch/alpha/include/asm/scatterlist.h +++ b/arch/alpha/include/asm/scatterlist.h | |||
@@ -3,6 +3,4 @@ | |||
3 | 3 | ||
4 | #include <asm-generic/scatterlist.h> | 4 | #include <asm-generic/scatterlist.h> |
5 | 5 | ||
6 | #define ISA_DMA_THRESHOLD (~0UL) | ||
7 | |||
8 | #endif /* !(_ALPHA_SCATTERLIST_H) */ | 6 | #endif /* !(_ALPHA_SCATTERLIST_H) */ |
diff --git a/arch/avr32/include/asm/scatterlist.h b/arch/avr32/include/asm/scatterlist.h index 06394e5ead6c..a5902d9834e8 100644 --- a/arch/avr32/include/asm/scatterlist.h +++ b/arch/avr32/include/asm/scatterlist.h | |||
@@ -3,6 +3,4 @@ | |||
3 | 3 | ||
4 | #include <asm-generic/scatterlist.h> | 4 | #include <asm-generic/scatterlist.h> |
5 | 5 | ||
6 | #define ISA_DMA_THRESHOLD (0xffffffff) | ||
7 | |||
8 | #endif /* __ASM_AVR32_SCATTERLIST_H */ | 6 | #endif /* __ASM_AVR32_SCATTERLIST_H */ |
diff --git a/arch/blackfin/include/asm/scatterlist.h b/arch/blackfin/include/asm/scatterlist.h index 64d41d34ab0b..d177a1588958 100644 --- a/arch/blackfin/include/asm/scatterlist.h +++ b/arch/blackfin/include/asm/scatterlist.h | |||
@@ -3,6 +3,4 @@ | |||
3 | 3 | ||
4 | #include <asm-generic/scatterlist.h> | 4 | #include <asm-generic/scatterlist.h> |
5 | 5 | ||
6 | #define ISA_DMA_THRESHOLD (0xffffffff) | ||
7 | |||
8 | #endif /* !(_BLACKFIN_SCATTERLIST_H) */ | 6 | #endif /* !(_BLACKFIN_SCATTERLIST_H) */ |
diff --git a/arch/cris/include/asm/scatterlist.h b/arch/cris/include/asm/scatterlist.h index 249a7842ff5f..f11f8f40ec4a 100644 --- a/arch/cris/include/asm/scatterlist.h +++ b/arch/cris/include/asm/scatterlist.h | |||
@@ -3,6 +3,4 @@ | |||
3 | 3 | ||
4 | #include <asm-generic/scatterlist.h> | 4 | #include <asm-generic/scatterlist.h> |
5 | 5 | ||
6 | #define ISA_DMA_THRESHOLD (0x1fffffff) | ||
7 | |||
8 | #endif /* !(__ASM_CRIS_SCATTERLIST_H) */ | 6 | #endif /* !(__ASM_CRIS_SCATTERLIST_H) */ |
diff --git a/arch/frv/include/asm/scatterlist.h b/arch/frv/include/asm/scatterlist.h index 1614bfd7e3a4..0e5eb3018468 100644 --- a/arch/frv/include/asm/scatterlist.h +++ b/arch/frv/include/asm/scatterlist.h | |||
@@ -3,6 +3,4 @@ | |||
3 | 3 | ||
4 | #include <asm-generic/scatterlist.h> | 4 | #include <asm-generic/scatterlist.h> |
5 | 5 | ||
6 | #define ISA_DMA_THRESHOLD (0xffffffffUL) | ||
7 | |||
8 | #endif /* !_ASM_SCATTERLIST_H */ | 6 | #endif /* !_ASM_SCATTERLIST_H */ |
diff --git a/arch/h8300/include/asm/scatterlist.h b/arch/h8300/include/asm/scatterlist.h index de08a4a2cc1c..82130eda0e5f 100644 --- a/arch/h8300/include/asm/scatterlist.h +++ b/arch/h8300/include/asm/scatterlist.h | |||
@@ -3,6 +3,4 @@ | |||
3 | 3 | ||
4 | #include <asm-generic/scatterlist.h> | 4 | #include <asm-generic/scatterlist.h> |
5 | 5 | ||
6 | #define ISA_DMA_THRESHOLD (0xffffffff) | ||
7 | |||
8 | #endif /* !(_H8300_SCATTERLIST_H) */ | 6 | #endif /* !(_H8300_SCATTERLIST_H) */ |
diff --git a/arch/ia64/include/asm/scatterlist.h b/arch/ia64/include/asm/scatterlist.h index f299a4fb25c8..08fd93bff1db 100644 --- a/arch/ia64/include/asm/scatterlist.h +++ b/arch/ia64/include/asm/scatterlist.h | |||
@@ -2,15 +2,6 @@ | |||
2 | #define _ASM_IA64_SCATTERLIST_H | 2 | #define _ASM_IA64_SCATTERLIST_H |
3 | 3 | ||
4 | #include <asm-generic/scatterlist.h> | 4 | #include <asm-generic/scatterlist.h> |
5 | /* | ||
6 | * It used to be that ISA_DMA_THRESHOLD had something to do with the | ||
7 | * DMA-limits of ISA-devices. Nowadays, its only remaining use (apart | ||
8 | * from the aha1542.c driver, which isn't 64-bit clean anyhow) is to | ||
9 | * tell the block-layer (via BLK_BOUNCE_ISA) what the max. physical | ||
10 | * address of a page is that is allocated with GFP_DMA. On IA-64, | ||
11 | * that's 4GB - 1. | ||
12 | */ | ||
13 | #define ISA_DMA_THRESHOLD 0xffffffff | ||
14 | #define ARCH_HAS_SG_CHAIN | 5 | #define ARCH_HAS_SG_CHAIN |
15 | 6 | ||
16 | #endif /* _ASM_IA64_SCATTERLIST_H */ | 7 | #endif /* _ASM_IA64_SCATTERLIST_H */ |
diff --git a/arch/m32r/include/asm/scatterlist.h b/arch/m32r/include/asm/scatterlist.h index aeeddd8dac17..7370b8b6243e 100644 --- a/arch/m32r/include/asm/scatterlist.h +++ b/arch/m32r/include/asm/scatterlist.h | |||
@@ -3,6 +3,4 @@ | |||
3 | 3 | ||
4 | #include <asm-generic/scatterlist.h> | 4 | #include <asm-generic/scatterlist.h> |
5 | 5 | ||
6 | #define ISA_DMA_THRESHOLD (0x1fffffff) | ||
7 | |||
8 | #endif /* _ASM_M32R_SCATTERLIST_H */ | 6 | #endif /* _ASM_M32R_SCATTERLIST_H */ |
diff --git a/arch/m68k/include/asm/scatterlist.h b/arch/m68k/include/asm/scatterlist.h index 175da06c6b95..312505452a1e 100644 --- a/arch/m68k/include/asm/scatterlist.h +++ b/arch/m68k/include/asm/scatterlist.h | |||
@@ -3,7 +3,4 @@ | |||
3 | 3 | ||
4 | #include <asm-generic/scatterlist.h> | 4 | #include <asm-generic/scatterlist.h> |
5 | 5 | ||
6 | /* This is bogus and should go away. */ | ||
7 | #define ISA_DMA_THRESHOLD (0x00ffffff) | ||
8 | |||
9 | #endif /* !(_M68K_SCATTERLIST_H) */ | 6 | #endif /* !(_M68K_SCATTERLIST_H) */ |
diff --git a/arch/microblaze/include/asm/scatterlist.h b/arch/microblaze/include/asm/scatterlist.h index dc4a8900cc80..35d786fe93ae 100644 --- a/arch/microblaze/include/asm/scatterlist.h +++ b/arch/microblaze/include/asm/scatterlist.h | |||
@@ -1,3 +1 @@ | |||
1 | #include <asm-generic/scatterlist.h> | #include <asm-generic/scatterlist.h> | |
2 | |||
3 | #define ISA_DMA_THRESHOLD (~0UL) | ||
diff --git a/arch/mips/include/asm/scatterlist.h b/arch/mips/include/asm/scatterlist.h index 9af65e79be36..7ee0e646d82c 100644 --- a/arch/mips/include/asm/scatterlist.h +++ b/arch/mips/include/asm/scatterlist.h | |||
@@ -3,6 +3,4 @@ | |||
3 | 3 | ||
4 | #include <asm-generic/scatterlist.h> | 4 | #include <asm-generic/scatterlist.h> |
5 | 5 | ||
6 | #define ISA_DMA_THRESHOLD (0x00ffffffUL) | ||
7 | |||
8 | #endif /* __ASM_SCATTERLIST_H */ | 6 | #endif /* __ASM_SCATTERLIST_H */ |
diff --git a/arch/mn10300/include/asm/scatterlist.h b/arch/mn10300/include/asm/scatterlist.h index 7bd00b9e030d..7baa4006008a 100644 --- a/arch/mn10300/include/asm/scatterlist.h +++ b/arch/mn10300/include/asm/scatterlist.h | |||
@@ -13,6 +13,4 @@ | |||
13 | 13 | ||
14 | #include <asm-generic/scatterlist.h> | 14 | #include <asm-generic/scatterlist.h> |
15 | 15 | ||
16 | #define ISA_DMA_THRESHOLD (0x00ffffff) | ||
17 | |||
18 | #endif /* _ASM_SCATTERLIST_H */ | 16 | #endif /* _ASM_SCATTERLIST_H */ |
diff --git a/arch/parisc/include/asm/scatterlist.h b/arch/parisc/include/asm/scatterlist.h index 2c3b79b54b28..8bf1f0dd1f15 100644 --- a/arch/parisc/include/asm/scatterlist.h +++ b/arch/parisc/include/asm/scatterlist.h | |||
@@ -5,7 +5,6 @@ | |||
5 | #include <asm/types.h> | 5 | #include <asm/types.h> |
6 | #include <asm-generic/scatterlist.h> | 6 | #include <asm-generic/scatterlist.h> |
7 | 7 | ||
8 | #define ISA_DMA_THRESHOLD (~0UL) | ||
9 | #define sg_virt_addr(sg) ((unsigned long)sg_virt(sg)) | 8 | #define sg_virt_addr(sg) ((unsigned long)sg_virt(sg)) |
10 | 9 | ||
11 | #endif /* _ASM_PARISC_SCATTERLIST_H */ | 10 | #endif /* _ASM_PARISC_SCATTERLIST_H */ |
diff --git a/arch/powerpc/include/asm/scatterlist.h b/arch/powerpc/include/asm/scatterlist.h index 34cc78fd0ef4..de1f620bd5c9 100644 --- a/arch/powerpc/include/asm/scatterlist.h +++ b/arch/powerpc/include/asm/scatterlist.h | |||
@@ -12,9 +12,6 @@ | |||
12 | #include <asm/dma.h> | 12 | #include <asm/dma.h> |
13 | #include <asm-generic/scatterlist.h> | 13 | #include <asm-generic/scatterlist.h> |
14 | 14 | ||
15 | #ifdef __powerpc64__ | ||
16 | #define ISA_DMA_THRESHOLD (~0UL) | ||
17 | #endif | ||
18 | #define ARCH_HAS_SG_CHAIN | 15 | #define ARCH_HAS_SG_CHAIN |
19 | 16 | ||
20 | #endif /* _ASM_POWERPC_SCATTERLIST_H */ | 17 | #endif /* _ASM_POWERPC_SCATTERLIST_H */ |
diff --git a/arch/s390/include/asm/scatterlist.h b/arch/s390/include/asm/scatterlist.h index be44d94cba54..35d786fe93ae 100644 --- a/arch/s390/include/asm/scatterlist.h +++ b/arch/s390/include/asm/scatterlist.h | |||
@@ -1,3 +1 @@ | |||
1 | #define ISA_DMA_THRESHOLD (~0UL) | ||
2 | |||
3 | #include <asm-generic/scatterlist.h> | #include <asm-generic/scatterlist.h> | |
diff --git a/arch/score/include/asm/scatterlist.h b/arch/score/include/asm/scatterlist.h index 4fa1a6658215..9f533b8362c7 100644 --- a/arch/score/include/asm/scatterlist.h +++ b/arch/score/include/asm/scatterlist.h | |||
@@ -1,8 +1,6 @@ | |||
1 | #ifndef _ASM_SCORE_SCATTERLIST_H | 1 | #ifndef _ASM_SCORE_SCATTERLIST_H |
2 | #define _ASM_SCORE_SCATTERLIST_H | 2 | #define _ASM_SCORE_SCATTERLIST_H |
3 | 3 | ||
4 | #define ISA_DMA_THRESHOLD (~0UL) | ||
5 | |||
6 | #include <asm-generic/scatterlist.h> | 4 | #include <asm-generic/scatterlist.h> |
7 | 5 | ||
8 | #endif /* _ASM_SCORE_SCATTERLIST_H */ | 6 | #endif /* _ASM_SCORE_SCATTERLIST_H */ |
diff --git a/arch/sh/include/asm/scatterlist.h b/arch/sh/include/asm/scatterlist.h index e38d1d4c7f6f..98dfc3510f10 100644 --- a/arch/sh/include/asm/scatterlist.h +++ b/arch/sh/include/asm/scatterlist.h | |||
@@ -1,8 +1,6 @@ | |||
1 | #ifndef __ASM_SH_SCATTERLIST_H | 1 | #ifndef __ASM_SH_SCATTERLIST_H |
2 | #define __ASM_SH_SCATTERLIST_H | 2 | #define __ASM_SH_SCATTERLIST_H |
3 | 3 | ||
4 | #define ISA_DMA_THRESHOLD phys_addr_mask() | ||
5 | |||
6 | #include <asm-generic/scatterlist.h> | 4 | #include <asm-generic/scatterlist.h> |
7 | 5 | ||
8 | #endif /* __ASM_SH_SCATTERLIST_H */ | 6 | #endif /* __ASM_SH_SCATTERLIST_H */ |
diff --git a/arch/sparc/include/asm/scatterlist.h b/arch/sparc/include/asm/scatterlist.h index 433e45f05fd4..92bb638313f8 100644 --- a/arch/sparc/include/asm/scatterlist.h +++ b/arch/sparc/include/asm/scatterlist.h | |||
@@ -3,7 +3,6 @@ | |||
3 | 3 | ||
4 | #include <asm-generic/scatterlist.h> | 4 | #include <asm-generic/scatterlist.h> |
5 | 5 | ||
6 | #define ISA_DMA_THRESHOLD (~0UL) | ||
7 | #define ARCH_HAS_SG_CHAIN | 6 | #define ARCH_HAS_SG_CHAIN |
8 | 7 | ||
9 | #endif /* !(_SPARC_SCATTERLIST_H) */ | 8 | #endif /* !(_SPARC_SCATTERLIST_H) */ |
diff --git a/arch/um/drivers/ubd_kern.c b/arch/um/drivers/ubd_kern.c index da992a3ad6b7..1bcd208c459f 100644 --- a/arch/um/drivers/ubd_kern.c +++ b/arch/um/drivers/ubd_kern.c | |||
@@ -33,6 +33,7 @@ | |||
33 | #include "linux/mm.h" | 33 | #include "linux/mm.h" |
34 | #include "linux/slab.h" | 34 | #include "linux/slab.h" |
35 | #include "linux/vmalloc.h" | 35 | #include "linux/vmalloc.h" |
36 | #include "linux/smp_lock.h" | ||
36 | #include "linux/blkpg.h" | 37 | #include "linux/blkpg.h" |
37 | #include "linux/genhd.h" | 38 | #include "linux/genhd.h" |
38 | #include "linux/spinlock.h" | 39 | #include "linux/spinlock.h" |
@@ -1098,6 +1099,7 @@ static int ubd_open(struct block_device *bdev, fmode_t mode) | |||
1098 | struct ubd *ubd_dev = disk->private_data; | 1099 | struct ubd *ubd_dev = disk->private_data; |
1099 | int err = 0; | 1100 | int err = 0; |
1100 | 1101 | ||
1102 | lock_kernel(); | ||
1101 | if(ubd_dev->count == 0){ | 1103 | if(ubd_dev->count == 0){ |
1102 | err = ubd_open_dev(ubd_dev); | 1104 | err = ubd_open_dev(ubd_dev); |
1103 | if(err){ | 1105 | if(err){ |
@@ -1115,7 +1117,8 @@ static int ubd_open(struct block_device *bdev, fmode_t mode) | |||
1115 | if(--ubd_dev->count == 0) ubd_close_dev(ubd_dev); | 1117 | if(--ubd_dev->count == 0) ubd_close_dev(ubd_dev); |
1116 | err = -EROFS; | 1118 | err = -EROFS; |
1117 | }*/ | 1119 | }*/ |
1118 | out: | 1120 | out: |
1121 | unlock_kernel(); | ||
1119 | return err; | 1122 | return err; |
1120 | } | 1123 | } |
1121 | 1124 | ||
@@ -1123,8 +1126,10 @@ static int ubd_release(struct gendisk *disk, fmode_t mode) | |||
1123 | { | 1126 | { |
1124 | struct ubd *ubd_dev = disk->private_data; | 1127 | struct ubd *ubd_dev = disk->private_data; |
1125 | 1128 | ||
1129 | lock_kernel(); | ||
1126 | if(--ubd_dev->count == 0) | 1130 | if(--ubd_dev->count == 0) |
1127 | ubd_close_dev(ubd_dev); | 1131 | ubd_close_dev(ubd_dev); |
1132 | unlock_kernel(); | ||
1128 | return 0; | 1133 | return 0; |
1129 | } | 1134 | } |
1130 | 1135 | ||
diff --git a/arch/x86/include/asm/scatterlist.h b/arch/x86/include/asm/scatterlist.h index fb0b1874396f..4240878b9d76 100644 --- a/arch/x86/include/asm/scatterlist.h +++ b/arch/x86/include/asm/scatterlist.h | |||
@@ -3,7 +3,6 @@ | |||
3 | 3 | ||
4 | #include <asm-generic/scatterlist.h> | 4 | #include <asm-generic/scatterlist.h> |
5 | 5 | ||
6 | #define ISA_DMA_THRESHOLD (0x00ffffff) | ||
7 | #define ARCH_HAS_SG_CHAIN | 6 | #define ARCH_HAS_SG_CHAIN |
8 | 7 | ||
9 | #endif /* _ASM_X86_SCATTERLIST_H */ | 8 | #endif /* _ASM_X86_SCATTERLIST_H */ |
diff --git a/arch/xtensa/include/asm/scatterlist.h b/arch/xtensa/include/asm/scatterlist.h index b1f9fdc1d5ba..a0421a61d9e1 100644 --- a/arch/xtensa/include/asm/scatterlist.h +++ b/arch/xtensa/include/asm/scatterlist.h | |||
@@ -13,6 +13,4 @@ | |||
13 | 13 | ||
14 | #include <asm-generic/scatterlist.h> | 14 | #include <asm-generic/scatterlist.h> |
15 | 15 | ||
16 | #define ISA_DMA_THRESHOLD (~0UL) | ||
17 | |||
18 | #endif /* _XTENSA_SCATTERLIST_H */ | 16 | #endif /* _XTENSA_SCATTERLIST_H */ |
diff --git a/block/blk-barrier.c b/block/blk-barrier.c index 0d710c9d403b..f0faefca032f 100644 --- a/block/blk-barrier.c +++ b/block/blk-barrier.c | |||
@@ -13,7 +13,6 @@ | |||
13 | * blk_queue_ordered - does this queue support ordered writes | 13 | * blk_queue_ordered - does this queue support ordered writes |
14 | * @q: the request queue | 14 | * @q: the request queue |
15 | * @ordered: one of QUEUE_ORDERED_* | 15 | * @ordered: one of QUEUE_ORDERED_* |
16 | * @prepare_flush_fn: rq setup helper for cache flush ordered writes | ||
17 | * | 16 | * |
18 | * Description: | 17 | * Description: |
19 | * For journalled file systems, doing ordered writes on a commit | 18 | * For journalled file systems, doing ordered writes on a commit |
@@ -22,15 +21,8 @@ | |||
22 | * feature should call this function and indicate so. | 21 | * feature should call this function and indicate so. |
23 | * | 22 | * |
24 | **/ | 23 | **/ |
25 | int blk_queue_ordered(struct request_queue *q, unsigned ordered, | 24 | int blk_queue_ordered(struct request_queue *q, unsigned ordered) |
26 | prepare_flush_fn *prepare_flush_fn) | ||
27 | { | 25 | { |
28 | if (!prepare_flush_fn && (ordered & (QUEUE_ORDERED_DO_PREFLUSH | | ||
29 | QUEUE_ORDERED_DO_POSTFLUSH))) { | ||
30 | printk(KERN_ERR "%s: prepare_flush_fn required\n", __func__); | ||
31 | return -EINVAL; | ||
32 | } | ||
33 | |||
34 | if (ordered != QUEUE_ORDERED_NONE && | 26 | if (ordered != QUEUE_ORDERED_NONE && |
35 | ordered != QUEUE_ORDERED_DRAIN && | 27 | ordered != QUEUE_ORDERED_DRAIN && |
36 | ordered != QUEUE_ORDERED_DRAIN_FLUSH && | 28 | ordered != QUEUE_ORDERED_DRAIN_FLUSH && |
@@ -44,7 +36,6 @@ int blk_queue_ordered(struct request_queue *q, unsigned ordered, | |||
44 | 36 | ||
45 | q->ordered = ordered; | 37 | q->ordered = ordered; |
46 | q->next_ordered = ordered; | 38 | q->next_ordered = ordered; |
47 | q->prepare_flush_fn = prepare_flush_fn; | ||
48 | 39 | ||
49 | return 0; | 40 | return 0; |
50 | } | 41 | } |
@@ -79,7 +70,7 @@ unsigned blk_ordered_req_seq(struct request *rq) | |||
79 | * | 70 | * |
80 | * http://thread.gmane.org/gmane.linux.kernel/537473 | 71 | * http://thread.gmane.org/gmane.linux.kernel/537473 |
81 | */ | 72 | */ |
82 | if (!blk_fs_request(rq)) | 73 | if (rq->cmd_type != REQ_TYPE_FS) |
83 | return QUEUE_ORDSEQ_DRAIN; | 74 | return QUEUE_ORDSEQ_DRAIN; |
84 | 75 | ||
85 | if ((rq->cmd_flags & REQ_ORDERED_COLOR) == | 76 | if ((rq->cmd_flags & REQ_ORDERED_COLOR) == |
@@ -143,10 +134,10 @@ static void queue_flush(struct request_queue *q, unsigned which) | |||
143 | } | 134 | } |
144 | 135 | ||
145 | blk_rq_init(q, rq); | 136 | blk_rq_init(q, rq); |
146 | rq->cmd_flags = REQ_HARDBARRIER; | 137 | rq->cmd_type = REQ_TYPE_FS; |
147 | rq->rq_disk = q->bar_rq.rq_disk; | 138 | rq->cmd_flags = REQ_HARDBARRIER | REQ_FLUSH; |
139 | rq->rq_disk = q->orig_bar_rq->rq_disk; | ||
148 | rq->end_io = end_io; | 140 | rq->end_io = end_io; |
149 | q->prepare_flush_fn(q, rq); | ||
150 | 141 | ||
151 | elv_insert(q, rq, ELEVATOR_INSERT_FRONT); | 142 | elv_insert(q, rq, ELEVATOR_INSERT_FRONT); |
152 | } | 143 | } |
@@ -203,7 +194,7 @@ static inline bool start_ordered(struct request_queue *q, struct request **rqp) | |||
203 | /* initialize proxy request and queue it */ | 194 | /* initialize proxy request and queue it */ |
204 | blk_rq_init(q, rq); | 195 | blk_rq_init(q, rq); |
205 | if (bio_data_dir(q->orig_bar_rq->bio) == WRITE) | 196 | if (bio_data_dir(q->orig_bar_rq->bio) == WRITE) |
206 | rq->cmd_flags |= REQ_RW; | 197 | rq->cmd_flags |= REQ_WRITE; |
207 | if (q->ordered & QUEUE_ORDERED_DO_FUA) | 198 | if (q->ordered & QUEUE_ORDERED_DO_FUA) |
208 | rq->cmd_flags |= REQ_FUA; | 199 | rq->cmd_flags |= REQ_FUA; |
209 | init_request_from_bio(rq, q->orig_bar_rq->bio); | 200 | init_request_from_bio(rq, q->orig_bar_rq->bio); |
@@ -236,7 +227,8 @@ static inline bool start_ordered(struct request_queue *q, struct request **rqp) | |||
236 | bool blk_do_ordered(struct request_queue *q, struct request **rqp) | 227 | bool blk_do_ordered(struct request_queue *q, struct request **rqp) |
237 | { | 228 | { |
238 | struct request *rq = *rqp; | 229 | struct request *rq = *rqp; |
239 | const int is_barrier = blk_fs_request(rq) && blk_barrier_rq(rq); | 230 | const int is_barrier = rq->cmd_type == REQ_TYPE_FS && |
231 | (rq->cmd_flags & REQ_HARDBARRIER); | ||
240 | 232 | ||
241 | if (!q->ordseq) { | 233 | if (!q->ordseq) { |
242 | if (!is_barrier) | 234 | if (!is_barrier) |
@@ -261,7 +253,7 @@ bool blk_do_ordered(struct request_queue *q, struct request **rqp) | |||
261 | */ | 253 | */ |
262 | 254 | ||
263 | /* Special requests are not subject to ordering rules. */ | 255 | /* Special requests are not subject to ordering rules. */ |
264 | if (!blk_fs_request(rq) && | 256 | if (rq->cmd_type != REQ_TYPE_FS && |
265 | rq != &q->pre_flush_rq && rq != &q->post_flush_rq) | 257 | rq != &q->pre_flush_rq && rq != &q->post_flush_rq) |
266 | return true; | 258 | return true; |
267 | 259 | ||
@@ -319,6 +311,15 @@ int blkdev_issue_flush(struct block_device *bdev, gfp_t gfp_mask, | |||
319 | if (!q) | 311 | if (!q) |
320 | return -ENXIO; | 312 | return -ENXIO; |
321 | 313 | ||
314 | /* | ||
315 | * some block devices may not have their queue correctly set up here | ||
316 | * (e.g. loop device without a backing file) and so issuing a flush | ||
317 | * here will panic. Ensure there is a request function before issuing | ||
318 | * the barrier. | ||
319 | */ | ||
320 | if (!q->make_request_fn) | ||
321 | return -ENXIO; | ||
322 | |||
322 | bio = bio_alloc(gfp_mask, 0); | 323 | bio = bio_alloc(gfp_mask, 0); |
323 | bio->bi_end_io = bio_end_empty_barrier; | 324 | bio->bi_end_io = bio_end_empty_barrier; |
324 | bio->bi_bdev = bdev; | 325 | bio->bi_bdev = bdev; |
diff --git a/block/blk-core.c b/block/blk-core.c index f0640d7f800f..7da630e25ae7 100644 --- a/block/blk-core.c +++ b/block/blk-core.c | |||
@@ -184,7 +184,7 @@ void blk_dump_rq_flags(struct request *rq, char *msg) | |||
184 | printk(KERN_INFO " bio %p, biotail %p, buffer %p, len %u\n", | 184 | printk(KERN_INFO " bio %p, biotail %p, buffer %p, len %u\n", |
185 | rq->bio, rq->biotail, rq->buffer, blk_rq_bytes(rq)); | 185 | rq->bio, rq->biotail, rq->buffer, blk_rq_bytes(rq)); |
186 | 186 | ||
187 | if (blk_pc_request(rq)) { | 187 | if (rq->cmd_type == REQ_TYPE_BLOCK_PC) { |
188 | printk(KERN_INFO " cdb: "); | 188 | printk(KERN_INFO " cdb: "); |
189 | for (bit = 0; bit < BLK_MAX_CDB; bit++) | 189 | for (bit = 0; bit < BLK_MAX_CDB; bit++) |
190 | printk("%02x ", rq->cmd[bit]); | 190 | printk("%02x ", rq->cmd[bit]); |
@@ -608,6 +608,7 @@ blk_init_allocated_queue_node(struct request_queue *q, request_fn_proc *rfn, | |||
608 | 608 | ||
609 | q->request_fn = rfn; | 609 | q->request_fn = rfn; |
610 | q->prep_rq_fn = NULL; | 610 | q->prep_rq_fn = NULL; |
611 | q->unprep_rq_fn = NULL; | ||
611 | q->unplug_fn = generic_unplug_device; | 612 | q->unplug_fn = generic_unplug_device; |
612 | q->queue_flags = QUEUE_FLAG_DEFAULT; | 613 | q->queue_flags = QUEUE_FLAG_DEFAULT; |
613 | q->queue_lock = lock; | 614 | q->queue_lock = lock; |
@@ -1135,30 +1136,46 @@ void blk_put_request(struct request *req) | |||
1135 | } | 1136 | } |
1136 | EXPORT_SYMBOL(blk_put_request); | 1137 | EXPORT_SYMBOL(blk_put_request); |
1137 | 1138 | ||
1139 | /** | ||
1140 | * blk_add_request_payload - add a payload to a request | ||
1141 | * @rq: request to update | ||
1142 | * @page: page backing the payload | ||
1143 | * @len: length of the payload. | ||
1144 | * | ||
1145 | * This allows to later add a payload to an already submitted request by | ||
1146 | * a block driver. The driver needs to take care of freeing the payload | ||
1147 | * itself. | ||
1148 | * | ||
1149 | * Note that this is a quite horrible hack and nothing but handling of | ||
1150 | * discard requests should ever use it. | ||
1151 | */ | ||
1152 | void blk_add_request_payload(struct request *rq, struct page *page, | ||
1153 | unsigned int len) | ||
1154 | { | ||
1155 | struct bio *bio = rq->bio; | ||
1156 | |||
1157 | bio->bi_io_vec->bv_page = page; | ||
1158 | bio->bi_io_vec->bv_offset = 0; | ||
1159 | bio->bi_io_vec->bv_len = len; | ||
1160 | |||
1161 | bio->bi_size = len; | ||
1162 | bio->bi_vcnt = 1; | ||
1163 | bio->bi_phys_segments = 1; | ||
1164 | |||
1165 | rq->__data_len = rq->resid_len = len; | ||
1166 | rq->nr_phys_segments = 1; | ||
1167 | rq->buffer = bio_data(bio); | ||
1168 | } | ||
1169 | EXPORT_SYMBOL_GPL(blk_add_request_payload); | ||
1170 | |||
1138 | void init_request_from_bio(struct request *req, struct bio *bio) | 1171 | void init_request_from_bio(struct request *req, struct bio *bio) |
1139 | { | 1172 | { |
1140 | req->cpu = bio->bi_comp_cpu; | 1173 | req->cpu = bio->bi_comp_cpu; |
1141 | req->cmd_type = REQ_TYPE_FS; | 1174 | req->cmd_type = REQ_TYPE_FS; |
1142 | 1175 | ||
1143 | /* | 1176 | req->cmd_flags |= bio->bi_rw & REQ_COMMON_MASK; |
1144 | * Inherit FAILFAST from bio (for read-ahead, and explicit | 1177 | if (bio->bi_rw & REQ_RAHEAD) |
1145 | * FAILFAST). FAILFAST flags are identical for req and bio. | ||
1146 | */ | ||
1147 | if (bio_rw_flagged(bio, BIO_RW_AHEAD)) | ||
1148 | req->cmd_flags |= REQ_FAILFAST_MASK; | 1178 | req->cmd_flags |= REQ_FAILFAST_MASK; |
1149 | else | ||
1150 | req->cmd_flags |= bio->bi_rw & REQ_FAILFAST_MASK; | ||
1151 | |||
1152 | if (bio_rw_flagged(bio, BIO_RW_DISCARD)) | ||
1153 | req->cmd_flags |= REQ_DISCARD; | ||
1154 | if (bio_rw_flagged(bio, BIO_RW_BARRIER)) | ||
1155 | req->cmd_flags |= REQ_HARDBARRIER; | ||
1156 | if (bio_rw_flagged(bio, BIO_RW_SYNCIO)) | ||
1157 | req->cmd_flags |= REQ_RW_SYNC; | ||
1158 | if (bio_rw_flagged(bio, BIO_RW_META)) | ||
1159 | req->cmd_flags |= REQ_RW_META; | ||
1160 | if (bio_rw_flagged(bio, BIO_RW_NOIDLE)) | ||
1161 | req->cmd_flags |= REQ_NOIDLE; | ||
1162 | 1179 | ||
1163 | req->errors = 0; | 1180 | req->errors = 0; |
1164 | req->__sector = bio->bi_sector; | 1181 | req->__sector = bio->bi_sector; |
@@ -1181,12 +1198,12 @@ static int __make_request(struct request_queue *q, struct bio *bio) | |||
1181 | int el_ret; | 1198 | int el_ret; |
1182 | unsigned int bytes = bio->bi_size; | 1199 | unsigned int bytes = bio->bi_size; |
1183 | const unsigned short prio = bio_prio(bio); | 1200 | const unsigned short prio = bio_prio(bio); |
1184 | const bool sync = bio_rw_flagged(bio, BIO_RW_SYNCIO); | 1201 | const bool sync = (bio->bi_rw & REQ_SYNC); |
1185 | const bool unplug = bio_rw_flagged(bio, BIO_RW_UNPLUG); | 1202 | const bool unplug = (bio->bi_rw & REQ_UNPLUG); |
1186 | const unsigned int ff = bio->bi_rw & REQ_FAILFAST_MASK; | 1203 | const unsigned int ff = bio->bi_rw & REQ_FAILFAST_MASK; |
1187 | int rw_flags; | 1204 | int rw_flags; |
1188 | 1205 | ||
1189 | if (bio_rw_flagged(bio, BIO_RW_BARRIER) && | 1206 | if ((bio->bi_rw & REQ_HARDBARRIER) && |
1190 | (q->next_ordered == QUEUE_ORDERED_NONE)) { | 1207 | (q->next_ordered == QUEUE_ORDERED_NONE)) { |
1191 | bio_endio(bio, -EOPNOTSUPP); | 1208 | bio_endio(bio, -EOPNOTSUPP); |
1192 | return 0; | 1209 | return 0; |
@@ -1200,7 +1217,7 @@ static int __make_request(struct request_queue *q, struct bio *bio) | |||
1200 | 1217 | ||
1201 | spin_lock_irq(q->queue_lock); | 1218 | spin_lock_irq(q->queue_lock); |
1202 | 1219 | ||
1203 | if (unlikely(bio_rw_flagged(bio, BIO_RW_BARRIER)) || elv_queue_empty(q)) | 1220 | if (unlikely((bio->bi_rw & REQ_HARDBARRIER)) || elv_queue_empty(q)) |
1204 | goto get_rq; | 1221 | goto get_rq; |
1205 | 1222 | ||
1206 | el_ret = elv_merge(q, &req, bio); | 1223 | el_ret = elv_merge(q, &req, bio); |
@@ -1275,7 +1292,7 @@ get_rq: | |||
1275 | */ | 1292 | */ |
1276 | rw_flags = bio_data_dir(bio); | 1293 | rw_flags = bio_data_dir(bio); |
1277 | if (sync) | 1294 | if (sync) |
1278 | rw_flags |= REQ_RW_SYNC; | 1295 | rw_flags |= REQ_SYNC; |
1279 | 1296 | ||
1280 | /* | 1297 | /* |
1281 | * Grab a free request. This is might sleep but can not fail. | 1298 | * Grab a free request. This is might sleep but can not fail. |
@@ -1464,7 +1481,7 @@ static inline void __generic_make_request(struct bio *bio) | |||
1464 | goto end_io; | 1481 | goto end_io; |
1465 | } | 1482 | } |
1466 | 1483 | ||
1467 | if (unlikely(!bio_rw_flagged(bio, BIO_RW_DISCARD) && | 1484 | if (unlikely(!(bio->bi_rw & REQ_DISCARD) && |
1468 | nr_sectors > queue_max_hw_sectors(q))) { | 1485 | nr_sectors > queue_max_hw_sectors(q))) { |
1469 | printk(KERN_ERR "bio too big device %s (%u > %u)\n", | 1486 | printk(KERN_ERR "bio too big device %s (%u > %u)\n", |
1470 | bdevname(bio->bi_bdev, b), | 1487 | bdevname(bio->bi_bdev, b), |
@@ -1497,8 +1514,7 @@ static inline void __generic_make_request(struct bio *bio) | |||
1497 | if (bio_check_eod(bio, nr_sectors)) | 1514 | if (bio_check_eod(bio, nr_sectors)) |
1498 | goto end_io; | 1515 | goto end_io; |
1499 | 1516 | ||
1500 | if (bio_rw_flagged(bio, BIO_RW_DISCARD) && | 1517 | if ((bio->bi_rw & REQ_DISCARD) && !blk_queue_discard(q)) { |
1501 | !blk_queue_discard(q)) { | ||
1502 | err = -EOPNOTSUPP; | 1518 | err = -EOPNOTSUPP; |
1503 | goto end_io; | 1519 | goto end_io; |
1504 | } | 1520 | } |
@@ -1583,7 +1599,7 @@ void submit_bio(int rw, struct bio *bio) | |||
1583 | * If it's a regular read/write or a barrier with data attached, | 1599 | * If it's a regular read/write or a barrier with data attached, |
1584 | * go through the normal accounting stuff before submission. | 1600 | * go through the normal accounting stuff before submission. |
1585 | */ | 1601 | */ |
1586 | if (bio_has_data(bio) && !(rw & (1 << BIO_RW_DISCARD))) { | 1602 | if (bio_has_data(bio) && !(rw & REQ_DISCARD)) { |
1587 | if (rw & WRITE) { | 1603 | if (rw & WRITE) { |
1588 | count_vm_events(PGPGOUT, count); | 1604 | count_vm_events(PGPGOUT, count); |
1589 | } else { | 1605 | } else { |
@@ -1628,6 +1644,9 @@ EXPORT_SYMBOL(submit_bio); | |||
1628 | */ | 1644 | */ |
1629 | int blk_rq_check_limits(struct request_queue *q, struct request *rq) | 1645 | int blk_rq_check_limits(struct request_queue *q, struct request *rq) |
1630 | { | 1646 | { |
1647 | if (rq->cmd_flags & REQ_DISCARD) | ||
1648 | return 0; | ||
1649 | |||
1631 | if (blk_rq_sectors(rq) > queue_max_sectors(q) || | 1650 | if (blk_rq_sectors(rq) > queue_max_sectors(q) || |
1632 | blk_rq_bytes(rq) > queue_max_hw_sectors(q) << 9) { | 1651 | blk_rq_bytes(rq) > queue_max_hw_sectors(q) << 9) { |
1633 | printk(KERN_ERR "%s: over max size limit.\n", __func__); | 1652 | printk(KERN_ERR "%s: over max size limit.\n", __func__); |
@@ -1796,7 +1815,7 @@ struct request *blk_peek_request(struct request_queue *q) | |||
1796 | * sees this request (possibly after | 1815 | * sees this request (possibly after |
1797 | * requeueing). Notify IO scheduler. | 1816 | * requeueing). Notify IO scheduler. |
1798 | */ | 1817 | */ |
1799 | if (blk_sorted_rq(rq)) | 1818 | if (rq->cmd_flags & REQ_SORTED) |
1800 | elv_activate_rq(q, rq); | 1819 | elv_activate_rq(q, rq); |
1801 | 1820 | ||
1802 | /* | 1821 | /* |
@@ -1984,10 +2003,11 @@ bool blk_update_request(struct request *req, int error, unsigned int nr_bytes) | |||
1984 | * TODO: tj: This is too subtle. It would be better to let | 2003 | * TODO: tj: This is too subtle. It would be better to let |
1985 | * low level drivers do what they see fit. | 2004 | * low level drivers do what they see fit. |
1986 | */ | 2005 | */ |
1987 | if (blk_fs_request(req)) | 2006 | if (req->cmd_type == REQ_TYPE_FS) |
1988 | req->errors = 0; | 2007 | req->errors = 0; |
1989 | 2008 | ||
1990 | if (error && (blk_fs_request(req) && !(req->cmd_flags & REQ_QUIET))) { | 2009 | if (error && req->cmd_type == REQ_TYPE_FS && |
2010 | !(req->cmd_flags & REQ_QUIET)) { | ||
1991 | printk(KERN_ERR "end_request: I/O error, dev %s, sector %llu\n", | 2011 | printk(KERN_ERR "end_request: I/O error, dev %s, sector %llu\n", |
1992 | req->rq_disk ? req->rq_disk->disk_name : "?", | 2012 | req->rq_disk ? req->rq_disk->disk_name : "?", |
1993 | (unsigned long long)blk_rq_pos(req)); | 2013 | (unsigned long long)blk_rq_pos(req)); |
@@ -2074,7 +2094,7 @@ bool blk_update_request(struct request *req, int error, unsigned int nr_bytes) | |||
2074 | req->buffer = bio_data(req->bio); | 2094 | req->buffer = bio_data(req->bio); |
2075 | 2095 | ||
2076 | /* update sector only for requests with clear definition of sector */ | 2096 | /* update sector only for requests with clear definition of sector */ |
2077 | if (blk_fs_request(req) || blk_discard_rq(req)) | 2097 | if (req->cmd_type == REQ_TYPE_FS || (req->cmd_flags & REQ_DISCARD)) |
2078 | req->__sector += total_bytes >> 9; | 2098 | req->__sector += total_bytes >> 9; |
2079 | 2099 | ||
2080 | /* mixed attributes always follow the first bio */ | 2100 | /* mixed attributes always follow the first bio */ |
@@ -2111,11 +2131,32 @@ static bool blk_update_bidi_request(struct request *rq, int error, | |||
2111 | blk_update_request(rq->next_rq, error, bidi_bytes)) | 2131 | blk_update_request(rq->next_rq, error, bidi_bytes)) |
2112 | return true; | 2132 | return true; |
2113 | 2133 | ||
2114 | add_disk_randomness(rq->rq_disk); | 2134 | if (blk_queue_add_random(rq->q)) |
2135 | add_disk_randomness(rq->rq_disk); | ||
2115 | 2136 | ||
2116 | return false; | 2137 | return false; |
2117 | } | 2138 | } |
2118 | 2139 | ||
2140 | /** | ||
2141 | * blk_unprep_request - unprepare a request | ||
2142 | * @req: the request | ||
2143 | * | ||
2144 | * This function makes a request ready for complete resubmission (or | ||
2145 | * completion). It happens only after all error handling is complete, | ||
2146 | * so represents the appropriate moment to deallocate any resources | ||
2147 | * that were allocated to the request in the prep_rq_fn. The queue | ||
2148 | * lock is held when calling this. | ||
2149 | */ | ||
2150 | void blk_unprep_request(struct request *req) | ||
2151 | { | ||
2152 | struct request_queue *q = req->q; | ||
2153 | |||
2154 | req->cmd_flags &= ~REQ_DONTPREP; | ||
2155 | if (q->unprep_rq_fn) | ||
2156 | q->unprep_rq_fn(q, req); | ||
2157 | } | ||
2158 | EXPORT_SYMBOL_GPL(blk_unprep_request); | ||
2159 | |||
2119 | /* | 2160 | /* |
2120 | * queue lock must be held | 2161 | * queue lock must be held |
2121 | */ | 2162 | */ |
@@ -2126,11 +2167,15 @@ static void blk_finish_request(struct request *req, int error) | |||
2126 | 2167 | ||
2127 | BUG_ON(blk_queued_rq(req)); | 2168 | BUG_ON(blk_queued_rq(req)); |
2128 | 2169 | ||
2129 | if (unlikely(laptop_mode) && blk_fs_request(req)) | 2170 | if (unlikely(laptop_mode) && req->cmd_type == REQ_TYPE_FS) |
2130 | laptop_io_completion(&req->q->backing_dev_info); | 2171 | laptop_io_completion(&req->q->backing_dev_info); |
2131 | 2172 | ||
2132 | blk_delete_timer(req); | 2173 | blk_delete_timer(req); |
2133 | 2174 | ||
2175 | if (req->cmd_flags & REQ_DONTPREP) | ||
2176 | blk_unprep_request(req); | ||
2177 | |||
2178 | |||
2134 | blk_account_io_done(req); | 2179 | blk_account_io_done(req); |
2135 | 2180 | ||
2136 | if (req->end_io) | 2181 | if (req->end_io) |
@@ -2363,7 +2408,7 @@ void blk_rq_bio_prep(struct request_queue *q, struct request *rq, | |||
2363 | struct bio *bio) | 2408 | struct bio *bio) |
2364 | { | 2409 | { |
2365 | /* Bit 0 (R/W) is identical in rq->cmd_flags and bio->bi_rw */ | 2410 | /* Bit 0 (R/W) is identical in rq->cmd_flags and bio->bi_rw */ |
2366 | rq->cmd_flags |= bio->bi_rw & REQ_RW; | 2411 | rq->cmd_flags |= bio->bi_rw & REQ_WRITE; |
2367 | 2412 | ||
2368 | if (bio_has_data(bio)) { | 2413 | if (bio_has_data(bio)) { |
2369 | rq->nr_phys_segments = bio_phys_segments(q, bio); | 2414 | rq->nr_phys_segments = bio_phys_segments(q, bio); |
@@ -2450,6 +2495,8 @@ static void __blk_rq_prep_clone(struct request *dst, struct request *src) | |||
2450 | { | 2495 | { |
2451 | dst->cpu = src->cpu; | 2496 | dst->cpu = src->cpu; |
2452 | dst->cmd_flags = (rq_data_dir(src) | REQ_NOMERGE); | 2497 | dst->cmd_flags = (rq_data_dir(src) | REQ_NOMERGE); |
2498 | if (src->cmd_flags & REQ_DISCARD) | ||
2499 | dst->cmd_flags |= REQ_DISCARD; | ||
2453 | dst->cmd_type = src->cmd_type; | 2500 | dst->cmd_type = src->cmd_type; |
2454 | dst->__sector = blk_rq_pos(src); | 2501 | dst->__sector = blk_rq_pos(src); |
2455 | dst->__data_len = blk_rq_bytes(src); | 2502 | dst->__data_len = blk_rq_bytes(src); |
diff --git a/block/blk-exec.c b/block/blk-exec.c index 49557e91f0da..e1672f14840e 100644 --- a/block/blk-exec.c +++ b/block/blk-exec.c | |||
@@ -57,7 +57,7 @@ void blk_execute_rq_nowait(struct request_queue *q, struct gendisk *bd_disk, | |||
57 | __elv_add_request(q, rq, where, 1); | 57 | __elv_add_request(q, rq, where, 1); |
58 | __generic_unplug_device(q); | 58 | __generic_unplug_device(q); |
59 | /* the queue is stopped so it won't be plugged+unplugged */ | 59 | /* the queue is stopped so it won't be plugged+unplugged */ |
60 | if (blk_pm_resume_request(rq)) | 60 | if (rq->cmd_type == REQ_TYPE_PM_RESUME) |
61 | q->request_fn(q); | 61 | q->request_fn(q); |
62 | spin_unlock_irq(q->queue_lock); | 62 | spin_unlock_irq(q->queue_lock); |
63 | } | 63 | } |
diff --git a/block/blk-lib.c b/block/blk-lib.c index d0216b9f22d4..c1fc55a83ba1 100644 --- a/block/blk-lib.c +++ b/block/blk-lib.c | |||
@@ -19,7 +19,6 @@ static void blkdev_discard_end_io(struct bio *bio, int err) | |||
19 | 19 | ||
20 | if (bio->bi_private) | 20 | if (bio->bi_private) |
21 | complete(bio->bi_private); | 21 | complete(bio->bi_private); |
22 | __free_page(bio_page(bio)); | ||
23 | 22 | ||
24 | bio_put(bio); | 23 | bio_put(bio); |
25 | } | 24 | } |
@@ -42,8 +41,8 @@ int blkdev_issue_discard(struct block_device *bdev, sector_t sector, | |||
42 | struct request_queue *q = bdev_get_queue(bdev); | 41 | struct request_queue *q = bdev_get_queue(bdev); |
43 | int type = flags & BLKDEV_IFL_BARRIER ? | 42 | int type = flags & BLKDEV_IFL_BARRIER ? |
44 | DISCARD_BARRIER : DISCARD_NOBARRIER; | 43 | DISCARD_BARRIER : DISCARD_NOBARRIER; |
44 | unsigned int max_discard_sectors; | ||
45 | struct bio *bio; | 45 | struct bio *bio; |
46 | struct page *page; | ||
47 | int ret = 0; | 46 | int ret = 0; |
48 | 47 | ||
49 | if (!q) | 48 | if (!q) |
@@ -52,36 +51,30 @@ int blkdev_issue_discard(struct block_device *bdev, sector_t sector, | |||
52 | if (!blk_queue_discard(q)) | 51 | if (!blk_queue_discard(q)) |
53 | return -EOPNOTSUPP; | 52 | return -EOPNOTSUPP; |
54 | 53 | ||
55 | while (nr_sects && !ret) { | 54 | /* |
56 | unsigned int sector_size = q->limits.logical_block_size; | 55 | * Ensure that max_discard_sectors is of the proper |
57 | unsigned int max_discard_sectors = | 56 | * granularity |
58 | min(q->limits.max_discard_sectors, UINT_MAX >> 9); | 57 | */ |
58 | max_discard_sectors = min(q->limits.max_discard_sectors, UINT_MAX >> 9); | ||
59 | if (q->limits.discard_granularity) { | ||
60 | unsigned int disc_sects = q->limits.discard_granularity >> 9; | ||
59 | 61 | ||
62 | max_discard_sectors &= ~(disc_sects - 1); | ||
63 | } | ||
64 | |||
65 | while (nr_sects && !ret) { | ||
60 | bio = bio_alloc(gfp_mask, 1); | 66 | bio = bio_alloc(gfp_mask, 1); |
61 | if (!bio) | 67 | if (!bio) { |
62 | goto out; | 68 | ret = -ENOMEM; |
69 | break; | ||
70 | } | ||
71 | |||
63 | bio->bi_sector = sector; | 72 | bio->bi_sector = sector; |
64 | bio->bi_end_io = blkdev_discard_end_io; | 73 | bio->bi_end_io = blkdev_discard_end_io; |
65 | bio->bi_bdev = bdev; | 74 | bio->bi_bdev = bdev; |
66 | if (flags & BLKDEV_IFL_WAIT) | 75 | if (flags & BLKDEV_IFL_WAIT) |
67 | bio->bi_private = &wait; | 76 | bio->bi_private = &wait; |
68 | 77 | ||
69 | /* | ||
70 | * Add a zeroed one-sector payload as that's what | ||
71 | * our current implementations need. If we'll ever need | ||
72 | * more the interface will need revisiting. | ||
73 | */ | ||
74 | page = alloc_page(gfp_mask | __GFP_ZERO); | ||
75 | if (!page) | ||
76 | goto out_free_bio; | ||
77 | if (bio_add_pc_page(q, bio, page, sector_size, 0) < sector_size) | ||
78 | goto out_free_page; | ||
79 | |||
80 | /* | ||
81 | * And override the bio size - the way discard works we | ||
82 | * touch many more blocks on disk than the actual payload | ||
83 | * length. | ||
84 | */ | ||
85 | if (nr_sects > max_discard_sectors) { | 78 | if (nr_sects > max_discard_sectors) { |
86 | bio->bi_size = max_discard_sectors << 9; | 79 | bio->bi_size = max_discard_sectors << 9; |
87 | nr_sects -= max_discard_sectors; | 80 | nr_sects -= max_discard_sectors; |
@@ -103,13 +96,8 @@ int blkdev_issue_discard(struct block_device *bdev, sector_t sector, | |||
103 | ret = -EIO; | 96 | ret = -EIO; |
104 | bio_put(bio); | 97 | bio_put(bio); |
105 | } | 98 | } |
99 | |||
106 | return ret; | 100 | return ret; |
107 | out_free_page: | ||
108 | __free_page(page); | ||
109 | out_free_bio: | ||
110 | bio_put(bio); | ||
111 | out: | ||
112 | return -ENOMEM; | ||
113 | } | 101 | } |
114 | EXPORT_SYMBOL(blkdev_issue_discard); | 102 | EXPORT_SYMBOL(blkdev_issue_discard); |
115 | 103 | ||
@@ -157,7 +145,7 @@ static void bio_batch_end_io(struct bio *bio, int err) | |||
157 | int blkdev_issue_zeroout(struct block_device *bdev, sector_t sector, | 145 | int blkdev_issue_zeroout(struct block_device *bdev, sector_t sector, |
158 | sector_t nr_sects, gfp_t gfp_mask, unsigned long flags) | 146 | sector_t nr_sects, gfp_t gfp_mask, unsigned long flags) |
159 | { | 147 | { |
160 | int ret = 0; | 148 | int ret; |
161 | struct bio *bio; | 149 | struct bio *bio; |
162 | struct bio_batch bb; | 150 | struct bio_batch bb; |
163 | unsigned int sz, issued = 0; | 151 | unsigned int sz, issued = 0; |
@@ -175,11 +163,14 @@ int blkdev_issue_zeroout(struct block_device *bdev, sector_t sector, | |||
175 | return ret; | 163 | return ret; |
176 | } | 164 | } |
177 | submit: | 165 | submit: |
166 | ret = 0; | ||
178 | while (nr_sects != 0) { | 167 | while (nr_sects != 0) { |
179 | bio = bio_alloc(gfp_mask, | 168 | bio = bio_alloc(gfp_mask, |
180 | min(nr_sects, (sector_t)BIO_MAX_PAGES)); | 169 | min(nr_sects, (sector_t)BIO_MAX_PAGES)); |
181 | if (!bio) | 170 | if (!bio) { |
171 | ret = -ENOMEM; | ||
182 | break; | 172 | break; |
173 | } | ||
183 | 174 | ||
184 | bio->bi_sector = sector; | 175 | bio->bi_sector = sector; |
185 | bio->bi_bdev = bdev; | 176 | bio->bi_bdev = bdev; |
@@ -198,6 +189,7 @@ submit: | |||
198 | if (ret < (sz << 9)) | 189 | if (ret < (sz << 9)) |
199 | break; | 190 | break; |
200 | } | 191 | } |
192 | ret = 0; | ||
201 | issued++; | 193 | issued++; |
202 | submit_bio(WRITE, bio); | 194 | submit_bio(WRITE, bio); |
203 | } | 195 | } |
diff --git a/block/blk-map.c b/block/blk-map.c index 9083cf0180cc..c65d7593f7f1 100644 --- a/block/blk-map.c +++ b/block/blk-map.c | |||
@@ -307,7 +307,7 @@ int blk_rq_map_kern(struct request_queue *q, struct request *rq, void *kbuf, | |||
307 | return PTR_ERR(bio); | 307 | return PTR_ERR(bio); |
308 | 308 | ||
309 | if (rq_data_dir(rq) == WRITE) | 309 | if (rq_data_dir(rq) == WRITE) |
310 | bio->bi_rw |= (1 << BIO_RW); | 310 | bio->bi_rw |= (1 << REQ_WRITE); |
311 | 311 | ||
312 | if (do_copy) | 312 | if (do_copy) |
313 | rq->cmd_flags |= REQ_COPY_USER; | 313 | rq->cmd_flags |= REQ_COPY_USER; |
diff --git a/block/blk-merge.c b/block/blk-merge.c index 5e7dc9973458..3b0cd4249671 100644 --- a/block/blk-merge.c +++ b/block/blk-merge.c | |||
@@ -12,7 +12,6 @@ | |||
12 | static unsigned int __blk_recalc_rq_segments(struct request_queue *q, | 12 | static unsigned int __blk_recalc_rq_segments(struct request_queue *q, |
13 | struct bio *bio) | 13 | struct bio *bio) |
14 | { | 14 | { |
15 | unsigned int phys_size; | ||
16 | struct bio_vec *bv, *bvprv = NULL; | 15 | struct bio_vec *bv, *bvprv = NULL; |
17 | int cluster, i, high, highprv = 1; | 16 | int cluster, i, high, highprv = 1; |
18 | unsigned int seg_size, nr_phys_segs; | 17 | unsigned int seg_size, nr_phys_segs; |
@@ -24,7 +23,7 @@ static unsigned int __blk_recalc_rq_segments(struct request_queue *q, | |||
24 | fbio = bio; | 23 | fbio = bio; |
25 | cluster = test_bit(QUEUE_FLAG_CLUSTER, &q->queue_flags); | 24 | cluster = test_bit(QUEUE_FLAG_CLUSTER, &q->queue_flags); |
26 | seg_size = 0; | 25 | seg_size = 0; |
27 | phys_size = nr_phys_segs = 0; | 26 | nr_phys_segs = 0; |
28 | for_each_bio(bio) { | 27 | for_each_bio(bio) { |
29 | bio_for_each_segment(bv, bio, i) { | 28 | bio_for_each_segment(bv, bio, i) { |
30 | /* | 29 | /* |
@@ -180,7 +179,7 @@ new_segment: | |||
180 | } | 179 | } |
181 | 180 | ||
182 | if (q->dma_drain_size && q->dma_drain_needed(rq)) { | 181 | if (q->dma_drain_size && q->dma_drain_needed(rq)) { |
183 | if (rq->cmd_flags & REQ_RW) | 182 | if (rq->cmd_flags & REQ_WRITE) |
184 | memset(q->dma_drain_buffer, 0, q->dma_drain_size); | 183 | memset(q->dma_drain_buffer, 0, q->dma_drain_size); |
185 | 184 | ||
186 | sg->page_link &= ~0x02; | 185 | sg->page_link &= ~0x02; |
@@ -226,7 +225,7 @@ int ll_back_merge_fn(struct request_queue *q, struct request *req, | |||
226 | { | 225 | { |
227 | unsigned short max_sectors; | 226 | unsigned short max_sectors; |
228 | 227 | ||
229 | if (unlikely(blk_pc_request(req))) | 228 | if (unlikely(req->cmd_type == REQ_TYPE_BLOCK_PC)) |
230 | max_sectors = queue_max_hw_sectors(q); | 229 | max_sectors = queue_max_hw_sectors(q); |
231 | else | 230 | else |
232 | max_sectors = queue_max_sectors(q); | 231 | max_sectors = queue_max_sectors(q); |
@@ -250,7 +249,7 @@ int ll_front_merge_fn(struct request_queue *q, struct request *req, | |||
250 | { | 249 | { |
251 | unsigned short max_sectors; | 250 | unsigned short max_sectors; |
252 | 251 | ||
253 | if (unlikely(blk_pc_request(req))) | 252 | if (unlikely(req->cmd_type == REQ_TYPE_BLOCK_PC)) |
254 | max_sectors = queue_max_hw_sectors(q); | 253 | max_sectors = queue_max_hw_sectors(q); |
255 | else | 254 | else |
256 | max_sectors = queue_max_sectors(q); | 255 | max_sectors = queue_max_sectors(q); |
diff --git a/block/blk-settings.c b/block/blk-settings.c index f5ed5a1187ba..a234f4bf1d6f 100644 --- a/block/blk-settings.c +++ b/block/blk-settings.c | |||
@@ -37,6 +37,23 @@ void blk_queue_prep_rq(struct request_queue *q, prep_rq_fn *pfn) | |||
37 | EXPORT_SYMBOL(blk_queue_prep_rq); | 37 | EXPORT_SYMBOL(blk_queue_prep_rq); |
38 | 38 | ||
39 | /** | 39 | /** |
40 | * blk_queue_unprep_rq - set an unprepare_request function for queue | ||
41 | * @q: queue | ||
42 | * @ufn: unprepare_request function | ||
43 | * | ||
44 | * It's possible for a queue to register an unprepare_request callback | ||
45 | * which is invoked before the request is finally completed. The goal | ||
46 | * of the function is to deallocate any data that was allocated in the | ||
47 | * prepare_request callback. | ||
48 | * | ||
49 | */ | ||
50 | void blk_queue_unprep_rq(struct request_queue *q, unprep_rq_fn *ufn) | ||
51 | { | ||
52 | q->unprep_rq_fn = ufn; | ||
53 | } | ||
54 | EXPORT_SYMBOL(blk_queue_unprep_rq); | ||
55 | |||
56 | /** | ||
40 | * blk_queue_merge_bvec - set a merge_bvec function for queue | 57 | * blk_queue_merge_bvec - set a merge_bvec function for queue |
41 | * @q: queue | 58 | * @q: queue |
42 | * @mbfn: merge_bvec_fn | 59 | * @mbfn: merge_bvec_fn |
diff --git a/block/blk-sysfs.c b/block/blk-sysfs.c index 306759bbdf1b..001ab18078f5 100644 --- a/block/blk-sysfs.c +++ b/block/blk-sysfs.c | |||
@@ -180,26 +180,36 @@ static ssize_t queue_max_hw_sectors_show(struct request_queue *q, char *page) | |||
180 | return queue_var_show(max_hw_sectors_kb, (page)); | 180 | return queue_var_show(max_hw_sectors_kb, (page)); |
181 | } | 181 | } |
182 | 182 | ||
183 | static ssize_t queue_nonrot_show(struct request_queue *q, char *page) | 183 | #define QUEUE_SYSFS_BIT_FNS(name, flag, neg) \ |
184 | { | 184 | static ssize_t \ |
185 | return queue_var_show(!blk_queue_nonrot(q), page); | 185 | queue_show_##name(struct request_queue *q, char *page) \ |
186 | { \ | ||
187 | int bit; \ | ||
188 | bit = test_bit(QUEUE_FLAG_##flag, &q->queue_flags); \ | ||
189 | return queue_var_show(neg ? !bit : bit, page); \ | ||
190 | } \ | ||
191 | static ssize_t \ | ||
192 | queue_store_##name(struct request_queue *q, const char *page, size_t count) \ | ||
193 | { \ | ||
194 | unsigned long val; \ | ||
195 | ssize_t ret; \ | ||
196 | ret = queue_var_store(&val, page, count); \ | ||
197 | if (neg) \ | ||
198 | val = !val; \ | ||
199 | \ | ||
200 | spin_lock_irq(q->queue_lock); \ | ||
201 | if (val) \ | ||
202 | queue_flag_set(QUEUE_FLAG_##flag, q); \ | ||
203 | else \ | ||
204 | queue_flag_clear(QUEUE_FLAG_##flag, q); \ | ||
205 | spin_unlock_irq(q->queue_lock); \ | ||
206 | return ret; \ | ||
186 | } | 207 | } |
187 | 208 | ||
188 | static ssize_t queue_nonrot_store(struct request_queue *q, const char *page, | 209 | QUEUE_SYSFS_BIT_FNS(nonrot, NONROT, 1); |
189 | size_t count) | 210 | QUEUE_SYSFS_BIT_FNS(random, ADD_RANDOM, 0); |
190 | { | 211 | QUEUE_SYSFS_BIT_FNS(iostats, IO_STAT, 0); |
191 | unsigned long nm; | 212 | #undef QUEUE_SYSFS_BIT_FNS |
192 | ssize_t ret = queue_var_store(&nm, page, count); | ||
193 | |||
194 | spin_lock_irq(q->queue_lock); | ||
195 | if (nm) | ||
196 | queue_flag_clear(QUEUE_FLAG_NONROT, q); | ||
197 | else | ||
198 | queue_flag_set(QUEUE_FLAG_NONROT, q); | ||
199 | spin_unlock_irq(q->queue_lock); | ||
200 | |||
201 | return ret; | ||
202 | } | ||
203 | 213 | ||
204 | static ssize_t queue_nomerges_show(struct request_queue *q, char *page) | 214 | static ssize_t queue_nomerges_show(struct request_queue *q, char *page) |
205 | { | 215 | { |
@@ -250,27 +260,6 @@ queue_rq_affinity_store(struct request_queue *q, const char *page, size_t count) | |||
250 | return ret; | 260 | return ret; |
251 | } | 261 | } |
252 | 262 | ||
253 | static ssize_t queue_iostats_show(struct request_queue *q, char *page) | ||
254 | { | ||
255 | return queue_var_show(blk_queue_io_stat(q), page); | ||
256 | } | ||
257 | |||
258 | static ssize_t queue_iostats_store(struct request_queue *q, const char *page, | ||
259 | size_t count) | ||
260 | { | ||
261 | unsigned long stats; | ||
262 | ssize_t ret = queue_var_store(&stats, page, count); | ||
263 | |||
264 | spin_lock_irq(q->queue_lock); | ||
265 | if (stats) | ||
266 | queue_flag_set(QUEUE_FLAG_IO_STAT, q); | ||
267 | else | ||
268 | queue_flag_clear(QUEUE_FLAG_IO_STAT, q); | ||
269 | spin_unlock_irq(q->queue_lock); | ||
270 | |||
271 | return ret; | ||
272 | } | ||
273 | |||
274 | static struct queue_sysfs_entry queue_requests_entry = { | 263 | static struct queue_sysfs_entry queue_requests_entry = { |
275 | .attr = {.name = "nr_requests", .mode = S_IRUGO | S_IWUSR }, | 264 | .attr = {.name = "nr_requests", .mode = S_IRUGO | S_IWUSR }, |
276 | .show = queue_requests_show, | 265 | .show = queue_requests_show, |
@@ -352,8 +341,8 @@ static struct queue_sysfs_entry queue_discard_zeroes_data_entry = { | |||
352 | 341 | ||
353 | static struct queue_sysfs_entry queue_nonrot_entry = { | 342 | static struct queue_sysfs_entry queue_nonrot_entry = { |
354 | .attr = {.name = "rotational", .mode = S_IRUGO | S_IWUSR }, | 343 | .attr = {.name = "rotational", .mode = S_IRUGO | S_IWUSR }, |
355 | .show = queue_nonrot_show, | 344 | .show = queue_show_nonrot, |
356 | .store = queue_nonrot_store, | 345 | .store = queue_store_nonrot, |
357 | }; | 346 | }; |
358 | 347 | ||
359 | static struct queue_sysfs_entry queue_nomerges_entry = { | 348 | static struct queue_sysfs_entry queue_nomerges_entry = { |
@@ -370,8 +359,14 @@ static struct queue_sysfs_entry queue_rq_affinity_entry = { | |||
370 | 359 | ||
371 | static struct queue_sysfs_entry queue_iostats_entry = { | 360 | static struct queue_sysfs_entry queue_iostats_entry = { |
372 | .attr = {.name = "iostats", .mode = S_IRUGO | S_IWUSR }, | 361 | .attr = {.name = "iostats", .mode = S_IRUGO | S_IWUSR }, |
373 | .show = queue_iostats_show, | 362 | .show = queue_show_iostats, |
374 | .store = queue_iostats_store, | 363 | .store = queue_store_iostats, |
364 | }; | ||
365 | |||
366 | static struct queue_sysfs_entry queue_random_entry = { | ||
367 | .attr = {.name = "add_random", .mode = S_IRUGO | S_IWUSR }, | ||
368 | .show = queue_show_random, | ||
369 | .store = queue_store_random, | ||
375 | }; | 370 | }; |
376 | 371 | ||
377 | static struct attribute *default_attrs[] = { | 372 | static struct attribute *default_attrs[] = { |
@@ -394,6 +389,7 @@ static struct attribute *default_attrs[] = { | |||
394 | &queue_nomerges_entry.attr, | 389 | &queue_nomerges_entry.attr, |
395 | &queue_rq_affinity_entry.attr, | 390 | &queue_rq_affinity_entry.attr, |
396 | &queue_iostats_entry.attr, | 391 | &queue_iostats_entry.attr, |
392 | &queue_random_entry.attr, | ||
397 | NULL, | 393 | NULL, |
398 | }; | 394 | }; |
399 | 395 | ||
diff --git a/block/blk.h b/block/blk.h index 5ee3d7e72feb..6e7dc87141e4 100644 --- a/block/blk.h +++ b/block/blk.h | |||
@@ -161,8 +161,10 @@ static inline int blk_cpu_to_group(int cpu) | |||
161 | */ | 161 | */ |
162 | static inline int blk_do_io_stat(struct request *rq) | 162 | static inline int blk_do_io_stat(struct request *rq) |
163 | { | 163 | { |
164 | return rq->rq_disk && blk_rq_io_stat(rq) && | 164 | return rq->rq_disk && |
165 | (blk_fs_request(rq) || blk_discard_rq(rq)); | 165 | (rq->cmd_flags & REQ_IO_STAT) && |
166 | (rq->cmd_type == REQ_TYPE_FS || | ||
167 | (rq->cmd_flags & REQ_DISCARD)); | ||
166 | } | 168 | } |
167 | 169 | ||
168 | #endif | 170 | #endif |
diff --git a/block/cfq-iosched.c b/block/cfq-iosched.c index 7982b830db58..eb4086f7dfef 100644 --- a/block/cfq-iosched.c +++ b/block/cfq-iosched.c | |||
@@ -458,7 +458,7 @@ static inline struct cfq_data *cic_to_cfqd(struct cfq_io_context *cic) | |||
458 | */ | 458 | */ |
459 | static inline bool cfq_bio_sync(struct bio *bio) | 459 | static inline bool cfq_bio_sync(struct bio *bio) |
460 | { | 460 | { |
461 | return bio_data_dir(bio) == READ || bio_rw_flagged(bio, BIO_RW_SYNCIO); | 461 | return bio_data_dir(bio) == READ || (bio->bi_rw & REQ_SYNC); |
462 | } | 462 | } |
463 | 463 | ||
464 | /* | 464 | /* |
@@ -646,9 +646,10 @@ cfq_choose_req(struct cfq_data *cfqd, struct request *rq1, struct request *rq2, | |||
646 | return rq1; | 646 | return rq1; |
647 | else if (rq_is_sync(rq2) && !rq_is_sync(rq1)) | 647 | else if (rq_is_sync(rq2) && !rq_is_sync(rq1)) |
648 | return rq2; | 648 | return rq2; |
649 | if (rq_is_meta(rq1) && !rq_is_meta(rq2)) | 649 | if ((rq1->cmd_flags & REQ_META) && !(rq2->cmd_flags & REQ_META)) |
650 | return rq1; | 650 | return rq1; |
651 | else if (rq_is_meta(rq2) && !rq_is_meta(rq1)) | 651 | else if ((rq2->cmd_flags & REQ_META) && |
652 | !(rq1->cmd_flags & REQ_META)) | ||
652 | return rq2; | 653 | return rq2; |
653 | 654 | ||
654 | s1 = blk_rq_pos(rq1); | 655 | s1 = blk_rq_pos(rq1); |
@@ -1484,7 +1485,7 @@ static void cfq_remove_request(struct request *rq) | |||
1484 | cfqq->cfqd->rq_queued--; | 1485 | cfqq->cfqd->rq_queued--; |
1485 | cfq_blkiocg_update_io_remove_stats(&(RQ_CFQG(rq))->blkg, | 1486 | cfq_blkiocg_update_io_remove_stats(&(RQ_CFQG(rq))->blkg, |
1486 | rq_data_dir(rq), rq_is_sync(rq)); | 1487 | rq_data_dir(rq), rq_is_sync(rq)); |
1487 | if (rq_is_meta(rq)) { | 1488 | if (rq->cmd_flags & REQ_META) { |
1488 | WARN_ON(!cfqq->meta_pending); | 1489 | WARN_ON(!cfqq->meta_pending); |
1489 | cfqq->meta_pending--; | 1490 | cfqq->meta_pending--; |
1490 | } | 1491 | } |
@@ -3176,7 +3177,7 @@ cfq_should_preempt(struct cfq_data *cfqd, struct cfq_queue *new_cfqq, | |||
3176 | * So both queues are sync. Let the new request get disk time if | 3177 | * So both queues are sync. Let the new request get disk time if |
3177 | * it's a metadata request and the current queue is doing regular IO. | 3178 | * it's a metadata request and the current queue is doing regular IO. |
3178 | */ | 3179 | */ |
3179 | if (rq_is_meta(rq) && !cfqq->meta_pending) | 3180 | if ((rq->cmd_flags & REQ_META) && !cfqq->meta_pending) |
3180 | return true; | 3181 | return true; |
3181 | 3182 | ||
3182 | /* | 3183 | /* |
@@ -3230,7 +3231,7 @@ cfq_rq_enqueued(struct cfq_data *cfqd, struct cfq_queue *cfqq, | |||
3230 | struct cfq_io_context *cic = RQ_CIC(rq); | 3231 | struct cfq_io_context *cic = RQ_CIC(rq); |
3231 | 3232 | ||
3232 | cfqd->rq_queued++; | 3233 | cfqd->rq_queued++; |
3233 | if (rq_is_meta(rq)) | 3234 | if (rq->cmd_flags & REQ_META) |
3234 | cfqq->meta_pending++; | 3235 | cfqq->meta_pending++; |
3235 | 3236 | ||
3236 | cfq_update_io_thinktime(cfqd, cic); | 3237 | cfq_update_io_thinktime(cfqd, cic); |
@@ -3365,7 +3366,8 @@ static void cfq_completed_request(struct request_queue *q, struct request *rq) | |||
3365 | unsigned long now; | 3366 | unsigned long now; |
3366 | 3367 | ||
3367 | now = jiffies; | 3368 | now = jiffies; |
3368 | cfq_log_cfqq(cfqd, cfqq, "complete rqnoidle %d", !!rq_noidle(rq)); | 3369 | cfq_log_cfqq(cfqd, cfqq, "complete rqnoidle %d", |
3370 | !!(rq->cmd_flags & REQ_NOIDLE)); | ||
3369 | 3371 | ||
3370 | cfq_update_hw_tag(cfqd); | 3372 | cfq_update_hw_tag(cfqd); |
3371 | 3373 | ||
@@ -3419,11 +3421,12 @@ static void cfq_completed_request(struct request_queue *q, struct request *rq) | |||
3419 | cfq_slice_expired(cfqd, 1); | 3421 | cfq_slice_expired(cfqd, 1); |
3420 | else if (sync && cfqq_empty && | 3422 | else if (sync && cfqq_empty && |
3421 | !cfq_close_cooperator(cfqd, cfqq)) { | 3423 | !cfq_close_cooperator(cfqd, cfqq)) { |
3422 | cfqd->noidle_tree_requires_idle |= !rq_noidle(rq); | 3424 | cfqd->noidle_tree_requires_idle |= |
3425 | !(rq->cmd_flags & REQ_NOIDLE); | ||
3423 | /* | 3426 | /* |
3424 | * Idling is enabled for SYNC_WORKLOAD. | 3427 | * Idling is enabled for SYNC_WORKLOAD. |
3425 | * SYNC_NOIDLE_WORKLOAD idles at the end of the tree | 3428 | * SYNC_NOIDLE_WORKLOAD idles at the end of the tree |
3426 | * only if we processed at least one !rq_noidle request | 3429 | * only if we processed at least one !REQ_NOIDLE request |
3427 | */ | 3430 | */ |
3428 | if (cfqd->serving_type == SYNC_WORKLOAD | 3431 | if (cfqd->serving_type == SYNC_WORKLOAD |
3429 | || cfqd->noidle_tree_requires_idle | 3432 | || cfqd->noidle_tree_requires_idle |
diff --git a/block/compat_ioctl.c b/block/compat_ioctl.c index f26051f44681..d53085637731 100644 --- a/block/compat_ioctl.c +++ b/block/compat_ioctl.c | |||
@@ -535,56 +535,6 @@ out: | |||
535 | return err; | 535 | return err; |
536 | } | 536 | } |
537 | 537 | ||
538 | struct compat_blk_user_trace_setup { | ||
539 | char name[32]; | ||
540 | u16 act_mask; | ||
541 | u32 buf_size; | ||
542 | u32 buf_nr; | ||
543 | compat_u64 start_lba; | ||
544 | compat_u64 end_lba; | ||
545 | u32 pid; | ||
546 | }; | ||
547 | #define BLKTRACESETUP32 _IOWR(0x12, 115, struct compat_blk_user_trace_setup) | ||
548 | |||
549 | static int compat_blk_trace_setup(struct block_device *bdev, char __user *arg) | ||
550 | { | ||
551 | struct blk_user_trace_setup buts; | ||
552 | struct compat_blk_user_trace_setup cbuts; | ||
553 | struct request_queue *q; | ||
554 | char b[BDEVNAME_SIZE]; | ||
555 | int ret; | ||
556 | |||
557 | q = bdev_get_queue(bdev); | ||
558 | if (!q) | ||
559 | return -ENXIO; | ||
560 | |||
561 | if (copy_from_user(&cbuts, arg, sizeof(cbuts))) | ||
562 | return -EFAULT; | ||
563 | |||
564 | bdevname(bdev, b); | ||
565 | |||
566 | buts = (struct blk_user_trace_setup) { | ||
567 | .act_mask = cbuts.act_mask, | ||
568 | .buf_size = cbuts.buf_size, | ||
569 | .buf_nr = cbuts.buf_nr, | ||
570 | .start_lba = cbuts.start_lba, | ||
571 | .end_lba = cbuts.end_lba, | ||
572 | .pid = cbuts.pid, | ||
573 | }; | ||
574 | memcpy(&buts.name, &cbuts.name, 32); | ||
575 | |||
576 | mutex_lock(&bdev->bd_mutex); | ||
577 | ret = do_blk_trace_setup(q, b, bdev->bd_dev, bdev, &buts); | ||
578 | mutex_unlock(&bdev->bd_mutex); | ||
579 | if (ret) | ||
580 | return ret; | ||
581 | |||
582 | if (copy_to_user(arg, &buts.name, 32)) | ||
583 | return -EFAULT; | ||
584 | |||
585 | return 0; | ||
586 | } | ||
587 | |||
588 | static int compat_blkdev_driver_ioctl(struct block_device *bdev, fmode_t mode, | 538 | static int compat_blkdev_driver_ioctl(struct block_device *bdev, fmode_t mode, |
589 | unsigned cmd, unsigned long arg) | 539 | unsigned cmd, unsigned long arg) |
590 | { | 540 | { |
@@ -802,16 +752,10 @@ long compat_blkdev_ioctl(struct file *file, unsigned cmd, unsigned long arg) | |||
802 | return compat_put_u64(arg, bdev->bd_inode->i_size); | 752 | return compat_put_u64(arg, bdev->bd_inode->i_size); |
803 | 753 | ||
804 | case BLKTRACESETUP32: | 754 | case BLKTRACESETUP32: |
805 | lock_kernel(); | ||
806 | ret = compat_blk_trace_setup(bdev, compat_ptr(arg)); | ||
807 | unlock_kernel(); | ||
808 | return ret; | ||
809 | case BLKTRACESTART: /* compatible */ | 755 | case BLKTRACESTART: /* compatible */ |
810 | case BLKTRACESTOP: /* compatible */ | 756 | case BLKTRACESTOP: /* compatible */ |
811 | case BLKTRACETEARDOWN: /* compatible */ | 757 | case BLKTRACETEARDOWN: /* compatible */ |
812 | lock_kernel(); | ||
813 | ret = blk_trace_ioctl(bdev, cmd, compat_ptr(arg)); | 758 | ret = blk_trace_ioctl(bdev, cmd, compat_ptr(arg)); |
814 | unlock_kernel(); | ||
815 | return ret; | 759 | return ret; |
816 | default: | 760 | default: |
817 | if (disk->fops->compat_ioctl) | 761 | if (disk->fops->compat_ioctl) |
diff --git a/block/elevator.c b/block/elevator.c index 923a9139106c..816a7c8d6394 100644 --- a/block/elevator.c +++ b/block/elevator.c | |||
@@ -79,8 +79,7 @@ int elv_rq_merge_ok(struct request *rq, struct bio *bio) | |||
79 | /* | 79 | /* |
80 | * Don't merge file system requests and discard requests | 80 | * Don't merge file system requests and discard requests |
81 | */ | 81 | */ |
82 | if (bio_rw_flagged(bio, BIO_RW_DISCARD) != | 82 | if ((bio->bi_rw & REQ_DISCARD) != (rq->bio->bi_rw & REQ_DISCARD)) |
83 | bio_rw_flagged(rq->bio, BIO_RW_DISCARD)) | ||
84 | return 0; | 83 | return 0; |
85 | 84 | ||
86 | /* | 85 | /* |
@@ -428,7 +427,8 @@ void elv_dispatch_sort(struct request_queue *q, struct request *rq) | |||
428 | list_for_each_prev(entry, &q->queue_head) { | 427 | list_for_each_prev(entry, &q->queue_head) { |
429 | struct request *pos = list_entry_rq(entry); | 428 | struct request *pos = list_entry_rq(entry); |
430 | 429 | ||
431 | if (blk_discard_rq(rq) != blk_discard_rq(pos)) | 430 | if ((rq->cmd_flags & REQ_DISCARD) != |
431 | (pos->cmd_flags & REQ_DISCARD)) | ||
432 | break; | 432 | break; |
433 | if (rq_data_dir(rq) != rq_data_dir(pos)) | 433 | if (rq_data_dir(rq) != rq_data_dir(pos)) |
434 | break; | 434 | break; |
@@ -558,7 +558,7 @@ void elv_requeue_request(struct request_queue *q, struct request *rq) | |||
558 | */ | 558 | */ |
559 | if (blk_account_rq(rq)) { | 559 | if (blk_account_rq(rq)) { |
560 | q->in_flight[rq_is_sync(rq)]--; | 560 | q->in_flight[rq_is_sync(rq)]--; |
561 | if (blk_sorted_rq(rq)) | 561 | if (rq->cmd_flags & REQ_SORTED) |
562 | elv_deactivate_rq(q, rq); | 562 | elv_deactivate_rq(q, rq); |
563 | } | 563 | } |
564 | 564 | ||
@@ -644,7 +644,8 @@ void elv_insert(struct request_queue *q, struct request *rq, int where) | |||
644 | break; | 644 | break; |
645 | 645 | ||
646 | case ELEVATOR_INSERT_SORT: | 646 | case ELEVATOR_INSERT_SORT: |
647 | BUG_ON(!blk_fs_request(rq) && !blk_discard_rq(rq)); | 647 | BUG_ON(rq->cmd_type != REQ_TYPE_FS && |
648 | !(rq->cmd_flags & REQ_DISCARD)); | ||
648 | rq->cmd_flags |= REQ_SORTED; | 649 | rq->cmd_flags |= REQ_SORTED; |
649 | q->nr_sorted++; | 650 | q->nr_sorted++; |
650 | if (rq_mergeable(rq)) { | 651 | if (rq_mergeable(rq)) { |
@@ -716,7 +717,7 @@ void __elv_add_request(struct request_queue *q, struct request *rq, int where, | |||
716 | /* | 717 | /* |
717 | * toggle ordered color | 718 | * toggle ordered color |
718 | */ | 719 | */ |
719 | if (blk_barrier_rq(rq)) | 720 | if (rq->cmd_flags & REQ_HARDBARRIER) |
720 | q->ordcolor ^= 1; | 721 | q->ordcolor ^= 1; |
721 | 722 | ||
722 | /* | 723 | /* |
@@ -729,7 +730,8 @@ void __elv_add_request(struct request_queue *q, struct request *rq, int where, | |||
729 | * this request is scheduling boundary, update | 730 | * this request is scheduling boundary, update |
730 | * end_sector | 731 | * end_sector |
731 | */ | 732 | */ |
732 | if (blk_fs_request(rq) || blk_discard_rq(rq)) { | 733 | if (rq->cmd_type == REQ_TYPE_FS || |
734 | (rq->cmd_flags & REQ_DISCARD)) { | ||
733 | q->end_sector = rq_end_sector(rq); | 735 | q->end_sector = rq_end_sector(rq); |
734 | q->boundary_rq = rq; | 736 | q->boundary_rq = rq; |
735 | } | 737 | } |
@@ -843,7 +845,8 @@ void elv_completed_request(struct request_queue *q, struct request *rq) | |||
843 | */ | 845 | */ |
844 | if (blk_account_rq(rq)) { | 846 | if (blk_account_rq(rq)) { |
845 | q->in_flight[rq_is_sync(rq)]--; | 847 | q->in_flight[rq_is_sync(rq)]--; |
846 | if (blk_sorted_rq(rq) && e->ops->elevator_completed_req_fn) | 848 | if ((rq->cmd_flags & REQ_SORTED) && |
849 | e->ops->elevator_completed_req_fn) | ||
847 | e->ops->elevator_completed_req_fn(q, rq); | 850 | e->ops->elevator_completed_req_fn(q, rq); |
848 | } | 851 | } |
849 | 852 | ||
diff --git a/block/ioctl.c b/block/ioctl.c index e8eb679f2f9b..09fd7f1ef23a 100644 --- a/block/ioctl.c +++ b/block/ioctl.c | |||
@@ -163,18 +163,10 @@ int __blkdev_driver_ioctl(struct block_device *bdev, fmode_t mode, | |||
163 | unsigned cmd, unsigned long arg) | 163 | unsigned cmd, unsigned long arg) |
164 | { | 164 | { |
165 | struct gendisk *disk = bdev->bd_disk; | 165 | struct gendisk *disk = bdev->bd_disk; |
166 | int ret; | ||
167 | 166 | ||
168 | if (disk->fops->ioctl) | 167 | if (disk->fops->ioctl) |
169 | return disk->fops->ioctl(bdev, mode, cmd, arg); | 168 | return disk->fops->ioctl(bdev, mode, cmd, arg); |
170 | 169 | ||
171 | if (disk->fops->locked_ioctl) { | ||
172 | lock_kernel(); | ||
173 | ret = disk->fops->locked_ioctl(bdev, mode, cmd, arg); | ||
174 | unlock_kernel(); | ||
175 | return ret; | ||
176 | } | ||
177 | |||
178 | return -ENOTTY; | 170 | return -ENOTTY; |
179 | } | 171 | } |
180 | /* | 172 | /* |
@@ -185,8 +177,7 @@ int __blkdev_driver_ioctl(struct block_device *bdev, fmode_t mode, | |||
185 | EXPORT_SYMBOL_GPL(__blkdev_driver_ioctl); | 177 | EXPORT_SYMBOL_GPL(__blkdev_driver_ioctl); |
186 | 178 | ||
187 | /* | 179 | /* |
188 | * always keep this in sync with compat_blkdev_ioctl() and | 180 | * always keep this in sync with compat_blkdev_ioctl() |
189 | * compat_blkdev_locked_ioctl() | ||
190 | */ | 181 | */ |
191 | int blkdev_ioctl(struct block_device *bdev, fmode_t mode, unsigned cmd, | 182 | int blkdev_ioctl(struct block_device *bdev, fmode_t mode, unsigned cmd, |
192 | unsigned long arg) | 183 | unsigned long arg) |
@@ -206,10 +197,8 @@ int blkdev_ioctl(struct block_device *bdev, fmode_t mode, unsigned cmd, | |||
206 | if (ret != -EINVAL && ret != -ENOTTY) | 197 | if (ret != -EINVAL && ret != -ENOTTY) |
207 | return ret; | 198 | return ret; |
208 | 199 | ||
209 | lock_kernel(); | ||
210 | fsync_bdev(bdev); | 200 | fsync_bdev(bdev); |
211 | invalidate_bdev(bdev); | 201 | invalidate_bdev(bdev); |
212 | unlock_kernel(); | ||
213 | return 0; | 202 | return 0; |
214 | 203 | ||
215 | case BLKROSET: | 204 | case BLKROSET: |
@@ -221,9 +210,7 @@ int blkdev_ioctl(struct block_device *bdev, fmode_t mode, unsigned cmd, | |||
221 | return -EACCES; | 210 | return -EACCES; |
222 | if (get_user(n, (int __user *)(arg))) | 211 | if (get_user(n, (int __user *)(arg))) |
223 | return -EFAULT; | 212 | return -EFAULT; |
224 | lock_kernel(); | ||
225 | set_device_ro(bdev, n); | 213 | set_device_ro(bdev, n); |
226 | unlock_kernel(); | ||
227 | return 0; | 214 | return 0; |
228 | 215 | ||
229 | case BLKDISCARD: { | 216 | case BLKDISCARD: { |
@@ -309,14 +296,10 @@ int blkdev_ioctl(struct block_device *bdev, fmode_t mode, unsigned cmd, | |||
309 | bd_release(bdev); | 296 | bd_release(bdev); |
310 | return ret; | 297 | return ret; |
311 | case BLKPG: | 298 | case BLKPG: |
312 | lock_kernel(); | ||
313 | ret = blkpg_ioctl(bdev, (struct blkpg_ioctl_arg __user *) arg); | 299 | ret = blkpg_ioctl(bdev, (struct blkpg_ioctl_arg __user *) arg); |
314 | unlock_kernel(); | ||
315 | break; | 300 | break; |
316 | case BLKRRPART: | 301 | case BLKRRPART: |
317 | lock_kernel(); | ||
318 | ret = blkdev_reread_part(bdev); | 302 | ret = blkdev_reread_part(bdev); |
319 | unlock_kernel(); | ||
320 | break; | 303 | break; |
321 | case BLKGETSIZE: | 304 | case BLKGETSIZE: |
322 | size = bdev->bd_inode->i_size; | 305 | size = bdev->bd_inode->i_size; |
@@ -329,9 +312,7 @@ int blkdev_ioctl(struct block_device *bdev, fmode_t mode, unsigned cmd, | |||
329 | case BLKTRACESTOP: | 312 | case BLKTRACESTOP: |
330 | case BLKTRACESETUP: | 313 | case BLKTRACESETUP: |
331 | case BLKTRACETEARDOWN: | 314 | case BLKTRACETEARDOWN: |
332 | lock_kernel(); | ||
333 | ret = blk_trace_ioctl(bdev, cmd, (char __user *) arg); | 315 | ret = blk_trace_ioctl(bdev, cmd, (char __user *) arg); |
334 | unlock_kernel(); | ||
335 | break; | 316 | break; |
336 | default: | 317 | default: |
337 | ret = __blkdev_driver_ioctl(bdev, mode, cmd, arg); | 318 | ret = __blkdev_driver_ioctl(bdev, mode, cmd, arg); |
diff --git a/drivers/ata/libata-scsi.c b/drivers/ata/libata-scsi.c index d75c9c479d1a..a89172c100f5 100644 --- a/drivers/ata/libata-scsi.c +++ b/drivers/ata/libata-scsi.c | |||
@@ -1111,10 +1111,10 @@ static void ata_scsi_sdev_config(struct scsi_device *sdev) | |||
1111 | */ | 1111 | */ |
1112 | static int atapi_drain_needed(struct request *rq) | 1112 | static int atapi_drain_needed(struct request *rq) |
1113 | { | 1113 | { |
1114 | if (likely(!blk_pc_request(rq))) | 1114 | if (likely(rq->cmd_type != REQ_TYPE_BLOCK_PC)) |
1115 | return 0; | 1115 | return 0; |
1116 | 1116 | ||
1117 | if (!blk_rq_bytes(rq) || (rq->cmd_flags & REQ_RW)) | 1117 | if (!blk_rq_bytes(rq) || (rq->cmd_flags & REQ_WRITE)) |
1118 | return 0; | 1118 | return 0; |
1119 | 1119 | ||
1120 | return atapi_cmd_type(rq->cmd[0]) == ATAPI_MISC; | 1120 | return atapi_cmd_type(rq->cmd[0]) == ATAPI_MISC; |
diff --git a/drivers/block/DAC960.c b/drivers/block/DAC960.c index c5f22bb0a48e..4e2c367fec11 100644 --- a/drivers/block/DAC960.c +++ b/drivers/block/DAC960.c | |||
@@ -79,23 +79,28 @@ static int DAC960_open(struct block_device *bdev, fmode_t mode) | |||
79 | struct gendisk *disk = bdev->bd_disk; | 79 | struct gendisk *disk = bdev->bd_disk; |
80 | DAC960_Controller_T *p = disk->queue->queuedata; | 80 | DAC960_Controller_T *p = disk->queue->queuedata; |
81 | int drive_nr = (long)disk->private_data; | 81 | int drive_nr = (long)disk->private_data; |
82 | int ret = -ENXIO; | ||
82 | 83 | ||
84 | lock_kernel(); | ||
83 | if (p->FirmwareType == DAC960_V1_Controller) { | 85 | if (p->FirmwareType == DAC960_V1_Controller) { |
84 | if (p->V1.LogicalDriveInformation[drive_nr]. | 86 | if (p->V1.LogicalDriveInformation[drive_nr]. |
85 | LogicalDriveState == DAC960_V1_LogicalDrive_Offline) | 87 | LogicalDriveState == DAC960_V1_LogicalDrive_Offline) |
86 | return -ENXIO; | 88 | goto out; |
87 | } else { | 89 | } else { |
88 | DAC960_V2_LogicalDeviceInfo_T *i = | 90 | DAC960_V2_LogicalDeviceInfo_T *i = |
89 | p->V2.LogicalDeviceInformation[drive_nr]; | 91 | p->V2.LogicalDeviceInformation[drive_nr]; |
90 | if (!i || i->LogicalDeviceState == DAC960_V2_LogicalDevice_Offline) | 92 | if (!i || i->LogicalDeviceState == DAC960_V2_LogicalDevice_Offline) |
91 | return -ENXIO; | 93 | goto out; |
92 | } | 94 | } |
93 | 95 | ||
94 | check_disk_change(bdev); | 96 | check_disk_change(bdev); |
95 | 97 | ||
96 | if (!get_capacity(p->disks[drive_nr])) | 98 | if (!get_capacity(p->disks[drive_nr])) |
97 | return -ENXIO; | 99 | goto out; |
98 | return 0; | 100 | ret = 0; |
101 | out: | ||
102 | unlock_kernel(); | ||
103 | return ret; | ||
99 | } | 104 | } |
100 | 105 | ||
101 | static int DAC960_getgeo(struct block_device *bdev, struct hd_geometry *geo) | 106 | static int DAC960_getgeo(struct block_device *bdev, struct hd_geometry *geo) |
diff --git a/drivers/block/amiflop.c b/drivers/block/amiflop.c index 832798aa14f6..76f114f0bba3 100644 --- a/drivers/block/amiflop.c +++ b/drivers/block/amiflop.c | |||
@@ -60,6 +60,7 @@ | |||
60 | #include <linux/hdreg.h> | 60 | #include <linux/hdreg.h> |
61 | #include <linux/delay.h> | 61 | #include <linux/delay.h> |
62 | #include <linux/init.h> | 62 | #include <linux/init.h> |
63 | #include <linux/smp_lock.h> | ||
63 | #include <linux/amifdreg.h> | 64 | #include <linux/amifdreg.h> |
64 | #include <linux/amifd.h> | 65 | #include <linux/amifd.h> |
65 | #include <linux/buffer_head.h> | 66 | #include <linux/buffer_head.h> |
@@ -1423,7 +1424,7 @@ static int fd_getgeo(struct block_device *bdev, struct hd_geometry *geo) | |||
1423 | return 0; | 1424 | return 0; |
1424 | } | 1425 | } |
1425 | 1426 | ||
1426 | static int fd_ioctl(struct block_device *bdev, fmode_t mode, | 1427 | static int fd_locked_ioctl(struct block_device *bdev, fmode_t mode, |
1427 | unsigned int cmd, unsigned long param) | 1428 | unsigned int cmd, unsigned long param) |
1428 | { | 1429 | { |
1429 | struct amiga_floppy_struct *p = bdev->bd_disk->private_data; | 1430 | struct amiga_floppy_struct *p = bdev->bd_disk->private_data; |
@@ -1500,6 +1501,18 @@ static int fd_ioctl(struct block_device *bdev, fmode_t mode, | |||
1500 | return 0; | 1501 | return 0; |
1501 | } | 1502 | } |
1502 | 1503 | ||
1504 | static int fd_ioctl(struct block_device *bdev, fmode_t mode, | ||
1505 | unsigned int cmd, unsigned long param) | ||
1506 | { | ||
1507 | int ret; | ||
1508 | |||
1509 | lock_kernel(); | ||
1510 | ret = fd_locked_ioctl(bdev, mode, cmd, param); | ||
1511 | unlock_kernel(); | ||
1512 | |||
1513 | return ret; | ||
1514 | } | ||
1515 | |||
1503 | static void fd_probe(int dev) | 1516 | static void fd_probe(int dev) |
1504 | { | 1517 | { |
1505 | unsigned long code; | 1518 | unsigned long code; |
@@ -1542,10 +1555,13 @@ static int floppy_open(struct block_device *bdev, fmode_t mode) | |||
1542 | int old_dev; | 1555 | int old_dev; |
1543 | unsigned long flags; | 1556 | unsigned long flags; |
1544 | 1557 | ||
1558 | lock_kernel(); | ||
1545 | old_dev = fd_device[drive]; | 1559 | old_dev = fd_device[drive]; |
1546 | 1560 | ||
1547 | if (fd_ref[drive] && old_dev != system) | 1561 | if (fd_ref[drive] && old_dev != system) { |
1562 | unlock_kernel(); | ||
1548 | return -EBUSY; | 1563 | return -EBUSY; |
1564 | } | ||
1549 | 1565 | ||
1550 | if (mode & (FMODE_READ|FMODE_WRITE)) { | 1566 | if (mode & (FMODE_READ|FMODE_WRITE)) { |
1551 | check_disk_change(bdev); | 1567 | check_disk_change(bdev); |
@@ -1558,8 +1574,10 @@ static int floppy_open(struct block_device *bdev, fmode_t mode) | |||
1558 | fd_deselect (drive); | 1574 | fd_deselect (drive); |
1559 | rel_fdc(); | 1575 | rel_fdc(); |
1560 | 1576 | ||
1561 | if (wrprot) | 1577 | if (wrprot) { |
1578 | unlock_kernel(); | ||
1562 | return -EROFS; | 1579 | return -EROFS; |
1580 | } | ||
1563 | } | 1581 | } |
1564 | } | 1582 | } |
1565 | 1583 | ||
@@ -1576,6 +1594,7 @@ static int floppy_open(struct block_device *bdev, fmode_t mode) | |||
1576 | printk(KERN_INFO "fd%d: accessing %s-disk with %s-layout\n",drive, | 1594 | printk(KERN_INFO "fd%d: accessing %s-disk with %s-layout\n",drive, |
1577 | unit[drive].type->name, data_types[system].name); | 1595 | unit[drive].type->name, data_types[system].name); |
1578 | 1596 | ||
1597 | unlock_kernel(); | ||
1579 | return 0; | 1598 | return 0; |
1580 | } | 1599 | } |
1581 | 1600 | ||
@@ -1584,6 +1603,7 @@ static int floppy_release(struct gendisk *disk, fmode_t mode) | |||
1584 | struct amiga_floppy_struct *p = disk->private_data; | 1603 | struct amiga_floppy_struct *p = disk->private_data; |
1585 | int drive = p - unit; | 1604 | int drive = p - unit; |
1586 | 1605 | ||
1606 | lock_kernel(); | ||
1587 | if (unit[drive].dirty == 1) { | 1607 | if (unit[drive].dirty == 1) { |
1588 | del_timer (flush_track_timer + drive); | 1608 | del_timer (flush_track_timer + drive); |
1589 | non_int_flush_track (drive); | 1609 | non_int_flush_track (drive); |
@@ -1597,6 +1617,7 @@ static int floppy_release(struct gendisk *disk, fmode_t mode) | |||
1597 | /* the mod_use counter is handled this way */ | 1617 | /* the mod_use counter is handled this way */ |
1598 | floppy_off (drive | 0x40000000); | 1618 | floppy_off (drive | 0x40000000); |
1599 | #endif | 1619 | #endif |
1620 | unlock_kernel(); | ||
1600 | return 0; | 1621 | return 0; |
1601 | } | 1622 | } |
1602 | 1623 | ||
@@ -1638,7 +1659,7 @@ static const struct block_device_operations floppy_fops = { | |||
1638 | .owner = THIS_MODULE, | 1659 | .owner = THIS_MODULE, |
1639 | .open = floppy_open, | 1660 | .open = floppy_open, |
1640 | .release = floppy_release, | 1661 | .release = floppy_release, |
1641 | .locked_ioctl = fd_ioctl, | 1662 | .ioctl = fd_ioctl, |
1642 | .getgeo = fd_getgeo, | 1663 | .getgeo = fd_getgeo, |
1643 | .media_changed = amiga_floppy_change, | 1664 | .media_changed = amiga_floppy_change, |
1644 | }; | 1665 | }; |
diff --git a/drivers/block/aoe/aoeblk.c b/drivers/block/aoe/aoeblk.c index 035cefe4045a..a946929735a5 100644 --- a/drivers/block/aoe/aoeblk.c +++ b/drivers/block/aoe/aoeblk.c | |||
@@ -12,6 +12,7 @@ | |||
12 | #include <linux/slab.h> | 12 | #include <linux/slab.h> |
13 | #include <linux/genhd.h> | 13 | #include <linux/genhd.h> |
14 | #include <linux/netdevice.h> | 14 | #include <linux/netdevice.h> |
15 | #include <linux/smp_lock.h> | ||
15 | #include "aoe.h" | 16 | #include "aoe.h" |
16 | 17 | ||
17 | static struct kmem_cache *buf_pool_cache; | 18 | static struct kmem_cache *buf_pool_cache; |
@@ -124,13 +125,16 @@ aoeblk_open(struct block_device *bdev, fmode_t mode) | |||
124 | struct aoedev *d = bdev->bd_disk->private_data; | 125 | struct aoedev *d = bdev->bd_disk->private_data; |
125 | ulong flags; | 126 | ulong flags; |
126 | 127 | ||
128 | lock_kernel(); | ||
127 | spin_lock_irqsave(&d->lock, flags); | 129 | spin_lock_irqsave(&d->lock, flags); |
128 | if (d->flags & DEVFL_UP) { | 130 | if (d->flags & DEVFL_UP) { |
129 | d->nopen++; | 131 | d->nopen++; |
130 | spin_unlock_irqrestore(&d->lock, flags); | 132 | spin_unlock_irqrestore(&d->lock, flags); |
133 | unlock_kernel(); | ||
131 | return 0; | 134 | return 0; |
132 | } | 135 | } |
133 | spin_unlock_irqrestore(&d->lock, flags); | 136 | spin_unlock_irqrestore(&d->lock, flags); |
137 | unlock_kernel(); | ||
134 | return -ENODEV; | 138 | return -ENODEV; |
135 | } | 139 | } |
136 | 140 | ||
@@ -173,7 +177,7 @@ aoeblk_make_request(struct request_queue *q, struct bio *bio) | |||
173 | BUG(); | 177 | BUG(); |
174 | bio_endio(bio, -ENXIO); | 178 | bio_endio(bio, -ENXIO); |
175 | return 0; | 179 | return 0; |
176 | } else if (bio_rw_flagged(bio, BIO_RW_BARRIER)) { | 180 | } else if (bio->bi_rw & REQ_HARDBARRIER) { |
177 | bio_endio(bio, -EOPNOTSUPP); | 181 | bio_endio(bio, -EOPNOTSUPP); |
178 | return 0; | 182 | return 0; |
179 | } else if (bio->bi_io_vec == NULL) { | 183 | } else if (bio->bi_io_vec == NULL) { |
diff --git a/drivers/block/ataflop.c b/drivers/block/ataflop.c index e35cf59cbfde..aceb96476524 100644 --- a/drivers/block/ataflop.c +++ b/drivers/block/ataflop.c | |||
@@ -67,6 +67,7 @@ | |||
67 | #include <linux/delay.h> | 67 | #include <linux/delay.h> |
68 | #include <linux/init.h> | 68 | #include <linux/init.h> |
69 | #include <linux/blkdev.h> | 69 | #include <linux/blkdev.h> |
70 | #include <linux/smp_lock.h> | ||
70 | 71 | ||
71 | #include <asm/atafd.h> | 72 | #include <asm/atafd.h> |
72 | #include <asm/atafdreg.h> | 73 | #include <asm/atafdreg.h> |
@@ -359,7 +360,7 @@ static void finish_fdc( void ); | |||
359 | static void finish_fdc_done( int dummy ); | 360 | static void finish_fdc_done( int dummy ); |
360 | static void setup_req_params( int drive ); | 361 | static void setup_req_params( int drive ); |
361 | static void redo_fd_request( void); | 362 | static void redo_fd_request( void); |
362 | static int fd_ioctl(struct block_device *bdev, fmode_t mode, unsigned int | 363 | static int fd_locked_ioctl(struct block_device *bdev, fmode_t mode, unsigned int |
363 | cmd, unsigned long param); | 364 | cmd, unsigned long param); |
364 | static void fd_probe( int drive ); | 365 | static void fd_probe( int drive ); |
365 | static int fd_test_drive_present( int drive ); | 366 | static int fd_test_drive_present( int drive ); |
@@ -1480,7 +1481,7 @@ void do_fd_request(struct request_queue * q) | |||
1480 | atari_enable_irq( IRQ_MFP_FDC ); | 1481 | atari_enable_irq( IRQ_MFP_FDC ); |
1481 | } | 1482 | } |
1482 | 1483 | ||
1483 | static int fd_ioctl(struct block_device *bdev, fmode_t mode, | 1484 | static int fd_locked_ioctl(struct block_device *bdev, fmode_t mode, |
1484 | unsigned int cmd, unsigned long param) | 1485 | unsigned int cmd, unsigned long param) |
1485 | { | 1486 | { |
1486 | struct gendisk *disk = bdev->bd_disk; | 1487 | struct gendisk *disk = bdev->bd_disk; |
@@ -1665,6 +1666,17 @@ static int fd_ioctl(struct block_device *bdev, fmode_t mode, | |||
1665 | } | 1666 | } |
1666 | } | 1667 | } |
1667 | 1668 | ||
1669 | static int fd_ioctl(struct block_device *bdev, fmode_t mode, | ||
1670 | unsigned int cmd, unsigned long arg) | ||
1671 | { | ||
1672 | int ret; | ||
1673 | |||
1674 | lock_kernel(); | ||
1675 | ret = fd_locked_ioctl(bdev, mode, cmd, arg); | ||
1676 | unlock_kernel(); | ||
1677 | |||
1678 | return ret; | ||
1679 | } | ||
1668 | 1680 | ||
1669 | /* Initialize the 'unit' variable for drive 'drive' */ | 1681 | /* Initialize the 'unit' variable for drive 'drive' */ |
1670 | 1682 | ||
@@ -1838,24 +1850,36 @@ static int floppy_open(struct block_device *bdev, fmode_t mode) | |||
1838 | return 0; | 1850 | return 0; |
1839 | } | 1851 | } |
1840 | 1852 | ||
1853 | static int floppy_unlocked_open(struct block_device *bdev, fmode_t mode) | ||
1854 | { | ||
1855 | int ret; | ||
1856 | |||
1857 | lock_kernel(); | ||
1858 | ret = floppy_open(bdev, mode); | ||
1859 | unlock_kernel(); | ||
1860 | |||
1861 | return ret; | ||
1862 | } | ||
1841 | 1863 | ||
1842 | static int floppy_release(struct gendisk *disk, fmode_t mode) | 1864 | static int floppy_release(struct gendisk *disk, fmode_t mode) |
1843 | { | 1865 | { |
1844 | struct atari_floppy_struct *p = disk->private_data; | 1866 | struct atari_floppy_struct *p = disk->private_data; |
1867 | lock_kernel(); | ||
1845 | if (p->ref < 0) | 1868 | if (p->ref < 0) |
1846 | p->ref = 0; | 1869 | p->ref = 0; |
1847 | else if (!p->ref--) { | 1870 | else if (!p->ref--) { |
1848 | printk(KERN_ERR "floppy_release with fd_ref == 0"); | 1871 | printk(KERN_ERR "floppy_release with fd_ref == 0"); |
1849 | p->ref = 0; | 1872 | p->ref = 0; |
1850 | } | 1873 | } |
1874 | unlock_kernel(); | ||
1851 | return 0; | 1875 | return 0; |
1852 | } | 1876 | } |
1853 | 1877 | ||
1854 | static const struct block_device_operations floppy_fops = { | 1878 | static const struct block_device_operations floppy_fops = { |
1855 | .owner = THIS_MODULE, | 1879 | .owner = THIS_MODULE, |
1856 | .open = floppy_open, | 1880 | .open = floppy_unlocked_open, |
1857 | .release = floppy_release, | 1881 | .release = floppy_release, |
1858 | .locked_ioctl = fd_ioctl, | 1882 | .ioctl = fd_ioctl, |
1859 | .media_changed = check_floppy_change, | 1883 | .media_changed = check_floppy_change, |
1860 | .revalidate_disk= floppy_revalidate, | 1884 | .revalidate_disk= floppy_revalidate, |
1861 | }; | 1885 | }; |
diff --git a/drivers/block/brd.c b/drivers/block/brd.c index f1bf79d9bc0a..1c7f63792ff8 100644 --- a/drivers/block/brd.c +++ b/drivers/block/brd.c | |||
@@ -15,6 +15,7 @@ | |||
15 | #include <linux/blkdev.h> | 15 | #include <linux/blkdev.h> |
16 | #include <linux/bio.h> | 16 | #include <linux/bio.h> |
17 | #include <linux/highmem.h> | 17 | #include <linux/highmem.h> |
18 | #include <linux/smp_lock.h> | ||
18 | #include <linux/radix-tree.h> | 19 | #include <linux/radix-tree.h> |
19 | #include <linux/buffer_head.h> /* invalidate_bh_lrus() */ | 20 | #include <linux/buffer_head.h> /* invalidate_bh_lrus() */ |
20 | #include <linux/slab.h> | 21 | #include <linux/slab.h> |
@@ -340,7 +341,7 @@ static int brd_make_request(struct request_queue *q, struct bio *bio) | |||
340 | get_capacity(bdev->bd_disk)) | 341 | get_capacity(bdev->bd_disk)) |
341 | goto out; | 342 | goto out; |
342 | 343 | ||
343 | if (unlikely(bio_rw_flagged(bio, BIO_RW_DISCARD))) { | 344 | if (unlikely(bio->bi_rw & REQ_DISCARD)) { |
344 | err = 0; | 345 | err = 0; |
345 | discard_from_brd(brd, sector, bio->bi_size); | 346 | discard_from_brd(brd, sector, bio->bi_size); |
346 | goto out; | 347 | goto out; |
@@ -401,6 +402,7 @@ static int brd_ioctl(struct block_device *bdev, fmode_t mode, | |||
401 | * ram device BLKFLSBUF has special semantics, we want to actually | 402 | * ram device BLKFLSBUF has special semantics, we want to actually |
402 | * release and destroy the ramdisk data. | 403 | * release and destroy the ramdisk data. |
403 | */ | 404 | */ |
405 | lock_kernel(); | ||
404 | mutex_lock(&bdev->bd_mutex); | 406 | mutex_lock(&bdev->bd_mutex); |
405 | error = -EBUSY; | 407 | error = -EBUSY; |
406 | if (bdev->bd_openers <= 1) { | 408 | if (bdev->bd_openers <= 1) { |
@@ -417,13 +419,14 @@ static int brd_ioctl(struct block_device *bdev, fmode_t mode, | |||
417 | error = 0; | 419 | error = 0; |
418 | } | 420 | } |
419 | mutex_unlock(&bdev->bd_mutex); | 421 | mutex_unlock(&bdev->bd_mutex); |
422 | unlock_kernel(); | ||
420 | 423 | ||
421 | return error; | 424 | return error; |
422 | } | 425 | } |
423 | 426 | ||
424 | static const struct block_device_operations brd_fops = { | 427 | static const struct block_device_operations brd_fops = { |
425 | .owner = THIS_MODULE, | 428 | .owner = THIS_MODULE, |
426 | .locked_ioctl = brd_ioctl, | 429 | .ioctl = brd_ioctl, |
427 | #ifdef CONFIG_BLK_DEV_XIP | 430 | #ifdef CONFIG_BLK_DEV_XIP |
428 | .direct_access = brd_direct_access, | 431 | .direct_access = brd_direct_access, |
429 | #endif | 432 | #endif |
@@ -479,7 +482,7 @@ static struct brd_device *brd_alloc(int i) | |||
479 | if (!brd->brd_queue) | 482 | if (!brd->brd_queue) |
480 | goto out_free_dev; | 483 | goto out_free_dev; |
481 | blk_queue_make_request(brd->brd_queue, brd_make_request); | 484 | blk_queue_make_request(brd->brd_queue, brd_make_request); |
482 | blk_queue_ordered(brd->brd_queue, QUEUE_ORDERED_TAG, NULL); | 485 | blk_queue_ordered(brd->brd_queue, QUEUE_ORDERED_TAG); |
483 | blk_queue_max_hw_sectors(brd->brd_queue, 1024); | 486 | blk_queue_max_hw_sectors(brd->brd_queue, 1024); |
484 | blk_queue_bounce_limit(brd->brd_queue, BLK_BOUNCE_ANY); | 487 | blk_queue_bounce_limit(brd->brd_queue, BLK_BOUNCE_ANY); |
485 | 488 | ||
diff --git a/drivers/block/cciss.c b/drivers/block/cciss.c index e1e7143ca1e3..31064df1370a 100644 --- a/drivers/block/cciss.c +++ b/drivers/block/cciss.c | |||
@@ -56,16 +56,14 @@ | |||
56 | #include <linux/kthread.h> | 56 | #include <linux/kthread.h> |
57 | 57 | ||
58 | #define CCISS_DRIVER_VERSION(maj,min,submin) ((maj<<16)|(min<<8)|(submin)) | 58 | #define CCISS_DRIVER_VERSION(maj,min,submin) ((maj<<16)|(min<<8)|(submin)) |
59 | #define DRIVER_NAME "HP CISS Driver (v 3.6.20)" | 59 | #define DRIVER_NAME "HP CISS Driver (v 3.6.26)" |
60 | #define DRIVER_VERSION CCISS_DRIVER_VERSION(3, 6, 20) | 60 | #define DRIVER_VERSION CCISS_DRIVER_VERSION(3, 6, 26) |
61 | 61 | ||
62 | /* Embedded module documentation macros - see modules.h */ | 62 | /* Embedded module documentation macros - see modules.h */ |
63 | MODULE_AUTHOR("Hewlett-Packard Company"); | 63 | MODULE_AUTHOR("Hewlett-Packard Company"); |
64 | MODULE_DESCRIPTION("Driver for HP Smart Array Controllers"); | 64 | MODULE_DESCRIPTION("Driver for HP Smart Array Controllers"); |
65 | MODULE_SUPPORTED_DEVICE("HP SA5i SA5i+ SA532 SA5300 SA5312 SA641 SA642 SA6400" | 65 | MODULE_SUPPORTED_DEVICE("HP Smart Array Controllers"); |
66 | " SA6i P600 P800 P400 P400i E200 E200i E500 P700m" | 66 | MODULE_VERSION("3.6.26"); |
67 | " Smart Array G2 Series SAS/SATA Controllers"); | ||
68 | MODULE_VERSION("3.6.20"); | ||
69 | MODULE_LICENSE("GPL"); | 67 | MODULE_LICENSE("GPL"); |
70 | 68 | ||
71 | static int cciss_allow_hpsa; | 69 | static int cciss_allow_hpsa; |
@@ -107,6 +105,11 @@ static const struct pci_device_id cciss_pci_device_id[] = { | |||
107 | {PCI_VENDOR_ID_HP, PCI_DEVICE_ID_HP_CISSE, 0x103C, 0x3249}, | 105 | {PCI_VENDOR_ID_HP, PCI_DEVICE_ID_HP_CISSE, 0x103C, 0x3249}, |
108 | {PCI_VENDOR_ID_HP, PCI_DEVICE_ID_HP_CISSE, 0x103C, 0x324A}, | 106 | {PCI_VENDOR_ID_HP, PCI_DEVICE_ID_HP_CISSE, 0x103C, 0x324A}, |
109 | {PCI_VENDOR_ID_HP, PCI_DEVICE_ID_HP_CISSE, 0x103C, 0x324B}, | 107 | {PCI_VENDOR_ID_HP, PCI_DEVICE_ID_HP_CISSE, 0x103C, 0x324B}, |
108 | {PCI_VENDOR_ID_HP, PCI_DEVICE_ID_HP_CISSE, 0x103C, 0x3250}, | ||
109 | {PCI_VENDOR_ID_HP, PCI_DEVICE_ID_HP_CISSE, 0x103C, 0x3251}, | ||
110 | {PCI_VENDOR_ID_HP, PCI_DEVICE_ID_HP_CISSE, 0x103C, 0x3252}, | ||
111 | {PCI_VENDOR_ID_HP, PCI_DEVICE_ID_HP_CISSE, 0x103C, 0x3253}, | ||
112 | {PCI_VENDOR_ID_HP, PCI_DEVICE_ID_HP_CISSE, 0x103C, 0x3254}, | ||
110 | {0,} | 113 | {0,} |
111 | }; | 114 | }; |
112 | 115 | ||
@@ -146,6 +149,11 @@ static struct board_type products[] = { | |||
146 | {0x3249103C, "Smart Array P812", &SA5_access}, | 149 | {0x3249103C, "Smart Array P812", &SA5_access}, |
147 | {0x324A103C, "Smart Array P712m", &SA5_access}, | 150 | {0x324A103C, "Smart Array P712m", &SA5_access}, |
148 | {0x324B103C, "Smart Array P711m", &SA5_access}, | 151 | {0x324B103C, "Smart Array P711m", &SA5_access}, |
152 | {0x3250103C, "Smart Array", &SA5_access}, | ||
153 | {0x3251103C, "Smart Array", &SA5_access}, | ||
154 | {0x3252103C, "Smart Array", &SA5_access}, | ||
155 | {0x3253103C, "Smart Array", &SA5_access}, | ||
156 | {0x3254103C, "Smart Array", &SA5_access}, | ||
149 | }; | 157 | }; |
150 | 158 | ||
151 | /* How long to wait (in milliseconds) for board to go into simple mode */ | 159 | /* How long to wait (in milliseconds) for board to go into simple mode */ |
@@ -167,9 +175,13 @@ static DEFINE_MUTEX(scan_mutex); | |||
167 | static LIST_HEAD(scan_q); | 175 | static LIST_HEAD(scan_q); |
168 | 176 | ||
169 | static void do_cciss_request(struct request_queue *q); | 177 | static void do_cciss_request(struct request_queue *q); |
170 | static irqreturn_t do_cciss_intr(int irq, void *dev_id); | 178 | static irqreturn_t do_cciss_intx(int irq, void *dev_id); |
179 | static irqreturn_t do_cciss_msix_intr(int irq, void *dev_id); | ||
171 | static int cciss_open(struct block_device *bdev, fmode_t mode); | 180 | static int cciss_open(struct block_device *bdev, fmode_t mode); |
181 | static int cciss_unlocked_open(struct block_device *bdev, fmode_t mode); | ||
172 | static int cciss_release(struct gendisk *disk, fmode_t mode); | 182 | static int cciss_release(struct gendisk *disk, fmode_t mode); |
183 | static int do_ioctl(struct block_device *bdev, fmode_t mode, | ||
184 | unsigned int cmd, unsigned long arg); | ||
173 | static int cciss_ioctl(struct block_device *bdev, fmode_t mode, | 185 | static int cciss_ioctl(struct block_device *bdev, fmode_t mode, |
174 | unsigned int cmd, unsigned long arg); | 186 | unsigned int cmd, unsigned long arg); |
175 | static int cciss_getgeo(struct block_device *bdev, struct hd_geometry *geo); | 187 | static int cciss_getgeo(struct block_device *bdev, struct hd_geometry *geo); |
@@ -179,25 +191,23 @@ static int rebuild_lun_table(ctlr_info_t *h, int first_time, int via_ioctl); | |||
179 | static int deregister_disk(ctlr_info_t *h, int drv_index, | 191 | static int deregister_disk(ctlr_info_t *h, int drv_index, |
180 | int clear_all, int via_ioctl); | 192 | int clear_all, int via_ioctl); |
181 | 193 | ||
182 | static void cciss_read_capacity(int ctlr, int logvol, | 194 | static void cciss_read_capacity(ctlr_info_t *h, int logvol, |
183 | sector_t *total_size, unsigned int *block_size); | 195 | sector_t *total_size, unsigned int *block_size); |
184 | static void cciss_read_capacity_16(int ctlr, int logvol, | 196 | static void cciss_read_capacity_16(ctlr_info_t *h, int logvol, |
185 | sector_t *total_size, unsigned int *block_size); | 197 | sector_t *total_size, unsigned int *block_size); |
186 | static void cciss_geometry_inquiry(int ctlr, int logvol, | 198 | static void cciss_geometry_inquiry(ctlr_info_t *h, int logvol, |
187 | sector_t total_size, | 199 | sector_t total_size, |
188 | unsigned int block_size, InquiryData_struct *inq_buff, | 200 | unsigned int block_size, InquiryData_struct *inq_buff, |
189 | drive_info_struct *drv); | 201 | drive_info_struct *drv); |
190 | static void __devinit cciss_interrupt_mode(ctlr_info_t *, struct pci_dev *, | 202 | static void __devinit cciss_interrupt_mode(ctlr_info_t *); |
191 | __u32); | ||
192 | static void start_io(ctlr_info_t *h); | 203 | static void start_io(ctlr_info_t *h); |
193 | static int sendcmd_withirq(__u8 cmd, int ctlr, void *buff, size_t size, | 204 | static int sendcmd_withirq(ctlr_info_t *h, __u8 cmd, void *buff, size_t size, |
194 | __u8 page_code, unsigned char scsi3addr[], | 205 | __u8 page_code, unsigned char scsi3addr[], |
195 | int cmd_type); | 206 | int cmd_type); |
196 | static int sendcmd_withirq_core(ctlr_info_t *h, CommandList_struct *c, | 207 | static int sendcmd_withirq_core(ctlr_info_t *h, CommandList_struct *c, |
197 | int attempt_retry); | 208 | int attempt_retry); |
198 | static int process_sendcmd_error(ctlr_info_t *h, CommandList_struct *c); | 209 | static int process_sendcmd_error(ctlr_info_t *h, CommandList_struct *c); |
199 | 210 | ||
200 | static void fail_all_cmds(unsigned long ctlr); | ||
201 | static int add_to_scan_list(struct ctlr_info *h); | 211 | static int add_to_scan_list(struct ctlr_info *h); |
202 | static int scan_thread(void *data); | 212 | static int scan_thread(void *data); |
203 | static int check_for_unit_attention(ctlr_info_t *h, CommandList_struct *c); | 213 | static int check_for_unit_attention(ctlr_info_t *h, CommandList_struct *c); |
@@ -205,11 +215,23 @@ static void cciss_hba_release(struct device *dev); | |||
205 | static void cciss_device_release(struct device *dev); | 215 | static void cciss_device_release(struct device *dev); |
206 | static void cciss_free_gendisk(ctlr_info_t *h, int drv_index); | 216 | static void cciss_free_gendisk(ctlr_info_t *h, int drv_index); |
207 | static void cciss_free_drive_info(ctlr_info_t *h, int drv_index); | 217 | static void cciss_free_drive_info(ctlr_info_t *h, int drv_index); |
218 | static inline u32 next_command(ctlr_info_t *h); | ||
219 | static int __devinit cciss_find_cfg_addrs(struct pci_dev *pdev, | ||
220 | void __iomem *vaddr, u32 *cfg_base_addr, u64 *cfg_base_addr_index, | ||
221 | u64 *cfg_offset); | ||
222 | static int __devinit cciss_pci_find_memory_BAR(struct pci_dev *pdev, | ||
223 | unsigned long *memory_bar); | ||
224 | |||
225 | |||
226 | /* performant mode helper functions */ | ||
227 | static void calc_bucket_map(int *bucket, int num_buckets, int nsgs, | ||
228 | int *bucket_map); | ||
229 | static void cciss_put_controller_into_performant_mode(ctlr_info_t *h); | ||
208 | 230 | ||
209 | #ifdef CONFIG_PROC_FS | 231 | #ifdef CONFIG_PROC_FS |
210 | static void cciss_procinit(int i); | 232 | static void cciss_procinit(ctlr_info_t *h); |
211 | #else | 233 | #else |
212 | static void cciss_procinit(int i) | 234 | static void cciss_procinit(ctlr_info_t *h) |
213 | { | 235 | { |
214 | } | 236 | } |
215 | #endif /* CONFIG_PROC_FS */ | 237 | #endif /* CONFIG_PROC_FS */ |
@@ -221,9 +243,9 @@ static int cciss_compat_ioctl(struct block_device *, fmode_t, | |||
221 | 243 | ||
222 | static const struct block_device_operations cciss_fops = { | 244 | static const struct block_device_operations cciss_fops = { |
223 | .owner = THIS_MODULE, | 245 | .owner = THIS_MODULE, |
224 | .open = cciss_open, | 246 | .open = cciss_unlocked_open, |
225 | .release = cciss_release, | 247 | .release = cciss_release, |
226 | .locked_ioctl = cciss_ioctl, | 248 | .ioctl = do_ioctl, |
227 | .getgeo = cciss_getgeo, | 249 | .getgeo = cciss_getgeo, |
228 | #ifdef CONFIG_COMPAT | 250 | #ifdef CONFIG_COMPAT |
229 | .compat_ioctl = cciss_compat_ioctl, | 251 | .compat_ioctl = cciss_compat_ioctl, |
@@ -231,6 +253,16 @@ static const struct block_device_operations cciss_fops = { | |||
231 | .revalidate_disk = cciss_revalidate, | 253 | .revalidate_disk = cciss_revalidate, |
232 | }; | 254 | }; |
233 | 255 | ||
256 | /* set_performant_mode: Modify the tag for cciss performant | ||
257 | * set bit 0 for pull model, bits 3-1 for block fetch | ||
258 | * register number | ||
259 | */ | ||
260 | static void set_performant_mode(ctlr_info_t *h, CommandList_struct *c) | ||
261 | { | ||
262 | if (likely(h->transMethod == CFGTBL_Trans_Performant)) | ||
263 | c->busaddr |= 1 | (h->blockFetchTable[c->Header.SGList] << 1); | ||
264 | } | ||
265 | |||
234 | /* | 266 | /* |
235 | * Enqueuing and dequeuing functions for cmdlists. | 267 | * Enqueuing and dequeuing functions for cmdlists. |
236 | */ | 268 | */ |
@@ -257,6 +289,18 @@ static inline void removeQ(CommandList_struct *c) | |||
257 | hlist_del_init(&c->list); | 289 | hlist_del_init(&c->list); |
258 | } | 290 | } |
259 | 291 | ||
292 | static void enqueue_cmd_and_start_io(ctlr_info_t *h, | ||
293 | CommandList_struct *c) | ||
294 | { | ||
295 | unsigned long flags; | ||
296 | set_performant_mode(h, c); | ||
297 | spin_lock_irqsave(&h->lock, flags); | ||
298 | addQ(&h->reqQ, c); | ||
299 | h->Qdepth++; | ||
300 | start_io(h); | ||
301 | spin_unlock_irqrestore(&h->lock, flags); | ||
302 | } | ||
303 | |||
260 | static void cciss_free_sg_chain_blocks(SGDescriptor_struct **cmd_sg_list, | 304 | static void cciss_free_sg_chain_blocks(SGDescriptor_struct **cmd_sg_list, |
261 | int nr_cmds) | 305 | int nr_cmds) |
262 | { | 306 | { |
@@ -366,32 +410,31 @@ static void cciss_seq_show_header(struct seq_file *seq) | |||
366 | h->product_name, | 410 | h->product_name, |
367 | (unsigned long)h->board_id, | 411 | (unsigned long)h->board_id, |
368 | h->firm_ver[0], h->firm_ver[1], h->firm_ver[2], | 412 | h->firm_ver[0], h->firm_ver[1], h->firm_ver[2], |
369 | h->firm_ver[3], (unsigned int)h->intr[SIMPLE_MODE_INT], | 413 | h->firm_ver[3], (unsigned int)h->intr[PERF_MODE_INT], |
370 | h->num_luns, | 414 | h->num_luns, |
371 | h->Qdepth, h->commands_outstanding, | 415 | h->Qdepth, h->commands_outstanding, |
372 | h->maxQsinceinit, h->max_outstanding, h->maxSG); | 416 | h->maxQsinceinit, h->max_outstanding, h->maxSG); |
373 | 417 | ||
374 | #ifdef CONFIG_CISS_SCSI_TAPE | 418 | #ifdef CONFIG_CISS_SCSI_TAPE |
375 | cciss_seq_tape_report(seq, h->ctlr); | 419 | cciss_seq_tape_report(seq, h); |
376 | #endif /* CONFIG_CISS_SCSI_TAPE */ | 420 | #endif /* CONFIG_CISS_SCSI_TAPE */ |
377 | } | 421 | } |
378 | 422 | ||
379 | static void *cciss_seq_start(struct seq_file *seq, loff_t *pos) | 423 | static void *cciss_seq_start(struct seq_file *seq, loff_t *pos) |
380 | { | 424 | { |
381 | ctlr_info_t *h = seq->private; | 425 | ctlr_info_t *h = seq->private; |
382 | unsigned ctlr = h->ctlr; | ||
383 | unsigned long flags; | 426 | unsigned long flags; |
384 | 427 | ||
385 | /* prevent displaying bogus info during configuration | 428 | /* prevent displaying bogus info during configuration |
386 | * or deconfiguration of a logical volume | 429 | * or deconfiguration of a logical volume |
387 | */ | 430 | */ |
388 | spin_lock_irqsave(CCISS_LOCK(ctlr), flags); | 431 | spin_lock_irqsave(&h->lock, flags); |
389 | if (h->busy_configuring) { | 432 | if (h->busy_configuring) { |
390 | spin_unlock_irqrestore(CCISS_LOCK(ctlr), flags); | 433 | spin_unlock_irqrestore(&h->lock, flags); |
391 | return ERR_PTR(-EBUSY); | 434 | return ERR_PTR(-EBUSY); |
392 | } | 435 | } |
393 | h->busy_configuring = 1; | 436 | h->busy_configuring = 1; |
394 | spin_unlock_irqrestore(CCISS_LOCK(ctlr), flags); | 437 | spin_unlock_irqrestore(&h->lock, flags); |
395 | 438 | ||
396 | if (*pos == 0) | 439 | if (*pos == 0) |
397 | cciss_seq_show_header(seq); | 440 | cciss_seq_show_header(seq); |
@@ -499,7 +542,7 @@ cciss_proc_write(struct file *file, const char __user *buf, | |||
499 | struct seq_file *seq = file->private_data; | 542 | struct seq_file *seq = file->private_data; |
500 | ctlr_info_t *h = seq->private; | 543 | ctlr_info_t *h = seq->private; |
501 | 544 | ||
502 | err = cciss_engage_scsi(h->ctlr); | 545 | err = cciss_engage_scsi(h); |
503 | if (err == 0) | 546 | if (err == 0) |
504 | err = length; | 547 | err = length; |
505 | } else | 548 | } else |
@@ -522,7 +565,7 @@ static const struct file_operations cciss_proc_fops = { | |||
522 | .write = cciss_proc_write, | 565 | .write = cciss_proc_write, |
523 | }; | 566 | }; |
524 | 567 | ||
525 | static void __devinit cciss_procinit(int i) | 568 | static void __devinit cciss_procinit(ctlr_info_t *h) |
526 | { | 569 | { |
527 | struct proc_dir_entry *pde; | 570 | struct proc_dir_entry *pde; |
528 | 571 | ||
@@ -530,9 +573,9 @@ static void __devinit cciss_procinit(int i) | |||
530 | proc_cciss = proc_mkdir("driver/cciss", NULL); | 573 | proc_cciss = proc_mkdir("driver/cciss", NULL); |
531 | if (!proc_cciss) | 574 | if (!proc_cciss) |
532 | return; | 575 | return; |
533 | pde = proc_create_data(hba[i]->devname, S_IWUSR | S_IRUSR | S_IRGRP | | 576 | pde = proc_create_data(h->devname, S_IWUSR | S_IRUSR | S_IRGRP | |
534 | S_IROTH, proc_cciss, | 577 | S_IROTH, proc_cciss, |
535 | &cciss_proc_fops, hba[i]); | 578 | &cciss_proc_fops, h); |
536 | } | 579 | } |
537 | #endif /* CONFIG_PROC_FS */ | 580 | #endif /* CONFIG_PROC_FS */ |
538 | 581 | ||
@@ -565,12 +608,12 @@ static ssize_t dev_show_unique_id(struct device *dev, | |||
565 | unsigned long flags; | 608 | unsigned long flags; |
566 | int ret = 0; | 609 | int ret = 0; |
567 | 610 | ||
568 | spin_lock_irqsave(CCISS_LOCK(h->ctlr), flags); | 611 | spin_lock_irqsave(&h->lock, flags); |
569 | if (h->busy_configuring) | 612 | if (h->busy_configuring) |
570 | ret = -EBUSY; | 613 | ret = -EBUSY; |
571 | else | 614 | else |
572 | memcpy(sn, drv->serial_no, sizeof(sn)); | 615 | memcpy(sn, drv->serial_no, sizeof(sn)); |
573 | spin_unlock_irqrestore(CCISS_LOCK(h->ctlr), flags); | 616 | spin_unlock_irqrestore(&h->lock, flags); |
574 | 617 | ||
575 | if (ret) | 618 | if (ret) |
576 | return ret; | 619 | return ret; |
@@ -595,12 +638,12 @@ static ssize_t dev_show_vendor(struct device *dev, | |||
595 | unsigned long flags; | 638 | unsigned long flags; |
596 | int ret = 0; | 639 | int ret = 0; |
597 | 640 | ||
598 | spin_lock_irqsave(CCISS_LOCK(h->ctlr), flags); | 641 | spin_lock_irqsave(&h->lock, flags); |
599 | if (h->busy_configuring) | 642 | if (h->busy_configuring) |
600 | ret = -EBUSY; | 643 | ret = -EBUSY; |
601 | else | 644 | else |
602 | memcpy(vendor, drv->vendor, VENDOR_LEN + 1); | 645 | memcpy(vendor, drv->vendor, VENDOR_LEN + 1); |
603 | spin_unlock_irqrestore(CCISS_LOCK(h->ctlr), flags); | 646 | spin_unlock_irqrestore(&h->lock, flags); |
604 | 647 | ||
605 | if (ret) | 648 | if (ret) |
606 | return ret; | 649 | return ret; |
@@ -619,12 +662,12 @@ static ssize_t dev_show_model(struct device *dev, | |||
619 | unsigned long flags; | 662 | unsigned long flags; |
620 | int ret = 0; | 663 | int ret = 0; |
621 | 664 | ||
622 | spin_lock_irqsave(CCISS_LOCK(h->ctlr), flags); | 665 | spin_lock_irqsave(&h->lock, flags); |
623 | if (h->busy_configuring) | 666 | if (h->busy_configuring) |
624 | ret = -EBUSY; | 667 | ret = -EBUSY; |
625 | else | 668 | else |
626 | memcpy(model, drv->model, MODEL_LEN + 1); | 669 | memcpy(model, drv->model, MODEL_LEN + 1); |
627 | spin_unlock_irqrestore(CCISS_LOCK(h->ctlr), flags); | 670 | spin_unlock_irqrestore(&h->lock, flags); |
628 | 671 | ||
629 | if (ret) | 672 | if (ret) |
630 | return ret; | 673 | return ret; |
@@ -643,12 +686,12 @@ static ssize_t dev_show_rev(struct device *dev, | |||
643 | unsigned long flags; | 686 | unsigned long flags; |
644 | int ret = 0; | 687 | int ret = 0; |
645 | 688 | ||
646 | spin_lock_irqsave(CCISS_LOCK(h->ctlr), flags); | 689 | spin_lock_irqsave(&h->lock, flags); |
647 | if (h->busy_configuring) | 690 | if (h->busy_configuring) |
648 | ret = -EBUSY; | 691 | ret = -EBUSY; |
649 | else | 692 | else |
650 | memcpy(rev, drv->rev, REV_LEN + 1); | 693 | memcpy(rev, drv->rev, REV_LEN + 1); |
651 | spin_unlock_irqrestore(CCISS_LOCK(h->ctlr), flags); | 694 | spin_unlock_irqrestore(&h->lock, flags); |
652 | 695 | ||
653 | if (ret) | 696 | if (ret) |
654 | return ret; | 697 | return ret; |
@@ -665,17 +708,17 @@ static ssize_t cciss_show_lunid(struct device *dev, | |||
665 | unsigned long flags; | 708 | unsigned long flags; |
666 | unsigned char lunid[8]; | 709 | unsigned char lunid[8]; |
667 | 710 | ||
668 | spin_lock_irqsave(CCISS_LOCK(h->ctlr), flags); | 711 | spin_lock_irqsave(&h->lock, flags); |
669 | if (h->busy_configuring) { | 712 | if (h->busy_configuring) { |
670 | spin_unlock_irqrestore(CCISS_LOCK(h->ctlr), flags); | 713 | spin_unlock_irqrestore(&h->lock, flags); |
671 | return -EBUSY; | 714 | return -EBUSY; |
672 | } | 715 | } |
673 | if (!drv->heads) { | 716 | if (!drv->heads) { |
674 | spin_unlock_irqrestore(CCISS_LOCK(h->ctlr), flags); | 717 | spin_unlock_irqrestore(&h->lock, flags); |
675 | return -ENOTTY; | 718 | return -ENOTTY; |
676 | } | 719 | } |
677 | memcpy(lunid, drv->LunID, sizeof(lunid)); | 720 | memcpy(lunid, drv->LunID, sizeof(lunid)); |
678 | spin_unlock_irqrestore(CCISS_LOCK(h->ctlr), flags); | 721 | spin_unlock_irqrestore(&h->lock, flags); |
679 | return snprintf(buf, 20, "0x%02x%02x%02x%02x%02x%02x%02x%02x\n", | 722 | return snprintf(buf, 20, "0x%02x%02x%02x%02x%02x%02x%02x%02x\n", |
680 | lunid[0], lunid[1], lunid[2], lunid[3], | 723 | lunid[0], lunid[1], lunid[2], lunid[3], |
681 | lunid[4], lunid[5], lunid[6], lunid[7]); | 724 | lunid[4], lunid[5], lunid[6], lunid[7]); |
@@ -690,13 +733,13 @@ static ssize_t cciss_show_raid_level(struct device *dev, | |||
690 | int raid; | 733 | int raid; |
691 | unsigned long flags; | 734 | unsigned long flags; |
692 | 735 | ||
693 | spin_lock_irqsave(CCISS_LOCK(h->ctlr), flags); | 736 | spin_lock_irqsave(&h->lock, flags); |
694 | if (h->busy_configuring) { | 737 | if (h->busy_configuring) { |
695 | spin_unlock_irqrestore(CCISS_LOCK(h->ctlr), flags); | 738 | spin_unlock_irqrestore(&h->lock, flags); |
696 | return -EBUSY; | 739 | return -EBUSY; |
697 | } | 740 | } |
698 | raid = drv->raid_level; | 741 | raid = drv->raid_level; |
699 | spin_unlock_irqrestore(CCISS_LOCK(h->ctlr), flags); | 742 | spin_unlock_irqrestore(&h->lock, flags); |
700 | if (raid < 0 || raid > RAID_UNKNOWN) | 743 | if (raid < 0 || raid > RAID_UNKNOWN) |
701 | raid = RAID_UNKNOWN; | 744 | raid = RAID_UNKNOWN; |
702 | 745 | ||
@@ -713,13 +756,13 @@ static ssize_t cciss_show_usage_count(struct device *dev, | |||
713 | unsigned long flags; | 756 | unsigned long flags; |
714 | int count; | 757 | int count; |
715 | 758 | ||
716 | spin_lock_irqsave(CCISS_LOCK(h->ctlr), flags); | 759 | spin_lock_irqsave(&h->lock, flags); |
717 | if (h->busy_configuring) { | 760 | if (h->busy_configuring) { |
718 | spin_unlock_irqrestore(CCISS_LOCK(h->ctlr), flags); | 761 | spin_unlock_irqrestore(&h->lock, flags); |
719 | return -EBUSY; | 762 | return -EBUSY; |
720 | } | 763 | } |
721 | count = drv->usage_count; | 764 | count = drv->usage_count; |
722 | spin_unlock_irqrestore(CCISS_LOCK(h->ctlr), flags); | 765 | spin_unlock_irqrestore(&h->lock, flags); |
723 | return snprintf(buf, 20, "%d\n", count); | 766 | return snprintf(buf, 20, "%d\n", count); |
724 | } | 767 | } |
725 | static DEVICE_ATTR(usage_count, S_IRUGO, cciss_show_usage_count, NULL); | 768 | static DEVICE_ATTR(usage_count, S_IRUGO, cciss_show_usage_count, NULL); |
@@ -864,60 +907,70 @@ static void cciss_destroy_ld_sysfs_entry(struct ctlr_info *h, int drv_index, | |||
864 | /* | 907 | /* |
865 | * For operations that cannot sleep, a command block is allocated at init, | 908 | * For operations that cannot sleep, a command block is allocated at init, |
866 | * and managed by cmd_alloc() and cmd_free() using a simple bitmap to track | 909 | * and managed by cmd_alloc() and cmd_free() using a simple bitmap to track |
867 | * which ones are free or in use. For operations that can wait for kmalloc | 910 | * which ones are free or in use. |
868 | * to possible sleep, this routine can be called with get_from_pool set to 0. | ||
869 | * cmd_free() MUST be called with a got_from_pool set to 0 if cmd_alloc was. | ||
870 | */ | 911 | */ |
871 | static CommandList_struct *cmd_alloc(ctlr_info_t *h, int get_from_pool) | 912 | static CommandList_struct *cmd_alloc(ctlr_info_t *h) |
872 | { | 913 | { |
873 | CommandList_struct *c; | 914 | CommandList_struct *c; |
874 | int i; | 915 | int i; |
875 | u64bit temp64; | 916 | u64bit temp64; |
876 | dma_addr_t cmd_dma_handle, err_dma_handle; | 917 | dma_addr_t cmd_dma_handle, err_dma_handle; |
877 | 918 | ||
878 | if (!get_from_pool) { | 919 | do { |
879 | c = (CommandList_struct *) pci_alloc_consistent(h->pdev, | 920 | i = find_first_zero_bit(h->cmd_pool_bits, h->nr_cmds); |
880 | sizeof(CommandList_struct), &cmd_dma_handle); | 921 | if (i == h->nr_cmds) |
881 | if (c == NULL) | ||
882 | return NULL; | 922 | return NULL; |
883 | memset(c, 0, sizeof(CommandList_struct)); | 923 | } while (test_and_set_bit(i & (BITS_PER_LONG - 1), |
924 | h->cmd_pool_bits + (i / BITS_PER_LONG)) != 0); | ||
925 | c = h->cmd_pool + i; | ||
926 | memset(c, 0, sizeof(CommandList_struct)); | ||
927 | cmd_dma_handle = h->cmd_pool_dhandle + i * sizeof(CommandList_struct); | ||
928 | c->err_info = h->errinfo_pool + i; | ||
929 | memset(c->err_info, 0, sizeof(ErrorInfo_struct)); | ||
930 | err_dma_handle = h->errinfo_pool_dhandle | ||
931 | + i * sizeof(ErrorInfo_struct); | ||
932 | h->nr_allocs++; | ||
884 | 933 | ||
885 | c->cmdindex = -1; | 934 | c->cmdindex = i; |
886 | 935 | ||
887 | c->err_info = (ErrorInfo_struct *) | 936 | INIT_HLIST_NODE(&c->list); |
888 | pci_alloc_consistent(h->pdev, sizeof(ErrorInfo_struct), | 937 | c->busaddr = (__u32) cmd_dma_handle; |
889 | &err_dma_handle); | 938 | temp64.val = (__u64) err_dma_handle; |
939 | c->ErrDesc.Addr.lower = temp64.val32.lower; | ||
940 | c->ErrDesc.Addr.upper = temp64.val32.upper; | ||
941 | c->ErrDesc.Len = sizeof(ErrorInfo_struct); | ||
890 | 942 | ||
891 | if (c->err_info == NULL) { | 943 | c->ctlr = h->ctlr; |
892 | pci_free_consistent(h->pdev, | 944 | return c; |
893 | sizeof(CommandList_struct), c, cmd_dma_handle); | 945 | } |
894 | return NULL; | ||
895 | } | ||
896 | memset(c->err_info, 0, sizeof(ErrorInfo_struct)); | ||
897 | } else { /* get it out of the controllers pool */ | ||
898 | |||
899 | do { | ||
900 | i = find_first_zero_bit(h->cmd_pool_bits, h->nr_cmds); | ||
901 | if (i == h->nr_cmds) | ||
902 | return NULL; | ||
903 | } while (test_and_set_bit | ||
904 | (i & (BITS_PER_LONG - 1), | ||
905 | h->cmd_pool_bits + (i / BITS_PER_LONG)) != 0); | ||
906 | #ifdef CCISS_DEBUG | ||
907 | printk(KERN_DEBUG "cciss: using command buffer %d\n", i); | ||
908 | #endif | ||
909 | c = h->cmd_pool + i; | ||
910 | memset(c, 0, sizeof(CommandList_struct)); | ||
911 | cmd_dma_handle = h->cmd_pool_dhandle | ||
912 | + i * sizeof(CommandList_struct); | ||
913 | c->err_info = h->errinfo_pool + i; | ||
914 | memset(c->err_info, 0, sizeof(ErrorInfo_struct)); | ||
915 | err_dma_handle = h->errinfo_pool_dhandle | ||
916 | + i * sizeof(ErrorInfo_struct); | ||
917 | h->nr_allocs++; | ||
918 | 946 | ||
919 | c->cmdindex = i; | 947 | /* allocate a command using pci_alloc_consistent, used for ioctls, |
948 | * etc., not for the main i/o path. | ||
949 | */ | ||
950 | static CommandList_struct *cmd_special_alloc(ctlr_info_t *h) | ||
951 | { | ||
952 | CommandList_struct *c; | ||
953 | u64bit temp64; | ||
954 | dma_addr_t cmd_dma_handle, err_dma_handle; | ||
955 | |||
956 | c = (CommandList_struct *) pci_alloc_consistent(h->pdev, | ||
957 | sizeof(CommandList_struct), &cmd_dma_handle); | ||
958 | if (c == NULL) | ||
959 | return NULL; | ||
960 | memset(c, 0, sizeof(CommandList_struct)); | ||
961 | |||
962 | c->cmdindex = -1; | ||
963 | |||
964 | c->err_info = (ErrorInfo_struct *) | ||
965 | pci_alloc_consistent(h->pdev, sizeof(ErrorInfo_struct), | ||
966 | &err_dma_handle); | ||
967 | |||
968 | if (c->err_info == NULL) { | ||
969 | pci_free_consistent(h->pdev, | ||
970 | sizeof(CommandList_struct), c, cmd_dma_handle); | ||
971 | return NULL; | ||
920 | } | 972 | } |
973 | memset(c->err_info, 0, sizeof(ErrorInfo_struct)); | ||
921 | 974 | ||
922 | INIT_HLIST_NODE(&c->list); | 975 | INIT_HLIST_NODE(&c->list); |
923 | c->busaddr = (__u32) cmd_dma_handle; | 976 | c->busaddr = (__u32) cmd_dma_handle; |
@@ -930,27 +983,26 @@ static CommandList_struct *cmd_alloc(ctlr_info_t *h, int get_from_pool) | |||
930 | return c; | 983 | return c; |
931 | } | 984 | } |
932 | 985 | ||
933 | /* | 986 | static void cmd_free(ctlr_info_t *h, CommandList_struct *c) |
934 | * Frees a command block that was previously allocated with cmd_alloc(). | ||
935 | */ | ||
936 | static void cmd_free(ctlr_info_t *h, CommandList_struct *c, int got_from_pool) | ||
937 | { | 987 | { |
938 | int i; | 988 | int i; |
989 | |||
990 | i = c - h->cmd_pool; | ||
991 | clear_bit(i & (BITS_PER_LONG - 1), | ||
992 | h->cmd_pool_bits + (i / BITS_PER_LONG)); | ||
993 | h->nr_frees++; | ||
994 | } | ||
995 | |||
996 | static void cmd_special_free(ctlr_info_t *h, CommandList_struct *c) | ||
997 | { | ||
939 | u64bit temp64; | 998 | u64bit temp64; |
940 | 999 | ||
941 | if (!got_from_pool) { | 1000 | temp64.val32.lower = c->ErrDesc.Addr.lower; |
942 | temp64.val32.lower = c->ErrDesc.Addr.lower; | 1001 | temp64.val32.upper = c->ErrDesc.Addr.upper; |
943 | temp64.val32.upper = c->ErrDesc.Addr.upper; | 1002 | pci_free_consistent(h->pdev, sizeof(ErrorInfo_struct), |
944 | pci_free_consistent(h->pdev, sizeof(ErrorInfo_struct), | 1003 | c->err_info, (dma_addr_t) temp64.val); |
945 | c->err_info, (dma_addr_t) temp64.val); | 1004 | pci_free_consistent(h->pdev, sizeof(CommandList_struct), |
946 | pci_free_consistent(h->pdev, sizeof(CommandList_struct), | 1005 | c, (dma_addr_t) c->busaddr); |
947 | c, (dma_addr_t) c->busaddr); | ||
948 | } else { | ||
949 | i = c - h->cmd_pool; | ||
950 | clear_bit(i & (BITS_PER_LONG - 1), | ||
951 | h->cmd_pool_bits + (i / BITS_PER_LONG)); | ||
952 | h->nr_frees++; | ||
953 | } | ||
954 | } | 1006 | } |
955 | 1007 | ||
956 | static inline ctlr_info_t *get_host(struct gendisk *disk) | 1008 | static inline ctlr_info_t *get_host(struct gendisk *disk) |
@@ -968,13 +1020,10 @@ static inline drive_info_struct *get_drv(struct gendisk *disk) | |||
968 | */ | 1020 | */ |
969 | static int cciss_open(struct block_device *bdev, fmode_t mode) | 1021 | static int cciss_open(struct block_device *bdev, fmode_t mode) |
970 | { | 1022 | { |
971 | ctlr_info_t *host = get_host(bdev->bd_disk); | 1023 | ctlr_info_t *h = get_host(bdev->bd_disk); |
972 | drive_info_struct *drv = get_drv(bdev->bd_disk); | 1024 | drive_info_struct *drv = get_drv(bdev->bd_disk); |
973 | 1025 | ||
974 | #ifdef CCISS_DEBUG | 1026 | dev_dbg(&h->pdev->dev, "cciss_open %s\n", bdev->bd_disk->disk_name); |
975 | printk(KERN_DEBUG "cciss_open %s\n", bdev->bd_disk->disk_name); | ||
976 | #endif /* CCISS_DEBUG */ | ||
977 | |||
978 | if (drv->busy_configuring) | 1027 | if (drv->busy_configuring) |
979 | return -EBUSY; | 1028 | return -EBUSY; |
980 | /* | 1029 | /* |
@@ -1000,29 +1049,39 @@ static int cciss_open(struct block_device *bdev, fmode_t mode) | |||
1000 | return -EPERM; | 1049 | return -EPERM; |
1001 | } | 1050 | } |
1002 | drv->usage_count++; | 1051 | drv->usage_count++; |
1003 | host->usage_count++; | 1052 | h->usage_count++; |
1004 | return 0; | 1053 | return 0; |
1005 | } | 1054 | } |
1006 | 1055 | ||
1056 | static int cciss_unlocked_open(struct block_device *bdev, fmode_t mode) | ||
1057 | { | ||
1058 | int ret; | ||
1059 | |||
1060 | lock_kernel(); | ||
1061 | ret = cciss_open(bdev, mode); | ||
1062 | unlock_kernel(); | ||
1063 | |||
1064 | return ret; | ||
1065 | } | ||
1066 | |||
1007 | /* | 1067 | /* |
1008 | * Close. Sync first. | 1068 | * Close. Sync first. |
1009 | */ | 1069 | */ |
1010 | static int cciss_release(struct gendisk *disk, fmode_t mode) | 1070 | static int cciss_release(struct gendisk *disk, fmode_t mode) |
1011 | { | 1071 | { |
1012 | ctlr_info_t *host = get_host(disk); | 1072 | ctlr_info_t *h; |
1013 | drive_info_struct *drv = get_drv(disk); | 1073 | drive_info_struct *drv; |
1014 | |||
1015 | #ifdef CCISS_DEBUG | ||
1016 | printk(KERN_DEBUG "cciss_release %s\n", disk->disk_name); | ||
1017 | #endif /* CCISS_DEBUG */ | ||
1018 | 1074 | ||
1075 | lock_kernel(); | ||
1076 | h = get_host(disk); | ||
1077 | drv = get_drv(disk); | ||
1078 | dev_dbg(&h->pdev->dev, "cciss_release %s\n", disk->disk_name); | ||
1019 | drv->usage_count--; | 1079 | drv->usage_count--; |
1020 | host->usage_count--; | 1080 | h->usage_count--; |
1081 | unlock_kernel(); | ||
1021 | return 0; | 1082 | return 0; |
1022 | } | 1083 | } |
1023 | 1084 | ||
1024 | #ifdef CONFIG_COMPAT | ||
1025 | |||
1026 | static int do_ioctl(struct block_device *bdev, fmode_t mode, | 1085 | static int do_ioctl(struct block_device *bdev, fmode_t mode, |
1027 | unsigned cmd, unsigned long arg) | 1086 | unsigned cmd, unsigned long arg) |
1028 | { | 1087 | { |
@@ -1033,6 +1092,8 @@ static int do_ioctl(struct block_device *bdev, fmode_t mode, | |||
1033 | return ret; | 1092 | return ret; |
1034 | } | 1093 | } |
1035 | 1094 | ||
1095 | #ifdef CONFIG_COMPAT | ||
1096 | |||
1036 | static int cciss_ioctl32_passthru(struct block_device *bdev, fmode_t mode, | 1097 | static int cciss_ioctl32_passthru(struct block_device *bdev, fmode_t mode, |
1037 | unsigned cmd, unsigned long arg); | 1098 | unsigned cmd, unsigned long arg); |
1038 | static int cciss_ioctl32_big_passthru(struct block_device *bdev, fmode_t mode, | 1099 | static int cciss_ioctl32_big_passthru(struct block_device *bdev, fmode_t mode, |
@@ -1163,11 +1224,11 @@ static int cciss_getgeo(struct block_device *bdev, struct hd_geometry *geo) | |||
1163 | return 0; | 1224 | return 0; |
1164 | } | 1225 | } |
1165 | 1226 | ||
1166 | static void check_ioctl_unit_attention(ctlr_info_t *host, CommandList_struct *c) | 1227 | static void check_ioctl_unit_attention(ctlr_info_t *h, CommandList_struct *c) |
1167 | { | 1228 | { |
1168 | if (c->err_info->CommandStatus == CMD_TARGET_STATUS && | 1229 | if (c->err_info->CommandStatus == CMD_TARGET_STATUS && |
1169 | c->err_info->ScsiStatus != SAM_STAT_CHECK_CONDITION) | 1230 | c->err_info->ScsiStatus != SAM_STAT_CHECK_CONDITION) |
1170 | (void)check_for_unit_attention(host, c); | 1231 | (void)check_for_unit_attention(h, c); |
1171 | } | 1232 | } |
1172 | /* | 1233 | /* |
1173 | * ioctl | 1234 | * ioctl |
@@ -1176,15 +1237,12 @@ static int cciss_ioctl(struct block_device *bdev, fmode_t mode, | |||
1176 | unsigned int cmd, unsigned long arg) | 1237 | unsigned int cmd, unsigned long arg) |
1177 | { | 1238 | { |
1178 | struct gendisk *disk = bdev->bd_disk; | 1239 | struct gendisk *disk = bdev->bd_disk; |
1179 | ctlr_info_t *host = get_host(disk); | 1240 | ctlr_info_t *h = get_host(disk); |
1180 | drive_info_struct *drv = get_drv(disk); | 1241 | drive_info_struct *drv = get_drv(disk); |
1181 | int ctlr = host->ctlr; | ||
1182 | void __user *argp = (void __user *)arg; | 1242 | void __user *argp = (void __user *)arg; |
1183 | 1243 | ||
1184 | #ifdef CCISS_DEBUG | 1244 | dev_dbg(&h->pdev->dev, "cciss_ioctl: Called with cmd=%x %lx\n", |
1185 | printk(KERN_DEBUG "cciss_ioctl: Called with cmd=%x %lx\n", cmd, arg); | 1245 | cmd, arg); |
1186 | #endif /* CCISS_DEBUG */ | ||
1187 | |||
1188 | switch (cmd) { | 1246 | switch (cmd) { |
1189 | case CCISS_GETPCIINFO: | 1247 | case CCISS_GETPCIINFO: |
1190 | { | 1248 | { |
@@ -1192,10 +1250,10 @@ static int cciss_ioctl(struct block_device *bdev, fmode_t mode, | |||
1192 | 1250 | ||
1193 | if (!arg) | 1251 | if (!arg) |
1194 | return -EINVAL; | 1252 | return -EINVAL; |
1195 | pciinfo.domain = pci_domain_nr(host->pdev->bus); | 1253 | pciinfo.domain = pci_domain_nr(h->pdev->bus); |
1196 | pciinfo.bus = host->pdev->bus->number; | 1254 | pciinfo.bus = h->pdev->bus->number; |
1197 | pciinfo.dev_fn = host->pdev->devfn; | 1255 | pciinfo.dev_fn = h->pdev->devfn; |
1198 | pciinfo.board_id = host->board_id; | 1256 | pciinfo.board_id = h->board_id; |
1199 | if (copy_to_user | 1257 | if (copy_to_user |
1200 | (argp, &pciinfo, sizeof(cciss_pci_info_struct))) | 1258 | (argp, &pciinfo, sizeof(cciss_pci_info_struct))) |
1201 | return -EFAULT; | 1259 | return -EFAULT; |
@@ -1207,9 +1265,9 @@ static int cciss_ioctl(struct block_device *bdev, fmode_t mode, | |||
1207 | if (!arg) | 1265 | if (!arg) |
1208 | return -EINVAL; | 1266 | return -EINVAL; |
1209 | intinfo.delay = | 1267 | intinfo.delay = |
1210 | readl(&host->cfgtable->HostWrite.CoalIntDelay); | 1268 | readl(&h->cfgtable->HostWrite.CoalIntDelay); |
1211 | intinfo.count = | 1269 | intinfo.count = |
1212 | readl(&host->cfgtable->HostWrite.CoalIntCount); | 1270 | readl(&h->cfgtable->HostWrite.CoalIntCount); |
1213 | if (copy_to_user | 1271 | if (copy_to_user |
1214 | (argp, &intinfo, sizeof(cciss_coalint_struct))) | 1272 | (argp, &intinfo, sizeof(cciss_coalint_struct))) |
1215 | return -EFAULT; | 1273 | return -EFAULT; |
@@ -1229,26 +1287,23 @@ static int cciss_ioctl(struct block_device *bdev, fmode_t mode, | |||
1229 | (&intinfo, argp, sizeof(cciss_coalint_struct))) | 1287 | (&intinfo, argp, sizeof(cciss_coalint_struct))) |
1230 | return -EFAULT; | 1288 | return -EFAULT; |
1231 | if ((intinfo.delay == 0) && (intinfo.count == 0)) | 1289 | if ((intinfo.delay == 0) && (intinfo.count == 0)) |
1232 | { | ||
1233 | // printk("cciss_ioctl: delay and count cannot be 0\n"); | ||
1234 | return -EINVAL; | 1290 | return -EINVAL; |
1235 | } | 1291 | spin_lock_irqsave(&h->lock, flags); |
1236 | spin_lock_irqsave(CCISS_LOCK(ctlr), flags); | ||
1237 | /* Update the field, and then ring the doorbell */ | 1292 | /* Update the field, and then ring the doorbell */ |
1238 | writel(intinfo.delay, | 1293 | writel(intinfo.delay, |
1239 | &(host->cfgtable->HostWrite.CoalIntDelay)); | 1294 | &(h->cfgtable->HostWrite.CoalIntDelay)); |
1240 | writel(intinfo.count, | 1295 | writel(intinfo.count, |
1241 | &(host->cfgtable->HostWrite.CoalIntCount)); | 1296 | &(h->cfgtable->HostWrite.CoalIntCount)); |
1242 | writel(CFGTBL_ChangeReq, host->vaddr + SA5_DOORBELL); | 1297 | writel(CFGTBL_ChangeReq, h->vaddr + SA5_DOORBELL); |
1243 | 1298 | ||
1244 | for (i = 0; i < MAX_IOCTL_CONFIG_WAIT; i++) { | 1299 | for (i = 0; i < MAX_IOCTL_CONFIG_WAIT; i++) { |
1245 | if (!(readl(host->vaddr + SA5_DOORBELL) | 1300 | if (!(readl(h->vaddr + SA5_DOORBELL) |
1246 | & CFGTBL_ChangeReq)) | 1301 | & CFGTBL_ChangeReq)) |
1247 | break; | 1302 | break; |
1248 | /* delay and try again */ | 1303 | /* delay and try again */ |
1249 | udelay(1000); | 1304 | udelay(1000); |
1250 | } | 1305 | } |
1251 | spin_unlock_irqrestore(CCISS_LOCK(ctlr), flags); | 1306 | spin_unlock_irqrestore(&h->lock, flags); |
1252 | if (i >= MAX_IOCTL_CONFIG_WAIT) | 1307 | if (i >= MAX_IOCTL_CONFIG_WAIT) |
1253 | return -EAGAIN; | 1308 | return -EAGAIN; |
1254 | return 0; | 1309 | return 0; |
@@ -1262,7 +1317,7 @@ static int cciss_ioctl(struct block_device *bdev, fmode_t mode, | |||
1262 | return -EINVAL; | 1317 | return -EINVAL; |
1263 | for (i = 0; i < 16; i++) | 1318 | for (i = 0; i < 16; i++) |
1264 | NodeName[i] = | 1319 | NodeName[i] = |
1265 | readb(&host->cfgtable->ServerName[i]); | 1320 | readb(&h->cfgtable->ServerName[i]); |
1266 | if (copy_to_user(argp, NodeName, sizeof(NodeName_type))) | 1321 | if (copy_to_user(argp, NodeName, sizeof(NodeName_type))) |
1267 | return -EFAULT; | 1322 | return -EFAULT; |
1268 | return 0; | 1323 | return 0; |
@@ -1282,23 +1337,23 @@ static int cciss_ioctl(struct block_device *bdev, fmode_t mode, | |||
1282 | (NodeName, argp, sizeof(NodeName_type))) | 1337 | (NodeName, argp, sizeof(NodeName_type))) |
1283 | return -EFAULT; | 1338 | return -EFAULT; |
1284 | 1339 | ||
1285 | spin_lock_irqsave(CCISS_LOCK(ctlr), flags); | 1340 | spin_lock_irqsave(&h->lock, flags); |
1286 | 1341 | ||
1287 | /* Update the field, and then ring the doorbell */ | 1342 | /* Update the field, and then ring the doorbell */ |
1288 | for (i = 0; i < 16; i++) | 1343 | for (i = 0; i < 16; i++) |
1289 | writeb(NodeName[i], | 1344 | writeb(NodeName[i], |
1290 | &host->cfgtable->ServerName[i]); | 1345 | &h->cfgtable->ServerName[i]); |
1291 | 1346 | ||
1292 | writel(CFGTBL_ChangeReq, host->vaddr + SA5_DOORBELL); | 1347 | writel(CFGTBL_ChangeReq, h->vaddr + SA5_DOORBELL); |
1293 | 1348 | ||
1294 | for (i = 0; i < MAX_IOCTL_CONFIG_WAIT; i++) { | 1349 | for (i = 0; i < MAX_IOCTL_CONFIG_WAIT; i++) { |
1295 | if (!(readl(host->vaddr + SA5_DOORBELL) | 1350 | if (!(readl(h->vaddr + SA5_DOORBELL) |
1296 | & CFGTBL_ChangeReq)) | 1351 | & CFGTBL_ChangeReq)) |
1297 | break; | 1352 | break; |
1298 | /* delay and try again */ | 1353 | /* delay and try again */ |
1299 | udelay(1000); | 1354 | udelay(1000); |
1300 | } | 1355 | } |
1301 | spin_unlock_irqrestore(CCISS_LOCK(ctlr), flags); | 1356 | spin_unlock_irqrestore(&h->lock, flags); |
1302 | if (i >= MAX_IOCTL_CONFIG_WAIT) | 1357 | if (i >= MAX_IOCTL_CONFIG_WAIT) |
1303 | return -EAGAIN; | 1358 | return -EAGAIN; |
1304 | return 0; | 1359 | return 0; |
@@ -1310,7 +1365,7 @@ static int cciss_ioctl(struct block_device *bdev, fmode_t mode, | |||
1310 | 1365 | ||
1311 | if (!arg) | 1366 | if (!arg) |
1312 | return -EINVAL; | 1367 | return -EINVAL; |
1313 | heartbeat = readl(&host->cfgtable->HeartBeat); | 1368 | heartbeat = readl(&h->cfgtable->HeartBeat); |
1314 | if (copy_to_user | 1369 | if (copy_to_user |
1315 | (argp, &heartbeat, sizeof(Heartbeat_type))) | 1370 | (argp, &heartbeat, sizeof(Heartbeat_type))) |
1316 | return -EFAULT; | 1371 | return -EFAULT; |
@@ -1322,7 +1377,7 @@ static int cciss_ioctl(struct block_device *bdev, fmode_t mode, | |||
1322 | 1377 | ||
1323 | if (!arg) | 1378 | if (!arg) |
1324 | return -EINVAL; | 1379 | return -EINVAL; |
1325 | BusTypes = readl(&host->cfgtable->BusTypes); | 1380 | BusTypes = readl(&h->cfgtable->BusTypes); |
1326 | if (copy_to_user | 1381 | if (copy_to_user |
1327 | (argp, &BusTypes, sizeof(BusTypes_type))) | 1382 | (argp, &BusTypes, sizeof(BusTypes_type))) |
1328 | return -EFAULT; | 1383 | return -EFAULT; |
@@ -1334,7 +1389,7 @@ static int cciss_ioctl(struct block_device *bdev, fmode_t mode, | |||
1334 | 1389 | ||
1335 | if (!arg) | 1390 | if (!arg) |
1336 | return -EINVAL; | 1391 | return -EINVAL; |
1337 | memcpy(firmware, host->firm_ver, 4); | 1392 | memcpy(firmware, h->firm_ver, 4); |
1338 | 1393 | ||
1339 | if (copy_to_user | 1394 | if (copy_to_user |
1340 | (argp, firmware, sizeof(FirmwareVer_type))) | 1395 | (argp, firmware, sizeof(FirmwareVer_type))) |
@@ -1357,7 +1412,7 @@ static int cciss_ioctl(struct block_device *bdev, fmode_t mode, | |||
1357 | case CCISS_DEREGDISK: | 1412 | case CCISS_DEREGDISK: |
1358 | case CCISS_REGNEWD: | 1413 | case CCISS_REGNEWD: |
1359 | case CCISS_REVALIDVOLS: | 1414 | case CCISS_REVALIDVOLS: |
1360 | return rebuild_lun_table(host, 0, 1); | 1415 | return rebuild_lun_table(h, 0, 1); |
1361 | 1416 | ||
1362 | case CCISS_GETLUNINFO:{ | 1417 | case CCISS_GETLUNINFO:{ |
1363 | LogvolInfo_struct luninfo; | 1418 | LogvolInfo_struct luninfo; |
@@ -1377,7 +1432,6 @@ static int cciss_ioctl(struct block_device *bdev, fmode_t mode, | |||
1377 | CommandList_struct *c; | 1432 | CommandList_struct *c; |
1378 | char *buff = NULL; | 1433 | char *buff = NULL; |
1379 | u64bit temp64; | 1434 | u64bit temp64; |
1380 | unsigned long flags; | ||
1381 | DECLARE_COMPLETION_ONSTACK(wait); | 1435 | DECLARE_COMPLETION_ONSTACK(wait); |
1382 | 1436 | ||
1383 | if (!arg) | 1437 | if (!arg) |
@@ -1413,7 +1467,8 @@ static int cciss_ioctl(struct block_device *bdev, fmode_t mode, | |||
1413 | } else { | 1467 | } else { |
1414 | memset(buff, 0, iocommand.buf_size); | 1468 | memset(buff, 0, iocommand.buf_size); |
1415 | } | 1469 | } |
1416 | if ((c = cmd_alloc(host, 0)) == NULL) { | 1470 | c = cmd_special_alloc(h); |
1471 | if (!c) { | ||
1417 | kfree(buff); | 1472 | kfree(buff); |
1418 | return -ENOMEM; | 1473 | return -ENOMEM; |
1419 | } | 1474 | } |
@@ -1439,7 +1494,7 @@ static int cciss_ioctl(struct block_device *bdev, fmode_t mode, | |||
1439 | 1494 | ||
1440 | /* Fill in the scatter gather information */ | 1495 | /* Fill in the scatter gather information */ |
1441 | if (iocommand.buf_size > 0) { | 1496 | if (iocommand.buf_size > 0) { |
1442 | temp64.val = pci_map_single(host->pdev, buff, | 1497 | temp64.val = pci_map_single(h->pdev, buff, |
1443 | iocommand.buf_size, | 1498 | iocommand.buf_size, |
1444 | PCI_DMA_BIDIRECTIONAL); | 1499 | PCI_DMA_BIDIRECTIONAL); |
1445 | c->SG[0].Addr.lower = temp64.val32.lower; | 1500 | c->SG[0].Addr.lower = temp64.val32.lower; |
@@ -1449,30 +1504,24 @@ static int cciss_ioctl(struct block_device *bdev, fmode_t mode, | |||
1449 | } | 1504 | } |
1450 | c->waiting = &wait; | 1505 | c->waiting = &wait; |
1451 | 1506 | ||
1452 | /* Put the request on the tail of the request queue */ | 1507 | enqueue_cmd_and_start_io(h, c); |
1453 | spin_lock_irqsave(CCISS_LOCK(ctlr), flags); | ||
1454 | addQ(&host->reqQ, c); | ||
1455 | host->Qdepth++; | ||
1456 | start_io(host); | ||
1457 | spin_unlock_irqrestore(CCISS_LOCK(ctlr), flags); | ||
1458 | |||
1459 | wait_for_completion(&wait); | 1508 | wait_for_completion(&wait); |
1460 | 1509 | ||
1461 | /* unlock the buffers from DMA */ | 1510 | /* unlock the buffers from DMA */ |
1462 | temp64.val32.lower = c->SG[0].Addr.lower; | 1511 | temp64.val32.lower = c->SG[0].Addr.lower; |
1463 | temp64.val32.upper = c->SG[0].Addr.upper; | 1512 | temp64.val32.upper = c->SG[0].Addr.upper; |
1464 | pci_unmap_single(host->pdev, (dma_addr_t) temp64.val, | 1513 | pci_unmap_single(h->pdev, (dma_addr_t) temp64.val, |
1465 | iocommand.buf_size, | 1514 | iocommand.buf_size, |
1466 | PCI_DMA_BIDIRECTIONAL); | 1515 | PCI_DMA_BIDIRECTIONAL); |
1467 | 1516 | ||
1468 | check_ioctl_unit_attention(host, c); | 1517 | check_ioctl_unit_attention(h, c); |
1469 | 1518 | ||
1470 | /* Copy the error information out */ | 1519 | /* Copy the error information out */ |
1471 | iocommand.error_info = *(c->err_info); | 1520 | iocommand.error_info = *(c->err_info); |
1472 | if (copy_to_user | 1521 | if (copy_to_user |
1473 | (argp, &iocommand, sizeof(IOCTL_Command_struct))) { | 1522 | (argp, &iocommand, sizeof(IOCTL_Command_struct))) { |
1474 | kfree(buff); | 1523 | kfree(buff); |
1475 | cmd_free(host, c, 0); | 1524 | cmd_special_free(h, c); |
1476 | return -EFAULT; | 1525 | return -EFAULT; |
1477 | } | 1526 | } |
1478 | 1527 | ||
@@ -1481,12 +1530,12 @@ static int cciss_ioctl(struct block_device *bdev, fmode_t mode, | |||
1481 | if (copy_to_user | 1530 | if (copy_to_user |
1482 | (iocommand.buf, buff, iocommand.buf_size)) { | 1531 | (iocommand.buf, buff, iocommand.buf_size)) { |
1483 | kfree(buff); | 1532 | kfree(buff); |
1484 | cmd_free(host, c, 0); | 1533 | cmd_special_free(h, c); |
1485 | return -EFAULT; | 1534 | return -EFAULT; |
1486 | } | 1535 | } |
1487 | } | 1536 | } |
1488 | kfree(buff); | 1537 | kfree(buff); |
1489 | cmd_free(host, c, 0); | 1538 | cmd_special_free(h, c); |
1490 | return 0; | 1539 | return 0; |
1491 | } | 1540 | } |
1492 | case CCISS_BIG_PASSTHRU:{ | 1541 | case CCISS_BIG_PASSTHRU:{ |
@@ -1495,7 +1544,6 @@ static int cciss_ioctl(struct block_device *bdev, fmode_t mode, | |||
1495 | unsigned char **buff = NULL; | 1544 | unsigned char **buff = NULL; |
1496 | int *buff_size = NULL; | 1545 | int *buff_size = NULL; |
1497 | u64bit temp64; | 1546 | u64bit temp64; |
1498 | unsigned long flags; | ||
1499 | BYTE sg_used = 0; | 1547 | BYTE sg_used = 0; |
1500 | int status = 0; | 1548 | int status = 0; |
1501 | int i; | 1549 | int i; |
@@ -1569,7 +1617,8 @@ static int cciss_ioctl(struct block_device *bdev, fmode_t mode, | |||
1569 | data_ptr += sz; | 1617 | data_ptr += sz; |
1570 | sg_used++; | 1618 | sg_used++; |
1571 | } | 1619 | } |
1572 | if ((c = cmd_alloc(host, 0)) == NULL) { | 1620 | c = cmd_special_alloc(h); |
1621 | if (!c) { | ||
1573 | status = -ENOMEM; | 1622 | status = -ENOMEM; |
1574 | goto cleanup1; | 1623 | goto cleanup1; |
1575 | } | 1624 | } |
@@ -1590,7 +1639,7 @@ static int cciss_ioctl(struct block_device *bdev, fmode_t mode, | |||
1590 | if (ioc->buf_size > 0) { | 1639 | if (ioc->buf_size > 0) { |
1591 | for (i = 0; i < sg_used; i++) { | 1640 | for (i = 0; i < sg_used; i++) { |
1592 | temp64.val = | 1641 | temp64.val = |
1593 | pci_map_single(host->pdev, buff[i], | 1642 | pci_map_single(h->pdev, buff[i], |
1594 | buff_size[i], | 1643 | buff_size[i], |
1595 | PCI_DMA_BIDIRECTIONAL); | 1644 | PCI_DMA_BIDIRECTIONAL); |
1596 | c->SG[i].Addr.lower = | 1645 | c->SG[i].Addr.lower = |
@@ -1602,26 +1651,21 @@ static int cciss_ioctl(struct block_device *bdev, fmode_t mode, | |||
1602 | } | 1651 | } |
1603 | } | 1652 | } |
1604 | c->waiting = &wait; | 1653 | c->waiting = &wait; |
1605 | /* Put the request on the tail of the request queue */ | 1654 | enqueue_cmd_and_start_io(h, c); |
1606 | spin_lock_irqsave(CCISS_LOCK(ctlr), flags); | ||
1607 | addQ(&host->reqQ, c); | ||
1608 | host->Qdepth++; | ||
1609 | start_io(host); | ||
1610 | spin_unlock_irqrestore(CCISS_LOCK(ctlr), flags); | ||
1611 | wait_for_completion(&wait); | 1655 | wait_for_completion(&wait); |
1612 | /* unlock the buffers from DMA */ | 1656 | /* unlock the buffers from DMA */ |
1613 | for (i = 0; i < sg_used; i++) { | 1657 | for (i = 0; i < sg_used; i++) { |
1614 | temp64.val32.lower = c->SG[i].Addr.lower; | 1658 | temp64.val32.lower = c->SG[i].Addr.lower; |
1615 | temp64.val32.upper = c->SG[i].Addr.upper; | 1659 | temp64.val32.upper = c->SG[i].Addr.upper; |
1616 | pci_unmap_single(host->pdev, | 1660 | pci_unmap_single(h->pdev, |
1617 | (dma_addr_t) temp64.val, buff_size[i], | 1661 | (dma_addr_t) temp64.val, buff_size[i], |
1618 | PCI_DMA_BIDIRECTIONAL); | 1662 | PCI_DMA_BIDIRECTIONAL); |
1619 | } | 1663 | } |
1620 | check_ioctl_unit_attention(host, c); | 1664 | check_ioctl_unit_attention(h, c); |
1621 | /* Copy the error information out */ | 1665 | /* Copy the error information out */ |
1622 | ioc->error_info = *(c->err_info); | 1666 | ioc->error_info = *(c->err_info); |
1623 | if (copy_to_user(argp, ioc, sizeof(*ioc))) { | 1667 | if (copy_to_user(argp, ioc, sizeof(*ioc))) { |
1624 | cmd_free(host, c, 0); | 1668 | cmd_special_free(h, c); |
1625 | status = -EFAULT; | 1669 | status = -EFAULT; |
1626 | goto cleanup1; | 1670 | goto cleanup1; |
1627 | } | 1671 | } |
@@ -1631,14 +1675,14 @@ static int cciss_ioctl(struct block_device *bdev, fmode_t mode, | |||
1631 | for (i = 0; i < sg_used; i++) { | 1675 | for (i = 0; i < sg_used; i++) { |
1632 | if (copy_to_user | 1676 | if (copy_to_user |
1633 | (ptr, buff[i], buff_size[i])) { | 1677 | (ptr, buff[i], buff_size[i])) { |
1634 | cmd_free(host, c, 0); | 1678 | cmd_special_free(h, c); |
1635 | status = -EFAULT; | 1679 | status = -EFAULT; |
1636 | goto cleanup1; | 1680 | goto cleanup1; |
1637 | } | 1681 | } |
1638 | ptr += buff_size[i]; | 1682 | ptr += buff_size[i]; |
1639 | } | 1683 | } |
1640 | } | 1684 | } |
1641 | cmd_free(host, c, 0); | 1685 | cmd_special_free(h, c); |
1642 | status = 0; | 1686 | status = 0; |
1643 | cleanup1: | 1687 | cleanup1: |
1644 | if (buff) { | 1688 | if (buff) { |
@@ -1726,26 +1770,26 @@ static void cciss_check_queues(ctlr_info_t *h) | |||
1726 | 1770 | ||
1727 | static void cciss_softirq_done(struct request *rq) | 1771 | static void cciss_softirq_done(struct request *rq) |
1728 | { | 1772 | { |
1729 | CommandList_struct *cmd = rq->completion_data; | 1773 | CommandList_struct *c = rq->completion_data; |
1730 | ctlr_info_t *h = hba[cmd->ctlr]; | 1774 | ctlr_info_t *h = hba[c->ctlr]; |
1731 | SGDescriptor_struct *curr_sg = cmd->SG; | 1775 | SGDescriptor_struct *curr_sg = c->SG; |
1732 | unsigned long flags; | ||
1733 | u64bit temp64; | 1776 | u64bit temp64; |
1777 | unsigned long flags; | ||
1734 | int i, ddir; | 1778 | int i, ddir; |
1735 | int sg_index = 0; | 1779 | int sg_index = 0; |
1736 | 1780 | ||
1737 | if (cmd->Request.Type.Direction == XFER_READ) | 1781 | if (c->Request.Type.Direction == XFER_READ) |
1738 | ddir = PCI_DMA_FROMDEVICE; | 1782 | ddir = PCI_DMA_FROMDEVICE; |
1739 | else | 1783 | else |
1740 | ddir = PCI_DMA_TODEVICE; | 1784 | ddir = PCI_DMA_TODEVICE; |
1741 | 1785 | ||
1742 | /* command did not need to be retried */ | 1786 | /* command did not need to be retried */ |
1743 | /* unmap the DMA mapping for all the scatter gather elements */ | 1787 | /* unmap the DMA mapping for all the scatter gather elements */ |
1744 | for (i = 0; i < cmd->Header.SGList; i++) { | 1788 | for (i = 0; i < c->Header.SGList; i++) { |
1745 | if (curr_sg[sg_index].Ext == CCISS_SG_CHAIN) { | 1789 | if (curr_sg[sg_index].Ext == CCISS_SG_CHAIN) { |
1746 | cciss_unmap_sg_chain_block(h, cmd); | 1790 | cciss_unmap_sg_chain_block(h, c); |
1747 | /* Point to the next block */ | 1791 | /* Point to the next block */ |
1748 | curr_sg = h->cmd_sg_list[cmd->cmdindex]; | 1792 | curr_sg = h->cmd_sg_list[c->cmdindex]; |
1749 | sg_index = 0; | 1793 | sg_index = 0; |
1750 | } | 1794 | } |
1751 | temp64.val32.lower = curr_sg[sg_index].Addr.lower; | 1795 | temp64.val32.lower = curr_sg[sg_index].Addr.lower; |
@@ -1755,18 +1799,16 @@ static void cciss_softirq_done(struct request *rq) | |||
1755 | ++sg_index; | 1799 | ++sg_index; |
1756 | } | 1800 | } |
1757 | 1801 | ||
1758 | #ifdef CCISS_DEBUG | 1802 | dev_dbg(&h->pdev->dev, "Done with %p\n", rq); |
1759 | printk("Done with %p\n", rq); | ||
1760 | #endif /* CCISS_DEBUG */ | ||
1761 | 1803 | ||
1762 | /* set the residual count for pc requests */ | 1804 | /* set the residual count for pc requests */ |
1763 | if (blk_pc_request(rq)) | 1805 | if (rq->cmd_type == REQ_TYPE_BLOCK_PC) |
1764 | rq->resid_len = cmd->err_info->ResidualCnt; | 1806 | rq->resid_len = c->err_info->ResidualCnt; |
1765 | 1807 | ||
1766 | blk_end_request_all(rq, (rq->errors == 0) ? 0 : -EIO); | 1808 | blk_end_request_all(rq, (rq->errors == 0) ? 0 : -EIO); |
1767 | 1809 | ||
1768 | spin_lock_irqsave(&h->lock, flags); | 1810 | spin_lock_irqsave(&h->lock, flags); |
1769 | cmd_free(h, cmd, 1); | 1811 | cmd_free(h, c); |
1770 | cciss_check_queues(h); | 1812 | cciss_check_queues(h); |
1771 | spin_unlock_irqrestore(&h->lock, flags); | 1813 | spin_unlock_irqrestore(&h->lock, flags); |
1772 | } | 1814 | } |
@@ -1782,7 +1824,7 @@ static inline void log_unit_to_scsi3addr(ctlr_info_t *h, | |||
1782 | * via the inquiry page 0. Model, vendor, and rev are set to empty strings if | 1824 | * via the inquiry page 0. Model, vendor, and rev are set to empty strings if |
1783 | * they cannot be read. | 1825 | * they cannot be read. |
1784 | */ | 1826 | */ |
1785 | static void cciss_get_device_descr(int ctlr, int logvol, | 1827 | static void cciss_get_device_descr(ctlr_info_t *h, int logvol, |
1786 | char *vendor, char *model, char *rev) | 1828 | char *vendor, char *model, char *rev) |
1787 | { | 1829 | { |
1788 | int rc; | 1830 | int rc; |
@@ -1797,8 +1839,8 @@ static void cciss_get_device_descr(int ctlr, int logvol, | |||
1797 | if (!inq_buf) | 1839 | if (!inq_buf) |
1798 | return; | 1840 | return; |
1799 | 1841 | ||
1800 | log_unit_to_scsi3addr(hba[ctlr], scsi3addr, logvol); | 1842 | log_unit_to_scsi3addr(h, scsi3addr, logvol); |
1801 | rc = sendcmd_withirq(CISS_INQUIRY, ctlr, inq_buf, sizeof(*inq_buf), 0, | 1843 | rc = sendcmd_withirq(h, CISS_INQUIRY, inq_buf, sizeof(*inq_buf), 0, |
1802 | scsi3addr, TYPE_CMD); | 1844 | scsi3addr, TYPE_CMD); |
1803 | if (rc == IO_OK) { | 1845 | if (rc == IO_OK) { |
1804 | memcpy(vendor, &inq_buf->data_byte[8], VENDOR_LEN); | 1846 | memcpy(vendor, &inq_buf->data_byte[8], VENDOR_LEN); |
@@ -1818,7 +1860,7 @@ static void cciss_get_device_descr(int ctlr, int logvol, | |||
1818 | * number cannot be had, for whatever reason, 16 bytes of 0xff | 1860 | * number cannot be had, for whatever reason, 16 bytes of 0xff |
1819 | * are returned instead. | 1861 | * are returned instead. |
1820 | */ | 1862 | */ |
1821 | static void cciss_get_serial_no(int ctlr, int logvol, | 1863 | static void cciss_get_serial_no(ctlr_info_t *h, int logvol, |
1822 | unsigned char *serial_no, int buflen) | 1864 | unsigned char *serial_no, int buflen) |
1823 | { | 1865 | { |
1824 | #define PAGE_83_INQ_BYTES 64 | 1866 | #define PAGE_83_INQ_BYTES 64 |
@@ -1833,8 +1875,8 @@ static void cciss_get_serial_no(int ctlr, int logvol, | |||
1833 | if (!buf) | 1875 | if (!buf) |
1834 | return; | 1876 | return; |
1835 | memset(serial_no, 0, buflen); | 1877 | memset(serial_no, 0, buflen); |
1836 | log_unit_to_scsi3addr(hba[ctlr], scsi3addr, logvol); | 1878 | log_unit_to_scsi3addr(h, scsi3addr, logvol); |
1837 | rc = sendcmd_withirq(CISS_INQUIRY, ctlr, buf, | 1879 | rc = sendcmd_withirq(h, CISS_INQUIRY, buf, |
1838 | PAGE_83_INQ_BYTES, 0x83, scsi3addr, TYPE_CMD); | 1880 | PAGE_83_INQ_BYTES, 0x83, scsi3addr, TYPE_CMD); |
1839 | if (rc == IO_OK) | 1881 | if (rc == IO_OK) |
1840 | memcpy(serial_no, &buf[8], buflen); | 1882 | memcpy(serial_no, &buf[8], buflen); |
@@ -1900,10 +1942,9 @@ init_queue_failure: | |||
1900 | * is also the controller node. Any changes to disk 0 will show up on | 1942 | * is also the controller node. Any changes to disk 0 will show up on |
1901 | * the next reboot. | 1943 | * the next reboot. |
1902 | */ | 1944 | */ |
1903 | static void cciss_update_drive_info(int ctlr, int drv_index, int first_time, | 1945 | static void cciss_update_drive_info(ctlr_info_t *h, int drv_index, |
1904 | int via_ioctl) | 1946 | int first_time, int via_ioctl) |
1905 | { | 1947 | { |
1906 | ctlr_info_t *h = hba[ctlr]; | ||
1907 | struct gendisk *disk; | 1948 | struct gendisk *disk; |
1908 | InquiryData_struct *inq_buff = NULL; | 1949 | InquiryData_struct *inq_buff = NULL; |
1909 | unsigned int block_size; | 1950 | unsigned int block_size; |
@@ -1920,16 +1961,16 @@ static void cciss_update_drive_info(int ctlr, int drv_index, int first_time, | |||
1920 | 1961 | ||
1921 | /* testing to see if 16-byte CDBs are already being used */ | 1962 | /* testing to see if 16-byte CDBs are already being used */ |
1922 | if (h->cciss_read == CCISS_READ_16) { | 1963 | if (h->cciss_read == CCISS_READ_16) { |
1923 | cciss_read_capacity_16(h->ctlr, drv_index, | 1964 | cciss_read_capacity_16(h, drv_index, |
1924 | &total_size, &block_size); | 1965 | &total_size, &block_size); |
1925 | 1966 | ||
1926 | } else { | 1967 | } else { |
1927 | cciss_read_capacity(ctlr, drv_index, &total_size, &block_size); | 1968 | cciss_read_capacity(h, drv_index, &total_size, &block_size); |
1928 | /* if read_capacity returns all F's this volume is >2TB */ | 1969 | /* if read_capacity returns all F's this volume is >2TB */ |
1929 | /* in size so we switch to 16-byte CDB's for all */ | 1970 | /* in size so we switch to 16-byte CDB's for all */ |
1930 | /* read/write ops */ | 1971 | /* read/write ops */ |
1931 | if (total_size == 0xFFFFFFFFULL) { | 1972 | if (total_size == 0xFFFFFFFFULL) { |
1932 | cciss_read_capacity_16(ctlr, drv_index, | 1973 | cciss_read_capacity_16(h, drv_index, |
1933 | &total_size, &block_size); | 1974 | &total_size, &block_size); |
1934 | h->cciss_read = CCISS_READ_16; | 1975 | h->cciss_read = CCISS_READ_16; |
1935 | h->cciss_write = CCISS_WRITE_16; | 1976 | h->cciss_write = CCISS_WRITE_16; |
@@ -1939,14 +1980,14 @@ static void cciss_update_drive_info(int ctlr, int drv_index, int first_time, | |||
1939 | } | 1980 | } |
1940 | } | 1981 | } |
1941 | 1982 | ||
1942 | cciss_geometry_inquiry(ctlr, drv_index, total_size, block_size, | 1983 | cciss_geometry_inquiry(h, drv_index, total_size, block_size, |
1943 | inq_buff, drvinfo); | 1984 | inq_buff, drvinfo); |
1944 | drvinfo->block_size = block_size; | 1985 | drvinfo->block_size = block_size; |
1945 | drvinfo->nr_blocks = total_size + 1; | 1986 | drvinfo->nr_blocks = total_size + 1; |
1946 | 1987 | ||
1947 | cciss_get_device_descr(ctlr, drv_index, drvinfo->vendor, | 1988 | cciss_get_device_descr(h, drv_index, drvinfo->vendor, |
1948 | drvinfo->model, drvinfo->rev); | 1989 | drvinfo->model, drvinfo->rev); |
1949 | cciss_get_serial_no(ctlr, drv_index, drvinfo->serial_no, | 1990 | cciss_get_serial_no(h, drv_index, drvinfo->serial_no, |
1950 | sizeof(drvinfo->serial_no)); | 1991 | sizeof(drvinfo->serial_no)); |
1951 | /* Save the lunid in case we deregister the disk, below. */ | 1992 | /* Save the lunid in case we deregister the disk, below. */ |
1952 | memcpy(drvinfo->LunID, h->drv[drv_index]->LunID, | 1993 | memcpy(drvinfo->LunID, h->drv[drv_index]->LunID, |
@@ -1971,10 +2012,10 @@ static void cciss_update_drive_info(int ctlr, int drv_index, int first_time, | |||
1971 | * (unless it's the first disk (for the controller node). | 2012 | * (unless it's the first disk (for the controller node). |
1972 | */ | 2013 | */ |
1973 | if (h->drv[drv_index]->raid_level != -1 && drv_index != 0) { | 2014 | if (h->drv[drv_index]->raid_level != -1 && drv_index != 0) { |
1974 | printk(KERN_WARNING "disk %d has changed.\n", drv_index); | 2015 | dev_warn(&h->pdev->dev, "disk %d has changed.\n", drv_index); |
1975 | spin_lock_irqsave(CCISS_LOCK(h->ctlr), flags); | 2016 | spin_lock_irqsave(&h->lock, flags); |
1976 | h->drv[drv_index]->busy_configuring = 1; | 2017 | h->drv[drv_index]->busy_configuring = 1; |
1977 | spin_unlock_irqrestore(CCISS_LOCK(h->ctlr), flags); | 2018 | spin_unlock_irqrestore(&h->lock, flags); |
1978 | 2019 | ||
1979 | /* deregister_disk sets h->drv[drv_index]->queue = NULL | 2020 | /* deregister_disk sets h->drv[drv_index]->queue = NULL |
1980 | * which keeps the interrupt handler from starting | 2021 | * which keeps the interrupt handler from starting |
@@ -2024,8 +2065,8 @@ static void cciss_update_drive_info(int ctlr, int drv_index, int first_time, | |||
2024 | if (cciss_add_disk(h, disk, drv_index) != 0) { | 2065 | if (cciss_add_disk(h, disk, drv_index) != 0) { |
2025 | cciss_free_gendisk(h, drv_index); | 2066 | cciss_free_gendisk(h, drv_index); |
2026 | cciss_free_drive_info(h, drv_index); | 2067 | cciss_free_drive_info(h, drv_index); |
2027 | printk(KERN_WARNING "cciss:%d could not update " | 2068 | dev_warn(&h->pdev->dev, "could not update disk %d\n", |
2028 | "disk %d\n", h->ctlr, drv_index); | 2069 | drv_index); |
2029 | --h->num_luns; | 2070 | --h->num_luns; |
2030 | } | 2071 | } |
2031 | } | 2072 | } |
@@ -2035,7 +2076,7 @@ freeret: | |||
2035 | kfree(drvinfo); | 2076 | kfree(drvinfo); |
2036 | return; | 2077 | return; |
2037 | mem_msg: | 2078 | mem_msg: |
2038 | printk(KERN_ERR "cciss: out of memory\n"); | 2079 | dev_err(&h->pdev->dev, "out of memory\n"); |
2039 | goto freeret; | 2080 | goto freeret; |
2040 | } | 2081 | } |
2041 | 2082 | ||
@@ -2127,9 +2168,9 @@ static int cciss_add_gendisk(ctlr_info_t *h, unsigned char lunid[], | |||
2127 | h->gendisk[drv_index] = | 2168 | h->gendisk[drv_index] = |
2128 | alloc_disk(1 << NWD_SHIFT); | 2169 | alloc_disk(1 << NWD_SHIFT); |
2129 | if (!h->gendisk[drv_index]) { | 2170 | if (!h->gendisk[drv_index]) { |
2130 | printk(KERN_ERR "cciss%d: could not " | 2171 | dev_err(&h->pdev->dev, |
2131 | "allocate a new disk %d\n", | 2172 | "could not allocate a new disk %d\n", |
2132 | h->ctlr, drv_index); | 2173 | drv_index); |
2133 | goto err_free_drive_info; | 2174 | goto err_free_drive_info; |
2134 | } | 2175 | } |
2135 | } | 2176 | } |
@@ -2180,8 +2221,7 @@ static void cciss_add_controller_node(ctlr_info_t *h) | |||
2180 | cciss_free_gendisk(h, drv_index); | 2221 | cciss_free_gendisk(h, drv_index); |
2181 | cciss_free_drive_info(h, drv_index); | 2222 | cciss_free_drive_info(h, drv_index); |
2182 | error: | 2223 | error: |
2183 | printk(KERN_WARNING "cciss%d: could not " | 2224 | dev_warn(&h->pdev->dev, "could not add disk 0.\n"); |
2184 | "add disk 0.\n", h->ctlr); | ||
2185 | return; | 2225 | return; |
2186 | } | 2226 | } |
2187 | 2227 | ||
@@ -2196,7 +2236,6 @@ error: | |||
2196 | static int rebuild_lun_table(ctlr_info_t *h, int first_time, | 2236 | static int rebuild_lun_table(ctlr_info_t *h, int first_time, |
2197 | int via_ioctl) | 2237 | int via_ioctl) |
2198 | { | 2238 | { |
2199 | int ctlr = h->ctlr; | ||
2200 | int num_luns; | 2239 | int num_luns; |
2201 | ReportLunData_struct *ld_buff = NULL; | 2240 | ReportLunData_struct *ld_buff = NULL; |
2202 | int return_code; | 2241 | int return_code; |
@@ -2211,27 +2250,27 @@ static int rebuild_lun_table(ctlr_info_t *h, int first_time, | |||
2211 | return -EPERM; | 2250 | return -EPERM; |
2212 | 2251 | ||
2213 | /* Set busy_configuring flag for this operation */ | 2252 | /* Set busy_configuring flag for this operation */ |
2214 | spin_lock_irqsave(CCISS_LOCK(h->ctlr), flags); | 2253 | spin_lock_irqsave(&h->lock, flags); |
2215 | if (h->busy_configuring) { | 2254 | if (h->busy_configuring) { |
2216 | spin_unlock_irqrestore(CCISS_LOCK(h->ctlr), flags); | 2255 | spin_unlock_irqrestore(&h->lock, flags); |
2217 | return -EBUSY; | 2256 | return -EBUSY; |
2218 | } | 2257 | } |
2219 | h->busy_configuring = 1; | 2258 | h->busy_configuring = 1; |
2220 | spin_unlock_irqrestore(CCISS_LOCK(h->ctlr), flags); | 2259 | spin_unlock_irqrestore(&h->lock, flags); |
2221 | 2260 | ||
2222 | ld_buff = kzalloc(sizeof(ReportLunData_struct), GFP_KERNEL); | 2261 | ld_buff = kzalloc(sizeof(ReportLunData_struct), GFP_KERNEL); |
2223 | if (ld_buff == NULL) | 2262 | if (ld_buff == NULL) |
2224 | goto mem_msg; | 2263 | goto mem_msg; |
2225 | 2264 | ||
2226 | return_code = sendcmd_withirq(CISS_REPORT_LOG, ctlr, ld_buff, | 2265 | return_code = sendcmd_withirq(h, CISS_REPORT_LOG, ld_buff, |
2227 | sizeof(ReportLunData_struct), | 2266 | sizeof(ReportLunData_struct), |
2228 | 0, CTLR_LUNID, TYPE_CMD); | 2267 | 0, CTLR_LUNID, TYPE_CMD); |
2229 | 2268 | ||
2230 | if (return_code == IO_OK) | 2269 | if (return_code == IO_OK) |
2231 | listlength = be32_to_cpu(*(__be32 *) ld_buff->LUNListLength); | 2270 | listlength = be32_to_cpu(*(__be32 *) ld_buff->LUNListLength); |
2232 | else { /* reading number of logical volumes failed */ | 2271 | else { /* reading number of logical volumes failed */ |
2233 | printk(KERN_WARNING "cciss: report logical volume" | 2272 | dev_warn(&h->pdev->dev, |
2234 | " command failed\n"); | 2273 | "report logical volume command failed\n"); |
2235 | listlength = 0; | 2274 | listlength = 0; |
2236 | goto freeret; | 2275 | goto freeret; |
2237 | } | 2276 | } |
@@ -2239,7 +2278,7 @@ static int rebuild_lun_table(ctlr_info_t *h, int first_time, | |||
2239 | num_luns = listlength / 8; /* 8 bytes per entry */ | 2278 | num_luns = listlength / 8; /* 8 bytes per entry */ |
2240 | if (num_luns > CISS_MAX_LUN) { | 2279 | if (num_luns > CISS_MAX_LUN) { |
2241 | num_luns = CISS_MAX_LUN; | 2280 | num_luns = CISS_MAX_LUN; |
2242 | printk(KERN_WARNING "cciss: more luns configured" | 2281 | dev_warn(&h->pdev->dev, "more luns configured" |
2243 | " on controller than can be handled by" | 2282 | " on controller than can be handled by" |
2244 | " this driver.\n"); | 2283 | " this driver.\n"); |
2245 | } | 2284 | } |
@@ -2270,9 +2309,9 @@ static int rebuild_lun_table(ctlr_info_t *h, int first_time, | |||
2270 | } | 2309 | } |
2271 | if (!drv_found) { | 2310 | if (!drv_found) { |
2272 | /* Deregister it from the OS, it's gone. */ | 2311 | /* Deregister it from the OS, it's gone. */ |
2273 | spin_lock_irqsave(CCISS_LOCK(h->ctlr), flags); | 2312 | spin_lock_irqsave(&h->lock, flags); |
2274 | h->drv[i]->busy_configuring = 1; | 2313 | h->drv[i]->busy_configuring = 1; |
2275 | spin_unlock_irqrestore(CCISS_LOCK(h->ctlr), flags); | 2314 | spin_unlock_irqrestore(&h->lock, flags); |
2276 | return_code = deregister_disk(h, i, 1, via_ioctl); | 2315 | return_code = deregister_disk(h, i, 1, via_ioctl); |
2277 | if (h->drv[i] != NULL) | 2316 | if (h->drv[i] != NULL) |
2278 | h->drv[i]->busy_configuring = 0; | 2317 | h->drv[i]->busy_configuring = 0; |
@@ -2311,8 +2350,7 @@ static int rebuild_lun_table(ctlr_info_t *h, int first_time, | |||
2311 | if (drv_index == -1) | 2350 | if (drv_index == -1) |
2312 | goto freeret; | 2351 | goto freeret; |
2313 | } | 2352 | } |
2314 | cciss_update_drive_info(ctlr, drv_index, first_time, | 2353 | cciss_update_drive_info(h, drv_index, first_time, via_ioctl); |
2315 | via_ioctl); | ||
2316 | } /* end for */ | 2354 | } /* end for */ |
2317 | 2355 | ||
2318 | freeret: | 2356 | freeret: |
@@ -2324,7 +2362,7 @@ freeret: | |||
2324 | */ | 2362 | */ |
2325 | return -1; | 2363 | return -1; |
2326 | mem_msg: | 2364 | mem_msg: |
2327 | printk(KERN_ERR "cciss: out of memory\n"); | 2365 | dev_err(&h->pdev->dev, "out of memory\n"); |
2328 | h->busy_configuring = 0; | 2366 | h->busy_configuring = 0; |
2329 | goto freeret; | 2367 | goto freeret; |
2330 | } | 2368 | } |
@@ -2444,11 +2482,10 @@ static int deregister_disk(ctlr_info_t *h, int drv_index, | |||
2444 | return 0; | 2482 | return 0; |
2445 | } | 2483 | } |
2446 | 2484 | ||
2447 | static int fill_cmd(CommandList_struct *c, __u8 cmd, int ctlr, void *buff, | 2485 | static int fill_cmd(ctlr_info_t *h, CommandList_struct *c, __u8 cmd, void *buff, |
2448 | size_t size, __u8 page_code, unsigned char *scsi3addr, | 2486 | size_t size, __u8 page_code, unsigned char *scsi3addr, |
2449 | int cmd_type) | 2487 | int cmd_type) |
2450 | { | 2488 | { |
2451 | ctlr_info_t *h = hba[ctlr]; | ||
2452 | u64bit buff_dma_handle; | 2489 | u64bit buff_dma_handle; |
2453 | int status = IO_OK; | 2490 | int status = IO_OK; |
2454 | 2491 | ||
@@ -2532,8 +2569,7 @@ static int fill_cmd(CommandList_struct *c, __u8 cmd, int ctlr, void *buff, | |||
2532 | c->Request.Timeout = 0; | 2569 | c->Request.Timeout = 0; |
2533 | break; | 2570 | break; |
2534 | default: | 2571 | default: |
2535 | printk(KERN_WARNING | 2572 | dev_warn(&h->pdev->dev, "Unknown Command 0x%c\n", cmd); |
2536 | "cciss%d: Unknown Command 0x%c\n", ctlr, cmd); | ||
2537 | return IO_ERROR; | 2573 | return IO_ERROR; |
2538 | } | 2574 | } |
2539 | } else if (cmd_type == TYPE_MSG) { | 2575 | } else if (cmd_type == TYPE_MSG) { |
@@ -2565,13 +2601,12 @@ static int fill_cmd(CommandList_struct *c, __u8 cmd, int ctlr, void *buff, | |||
2565 | c->Request.CDB[0] = cmd; | 2601 | c->Request.CDB[0] = cmd; |
2566 | break; | 2602 | break; |
2567 | default: | 2603 | default: |
2568 | printk(KERN_WARNING | 2604 | dev_warn(&h->pdev->dev, |
2569 | "cciss%d: unknown message type %d\n", ctlr, cmd); | 2605 | "unknown message type %d\n", cmd); |
2570 | return IO_ERROR; | 2606 | return IO_ERROR; |
2571 | } | 2607 | } |
2572 | } else { | 2608 | } else { |
2573 | printk(KERN_WARNING | 2609 | dev_warn(&h->pdev->dev, "unknown command type %d\n", cmd_type); |
2574 | "cciss%d: unknown command type %d\n", ctlr, cmd_type); | ||
2575 | return IO_ERROR; | 2610 | return IO_ERROR; |
2576 | } | 2611 | } |
2577 | /* Fill in the scatter gather information */ | 2612 | /* Fill in the scatter gather information */ |
@@ -2599,15 +2634,14 @@ static int check_target_status(ctlr_info_t *h, CommandList_struct *c) | |||
2599 | default: | 2634 | default: |
2600 | if (check_for_unit_attention(h, c)) | 2635 | if (check_for_unit_attention(h, c)) |
2601 | return IO_NEEDS_RETRY; | 2636 | return IO_NEEDS_RETRY; |
2602 | printk(KERN_WARNING "cciss%d: cmd 0x%02x " | 2637 | dev_warn(&h->pdev->dev, "cmd 0x%02x " |
2603 | "check condition, sense key = 0x%02x\n", | 2638 | "check condition, sense key = 0x%02x\n", |
2604 | h->ctlr, c->Request.CDB[0], | 2639 | c->Request.CDB[0], c->err_info->SenseInfo[2]); |
2605 | c->err_info->SenseInfo[2]); | ||
2606 | } | 2640 | } |
2607 | break; | 2641 | break; |
2608 | default: | 2642 | default: |
2609 | printk(KERN_WARNING "cciss%d: cmd 0x%02x" | 2643 | dev_warn(&h->pdev->dev, "cmd 0x%02x" |
2610 | "scsi status = 0x%02x\n", h->ctlr, | 2644 | "scsi status = 0x%02x\n", |
2611 | c->Request.CDB[0], c->err_info->ScsiStatus); | 2645 | c->Request.CDB[0], c->err_info->ScsiStatus); |
2612 | break; | 2646 | break; |
2613 | } | 2647 | } |
@@ -2630,43 +2664,42 @@ static int process_sendcmd_error(ctlr_info_t *h, CommandList_struct *c) | |||
2630 | /* expected for inquiry and report lun commands */ | 2664 | /* expected for inquiry and report lun commands */ |
2631 | break; | 2665 | break; |
2632 | case CMD_INVALID: | 2666 | case CMD_INVALID: |
2633 | printk(KERN_WARNING "cciss: cmd 0x%02x is " | 2667 | dev_warn(&h->pdev->dev, "cmd 0x%02x is " |
2634 | "reported invalid\n", c->Request.CDB[0]); | 2668 | "reported invalid\n", c->Request.CDB[0]); |
2635 | return_status = IO_ERROR; | 2669 | return_status = IO_ERROR; |
2636 | break; | 2670 | break; |
2637 | case CMD_PROTOCOL_ERR: | 2671 | case CMD_PROTOCOL_ERR: |
2638 | printk(KERN_WARNING "cciss: cmd 0x%02x has " | 2672 | dev_warn(&h->pdev->dev, "cmd 0x%02x has " |
2639 | "protocol error \n", c->Request.CDB[0]); | 2673 | "protocol error\n", c->Request.CDB[0]); |
2640 | return_status = IO_ERROR; | 2674 | return_status = IO_ERROR; |
2641 | break; | 2675 | break; |
2642 | case CMD_HARDWARE_ERR: | 2676 | case CMD_HARDWARE_ERR: |
2643 | printk(KERN_WARNING "cciss: cmd 0x%02x had " | 2677 | dev_warn(&h->pdev->dev, "cmd 0x%02x had " |
2644 | " hardware error\n", c->Request.CDB[0]); | 2678 | " hardware error\n", c->Request.CDB[0]); |
2645 | return_status = IO_ERROR; | 2679 | return_status = IO_ERROR; |
2646 | break; | 2680 | break; |
2647 | case CMD_CONNECTION_LOST: | 2681 | case CMD_CONNECTION_LOST: |
2648 | printk(KERN_WARNING "cciss: cmd 0x%02x had " | 2682 | dev_warn(&h->pdev->dev, "cmd 0x%02x had " |
2649 | "connection lost\n", c->Request.CDB[0]); | 2683 | "connection lost\n", c->Request.CDB[0]); |
2650 | return_status = IO_ERROR; | 2684 | return_status = IO_ERROR; |
2651 | break; | 2685 | break; |
2652 | case CMD_ABORTED: | 2686 | case CMD_ABORTED: |
2653 | printk(KERN_WARNING "cciss: cmd 0x%02x was " | 2687 | dev_warn(&h->pdev->dev, "cmd 0x%02x was " |
2654 | "aborted\n", c->Request.CDB[0]); | 2688 | "aborted\n", c->Request.CDB[0]); |
2655 | return_status = IO_ERROR; | 2689 | return_status = IO_ERROR; |
2656 | break; | 2690 | break; |
2657 | case CMD_ABORT_FAILED: | 2691 | case CMD_ABORT_FAILED: |
2658 | printk(KERN_WARNING "cciss: cmd 0x%02x reports " | 2692 | dev_warn(&h->pdev->dev, "cmd 0x%02x reports " |
2659 | "abort failed\n", c->Request.CDB[0]); | 2693 | "abort failed\n", c->Request.CDB[0]); |
2660 | return_status = IO_ERROR; | 2694 | return_status = IO_ERROR; |
2661 | break; | 2695 | break; |
2662 | case CMD_UNSOLICITED_ABORT: | 2696 | case CMD_UNSOLICITED_ABORT: |
2663 | printk(KERN_WARNING | 2697 | dev_warn(&h->pdev->dev, "unsolicited abort 0x%02x\n", |
2664 | "cciss%d: unsolicited abort 0x%02x\n", h->ctlr, | ||
2665 | c->Request.CDB[0]); | 2698 | c->Request.CDB[0]); |
2666 | return_status = IO_NEEDS_RETRY; | 2699 | return_status = IO_NEEDS_RETRY; |
2667 | break; | 2700 | break; |
2668 | default: | 2701 | default: |
2669 | printk(KERN_WARNING "cciss: cmd 0x%02x returned " | 2702 | dev_warn(&h->pdev->dev, "cmd 0x%02x returned " |
2670 | "unknown status %x\n", c->Request.CDB[0], | 2703 | "unknown status %x\n", c->Request.CDB[0], |
2671 | c->err_info->CommandStatus); | 2704 | c->err_info->CommandStatus); |
2672 | return_status = IO_ERROR; | 2705 | return_status = IO_ERROR; |
@@ -2679,17 +2712,11 @@ static int sendcmd_withirq_core(ctlr_info_t *h, CommandList_struct *c, | |||
2679 | { | 2712 | { |
2680 | DECLARE_COMPLETION_ONSTACK(wait); | 2713 | DECLARE_COMPLETION_ONSTACK(wait); |
2681 | u64bit buff_dma_handle; | 2714 | u64bit buff_dma_handle; |
2682 | unsigned long flags; | ||
2683 | int return_status = IO_OK; | 2715 | int return_status = IO_OK; |
2684 | 2716 | ||
2685 | resend_cmd2: | 2717 | resend_cmd2: |
2686 | c->waiting = &wait; | 2718 | c->waiting = &wait; |
2687 | /* Put the request on the tail of the queue and send it */ | 2719 | enqueue_cmd_and_start_io(h, c); |
2688 | spin_lock_irqsave(CCISS_LOCK(h->ctlr), flags); | ||
2689 | addQ(&h->reqQ, c); | ||
2690 | h->Qdepth++; | ||
2691 | start_io(h); | ||
2692 | spin_unlock_irqrestore(CCISS_LOCK(h->ctlr), flags); | ||
2693 | 2720 | ||
2694 | wait_for_completion(&wait); | 2721 | wait_for_completion(&wait); |
2695 | 2722 | ||
@@ -2700,7 +2727,7 @@ resend_cmd2: | |||
2700 | 2727 | ||
2701 | if (return_status == IO_NEEDS_RETRY && | 2728 | if (return_status == IO_NEEDS_RETRY && |
2702 | c->retry_count < MAX_CMD_RETRIES) { | 2729 | c->retry_count < MAX_CMD_RETRIES) { |
2703 | printk(KERN_WARNING "cciss%d: retrying 0x%02x\n", h->ctlr, | 2730 | dev_warn(&h->pdev->dev, "retrying 0x%02x\n", |
2704 | c->Request.CDB[0]); | 2731 | c->Request.CDB[0]); |
2705 | c->retry_count++; | 2732 | c->retry_count++; |
2706 | /* erase the old error information */ | 2733 | /* erase the old error information */ |
@@ -2719,27 +2746,26 @@ command_done: | |||
2719 | return return_status; | 2746 | return return_status; |
2720 | } | 2747 | } |
2721 | 2748 | ||
2722 | static int sendcmd_withirq(__u8 cmd, int ctlr, void *buff, size_t size, | 2749 | static int sendcmd_withirq(ctlr_info_t *h, __u8 cmd, void *buff, size_t size, |
2723 | __u8 page_code, unsigned char scsi3addr[], | 2750 | __u8 page_code, unsigned char scsi3addr[], |
2724 | int cmd_type) | 2751 | int cmd_type) |
2725 | { | 2752 | { |
2726 | ctlr_info_t *h = hba[ctlr]; | ||
2727 | CommandList_struct *c; | 2753 | CommandList_struct *c; |
2728 | int return_status; | 2754 | int return_status; |
2729 | 2755 | ||
2730 | c = cmd_alloc(h, 0); | 2756 | c = cmd_special_alloc(h); |
2731 | if (!c) | 2757 | if (!c) |
2732 | return -ENOMEM; | 2758 | return -ENOMEM; |
2733 | return_status = fill_cmd(c, cmd, ctlr, buff, size, page_code, | 2759 | return_status = fill_cmd(h, c, cmd, buff, size, page_code, |
2734 | scsi3addr, cmd_type); | 2760 | scsi3addr, cmd_type); |
2735 | if (return_status == IO_OK) | 2761 | if (return_status == IO_OK) |
2736 | return_status = sendcmd_withirq_core(h, c, 1); | 2762 | return_status = sendcmd_withirq_core(h, c, 1); |
2737 | 2763 | ||
2738 | cmd_free(h, c, 0); | 2764 | cmd_special_free(h, c); |
2739 | return return_status; | 2765 | return return_status; |
2740 | } | 2766 | } |
2741 | 2767 | ||
2742 | static void cciss_geometry_inquiry(int ctlr, int logvol, | 2768 | static void cciss_geometry_inquiry(ctlr_info_t *h, int logvol, |
2743 | sector_t total_size, | 2769 | sector_t total_size, |
2744 | unsigned int block_size, | 2770 | unsigned int block_size, |
2745 | InquiryData_struct *inq_buff, | 2771 | InquiryData_struct *inq_buff, |
@@ -2750,13 +2776,13 @@ static void cciss_geometry_inquiry(int ctlr, int logvol, | |||
2750 | unsigned char scsi3addr[8]; | 2776 | unsigned char scsi3addr[8]; |
2751 | 2777 | ||
2752 | memset(inq_buff, 0, sizeof(InquiryData_struct)); | 2778 | memset(inq_buff, 0, sizeof(InquiryData_struct)); |
2753 | log_unit_to_scsi3addr(hba[ctlr], scsi3addr, logvol); | 2779 | log_unit_to_scsi3addr(h, scsi3addr, logvol); |
2754 | return_code = sendcmd_withirq(CISS_INQUIRY, ctlr, inq_buff, | 2780 | return_code = sendcmd_withirq(h, CISS_INQUIRY, inq_buff, |
2755 | sizeof(*inq_buff), 0xC1, scsi3addr, TYPE_CMD); | 2781 | sizeof(*inq_buff), 0xC1, scsi3addr, TYPE_CMD); |
2756 | if (return_code == IO_OK) { | 2782 | if (return_code == IO_OK) { |
2757 | if (inq_buff->data_byte[8] == 0xFF) { | 2783 | if (inq_buff->data_byte[8] == 0xFF) { |
2758 | printk(KERN_WARNING | 2784 | dev_warn(&h->pdev->dev, |
2759 | "cciss: reading geometry failed, volume " | 2785 | "reading geometry failed, volume " |
2760 | "does not support reading geometry\n"); | 2786 | "does not support reading geometry\n"); |
2761 | drv->heads = 255; | 2787 | drv->heads = 255; |
2762 | drv->sectors = 32; /* Sectors per track */ | 2788 | drv->sectors = 32; /* Sectors per track */ |
@@ -2780,12 +2806,12 @@ static void cciss_geometry_inquiry(int ctlr, int logvol, | |||
2780 | drv->cylinders = real_size; | 2806 | drv->cylinders = real_size; |
2781 | } | 2807 | } |
2782 | } else { /* Get geometry failed */ | 2808 | } else { /* Get geometry failed */ |
2783 | printk(KERN_WARNING "cciss: reading geometry failed\n"); | 2809 | dev_warn(&h->pdev->dev, "reading geometry failed\n"); |
2784 | } | 2810 | } |
2785 | } | 2811 | } |
2786 | 2812 | ||
2787 | static void | 2813 | static void |
2788 | cciss_read_capacity(int ctlr, int logvol, sector_t *total_size, | 2814 | cciss_read_capacity(ctlr_info_t *h, int logvol, sector_t *total_size, |
2789 | unsigned int *block_size) | 2815 | unsigned int *block_size) |
2790 | { | 2816 | { |
2791 | ReadCapdata_struct *buf; | 2817 | ReadCapdata_struct *buf; |
@@ -2794,25 +2820,25 @@ cciss_read_capacity(int ctlr, int logvol, sector_t *total_size, | |||
2794 | 2820 | ||
2795 | buf = kzalloc(sizeof(ReadCapdata_struct), GFP_KERNEL); | 2821 | buf = kzalloc(sizeof(ReadCapdata_struct), GFP_KERNEL); |
2796 | if (!buf) { | 2822 | if (!buf) { |
2797 | printk(KERN_WARNING "cciss: out of memory\n"); | 2823 | dev_warn(&h->pdev->dev, "out of memory\n"); |
2798 | return; | 2824 | return; |
2799 | } | 2825 | } |
2800 | 2826 | ||
2801 | log_unit_to_scsi3addr(hba[ctlr], scsi3addr, logvol); | 2827 | log_unit_to_scsi3addr(h, scsi3addr, logvol); |
2802 | return_code = sendcmd_withirq(CCISS_READ_CAPACITY, ctlr, buf, | 2828 | return_code = sendcmd_withirq(h, CCISS_READ_CAPACITY, buf, |
2803 | sizeof(ReadCapdata_struct), 0, scsi3addr, TYPE_CMD); | 2829 | sizeof(ReadCapdata_struct), 0, scsi3addr, TYPE_CMD); |
2804 | if (return_code == IO_OK) { | 2830 | if (return_code == IO_OK) { |
2805 | *total_size = be32_to_cpu(*(__be32 *) buf->total_size); | 2831 | *total_size = be32_to_cpu(*(__be32 *) buf->total_size); |
2806 | *block_size = be32_to_cpu(*(__be32 *) buf->block_size); | 2832 | *block_size = be32_to_cpu(*(__be32 *) buf->block_size); |
2807 | } else { /* read capacity command failed */ | 2833 | } else { /* read capacity command failed */ |
2808 | printk(KERN_WARNING "cciss: read capacity failed\n"); | 2834 | dev_warn(&h->pdev->dev, "read capacity failed\n"); |
2809 | *total_size = 0; | 2835 | *total_size = 0; |
2810 | *block_size = BLOCK_SIZE; | 2836 | *block_size = BLOCK_SIZE; |
2811 | } | 2837 | } |
2812 | kfree(buf); | 2838 | kfree(buf); |
2813 | } | 2839 | } |
2814 | 2840 | ||
2815 | static void cciss_read_capacity_16(int ctlr, int logvol, | 2841 | static void cciss_read_capacity_16(ctlr_info_t *h, int logvol, |
2816 | sector_t *total_size, unsigned int *block_size) | 2842 | sector_t *total_size, unsigned int *block_size) |
2817 | { | 2843 | { |
2818 | ReadCapdata_struct_16 *buf; | 2844 | ReadCapdata_struct_16 *buf; |
@@ -2821,23 +2847,23 @@ static void cciss_read_capacity_16(int ctlr, int logvol, | |||
2821 | 2847 | ||
2822 | buf = kzalloc(sizeof(ReadCapdata_struct_16), GFP_KERNEL); | 2848 | buf = kzalloc(sizeof(ReadCapdata_struct_16), GFP_KERNEL); |
2823 | if (!buf) { | 2849 | if (!buf) { |
2824 | printk(KERN_WARNING "cciss: out of memory\n"); | 2850 | dev_warn(&h->pdev->dev, "out of memory\n"); |
2825 | return; | 2851 | return; |
2826 | } | 2852 | } |
2827 | 2853 | ||
2828 | log_unit_to_scsi3addr(hba[ctlr], scsi3addr, logvol); | 2854 | log_unit_to_scsi3addr(h, scsi3addr, logvol); |
2829 | return_code = sendcmd_withirq(CCISS_READ_CAPACITY_16, | 2855 | return_code = sendcmd_withirq(h, CCISS_READ_CAPACITY_16, |
2830 | ctlr, buf, sizeof(ReadCapdata_struct_16), | 2856 | buf, sizeof(ReadCapdata_struct_16), |
2831 | 0, scsi3addr, TYPE_CMD); | 2857 | 0, scsi3addr, TYPE_CMD); |
2832 | if (return_code == IO_OK) { | 2858 | if (return_code == IO_OK) { |
2833 | *total_size = be64_to_cpu(*(__be64 *) buf->total_size); | 2859 | *total_size = be64_to_cpu(*(__be64 *) buf->total_size); |
2834 | *block_size = be32_to_cpu(*(__be32 *) buf->block_size); | 2860 | *block_size = be32_to_cpu(*(__be32 *) buf->block_size); |
2835 | } else { /* read capacity command failed */ | 2861 | } else { /* read capacity command failed */ |
2836 | printk(KERN_WARNING "cciss: read capacity failed\n"); | 2862 | dev_warn(&h->pdev->dev, "read capacity failed\n"); |
2837 | *total_size = 0; | 2863 | *total_size = 0; |
2838 | *block_size = BLOCK_SIZE; | 2864 | *block_size = BLOCK_SIZE; |
2839 | } | 2865 | } |
2840 | printk(KERN_INFO " blocks= %llu block_size= %d\n", | 2866 | dev_info(&h->pdev->dev, " blocks= %llu block_size= %d\n", |
2841 | (unsigned long long)*total_size+1, *block_size); | 2867 | (unsigned long long)*total_size+1, *block_size); |
2842 | kfree(buf); | 2868 | kfree(buf); |
2843 | } | 2869 | } |
@@ -2865,17 +2891,17 @@ static int cciss_revalidate(struct gendisk *disk) | |||
2865 | 2891 | ||
2866 | inq_buff = kmalloc(sizeof(InquiryData_struct), GFP_KERNEL); | 2892 | inq_buff = kmalloc(sizeof(InquiryData_struct), GFP_KERNEL); |
2867 | if (inq_buff == NULL) { | 2893 | if (inq_buff == NULL) { |
2868 | printk(KERN_WARNING "cciss: out of memory\n"); | 2894 | dev_warn(&h->pdev->dev, "out of memory\n"); |
2869 | return 1; | 2895 | return 1; |
2870 | } | 2896 | } |
2871 | if (h->cciss_read == CCISS_READ_10) { | 2897 | if (h->cciss_read == CCISS_READ_10) { |
2872 | cciss_read_capacity(h->ctlr, logvol, | 2898 | cciss_read_capacity(h, logvol, |
2873 | &total_size, &block_size); | 2899 | &total_size, &block_size); |
2874 | } else { | 2900 | } else { |
2875 | cciss_read_capacity_16(h->ctlr, logvol, | 2901 | cciss_read_capacity_16(h, logvol, |
2876 | &total_size, &block_size); | 2902 | &total_size, &block_size); |
2877 | } | 2903 | } |
2878 | cciss_geometry_inquiry(h->ctlr, logvol, total_size, block_size, | 2904 | cciss_geometry_inquiry(h, logvol, total_size, block_size, |
2879 | inq_buff, drv); | 2905 | inq_buff, drv); |
2880 | 2906 | ||
2881 | blk_queue_logical_block_size(drv->queue, drv->block_size); | 2907 | blk_queue_logical_block_size(drv->queue, drv->block_size); |
@@ -2909,7 +2935,7 @@ static void start_io(ctlr_info_t *h) | |||
2909 | c = hlist_entry(h->reqQ.first, CommandList_struct, list); | 2935 | c = hlist_entry(h->reqQ.first, CommandList_struct, list); |
2910 | /* can't do anything if fifo is full */ | 2936 | /* can't do anything if fifo is full */ |
2911 | if ((h->access.fifo_full(h))) { | 2937 | if ((h->access.fifo_full(h))) { |
2912 | printk(KERN_WARNING "cciss: fifo full\n"); | 2938 | dev_warn(&h->pdev->dev, "fifo full\n"); |
2913 | break; | 2939 | break; |
2914 | } | 2940 | } |
2915 | 2941 | ||
@@ -2925,7 +2951,7 @@ static void start_io(ctlr_info_t *h) | |||
2925 | } | 2951 | } |
2926 | } | 2952 | } |
2927 | 2953 | ||
2928 | /* Assumes that CCISS_LOCK(h->ctlr) is held. */ | 2954 | /* Assumes that h->lock is held. */ |
2929 | /* Zeros out the error record and then resends the command back */ | 2955 | /* Zeros out the error record and then resends the command back */ |
2930 | /* to the controller */ | 2956 | /* to the controller */ |
2931 | static inline void resend_cciss_cmd(ctlr_info_t *h, CommandList_struct *c) | 2957 | static inline void resend_cciss_cmd(ctlr_info_t *h, CommandList_struct *c) |
@@ -2966,7 +2992,7 @@ static inline int evaluate_target_status(ctlr_info_t *h, | |||
2966 | driver_byte = DRIVER_OK; | 2992 | driver_byte = DRIVER_OK; |
2967 | msg_byte = cmd->err_info->CommandStatus; /* correct? seems too device specific */ | 2993 | msg_byte = cmd->err_info->CommandStatus; /* correct? seems too device specific */ |
2968 | 2994 | ||
2969 | if (blk_pc_request(cmd->rq)) | 2995 | if (cmd->rq->cmd_type == REQ_TYPE_BLOCK_PC) |
2970 | host_byte = DID_PASSTHROUGH; | 2996 | host_byte = DID_PASSTHROUGH; |
2971 | else | 2997 | else |
2972 | host_byte = DID_OK; | 2998 | host_byte = DID_OK; |
@@ -2975,8 +3001,8 @@ static inline int evaluate_target_status(ctlr_info_t *h, | |||
2975 | host_byte, driver_byte); | 3001 | host_byte, driver_byte); |
2976 | 3002 | ||
2977 | if (cmd->err_info->ScsiStatus != SAM_STAT_CHECK_CONDITION) { | 3003 | if (cmd->err_info->ScsiStatus != SAM_STAT_CHECK_CONDITION) { |
2978 | if (!blk_pc_request(cmd->rq)) | 3004 | if (cmd->rq->cmd_type != REQ_TYPE_BLOCK_PC) |
2979 | printk(KERN_WARNING "cciss: cmd %p " | 3005 | dev_warn(&h->pdev->dev, "cmd %p " |
2980 | "has SCSI Status 0x%x\n", | 3006 | "has SCSI Status 0x%x\n", |
2981 | cmd, cmd->err_info->ScsiStatus); | 3007 | cmd, cmd->err_info->ScsiStatus); |
2982 | return error_value; | 3008 | return error_value; |
@@ -2985,17 +3011,19 @@ static inline int evaluate_target_status(ctlr_info_t *h, | |||
2985 | /* check the sense key */ | 3011 | /* check the sense key */ |
2986 | sense_key = 0xf & cmd->err_info->SenseInfo[2]; | 3012 | sense_key = 0xf & cmd->err_info->SenseInfo[2]; |
2987 | /* no status or recovered error */ | 3013 | /* no status or recovered error */ |
2988 | if (((sense_key == 0x0) || (sense_key == 0x1)) && !blk_pc_request(cmd->rq)) | 3014 | if (((sense_key == 0x0) || (sense_key == 0x1)) && |
3015 | (cmd->rq->cmd_type != REQ_TYPE_BLOCK_PC)) | ||
2989 | error_value = 0; | 3016 | error_value = 0; |
2990 | 3017 | ||
2991 | if (check_for_unit_attention(h, cmd)) { | 3018 | if (check_for_unit_attention(h, cmd)) { |
2992 | *retry_cmd = !blk_pc_request(cmd->rq); | 3019 | *retry_cmd = !(cmd->rq->cmd_type == REQ_TYPE_BLOCK_PC); |
2993 | return 0; | 3020 | return 0; |
2994 | } | 3021 | } |
2995 | 3022 | ||
2996 | if (!blk_pc_request(cmd->rq)) { /* Not SG_IO or similar? */ | 3023 | /* Not SG_IO or similar? */ |
3024 | if (cmd->rq->cmd_type != REQ_TYPE_BLOCK_PC) { | ||
2997 | if (error_value != 0) | 3025 | if (error_value != 0) |
2998 | printk(KERN_WARNING "cciss: cmd %p has CHECK CONDITION" | 3026 | dev_warn(&h->pdev->dev, "cmd %p has CHECK CONDITION" |
2999 | " sense key = 0x%x\n", cmd, sense_key); | 3027 | " sense key = 0x%x\n", cmd, sense_key); |
3000 | return error_value; | 3028 | return error_value; |
3001 | } | 3029 | } |
@@ -3035,90 +3063,97 @@ static inline void complete_command(ctlr_info_t *h, CommandList_struct *cmd, | |||
3035 | rq->errors = evaluate_target_status(h, cmd, &retry_cmd); | 3063 | rq->errors = evaluate_target_status(h, cmd, &retry_cmd); |
3036 | break; | 3064 | break; |
3037 | case CMD_DATA_UNDERRUN: | 3065 | case CMD_DATA_UNDERRUN: |
3038 | if (blk_fs_request(cmd->rq)) { | 3066 | if (cmd->rq->cmd_type == REQ_TYPE_FS) { |
3039 | printk(KERN_WARNING "cciss: cmd %p has" | 3067 | dev_warn(&h->pdev->dev, "cmd %p has" |
3040 | " completed with data underrun " | 3068 | " completed with data underrun " |
3041 | "reported\n", cmd); | 3069 | "reported\n", cmd); |
3042 | cmd->rq->resid_len = cmd->err_info->ResidualCnt; | 3070 | cmd->rq->resid_len = cmd->err_info->ResidualCnt; |
3043 | } | 3071 | } |
3044 | break; | 3072 | break; |
3045 | case CMD_DATA_OVERRUN: | 3073 | case CMD_DATA_OVERRUN: |
3046 | if (blk_fs_request(cmd->rq)) | 3074 | if (cmd->rq->cmd_type == REQ_TYPE_FS) |
3047 | printk(KERN_WARNING "cciss: cmd %p has" | 3075 | dev_warn(&h->pdev->dev, "cciss: cmd %p has" |
3048 | " completed with data overrun " | 3076 | " completed with data overrun " |
3049 | "reported\n", cmd); | 3077 | "reported\n", cmd); |
3050 | break; | 3078 | break; |
3051 | case CMD_INVALID: | 3079 | case CMD_INVALID: |
3052 | printk(KERN_WARNING "cciss: cmd %p is " | 3080 | dev_warn(&h->pdev->dev, "cciss: cmd %p is " |
3053 | "reported invalid\n", cmd); | 3081 | "reported invalid\n", cmd); |
3054 | rq->errors = make_status_bytes(SAM_STAT_GOOD, | 3082 | rq->errors = make_status_bytes(SAM_STAT_GOOD, |
3055 | cmd->err_info->CommandStatus, DRIVER_OK, | 3083 | cmd->err_info->CommandStatus, DRIVER_OK, |
3056 | blk_pc_request(cmd->rq) ? DID_PASSTHROUGH : DID_ERROR); | 3084 | (cmd->rq->cmd_type == REQ_TYPE_BLOCK_PC) ? |
3085 | DID_PASSTHROUGH : DID_ERROR); | ||
3057 | break; | 3086 | break; |
3058 | case CMD_PROTOCOL_ERR: | 3087 | case CMD_PROTOCOL_ERR: |
3059 | printk(KERN_WARNING "cciss: cmd %p has " | 3088 | dev_warn(&h->pdev->dev, "cciss: cmd %p has " |
3060 | "protocol error \n", cmd); | 3089 | "protocol error\n", cmd); |
3061 | rq->errors = make_status_bytes(SAM_STAT_GOOD, | 3090 | rq->errors = make_status_bytes(SAM_STAT_GOOD, |
3062 | cmd->err_info->CommandStatus, DRIVER_OK, | 3091 | cmd->err_info->CommandStatus, DRIVER_OK, |
3063 | blk_pc_request(cmd->rq) ? DID_PASSTHROUGH : DID_ERROR); | 3092 | (cmd->rq->cmd_type == REQ_TYPE_BLOCK_PC) ? |
3093 | DID_PASSTHROUGH : DID_ERROR); | ||
3064 | break; | 3094 | break; |
3065 | case CMD_HARDWARE_ERR: | 3095 | case CMD_HARDWARE_ERR: |
3066 | printk(KERN_WARNING "cciss: cmd %p had " | 3096 | dev_warn(&h->pdev->dev, "cciss: cmd %p had " |
3067 | " hardware error\n", cmd); | 3097 | " hardware error\n", cmd); |
3068 | rq->errors = make_status_bytes(SAM_STAT_GOOD, | 3098 | rq->errors = make_status_bytes(SAM_STAT_GOOD, |
3069 | cmd->err_info->CommandStatus, DRIVER_OK, | 3099 | cmd->err_info->CommandStatus, DRIVER_OK, |
3070 | blk_pc_request(cmd->rq) ? DID_PASSTHROUGH : DID_ERROR); | 3100 | (cmd->rq->cmd_type == REQ_TYPE_BLOCK_PC) ? |
3101 | DID_PASSTHROUGH : DID_ERROR); | ||
3071 | break; | 3102 | break; |
3072 | case CMD_CONNECTION_LOST: | 3103 | case CMD_CONNECTION_LOST: |
3073 | printk(KERN_WARNING "cciss: cmd %p had " | 3104 | dev_warn(&h->pdev->dev, "cciss: cmd %p had " |
3074 | "connection lost\n", cmd); | 3105 | "connection lost\n", cmd); |
3075 | rq->errors = make_status_bytes(SAM_STAT_GOOD, | 3106 | rq->errors = make_status_bytes(SAM_STAT_GOOD, |
3076 | cmd->err_info->CommandStatus, DRIVER_OK, | 3107 | cmd->err_info->CommandStatus, DRIVER_OK, |
3077 | blk_pc_request(cmd->rq) ? DID_PASSTHROUGH : DID_ERROR); | 3108 | (cmd->rq->cmd_type == REQ_TYPE_BLOCK_PC) ? |
3109 | DID_PASSTHROUGH : DID_ERROR); | ||
3078 | break; | 3110 | break; |
3079 | case CMD_ABORTED: | 3111 | case CMD_ABORTED: |
3080 | printk(KERN_WARNING "cciss: cmd %p was " | 3112 | dev_warn(&h->pdev->dev, "cciss: cmd %p was " |
3081 | "aborted\n", cmd); | 3113 | "aborted\n", cmd); |
3082 | rq->errors = make_status_bytes(SAM_STAT_GOOD, | 3114 | rq->errors = make_status_bytes(SAM_STAT_GOOD, |
3083 | cmd->err_info->CommandStatus, DRIVER_OK, | 3115 | cmd->err_info->CommandStatus, DRIVER_OK, |
3084 | blk_pc_request(cmd->rq) ? DID_PASSTHROUGH : DID_ABORT); | 3116 | (cmd->rq->cmd_type == REQ_TYPE_BLOCK_PC) ? |
3117 | DID_PASSTHROUGH : DID_ABORT); | ||
3085 | break; | 3118 | break; |
3086 | case CMD_ABORT_FAILED: | 3119 | case CMD_ABORT_FAILED: |
3087 | printk(KERN_WARNING "cciss: cmd %p reports " | 3120 | dev_warn(&h->pdev->dev, "cciss: cmd %p reports " |
3088 | "abort failed\n", cmd); | 3121 | "abort failed\n", cmd); |
3089 | rq->errors = make_status_bytes(SAM_STAT_GOOD, | 3122 | rq->errors = make_status_bytes(SAM_STAT_GOOD, |
3090 | cmd->err_info->CommandStatus, DRIVER_OK, | 3123 | cmd->err_info->CommandStatus, DRIVER_OK, |
3091 | blk_pc_request(cmd->rq) ? DID_PASSTHROUGH : DID_ERROR); | 3124 | (cmd->rq->cmd_type == REQ_TYPE_BLOCK_PC) ? |
3125 | DID_PASSTHROUGH : DID_ERROR); | ||
3092 | break; | 3126 | break; |
3093 | case CMD_UNSOLICITED_ABORT: | 3127 | case CMD_UNSOLICITED_ABORT: |
3094 | printk(KERN_WARNING "cciss%d: unsolicited " | 3128 | dev_warn(&h->pdev->dev, "cciss%d: unsolicited " |
3095 | "abort %p\n", h->ctlr, cmd); | 3129 | "abort %p\n", h->ctlr, cmd); |
3096 | if (cmd->retry_count < MAX_CMD_RETRIES) { | 3130 | if (cmd->retry_count < MAX_CMD_RETRIES) { |
3097 | retry_cmd = 1; | 3131 | retry_cmd = 1; |
3098 | printk(KERN_WARNING | 3132 | dev_warn(&h->pdev->dev, "retrying %p\n", cmd); |
3099 | "cciss%d: retrying %p\n", h->ctlr, cmd); | ||
3100 | cmd->retry_count++; | 3133 | cmd->retry_count++; |
3101 | } else | 3134 | } else |
3102 | printk(KERN_WARNING | 3135 | dev_warn(&h->pdev->dev, |
3103 | "cciss%d: %p retried too " | 3136 | "%p retried too many times\n", cmd); |
3104 | "many times\n", h->ctlr, cmd); | ||
3105 | rq->errors = make_status_bytes(SAM_STAT_GOOD, | 3137 | rq->errors = make_status_bytes(SAM_STAT_GOOD, |
3106 | cmd->err_info->CommandStatus, DRIVER_OK, | 3138 | cmd->err_info->CommandStatus, DRIVER_OK, |
3107 | blk_pc_request(cmd->rq) ? DID_PASSTHROUGH : DID_ABORT); | 3139 | (cmd->rq->cmd_type == REQ_TYPE_BLOCK_PC) ? |
3140 | DID_PASSTHROUGH : DID_ABORT); | ||
3108 | break; | 3141 | break; |
3109 | case CMD_TIMEOUT: | 3142 | case CMD_TIMEOUT: |
3110 | printk(KERN_WARNING "cciss: cmd %p timedout\n", cmd); | 3143 | dev_warn(&h->pdev->dev, "cmd %p timedout\n", cmd); |
3111 | rq->errors = make_status_bytes(SAM_STAT_GOOD, | 3144 | rq->errors = make_status_bytes(SAM_STAT_GOOD, |
3112 | cmd->err_info->CommandStatus, DRIVER_OK, | 3145 | cmd->err_info->CommandStatus, DRIVER_OK, |
3113 | blk_pc_request(cmd->rq) ? DID_PASSTHROUGH : DID_ERROR); | 3146 | (cmd->rq->cmd_type == REQ_TYPE_BLOCK_PC) ? |
3147 | DID_PASSTHROUGH : DID_ERROR); | ||
3114 | break; | 3148 | break; |
3115 | default: | 3149 | default: |
3116 | printk(KERN_WARNING "cciss: cmd %p returned " | 3150 | dev_warn(&h->pdev->dev, "cmd %p returned " |
3117 | "unknown status %x\n", cmd, | 3151 | "unknown status %x\n", cmd, |
3118 | cmd->err_info->CommandStatus); | 3152 | cmd->err_info->CommandStatus); |
3119 | rq->errors = make_status_bytes(SAM_STAT_GOOD, | 3153 | rq->errors = make_status_bytes(SAM_STAT_GOOD, |
3120 | cmd->err_info->CommandStatus, DRIVER_OK, | 3154 | cmd->err_info->CommandStatus, DRIVER_OK, |
3121 | blk_pc_request(cmd->rq) ? DID_PASSTHROUGH : DID_ERROR); | 3155 | (cmd->rq->cmd_type == REQ_TYPE_BLOCK_PC) ? |
3156 | DID_PASSTHROUGH : DID_ERROR); | ||
3122 | } | 3157 | } |
3123 | 3158 | ||
3124 | after_error_processing: | 3159 | after_error_processing: |
@@ -3132,6 +3167,34 @@ after_error_processing: | |||
3132 | blk_complete_request(cmd->rq); | 3167 | blk_complete_request(cmd->rq); |
3133 | } | 3168 | } |
3134 | 3169 | ||
3170 | static inline u32 cciss_tag_contains_index(u32 tag) | ||
3171 | { | ||
3172 | #define DIRECT_LOOKUP_BIT 0x10 | ||
3173 | return tag & DIRECT_LOOKUP_BIT; | ||
3174 | } | ||
3175 | |||
3176 | static inline u32 cciss_tag_to_index(u32 tag) | ||
3177 | { | ||
3178 | #define DIRECT_LOOKUP_SHIFT 5 | ||
3179 | return tag >> DIRECT_LOOKUP_SHIFT; | ||
3180 | } | ||
3181 | |||
3182 | static inline u32 cciss_tag_discard_error_bits(u32 tag) | ||
3183 | { | ||
3184 | #define CCISS_ERROR_BITS 0x03 | ||
3185 | return tag & ~CCISS_ERROR_BITS; | ||
3186 | } | ||
3187 | |||
3188 | static inline void cciss_mark_tag_indexed(u32 *tag) | ||
3189 | { | ||
3190 | *tag |= DIRECT_LOOKUP_BIT; | ||
3191 | } | ||
3192 | |||
3193 | static inline void cciss_set_tag_index(u32 *tag, u32 index) | ||
3194 | { | ||
3195 | *tag |= (index << DIRECT_LOOKUP_SHIFT); | ||
3196 | } | ||
3197 | |||
3135 | /* | 3198 | /* |
3136 | * Get a request and submit it to the controller. | 3199 | * Get a request and submit it to the controller. |
3137 | */ | 3200 | */ |
@@ -3163,7 +3226,8 @@ static void do_cciss_request(struct request_queue *q) | |||
3163 | 3226 | ||
3164 | BUG_ON(creq->nr_phys_segments > h->maxsgentries); | 3227 | BUG_ON(creq->nr_phys_segments > h->maxsgentries); |
3165 | 3228 | ||
3166 | if ((c = cmd_alloc(h, 1)) == NULL) | 3229 | c = cmd_alloc(h); |
3230 | if (!c) | ||
3167 | goto full; | 3231 | goto full; |
3168 | 3232 | ||
3169 | blk_start_request(creq); | 3233 | blk_start_request(creq); |
@@ -3180,8 +3244,8 @@ static void do_cciss_request(struct request_queue *q) | |||
3180 | /* got command from pool, so use the command block index instead */ | 3244 | /* got command from pool, so use the command block index instead */ |
3181 | /* for direct lookups. */ | 3245 | /* for direct lookups. */ |
3182 | /* The first 2 bits are reserved for controller error reporting. */ | 3246 | /* The first 2 bits are reserved for controller error reporting. */ |
3183 | c->Header.Tag.lower = (c->cmdindex << 3); | 3247 | cciss_set_tag_index(&c->Header.Tag.lower, c->cmdindex); |
3184 | c->Header.Tag.lower |= 0x04; /* flag for direct lookup. */ | 3248 | cciss_mark_tag_indexed(&c->Header.Tag.lower); |
3185 | memcpy(&c->Header.LUN, drv->LunID, sizeof(drv->LunID)); | 3249 | memcpy(&c->Header.LUN, drv->LunID, sizeof(drv->LunID)); |
3186 | c->Request.CDBLen = 10; /* 12 byte commands not in FW yet; */ | 3250 | c->Request.CDBLen = 10; /* 12 byte commands not in FW yet; */ |
3187 | c->Request.Type.Type = TYPE_CMD; /* It is a command. */ | 3251 | c->Request.Type.Type = TYPE_CMD; /* It is a command. */ |
@@ -3192,11 +3256,8 @@ static void do_cciss_request(struct request_queue *q) | |||
3192 | c->Request.CDB[0] = | 3256 | c->Request.CDB[0] = |
3193 | (rq_data_dir(creq) == READ) ? h->cciss_read : h->cciss_write; | 3257 | (rq_data_dir(creq) == READ) ? h->cciss_read : h->cciss_write; |
3194 | start_blk = blk_rq_pos(creq); | 3258 | start_blk = blk_rq_pos(creq); |
3195 | #ifdef CCISS_DEBUG | 3259 | dev_dbg(&h->pdev->dev, "sector =%d nr_sectors=%d\n", |
3196 | printk(KERN_DEBUG "ciss: sector =%d nr_sectors=%d\n", | ||
3197 | (int)blk_rq_pos(creq), (int)blk_rq_sectors(creq)); | 3260 | (int)blk_rq_pos(creq), (int)blk_rq_sectors(creq)); |
3198 | #endif /* CCISS_DEBUG */ | ||
3199 | |||
3200 | sg_init_table(tmp_sg, h->maxsgentries); | 3261 | sg_init_table(tmp_sg, h->maxsgentries); |
3201 | seg = blk_rq_map_sg(q, creq, tmp_sg); | 3262 | seg = blk_rq_map_sg(q, creq, tmp_sg); |
3202 | 3263 | ||
@@ -3236,17 +3297,18 @@ static void do_cciss_request(struct request_queue *q) | |||
3236 | if (seg > h->maxSG) | 3297 | if (seg > h->maxSG) |
3237 | h->maxSG = seg; | 3298 | h->maxSG = seg; |
3238 | 3299 | ||
3239 | #ifdef CCISS_DEBUG | 3300 | dev_dbg(&h->pdev->dev, "Submitting %u sectors in %d segments " |
3240 | printk(KERN_DEBUG "cciss: Submitting %ld sectors in %d segments " | ||
3241 | "chained[%d]\n", | 3301 | "chained[%d]\n", |
3242 | blk_rq_sectors(creq), seg, chained); | 3302 | blk_rq_sectors(creq), seg, chained); |
3243 | #endif /* CCISS_DEBUG */ | ||
3244 | 3303 | ||
3245 | c->Header.SGList = c->Header.SGTotal = seg + chained; | 3304 | c->Header.SGTotal = seg + chained; |
3246 | if (seg > h->max_cmd_sgentries) | 3305 | if (seg <= h->max_cmd_sgentries) |
3306 | c->Header.SGList = c->Header.SGTotal; | ||
3307 | else | ||
3247 | c->Header.SGList = h->max_cmd_sgentries; | 3308 | c->Header.SGList = h->max_cmd_sgentries; |
3309 | set_performant_mode(h, c); | ||
3248 | 3310 | ||
3249 | if (likely(blk_fs_request(creq))) { | 3311 | if (likely(creq->cmd_type == REQ_TYPE_FS)) { |
3250 | if(h->cciss_read == CCISS_READ_10) { | 3312 | if(h->cciss_read == CCISS_READ_10) { |
3251 | c->Request.CDB[1] = 0; | 3313 | c->Request.CDB[1] = 0; |
3252 | c->Request.CDB[2] = (start_blk >> 24) & 0xff; /* MSB */ | 3314 | c->Request.CDB[2] = (start_blk >> 24) & 0xff; /* MSB */ |
@@ -3276,11 +3338,12 @@ static void do_cciss_request(struct request_queue *q) | |||
3276 | c->Request.CDB[13]= blk_rq_sectors(creq) & 0xff; | 3338 | c->Request.CDB[13]= blk_rq_sectors(creq) & 0xff; |
3277 | c->Request.CDB[14] = c->Request.CDB[15] = 0; | 3339 | c->Request.CDB[14] = c->Request.CDB[15] = 0; |
3278 | } | 3340 | } |
3279 | } else if (blk_pc_request(creq)) { | 3341 | } else if (creq->cmd_type == REQ_TYPE_BLOCK_PC) { |
3280 | c->Request.CDBLen = creq->cmd_len; | 3342 | c->Request.CDBLen = creq->cmd_len; |
3281 | memcpy(c->Request.CDB, creq->cmd, BLK_MAX_CDB); | 3343 | memcpy(c->Request.CDB, creq->cmd, BLK_MAX_CDB); |
3282 | } else { | 3344 | } else { |
3283 | printk(KERN_WARNING "cciss%d: bad request type %d\n", h->ctlr, creq->cmd_type); | 3345 | dev_warn(&h->pdev->dev, "bad request type %d\n", |
3346 | creq->cmd_type); | ||
3284 | BUG(); | 3347 | BUG(); |
3285 | } | 3348 | } |
3286 | 3349 | ||
@@ -3313,72 +3376,131 @@ static inline int interrupt_pending(ctlr_info_t *h) | |||
3313 | 3376 | ||
3314 | static inline long interrupt_not_for_us(ctlr_info_t *h) | 3377 | static inline long interrupt_not_for_us(ctlr_info_t *h) |
3315 | { | 3378 | { |
3316 | return (((h->access.intr_pending(h) == 0) || | 3379 | return ((h->access.intr_pending(h) == 0) || |
3317 | (h->interrupts_enabled == 0))); | 3380 | (h->interrupts_enabled == 0)); |
3318 | } | 3381 | } |
3319 | 3382 | ||
3320 | static irqreturn_t do_cciss_intr(int irq, void *dev_id) | 3383 | static inline int bad_tag(ctlr_info_t *h, u32 tag_index, |
3384 | u32 raw_tag) | ||
3321 | { | 3385 | { |
3322 | ctlr_info_t *h = dev_id; | 3386 | if (unlikely(tag_index >= h->nr_cmds)) { |
3387 | dev_warn(&h->pdev->dev, "bad tag 0x%08x ignored.\n", raw_tag); | ||
3388 | return 1; | ||
3389 | } | ||
3390 | return 0; | ||
3391 | } | ||
3392 | |||
3393 | static inline void finish_cmd(ctlr_info_t *h, CommandList_struct *c, | ||
3394 | u32 raw_tag) | ||
3395 | { | ||
3396 | removeQ(c); | ||
3397 | if (likely(c->cmd_type == CMD_RWREQ)) | ||
3398 | complete_command(h, c, 0); | ||
3399 | else if (c->cmd_type == CMD_IOCTL_PEND) | ||
3400 | complete(c->waiting); | ||
3401 | #ifdef CONFIG_CISS_SCSI_TAPE | ||
3402 | else if (c->cmd_type == CMD_SCSI) | ||
3403 | complete_scsi_command(c, 0, raw_tag); | ||
3404 | #endif | ||
3405 | } | ||
3406 | |||
3407 | static inline u32 next_command(ctlr_info_t *h) | ||
3408 | { | ||
3409 | u32 a; | ||
3410 | |||
3411 | if (unlikely(h->transMethod != CFGTBL_Trans_Performant)) | ||
3412 | return h->access.command_completed(h); | ||
3413 | |||
3414 | if ((*(h->reply_pool_head) & 1) == (h->reply_pool_wraparound)) { | ||
3415 | a = *(h->reply_pool_head); /* Next cmd in ring buffer */ | ||
3416 | (h->reply_pool_head)++; | ||
3417 | h->commands_outstanding--; | ||
3418 | } else { | ||
3419 | a = FIFO_EMPTY; | ||
3420 | } | ||
3421 | /* Check for wraparound */ | ||
3422 | if (h->reply_pool_head == (h->reply_pool + h->max_commands)) { | ||
3423 | h->reply_pool_head = h->reply_pool; | ||
3424 | h->reply_pool_wraparound ^= 1; | ||
3425 | } | ||
3426 | return a; | ||
3427 | } | ||
3428 | |||
3429 | /* process completion of an indexed ("direct lookup") command */ | ||
3430 | static inline u32 process_indexed_cmd(ctlr_info_t *h, u32 raw_tag) | ||
3431 | { | ||
3432 | u32 tag_index; | ||
3323 | CommandList_struct *c; | 3433 | CommandList_struct *c; |
3434 | |||
3435 | tag_index = cciss_tag_to_index(raw_tag); | ||
3436 | if (bad_tag(h, tag_index, raw_tag)) | ||
3437 | return next_command(h); | ||
3438 | c = h->cmd_pool + tag_index; | ||
3439 | finish_cmd(h, c, raw_tag); | ||
3440 | return next_command(h); | ||
3441 | } | ||
3442 | |||
3443 | /* process completion of a non-indexed command */ | ||
3444 | static inline u32 process_nonindexed_cmd(ctlr_info_t *h, u32 raw_tag) | ||
3445 | { | ||
3446 | u32 tag; | ||
3447 | CommandList_struct *c = NULL; | ||
3448 | struct hlist_node *tmp; | ||
3449 | __u32 busaddr_masked, tag_masked; | ||
3450 | |||
3451 | tag = cciss_tag_discard_error_bits(raw_tag); | ||
3452 | hlist_for_each_entry(c, tmp, &h->cmpQ, list) { | ||
3453 | busaddr_masked = cciss_tag_discard_error_bits(c->busaddr); | ||
3454 | tag_masked = cciss_tag_discard_error_bits(tag); | ||
3455 | if (busaddr_masked == tag_masked) { | ||
3456 | finish_cmd(h, c, raw_tag); | ||
3457 | return next_command(h); | ||
3458 | } | ||
3459 | } | ||
3460 | bad_tag(h, h->nr_cmds + 1, raw_tag); | ||
3461 | return next_command(h); | ||
3462 | } | ||
3463 | |||
3464 | static irqreturn_t do_cciss_intx(int irq, void *dev_id) | ||
3465 | { | ||
3466 | ctlr_info_t *h = dev_id; | ||
3324 | unsigned long flags; | 3467 | unsigned long flags; |
3325 | __u32 a, a1, a2; | 3468 | u32 raw_tag; |
3326 | 3469 | ||
3327 | if (interrupt_not_for_us(h)) | 3470 | if (interrupt_not_for_us(h)) |
3328 | return IRQ_NONE; | 3471 | return IRQ_NONE; |
3329 | /* | 3472 | spin_lock_irqsave(&h->lock, flags); |
3330 | * If there are completed commands in the completion queue, | ||
3331 | * we had better do something about it. | ||
3332 | */ | ||
3333 | spin_lock_irqsave(CCISS_LOCK(h->ctlr), flags); | ||
3334 | while (interrupt_pending(h)) { | 3473 | while (interrupt_pending(h)) { |
3335 | while ((a = get_next_completion(h)) != FIFO_EMPTY) { | 3474 | raw_tag = get_next_completion(h); |
3336 | a1 = a; | 3475 | while (raw_tag != FIFO_EMPTY) { |
3337 | if ((a & 0x04)) { | 3476 | if (cciss_tag_contains_index(raw_tag)) |
3338 | a2 = (a >> 3); | 3477 | raw_tag = process_indexed_cmd(h, raw_tag); |
3339 | if (a2 >= h->nr_cmds) { | 3478 | else |
3340 | printk(KERN_WARNING | 3479 | raw_tag = process_nonindexed_cmd(h, raw_tag); |
3341 | "cciss: controller cciss%d failed, stopping.\n", | ||
3342 | h->ctlr); | ||
3343 | spin_unlock_irqrestore(CCISS_LOCK(h->ctlr), flags); | ||
3344 | fail_all_cmds(h->ctlr); | ||
3345 | return IRQ_HANDLED; | ||
3346 | } | ||
3347 | |||
3348 | c = h->cmd_pool + a2; | ||
3349 | a = c->busaddr; | ||
3350 | |||
3351 | } else { | ||
3352 | struct hlist_node *tmp; | ||
3353 | |||
3354 | a &= ~3; | ||
3355 | c = NULL; | ||
3356 | hlist_for_each_entry(c, tmp, &h->cmpQ, list) { | ||
3357 | if (c->busaddr == a) | ||
3358 | break; | ||
3359 | } | ||
3360 | } | ||
3361 | /* | ||
3362 | * If we've found the command, take it off the | ||
3363 | * completion Q and free it | ||
3364 | */ | ||
3365 | if (c && c->busaddr == a) { | ||
3366 | removeQ(c); | ||
3367 | if (c->cmd_type == CMD_RWREQ) { | ||
3368 | complete_command(h, c, 0); | ||
3369 | } else if (c->cmd_type == CMD_IOCTL_PEND) { | ||
3370 | complete(c->waiting); | ||
3371 | } | ||
3372 | # ifdef CONFIG_CISS_SCSI_TAPE | ||
3373 | else if (c->cmd_type == CMD_SCSI) | ||
3374 | complete_scsi_command(c, 0, a1); | ||
3375 | # endif | ||
3376 | continue; | ||
3377 | } | ||
3378 | } | 3480 | } |
3379 | } | 3481 | } |
3482 | spin_unlock_irqrestore(&h->lock, flags); | ||
3483 | return IRQ_HANDLED; | ||
3484 | } | ||
3380 | 3485 | ||
3381 | spin_unlock_irqrestore(CCISS_LOCK(h->ctlr), flags); | 3486 | /* Add a second interrupt handler for MSI/MSI-X mode. In this mode we never |
3487 | * check the interrupt pending register because it is not set. | ||
3488 | */ | ||
3489 | static irqreturn_t do_cciss_msix_intr(int irq, void *dev_id) | ||
3490 | { | ||
3491 | ctlr_info_t *h = dev_id; | ||
3492 | unsigned long flags; | ||
3493 | u32 raw_tag; | ||
3494 | |||
3495 | spin_lock_irqsave(&h->lock, flags); | ||
3496 | raw_tag = get_next_completion(h); | ||
3497 | while (raw_tag != FIFO_EMPTY) { | ||
3498 | if (cciss_tag_contains_index(raw_tag)) | ||
3499 | raw_tag = process_indexed_cmd(h, raw_tag); | ||
3500 | else | ||
3501 | raw_tag = process_nonindexed_cmd(h, raw_tag); | ||
3502 | } | ||
3503 | spin_unlock_irqrestore(&h->lock, flags); | ||
3382 | return IRQ_HANDLED; | 3504 | return IRQ_HANDLED; |
3383 | } | 3505 | } |
3384 | 3506 | ||
@@ -3510,18 +3632,17 @@ static int check_for_unit_attention(ctlr_info_t *h, CommandList_struct *c) | |||
3510 | 3632 | ||
3511 | switch (c->err_info->SenseInfo[12]) { | 3633 | switch (c->err_info->SenseInfo[12]) { |
3512 | case STATE_CHANGED: | 3634 | case STATE_CHANGED: |
3513 | printk(KERN_WARNING "cciss%d: a state change " | 3635 | dev_warn(&h->pdev->dev, "a state change " |
3514 | "detected, command retried\n", h->ctlr); | 3636 | "detected, command retried\n"); |
3515 | return 1; | 3637 | return 1; |
3516 | break; | 3638 | break; |
3517 | case LUN_FAILED: | 3639 | case LUN_FAILED: |
3518 | printk(KERN_WARNING "cciss%d: LUN failure " | 3640 | dev_warn(&h->pdev->dev, "LUN failure " |
3519 | "detected, action required\n", h->ctlr); | 3641 | "detected, action required\n"); |
3520 | return 1; | 3642 | return 1; |
3521 | break; | 3643 | break; |
3522 | case REPORT_LUNS_CHANGED: | 3644 | case REPORT_LUNS_CHANGED: |
3523 | printk(KERN_WARNING "cciss%d: report LUN data " | 3645 | dev_warn(&h->pdev->dev, "report LUN data changed\n"); |
3524 | "changed\n", h->ctlr); | ||
3525 | /* | 3646 | /* |
3526 | * Here, we could call add_to_scan_list and wake up the scan thread, | 3647 | * Here, we could call add_to_scan_list and wake up the scan thread, |
3527 | * except that it's quite likely that we will get more than one | 3648 | * except that it's quite likely that we will get more than one |
@@ -3541,19 +3662,18 @@ static int check_for_unit_attention(ctlr_info_t *h, CommandList_struct *c) | |||
3541 | return 1; | 3662 | return 1; |
3542 | break; | 3663 | break; |
3543 | case POWER_OR_RESET: | 3664 | case POWER_OR_RESET: |
3544 | printk(KERN_WARNING "cciss%d: a power on " | 3665 | dev_warn(&h->pdev->dev, |
3545 | "or device reset detected\n", h->ctlr); | 3666 | "a power on or device reset detected\n"); |
3546 | return 1; | 3667 | return 1; |
3547 | break; | 3668 | break; |
3548 | case UNIT_ATTENTION_CLEARED: | 3669 | case UNIT_ATTENTION_CLEARED: |
3549 | printk(KERN_WARNING "cciss%d: unit attention " | 3670 | dev_warn(&h->pdev->dev, |
3550 | "cleared by another initiator\n", h->ctlr); | 3671 | "unit attention cleared by another initiator\n"); |
3551 | return 1; | 3672 | return 1; |
3552 | break; | 3673 | break; |
3553 | default: | 3674 | default: |
3554 | printk(KERN_WARNING "cciss%d: unknown " | 3675 | dev_warn(&h->pdev->dev, "unknown unit attention detected\n"); |
3555 | "unit attention detected\n", h->ctlr); | 3676 | return 1; |
3556 | return 1; | ||
3557 | } | 3677 | } |
3558 | } | 3678 | } |
3559 | 3679 | ||
@@ -3562,39 +3682,41 @@ static int check_for_unit_attention(ctlr_info_t *h, CommandList_struct *c) | |||
3562 | * the io functions. | 3682 | * the io functions. |
3563 | * This is for debug only. | 3683 | * This is for debug only. |
3564 | */ | 3684 | */ |
3565 | #ifdef CCISS_DEBUG | 3685 | static void print_cfg_table(ctlr_info_t *h) |
3566 | static void print_cfg_table(CfgTable_struct *tb) | ||
3567 | { | 3686 | { |
3568 | int i; | 3687 | int i; |
3569 | char temp_name[17]; | 3688 | char temp_name[17]; |
3689 | CfgTable_struct *tb = h->cfgtable; | ||
3570 | 3690 | ||
3571 | printk("Controller Configuration information\n"); | 3691 | dev_dbg(&h->pdev->dev, "Controller Configuration information\n"); |
3572 | printk("------------------------------------\n"); | 3692 | dev_dbg(&h->pdev->dev, "------------------------------------\n"); |
3573 | for (i = 0; i < 4; i++) | 3693 | for (i = 0; i < 4; i++) |
3574 | temp_name[i] = readb(&(tb->Signature[i])); | 3694 | temp_name[i] = readb(&(tb->Signature[i])); |
3575 | temp_name[4] = '\0'; | 3695 | temp_name[4] = '\0'; |
3576 | printk(" Signature = %s\n", temp_name); | 3696 | dev_dbg(&h->pdev->dev, " Signature = %s\n", temp_name); |
3577 | printk(" Spec Number = %d\n", readl(&(tb->SpecValence))); | 3697 | dev_dbg(&h->pdev->dev, " Spec Number = %d\n", |
3578 | printk(" Transport methods supported = 0x%x\n", | 3698 | readl(&(tb->SpecValence))); |
3699 | dev_dbg(&h->pdev->dev, " Transport methods supported = 0x%x\n", | ||
3579 | readl(&(tb->TransportSupport))); | 3700 | readl(&(tb->TransportSupport))); |
3580 | printk(" Transport methods active = 0x%x\n", | 3701 | dev_dbg(&h->pdev->dev, " Transport methods active = 0x%x\n", |
3581 | readl(&(tb->TransportActive))); | 3702 | readl(&(tb->TransportActive))); |
3582 | printk(" Requested transport Method = 0x%x\n", | 3703 | dev_dbg(&h->pdev->dev, " Requested transport Method = 0x%x\n", |
3583 | readl(&(tb->HostWrite.TransportRequest))); | 3704 | readl(&(tb->HostWrite.TransportRequest))); |
3584 | printk(" Coalesce Interrupt Delay = 0x%x\n", | 3705 | dev_dbg(&h->pdev->dev, " Coalesce Interrupt Delay = 0x%x\n", |
3585 | readl(&(tb->HostWrite.CoalIntDelay))); | 3706 | readl(&(tb->HostWrite.CoalIntDelay))); |
3586 | printk(" Coalesce Interrupt Count = 0x%x\n", | 3707 | dev_dbg(&h->pdev->dev, " Coalesce Interrupt Count = 0x%x\n", |
3587 | readl(&(tb->HostWrite.CoalIntCount))); | 3708 | readl(&(tb->HostWrite.CoalIntCount))); |
3588 | printk(" Max outstanding commands = 0x%d\n", | 3709 | dev_dbg(&h->pdev->dev, " Max outstanding commands = 0x%d\n", |
3589 | readl(&(tb->CmdsOutMax))); | 3710 | readl(&(tb->CmdsOutMax))); |
3590 | printk(" Bus Types = 0x%x\n", readl(&(tb->BusTypes))); | 3711 | dev_dbg(&h->pdev->dev, " Bus Types = 0x%x\n", |
3712 | readl(&(tb->BusTypes))); | ||
3591 | for (i = 0; i < 16; i++) | 3713 | for (i = 0; i < 16; i++) |
3592 | temp_name[i] = readb(&(tb->ServerName[i])); | 3714 | temp_name[i] = readb(&(tb->ServerName[i])); |
3593 | temp_name[16] = '\0'; | 3715 | temp_name[16] = '\0'; |
3594 | printk(" Server Name = %s\n", temp_name); | 3716 | dev_dbg(&h->pdev->dev, " Server Name = %s\n", temp_name); |
3595 | printk(" Heartbeat Counter = 0x%x\n\n\n", readl(&(tb->HeartBeat))); | 3717 | dev_dbg(&h->pdev->dev, " Heartbeat Counter = 0x%x\n\n\n", |
3718 | readl(&(tb->HeartBeat))); | ||
3596 | } | 3719 | } |
3597 | #endif /* CCISS_DEBUG */ | ||
3598 | 3720 | ||
3599 | static int find_PCI_BAR_index(struct pci_dev *pdev, unsigned long pci_bar_addr) | 3721 | static int find_PCI_BAR_index(struct pci_dev *pdev, unsigned long pci_bar_addr) |
3600 | { | 3722 | { |
@@ -3618,7 +3740,7 @@ static int find_PCI_BAR_index(struct pci_dev *pdev, unsigned long pci_bar_addr) | |||
3618 | offset += 8; | 3740 | offset += 8; |
3619 | break; | 3741 | break; |
3620 | default: /* reserved in PCI 2.2 */ | 3742 | default: /* reserved in PCI 2.2 */ |
3621 | printk(KERN_WARNING | 3743 | dev_warn(&pdev->dev, |
3622 | "Base address is invalid\n"); | 3744 | "Base address is invalid\n"); |
3623 | return -1; | 3745 | return -1; |
3624 | break; | 3746 | break; |
@@ -3630,12 +3752,182 @@ static int find_PCI_BAR_index(struct pci_dev *pdev, unsigned long pci_bar_addr) | |||
3630 | return -1; | 3752 | return -1; |
3631 | } | 3753 | } |
3632 | 3754 | ||
3755 | /* Fill in bucket_map[], given nsgs (the max number of | ||
3756 | * scatter gather elements supported) and bucket[], | ||
3757 | * which is an array of 8 integers. The bucket[] array | ||
3758 | * contains 8 different DMA transfer sizes (in 16 | ||
3759 | * byte increments) which the controller uses to fetch | ||
3760 | * commands. This function fills in bucket_map[], which | ||
3761 | * maps a given number of scatter gather elements to one of | ||
3762 | * the 8 DMA transfer sizes. The point of it is to allow the | ||
3763 | * controller to only do as much DMA as needed to fetch the | ||
3764 | * command, with the DMA transfer size encoded in the lower | ||
3765 | * bits of the command address. | ||
3766 | */ | ||
3767 | static void calc_bucket_map(int bucket[], int num_buckets, | ||
3768 | int nsgs, int *bucket_map) | ||
3769 | { | ||
3770 | int i, j, b, size; | ||
3771 | |||
3772 | /* even a command with 0 SGs requires 4 blocks */ | ||
3773 | #define MINIMUM_TRANSFER_BLOCKS 4 | ||
3774 | #define NUM_BUCKETS 8 | ||
3775 | /* Note, bucket_map must have nsgs+1 entries. */ | ||
3776 | for (i = 0; i <= nsgs; i++) { | ||
3777 | /* Compute size of a command with i SG entries */ | ||
3778 | size = i + MINIMUM_TRANSFER_BLOCKS; | ||
3779 | b = num_buckets; /* Assume the biggest bucket */ | ||
3780 | /* Find the bucket that is just big enough */ | ||
3781 | for (j = 0; j < 8; j++) { | ||
3782 | if (bucket[j] >= size) { | ||
3783 | b = j; | ||
3784 | break; | ||
3785 | } | ||
3786 | } | ||
3787 | /* for a command with i SG entries, use bucket b. */ | ||
3788 | bucket_map[i] = b; | ||
3789 | } | ||
3790 | } | ||
3791 | |||
3792 | static void __devinit cciss_wait_for_mode_change_ack(ctlr_info_t *h) | ||
3793 | { | ||
3794 | int i; | ||
3795 | |||
3796 | /* under certain very rare conditions, this can take awhile. | ||
3797 | * (e.g.: hot replace a failed 144GB drive in a RAID 5 set right | ||
3798 | * as we enter this code.) */ | ||
3799 | for (i = 0; i < MAX_CONFIG_WAIT; i++) { | ||
3800 | if (!(readl(h->vaddr + SA5_DOORBELL) & CFGTBL_ChangeReq)) | ||
3801 | break; | ||
3802 | msleep(10); | ||
3803 | } | ||
3804 | } | ||
3805 | |||
3806 | static __devinit void cciss_enter_performant_mode(ctlr_info_t *h) | ||
3807 | { | ||
3808 | /* This is a bit complicated. There are 8 registers on | ||
3809 | * the controller which we write to to tell it 8 different | ||
3810 | * sizes of commands which there may be. It's a way of | ||
3811 | * reducing the DMA done to fetch each command. Encoded into | ||
3812 | * each command's tag are 3 bits which communicate to the controller | ||
3813 | * which of the eight sizes that command fits within. The size of | ||
3814 | * each command depends on how many scatter gather entries there are. | ||
3815 | * Each SG entry requires 16 bytes. The eight registers are programmed | ||
3816 | * with the number of 16-byte blocks a command of that size requires. | ||
3817 | * The smallest command possible requires 5 such 16 byte blocks. | ||
3818 | * the largest command possible requires MAXSGENTRIES + 4 16-byte | ||
3819 | * blocks. Note, this only extends to the SG entries contained | ||
3820 | * within the command block, and does not extend to chained blocks | ||
3821 | * of SG elements. bft[] contains the eight values we write to | ||
3822 | * the registers. They are not evenly distributed, but have more | ||
3823 | * sizes for small commands, and fewer sizes for larger commands. | ||
3824 | */ | ||
3825 | __u32 trans_offset; | ||
3826 | int bft[8] = { 5, 6, 8, 10, 12, 20, 28, MAXSGENTRIES + 4}; | ||
3827 | /* | ||
3828 | * 5 = 1 s/g entry or 4k | ||
3829 | * 6 = 2 s/g entry or 8k | ||
3830 | * 8 = 4 s/g entry or 16k | ||
3831 | * 10 = 6 s/g entry or 24k | ||
3832 | */ | ||
3833 | unsigned long register_value; | ||
3834 | BUILD_BUG_ON(28 > MAXSGENTRIES + 4); | ||
3835 | |||
3836 | h->reply_pool_wraparound = 1; /* spec: init to 1 */ | ||
3837 | |||
3838 | /* Controller spec: zero out this buffer. */ | ||
3839 | memset(h->reply_pool, 0, h->max_commands * sizeof(__u64)); | ||
3840 | h->reply_pool_head = h->reply_pool; | ||
3841 | |||
3842 | trans_offset = readl(&(h->cfgtable->TransMethodOffset)); | ||
3843 | calc_bucket_map(bft, ARRAY_SIZE(bft), h->maxsgentries, | ||
3844 | h->blockFetchTable); | ||
3845 | writel(bft[0], &h->transtable->BlockFetch0); | ||
3846 | writel(bft[1], &h->transtable->BlockFetch1); | ||
3847 | writel(bft[2], &h->transtable->BlockFetch2); | ||
3848 | writel(bft[3], &h->transtable->BlockFetch3); | ||
3849 | writel(bft[4], &h->transtable->BlockFetch4); | ||
3850 | writel(bft[5], &h->transtable->BlockFetch5); | ||
3851 | writel(bft[6], &h->transtable->BlockFetch6); | ||
3852 | writel(bft[7], &h->transtable->BlockFetch7); | ||
3853 | |||
3854 | /* size of controller ring buffer */ | ||
3855 | writel(h->max_commands, &h->transtable->RepQSize); | ||
3856 | writel(1, &h->transtable->RepQCount); | ||
3857 | writel(0, &h->transtable->RepQCtrAddrLow32); | ||
3858 | writel(0, &h->transtable->RepQCtrAddrHigh32); | ||
3859 | writel(h->reply_pool_dhandle, &h->transtable->RepQAddr0Low32); | ||
3860 | writel(0, &h->transtable->RepQAddr0High32); | ||
3861 | writel(CFGTBL_Trans_Performant, | ||
3862 | &(h->cfgtable->HostWrite.TransportRequest)); | ||
3863 | |||
3864 | writel(CFGTBL_ChangeReq, h->vaddr + SA5_DOORBELL); | ||
3865 | cciss_wait_for_mode_change_ack(h); | ||
3866 | register_value = readl(&(h->cfgtable->TransportActive)); | ||
3867 | if (!(register_value & CFGTBL_Trans_Performant)) | ||
3868 | dev_warn(&h->pdev->dev, "cciss: unable to get board into" | ||
3869 | " performant mode\n"); | ||
3870 | } | ||
3871 | |||
3872 | static void __devinit cciss_put_controller_into_performant_mode(ctlr_info_t *h) | ||
3873 | { | ||
3874 | __u32 trans_support; | ||
3875 | |||
3876 | dev_dbg(&h->pdev->dev, "Trying to put board into Performant mode\n"); | ||
3877 | /* Attempt to put controller into performant mode if supported */ | ||
3878 | /* Does board support performant mode? */ | ||
3879 | trans_support = readl(&(h->cfgtable->TransportSupport)); | ||
3880 | if (!(trans_support & PERFORMANT_MODE)) | ||
3881 | return; | ||
3882 | |||
3883 | dev_dbg(&h->pdev->dev, "Placing controller into performant mode\n"); | ||
3884 | /* Performant mode demands commands on a 32 byte boundary | ||
3885 | * pci_alloc_consistent aligns on page boundarys already. | ||
3886 | * Just need to check if divisible by 32 | ||
3887 | */ | ||
3888 | if ((sizeof(CommandList_struct) % 32) != 0) { | ||
3889 | dev_warn(&h->pdev->dev, "%s %d %s\n", | ||
3890 | "cciss info: command size[", | ||
3891 | (int)sizeof(CommandList_struct), | ||
3892 | "] not divisible by 32, no performant mode..\n"); | ||
3893 | return; | ||
3894 | } | ||
3895 | |||
3896 | /* Performant mode ring buffer and supporting data structures */ | ||
3897 | h->reply_pool = (__u64 *)pci_alloc_consistent( | ||
3898 | h->pdev, h->max_commands * sizeof(__u64), | ||
3899 | &(h->reply_pool_dhandle)); | ||
3900 | |||
3901 | /* Need a block fetch table for performant mode */ | ||
3902 | h->blockFetchTable = kmalloc(((h->maxsgentries+1) * | ||
3903 | sizeof(__u32)), GFP_KERNEL); | ||
3904 | |||
3905 | if ((h->reply_pool == NULL) || (h->blockFetchTable == NULL)) | ||
3906 | goto clean_up; | ||
3907 | |||
3908 | cciss_enter_performant_mode(h); | ||
3909 | |||
3910 | /* Change the access methods to the performant access methods */ | ||
3911 | h->access = SA5_performant_access; | ||
3912 | h->transMethod = CFGTBL_Trans_Performant; | ||
3913 | |||
3914 | return; | ||
3915 | clean_up: | ||
3916 | kfree(h->blockFetchTable); | ||
3917 | if (h->reply_pool) | ||
3918 | pci_free_consistent(h->pdev, | ||
3919 | h->max_commands * sizeof(__u64), | ||
3920 | h->reply_pool, | ||
3921 | h->reply_pool_dhandle); | ||
3922 | return; | ||
3923 | |||
3924 | } /* cciss_put_controller_into_performant_mode */ | ||
3925 | |||
3633 | /* If MSI/MSI-X is supported by the kernel we will try to enable it on | 3926 | /* If MSI/MSI-X is supported by the kernel we will try to enable it on |
3634 | * controllers that are capable. If not, we use IO-APIC mode. | 3927 | * controllers that are capable. If not, we use IO-APIC mode. |
3635 | */ | 3928 | */ |
3636 | 3929 | ||
3637 | static void __devinit cciss_interrupt_mode(ctlr_info_t *c, | 3930 | static void __devinit cciss_interrupt_mode(ctlr_info_t *h) |
3638 | struct pci_dev *pdev, __u32 board_id) | ||
3639 | { | 3931 | { |
3640 | #ifdef CONFIG_PCI_MSI | 3932 | #ifdef CONFIG_PCI_MSI |
3641 | int err; | 3933 | int err; |
@@ -3644,268 +3936,283 @@ static void __devinit cciss_interrupt_mode(ctlr_info_t *c, | |||
3644 | }; | 3936 | }; |
3645 | 3937 | ||
3646 | /* Some boards advertise MSI but don't really support it */ | 3938 | /* Some boards advertise MSI but don't really support it */ |
3647 | if ((board_id == 0x40700E11) || | 3939 | if ((h->board_id == 0x40700E11) || (h->board_id == 0x40800E11) || |
3648 | (board_id == 0x40800E11) || | 3940 | (h->board_id == 0x40820E11) || (h->board_id == 0x40830E11)) |
3649 | (board_id == 0x40820E11) || (board_id == 0x40830E11)) | ||
3650 | goto default_int_mode; | 3941 | goto default_int_mode; |
3651 | 3942 | ||
3652 | if (pci_find_capability(pdev, PCI_CAP_ID_MSIX)) { | 3943 | if (pci_find_capability(h->pdev, PCI_CAP_ID_MSIX)) { |
3653 | err = pci_enable_msix(pdev, cciss_msix_entries, 4); | 3944 | err = pci_enable_msix(h->pdev, cciss_msix_entries, 4); |
3654 | if (!err) { | 3945 | if (!err) { |
3655 | c->intr[0] = cciss_msix_entries[0].vector; | 3946 | h->intr[0] = cciss_msix_entries[0].vector; |
3656 | c->intr[1] = cciss_msix_entries[1].vector; | 3947 | h->intr[1] = cciss_msix_entries[1].vector; |
3657 | c->intr[2] = cciss_msix_entries[2].vector; | 3948 | h->intr[2] = cciss_msix_entries[2].vector; |
3658 | c->intr[3] = cciss_msix_entries[3].vector; | 3949 | h->intr[3] = cciss_msix_entries[3].vector; |
3659 | c->msix_vector = 1; | 3950 | h->msix_vector = 1; |
3660 | return; | 3951 | return; |
3661 | } | 3952 | } |
3662 | if (err > 0) { | 3953 | if (err > 0) { |
3663 | printk(KERN_WARNING "cciss: only %d MSI-X vectors " | 3954 | dev_warn(&h->pdev->dev, |
3664 | "available\n", err); | 3955 | "only %d MSI-X vectors available\n", err); |
3665 | goto default_int_mode; | 3956 | goto default_int_mode; |
3666 | } else { | 3957 | } else { |
3667 | printk(KERN_WARNING "cciss: MSI-X init failed %d\n", | 3958 | dev_warn(&h->pdev->dev, |
3668 | err); | 3959 | "MSI-X init failed %d\n", err); |
3669 | goto default_int_mode; | 3960 | goto default_int_mode; |
3670 | } | 3961 | } |
3671 | } | 3962 | } |
3672 | if (pci_find_capability(pdev, PCI_CAP_ID_MSI)) { | 3963 | if (pci_find_capability(h->pdev, PCI_CAP_ID_MSI)) { |
3673 | if (!pci_enable_msi(pdev)) { | 3964 | if (!pci_enable_msi(h->pdev)) |
3674 | c->msi_vector = 1; | 3965 | h->msi_vector = 1; |
3675 | } else { | 3966 | else |
3676 | printk(KERN_WARNING "cciss: MSI init failed\n"); | 3967 | dev_warn(&h->pdev->dev, "MSI init failed\n"); |
3677 | } | ||
3678 | } | 3968 | } |
3679 | default_int_mode: | 3969 | default_int_mode: |
3680 | #endif /* CONFIG_PCI_MSI */ | 3970 | #endif /* CONFIG_PCI_MSI */ |
3681 | /* if we get here we're going to use the default interrupt mode */ | 3971 | /* if we get here we're going to use the default interrupt mode */ |
3682 | c->intr[SIMPLE_MODE_INT] = pdev->irq; | 3972 | h->intr[PERF_MODE_INT] = h->pdev->irq; |
3683 | return; | 3973 | return; |
3684 | } | 3974 | } |
3685 | 3975 | ||
3686 | static int __devinit cciss_pci_init(ctlr_info_t *c, struct pci_dev *pdev) | 3976 | static int __devinit cciss_lookup_board_id(struct pci_dev *pdev, u32 *board_id) |
3687 | { | 3977 | { |
3688 | ushort subsystem_vendor_id, subsystem_device_id, command; | 3978 | int i; |
3689 | __u32 board_id, scratchpad = 0; | 3979 | u32 subsystem_vendor_id, subsystem_device_id; |
3690 | __u64 cfg_offset; | ||
3691 | __u32 cfg_base_addr; | ||
3692 | __u64 cfg_base_addr_index; | ||
3693 | int i, prod_index, err; | ||
3694 | 3980 | ||
3695 | subsystem_vendor_id = pdev->subsystem_vendor; | 3981 | subsystem_vendor_id = pdev->subsystem_vendor; |
3696 | subsystem_device_id = pdev->subsystem_device; | 3982 | subsystem_device_id = pdev->subsystem_device; |
3697 | board_id = (((__u32) (subsystem_device_id << 16) & 0xffff0000) | | 3983 | *board_id = ((subsystem_device_id << 16) & 0xffff0000) | |
3698 | subsystem_vendor_id); | 3984 | subsystem_vendor_id; |
3699 | 3985 | ||
3700 | for (i = 0; i < ARRAY_SIZE(products); i++) { | 3986 | for (i = 0; i < ARRAY_SIZE(products); i++) { |
3701 | /* Stand aside for hpsa driver on request */ | 3987 | /* Stand aside for hpsa driver on request */ |
3702 | if (cciss_allow_hpsa && products[i].board_id == HPSA_BOUNDARY) | 3988 | if (cciss_allow_hpsa && products[i].board_id == HPSA_BOUNDARY) |
3703 | return -ENODEV; | 3989 | return -ENODEV; |
3704 | if (board_id == products[i].board_id) | 3990 | if (*board_id == products[i].board_id) |
3705 | break; | 3991 | return i; |
3706 | } | ||
3707 | prod_index = i; | ||
3708 | if (prod_index == ARRAY_SIZE(products)) { | ||
3709 | dev_warn(&pdev->dev, | ||
3710 | "unrecognized board ID: 0x%08lx, ignoring.\n", | ||
3711 | (unsigned long) board_id); | ||
3712 | return -ENODEV; | ||
3713 | } | 3992 | } |
3993 | dev_warn(&pdev->dev, "unrecognized board ID: 0x%08x, ignoring.\n", | ||
3994 | *board_id); | ||
3995 | return -ENODEV; | ||
3996 | } | ||
3714 | 3997 | ||
3715 | /* check to see if controller has been disabled */ | 3998 | static inline bool cciss_board_disabled(ctlr_info_t *h) |
3716 | /* BEFORE trying to enable it */ | 3999 | { |
3717 | (void)pci_read_config_word(pdev, PCI_COMMAND, &command); | 4000 | u16 command; |
3718 | if (!(command & 0x02)) { | ||
3719 | printk(KERN_WARNING | ||
3720 | "cciss: controller appears to be disabled\n"); | ||
3721 | return -ENODEV; | ||
3722 | } | ||
3723 | 4001 | ||
3724 | err = pci_enable_device(pdev); | 4002 | (void) pci_read_config_word(h->pdev, PCI_COMMAND, &command); |
3725 | if (err) { | 4003 | return ((command & PCI_COMMAND_MEMORY) == 0); |
3726 | printk(KERN_ERR "cciss: Unable to Enable PCI device\n"); | 4004 | } |
3727 | return err; | ||
3728 | } | ||
3729 | 4005 | ||
3730 | err = pci_request_regions(pdev, "cciss"); | 4006 | static int __devinit cciss_pci_find_memory_BAR(struct pci_dev *pdev, |
3731 | if (err) { | 4007 | unsigned long *memory_bar) |
3732 | printk(KERN_ERR "cciss: Cannot obtain PCI resources, " | 4008 | { |
3733 | "aborting\n"); | 4009 | int i; |
3734 | return err; | ||
3735 | } | ||
3736 | 4010 | ||
3737 | #ifdef CCISS_DEBUG | 4011 | for (i = 0; i < DEVICE_COUNT_RESOURCE; i++) |
3738 | printk("command = %x\n", command); | 4012 | if (pci_resource_flags(pdev, i) & IORESOURCE_MEM) { |
3739 | printk("irq = %x\n", pdev->irq); | 4013 | /* addressing mode bits already removed */ |
3740 | printk("board_id = %x\n", board_id); | 4014 | *memory_bar = pci_resource_start(pdev, i); |
3741 | #endif /* CCISS_DEBUG */ | 4015 | dev_dbg(&pdev->dev, "memory BAR = %lx\n", |
4016 | *memory_bar); | ||
4017 | return 0; | ||
4018 | } | ||
4019 | dev_warn(&pdev->dev, "no memory BAR found\n"); | ||
4020 | return -ENODEV; | ||
4021 | } | ||
3742 | 4022 | ||
3743 | /* If the kernel supports MSI/MSI-X we will try to enable that functionality, | 4023 | static int __devinit cciss_wait_for_board_ready(ctlr_info_t *h) |
3744 | * else we use the IO-APIC interrupt assigned to us by system ROM. | 4024 | { |
3745 | */ | 4025 | int i; |
3746 | cciss_interrupt_mode(c, pdev, board_id); | 4026 | u32 scratchpad; |
3747 | 4027 | ||
3748 | /* find the memory BAR */ | 4028 | for (i = 0; i < CCISS_BOARD_READY_ITERATIONS; i++) { |
3749 | for (i = 0; i < DEVICE_COUNT_RESOURCE; i++) { | 4029 | scratchpad = readl(h->vaddr + SA5_SCRATCHPAD_OFFSET); |
3750 | if (pci_resource_flags(pdev, i) & IORESOURCE_MEM) | 4030 | if (scratchpad == CCISS_FIRMWARE_READY) |
3751 | break; | 4031 | return 0; |
3752 | } | 4032 | msleep(CCISS_BOARD_READY_POLL_INTERVAL_MSECS); |
3753 | if (i == DEVICE_COUNT_RESOURCE) { | ||
3754 | printk(KERN_WARNING "cciss: No memory BAR found\n"); | ||
3755 | err = -ENODEV; | ||
3756 | goto err_out_free_res; | ||
3757 | } | 4033 | } |
4034 | dev_warn(&h->pdev->dev, "board not ready, timed out.\n"); | ||
4035 | return -ENODEV; | ||
4036 | } | ||
3758 | 4037 | ||
3759 | c->paddr = pci_resource_start(pdev, i); /* addressing mode bits | 4038 | static int __devinit cciss_find_cfg_addrs(struct pci_dev *pdev, |
3760 | * already removed | 4039 | void __iomem *vaddr, u32 *cfg_base_addr, u64 *cfg_base_addr_index, |
3761 | */ | 4040 | u64 *cfg_offset) |
4041 | { | ||
4042 | *cfg_base_addr = readl(vaddr + SA5_CTCFG_OFFSET); | ||
4043 | *cfg_offset = readl(vaddr + SA5_CTMEM_OFFSET); | ||
4044 | *cfg_base_addr &= (u32) 0x0000ffff; | ||
4045 | *cfg_base_addr_index = find_PCI_BAR_index(pdev, *cfg_base_addr); | ||
4046 | if (*cfg_base_addr_index == -1) { | ||
4047 | dev_warn(&pdev->dev, "cannot find cfg_base_addr_index, " | ||
4048 | "*cfg_base_addr = 0x%08x\n", *cfg_base_addr); | ||
4049 | return -ENODEV; | ||
4050 | } | ||
4051 | return 0; | ||
4052 | } | ||
3762 | 4053 | ||
3763 | #ifdef CCISS_DEBUG | 4054 | static int __devinit cciss_find_cfgtables(ctlr_info_t *h) |
3764 | printk("address 0 = %lx\n", c->paddr); | 4055 | { |
3765 | #endif /* CCISS_DEBUG */ | 4056 | u64 cfg_offset; |
3766 | c->vaddr = remap_pci_mem(c->paddr, 0x250); | 4057 | u32 cfg_base_addr; |
4058 | u64 cfg_base_addr_index; | ||
4059 | u32 trans_offset; | ||
4060 | int rc; | ||
3767 | 4061 | ||
3768 | /* Wait for the board to become ready. (PCI hotplug needs this.) | 4062 | rc = cciss_find_cfg_addrs(h->pdev, h->vaddr, &cfg_base_addr, |
3769 | * We poll for up to 120 secs, once per 100ms. */ | 4063 | &cfg_base_addr_index, &cfg_offset); |
3770 | for (i = 0; i < 1200; i++) { | 4064 | if (rc) |
3771 | scratchpad = readl(c->vaddr + SA5_SCRATCHPAD_OFFSET); | 4065 | return rc; |
3772 | if (scratchpad == CCISS_FIRMWARE_READY) | 4066 | h->cfgtable = remap_pci_mem(pci_resource_start(h->pdev, |
3773 | break; | 4067 | cfg_base_addr_index) + cfg_offset, sizeof(h->cfgtable)); |
3774 | set_current_state(TASK_INTERRUPTIBLE); | 4068 | if (!h->cfgtable) |
3775 | schedule_timeout(msecs_to_jiffies(100)); /* wait 100ms */ | 4069 | return -ENOMEM; |
3776 | } | 4070 | /* Find performant mode table. */ |
3777 | if (scratchpad != CCISS_FIRMWARE_READY) { | 4071 | trans_offset = readl(&h->cfgtable->TransMethodOffset); |
3778 | printk(KERN_WARNING "cciss: Board not ready. Timed out.\n"); | 4072 | h->transtable = remap_pci_mem(pci_resource_start(h->pdev, |
3779 | err = -ENODEV; | 4073 | cfg_base_addr_index)+cfg_offset+trans_offset, |
3780 | goto err_out_free_res; | 4074 | sizeof(*h->transtable)); |
3781 | } | 4075 | if (!h->transtable) |
4076 | return -ENOMEM; | ||
4077 | return 0; | ||
4078 | } | ||
3782 | 4079 | ||
3783 | /* get the address index number */ | 4080 | static void __devinit cciss_get_max_perf_mode_cmds(struct ctlr_info *h) |
3784 | cfg_base_addr = readl(c->vaddr + SA5_CTCFG_OFFSET); | 4081 | { |
3785 | cfg_base_addr &= (__u32) 0x0000ffff; | 4082 | h->max_commands = readl(&(h->cfgtable->MaxPerformantModeCommands)); |
3786 | #ifdef CCISS_DEBUG | 4083 | if (h->max_commands < 16) { |
3787 | printk("cfg base address = %x\n", cfg_base_addr); | 4084 | dev_warn(&h->pdev->dev, "Controller reports " |
3788 | #endif /* CCISS_DEBUG */ | 4085 | "max supported commands of %d, an obvious lie. " |
3789 | cfg_base_addr_index = find_PCI_BAR_index(pdev, cfg_base_addr); | 4086 | "Using 16. Ensure that firmware is up to date.\n", |
3790 | #ifdef CCISS_DEBUG | 4087 | h->max_commands); |
3791 | printk("cfg base address index = %llx\n", | 4088 | h->max_commands = 16; |
3792 | (unsigned long long)cfg_base_addr_index); | ||
3793 | #endif /* CCISS_DEBUG */ | ||
3794 | if (cfg_base_addr_index == -1) { | ||
3795 | printk(KERN_WARNING "cciss: Cannot find cfg_base_addr_index\n"); | ||
3796 | err = -ENODEV; | ||
3797 | goto err_out_free_res; | ||
3798 | } | 4089 | } |
4090 | } | ||
3799 | 4091 | ||
3800 | cfg_offset = readl(c->vaddr + SA5_CTMEM_OFFSET); | 4092 | /* Interrogate the hardware for some limits: |
3801 | #ifdef CCISS_DEBUG | 4093 | * max commands, max SG elements without chaining, and with chaining, |
3802 | printk("cfg offset = %llx\n", (unsigned long long)cfg_offset); | 4094 | * SG chain block size, etc. |
3803 | #endif /* CCISS_DEBUG */ | 4095 | */ |
3804 | c->cfgtable = remap_pci_mem(pci_resource_start(pdev, | 4096 | static void __devinit cciss_find_board_params(ctlr_info_t *h) |
3805 | cfg_base_addr_index) + | 4097 | { |
3806 | cfg_offset, sizeof(CfgTable_struct)); | 4098 | cciss_get_max_perf_mode_cmds(h); |
3807 | c->board_id = board_id; | 4099 | h->nr_cmds = h->max_commands - 4; /* Allow room for some ioctls */ |
3808 | 4100 | h->maxsgentries = readl(&(h->cfgtable->MaxSGElements)); | |
3809 | #ifdef CCISS_DEBUG | ||
3810 | print_cfg_table(c->cfgtable); | ||
3811 | #endif /* CCISS_DEBUG */ | ||
3812 | |||
3813 | /* Some controllers support Zero Memory Raid (ZMR). | ||
3814 | * When configured in ZMR mode the number of supported | ||
3815 | * commands drops to 64. So instead of just setting an | ||
3816 | * arbitrary value we make the driver a little smarter. | ||
3817 | * We read the config table to tell us how many commands | ||
3818 | * are supported on the controller then subtract 4 to | ||
3819 | * leave a little room for ioctl calls. | ||
3820 | */ | ||
3821 | c->max_commands = readl(&(c->cfgtable->CmdsOutMax)); | ||
3822 | c->maxsgentries = readl(&(c->cfgtable->MaxSGElements)); | ||
3823 | |||
3824 | /* | 4101 | /* |
3825 | * Limit native command to 32 s/g elements to save dma'able memory. | 4102 | * Limit in-command s/g elements to 32 save dma'able memory. |
3826 | * Howvever spec says if 0, use 31 | 4103 | * Howvever spec says if 0, use 31 |
3827 | */ | 4104 | */ |
3828 | 4105 | h->max_cmd_sgentries = 31; | |
3829 | c->max_cmd_sgentries = 31; | 4106 | if (h->maxsgentries > 512) { |
3830 | if (c->maxsgentries > 512) { | 4107 | h->max_cmd_sgentries = 32; |
3831 | c->max_cmd_sgentries = 32; | 4108 | h->chainsize = h->maxsgentries - h->max_cmd_sgentries + 1; |
3832 | c->chainsize = c->maxsgentries - c->max_cmd_sgentries + 1; | 4109 | h->maxsgentries--; /* save one for chain pointer */ |
3833 | c->maxsgentries -= 1; /* account for chain pointer */ | ||
3834 | } else { | 4110 | } else { |
3835 | c->maxsgentries = 31; /* Default to traditional value */ | 4111 | h->maxsgentries = 31; /* default to traditional values */ |
3836 | c->chainsize = 0; /* traditional */ | 4112 | h->chainsize = 0; |
3837 | } | 4113 | } |
4114 | } | ||
3838 | 4115 | ||
3839 | c->product_name = products[prod_index].product_name; | 4116 | static inline bool CISS_signature_present(ctlr_info_t *h) |
3840 | c->access = *(products[prod_index].access); | 4117 | { |
3841 | c->nr_cmds = c->max_commands - 4; | 4118 | if ((readb(&h->cfgtable->Signature[0]) != 'C') || |
3842 | if ((readb(&c->cfgtable->Signature[0]) != 'C') || | 4119 | (readb(&h->cfgtable->Signature[1]) != 'I') || |
3843 | (readb(&c->cfgtable->Signature[1]) != 'I') || | 4120 | (readb(&h->cfgtable->Signature[2]) != 'S') || |
3844 | (readb(&c->cfgtable->Signature[2]) != 'S') || | 4121 | (readb(&h->cfgtable->Signature[3]) != 'S')) { |
3845 | (readb(&c->cfgtable->Signature[3]) != 'S')) { | 4122 | dev_warn(&h->pdev->dev, "not a valid CISS config table\n"); |
3846 | printk("Does not appear to be a valid CISS config table\n"); | 4123 | return false; |
3847 | err = -ENODEV; | ||
3848 | goto err_out_free_res; | ||
3849 | } | 4124 | } |
4125 | return true; | ||
4126 | } | ||
4127 | |||
4128 | /* Need to enable prefetch in the SCSI core for 6400 in x86 */ | ||
4129 | static inline void cciss_enable_scsi_prefetch(ctlr_info_t *h) | ||
4130 | { | ||
3850 | #ifdef CONFIG_X86 | 4131 | #ifdef CONFIG_X86 |
3851 | { | 4132 | u32 prefetch; |
3852 | /* Need to enable prefetch in the SCSI core for 6400 in x86 */ | 4133 | |
3853 | __u32 prefetch; | 4134 | prefetch = readl(&(h->cfgtable->SCSI_Prefetch)); |
3854 | prefetch = readl(&(c->cfgtable->SCSI_Prefetch)); | 4135 | prefetch |= 0x100; |
3855 | prefetch |= 0x100; | 4136 | writel(prefetch, &(h->cfgtable->SCSI_Prefetch)); |
3856 | writel(prefetch, &(c->cfgtable->SCSI_Prefetch)); | ||
3857 | } | ||
3858 | #endif | 4137 | #endif |
4138 | } | ||
3859 | 4139 | ||
3860 | /* Disabling DMA prefetch and refetch for the P600. | 4140 | /* Disable DMA prefetch for the P600. Otherwise an ASIC bug may result |
3861 | * An ASIC bug may result in accesses to invalid memory addresses. | 4141 | * in a prefetch beyond physical memory. |
3862 | * We've disabled prefetch for some time now. Testing with XEN | 4142 | */ |
3863 | * kernels revealed a bug in the refetch if dom0 resides on a P600. | 4143 | static inline void cciss_p600_dma_prefetch_quirk(ctlr_info_t *h) |
3864 | */ | 4144 | { |
3865 | if(board_id == 0x3225103C) { | 4145 | u32 dma_prefetch; |
3866 | __u32 dma_prefetch; | 4146 | __u32 dma_refetch; |
3867 | __u32 dma_refetch; | 4147 | |
3868 | dma_prefetch = readl(c->vaddr + I2O_DMA1_CFG); | 4148 | if (h->board_id != 0x3225103C) |
3869 | dma_prefetch |= 0x8000; | 4149 | return; |
3870 | writel(dma_prefetch, c->vaddr + I2O_DMA1_CFG); | 4150 | dma_prefetch = readl(h->vaddr + I2O_DMA1_CFG); |
3871 | pci_read_config_dword(pdev, PCI_COMMAND_PARITY, &dma_refetch); | 4151 | dma_prefetch |= 0x8000; |
3872 | dma_refetch |= 0x1; | 4152 | writel(dma_prefetch, h->vaddr + I2O_DMA1_CFG); |
3873 | pci_write_config_dword(pdev, PCI_COMMAND_PARITY, dma_refetch); | 4153 | pci_read_config_dword(h->pdev, PCI_COMMAND_PARITY, &dma_refetch); |
4154 | dma_refetch |= 0x1; | ||
4155 | pci_write_config_dword(h->pdev, PCI_COMMAND_PARITY, dma_refetch); | ||
4156 | } | ||
4157 | |||
4158 | static int __devinit cciss_pci_init(ctlr_info_t *h) | ||
4159 | { | ||
4160 | int prod_index, err; | ||
4161 | |||
4162 | prod_index = cciss_lookup_board_id(h->pdev, &h->board_id); | ||
4163 | if (prod_index < 0) | ||
4164 | return -ENODEV; | ||
4165 | h->product_name = products[prod_index].product_name; | ||
4166 | h->access = *(products[prod_index].access); | ||
4167 | |||
4168 | if (cciss_board_disabled(h)) { | ||
4169 | dev_warn(&h->pdev->dev, "controller appears to be disabled\n"); | ||
4170 | return -ENODEV; | ||
4171 | } | ||
4172 | err = pci_enable_device(h->pdev); | ||
4173 | if (err) { | ||
4174 | dev_warn(&h->pdev->dev, "Unable to Enable PCI device\n"); | ||
4175 | return err; | ||
3874 | } | 4176 | } |
3875 | 4177 | ||
3876 | #ifdef CCISS_DEBUG | 4178 | err = pci_request_regions(h->pdev, "cciss"); |
3877 | printk("Trying to put board into Simple mode\n"); | 4179 | if (err) { |
3878 | #endif /* CCISS_DEBUG */ | 4180 | dev_warn(&h->pdev->dev, |
3879 | c->max_commands = readl(&(c->cfgtable->CmdsOutMax)); | 4181 | "Cannot obtain PCI resources, aborting\n"); |
3880 | /* Update the field, and then ring the doorbell */ | 4182 | return err; |
3881 | writel(CFGTBL_Trans_Simple, &(c->cfgtable->HostWrite.TransportRequest)); | 4183 | } |
3882 | writel(CFGTBL_ChangeReq, c->vaddr + SA5_DOORBELL); | ||
3883 | 4184 | ||
3884 | /* under certain very rare conditions, this can take awhile. | 4185 | dev_dbg(&h->pdev->dev, "irq = %x\n", h->pdev->irq); |
3885 | * (e.g.: hot replace a failed 144GB drive in a RAID 5 set right | 4186 | dev_dbg(&h->pdev->dev, "board_id = %x\n", h->board_id); |
3886 | * as we enter this code.) */ | 4187 | |
3887 | for (i = 0; i < MAX_CONFIG_WAIT; i++) { | 4188 | /* If the kernel supports MSI/MSI-X we will try to enable that functionality, |
3888 | if (!(readl(c->vaddr + SA5_DOORBELL) & CFGTBL_ChangeReq)) | 4189 | * else we use the IO-APIC interrupt assigned to us by system ROM. |
3889 | break; | 4190 | */ |
3890 | /* delay and try again */ | 4191 | cciss_interrupt_mode(h); |
3891 | set_current_state(TASK_INTERRUPTIBLE); | 4192 | err = cciss_pci_find_memory_BAR(h->pdev, &h->paddr); |
3892 | schedule_timeout(msecs_to_jiffies(1)); | 4193 | if (err) |
4194 | goto err_out_free_res; | ||
4195 | h->vaddr = remap_pci_mem(h->paddr, 0x250); | ||
4196 | if (!h->vaddr) { | ||
4197 | err = -ENOMEM; | ||
4198 | goto err_out_free_res; | ||
3893 | } | 4199 | } |
4200 | err = cciss_wait_for_board_ready(h); | ||
4201 | if (err) | ||
4202 | goto err_out_free_res; | ||
4203 | err = cciss_find_cfgtables(h); | ||
4204 | if (err) | ||
4205 | goto err_out_free_res; | ||
4206 | print_cfg_table(h); | ||
4207 | cciss_find_board_params(h); | ||
3894 | 4208 | ||
3895 | #ifdef CCISS_DEBUG | 4209 | if (!CISS_signature_present(h)) { |
3896 | printk(KERN_DEBUG "I counter got to %d %x\n", i, | ||
3897 | readl(c->vaddr + SA5_DOORBELL)); | ||
3898 | #endif /* CCISS_DEBUG */ | ||
3899 | #ifdef CCISS_DEBUG | ||
3900 | print_cfg_table(c->cfgtable); | ||
3901 | #endif /* CCISS_DEBUG */ | ||
3902 | |||
3903 | if (!(readl(&(c->cfgtable->TransportActive)) & CFGTBL_Trans_Simple)) { | ||
3904 | printk(KERN_WARNING "cciss: unable to get board into" | ||
3905 | " simple mode\n"); | ||
3906 | err = -ENODEV; | 4210 | err = -ENODEV; |
3907 | goto err_out_free_res; | 4211 | goto err_out_free_res; |
3908 | } | 4212 | } |
4213 | cciss_enable_scsi_prefetch(h); | ||
4214 | cciss_p600_dma_prefetch_quirk(h); | ||
4215 | cciss_put_controller_into_performant_mode(h); | ||
3909 | return 0; | 4216 | return 0; |
3910 | 4217 | ||
3911 | err_out_free_res: | 4218 | err_out_free_res: |
@@ -3913,42 +4220,47 @@ err_out_free_res: | |||
3913 | * Deliberately omit pci_disable_device(): it does something nasty to | 4220 | * Deliberately omit pci_disable_device(): it does something nasty to |
3914 | * Smart Array controllers that pci_enable_device does not undo | 4221 | * Smart Array controllers that pci_enable_device does not undo |
3915 | */ | 4222 | */ |
3916 | pci_release_regions(pdev); | 4223 | if (h->transtable) |
4224 | iounmap(h->transtable); | ||
4225 | if (h->cfgtable) | ||
4226 | iounmap(h->cfgtable); | ||
4227 | if (h->vaddr) | ||
4228 | iounmap(h->vaddr); | ||
4229 | pci_release_regions(h->pdev); | ||
3917 | return err; | 4230 | return err; |
3918 | } | 4231 | } |
3919 | 4232 | ||
3920 | /* Function to find the first free pointer into our hba[] array | 4233 | /* Function to find the first free pointer into our hba[] array |
3921 | * Returns -1 if no free entries are left. | 4234 | * Returns -1 if no free entries are left. |
3922 | */ | 4235 | */ |
3923 | static int alloc_cciss_hba(void) | 4236 | static int alloc_cciss_hba(struct pci_dev *pdev) |
3924 | { | 4237 | { |
3925 | int i; | 4238 | int i; |
3926 | 4239 | ||
3927 | for (i = 0; i < MAX_CTLR; i++) { | 4240 | for (i = 0; i < MAX_CTLR; i++) { |
3928 | if (!hba[i]) { | 4241 | if (!hba[i]) { |
3929 | ctlr_info_t *p; | 4242 | ctlr_info_t *h; |
3930 | 4243 | ||
3931 | p = kzalloc(sizeof(ctlr_info_t), GFP_KERNEL); | 4244 | h = kzalloc(sizeof(ctlr_info_t), GFP_KERNEL); |
3932 | if (!p) | 4245 | if (!h) |
3933 | goto Enomem; | 4246 | goto Enomem; |
3934 | hba[i] = p; | 4247 | hba[i] = h; |
3935 | return i; | 4248 | return i; |
3936 | } | 4249 | } |
3937 | } | 4250 | } |
3938 | printk(KERN_WARNING "cciss: This driver supports a maximum" | 4251 | dev_warn(&pdev->dev, "This driver supports a maximum" |
3939 | " of %d controllers.\n", MAX_CTLR); | 4252 | " of %d controllers.\n", MAX_CTLR); |
3940 | return -1; | 4253 | return -1; |
3941 | Enomem: | 4254 | Enomem: |
3942 | printk(KERN_ERR "cciss: out of memory.\n"); | 4255 | dev_warn(&pdev->dev, "out of memory.\n"); |
3943 | return -1; | 4256 | return -1; |
3944 | } | 4257 | } |
3945 | 4258 | ||
3946 | static void free_hba(int n) | 4259 | static void free_hba(ctlr_info_t *h) |
3947 | { | 4260 | { |
3948 | ctlr_info_t *h = hba[n]; | ||
3949 | int i; | 4261 | int i; |
3950 | 4262 | ||
3951 | hba[n] = NULL; | 4263 | hba[h->ctlr] = NULL; |
3952 | for (i = 0; i < h->highest_lun + 1; i++) | 4264 | for (i = 0; i < h->highest_lun + 1; i++) |
3953 | if (h->gendisk[i] != NULL) | 4265 | if (h->gendisk[i] != NULL) |
3954 | put_disk(h->gendisk[i]); | 4266 | put_disk(h->gendisk[i]); |
@@ -4028,7 +4340,8 @@ static __devinit int cciss_message(struct pci_dev *pdev, unsigned char opcode, u | |||
4028 | /* we leak the DMA buffer here ... no choice since the controller could | 4340 | /* we leak the DMA buffer here ... no choice since the controller could |
4029 | still complete the command. */ | 4341 | still complete the command. */ |
4030 | if (i == 10) { | 4342 | if (i == 10) { |
4031 | printk(KERN_ERR "cciss: controller message %02x:%02x timed out\n", | 4343 | dev_err(&pdev->dev, |
4344 | "controller message %02x:%02x timed out\n", | ||
4032 | opcode, type); | 4345 | opcode, type); |
4033 | return -ETIMEDOUT; | 4346 | return -ETIMEDOUT; |
4034 | } | 4347 | } |
@@ -4036,12 +4349,12 @@ static __devinit int cciss_message(struct pci_dev *pdev, unsigned char opcode, u | |||
4036 | pci_free_consistent(pdev, cmd_sz, cmd, paddr64); | 4349 | pci_free_consistent(pdev, cmd_sz, cmd, paddr64); |
4037 | 4350 | ||
4038 | if (tag & 2) { | 4351 | if (tag & 2) { |
4039 | printk(KERN_ERR "cciss: controller message %02x:%02x failed\n", | 4352 | dev_err(&pdev->dev, "controller message %02x:%02x failed\n", |
4040 | opcode, type); | 4353 | opcode, type); |
4041 | return -EIO; | 4354 | return -EIO; |
4042 | } | 4355 | } |
4043 | 4356 | ||
4044 | printk(KERN_INFO "cciss: controller message %02x:%02x succeeded\n", | 4357 | dev_info(&pdev->dev, "controller message %02x:%02x succeeded\n", |
4045 | opcode, type); | 4358 | opcode, type); |
4046 | return 0; | 4359 | return 0; |
4047 | } | 4360 | } |
@@ -4062,7 +4375,7 @@ static __devinit int cciss_reset_msi(struct pci_dev *pdev) | |||
4062 | if (pos) { | 4375 | if (pos) { |
4063 | pci_read_config_word(pdev, msi_control_reg(pos), &control); | 4376 | pci_read_config_word(pdev, msi_control_reg(pos), &control); |
4064 | if (control & PCI_MSI_FLAGS_ENABLE) { | 4377 | if (control & PCI_MSI_FLAGS_ENABLE) { |
4065 | printk(KERN_INFO "cciss: resetting MSI\n"); | 4378 | dev_info(&pdev->dev, "resetting MSI\n"); |
4066 | pci_write_config_word(pdev, msi_control_reg(pos), control & ~PCI_MSI_FLAGS_ENABLE); | 4379 | pci_write_config_word(pdev, msi_control_reg(pos), control & ~PCI_MSI_FLAGS_ENABLE); |
4067 | } | 4380 | } |
4068 | } | 4381 | } |
@@ -4071,7 +4384,7 @@ static __devinit int cciss_reset_msi(struct pci_dev *pdev) | |||
4071 | if (pos) { | 4384 | if (pos) { |
4072 | pci_read_config_word(pdev, msi_control_reg(pos), &control); | 4385 | pci_read_config_word(pdev, msi_control_reg(pos), &control); |
4073 | if (control & PCI_MSIX_FLAGS_ENABLE) { | 4386 | if (control & PCI_MSIX_FLAGS_ENABLE) { |
4074 | printk(KERN_INFO "cciss: resetting MSI-X\n"); | 4387 | dev_info(&pdev->dev, "resetting MSI-X\n"); |
4075 | pci_write_config_word(pdev, msi_control_reg(pos), control & ~PCI_MSIX_FLAGS_ENABLE); | 4388 | pci_write_config_word(pdev, msi_control_reg(pos), control & ~PCI_MSIX_FLAGS_ENABLE); |
4076 | } | 4389 | } |
4077 | } | 4390 | } |
@@ -4079,68 +4392,144 @@ static __devinit int cciss_reset_msi(struct pci_dev *pdev) | |||
4079 | return 0; | 4392 | return 0; |
4080 | } | 4393 | } |
4081 | 4394 | ||
4082 | /* This does a hard reset of the controller using PCI power management | 4395 | static int cciss_controller_hard_reset(struct pci_dev *pdev, |
4083 | * states. */ | 4396 | void * __iomem vaddr, bool use_doorbell) |
4084 | static __devinit int cciss_hard_reset_controller(struct pci_dev *pdev) | ||
4085 | { | 4397 | { |
4086 | u16 pmcsr, saved_config_space[32]; | 4398 | u16 pmcsr; |
4087 | int i, pos; | 4399 | int pos; |
4088 | 4400 | ||
4089 | printk(KERN_INFO "cciss: using PCI PM to reset controller\n"); | 4401 | if (use_doorbell) { |
4402 | /* For everything after the P600, the PCI power state method | ||
4403 | * of resetting the controller doesn't work, so we have this | ||
4404 | * other way using the doorbell register. | ||
4405 | */ | ||
4406 | dev_info(&pdev->dev, "using doorbell to reset controller\n"); | ||
4407 | writel(DOORBELL_CTLR_RESET, vaddr + SA5_DOORBELL); | ||
4408 | msleep(1000); | ||
4409 | } else { /* Try to do it the PCI power state way */ | ||
4410 | |||
4411 | /* Quoting from the Open CISS Specification: "The Power | ||
4412 | * Management Control/Status Register (CSR) controls the power | ||
4413 | * state of the device. The normal operating state is D0, | ||
4414 | * CSR=00h. The software off state is D3, CSR=03h. To reset | ||
4415 | * the controller, place the interface device in D3 then to D0, | ||
4416 | * this causes a secondary PCI reset which will reset the | ||
4417 | * controller." */ | ||
4418 | |||
4419 | pos = pci_find_capability(pdev, PCI_CAP_ID_PM); | ||
4420 | if (pos == 0) { | ||
4421 | dev_err(&pdev->dev, | ||
4422 | "cciss_controller_hard_reset: " | ||
4423 | "PCI PM not supported\n"); | ||
4424 | return -ENODEV; | ||
4425 | } | ||
4426 | dev_info(&pdev->dev, "using PCI PM to reset controller\n"); | ||
4427 | /* enter the D3hot power management state */ | ||
4428 | pci_read_config_word(pdev, pos + PCI_PM_CTRL, &pmcsr); | ||
4429 | pmcsr &= ~PCI_PM_CTRL_STATE_MASK; | ||
4430 | pmcsr |= PCI_D3hot; | ||
4431 | pci_write_config_word(pdev, pos + PCI_PM_CTRL, pmcsr); | ||
4090 | 4432 | ||
4091 | /* This is very nearly the same thing as | 4433 | msleep(500); |
4092 | 4434 | ||
4093 | pci_save_state(pci_dev); | 4435 | /* enter the D0 power management state */ |
4094 | pci_set_power_state(pci_dev, PCI_D3hot); | 4436 | pmcsr &= ~PCI_PM_CTRL_STATE_MASK; |
4095 | pci_set_power_state(pci_dev, PCI_D0); | 4437 | pmcsr |= PCI_D0; |
4096 | pci_restore_state(pci_dev); | 4438 | pci_write_config_word(pdev, pos + PCI_PM_CTRL, pmcsr); |
4097 | 4439 | ||
4098 | but we can't use these nice canned kernel routines on | 4440 | msleep(500); |
4099 | kexec, because they also check the MSI/MSI-X state in PCI | 4441 | } |
4100 | configuration space and do the wrong thing when it is | 4442 | return 0; |
4101 | set/cleared. Also, the pci_save/restore_state functions | 4443 | } |
4102 | violate the ordering requirements for restoring the | ||
4103 | configuration space from the CCISS document (see the | ||
4104 | comment below). So we roll our own .... */ | ||
4105 | 4444 | ||
4106 | for (i = 0; i < 32; i++) | 4445 | /* This does a hard reset of the controller using PCI power management |
4107 | pci_read_config_word(pdev, 2*i, &saved_config_space[i]); | 4446 | * states or using the doorbell register. */ |
4447 | static __devinit int cciss_kdump_hard_reset_controller(struct pci_dev *pdev) | ||
4448 | { | ||
4449 | u16 saved_config_space[32]; | ||
4450 | u64 cfg_offset; | ||
4451 | u32 cfg_base_addr; | ||
4452 | u64 cfg_base_addr_index; | ||
4453 | void __iomem *vaddr; | ||
4454 | unsigned long paddr; | ||
4455 | u32 misc_fw_support, active_transport; | ||
4456 | int rc, i; | ||
4457 | CfgTable_struct __iomem *cfgtable; | ||
4458 | bool use_doorbell; | ||
4459 | u32 board_id; | ||
4460 | |||
4461 | /* For controllers as old a the p600, this is very nearly | ||
4462 | * the same thing as | ||
4463 | * | ||
4464 | * pci_save_state(pci_dev); | ||
4465 | * pci_set_power_state(pci_dev, PCI_D3hot); | ||
4466 | * pci_set_power_state(pci_dev, PCI_D0); | ||
4467 | * pci_restore_state(pci_dev); | ||
4468 | * | ||
4469 | * but we can't use these nice canned kernel routines on | ||
4470 | * kexec, because they also check the MSI/MSI-X state in PCI | ||
4471 | * configuration space and do the wrong thing when it is | ||
4472 | * set/cleared. Also, the pci_save/restore_state functions | ||
4473 | * violate the ordering requirements for restoring the | ||
4474 | * configuration space from the CCISS document (see the | ||
4475 | * comment below). So we roll our own .... | ||
4476 | * | ||
4477 | * For controllers newer than the P600, the pci power state | ||
4478 | * method of resetting doesn't work so we have another way | ||
4479 | * using the doorbell register. | ||
4480 | */ | ||
4108 | 4481 | ||
4109 | pos = pci_find_capability(pdev, PCI_CAP_ID_PM); | 4482 | /* Exclude 640x boards. These are two pci devices in one slot |
4110 | if (pos == 0) { | 4483 | * which share a battery backed cache module. One controls the |
4111 | printk(KERN_ERR "cciss_reset_controller: PCI PM not supported\n"); | 4484 | * cache, the other accesses the cache through the one that controls |
4485 | * it. If we reset the one controlling the cache, the other will | ||
4486 | * likely not be happy. Just forbid resetting this conjoined mess. | ||
4487 | */ | ||
4488 | cciss_lookup_board_id(pdev, &board_id); | ||
4489 | if (board_id == 0x409C0E11 || board_id == 0x409D0E11) { | ||
4490 | dev_warn(&pdev->dev, "Cannot reset Smart Array 640x " | ||
4491 | "due to shared cache module."); | ||
4112 | return -ENODEV; | 4492 | return -ENODEV; |
4113 | } | 4493 | } |
4114 | 4494 | ||
4115 | /* Quoting from the Open CISS Specification: "The Power | 4495 | for (i = 0; i < 32; i++) |
4116 | * Management Control/Status Register (CSR) controls the power | 4496 | pci_read_config_word(pdev, 2*i, &saved_config_space[i]); |
4117 | * state of the device. The normal operating state is D0, | ||
4118 | * CSR=00h. The software off state is D3, CSR=03h. To reset | ||
4119 | * the controller, place the interface device in D3 then to | ||
4120 | * D0, this causes a secondary PCI reset which will reset the | ||
4121 | * controller." */ | ||
4122 | 4497 | ||
4123 | /* enter the D3hot power management state */ | 4498 | /* find the first memory BAR, so we can find the cfg table */ |
4124 | pci_read_config_word(pdev, pos + PCI_PM_CTRL, &pmcsr); | 4499 | rc = cciss_pci_find_memory_BAR(pdev, &paddr); |
4125 | pmcsr &= ~PCI_PM_CTRL_STATE_MASK; | 4500 | if (rc) |
4126 | pmcsr |= PCI_D3hot; | 4501 | return rc; |
4127 | pci_write_config_word(pdev, pos + PCI_PM_CTRL, pmcsr); | 4502 | vaddr = remap_pci_mem(paddr, 0x250); |
4503 | if (!vaddr) | ||
4504 | return -ENOMEM; | ||
4128 | 4505 | ||
4129 | schedule_timeout_uninterruptible(HZ >> 1); | 4506 | /* find cfgtable in order to check if reset via doorbell is supported */ |
4507 | rc = cciss_find_cfg_addrs(pdev, vaddr, &cfg_base_addr, | ||
4508 | &cfg_base_addr_index, &cfg_offset); | ||
4509 | if (rc) | ||
4510 | goto unmap_vaddr; | ||
4511 | cfgtable = remap_pci_mem(pci_resource_start(pdev, | ||
4512 | cfg_base_addr_index) + cfg_offset, sizeof(*cfgtable)); | ||
4513 | if (!cfgtable) { | ||
4514 | rc = -ENOMEM; | ||
4515 | goto unmap_vaddr; | ||
4516 | } | ||
4130 | 4517 | ||
4131 | /* enter the D0 power management state */ | 4518 | /* If reset via doorbell register is supported, use that. */ |
4132 | pmcsr &= ~PCI_PM_CTRL_STATE_MASK; | 4519 | misc_fw_support = readl(&cfgtable->misc_fw_support); |
4133 | pmcsr |= PCI_D0; | 4520 | use_doorbell = misc_fw_support & MISC_FW_DOORBELL_RESET; |
4134 | pci_write_config_word(pdev, pos + PCI_PM_CTRL, pmcsr); | ||
4135 | 4521 | ||
4136 | schedule_timeout_uninterruptible(HZ >> 1); | 4522 | rc = cciss_controller_hard_reset(pdev, vaddr, use_doorbell); |
4523 | if (rc) | ||
4524 | goto unmap_cfgtable; | ||
4137 | 4525 | ||
4138 | /* Restore the PCI configuration space. The Open CISS | 4526 | /* Restore the PCI configuration space. The Open CISS |
4139 | * Specification says, "Restore the PCI Configuration | 4527 | * Specification says, "Restore the PCI Configuration |
4140 | * Registers, offsets 00h through 60h. It is important to | 4528 | * Registers, offsets 00h through 60h. It is important to |
4141 | * restore the command register, 16-bits at offset 04h, | 4529 | * restore the command register, 16-bits at offset 04h, |
4142 | * last. Do not restore the configuration status register, | 4530 | * last. Do not restore the configuration status register, |
4143 | * 16-bits at offset 06h." Note that the offset is 2*i. */ | 4531 | * 16-bits at offset 06h." Note that the offset is 2*i. |
4532 | */ | ||
4144 | for (i = 0; i < 32; i++) { | 4533 | for (i = 0; i < 32; i++) { |
4145 | if (i == 2 || i == 3) | 4534 | if (i == 2 || i == 3) |
4146 | continue; | 4535 | continue; |
@@ -4149,6 +4538,63 @@ static __devinit int cciss_hard_reset_controller(struct pci_dev *pdev) | |||
4149 | wmb(); | 4538 | wmb(); |
4150 | pci_write_config_word(pdev, 4, saved_config_space[2]); | 4539 | pci_write_config_word(pdev, 4, saved_config_space[2]); |
4151 | 4540 | ||
4541 | /* Some devices (notably the HP Smart Array 5i Controller) | ||
4542 | need a little pause here */ | ||
4543 | msleep(CCISS_POST_RESET_PAUSE_MSECS); | ||
4544 | |||
4545 | /* Controller should be in simple mode at this point. If it's not, | ||
4546 | * It means we're on one of those controllers which doesn't support | ||
4547 | * the doorbell reset method and on which the PCI power management reset | ||
4548 | * method doesn't work (P800, for example.) | ||
4549 | * In those cases, don't try to proceed, as it generally doesn't work. | ||
4550 | */ | ||
4551 | active_transport = readl(&cfgtable->TransportActive); | ||
4552 | if (active_transport & PERFORMANT_MODE) { | ||
4553 | dev_warn(&pdev->dev, "Unable to successfully reset controller," | ||
4554 | " Ignoring controller.\n"); | ||
4555 | rc = -ENODEV; | ||
4556 | } | ||
4557 | |||
4558 | unmap_cfgtable: | ||
4559 | iounmap(cfgtable); | ||
4560 | |||
4561 | unmap_vaddr: | ||
4562 | iounmap(vaddr); | ||
4563 | return rc; | ||
4564 | } | ||
4565 | |||
4566 | static __devinit int cciss_init_reset_devices(struct pci_dev *pdev) | ||
4567 | { | ||
4568 | int rc, i; | ||
4569 | |||
4570 | if (!reset_devices) | ||
4571 | return 0; | ||
4572 | |||
4573 | /* Reset the controller with a PCI power-cycle or via doorbell */ | ||
4574 | rc = cciss_kdump_hard_reset_controller(pdev); | ||
4575 | |||
4576 | /* -ENOTSUPP here means we cannot reset the controller | ||
4577 | * but it's already (and still) up and running in | ||
4578 | * "performant mode". Or, it might be 640x, which can't reset | ||
4579 | * due to concerns about shared bbwc between 6402/6404 pair. | ||
4580 | */ | ||
4581 | if (rc == -ENOTSUPP) | ||
4582 | return 0; /* just try to do the kdump anyhow. */ | ||
4583 | if (rc) | ||
4584 | return -ENODEV; | ||
4585 | if (cciss_reset_msi(pdev)) | ||
4586 | return -ENODEV; | ||
4587 | |||
4588 | /* Now try to get the controller to respond to a no-op */ | ||
4589 | for (i = 0; i < CCISS_POST_RESET_NOOP_RETRIES; i++) { | ||
4590 | if (cciss_noop(pdev) == 0) | ||
4591 | break; | ||
4592 | else | ||
4593 | dev_warn(&pdev->dev, "no-op failed%s\n", | ||
4594 | (i < CCISS_POST_RESET_NOOP_RETRIES - 1 ? | ||
4595 | "; re-trying" : "")); | ||
4596 | msleep(CCISS_POST_RESET_NOOP_INTERVAL_MSECS); | ||
4597 | } | ||
4152 | return 0; | 4598 | return 0; |
4153 | } | 4599 | } |
4154 | 4600 | ||
@@ -4166,46 +4612,31 @@ static int __devinit cciss_init_one(struct pci_dev *pdev, | |||
4166 | int rc; | 4612 | int rc; |
4167 | int dac, return_code; | 4613 | int dac, return_code; |
4168 | InquiryData_struct *inq_buff; | 4614 | InquiryData_struct *inq_buff; |
4615 | ctlr_info_t *h; | ||
4169 | 4616 | ||
4170 | if (reset_devices) { | 4617 | rc = cciss_init_reset_devices(pdev); |
4171 | /* Reset the controller with a PCI power-cycle */ | 4618 | if (rc) |
4172 | if (cciss_hard_reset_controller(pdev) || cciss_reset_msi(pdev)) | 4619 | return rc; |
4173 | return -ENODEV; | 4620 | i = alloc_cciss_hba(pdev); |
4174 | |||
4175 | /* Now try to get the controller to respond to a no-op. Some | ||
4176 | devices (notably the HP Smart Array 5i Controller) need | ||
4177 | up to 30 seconds to respond. */ | ||
4178 | for (i=0; i<30; i++) { | ||
4179 | if (cciss_noop(pdev) == 0) | ||
4180 | break; | ||
4181 | |||
4182 | schedule_timeout_uninterruptible(HZ); | ||
4183 | } | ||
4184 | if (i == 30) { | ||
4185 | printk(KERN_ERR "cciss: controller seems dead\n"); | ||
4186 | return -EBUSY; | ||
4187 | } | ||
4188 | } | ||
4189 | |||
4190 | i = alloc_cciss_hba(); | ||
4191 | if (i < 0) | 4621 | if (i < 0) |
4192 | return -1; | 4622 | return -1; |
4193 | 4623 | ||
4194 | hba[i]->busy_initializing = 1; | 4624 | h = hba[i]; |
4195 | INIT_HLIST_HEAD(&hba[i]->cmpQ); | 4625 | h->pdev = pdev; |
4196 | INIT_HLIST_HEAD(&hba[i]->reqQ); | 4626 | h->busy_initializing = 1; |
4197 | mutex_init(&hba[i]->busy_shutting_down); | 4627 | INIT_HLIST_HEAD(&h->cmpQ); |
4628 | INIT_HLIST_HEAD(&h->reqQ); | ||
4629 | mutex_init(&h->busy_shutting_down); | ||
4198 | 4630 | ||
4199 | if (cciss_pci_init(hba[i], pdev) != 0) | 4631 | if (cciss_pci_init(h) != 0) |
4200 | goto clean_no_release_regions; | 4632 | goto clean_no_release_regions; |
4201 | 4633 | ||
4202 | sprintf(hba[i]->devname, "cciss%d", i); | 4634 | sprintf(h->devname, "cciss%d", i); |
4203 | hba[i]->ctlr = i; | 4635 | h->ctlr = i; |
4204 | hba[i]->pdev = pdev; | ||
4205 | 4636 | ||
4206 | init_completion(&hba[i]->scan_wait); | 4637 | init_completion(&h->scan_wait); |
4207 | 4638 | ||
4208 | if (cciss_create_hba_sysfs_entry(hba[i])) | 4639 | if (cciss_create_hba_sysfs_entry(h)) |
4209 | goto clean0; | 4640 | goto clean0; |
4210 | 4641 | ||
4211 | /* configure PCI DMA stuff */ | 4642 | /* configure PCI DMA stuff */ |
@@ -4214,7 +4645,7 @@ static int __devinit cciss_init_one(struct pci_dev *pdev, | |||
4214 | else if (!pci_set_dma_mask(pdev, DMA_BIT_MASK(32))) | 4645 | else if (!pci_set_dma_mask(pdev, DMA_BIT_MASK(32))) |
4215 | dac = 0; | 4646 | dac = 0; |
4216 | else { | 4647 | else { |
4217 | printk(KERN_ERR "cciss: no suitable DMA available\n"); | 4648 | dev_err(&h->pdev->dev, "no suitable DMA available\n"); |
4218 | goto clean1; | 4649 | goto clean1; |
4219 | } | 4650 | } |
4220 | 4651 | ||
@@ -4224,151 +4655,161 @@ static int __devinit cciss_init_one(struct pci_dev *pdev, | |||
4224 | * 8 controller support. | 4655 | * 8 controller support. |
4225 | */ | 4656 | */ |
4226 | if (i < MAX_CTLR_ORIG) | 4657 | if (i < MAX_CTLR_ORIG) |
4227 | hba[i]->major = COMPAQ_CISS_MAJOR + i; | 4658 | h->major = COMPAQ_CISS_MAJOR + i; |
4228 | rc = register_blkdev(hba[i]->major, hba[i]->devname); | 4659 | rc = register_blkdev(h->major, h->devname); |
4229 | if (rc == -EBUSY || rc == -EINVAL) { | 4660 | if (rc == -EBUSY || rc == -EINVAL) { |
4230 | printk(KERN_ERR | 4661 | dev_err(&h->pdev->dev, |
4231 | "cciss: Unable to get major number %d for %s " | 4662 | "Unable to get major number %d for %s " |
4232 | "on hba %d\n", hba[i]->major, hba[i]->devname, i); | 4663 | "on hba %d\n", h->major, h->devname, i); |
4233 | goto clean1; | 4664 | goto clean1; |
4234 | } else { | 4665 | } else { |
4235 | if (i >= MAX_CTLR_ORIG) | 4666 | if (i >= MAX_CTLR_ORIG) |
4236 | hba[i]->major = rc; | 4667 | h->major = rc; |
4237 | } | 4668 | } |
4238 | 4669 | ||
4239 | /* make sure the board interrupts are off */ | 4670 | /* make sure the board interrupts are off */ |
4240 | hba[i]->access.set_intr_mask(hba[i], CCISS_INTR_OFF); | 4671 | h->access.set_intr_mask(h, CCISS_INTR_OFF); |
4241 | if (request_irq(hba[i]->intr[SIMPLE_MODE_INT], do_cciss_intr, | 4672 | if (h->msi_vector || h->msix_vector) { |
4242 | IRQF_DISABLED | IRQF_SHARED, hba[i]->devname, hba[i])) { | 4673 | if (request_irq(h->intr[PERF_MODE_INT], |
4243 | printk(KERN_ERR "cciss: Unable to get irq %d for %s\n", | 4674 | do_cciss_msix_intr, |
4244 | hba[i]->intr[SIMPLE_MODE_INT], hba[i]->devname); | 4675 | IRQF_DISABLED, h->devname, h)) { |
4245 | goto clean2; | 4676 | dev_err(&h->pdev->dev, "Unable to get irq %d for %s\n", |
4677 | h->intr[PERF_MODE_INT], h->devname); | ||
4678 | goto clean2; | ||
4679 | } | ||
4680 | } else { | ||
4681 | if (request_irq(h->intr[PERF_MODE_INT], do_cciss_intx, | ||
4682 | IRQF_DISABLED, h->devname, h)) { | ||
4683 | dev_err(&h->pdev->dev, "Unable to get irq %d for %s\n", | ||
4684 | h->intr[PERF_MODE_INT], h->devname); | ||
4685 | goto clean2; | ||
4686 | } | ||
4246 | } | 4687 | } |
4247 | 4688 | ||
4248 | printk(KERN_INFO "%s: <0x%x> at PCI %s IRQ %d%s using DAC\n", | 4689 | dev_info(&h->pdev->dev, "%s: <0x%x> at PCI %s IRQ %d%s using DAC\n", |
4249 | hba[i]->devname, pdev->device, pci_name(pdev), | 4690 | h->devname, pdev->device, pci_name(pdev), |
4250 | hba[i]->intr[SIMPLE_MODE_INT], dac ? "" : " not"); | 4691 | h->intr[PERF_MODE_INT], dac ? "" : " not"); |
4251 | 4692 | ||
4252 | hba[i]->cmd_pool_bits = | 4693 | h->cmd_pool_bits = |
4253 | kmalloc(DIV_ROUND_UP(hba[i]->nr_cmds, BITS_PER_LONG) | 4694 | kmalloc(DIV_ROUND_UP(h->nr_cmds, BITS_PER_LONG) |
4254 | * sizeof(unsigned long), GFP_KERNEL); | 4695 | * sizeof(unsigned long), GFP_KERNEL); |
4255 | hba[i]->cmd_pool = (CommandList_struct *) | 4696 | h->cmd_pool = (CommandList_struct *) |
4256 | pci_alloc_consistent(hba[i]->pdev, | 4697 | pci_alloc_consistent(h->pdev, |
4257 | hba[i]->nr_cmds * sizeof(CommandList_struct), | 4698 | h->nr_cmds * sizeof(CommandList_struct), |
4258 | &(hba[i]->cmd_pool_dhandle)); | 4699 | &(h->cmd_pool_dhandle)); |
4259 | hba[i]->errinfo_pool = (ErrorInfo_struct *) | 4700 | h->errinfo_pool = (ErrorInfo_struct *) |
4260 | pci_alloc_consistent(hba[i]->pdev, | 4701 | pci_alloc_consistent(h->pdev, |
4261 | hba[i]->nr_cmds * sizeof(ErrorInfo_struct), | 4702 | h->nr_cmds * sizeof(ErrorInfo_struct), |
4262 | &(hba[i]->errinfo_pool_dhandle)); | 4703 | &(h->errinfo_pool_dhandle)); |
4263 | if ((hba[i]->cmd_pool_bits == NULL) | 4704 | if ((h->cmd_pool_bits == NULL) |
4264 | || (hba[i]->cmd_pool == NULL) | 4705 | || (h->cmd_pool == NULL) |
4265 | || (hba[i]->errinfo_pool == NULL)) { | 4706 | || (h->errinfo_pool == NULL)) { |
4266 | printk(KERN_ERR "cciss: out of memory"); | 4707 | dev_err(&h->pdev->dev, "out of memory"); |
4267 | goto clean4; | 4708 | goto clean4; |
4268 | } | 4709 | } |
4269 | 4710 | ||
4270 | /* Need space for temp scatter list */ | 4711 | /* Need space for temp scatter list */ |
4271 | hba[i]->scatter_list = kmalloc(hba[i]->max_commands * | 4712 | h->scatter_list = kmalloc(h->max_commands * |
4272 | sizeof(struct scatterlist *), | 4713 | sizeof(struct scatterlist *), |
4273 | GFP_KERNEL); | 4714 | GFP_KERNEL); |
4274 | for (k = 0; k < hba[i]->nr_cmds; k++) { | 4715 | for (k = 0; k < h->nr_cmds; k++) { |
4275 | hba[i]->scatter_list[k] = kmalloc(sizeof(struct scatterlist) * | 4716 | h->scatter_list[k] = kmalloc(sizeof(struct scatterlist) * |
4276 | hba[i]->maxsgentries, | 4717 | h->maxsgentries, |
4277 | GFP_KERNEL); | 4718 | GFP_KERNEL); |
4278 | if (hba[i]->scatter_list[k] == NULL) { | 4719 | if (h->scatter_list[k] == NULL) { |
4279 | printk(KERN_ERR "cciss%d: could not allocate " | 4720 | dev_err(&h->pdev->dev, |
4280 | "s/g lists\n", i); | 4721 | "could not allocate s/g lists\n"); |
4281 | goto clean4; | 4722 | goto clean4; |
4282 | } | 4723 | } |
4283 | } | 4724 | } |
4284 | hba[i]->cmd_sg_list = cciss_allocate_sg_chain_blocks(hba[i], | 4725 | h->cmd_sg_list = cciss_allocate_sg_chain_blocks(h, |
4285 | hba[i]->chainsize, hba[i]->nr_cmds); | 4726 | h->chainsize, h->nr_cmds); |
4286 | if (!hba[i]->cmd_sg_list && hba[i]->chainsize > 0) | 4727 | if (!h->cmd_sg_list && h->chainsize > 0) |
4287 | goto clean4; | 4728 | goto clean4; |
4288 | 4729 | ||
4289 | spin_lock_init(&hba[i]->lock); | 4730 | spin_lock_init(&h->lock); |
4290 | 4731 | ||
4291 | /* Initialize the pdev driver private data. | 4732 | /* Initialize the pdev driver private data. |
4292 | have it point to hba[i]. */ | 4733 | have it point to h. */ |
4293 | pci_set_drvdata(pdev, hba[i]); | 4734 | pci_set_drvdata(pdev, h); |
4294 | /* command and error info recs zeroed out before | 4735 | /* command and error info recs zeroed out before |
4295 | they are used */ | 4736 | they are used */ |
4296 | memset(hba[i]->cmd_pool_bits, 0, | 4737 | memset(h->cmd_pool_bits, 0, |
4297 | DIV_ROUND_UP(hba[i]->nr_cmds, BITS_PER_LONG) | 4738 | DIV_ROUND_UP(h->nr_cmds, BITS_PER_LONG) |
4298 | * sizeof(unsigned long)); | 4739 | * sizeof(unsigned long)); |
4299 | 4740 | ||
4300 | hba[i]->num_luns = 0; | 4741 | h->num_luns = 0; |
4301 | hba[i]->highest_lun = -1; | 4742 | h->highest_lun = -1; |
4302 | for (j = 0; j < CISS_MAX_LUN; j++) { | 4743 | for (j = 0; j < CISS_MAX_LUN; j++) { |
4303 | hba[i]->drv[j] = NULL; | 4744 | h->drv[j] = NULL; |
4304 | hba[i]->gendisk[j] = NULL; | 4745 | h->gendisk[j] = NULL; |
4305 | } | 4746 | } |
4306 | 4747 | ||
4307 | cciss_scsi_setup(i); | 4748 | cciss_scsi_setup(h); |
4308 | 4749 | ||
4309 | /* Turn the interrupts on so we can service requests */ | 4750 | /* Turn the interrupts on so we can service requests */ |
4310 | hba[i]->access.set_intr_mask(hba[i], CCISS_INTR_ON); | 4751 | h->access.set_intr_mask(h, CCISS_INTR_ON); |
4311 | 4752 | ||
4312 | /* Get the firmware version */ | 4753 | /* Get the firmware version */ |
4313 | inq_buff = kzalloc(sizeof(InquiryData_struct), GFP_KERNEL); | 4754 | inq_buff = kzalloc(sizeof(InquiryData_struct), GFP_KERNEL); |
4314 | if (inq_buff == NULL) { | 4755 | if (inq_buff == NULL) { |
4315 | printk(KERN_ERR "cciss: out of memory\n"); | 4756 | dev_err(&h->pdev->dev, "out of memory\n"); |
4316 | goto clean4; | 4757 | goto clean4; |
4317 | } | 4758 | } |
4318 | 4759 | ||
4319 | return_code = sendcmd_withirq(CISS_INQUIRY, i, inq_buff, | 4760 | return_code = sendcmd_withirq(h, CISS_INQUIRY, inq_buff, |
4320 | sizeof(InquiryData_struct), 0, CTLR_LUNID, TYPE_CMD); | 4761 | sizeof(InquiryData_struct), 0, CTLR_LUNID, TYPE_CMD); |
4321 | if (return_code == IO_OK) { | 4762 | if (return_code == IO_OK) { |
4322 | hba[i]->firm_ver[0] = inq_buff->data_byte[32]; | 4763 | h->firm_ver[0] = inq_buff->data_byte[32]; |
4323 | hba[i]->firm_ver[1] = inq_buff->data_byte[33]; | 4764 | h->firm_ver[1] = inq_buff->data_byte[33]; |
4324 | hba[i]->firm_ver[2] = inq_buff->data_byte[34]; | 4765 | h->firm_ver[2] = inq_buff->data_byte[34]; |
4325 | hba[i]->firm_ver[3] = inq_buff->data_byte[35]; | 4766 | h->firm_ver[3] = inq_buff->data_byte[35]; |
4326 | } else { /* send command failed */ | 4767 | } else { /* send command failed */ |
4327 | printk(KERN_WARNING "cciss: unable to determine firmware" | 4768 | dev_warn(&h->pdev->dev, "unable to determine firmware" |
4328 | " version of controller\n"); | 4769 | " version of controller\n"); |
4329 | } | 4770 | } |
4330 | kfree(inq_buff); | 4771 | kfree(inq_buff); |
4331 | 4772 | ||
4332 | cciss_procinit(i); | 4773 | cciss_procinit(h); |
4333 | 4774 | ||
4334 | hba[i]->cciss_max_sectors = 8192; | 4775 | h->cciss_max_sectors = 8192; |
4335 | 4776 | ||
4336 | rebuild_lun_table(hba[i], 1, 0); | 4777 | rebuild_lun_table(h, 1, 0); |
4337 | hba[i]->busy_initializing = 0; | 4778 | h->busy_initializing = 0; |
4338 | return 1; | 4779 | return 1; |
4339 | 4780 | ||
4340 | clean4: | 4781 | clean4: |
4341 | kfree(hba[i]->cmd_pool_bits); | 4782 | kfree(h->cmd_pool_bits); |
4342 | /* Free up sg elements */ | 4783 | /* Free up sg elements */ |
4343 | for (k = 0; k < hba[i]->nr_cmds; k++) | 4784 | for (k = 0; k < h->nr_cmds; k++) |
4344 | kfree(hba[i]->scatter_list[k]); | 4785 | kfree(h->scatter_list[k]); |
4345 | kfree(hba[i]->scatter_list); | 4786 | kfree(h->scatter_list); |
4346 | cciss_free_sg_chain_blocks(hba[i]->cmd_sg_list, hba[i]->nr_cmds); | 4787 | cciss_free_sg_chain_blocks(h->cmd_sg_list, h->nr_cmds); |
4347 | if (hba[i]->cmd_pool) | 4788 | if (h->cmd_pool) |
4348 | pci_free_consistent(hba[i]->pdev, | 4789 | pci_free_consistent(h->pdev, |
4349 | hba[i]->nr_cmds * sizeof(CommandList_struct), | 4790 | h->nr_cmds * sizeof(CommandList_struct), |
4350 | hba[i]->cmd_pool, hba[i]->cmd_pool_dhandle); | 4791 | h->cmd_pool, h->cmd_pool_dhandle); |
4351 | if (hba[i]->errinfo_pool) | 4792 | if (h->errinfo_pool) |
4352 | pci_free_consistent(hba[i]->pdev, | 4793 | pci_free_consistent(h->pdev, |
4353 | hba[i]->nr_cmds * sizeof(ErrorInfo_struct), | 4794 | h->nr_cmds * sizeof(ErrorInfo_struct), |
4354 | hba[i]->errinfo_pool, | 4795 | h->errinfo_pool, |
4355 | hba[i]->errinfo_pool_dhandle); | 4796 | h->errinfo_pool_dhandle); |
4356 | free_irq(hba[i]->intr[SIMPLE_MODE_INT], hba[i]); | 4797 | free_irq(h->intr[PERF_MODE_INT], h); |
4357 | clean2: | 4798 | clean2: |
4358 | unregister_blkdev(hba[i]->major, hba[i]->devname); | 4799 | unregister_blkdev(h->major, h->devname); |
4359 | clean1: | 4800 | clean1: |
4360 | cciss_destroy_hba_sysfs_entry(hba[i]); | 4801 | cciss_destroy_hba_sysfs_entry(h); |
4361 | clean0: | 4802 | clean0: |
4362 | pci_release_regions(pdev); | 4803 | pci_release_regions(pdev); |
4363 | clean_no_release_regions: | 4804 | clean_no_release_regions: |
4364 | hba[i]->busy_initializing = 0; | 4805 | h->busy_initializing = 0; |
4365 | 4806 | ||
4366 | /* | 4807 | /* |
4367 | * Deliberately omit pci_disable_device(): it does something nasty to | 4808 | * Deliberately omit pci_disable_device(): it does something nasty to |
4368 | * Smart Array controllers that pci_enable_device does not undo | 4809 | * Smart Array controllers that pci_enable_device does not undo |
4369 | */ | 4810 | */ |
4370 | pci_set_drvdata(pdev, NULL); | 4811 | pci_set_drvdata(pdev, NULL); |
4371 | free_hba(i); | 4812 | free_hba(h); |
4372 | return -1; | 4813 | return -1; |
4373 | } | 4814 | } |
4374 | 4815 | ||
@@ -4381,55 +4822,51 @@ static void cciss_shutdown(struct pci_dev *pdev) | |||
4381 | h = pci_get_drvdata(pdev); | 4822 | h = pci_get_drvdata(pdev); |
4382 | flush_buf = kzalloc(4, GFP_KERNEL); | 4823 | flush_buf = kzalloc(4, GFP_KERNEL); |
4383 | if (!flush_buf) { | 4824 | if (!flush_buf) { |
4384 | printk(KERN_WARNING | 4825 | dev_warn(&h->pdev->dev, "cache not flushed, out of memory.\n"); |
4385 | "cciss:%d cache not flushed, out of memory.\n", | ||
4386 | h->ctlr); | ||
4387 | return; | 4826 | return; |
4388 | } | 4827 | } |
4389 | /* write all data in the battery backed cache to disk */ | 4828 | /* write all data in the battery backed cache to disk */ |
4390 | memset(flush_buf, 0, 4); | 4829 | memset(flush_buf, 0, 4); |
4391 | return_code = sendcmd_withirq(CCISS_CACHE_FLUSH, h->ctlr, flush_buf, | 4830 | return_code = sendcmd_withirq(h, CCISS_CACHE_FLUSH, flush_buf, |
4392 | 4, 0, CTLR_LUNID, TYPE_CMD); | 4831 | 4, 0, CTLR_LUNID, TYPE_CMD); |
4393 | kfree(flush_buf); | 4832 | kfree(flush_buf); |
4394 | if (return_code != IO_OK) | 4833 | if (return_code != IO_OK) |
4395 | printk(KERN_WARNING "cciss%d: Error flushing cache\n", | 4834 | dev_warn(&h->pdev->dev, "Error flushing cache\n"); |
4396 | h->ctlr); | ||
4397 | h->access.set_intr_mask(h, CCISS_INTR_OFF); | 4835 | h->access.set_intr_mask(h, CCISS_INTR_OFF); |
4398 | free_irq(h->intr[2], h); | 4836 | free_irq(h->intr[PERF_MODE_INT], h); |
4399 | } | 4837 | } |
4400 | 4838 | ||
4401 | static void __devexit cciss_remove_one(struct pci_dev *pdev) | 4839 | static void __devexit cciss_remove_one(struct pci_dev *pdev) |
4402 | { | 4840 | { |
4403 | ctlr_info_t *tmp_ptr; | 4841 | ctlr_info_t *h; |
4404 | int i, j; | 4842 | int i, j; |
4405 | 4843 | ||
4406 | if (pci_get_drvdata(pdev) == NULL) { | 4844 | if (pci_get_drvdata(pdev) == NULL) { |
4407 | printk(KERN_ERR "cciss: Unable to remove device \n"); | 4845 | dev_err(&pdev->dev, "Unable to remove device\n"); |
4408 | return; | 4846 | return; |
4409 | } | 4847 | } |
4410 | 4848 | ||
4411 | tmp_ptr = pci_get_drvdata(pdev); | 4849 | h = pci_get_drvdata(pdev); |
4412 | i = tmp_ptr->ctlr; | 4850 | i = h->ctlr; |
4413 | if (hba[i] == NULL) { | 4851 | if (hba[i] == NULL) { |
4414 | printk(KERN_ERR "cciss: device appears to " | 4852 | dev_err(&pdev->dev, "device appears to already be removed\n"); |
4415 | "already be removed \n"); | ||
4416 | return; | 4853 | return; |
4417 | } | 4854 | } |
4418 | 4855 | ||
4419 | mutex_lock(&hba[i]->busy_shutting_down); | 4856 | mutex_lock(&h->busy_shutting_down); |
4420 | 4857 | ||
4421 | remove_from_scan_list(hba[i]); | 4858 | remove_from_scan_list(h); |
4422 | remove_proc_entry(hba[i]->devname, proc_cciss); | 4859 | remove_proc_entry(h->devname, proc_cciss); |
4423 | unregister_blkdev(hba[i]->major, hba[i]->devname); | 4860 | unregister_blkdev(h->major, h->devname); |
4424 | 4861 | ||
4425 | /* remove it from the disk list */ | 4862 | /* remove it from the disk list */ |
4426 | for (j = 0; j < CISS_MAX_LUN; j++) { | 4863 | for (j = 0; j < CISS_MAX_LUN; j++) { |
4427 | struct gendisk *disk = hba[i]->gendisk[j]; | 4864 | struct gendisk *disk = h->gendisk[j]; |
4428 | if (disk) { | 4865 | if (disk) { |
4429 | struct request_queue *q = disk->queue; | 4866 | struct request_queue *q = disk->queue; |
4430 | 4867 | ||
4431 | if (disk->flags & GENHD_FL_UP) { | 4868 | if (disk->flags & GENHD_FL_UP) { |
4432 | cciss_destroy_ld_sysfs_entry(hba[i], j, 1); | 4869 | cciss_destroy_ld_sysfs_entry(h, j, 1); |
4433 | del_gendisk(disk); | 4870 | del_gendisk(disk); |
4434 | } | 4871 | } |
4435 | if (q) | 4872 | if (q) |
@@ -4438,39 +4875,41 @@ static void __devexit cciss_remove_one(struct pci_dev *pdev) | |||
4438 | } | 4875 | } |
4439 | 4876 | ||
4440 | #ifdef CONFIG_CISS_SCSI_TAPE | 4877 | #ifdef CONFIG_CISS_SCSI_TAPE |
4441 | cciss_unregister_scsi(i); /* unhook from SCSI subsystem */ | 4878 | cciss_unregister_scsi(h); /* unhook from SCSI subsystem */ |
4442 | #endif | 4879 | #endif |
4443 | 4880 | ||
4444 | cciss_shutdown(pdev); | 4881 | cciss_shutdown(pdev); |
4445 | 4882 | ||
4446 | #ifdef CONFIG_PCI_MSI | 4883 | #ifdef CONFIG_PCI_MSI |
4447 | if (hba[i]->msix_vector) | 4884 | if (h->msix_vector) |
4448 | pci_disable_msix(hba[i]->pdev); | 4885 | pci_disable_msix(h->pdev); |
4449 | else if (hba[i]->msi_vector) | 4886 | else if (h->msi_vector) |
4450 | pci_disable_msi(hba[i]->pdev); | 4887 | pci_disable_msi(h->pdev); |
4451 | #endif /* CONFIG_PCI_MSI */ | 4888 | #endif /* CONFIG_PCI_MSI */ |
4452 | 4889 | ||
4453 | iounmap(hba[i]->vaddr); | 4890 | iounmap(h->transtable); |
4891 | iounmap(h->cfgtable); | ||
4892 | iounmap(h->vaddr); | ||
4454 | 4893 | ||
4455 | pci_free_consistent(hba[i]->pdev, hba[i]->nr_cmds * sizeof(CommandList_struct), | 4894 | pci_free_consistent(h->pdev, h->nr_cmds * sizeof(CommandList_struct), |
4456 | hba[i]->cmd_pool, hba[i]->cmd_pool_dhandle); | 4895 | h->cmd_pool, h->cmd_pool_dhandle); |
4457 | pci_free_consistent(hba[i]->pdev, hba[i]->nr_cmds * sizeof(ErrorInfo_struct), | 4896 | pci_free_consistent(h->pdev, h->nr_cmds * sizeof(ErrorInfo_struct), |
4458 | hba[i]->errinfo_pool, hba[i]->errinfo_pool_dhandle); | 4897 | h->errinfo_pool, h->errinfo_pool_dhandle); |
4459 | kfree(hba[i]->cmd_pool_bits); | 4898 | kfree(h->cmd_pool_bits); |
4460 | /* Free up sg elements */ | 4899 | /* Free up sg elements */ |
4461 | for (j = 0; j < hba[i]->nr_cmds; j++) | 4900 | for (j = 0; j < h->nr_cmds; j++) |
4462 | kfree(hba[i]->scatter_list[j]); | 4901 | kfree(h->scatter_list[j]); |
4463 | kfree(hba[i]->scatter_list); | 4902 | kfree(h->scatter_list); |
4464 | cciss_free_sg_chain_blocks(hba[i]->cmd_sg_list, hba[i]->nr_cmds); | 4903 | cciss_free_sg_chain_blocks(h->cmd_sg_list, h->nr_cmds); |
4465 | /* | 4904 | /* |
4466 | * Deliberately omit pci_disable_device(): it does something nasty to | 4905 | * Deliberately omit pci_disable_device(): it does something nasty to |
4467 | * Smart Array controllers that pci_enable_device does not undo | 4906 | * Smart Array controllers that pci_enable_device does not undo |
4468 | */ | 4907 | */ |
4469 | pci_release_regions(pdev); | 4908 | pci_release_regions(pdev); |
4470 | pci_set_drvdata(pdev, NULL); | 4909 | pci_set_drvdata(pdev, NULL); |
4471 | cciss_destroy_hba_sysfs_entry(hba[i]); | 4910 | cciss_destroy_hba_sysfs_entry(h); |
4472 | mutex_unlock(&hba[i]->busy_shutting_down); | 4911 | mutex_unlock(&h->busy_shutting_down); |
4473 | free_hba(i); | 4912 | free_hba(h); |
4474 | } | 4913 | } |
4475 | 4914 | ||
4476 | static struct pci_driver cciss_pci_driver = { | 4915 | static struct pci_driver cciss_pci_driver = { |
@@ -4495,7 +4934,6 @@ static int __init cciss_init(void) | |||
4495 | * array of them, the size must be a multiple of 8 bytes. | 4934 | * array of them, the size must be a multiple of 8 bytes. |
4496 | */ | 4935 | */ |
4497 | BUILD_BUG_ON(sizeof(CommandList_struct) % COMMANDLIST_ALIGNMENT); | 4936 | BUILD_BUG_ON(sizeof(CommandList_struct) % COMMANDLIST_ALIGNMENT); |
4498 | |||
4499 | printk(KERN_INFO DRIVER_NAME "\n"); | 4937 | printk(KERN_INFO DRIVER_NAME "\n"); |
4500 | 4938 | ||
4501 | err = bus_register(&cciss_bus_type); | 4939 | err = bus_register(&cciss_bus_type); |
@@ -4532,8 +4970,8 @@ static void __exit cciss_cleanup(void) | |||
4532 | /* double check that all controller entrys have been removed */ | 4970 | /* double check that all controller entrys have been removed */ |
4533 | for (i = 0; i < MAX_CTLR; i++) { | 4971 | for (i = 0; i < MAX_CTLR; i++) { |
4534 | if (hba[i] != NULL) { | 4972 | if (hba[i] != NULL) { |
4535 | printk(KERN_WARNING "cciss: had to remove" | 4973 | dev_warn(&hba[i]->pdev->dev, |
4536 | " controller %d\n", i); | 4974 | "had to remove controller\n"); |
4537 | cciss_remove_one(hba[i]->pdev); | 4975 | cciss_remove_one(hba[i]->pdev); |
4538 | } | 4976 | } |
4539 | } | 4977 | } |
@@ -4542,46 +4980,5 @@ static void __exit cciss_cleanup(void) | |||
4542 | bus_unregister(&cciss_bus_type); | 4980 | bus_unregister(&cciss_bus_type); |
4543 | } | 4981 | } |
4544 | 4982 | ||
4545 | static void fail_all_cmds(unsigned long ctlr) | ||
4546 | { | ||
4547 | /* If we get here, the board is apparently dead. */ | ||
4548 | ctlr_info_t *h = hba[ctlr]; | ||
4549 | CommandList_struct *c; | ||
4550 | unsigned long flags; | ||
4551 | |||
4552 | printk(KERN_WARNING "cciss%d: controller not responding.\n", h->ctlr); | ||
4553 | h->alive = 0; /* the controller apparently died... */ | ||
4554 | |||
4555 | spin_lock_irqsave(CCISS_LOCK(ctlr), flags); | ||
4556 | |||
4557 | pci_disable_device(h->pdev); /* Make sure it is really dead. */ | ||
4558 | |||
4559 | /* move everything off the request queue onto the completed queue */ | ||
4560 | while (!hlist_empty(&h->reqQ)) { | ||
4561 | c = hlist_entry(h->reqQ.first, CommandList_struct, list); | ||
4562 | removeQ(c); | ||
4563 | h->Qdepth--; | ||
4564 | addQ(&h->cmpQ, c); | ||
4565 | } | ||
4566 | |||
4567 | /* Now, fail everything on the completed queue with a HW error */ | ||
4568 | while (!hlist_empty(&h->cmpQ)) { | ||
4569 | c = hlist_entry(h->cmpQ.first, CommandList_struct, list); | ||
4570 | removeQ(c); | ||
4571 | if (c->cmd_type != CMD_MSG_STALE) | ||
4572 | c->err_info->CommandStatus = CMD_HARDWARE_ERR; | ||
4573 | if (c->cmd_type == CMD_RWREQ) { | ||
4574 | complete_command(h, c, 0); | ||
4575 | } else if (c->cmd_type == CMD_IOCTL_PEND) | ||
4576 | complete(c->waiting); | ||
4577 | #ifdef CONFIG_CISS_SCSI_TAPE | ||
4578 | else if (c->cmd_type == CMD_SCSI) | ||
4579 | complete_scsi_command(c, 0, 0); | ||
4580 | #endif | ||
4581 | } | ||
4582 | spin_unlock_irqrestore(CCISS_LOCK(ctlr), flags); | ||
4583 | return; | ||
4584 | } | ||
4585 | |||
4586 | module_init(cciss_init); | 4983 | module_init(cciss_init); |
4587 | module_exit(cciss_cleanup); | 4984 | module_exit(cciss_cleanup); |
diff --git a/drivers/block/cciss.h b/drivers/block/cciss.h index c5d411174db0..ae340ffc8f81 100644 --- a/drivers/block/cciss.h +++ b/drivers/block/cciss.h | |||
@@ -25,7 +25,7 @@ struct access_method { | |||
25 | void (*submit_command)(ctlr_info_t *h, CommandList_struct *c); | 25 | void (*submit_command)(ctlr_info_t *h, CommandList_struct *c); |
26 | void (*set_intr_mask)(ctlr_info_t *h, unsigned long val); | 26 | void (*set_intr_mask)(ctlr_info_t *h, unsigned long val); |
27 | unsigned long (*fifo_full)(ctlr_info_t *h); | 27 | unsigned long (*fifo_full)(ctlr_info_t *h); |
28 | unsigned long (*intr_pending)(ctlr_info_t *h); | 28 | bool (*intr_pending)(ctlr_info_t *h); |
29 | unsigned long (*command_completed)(ctlr_info_t *h); | 29 | unsigned long (*command_completed)(ctlr_info_t *h); |
30 | }; | 30 | }; |
31 | typedef struct _drive_info_struct | 31 | typedef struct _drive_info_struct |
@@ -85,8 +85,8 @@ struct ctlr_info | |||
85 | int max_cmd_sgentries; | 85 | int max_cmd_sgentries; |
86 | SGDescriptor_struct **cmd_sg_list; | 86 | SGDescriptor_struct **cmd_sg_list; |
87 | 87 | ||
88 | # define DOORBELL_INT 0 | 88 | # define PERF_MODE_INT 0 |
89 | # define PERF_MODE_INT 1 | 89 | # define DOORBELL_INT 1 |
90 | # define SIMPLE_MODE_INT 2 | 90 | # define SIMPLE_MODE_INT 2 |
91 | # define MEMQ_MODE_INT 3 | 91 | # define MEMQ_MODE_INT 3 |
92 | unsigned int intr[4]; | 92 | unsigned int intr[4]; |
@@ -137,10 +137,27 @@ struct ctlr_info | |||
137 | struct list_head scan_list; | 137 | struct list_head scan_list; |
138 | struct completion scan_wait; | 138 | struct completion scan_wait; |
139 | struct device dev; | 139 | struct device dev; |
140 | /* | ||
141 | * Performant mode tables. | ||
142 | */ | ||
143 | u32 trans_support; | ||
144 | u32 trans_offset; | ||
145 | struct TransTable_struct *transtable; | ||
146 | unsigned long transMethod; | ||
147 | |||
148 | /* | ||
149 | * Performant mode completion buffer | ||
150 | */ | ||
151 | u64 *reply_pool; | ||
152 | dma_addr_t reply_pool_dhandle; | ||
153 | u64 *reply_pool_head; | ||
154 | size_t reply_pool_size; | ||
155 | unsigned char reply_pool_wraparound; | ||
156 | u32 *blockFetchTable; | ||
140 | }; | 157 | }; |
141 | 158 | ||
142 | /* Defining the diffent access_menthods */ | 159 | /* Defining the diffent access_methods |
143 | /* | 160 | * |
144 | * Memory mapped FIFO interface (SMART 53xx cards) | 161 | * Memory mapped FIFO interface (SMART 53xx cards) |
145 | */ | 162 | */ |
146 | #define SA5_DOORBELL 0x20 | 163 | #define SA5_DOORBELL 0x20 |
@@ -159,19 +176,47 @@ struct ctlr_info | |||
159 | #define SA5B_INTR_PENDING 0x04 | 176 | #define SA5B_INTR_PENDING 0x04 |
160 | #define FIFO_EMPTY 0xffffffff | 177 | #define FIFO_EMPTY 0xffffffff |
161 | #define CCISS_FIRMWARE_READY 0xffff0000 /* value in scratchpad register */ | 178 | #define CCISS_FIRMWARE_READY 0xffff0000 /* value in scratchpad register */ |
179 | /* Perf. mode flags */ | ||
180 | #define SA5_PERF_INTR_PENDING 0x04 | ||
181 | #define SA5_PERF_INTR_OFF 0x05 | ||
182 | #define SA5_OUTDB_STATUS_PERF_BIT 0x01 | ||
183 | #define SA5_OUTDB_CLEAR_PERF_BIT 0x01 | ||
184 | #define SA5_OUTDB_CLEAR 0xA0 | ||
185 | #define SA5_OUTDB_CLEAR_PERF_BIT 0x01 | ||
186 | #define SA5_OUTDB_STATUS 0x9C | ||
187 | |||
162 | 188 | ||
163 | #define CISS_ERROR_BIT 0x02 | 189 | #define CISS_ERROR_BIT 0x02 |
164 | 190 | ||
165 | #define CCISS_INTR_ON 1 | 191 | #define CCISS_INTR_ON 1 |
166 | #define CCISS_INTR_OFF 0 | 192 | #define CCISS_INTR_OFF 0 |
193 | |||
194 | |||
195 | /* CCISS_BOARD_READY_WAIT_SECS is how long to wait for a board | ||
196 | * to become ready, in seconds, before giving up on it. | ||
197 | * CCISS_BOARD_READY_POLL_INTERVAL_MSECS * is how long to wait | ||
198 | * between polling the board to see if it is ready, in | ||
199 | * milliseconds. CCISS_BOARD_READY_ITERATIONS is derived | ||
200 | * the above. | ||
201 | */ | ||
202 | #define CCISS_BOARD_READY_WAIT_SECS (120) | ||
203 | #define CCISS_BOARD_READY_POLL_INTERVAL_MSECS (100) | ||
204 | #define CCISS_BOARD_READY_ITERATIONS \ | ||
205 | ((CCISS_BOARD_READY_WAIT_SECS * 1000) / \ | ||
206 | CCISS_BOARD_READY_POLL_INTERVAL_MSECS) | ||
207 | #define CCISS_POST_RESET_PAUSE_MSECS (3000) | ||
208 | #define CCISS_POST_RESET_NOOP_INTERVAL_MSECS (1000) | ||
209 | #define CCISS_POST_RESET_NOOP_RETRIES (12) | ||
210 | |||
167 | /* | 211 | /* |
168 | Send the command to the hardware | 212 | Send the command to the hardware |
169 | */ | 213 | */ |
170 | static void SA5_submit_command( ctlr_info_t *h, CommandList_struct *c) | 214 | static void SA5_submit_command( ctlr_info_t *h, CommandList_struct *c) |
171 | { | 215 | { |
172 | #ifdef CCISS_DEBUG | 216 | #ifdef CCISS_DEBUG |
173 | printk("Sending %x - down to controller\n", c->busaddr ); | 217 | printk(KERN_WARNING "cciss%d: Sending %08x - down to controller\n", |
174 | #endif /* CCISS_DEBUG */ | 218 | h->ctlr, c->busaddr); |
219 | #endif /* CCISS_DEBUG */ | ||
175 | writel(c->busaddr, h->vaddr + SA5_REQUEST_PORT_OFFSET); | 220 | writel(c->busaddr, h->vaddr + SA5_REQUEST_PORT_OFFSET); |
176 | h->commands_outstanding++; | 221 | h->commands_outstanding++; |
177 | if ( h->commands_outstanding > h->max_outstanding) | 222 | if ( h->commands_outstanding > h->max_outstanding) |
@@ -214,6 +259,20 @@ static void SA5B_intr_mask(ctlr_info_t *h, unsigned long val) | |||
214 | h->vaddr + SA5_REPLY_INTR_MASK_OFFSET); | 259 | h->vaddr + SA5_REPLY_INTR_MASK_OFFSET); |
215 | } | 260 | } |
216 | } | 261 | } |
262 | |||
263 | /* Performant mode intr_mask */ | ||
264 | static void SA5_performant_intr_mask(ctlr_info_t *h, unsigned long val) | ||
265 | { | ||
266 | if (val) { /* turn on interrupts */ | ||
267 | h->interrupts_enabled = 1; | ||
268 | writel(0, h->vaddr + SA5_REPLY_INTR_MASK_OFFSET); | ||
269 | } else { | ||
270 | h->interrupts_enabled = 0; | ||
271 | writel(SA5_PERF_INTR_OFF, | ||
272 | h->vaddr + SA5_REPLY_INTR_MASK_OFFSET); | ||
273 | } | ||
274 | } | ||
275 | |||
217 | /* | 276 | /* |
218 | * Returns true if fifo is full. | 277 | * Returns true if fifo is full. |
219 | * | 278 | * |
@@ -250,10 +309,44 @@ static unsigned long SA5_completed(ctlr_info_t *h) | |||
250 | return ( register_value); | 309 | return ( register_value); |
251 | 310 | ||
252 | } | 311 | } |
312 | |||
313 | /* Performant mode command completed */ | ||
314 | static unsigned long SA5_performant_completed(ctlr_info_t *h) | ||
315 | { | ||
316 | unsigned long register_value = FIFO_EMPTY; | ||
317 | |||
318 | /* flush the controller write of the reply queue by reading | ||
319 | * outbound doorbell status register. | ||
320 | */ | ||
321 | register_value = readl(h->vaddr + SA5_OUTDB_STATUS); | ||
322 | /* msi auto clears the interrupt pending bit. */ | ||
323 | if (!(h->msi_vector || h->msix_vector)) { | ||
324 | writel(SA5_OUTDB_CLEAR_PERF_BIT, h->vaddr + SA5_OUTDB_CLEAR); | ||
325 | /* Do a read in order to flush the write to the controller | ||
326 | * (as per spec.) | ||
327 | */ | ||
328 | register_value = readl(h->vaddr + SA5_OUTDB_STATUS); | ||
329 | } | ||
330 | |||
331 | if ((*(h->reply_pool_head) & 1) == (h->reply_pool_wraparound)) { | ||
332 | register_value = *(h->reply_pool_head); | ||
333 | (h->reply_pool_head)++; | ||
334 | h->commands_outstanding--; | ||
335 | } else { | ||
336 | register_value = FIFO_EMPTY; | ||
337 | } | ||
338 | /* Check for wraparound */ | ||
339 | if (h->reply_pool_head == (h->reply_pool + h->max_commands)) { | ||
340 | h->reply_pool_head = h->reply_pool; | ||
341 | h->reply_pool_wraparound ^= 1; | ||
342 | } | ||
343 | |||
344 | return register_value; | ||
345 | } | ||
253 | /* | 346 | /* |
254 | * Returns true if an interrupt is pending.. | 347 | * Returns true if an interrupt is pending.. |
255 | */ | 348 | */ |
256 | static unsigned long SA5_intr_pending(ctlr_info_t *h) | 349 | static bool SA5_intr_pending(ctlr_info_t *h) |
257 | { | 350 | { |
258 | unsigned long register_value = | 351 | unsigned long register_value = |
259 | readl(h->vaddr + SA5_INTR_STATUS); | 352 | readl(h->vaddr + SA5_INTR_STATUS); |
@@ -268,7 +361,7 @@ static unsigned long SA5_intr_pending(ctlr_info_t *h) | |||
268 | /* | 361 | /* |
269 | * Returns true if an interrupt is pending.. | 362 | * Returns true if an interrupt is pending.. |
270 | */ | 363 | */ |
271 | static unsigned long SA5B_intr_pending(ctlr_info_t *h) | 364 | static bool SA5B_intr_pending(ctlr_info_t *h) |
272 | { | 365 | { |
273 | unsigned long register_value = | 366 | unsigned long register_value = |
274 | readl(h->vaddr + SA5_INTR_STATUS); | 367 | readl(h->vaddr + SA5_INTR_STATUS); |
@@ -280,6 +373,20 @@ static unsigned long SA5B_intr_pending(ctlr_info_t *h) | |||
280 | return 0 ; | 373 | return 0 ; |
281 | } | 374 | } |
282 | 375 | ||
376 | static bool SA5_performant_intr_pending(ctlr_info_t *h) | ||
377 | { | ||
378 | unsigned long register_value = readl(h->vaddr + SA5_INTR_STATUS); | ||
379 | |||
380 | if (!register_value) | ||
381 | return false; | ||
382 | |||
383 | if (h->msi_vector || h->msix_vector) | ||
384 | return true; | ||
385 | |||
386 | /* Read outbound doorbell to flush */ | ||
387 | register_value = readl(h->vaddr + SA5_OUTDB_STATUS); | ||
388 | return register_value & SA5_OUTDB_STATUS_PERF_BIT; | ||
389 | } | ||
283 | 390 | ||
284 | static struct access_method SA5_access = { | 391 | static struct access_method SA5_access = { |
285 | SA5_submit_command, | 392 | SA5_submit_command, |
@@ -297,6 +404,14 @@ static struct access_method SA5B_access = { | |||
297 | SA5_completed, | 404 | SA5_completed, |
298 | }; | 405 | }; |
299 | 406 | ||
407 | static struct access_method SA5_performant_access = { | ||
408 | SA5_submit_command, | ||
409 | SA5_performant_intr_mask, | ||
410 | SA5_fifo_full, | ||
411 | SA5_performant_intr_pending, | ||
412 | SA5_performant_completed, | ||
413 | }; | ||
414 | |||
300 | struct board_type { | 415 | struct board_type { |
301 | __u32 board_id; | 416 | __u32 board_id; |
302 | char *product_name; | 417 | char *product_name; |
@@ -304,6 +419,4 @@ struct board_type { | |||
304 | int nr_cmds; /* Max cmds this kind of ctlr can handle. */ | 419 | int nr_cmds; /* Max cmds this kind of ctlr can handle. */ |
305 | }; | 420 | }; |
306 | 421 | ||
307 | #define CCISS_LOCK(i) (&hba[i]->lock) | ||
308 | |||
309 | #endif /* CCISS_H */ | 422 | #endif /* CCISS_H */ |
diff --git a/drivers/block/cciss_cmd.h b/drivers/block/cciss_cmd.h index e624ff959cb6..eb060f1b00b6 100644 --- a/drivers/block/cciss_cmd.h +++ b/drivers/block/cciss_cmd.h | |||
@@ -52,8 +52,10 @@ | |||
52 | /* Configuration Table */ | 52 | /* Configuration Table */ |
53 | #define CFGTBL_ChangeReq 0x00000001l | 53 | #define CFGTBL_ChangeReq 0x00000001l |
54 | #define CFGTBL_AccCmds 0x00000001l | 54 | #define CFGTBL_AccCmds 0x00000001l |
55 | #define DOORBELL_CTLR_RESET 0x00000004l | ||
55 | 56 | ||
56 | #define CFGTBL_Trans_Simple 0x00000002l | 57 | #define CFGTBL_Trans_Simple 0x00000002l |
58 | #define CFGTBL_Trans_Performant 0x00000004l | ||
57 | 59 | ||
58 | #define CFGTBL_BusType_Ultra2 0x00000001l | 60 | #define CFGTBL_BusType_Ultra2 0x00000001l |
59 | #define CFGTBL_BusType_Ultra3 0x00000002l | 61 | #define CFGTBL_BusType_Ultra3 0x00000002l |
@@ -173,12 +175,15 @@ typedef struct _SGDescriptor_struct { | |||
173 | * PAD_64 can be adjusted independently as needed for 32-bit | 175 | * PAD_64 can be adjusted independently as needed for 32-bit |
174 | * and 64-bits systems. | 176 | * and 64-bits systems. |
175 | */ | 177 | */ |
176 | #define COMMANDLIST_ALIGNMENT (8) | 178 | #define COMMANDLIST_ALIGNMENT (32) |
177 | #define IS_64_BIT ((sizeof(long) - 4)/4) | 179 | #define IS_64_BIT ((sizeof(long) - 4)/4) |
178 | #define IS_32_BIT (!IS_64_BIT) | 180 | #define IS_32_BIT (!IS_64_BIT) |
179 | #define PAD_32 (0) | 181 | #define PAD_32 (0) |
180 | #define PAD_64 (4) | 182 | #define PAD_64 (4) |
181 | #define PADSIZE (IS_32_BIT * PAD_32 + IS_64_BIT * PAD_64) | 183 | #define PADSIZE (IS_32_BIT * PAD_32 + IS_64_BIT * PAD_64) |
184 | #define DIRECT_LOOKUP_BIT 0x10 | ||
185 | #define DIRECT_LOOKUP_SHIFT 5 | ||
186 | |||
182 | typedef struct _CommandList_struct { | 187 | typedef struct _CommandList_struct { |
183 | CommandListHeader_struct Header; | 188 | CommandListHeader_struct Header; |
184 | RequestBlock_struct Request; | 189 | RequestBlock_struct Request; |
@@ -195,7 +200,7 @@ typedef struct _CommandList_struct { | |||
195 | struct completion *waiting; | 200 | struct completion *waiting; |
196 | int retry_count; | 201 | int retry_count; |
197 | void * scsi_cmd; | 202 | void * scsi_cmd; |
198 | char pad[PADSIZE]; | 203 | char pad[PADSIZE]; |
199 | } CommandList_struct; | 204 | } CommandList_struct; |
200 | 205 | ||
201 | /* Configuration Table Structure */ | 206 | /* Configuration Table Structure */ |
@@ -209,12 +214,15 @@ typedef struct _HostWrite_struct { | |||
209 | typedef struct _CfgTable_struct { | 214 | typedef struct _CfgTable_struct { |
210 | BYTE Signature[4]; | 215 | BYTE Signature[4]; |
211 | DWORD SpecValence; | 216 | DWORD SpecValence; |
217 | #define SIMPLE_MODE 0x02 | ||
218 | #define PERFORMANT_MODE 0x04 | ||
219 | #define MEMQ_MODE 0x08 | ||
212 | DWORD TransportSupport; | 220 | DWORD TransportSupport; |
213 | DWORD TransportActive; | 221 | DWORD TransportActive; |
214 | HostWrite_struct HostWrite; | 222 | HostWrite_struct HostWrite; |
215 | DWORD CmdsOutMax; | 223 | DWORD CmdsOutMax; |
216 | DWORD BusTypes; | 224 | DWORD BusTypes; |
217 | DWORD Reserved; | 225 | DWORD TransMethodOffset; |
218 | BYTE ServerName[16]; | 226 | BYTE ServerName[16]; |
219 | DWORD HeartBeat; | 227 | DWORD HeartBeat; |
220 | DWORD SCSI_Prefetch; | 228 | DWORD SCSI_Prefetch; |
@@ -222,6 +230,28 @@ typedef struct _CfgTable_struct { | |||
222 | DWORD MaxLogicalUnits; | 230 | DWORD MaxLogicalUnits; |
223 | DWORD MaxPhysicalDrives; | 231 | DWORD MaxPhysicalDrives; |
224 | DWORD MaxPhysicalDrivesPerLogicalUnit; | 232 | DWORD MaxPhysicalDrivesPerLogicalUnit; |
233 | DWORD MaxPerformantModeCommands; | ||
234 | u8 reserved[0x78 - 0x58]; | ||
235 | u32 misc_fw_support; /* offset 0x78 */ | ||
236 | #define MISC_FW_DOORBELL_RESET (0x02) | ||
225 | } CfgTable_struct; | 237 | } CfgTable_struct; |
238 | |||
239 | struct TransTable_struct { | ||
240 | u32 BlockFetch0; | ||
241 | u32 BlockFetch1; | ||
242 | u32 BlockFetch2; | ||
243 | u32 BlockFetch3; | ||
244 | u32 BlockFetch4; | ||
245 | u32 BlockFetch5; | ||
246 | u32 BlockFetch6; | ||
247 | u32 BlockFetch7; | ||
248 | u32 RepQSize; | ||
249 | u32 RepQCount; | ||
250 | u32 RepQCtrAddrLow32; | ||
251 | u32 RepQCtrAddrHigh32; | ||
252 | u32 RepQAddr0Low32; | ||
253 | u32 RepQAddr0High32; | ||
254 | }; | ||
255 | |||
226 | #pragma pack() | 256 | #pragma pack() |
227 | #endif /* CCISS_CMD_H */ | 257 | #endif /* CCISS_CMD_H */ |
diff --git a/drivers/block/cciss_scsi.c b/drivers/block/cciss_scsi.c index 72dae92f3cab..575495f3c4b8 100644 --- a/drivers/block/cciss_scsi.c +++ b/drivers/block/cciss_scsi.c | |||
@@ -44,13 +44,15 @@ | |||
44 | #define CCISS_ABORT_MSG 0x00 | 44 | #define CCISS_ABORT_MSG 0x00 |
45 | #define CCISS_RESET_MSG 0x01 | 45 | #define CCISS_RESET_MSG 0x01 |
46 | 46 | ||
47 | static int fill_cmd(CommandList_struct *c, __u8 cmd, int ctlr, void *buff, | 47 | static int fill_cmd(ctlr_info_t *h, CommandList_struct *c, __u8 cmd, void *buff, |
48 | size_t size, | 48 | size_t size, |
49 | __u8 page_code, unsigned char *scsi3addr, | 49 | __u8 page_code, unsigned char *scsi3addr, |
50 | int cmd_type); | 50 | int cmd_type); |
51 | 51 | ||
52 | static CommandList_struct *cmd_alloc(ctlr_info_t *h, int get_from_pool); | 52 | static CommandList_struct *cmd_alloc(ctlr_info_t *h); |
53 | static void cmd_free(ctlr_info_t *h, CommandList_struct *c, int got_from_pool); | 53 | static CommandList_struct *cmd_special_alloc(ctlr_info_t *h); |
54 | static void cmd_free(ctlr_info_t *h, CommandList_struct *c); | ||
55 | static void cmd_special_free(ctlr_info_t *h, CommandList_struct *c); | ||
54 | 56 | ||
55 | static int cciss_scsi_proc_info( | 57 | static int cciss_scsi_proc_info( |
56 | struct Scsi_Host *sh, | 58 | struct Scsi_Host *sh, |
@@ -93,8 +95,8 @@ static struct scsi_host_template cciss_driver_template = { | |||
93 | 95 | ||
94 | #pragma pack(1) | 96 | #pragma pack(1) |
95 | 97 | ||
96 | #define SCSI_PAD_32 0 | 98 | #define SCSI_PAD_32 8 |
97 | #define SCSI_PAD_64 0 | 99 | #define SCSI_PAD_64 8 |
98 | 100 | ||
99 | struct cciss_scsi_cmd_stack_elem_t { | 101 | struct cciss_scsi_cmd_stack_elem_t { |
100 | CommandList_struct cmd; | 102 | CommandList_struct cmd; |
@@ -127,16 +129,16 @@ struct cciss_scsi_adapter_data_t { | |||
127 | spinlock_t lock; // to protect ccissscsi[ctlr]; | 129 | spinlock_t lock; // to protect ccissscsi[ctlr]; |
128 | }; | 130 | }; |
129 | 131 | ||
130 | #define CPQ_TAPE_LOCK(ctlr, flags) spin_lock_irqsave( \ | 132 | #define CPQ_TAPE_LOCK(h, flags) spin_lock_irqsave( \ |
131 | &hba[ctlr]->scsi_ctlr->lock, flags); | 133 | &h->scsi_ctlr->lock, flags); |
132 | #define CPQ_TAPE_UNLOCK(ctlr, flags) spin_unlock_irqrestore( \ | 134 | #define CPQ_TAPE_UNLOCK(h, flags) spin_unlock_irqrestore( \ |
133 | &hba[ctlr]->scsi_ctlr->lock, flags); | 135 | &h->scsi_ctlr->lock, flags); |
134 | 136 | ||
135 | static CommandList_struct * | 137 | static CommandList_struct * |
136 | scsi_cmd_alloc(ctlr_info_t *h) | 138 | scsi_cmd_alloc(ctlr_info_t *h) |
137 | { | 139 | { |
138 | /* assume only one process in here at a time, locking done by caller. */ | 140 | /* assume only one process in here at a time, locking done by caller. */ |
139 | /* use CCISS_LOCK(ctlr) */ | 141 | /* use h->lock */ |
140 | /* might be better to rewrite how we allocate scsi commands in a way that */ | 142 | /* might be better to rewrite how we allocate scsi commands in a way that */ |
141 | /* needs no locking at all. */ | 143 | /* needs no locking at all. */ |
142 | 144 | ||
@@ -177,10 +179,10 @@ scsi_cmd_alloc(ctlr_info_t *h) | |||
177 | } | 179 | } |
178 | 180 | ||
179 | static void | 181 | static void |
180 | scsi_cmd_free(ctlr_info_t *h, CommandList_struct *cmd) | 182 | scsi_cmd_free(ctlr_info_t *h, CommandList_struct *c) |
181 | { | 183 | { |
182 | /* assume only one process in here at a time, locking done by caller. */ | 184 | /* assume only one process in here at a time, locking done by caller. */ |
183 | /* use CCISS_LOCK(ctlr) */ | 185 | /* use h->lock */ |
184 | /* drop the free memory chunk on top of the stack. */ | 186 | /* drop the free memory chunk on top of the stack. */ |
185 | 187 | ||
186 | struct cciss_scsi_adapter_data_t *sa; | 188 | struct cciss_scsi_adapter_data_t *sa; |
@@ -190,22 +192,23 @@ scsi_cmd_free(ctlr_info_t *h, CommandList_struct *cmd) | |||
190 | stk = &sa->cmd_stack; | 192 | stk = &sa->cmd_stack; |
191 | stk->top++; | 193 | stk->top++; |
192 | if (stk->top >= CMD_STACK_SIZE) { | 194 | if (stk->top >= CMD_STACK_SIZE) { |
193 | printk("cciss: scsi_cmd_free called too many times.\n"); | 195 | dev_err(&h->pdev->dev, |
196 | "scsi_cmd_free called too many times.\n"); | ||
194 | BUG(); | 197 | BUG(); |
195 | } | 198 | } |
196 | stk->elem[stk->top] = (struct cciss_scsi_cmd_stack_elem_t *) cmd; | 199 | stk->elem[stk->top] = (struct cciss_scsi_cmd_stack_elem_t *) c; |
197 | } | 200 | } |
198 | 201 | ||
199 | static int | 202 | static int |
200 | scsi_cmd_stack_setup(int ctlr, struct cciss_scsi_adapter_data_t *sa) | 203 | scsi_cmd_stack_setup(ctlr_info_t *h, struct cciss_scsi_adapter_data_t *sa) |
201 | { | 204 | { |
202 | int i; | 205 | int i; |
203 | struct cciss_scsi_cmd_stack_t *stk; | 206 | struct cciss_scsi_cmd_stack_t *stk; |
204 | size_t size; | 207 | size_t size; |
205 | 208 | ||
206 | sa->cmd_sg_list = cciss_allocate_sg_chain_blocks(hba[ctlr], | 209 | sa->cmd_sg_list = cciss_allocate_sg_chain_blocks(h, |
207 | hba[ctlr]->chainsize, CMD_STACK_SIZE); | 210 | h->chainsize, CMD_STACK_SIZE); |
208 | if (!sa->cmd_sg_list && hba[ctlr]->chainsize > 0) | 211 | if (!sa->cmd_sg_list && h->chainsize > 0) |
209 | return -ENOMEM; | 212 | return -ENOMEM; |
210 | 213 | ||
211 | stk = &sa->cmd_stack; | 214 | stk = &sa->cmd_stack; |
@@ -215,7 +218,7 @@ scsi_cmd_stack_setup(int ctlr, struct cciss_scsi_adapter_data_t *sa) | |||
215 | BUILD_BUG_ON((sizeof(*stk->pool) % COMMANDLIST_ALIGNMENT) != 0); | 218 | BUILD_BUG_ON((sizeof(*stk->pool) % COMMANDLIST_ALIGNMENT) != 0); |
216 | /* pci_alloc_consistent guarantees 32-bit DMA address will be used */ | 219 | /* pci_alloc_consistent guarantees 32-bit DMA address will be used */ |
217 | stk->pool = (struct cciss_scsi_cmd_stack_elem_t *) | 220 | stk->pool = (struct cciss_scsi_cmd_stack_elem_t *) |
218 | pci_alloc_consistent(hba[ctlr]->pdev, size, &stk->cmd_pool_handle); | 221 | pci_alloc_consistent(h->pdev, size, &stk->cmd_pool_handle); |
219 | 222 | ||
220 | if (stk->pool == NULL) { | 223 | if (stk->pool == NULL) { |
221 | cciss_free_sg_chain_blocks(sa->cmd_sg_list, CMD_STACK_SIZE); | 224 | cciss_free_sg_chain_blocks(sa->cmd_sg_list, CMD_STACK_SIZE); |
@@ -234,23 +237,22 @@ scsi_cmd_stack_setup(int ctlr, struct cciss_scsi_adapter_data_t *sa) | |||
234 | } | 237 | } |
235 | 238 | ||
236 | static void | 239 | static void |
237 | scsi_cmd_stack_free(int ctlr) | 240 | scsi_cmd_stack_free(ctlr_info_t *h) |
238 | { | 241 | { |
239 | struct cciss_scsi_adapter_data_t *sa; | 242 | struct cciss_scsi_adapter_data_t *sa; |
240 | struct cciss_scsi_cmd_stack_t *stk; | 243 | struct cciss_scsi_cmd_stack_t *stk; |
241 | size_t size; | 244 | size_t size; |
242 | 245 | ||
243 | sa = hba[ctlr]->scsi_ctlr; | 246 | sa = h->scsi_ctlr; |
244 | stk = &sa->cmd_stack; | 247 | stk = &sa->cmd_stack; |
245 | if (stk->top != CMD_STACK_SIZE-1) { | 248 | if (stk->top != CMD_STACK_SIZE-1) { |
246 | printk( "cciss: %d scsi commands are still outstanding.\n", | 249 | dev_warn(&h->pdev->dev, |
250 | "bug: %d scsi commands are still outstanding.\n", | ||
247 | CMD_STACK_SIZE - stk->top); | 251 | CMD_STACK_SIZE - stk->top); |
248 | // BUG(); | ||
249 | printk("WE HAVE A BUG HERE!!! stk=0x%p\n", stk); | ||
250 | } | 252 | } |
251 | size = sizeof(struct cciss_scsi_cmd_stack_elem_t) * CMD_STACK_SIZE; | 253 | size = sizeof(struct cciss_scsi_cmd_stack_elem_t) * CMD_STACK_SIZE; |
252 | 254 | ||
253 | pci_free_consistent(hba[ctlr]->pdev, size, stk->pool, stk->cmd_pool_handle); | 255 | pci_free_consistent(h->pdev, size, stk->pool, stk->cmd_pool_handle); |
254 | stk->pool = NULL; | 256 | stk->pool = NULL; |
255 | cciss_free_sg_chain_blocks(sa->cmd_sg_list, CMD_STACK_SIZE); | 257 | cciss_free_sg_chain_blocks(sa->cmd_sg_list, CMD_STACK_SIZE); |
256 | } | 258 | } |
@@ -342,20 +344,20 @@ print_cmd(CommandList_struct *cp) | |||
342 | #endif | 344 | #endif |
343 | 345 | ||
344 | static int | 346 | static int |
345 | find_bus_target_lun(int ctlr, int *bus, int *target, int *lun) | 347 | find_bus_target_lun(ctlr_info_t *h, int *bus, int *target, int *lun) |
346 | { | 348 | { |
347 | /* finds an unused bus, target, lun for a new device */ | 349 | /* finds an unused bus, target, lun for a new device */ |
348 | /* assumes hba[ctlr]->scsi_ctlr->lock is held */ | 350 | /* assumes h->scsi_ctlr->lock is held */ |
349 | int i, found=0; | 351 | int i, found=0; |
350 | unsigned char target_taken[CCISS_MAX_SCSI_DEVS_PER_HBA]; | 352 | unsigned char target_taken[CCISS_MAX_SCSI_DEVS_PER_HBA]; |
351 | 353 | ||
352 | memset(&target_taken[0], 0, CCISS_MAX_SCSI_DEVS_PER_HBA); | 354 | memset(&target_taken[0], 0, CCISS_MAX_SCSI_DEVS_PER_HBA); |
353 | 355 | ||
354 | target_taken[SELF_SCSI_ID] = 1; | 356 | target_taken[SELF_SCSI_ID] = 1; |
355 | for (i=0;i<ccissscsi[ctlr].ndevices;i++) | 357 | for (i = 0; i < ccissscsi[h->ctlr].ndevices; i++) |
356 | target_taken[ccissscsi[ctlr].dev[i].target] = 1; | 358 | target_taken[ccissscsi[h->ctlr].dev[i].target] = 1; |
357 | 359 | ||
358 | for (i=0;i<CCISS_MAX_SCSI_DEVS_PER_HBA;i++) { | 360 | for (i = 0; i < CCISS_MAX_SCSI_DEVS_PER_HBA; i++) { |
359 | if (!target_taken[i]) { | 361 | if (!target_taken[i]) { |
360 | *bus = 0; *target=i; *lun = 0; found=1; | 362 | *bus = 0; *target=i; *lun = 0; found=1; |
361 | break; | 363 | break; |
@@ -369,19 +371,19 @@ struct scsi2map { | |||
369 | }; | 371 | }; |
370 | 372 | ||
371 | static int | 373 | static int |
372 | cciss_scsi_add_entry(int ctlr, int hostno, | 374 | cciss_scsi_add_entry(ctlr_info_t *h, int hostno, |
373 | struct cciss_scsi_dev_t *device, | 375 | struct cciss_scsi_dev_t *device, |
374 | struct scsi2map *added, int *nadded) | 376 | struct scsi2map *added, int *nadded) |
375 | { | 377 | { |
376 | /* assumes hba[ctlr]->scsi_ctlr->lock is held */ | 378 | /* assumes h->scsi_ctlr->lock is held */ |
377 | int n = ccissscsi[ctlr].ndevices; | 379 | int n = ccissscsi[h->ctlr].ndevices; |
378 | struct cciss_scsi_dev_t *sd; | 380 | struct cciss_scsi_dev_t *sd; |
379 | int i, bus, target, lun; | 381 | int i, bus, target, lun; |
380 | unsigned char addr1[8], addr2[8]; | 382 | unsigned char addr1[8], addr2[8]; |
381 | 383 | ||
382 | if (n >= CCISS_MAX_SCSI_DEVS_PER_HBA) { | 384 | if (n >= CCISS_MAX_SCSI_DEVS_PER_HBA) { |
383 | printk("cciss%d: Too many devices, " | 385 | dev_warn(&h->pdev->dev, "Too many devices, " |
384 | "some will be inaccessible.\n", ctlr); | 386 | "some will be inaccessible.\n"); |
385 | return -1; | 387 | return -1; |
386 | } | 388 | } |
387 | 389 | ||
@@ -397,7 +399,7 @@ cciss_scsi_add_entry(int ctlr, int hostno, | |||
397 | memcpy(addr1, device->scsi3addr, 8); | 399 | memcpy(addr1, device->scsi3addr, 8); |
398 | addr1[4] = 0; | 400 | addr1[4] = 0; |
399 | for (i = 0; i < n; i++) { | 401 | for (i = 0; i < n; i++) { |
400 | sd = &ccissscsi[ctlr].dev[i]; | 402 | sd = &ccissscsi[h->ctlr].dev[i]; |
401 | memcpy(addr2, sd->scsi3addr, 8); | 403 | memcpy(addr2, sd->scsi3addr, 8); |
402 | addr2[4] = 0; | 404 | addr2[4] = 0; |
403 | /* differ only in byte 4? */ | 405 | /* differ only in byte 4? */ |
@@ -410,9 +412,9 @@ cciss_scsi_add_entry(int ctlr, int hostno, | |||
410 | } | 412 | } |
411 | } | 413 | } |
412 | 414 | ||
413 | sd = &ccissscsi[ctlr].dev[n]; | 415 | sd = &ccissscsi[h->ctlr].dev[n]; |
414 | if (lun == 0) { | 416 | if (lun == 0) { |
415 | if (find_bus_target_lun(ctlr, | 417 | if (find_bus_target_lun(h, |
416 | &sd->bus, &sd->target, &sd->lun) != 0) | 418 | &sd->bus, &sd->target, &sd->lun) != 0) |
417 | return -1; | 419 | return -1; |
418 | } else { | 420 | } else { |
@@ -431,37 +433,37 @@ cciss_scsi_add_entry(int ctlr, int hostno, | |||
431 | memcpy(sd->device_id, device->device_id, sizeof(sd->device_id)); | 433 | memcpy(sd->device_id, device->device_id, sizeof(sd->device_id)); |
432 | sd->devtype = device->devtype; | 434 | sd->devtype = device->devtype; |
433 | 435 | ||
434 | ccissscsi[ctlr].ndevices++; | 436 | ccissscsi[h->ctlr].ndevices++; |
435 | 437 | ||
436 | /* initially, (before registering with scsi layer) we don't | 438 | /* initially, (before registering with scsi layer) we don't |
437 | know our hostno and we don't want to print anything first | 439 | know our hostno and we don't want to print anything first |
438 | time anyway (the scsi layer's inquiries will show that info) */ | 440 | time anyway (the scsi layer's inquiries will show that info) */ |
439 | if (hostno != -1) | 441 | if (hostno != -1) |
440 | printk("cciss%d: %s device c%db%dt%dl%d added.\n", | 442 | dev_info(&h->pdev->dev, "%s device c%db%dt%dl%d added.\n", |
441 | ctlr, scsi_device_type(sd->devtype), hostno, | 443 | scsi_device_type(sd->devtype), hostno, |
442 | sd->bus, sd->target, sd->lun); | 444 | sd->bus, sd->target, sd->lun); |
443 | return 0; | 445 | return 0; |
444 | } | 446 | } |
445 | 447 | ||
446 | static void | 448 | static void |
447 | cciss_scsi_remove_entry(int ctlr, int hostno, int entry, | 449 | cciss_scsi_remove_entry(ctlr_info_t *h, int hostno, int entry, |
448 | struct scsi2map *removed, int *nremoved) | 450 | struct scsi2map *removed, int *nremoved) |
449 | { | 451 | { |
450 | /* assumes hba[ctlr]->scsi_ctlr->lock is held */ | 452 | /* assumes h->ctlr]->scsi_ctlr->lock is held */ |
451 | int i; | 453 | int i; |
452 | struct cciss_scsi_dev_t sd; | 454 | struct cciss_scsi_dev_t sd; |
453 | 455 | ||
454 | if (entry < 0 || entry >= CCISS_MAX_SCSI_DEVS_PER_HBA) return; | 456 | if (entry < 0 || entry >= CCISS_MAX_SCSI_DEVS_PER_HBA) return; |
455 | sd = ccissscsi[ctlr].dev[entry]; | 457 | sd = ccissscsi[h->ctlr].dev[entry]; |
456 | removed[*nremoved].bus = sd.bus; | 458 | removed[*nremoved].bus = sd.bus; |
457 | removed[*nremoved].target = sd.target; | 459 | removed[*nremoved].target = sd.target; |
458 | removed[*nremoved].lun = sd.lun; | 460 | removed[*nremoved].lun = sd.lun; |
459 | (*nremoved)++; | 461 | (*nremoved)++; |
460 | for (i=entry;i<ccissscsi[ctlr].ndevices-1;i++) | 462 | for (i = entry; i < ccissscsi[h->ctlr].ndevices-1; i++) |
461 | ccissscsi[ctlr].dev[i] = ccissscsi[ctlr].dev[i+1]; | 463 | ccissscsi[h->ctlr].dev[i] = ccissscsi[h->ctlr].dev[i+1]; |
462 | ccissscsi[ctlr].ndevices--; | 464 | ccissscsi[h->ctlr].ndevices--; |
463 | printk("cciss%d: %s device c%db%dt%dl%d removed.\n", | 465 | dev_info(&h->pdev->dev, "%s device c%db%dt%dl%d removed.\n", |
464 | ctlr, scsi_device_type(sd.devtype), hostno, | 466 | scsi_device_type(sd.devtype), hostno, |
465 | sd.bus, sd.target, sd.lun); | 467 | sd.bus, sd.target, sd.lun); |
466 | } | 468 | } |
467 | 469 | ||
@@ -476,24 +478,24 @@ cciss_scsi_remove_entry(int ctlr, int hostno, int entry, | |||
476 | (a)[1] == (b)[1] && \ | 478 | (a)[1] == (b)[1] && \ |
477 | (a)[0] == (b)[0]) | 479 | (a)[0] == (b)[0]) |
478 | 480 | ||
479 | static void fixup_botched_add(int ctlr, char *scsi3addr) | 481 | static void fixup_botched_add(ctlr_info_t *h, char *scsi3addr) |
480 | { | 482 | { |
481 | /* called when scsi_add_device fails in order to re-adjust */ | 483 | /* called when scsi_add_device fails in order to re-adjust */ |
482 | /* ccissscsi[] to match the mid layer's view. */ | 484 | /* ccissscsi[] to match the mid layer's view. */ |
483 | unsigned long flags; | 485 | unsigned long flags; |
484 | int i, j; | 486 | int i, j; |
485 | CPQ_TAPE_LOCK(ctlr, flags); | 487 | CPQ_TAPE_LOCK(h, flags); |
486 | for (i = 0; i < ccissscsi[ctlr].ndevices; i++) { | 488 | for (i = 0; i < ccissscsi[h->ctlr].ndevices; i++) { |
487 | if (memcmp(scsi3addr, | 489 | if (memcmp(scsi3addr, |
488 | ccissscsi[ctlr].dev[i].scsi3addr, 8) == 0) { | 490 | ccissscsi[h->ctlr].dev[i].scsi3addr, 8) == 0) { |
489 | for (j = i; j < ccissscsi[ctlr].ndevices-1; j++) | 491 | for (j = i; j < ccissscsi[h->ctlr].ndevices-1; j++) |
490 | ccissscsi[ctlr].dev[j] = | 492 | ccissscsi[h->ctlr].dev[j] = |
491 | ccissscsi[ctlr].dev[j+1]; | 493 | ccissscsi[h->ctlr].dev[j+1]; |
492 | ccissscsi[ctlr].ndevices--; | 494 | ccissscsi[h->ctlr].ndevices--; |
493 | break; | 495 | break; |
494 | } | 496 | } |
495 | } | 497 | } |
496 | CPQ_TAPE_UNLOCK(ctlr, flags); | 498 | CPQ_TAPE_UNLOCK(h, flags); |
497 | } | 499 | } |
498 | 500 | ||
499 | static int device_is_the_same(struct cciss_scsi_dev_t *dev1, | 501 | static int device_is_the_same(struct cciss_scsi_dev_t *dev1, |
@@ -513,7 +515,7 @@ static int device_is_the_same(struct cciss_scsi_dev_t *dev1, | |||
513 | } | 515 | } |
514 | 516 | ||
515 | static int | 517 | static int |
516 | adjust_cciss_scsi_table(int ctlr, int hostno, | 518 | adjust_cciss_scsi_table(ctlr_info_t *h, int hostno, |
517 | struct cciss_scsi_dev_t sd[], int nsds) | 519 | struct cciss_scsi_dev_t sd[], int nsds) |
518 | { | 520 | { |
519 | /* sd contains scsi3 addresses and devtypes, but | 521 | /* sd contains scsi3 addresses and devtypes, but |
@@ -534,15 +536,15 @@ adjust_cciss_scsi_table(int ctlr, int hostno, | |||
534 | GFP_KERNEL); | 536 | GFP_KERNEL); |
535 | 537 | ||
536 | if (!added || !removed) { | 538 | if (!added || !removed) { |
537 | printk(KERN_WARNING "cciss%d: Out of memory in " | 539 | dev_warn(&h->pdev->dev, |
538 | "adjust_cciss_scsi_table\n", ctlr); | 540 | "Out of memory in adjust_cciss_scsi_table\n"); |
539 | goto free_and_out; | 541 | goto free_and_out; |
540 | } | 542 | } |
541 | 543 | ||
542 | CPQ_TAPE_LOCK(ctlr, flags); | 544 | CPQ_TAPE_LOCK(h, flags); |
543 | 545 | ||
544 | if (hostno != -1) /* if it's not the first time... */ | 546 | if (hostno != -1) /* if it's not the first time... */ |
545 | sh = hba[ctlr]->scsi_ctlr->scsi_host; | 547 | sh = h->scsi_ctlr->scsi_host; |
546 | 548 | ||
547 | /* find any devices in ccissscsi[] that are not in | 549 | /* find any devices in ccissscsi[] that are not in |
548 | sd[] and remove them from ccissscsi[] */ | 550 | sd[] and remove them from ccissscsi[] */ |
@@ -550,8 +552,8 @@ adjust_cciss_scsi_table(int ctlr, int hostno, | |||
550 | i = 0; | 552 | i = 0; |
551 | nremoved = 0; | 553 | nremoved = 0; |
552 | nadded = 0; | 554 | nadded = 0; |
553 | while(i<ccissscsi[ctlr].ndevices) { | 555 | while (i < ccissscsi[h->ctlr].ndevices) { |
554 | csd = &ccissscsi[ctlr].dev[i]; | 556 | csd = &ccissscsi[h->ctlr].dev[i]; |
555 | found=0; | 557 | found=0; |
556 | for (j=0;j<nsds;j++) { | 558 | for (j=0;j<nsds;j++) { |
557 | if (SCSI3ADDR_EQ(sd[j].scsi3addr, | 559 | if (SCSI3ADDR_EQ(sd[j].scsi3addr, |
@@ -566,20 +568,18 @@ adjust_cciss_scsi_table(int ctlr, int hostno, | |||
566 | 568 | ||
567 | if (found == 0) { /* device no longer present. */ | 569 | if (found == 0) { /* device no longer present. */ |
568 | changes++; | 570 | changes++; |
569 | /* printk("cciss%d: %s device c%db%dt%dl%d removed.\n", | 571 | cciss_scsi_remove_entry(h, hostno, i, |
570 | ctlr, scsi_device_type(csd->devtype), hostno, | ||
571 | csd->bus, csd->target, csd->lun); */ | ||
572 | cciss_scsi_remove_entry(ctlr, hostno, i, | ||
573 | removed, &nremoved); | 572 | removed, &nremoved); |
574 | /* remove ^^^, hence i not incremented */ | 573 | /* remove ^^^, hence i not incremented */ |
575 | } else if (found == 1) { /* device is different in some way */ | 574 | } else if (found == 1) { /* device is different in some way */ |
576 | changes++; | 575 | changes++; |
577 | printk("cciss%d: device c%db%dt%dl%d has changed.\n", | 576 | dev_info(&h->pdev->dev, |
578 | ctlr, hostno, csd->bus, csd->target, csd->lun); | 577 | "device c%db%dt%dl%d has changed.\n", |
579 | cciss_scsi_remove_entry(ctlr, hostno, i, | 578 | hostno, csd->bus, csd->target, csd->lun); |
579 | cciss_scsi_remove_entry(h, hostno, i, | ||
580 | removed, &nremoved); | 580 | removed, &nremoved); |
581 | /* remove ^^^, hence i not incremented */ | 581 | /* remove ^^^, hence i not incremented */ |
582 | if (cciss_scsi_add_entry(ctlr, hostno, &sd[j], | 582 | if (cciss_scsi_add_entry(h, hostno, &sd[j], |
583 | added, &nadded) != 0) | 583 | added, &nadded) != 0) |
584 | /* we just removed one, so add can't fail. */ | 584 | /* we just removed one, so add can't fail. */ |
585 | BUG(); | 585 | BUG(); |
@@ -601,8 +601,8 @@ adjust_cciss_scsi_table(int ctlr, int hostno, | |||
601 | 601 | ||
602 | for (i=0;i<nsds;i++) { | 602 | for (i=0;i<nsds;i++) { |
603 | found=0; | 603 | found=0; |
604 | for (j=0;j<ccissscsi[ctlr].ndevices;j++) { | 604 | for (j = 0; j < ccissscsi[h->ctlr].ndevices; j++) { |
605 | csd = &ccissscsi[ctlr].dev[j]; | 605 | csd = &ccissscsi[h->ctlr].dev[j]; |
606 | if (SCSI3ADDR_EQ(sd[i].scsi3addr, | 606 | if (SCSI3ADDR_EQ(sd[i].scsi3addr, |
607 | csd->scsi3addr)) { | 607 | csd->scsi3addr)) { |
608 | if (device_is_the_same(&sd[i], csd)) | 608 | if (device_is_the_same(&sd[i], csd)) |
@@ -614,18 +614,18 @@ adjust_cciss_scsi_table(int ctlr, int hostno, | |||
614 | } | 614 | } |
615 | if (!found) { | 615 | if (!found) { |
616 | changes++; | 616 | changes++; |
617 | if (cciss_scsi_add_entry(ctlr, hostno, &sd[i], | 617 | if (cciss_scsi_add_entry(h, hostno, &sd[i], |
618 | added, &nadded) != 0) | 618 | added, &nadded) != 0) |
619 | break; | 619 | break; |
620 | } else if (found == 1) { | 620 | } else if (found == 1) { |
621 | /* should never happen... */ | 621 | /* should never happen... */ |
622 | changes++; | 622 | changes++; |
623 | printk(KERN_WARNING "cciss%d: device " | 623 | dev_warn(&h->pdev->dev, |
624 | "unexpectedly changed\n", ctlr); | 624 | "device unexpectedly changed\n"); |
625 | /* but if it does happen, we just ignore that device */ | 625 | /* but if it does happen, we just ignore that device */ |
626 | } | 626 | } |
627 | } | 627 | } |
628 | CPQ_TAPE_UNLOCK(ctlr, flags); | 628 | CPQ_TAPE_UNLOCK(h, flags); |
629 | 629 | ||
630 | /* Don't notify scsi mid layer of any changes the first time through */ | 630 | /* Don't notify scsi mid layer of any changes the first time through */ |
631 | /* (or if there are no changes) scsi_scan_host will do it later the */ | 631 | /* (or if there are no changes) scsi_scan_host will do it later the */ |
@@ -645,9 +645,9 @@ adjust_cciss_scsi_table(int ctlr, int hostno, | |||
645 | /* We don't expect to get here. */ | 645 | /* We don't expect to get here. */ |
646 | /* future cmds to this device will get selection */ | 646 | /* future cmds to this device will get selection */ |
647 | /* timeout as if the device was gone. */ | 647 | /* timeout as if the device was gone. */ |
648 | printk(KERN_WARNING "cciss%d: didn't find " | 648 | dev_warn(&h->pdev->dev, "didn't find " |
649 | "c%db%dt%dl%d\n for removal.", | 649 | "c%db%dt%dl%d\n for removal.", |
650 | ctlr, hostno, removed[i].bus, | 650 | hostno, removed[i].bus, |
651 | removed[i].target, removed[i].lun); | 651 | removed[i].target, removed[i].lun); |
652 | } | 652 | } |
653 | } | 653 | } |
@@ -659,13 +659,12 @@ adjust_cciss_scsi_table(int ctlr, int hostno, | |||
659 | added[i].target, added[i].lun); | 659 | added[i].target, added[i].lun); |
660 | if (rc == 0) | 660 | if (rc == 0) |
661 | continue; | 661 | continue; |
662 | printk(KERN_WARNING "cciss%d: scsi_add_device " | 662 | dev_warn(&h->pdev->dev, "scsi_add_device " |
663 | "c%db%dt%dl%d failed, device not added.\n", | 663 | "c%db%dt%dl%d failed, device not added.\n", |
664 | ctlr, hostno, | 664 | hostno, added[i].bus, added[i].target, added[i].lun); |
665 | added[i].bus, added[i].target, added[i].lun); | ||
666 | /* now we have to remove it from ccissscsi, */ | 665 | /* now we have to remove it from ccissscsi, */ |
667 | /* since it didn't get added to scsi mid layer */ | 666 | /* since it didn't get added to scsi mid layer */ |
668 | fixup_botched_add(ctlr, added[i].scsi3addr); | 667 | fixup_botched_add(h, added[i].scsi3addr); |
669 | } | 668 | } |
670 | 669 | ||
671 | free_and_out: | 670 | free_and_out: |
@@ -675,33 +674,33 @@ free_and_out: | |||
675 | } | 674 | } |
676 | 675 | ||
677 | static int | 676 | static int |
678 | lookup_scsi3addr(int ctlr, int bus, int target, int lun, char *scsi3addr) | 677 | lookup_scsi3addr(ctlr_info_t *h, int bus, int target, int lun, char *scsi3addr) |
679 | { | 678 | { |
680 | int i; | 679 | int i; |
681 | struct cciss_scsi_dev_t *sd; | 680 | struct cciss_scsi_dev_t *sd; |
682 | unsigned long flags; | 681 | unsigned long flags; |
683 | 682 | ||
684 | CPQ_TAPE_LOCK(ctlr, flags); | 683 | CPQ_TAPE_LOCK(h, flags); |
685 | for (i=0;i<ccissscsi[ctlr].ndevices;i++) { | 684 | for (i = 0; i < ccissscsi[h->ctlr].ndevices; i++) { |
686 | sd = &ccissscsi[ctlr].dev[i]; | 685 | sd = &ccissscsi[h->ctlr].dev[i]; |
687 | if (sd->bus == bus && | 686 | if (sd->bus == bus && |
688 | sd->target == target && | 687 | sd->target == target && |
689 | sd->lun == lun) { | 688 | sd->lun == lun) { |
690 | memcpy(scsi3addr, &sd->scsi3addr[0], 8); | 689 | memcpy(scsi3addr, &sd->scsi3addr[0], 8); |
691 | CPQ_TAPE_UNLOCK(ctlr, flags); | 690 | CPQ_TAPE_UNLOCK(h, flags); |
692 | return 0; | 691 | return 0; |
693 | } | 692 | } |
694 | } | 693 | } |
695 | CPQ_TAPE_UNLOCK(ctlr, flags); | 694 | CPQ_TAPE_UNLOCK(h, flags); |
696 | return -1; | 695 | return -1; |
697 | } | 696 | } |
698 | 697 | ||
699 | static void | 698 | static void |
700 | cciss_scsi_setup(int cntl_num) | 699 | cciss_scsi_setup(ctlr_info_t *h) |
701 | { | 700 | { |
702 | struct cciss_scsi_adapter_data_t * shba; | 701 | struct cciss_scsi_adapter_data_t * shba; |
703 | 702 | ||
704 | ccissscsi[cntl_num].ndevices = 0; | 703 | ccissscsi[h->ctlr].ndevices = 0; |
705 | shba = (struct cciss_scsi_adapter_data_t *) | 704 | shba = (struct cciss_scsi_adapter_data_t *) |
706 | kmalloc(sizeof(*shba), GFP_KERNEL); | 705 | kmalloc(sizeof(*shba), GFP_KERNEL); |
707 | if (shba == NULL) | 706 | if (shba == NULL) |
@@ -709,35 +708,35 @@ cciss_scsi_setup(int cntl_num) | |||
709 | shba->scsi_host = NULL; | 708 | shba->scsi_host = NULL; |
710 | spin_lock_init(&shba->lock); | 709 | spin_lock_init(&shba->lock); |
711 | shba->registered = 0; | 710 | shba->registered = 0; |
712 | if (scsi_cmd_stack_setup(cntl_num, shba) != 0) { | 711 | if (scsi_cmd_stack_setup(h, shba) != 0) { |
713 | kfree(shba); | 712 | kfree(shba); |
714 | shba = NULL; | 713 | shba = NULL; |
715 | } | 714 | } |
716 | hba[cntl_num]->scsi_ctlr = shba; | 715 | h->scsi_ctlr = shba; |
717 | return; | 716 | return; |
718 | } | 717 | } |
719 | 718 | ||
720 | static void | 719 | static void complete_scsi_command(CommandList_struct *c, int timeout, |
721 | complete_scsi_command( CommandList_struct *cp, int timeout, __u32 tag) | 720 | __u32 tag) |
722 | { | 721 | { |
723 | struct scsi_cmnd *cmd; | 722 | struct scsi_cmnd *cmd; |
724 | ctlr_info_t *ctlr; | 723 | ctlr_info_t *h; |
725 | ErrorInfo_struct *ei; | 724 | ErrorInfo_struct *ei; |
726 | 725 | ||
727 | ei = cp->err_info; | 726 | ei = c->err_info; |
728 | 727 | ||
729 | /* First, see if it was a message rather than a command */ | 728 | /* First, see if it was a message rather than a command */ |
730 | if (cp->Request.Type.Type == TYPE_MSG) { | 729 | if (c->Request.Type.Type == TYPE_MSG) { |
731 | cp->cmd_type = CMD_MSG_DONE; | 730 | c->cmd_type = CMD_MSG_DONE; |
732 | return; | 731 | return; |
733 | } | 732 | } |
734 | 733 | ||
735 | cmd = (struct scsi_cmnd *) cp->scsi_cmd; | 734 | cmd = (struct scsi_cmnd *) c->scsi_cmd; |
736 | ctlr = hba[cp->ctlr]; | 735 | h = hba[c->ctlr]; |
737 | 736 | ||
738 | scsi_dma_unmap(cmd); | 737 | scsi_dma_unmap(cmd); |
739 | if (cp->Header.SGTotal > ctlr->max_cmd_sgentries) | 738 | if (c->Header.SGTotal > h->max_cmd_sgentries) |
740 | cciss_unmap_sg_chain_block(ctlr, cp); | 739 | cciss_unmap_sg_chain_block(h, c); |
741 | 740 | ||
742 | cmd->result = (DID_OK << 16); /* host byte */ | 741 | cmd->result = (DID_OK << 16); /* host byte */ |
743 | cmd->result |= (COMMAND_COMPLETE << 8); /* msg byte */ | 742 | cmd->result |= (COMMAND_COMPLETE << 8); /* msg byte */ |
@@ -764,9 +763,8 @@ complete_scsi_command( CommandList_struct *cp, int timeout, __u32 tag) | |||
764 | { | 763 | { |
765 | #if 0 | 764 | #if 0 |
766 | printk(KERN_WARNING "cciss: cmd %p " | 765 | printk(KERN_WARNING "cciss: cmd %p " |
767 | "has SCSI Status = %x\n", | 766 | "has SCSI Status = %x\n", |
768 | cp, | 767 | c, ei->ScsiStatus); |
769 | ei->ScsiStatus); | ||
770 | #endif | 768 | #endif |
771 | cmd->result |= (ei->ScsiStatus << 1); | 769 | cmd->result |= (ei->ScsiStatus << 1); |
772 | } | 770 | } |
@@ -786,13 +784,13 @@ complete_scsi_command( CommandList_struct *cp, int timeout, __u32 tag) | |||
786 | case CMD_DATA_UNDERRUN: /* let mid layer handle it. */ | 784 | case CMD_DATA_UNDERRUN: /* let mid layer handle it. */ |
787 | break; | 785 | break; |
788 | case CMD_DATA_OVERRUN: | 786 | case CMD_DATA_OVERRUN: |
789 | printk(KERN_WARNING "cciss: cp %p has" | 787 | dev_warn(&h->pdev->dev, "%p has" |
790 | " completed with data overrun " | 788 | " completed with data overrun " |
791 | "reported\n", cp); | 789 | "reported\n", c); |
792 | break; | 790 | break; |
793 | case CMD_INVALID: { | 791 | case CMD_INVALID: { |
794 | /* print_bytes(cp, sizeof(*cp), 1, 0); | 792 | /* print_bytes(c, sizeof(*c), 1, 0); |
795 | print_cmd(cp); */ | 793 | print_cmd(c); */ |
796 | /* We get CMD_INVALID if you address a non-existent tape drive instead | 794 | /* We get CMD_INVALID if you address a non-existent tape drive instead |
797 | of a selection timeout (no response). You will see this if you yank | 795 | of a selection timeout (no response). You will see this if you yank |
798 | out a tape drive, then try to access it. This is kind of a shame | 796 | out a tape drive, then try to access it. This is kind of a shame |
@@ -802,54 +800,50 @@ complete_scsi_command( CommandList_struct *cp, int timeout, __u32 tag) | |||
802 | } | 800 | } |
803 | break; | 801 | break; |
804 | case CMD_PROTOCOL_ERR: | 802 | case CMD_PROTOCOL_ERR: |
805 | printk(KERN_WARNING "cciss: cp %p has " | 803 | dev_warn(&h->pdev->dev, |
806 | "protocol error \n", cp); | 804 | "%p has protocol error\n", c); |
807 | break; | 805 | break; |
808 | case CMD_HARDWARE_ERR: | 806 | case CMD_HARDWARE_ERR: |
809 | cmd->result = DID_ERROR << 16; | 807 | cmd->result = DID_ERROR << 16; |
810 | printk(KERN_WARNING "cciss: cp %p had " | 808 | dev_warn(&h->pdev->dev, |
811 | " hardware error\n", cp); | 809 | "%p had hardware error\n", c); |
812 | break; | 810 | break; |
813 | case CMD_CONNECTION_LOST: | 811 | case CMD_CONNECTION_LOST: |
814 | cmd->result = DID_ERROR << 16; | 812 | cmd->result = DID_ERROR << 16; |
815 | printk(KERN_WARNING "cciss: cp %p had " | 813 | dev_warn(&h->pdev->dev, |
816 | "connection lost\n", cp); | 814 | "%p had connection lost\n", c); |
817 | break; | 815 | break; |
818 | case CMD_ABORTED: | 816 | case CMD_ABORTED: |
819 | cmd->result = DID_ABORT << 16; | 817 | cmd->result = DID_ABORT << 16; |
820 | printk(KERN_WARNING "cciss: cp %p was " | 818 | dev_warn(&h->pdev->dev, "%p was aborted\n", c); |
821 | "aborted\n", cp); | ||
822 | break; | 819 | break; |
823 | case CMD_ABORT_FAILED: | 820 | case CMD_ABORT_FAILED: |
824 | cmd->result = DID_ERROR << 16; | 821 | cmd->result = DID_ERROR << 16; |
825 | printk(KERN_WARNING "cciss: cp %p reports " | 822 | dev_warn(&h->pdev->dev, |
826 | "abort failed\n", cp); | 823 | "%p reports abort failed\n", c); |
827 | break; | 824 | break; |
828 | case CMD_UNSOLICITED_ABORT: | 825 | case CMD_UNSOLICITED_ABORT: |
829 | cmd->result = DID_ABORT << 16; | 826 | cmd->result = DID_ABORT << 16; |
830 | printk(KERN_WARNING "cciss: cp %p aborted " | 827 | dev_warn(&h->pdev->dev, "%p aborted do to an " |
831 | "do to an unsolicited abort\n", cp); | 828 | "unsolicited abort\n", c); |
832 | break; | 829 | break; |
833 | case CMD_TIMEOUT: | 830 | case CMD_TIMEOUT: |
834 | cmd->result = DID_TIME_OUT << 16; | 831 | cmd->result = DID_TIME_OUT << 16; |
835 | printk(KERN_WARNING "cciss: cp %p timedout\n", | 832 | dev_warn(&h->pdev->dev, "%p timedout\n", c); |
836 | cp); | ||
837 | break; | 833 | break; |
838 | default: | 834 | default: |
839 | cmd->result = DID_ERROR << 16; | 835 | cmd->result = DID_ERROR << 16; |
840 | printk(KERN_WARNING "cciss: cp %p returned " | 836 | dev_warn(&h->pdev->dev, |
841 | "unknown status %x\n", cp, | 837 | "%p returned unknown status %x\n", c, |
842 | ei->CommandStatus); | 838 | ei->CommandStatus); |
843 | } | 839 | } |
844 | } | 840 | } |
845 | // printk("c:%p:c%db%dt%dl%d ", cmd, ctlr->ctlr, cmd->channel, | ||
846 | // cmd->target, cmd->lun); | ||
847 | cmd->scsi_done(cmd); | 841 | cmd->scsi_done(cmd); |
848 | scsi_cmd_free(ctlr, cp); | 842 | scsi_cmd_free(h, c); |
849 | } | 843 | } |
850 | 844 | ||
851 | static int | 845 | static int |
852 | cciss_scsi_detect(int ctlr) | 846 | cciss_scsi_detect(ctlr_info_t *h) |
853 | { | 847 | { |
854 | struct Scsi_Host *sh; | 848 | struct Scsi_Host *sh; |
855 | int error; | 849 | int error; |
@@ -860,15 +854,15 @@ cciss_scsi_detect(int ctlr) | |||
860 | sh->io_port = 0; // good enough? FIXME, | 854 | sh->io_port = 0; // good enough? FIXME, |
861 | sh->n_io_port = 0; // I don't think we use these two... | 855 | sh->n_io_port = 0; // I don't think we use these two... |
862 | sh->this_id = SELF_SCSI_ID; | 856 | sh->this_id = SELF_SCSI_ID; |
863 | sh->sg_tablesize = hba[ctlr]->maxsgentries; | 857 | sh->sg_tablesize = h->maxsgentries; |
864 | sh->max_cmd_len = MAX_COMMAND_SIZE; | 858 | sh->max_cmd_len = MAX_COMMAND_SIZE; |
865 | 859 | ||
866 | ((struct cciss_scsi_adapter_data_t *) | 860 | ((struct cciss_scsi_adapter_data_t *) |
867 | hba[ctlr]->scsi_ctlr)->scsi_host = sh; | 861 | h->scsi_ctlr)->scsi_host = sh; |
868 | sh->hostdata[0] = (unsigned long) hba[ctlr]; | 862 | sh->hostdata[0] = (unsigned long) h; |
869 | sh->irq = hba[ctlr]->intr[SIMPLE_MODE_INT]; | 863 | sh->irq = h->intr[SIMPLE_MODE_INT]; |
870 | sh->unique_id = sh->irq; | 864 | sh->unique_id = sh->irq; |
871 | error = scsi_add_host(sh, &hba[ctlr]->pdev->dev); | 865 | error = scsi_add_host(sh, &h->pdev->dev); |
872 | if (error) | 866 | if (error) |
873 | goto fail_host_put; | 867 | goto fail_host_put; |
874 | scsi_scan_host(sh); | 868 | scsi_scan_host(sh); |
@@ -882,20 +876,20 @@ cciss_scsi_detect(int ctlr) | |||
882 | 876 | ||
883 | static void | 877 | static void |
884 | cciss_unmap_one(struct pci_dev *pdev, | 878 | cciss_unmap_one(struct pci_dev *pdev, |
885 | CommandList_struct *cp, | 879 | CommandList_struct *c, |
886 | size_t buflen, | 880 | size_t buflen, |
887 | int data_direction) | 881 | int data_direction) |
888 | { | 882 | { |
889 | u64bit addr64; | 883 | u64bit addr64; |
890 | 884 | ||
891 | addr64.val32.lower = cp->SG[0].Addr.lower; | 885 | addr64.val32.lower = c->SG[0].Addr.lower; |
892 | addr64.val32.upper = cp->SG[0].Addr.upper; | 886 | addr64.val32.upper = c->SG[0].Addr.upper; |
893 | pci_unmap_single(pdev, (dma_addr_t) addr64.val, buflen, data_direction); | 887 | pci_unmap_single(pdev, (dma_addr_t) addr64.val, buflen, data_direction); |
894 | } | 888 | } |
895 | 889 | ||
896 | static void | 890 | static void |
897 | cciss_map_one(struct pci_dev *pdev, | 891 | cciss_map_one(struct pci_dev *pdev, |
898 | CommandList_struct *cp, | 892 | CommandList_struct *c, |
899 | unsigned char *buf, | 893 | unsigned char *buf, |
900 | size_t buflen, | 894 | size_t buflen, |
901 | int data_direction) | 895 | int data_direction) |
@@ -903,164 +897,149 @@ cciss_map_one(struct pci_dev *pdev, | |||
903 | __u64 addr64; | 897 | __u64 addr64; |
904 | 898 | ||
905 | addr64 = (__u64) pci_map_single(pdev, buf, buflen, data_direction); | 899 | addr64 = (__u64) pci_map_single(pdev, buf, buflen, data_direction); |
906 | cp->SG[0].Addr.lower = | 900 | c->SG[0].Addr.lower = |
907 | (__u32) (addr64 & (__u64) 0x00000000FFFFFFFF); | 901 | (__u32) (addr64 & (__u64) 0x00000000FFFFFFFF); |
908 | cp->SG[0].Addr.upper = | 902 | c->SG[0].Addr.upper = |
909 | (__u32) ((addr64 >> 32) & (__u64) 0x00000000FFFFFFFF); | 903 | (__u32) ((addr64 >> 32) & (__u64) 0x00000000FFFFFFFF); |
910 | cp->SG[0].Len = buflen; | 904 | c->SG[0].Len = buflen; |
911 | cp->Header.SGList = (__u8) 1; /* no. SGs contig in this cmd */ | 905 | c->Header.SGList = (__u8) 1; /* no. SGs contig in this cmd */ |
912 | cp->Header.SGTotal = (__u16) 1; /* total sgs in this cmd list */ | 906 | c->Header.SGTotal = (__u16) 1; /* total sgs in this cmd list */ |
913 | } | 907 | } |
914 | 908 | ||
915 | static int | 909 | static int |
916 | cciss_scsi_do_simple_cmd(ctlr_info_t *c, | 910 | cciss_scsi_do_simple_cmd(ctlr_info_t *h, |
917 | CommandList_struct *cp, | 911 | CommandList_struct *c, |
918 | unsigned char *scsi3addr, | 912 | unsigned char *scsi3addr, |
919 | unsigned char *cdb, | 913 | unsigned char *cdb, |
920 | unsigned char cdblen, | 914 | unsigned char cdblen, |
921 | unsigned char *buf, int bufsize, | 915 | unsigned char *buf, int bufsize, |
922 | int direction) | 916 | int direction) |
923 | { | 917 | { |
924 | unsigned long flags; | ||
925 | DECLARE_COMPLETION_ONSTACK(wait); | 918 | DECLARE_COMPLETION_ONSTACK(wait); |
926 | 919 | ||
927 | cp->cmd_type = CMD_IOCTL_PEND; // treat this like an ioctl | 920 | c->cmd_type = CMD_IOCTL_PEND; /* treat this like an ioctl */ |
928 | cp->scsi_cmd = NULL; | 921 | c->scsi_cmd = NULL; |
929 | cp->Header.ReplyQueue = 0; // unused in simple mode | 922 | c->Header.ReplyQueue = 0; /* unused in simple mode */ |
930 | memcpy(&cp->Header.LUN, scsi3addr, sizeof(cp->Header.LUN)); | 923 | memcpy(&c->Header.LUN, scsi3addr, sizeof(c->Header.LUN)); |
931 | cp->Header.Tag.lower = cp->busaddr; // Use k. address of cmd as tag | 924 | c->Header.Tag.lower = c->busaddr; /* Use k. address of cmd as tag */ |
932 | // Fill in the request block... | 925 | // Fill in the request block... |
933 | 926 | ||
934 | /* printk("Using scsi3addr 0x%02x%0x2%0x2%0x2%0x2%0x2%0x2%0x2\n", | 927 | /* printk("Using scsi3addr 0x%02x%0x2%0x2%0x2%0x2%0x2%0x2%0x2\n", |
935 | scsi3addr[0], scsi3addr[1], scsi3addr[2], scsi3addr[3], | 928 | scsi3addr[0], scsi3addr[1], scsi3addr[2], scsi3addr[3], |
936 | scsi3addr[4], scsi3addr[5], scsi3addr[6], scsi3addr[7]); */ | 929 | scsi3addr[4], scsi3addr[5], scsi3addr[6], scsi3addr[7]); */ |
937 | 930 | ||
938 | memset(cp->Request.CDB, 0, sizeof(cp->Request.CDB)); | 931 | memset(c->Request.CDB, 0, sizeof(c->Request.CDB)); |
939 | memcpy(cp->Request.CDB, cdb, cdblen); | 932 | memcpy(c->Request.CDB, cdb, cdblen); |
940 | cp->Request.Timeout = 0; | 933 | c->Request.Timeout = 0; |
941 | cp->Request.CDBLen = cdblen; | 934 | c->Request.CDBLen = cdblen; |
942 | cp->Request.Type.Type = TYPE_CMD; | 935 | c->Request.Type.Type = TYPE_CMD; |
943 | cp->Request.Type.Attribute = ATTR_SIMPLE; | 936 | c->Request.Type.Attribute = ATTR_SIMPLE; |
944 | cp->Request.Type.Direction = direction; | 937 | c->Request.Type.Direction = direction; |
945 | 938 | ||
946 | /* Fill in the SG list and do dma mapping */ | 939 | /* Fill in the SG list and do dma mapping */ |
947 | cciss_map_one(c->pdev, cp, (unsigned char *) buf, | 940 | cciss_map_one(h->pdev, c, (unsigned char *) buf, |
948 | bufsize, DMA_FROM_DEVICE); | 941 | bufsize, DMA_FROM_DEVICE); |
949 | 942 | ||
950 | cp->waiting = &wait; | 943 | c->waiting = &wait; |
951 | 944 | enqueue_cmd_and_start_io(h, c); | |
952 | /* Put the request on the tail of the request queue */ | ||
953 | spin_lock_irqsave(CCISS_LOCK(c->ctlr), flags); | ||
954 | addQ(&c->reqQ, cp); | ||
955 | c->Qdepth++; | ||
956 | start_io(c); | ||
957 | spin_unlock_irqrestore(CCISS_LOCK(c->ctlr), flags); | ||
958 | |||
959 | wait_for_completion(&wait); | 945 | wait_for_completion(&wait); |
960 | 946 | ||
961 | /* undo the dma mapping */ | 947 | /* undo the dma mapping */ |
962 | cciss_unmap_one(c->pdev, cp, bufsize, DMA_FROM_DEVICE); | 948 | cciss_unmap_one(h->pdev, c, bufsize, DMA_FROM_DEVICE); |
963 | return(0); | 949 | return(0); |
964 | } | 950 | } |
965 | 951 | ||
966 | static void | 952 | static void |
967 | cciss_scsi_interpret_error(CommandList_struct *cp) | 953 | cciss_scsi_interpret_error(ctlr_info_t *h, CommandList_struct *c) |
968 | { | 954 | { |
969 | ErrorInfo_struct *ei; | 955 | ErrorInfo_struct *ei; |
970 | 956 | ||
971 | ei = cp->err_info; | 957 | ei = c->err_info; |
972 | switch(ei->CommandStatus) | 958 | switch(ei->CommandStatus) |
973 | { | 959 | { |
974 | case CMD_TARGET_STATUS: | 960 | case CMD_TARGET_STATUS: |
975 | printk(KERN_WARNING "cciss: cmd %p has " | 961 | dev_warn(&h->pdev->dev, |
976 | "completed with errors\n", cp); | 962 | "cmd %p has completed with errors\n", c); |
977 | printk(KERN_WARNING "cciss: cmd %p " | 963 | dev_warn(&h->pdev->dev, |
978 | "has SCSI Status = %x\n", | 964 | "cmd %p has SCSI Status = %x\n", |
979 | cp, | 965 | c, ei->ScsiStatus); |
980 | ei->ScsiStatus); | ||
981 | if (ei->ScsiStatus == 0) | 966 | if (ei->ScsiStatus == 0) |
982 | printk(KERN_WARNING | 967 | dev_warn(&h->pdev->dev, |
983 | "cciss:SCSI status is abnormally zero. " | 968 | "SCSI status is abnormally zero. " |
984 | "(probably indicates selection timeout " | 969 | "(probably indicates selection timeout " |
985 | "reported incorrectly due to a known " | 970 | "reported incorrectly due to a known " |
986 | "firmware bug, circa July, 2001.)\n"); | 971 | "firmware bug, circa July, 2001.)\n"); |
987 | break; | 972 | break; |
988 | case CMD_DATA_UNDERRUN: /* let mid layer handle it. */ | 973 | case CMD_DATA_UNDERRUN: /* let mid layer handle it. */ |
989 | printk("UNDERRUN\n"); | 974 | dev_info(&h->pdev->dev, "UNDERRUN\n"); |
990 | break; | 975 | break; |
991 | case CMD_DATA_OVERRUN: | 976 | case CMD_DATA_OVERRUN: |
992 | printk(KERN_WARNING "cciss: cp %p has" | 977 | dev_warn(&h->pdev->dev, "%p has" |
993 | " completed with data overrun " | 978 | " completed with data overrun " |
994 | "reported\n", cp); | 979 | "reported\n", c); |
995 | break; | 980 | break; |
996 | case CMD_INVALID: { | 981 | case CMD_INVALID: { |
997 | /* controller unfortunately reports SCSI passthru's */ | 982 | /* controller unfortunately reports SCSI passthru's */ |
998 | /* to non-existent targets as invalid commands. */ | 983 | /* to non-existent targets as invalid commands. */ |
999 | printk(KERN_WARNING "cciss: cp %p is " | 984 | dev_warn(&h->pdev->dev, |
1000 | "reported invalid (probably means " | 985 | "%p is reported invalid (probably means " |
1001 | "target device no longer present)\n", | 986 | "target device no longer present)\n", c); |
1002 | cp); | 987 | /* print_bytes((unsigned char *) c, sizeof(*c), 1, 0); |
1003 | /* print_bytes((unsigned char *) cp, sizeof(*cp), 1, 0); | 988 | print_cmd(c); */ |
1004 | print_cmd(cp); */ | ||
1005 | } | 989 | } |
1006 | break; | 990 | break; |
1007 | case CMD_PROTOCOL_ERR: | 991 | case CMD_PROTOCOL_ERR: |
1008 | printk(KERN_WARNING "cciss: cp %p has " | 992 | dev_warn(&h->pdev->dev, "%p has protocol error\n", c); |
1009 | "protocol error \n", cp); | ||
1010 | break; | 993 | break; |
1011 | case CMD_HARDWARE_ERR: | 994 | case CMD_HARDWARE_ERR: |
1012 | /* cmd->result = DID_ERROR << 16; */ | 995 | /* cmd->result = DID_ERROR << 16; */ |
1013 | printk(KERN_WARNING "cciss: cp %p had " | 996 | dev_warn(&h->pdev->dev, "%p had hardware error\n", c); |
1014 | " hardware error\n", cp); | ||
1015 | break; | 997 | break; |
1016 | case CMD_CONNECTION_LOST: | 998 | case CMD_CONNECTION_LOST: |
1017 | printk(KERN_WARNING "cciss: cp %p had " | 999 | dev_warn(&h->pdev->dev, "%p had connection lost\n", c); |
1018 | "connection lost\n", cp); | ||
1019 | break; | 1000 | break; |
1020 | case CMD_ABORTED: | 1001 | case CMD_ABORTED: |
1021 | printk(KERN_WARNING "cciss: cp %p was " | 1002 | dev_warn(&h->pdev->dev, "%p was aborted\n", c); |
1022 | "aborted\n", cp); | ||
1023 | break; | 1003 | break; |
1024 | case CMD_ABORT_FAILED: | 1004 | case CMD_ABORT_FAILED: |
1025 | printk(KERN_WARNING "cciss: cp %p reports " | 1005 | dev_warn(&h->pdev->dev, |
1026 | "abort failed\n", cp); | 1006 | "%p reports abort failed\n", c); |
1027 | break; | 1007 | break; |
1028 | case CMD_UNSOLICITED_ABORT: | 1008 | case CMD_UNSOLICITED_ABORT: |
1029 | printk(KERN_WARNING "cciss: cp %p aborted " | 1009 | dev_warn(&h->pdev->dev, |
1030 | "do to an unsolicited abort\n", cp); | 1010 | "%p aborted do to an unsolicited abort\n", c); |
1031 | break; | 1011 | break; |
1032 | case CMD_TIMEOUT: | 1012 | case CMD_TIMEOUT: |
1033 | printk(KERN_WARNING "cciss: cp %p timedout\n", | 1013 | dev_warn(&h->pdev->dev, "%p timedout\n", c); |
1034 | cp); | ||
1035 | break; | 1014 | break; |
1036 | default: | 1015 | default: |
1037 | printk(KERN_WARNING "cciss: cp %p returned " | 1016 | dev_warn(&h->pdev->dev, |
1038 | "unknown status %x\n", cp, | 1017 | "%p returned unknown status %x\n", |
1039 | ei->CommandStatus); | 1018 | c, ei->CommandStatus); |
1040 | } | 1019 | } |
1041 | } | 1020 | } |
1042 | 1021 | ||
1043 | static int | 1022 | static int |
1044 | cciss_scsi_do_inquiry(ctlr_info_t *c, unsigned char *scsi3addr, | 1023 | cciss_scsi_do_inquiry(ctlr_info_t *h, unsigned char *scsi3addr, |
1045 | unsigned char page, unsigned char *buf, | 1024 | unsigned char page, unsigned char *buf, |
1046 | unsigned char bufsize) | 1025 | unsigned char bufsize) |
1047 | { | 1026 | { |
1048 | int rc; | 1027 | int rc; |
1049 | CommandList_struct *cp; | 1028 | CommandList_struct *c; |
1050 | char cdb[6]; | 1029 | char cdb[6]; |
1051 | ErrorInfo_struct *ei; | 1030 | ErrorInfo_struct *ei; |
1052 | unsigned long flags; | 1031 | unsigned long flags; |
1053 | 1032 | ||
1054 | spin_lock_irqsave(CCISS_LOCK(c->ctlr), flags); | 1033 | spin_lock_irqsave(&h->lock, flags); |
1055 | cp = scsi_cmd_alloc(c); | 1034 | c = scsi_cmd_alloc(h); |
1056 | spin_unlock_irqrestore(CCISS_LOCK(c->ctlr), flags); | 1035 | spin_unlock_irqrestore(&h->lock, flags); |
1057 | 1036 | ||
1058 | if (cp == NULL) { /* trouble... */ | 1037 | if (c == NULL) { /* trouble... */ |
1059 | printk("cmd_alloc returned NULL!\n"); | 1038 | printk("cmd_alloc returned NULL!\n"); |
1060 | return -1; | 1039 | return -1; |
1061 | } | 1040 | } |
1062 | 1041 | ||
1063 | ei = cp->err_info; | 1042 | ei = c->err_info; |
1064 | 1043 | ||
1065 | cdb[0] = CISS_INQUIRY; | 1044 | cdb[0] = CISS_INQUIRY; |
1066 | cdb[1] = (page != 0); | 1045 | cdb[1] = (page != 0); |
@@ -1068,24 +1047,24 @@ cciss_scsi_do_inquiry(ctlr_info_t *c, unsigned char *scsi3addr, | |||
1068 | cdb[3] = 0; | 1047 | cdb[3] = 0; |
1069 | cdb[4] = bufsize; | 1048 | cdb[4] = bufsize; |
1070 | cdb[5] = 0; | 1049 | cdb[5] = 0; |
1071 | rc = cciss_scsi_do_simple_cmd(c, cp, scsi3addr, cdb, | 1050 | rc = cciss_scsi_do_simple_cmd(h, c, scsi3addr, cdb, |
1072 | 6, buf, bufsize, XFER_READ); | 1051 | 6, buf, bufsize, XFER_READ); |
1073 | 1052 | ||
1074 | if (rc != 0) return rc; /* something went wrong */ | 1053 | if (rc != 0) return rc; /* something went wrong */ |
1075 | 1054 | ||
1076 | if (ei->CommandStatus != 0 && | 1055 | if (ei->CommandStatus != 0 && |
1077 | ei->CommandStatus != CMD_DATA_UNDERRUN) { | 1056 | ei->CommandStatus != CMD_DATA_UNDERRUN) { |
1078 | cciss_scsi_interpret_error(cp); | 1057 | cciss_scsi_interpret_error(h, c); |
1079 | rc = -1; | 1058 | rc = -1; |
1080 | } | 1059 | } |
1081 | spin_lock_irqsave(CCISS_LOCK(c->ctlr), flags); | 1060 | spin_lock_irqsave(&h->lock, flags); |
1082 | scsi_cmd_free(c, cp); | 1061 | scsi_cmd_free(h, c); |
1083 | spin_unlock_irqrestore(CCISS_LOCK(c->ctlr), flags); | 1062 | spin_unlock_irqrestore(&h->lock, flags); |
1084 | return rc; | 1063 | return rc; |
1085 | } | 1064 | } |
1086 | 1065 | ||
1087 | /* Get the device id from inquiry page 0x83 */ | 1066 | /* Get the device id from inquiry page 0x83 */ |
1088 | static int cciss_scsi_get_device_id(ctlr_info_t *c, unsigned char *scsi3addr, | 1067 | static int cciss_scsi_get_device_id(ctlr_info_t *h, unsigned char *scsi3addr, |
1089 | unsigned char *device_id, int buflen) | 1068 | unsigned char *device_id, int buflen) |
1090 | { | 1069 | { |
1091 | int rc; | 1070 | int rc; |
@@ -1096,7 +1075,7 @@ static int cciss_scsi_get_device_id(ctlr_info_t *c, unsigned char *scsi3addr, | |||
1096 | buf = kzalloc(64, GFP_KERNEL); | 1075 | buf = kzalloc(64, GFP_KERNEL); |
1097 | if (!buf) | 1076 | if (!buf) |
1098 | return -1; | 1077 | return -1; |
1099 | rc = cciss_scsi_do_inquiry(c, scsi3addr, 0x83, buf, 64); | 1078 | rc = cciss_scsi_do_inquiry(h, scsi3addr, 0x83, buf, 64); |
1100 | if (rc == 0) | 1079 | if (rc == 0) |
1101 | memcpy(device_id, &buf[8], buflen); | 1080 | memcpy(device_id, &buf[8], buflen); |
1102 | kfree(buf); | 1081 | kfree(buf); |
@@ -1104,20 +1083,20 @@ static int cciss_scsi_get_device_id(ctlr_info_t *c, unsigned char *scsi3addr, | |||
1104 | } | 1083 | } |
1105 | 1084 | ||
1106 | static int | 1085 | static int |
1107 | cciss_scsi_do_report_phys_luns(ctlr_info_t *c, | 1086 | cciss_scsi_do_report_phys_luns(ctlr_info_t *h, |
1108 | ReportLunData_struct *buf, int bufsize) | 1087 | ReportLunData_struct *buf, int bufsize) |
1109 | { | 1088 | { |
1110 | int rc; | 1089 | int rc; |
1111 | CommandList_struct *cp; | 1090 | CommandList_struct *c; |
1112 | unsigned char cdb[12]; | 1091 | unsigned char cdb[12]; |
1113 | unsigned char scsi3addr[8]; | 1092 | unsigned char scsi3addr[8]; |
1114 | ErrorInfo_struct *ei; | 1093 | ErrorInfo_struct *ei; |
1115 | unsigned long flags; | 1094 | unsigned long flags; |
1116 | 1095 | ||
1117 | spin_lock_irqsave(CCISS_LOCK(c->ctlr), flags); | 1096 | spin_lock_irqsave(&h->lock, flags); |
1118 | cp = scsi_cmd_alloc(c); | 1097 | c = scsi_cmd_alloc(h); |
1119 | spin_unlock_irqrestore(CCISS_LOCK(c->ctlr), flags); | 1098 | spin_unlock_irqrestore(&h->lock, flags); |
1120 | if (cp == NULL) { /* trouble... */ | 1099 | if (c == NULL) { /* trouble... */ |
1121 | printk("cmd_alloc returned NULL!\n"); | 1100 | printk("cmd_alloc returned NULL!\n"); |
1122 | return -1; | 1101 | return -1; |
1123 | } | 1102 | } |
@@ -1136,27 +1115,27 @@ cciss_scsi_do_report_phys_luns(ctlr_info_t *c, | |||
1136 | cdb[10] = 0; | 1115 | cdb[10] = 0; |
1137 | cdb[11] = 0; | 1116 | cdb[11] = 0; |
1138 | 1117 | ||
1139 | rc = cciss_scsi_do_simple_cmd(c, cp, scsi3addr, | 1118 | rc = cciss_scsi_do_simple_cmd(h, c, scsi3addr, |
1140 | cdb, 12, | 1119 | cdb, 12, |
1141 | (unsigned char *) buf, | 1120 | (unsigned char *) buf, |
1142 | bufsize, XFER_READ); | 1121 | bufsize, XFER_READ); |
1143 | 1122 | ||
1144 | if (rc != 0) return rc; /* something went wrong */ | 1123 | if (rc != 0) return rc; /* something went wrong */ |
1145 | 1124 | ||
1146 | ei = cp->err_info; | 1125 | ei = c->err_info; |
1147 | if (ei->CommandStatus != 0 && | 1126 | if (ei->CommandStatus != 0 && |
1148 | ei->CommandStatus != CMD_DATA_UNDERRUN) { | 1127 | ei->CommandStatus != CMD_DATA_UNDERRUN) { |
1149 | cciss_scsi_interpret_error(cp); | 1128 | cciss_scsi_interpret_error(h, c); |
1150 | rc = -1; | 1129 | rc = -1; |
1151 | } | 1130 | } |
1152 | spin_lock_irqsave(CCISS_LOCK(c->ctlr), flags); | 1131 | spin_lock_irqsave(&h->lock, flags); |
1153 | scsi_cmd_free(c, cp); | 1132 | scsi_cmd_free(h, c); |
1154 | spin_unlock_irqrestore(CCISS_LOCK(c->ctlr), flags); | 1133 | spin_unlock_irqrestore(&h->lock, flags); |
1155 | return rc; | 1134 | return rc; |
1156 | } | 1135 | } |
1157 | 1136 | ||
1158 | static void | 1137 | static void |
1159 | cciss_update_non_disk_devices(int cntl_num, int hostno) | 1138 | cciss_update_non_disk_devices(ctlr_info_t *h, int hostno) |
1160 | { | 1139 | { |
1161 | /* the idea here is we could get notified from /proc | 1140 | /* the idea here is we could get notified from /proc |
1162 | that some devices have changed, so we do a report | 1141 | that some devices have changed, so we do a report |
@@ -1189,7 +1168,6 @@ cciss_update_non_disk_devices(int cntl_num, int hostno) | |||
1189 | ReportLunData_struct *ld_buff; | 1168 | ReportLunData_struct *ld_buff; |
1190 | unsigned char *inq_buff; | 1169 | unsigned char *inq_buff; |
1191 | unsigned char scsi3addr[8]; | 1170 | unsigned char scsi3addr[8]; |
1192 | ctlr_info_t *c; | ||
1193 | __u32 num_luns=0; | 1171 | __u32 num_luns=0; |
1194 | unsigned char *ch; | 1172 | unsigned char *ch; |
1195 | struct cciss_scsi_dev_t *currentsd, *this_device; | 1173 | struct cciss_scsi_dev_t *currentsd, *this_device; |
@@ -1197,7 +1175,6 @@ cciss_update_non_disk_devices(int cntl_num, int hostno) | |||
1197 | int reportlunsize = sizeof(*ld_buff) + CISS_MAX_PHYS_LUN * 8; | 1175 | int reportlunsize = sizeof(*ld_buff) + CISS_MAX_PHYS_LUN * 8; |
1198 | int i; | 1176 | int i; |
1199 | 1177 | ||
1200 | c = (ctlr_info_t *) hba[cntl_num]; | ||
1201 | ld_buff = kzalloc(reportlunsize, GFP_KERNEL); | 1178 | ld_buff = kzalloc(reportlunsize, GFP_KERNEL); |
1202 | inq_buff = kmalloc(OBDR_TAPE_INQ_SIZE, GFP_KERNEL); | 1179 | inq_buff = kmalloc(OBDR_TAPE_INQ_SIZE, GFP_KERNEL); |
1203 | currentsd = kzalloc(sizeof(*currentsd) * | 1180 | currentsd = kzalloc(sizeof(*currentsd) * |
@@ -1207,7 +1184,7 @@ cciss_update_non_disk_devices(int cntl_num, int hostno) | |||
1207 | goto out; | 1184 | goto out; |
1208 | } | 1185 | } |
1209 | this_device = ¤tsd[CCISS_MAX_SCSI_DEVS_PER_HBA]; | 1186 | this_device = ¤tsd[CCISS_MAX_SCSI_DEVS_PER_HBA]; |
1210 | if (cciss_scsi_do_report_phys_luns(c, ld_buff, reportlunsize) == 0) { | 1187 | if (cciss_scsi_do_report_phys_luns(h, ld_buff, reportlunsize) == 0) { |
1211 | ch = &ld_buff->LUNListLength[0]; | 1188 | ch = &ld_buff->LUNListLength[0]; |
1212 | num_luns = ((ch[0]<<24) | (ch[1]<<16) | (ch[2]<<8) | ch[3]) / 8; | 1189 | num_luns = ((ch[0]<<24) | (ch[1]<<16) | (ch[2]<<8) | ch[3]) / 8; |
1213 | if (num_luns > CISS_MAX_PHYS_LUN) { | 1190 | if (num_luns > CISS_MAX_PHYS_LUN) { |
@@ -1231,7 +1208,7 @@ cciss_update_non_disk_devices(int cntl_num, int hostno) | |||
1231 | memset(inq_buff, 0, OBDR_TAPE_INQ_SIZE); | 1208 | memset(inq_buff, 0, OBDR_TAPE_INQ_SIZE); |
1232 | memcpy(&scsi3addr[0], &ld_buff->LUN[i][0], 8); | 1209 | memcpy(&scsi3addr[0], &ld_buff->LUN[i][0], 8); |
1233 | 1210 | ||
1234 | if (cciss_scsi_do_inquiry(hba[cntl_num], scsi3addr, 0, inq_buff, | 1211 | if (cciss_scsi_do_inquiry(h, scsi3addr, 0, inq_buff, |
1235 | (unsigned char) OBDR_TAPE_INQ_SIZE) != 0) | 1212 | (unsigned char) OBDR_TAPE_INQ_SIZE) != 0) |
1236 | /* Inquiry failed (msg printed already) */ | 1213 | /* Inquiry failed (msg printed already) */ |
1237 | continue; /* so we will skip this device. */ | 1214 | continue; /* so we will skip this device. */ |
@@ -1249,7 +1226,7 @@ cciss_update_non_disk_devices(int cntl_num, int hostno) | |||
1249 | sizeof(this_device->revision)); | 1226 | sizeof(this_device->revision)); |
1250 | memset(this_device->device_id, 0, | 1227 | memset(this_device->device_id, 0, |
1251 | sizeof(this_device->device_id)); | 1228 | sizeof(this_device->device_id)); |
1252 | cciss_scsi_get_device_id(hba[cntl_num], scsi3addr, | 1229 | cciss_scsi_get_device_id(h, scsi3addr, |
1253 | this_device->device_id, sizeof(this_device->device_id)); | 1230 | this_device->device_id, sizeof(this_device->device_id)); |
1254 | 1231 | ||
1255 | switch (this_device->devtype) | 1232 | switch (this_device->devtype) |
@@ -1276,7 +1253,7 @@ cciss_update_non_disk_devices(int cntl_num, int hostno) | |||
1276 | case 0x08: /* medium changer */ | 1253 | case 0x08: /* medium changer */ |
1277 | if (ncurrent >= CCISS_MAX_SCSI_DEVS_PER_HBA) { | 1254 | if (ncurrent >= CCISS_MAX_SCSI_DEVS_PER_HBA) { |
1278 | printk(KERN_INFO "cciss%d: %s ignored, " | 1255 | printk(KERN_INFO "cciss%d: %s ignored, " |
1279 | "too many devices.\n", cntl_num, | 1256 | "too many devices.\n", h->ctlr, |
1280 | scsi_device_type(this_device->devtype)); | 1257 | scsi_device_type(this_device->devtype)); |
1281 | break; | 1258 | break; |
1282 | } | 1259 | } |
@@ -1288,7 +1265,7 @@ cciss_update_non_disk_devices(int cntl_num, int hostno) | |||
1288 | } | 1265 | } |
1289 | } | 1266 | } |
1290 | 1267 | ||
1291 | adjust_cciss_scsi_table(cntl_num, hostno, currentsd, ncurrent); | 1268 | adjust_cciss_scsi_table(h, hostno, currentsd, ncurrent); |
1292 | out: | 1269 | out: |
1293 | kfree(inq_buff); | 1270 | kfree(inq_buff); |
1294 | kfree(ld_buff); | 1271 | kfree(ld_buff); |
@@ -1307,12 +1284,12 @@ is_keyword(char *ptr, int len, char *verb) // Thanks to ncr53c8xx.c | |||
1307 | } | 1284 | } |
1308 | 1285 | ||
1309 | static int | 1286 | static int |
1310 | cciss_scsi_user_command(int ctlr, int hostno, char *buffer, int length) | 1287 | cciss_scsi_user_command(ctlr_info_t *h, int hostno, char *buffer, int length) |
1311 | { | 1288 | { |
1312 | int arg_len; | 1289 | int arg_len; |
1313 | 1290 | ||
1314 | if ((arg_len = is_keyword(buffer, length, "rescan")) != 0) | 1291 | if ((arg_len = is_keyword(buffer, length, "rescan")) != 0) |
1315 | cciss_update_non_disk_devices(ctlr, hostno); | 1292 | cciss_update_non_disk_devices(h, hostno); |
1316 | else | 1293 | else |
1317 | return -EINVAL; | 1294 | return -EINVAL; |
1318 | return length; | 1295 | return length; |
@@ -1329,20 +1306,16 @@ cciss_scsi_proc_info(struct Scsi_Host *sh, | |||
1329 | { | 1306 | { |
1330 | 1307 | ||
1331 | int buflen, datalen; | 1308 | int buflen, datalen; |
1332 | ctlr_info_t *ci; | 1309 | ctlr_info_t *h; |
1333 | int i; | 1310 | int i; |
1334 | int cntl_num; | ||
1335 | |||
1336 | 1311 | ||
1337 | ci = (ctlr_info_t *) sh->hostdata[0]; | 1312 | h = (ctlr_info_t *) sh->hostdata[0]; |
1338 | if (ci == NULL) /* This really shouldn't ever happen. */ | 1313 | if (h == NULL) /* This really shouldn't ever happen. */ |
1339 | return -EINVAL; | 1314 | return -EINVAL; |
1340 | 1315 | ||
1341 | cntl_num = ci->ctlr; /* Get our index into the hba[] array */ | ||
1342 | |||
1343 | if (func == 0) { /* User is reading from /proc/scsi/ciss*?/?* */ | 1316 | if (func == 0) { /* User is reading from /proc/scsi/ciss*?/?* */ |
1344 | buflen = sprintf(buffer, "cciss%d: SCSI host: %d\n", | 1317 | buflen = sprintf(buffer, "cciss%d: SCSI host: %d\n", |
1345 | cntl_num, sh->host_no); | 1318 | h->ctlr, sh->host_no); |
1346 | 1319 | ||
1347 | /* this information is needed by apps to know which cciss | 1320 | /* this information is needed by apps to know which cciss |
1348 | device corresponds to which scsi host number without | 1321 | device corresponds to which scsi host number without |
@@ -1352,8 +1325,9 @@ cciss_scsi_proc_info(struct Scsi_Host *sh, | |||
1352 | this info is for an app to be able to use to know how to | 1325 | this info is for an app to be able to use to know how to |
1353 | get them back in sync. */ | 1326 | get them back in sync. */ |
1354 | 1327 | ||
1355 | for (i=0;i<ccissscsi[cntl_num].ndevices;i++) { | 1328 | for (i = 0; i < ccissscsi[h->ctlr].ndevices; i++) { |
1356 | struct cciss_scsi_dev_t *sd = &ccissscsi[cntl_num].dev[i]; | 1329 | struct cciss_scsi_dev_t *sd = |
1330 | &ccissscsi[h->ctlr].dev[i]; | ||
1357 | buflen += sprintf(&buffer[buflen], "c%db%dt%dl%d %02d " | 1331 | buflen += sprintf(&buffer[buflen], "c%db%dt%dl%d %02d " |
1358 | "0x%02x%02x%02x%02x%02x%02x%02x%02x\n", | 1332 | "0x%02x%02x%02x%02x%02x%02x%02x%02x\n", |
1359 | sh->host_no, sd->bus, sd->target, sd->lun, | 1333 | sh->host_no, sd->bus, sd->target, sd->lun, |
@@ -1371,15 +1345,15 @@ cciss_scsi_proc_info(struct Scsi_Host *sh, | |||
1371 | *start = buffer + offset; | 1345 | *start = buffer + offset; |
1372 | return(datalen); | 1346 | return(datalen); |
1373 | } else /* User is writing to /proc/scsi/cciss*?/?* ... */ | 1347 | } else /* User is writing to /proc/scsi/cciss*?/?* ... */ |
1374 | return cciss_scsi_user_command(cntl_num, sh->host_no, | 1348 | return cciss_scsi_user_command(h, sh->host_no, |
1375 | buffer, length); | 1349 | buffer, length); |
1376 | } | 1350 | } |
1377 | 1351 | ||
1378 | /* cciss_scatter_gather takes a struct scsi_cmnd, (cmd), and does the pci | 1352 | /* cciss_scatter_gather takes a struct scsi_cmnd, (cmd), and does the pci |
1379 | dma mapping and fills in the scatter gather entries of the | 1353 | dma mapping and fills in the scatter gather entries of the |
1380 | cciss command, cp. */ | 1354 | cciss command, c. */ |
1381 | 1355 | ||
1382 | static void cciss_scatter_gather(ctlr_info_t *h, CommandList_struct *cp, | 1356 | static void cciss_scatter_gather(ctlr_info_t *h, CommandList_struct *c, |
1383 | struct scsi_cmnd *cmd) | 1357 | struct scsi_cmnd *cmd) |
1384 | { | 1358 | { |
1385 | unsigned int len; | 1359 | unsigned int len; |
@@ -1393,7 +1367,7 @@ static void cciss_scatter_gather(ctlr_info_t *h, CommandList_struct *cp, | |||
1393 | 1367 | ||
1394 | chained = 0; | 1368 | chained = 0; |
1395 | sg_index = 0; | 1369 | sg_index = 0; |
1396 | curr_sg = cp->SG; | 1370 | curr_sg = c->SG; |
1397 | request_nsgs = scsi_dma_map(cmd); | 1371 | request_nsgs = scsi_dma_map(cmd); |
1398 | if (request_nsgs) { | 1372 | if (request_nsgs) { |
1399 | scsi_for_each_sg(cmd, sg, request_nsgs, i) { | 1373 | scsi_for_each_sg(cmd, sg, request_nsgs, i) { |
@@ -1401,7 +1375,7 @@ static void cciss_scatter_gather(ctlr_info_t *h, CommandList_struct *cp, | |||
1401 | !chained && request_nsgs - i > 1) { | 1375 | !chained && request_nsgs - i > 1) { |
1402 | chained = 1; | 1376 | chained = 1; |
1403 | sg_index = 0; | 1377 | sg_index = 0; |
1404 | curr_sg = sa->cmd_sg_list[cp->cmdindex]; | 1378 | curr_sg = sa->cmd_sg_list[c->cmdindex]; |
1405 | } | 1379 | } |
1406 | addr64 = (__u64) sg_dma_address(sg); | 1380 | addr64 = (__u64) sg_dma_address(sg); |
1407 | len = sg_dma_len(sg); | 1381 | len = sg_dma_len(sg); |
@@ -1414,19 +1388,19 @@ static void cciss_scatter_gather(ctlr_info_t *h, CommandList_struct *cp, | |||
1414 | ++sg_index; | 1388 | ++sg_index; |
1415 | } | 1389 | } |
1416 | if (chained) | 1390 | if (chained) |
1417 | cciss_map_sg_chain_block(h, cp, | 1391 | cciss_map_sg_chain_block(h, c, |
1418 | sa->cmd_sg_list[cp->cmdindex], | 1392 | sa->cmd_sg_list[c->cmdindex], |
1419 | (request_nsgs - (h->max_cmd_sgentries - 1)) * | 1393 | (request_nsgs - (h->max_cmd_sgentries - 1)) * |
1420 | sizeof(SGDescriptor_struct)); | 1394 | sizeof(SGDescriptor_struct)); |
1421 | } | 1395 | } |
1422 | /* track how many SG entries we are using */ | 1396 | /* track how many SG entries we are using */ |
1423 | if (request_nsgs > h->maxSG) | 1397 | if (request_nsgs > h->maxSG) |
1424 | h->maxSG = request_nsgs; | 1398 | h->maxSG = request_nsgs; |
1425 | cp->Header.SGTotal = (__u8) request_nsgs + chained; | 1399 | c->Header.SGTotal = (__u8) request_nsgs + chained; |
1426 | if (request_nsgs > h->max_cmd_sgentries) | 1400 | if (request_nsgs > h->max_cmd_sgentries) |
1427 | cp->Header.SGList = h->max_cmd_sgentries; | 1401 | c->Header.SGList = h->max_cmd_sgentries; |
1428 | else | 1402 | else |
1429 | cp->Header.SGList = cp->Header.SGTotal; | 1403 | c->Header.SGList = c->Header.SGTotal; |
1430 | return; | 1404 | return; |
1431 | } | 1405 | } |
1432 | 1406 | ||
@@ -1434,18 +1408,17 @@ static void cciss_scatter_gather(ctlr_info_t *h, CommandList_struct *cp, | |||
1434 | static int | 1408 | static int |
1435 | cciss_scsi_queue_command (struct scsi_cmnd *cmd, void (* done)(struct scsi_cmnd *)) | 1409 | cciss_scsi_queue_command (struct scsi_cmnd *cmd, void (* done)(struct scsi_cmnd *)) |
1436 | { | 1410 | { |
1437 | ctlr_info_t *c; | 1411 | ctlr_info_t *h; |
1438 | int ctlr, rc; | 1412 | int rc; |
1439 | unsigned char scsi3addr[8]; | 1413 | unsigned char scsi3addr[8]; |
1440 | CommandList_struct *cp; | 1414 | CommandList_struct *c; |
1441 | unsigned long flags; | 1415 | unsigned long flags; |
1442 | 1416 | ||
1443 | // Get the ptr to our adapter structure (hba[i]) out of cmd->host. | 1417 | // Get the ptr to our adapter structure (hba[i]) out of cmd->host. |
1444 | // We violate cmd->host privacy here. (Is there another way?) | 1418 | // We violate cmd->host privacy here. (Is there another way?) |
1445 | c = (ctlr_info_t *) cmd->device->host->hostdata[0]; | 1419 | h = (ctlr_info_t *) cmd->device->host->hostdata[0]; |
1446 | ctlr = c->ctlr; | ||
1447 | 1420 | ||
1448 | rc = lookup_scsi3addr(ctlr, cmd->device->channel, cmd->device->id, | 1421 | rc = lookup_scsi3addr(h, cmd->device->channel, cmd->device->id, |
1449 | cmd->device->lun, scsi3addr); | 1422 | cmd->device->lun, scsi3addr); |
1450 | if (rc != 0) { | 1423 | if (rc != 0) { |
1451 | /* the scsi nexus does not match any that we presented... */ | 1424 | /* the scsi nexus does not match any that we presented... */ |
@@ -1457,19 +1430,14 @@ cciss_scsi_queue_command (struct scsi_cmnd *cmd, void (* done)(struct scsi_cmnd | |||
1457 | return 0; | 1430 | return 0; |
1458 | } | 1431 | } |
1459 | 1432 | ||
1460 | /* printk("cciss_queue_command, p=%p, cmd=0x%02x, c%db%dt%dl%d\n", | ||
1461 | cmd, cmd->cmnd[0], ctlr, cmd->channel, cmd->target, cmd->lun);*/ | ||
1462 | // printk("q:%p:c%db%dt%dl%d ", cmd, ctlr, cmd->channel, | ||
1463 | // cmd->target, cmd->lun); | ||
1464 | |||
1465 | /* Ok, we have a reasonable scsi nexus, so send the cmd down, and | 1433 | /* Ok, we have a reasonable scsi nexus, so send the cmd down, and |
1466 | see what the device thinks of it. */ | 1434 | see what the device thinks of it. */ |
1467 | 1435 | ||
1468 | spin_lock_irqsave(CCISS_LOCK(ctlr), flags); | 1436 | spin_lock_irqsave(&h->lock, flags); |
1469 | cp = scsi_cmd_alloc(c); | 1437 | c = scsi_cmd_alloc(h); |
1470 | spin_unlock_irqrestore(CCISS_LOCK(ctlr), flags); | 1438 | spin_unlock_irqrestore(&h->lock, flags); |
1471 | if (cp == NULL) { /* trouble... */ | 1439 | if (c == NULL) { /* trouble... */ |
1472 | printk("scsi_cmd_alloc returned NULL!\n"); | 1440 | dev_warn(&h->pdev->dev, "scsi_cmd_alloc returned NULL!\n"); |
1473 | /* FIXME: next 3 lines are -> BAD! <- */ | 1441 | /* FIXME: next 3 lines are -> BAD! <- */ |
1474 | cmd->result = DID_NO_CONNECT << 16; | 1442 | cmd->result = DID_NO_CONNECT << 16; |
1475 | done(cmd); | 1443 | done(cmd); |
@@ -1480,35 +1448,41 @@ cciss_scsi_queue_command (struct scsi_cmnd *cmd, void (* done)(struct scsi_cmnd | |||
1480 | 1448 | ||
1481 | cmd->scsi_done = done; // save this for use by completion code | 1449 | cmd->scsi_done = done; // save this for use by completion code |
1482 | 1450 | ||
1483 | // save cp in case we have to abort it | 1451 | /* save c in case we have to abort it */ |
1484 | cmd->host_scribble = (unsigned char *) cp; | 1452 | cmd->host_scribble = (unsigned char *) c; |
1485 | 1453 | ||
1486 | cp->cmd_type = CMD_SCSI; | 1454 | c->cmd_type = CMD_SCSI; |
1487 | cp->scsi_cmd = cmd; | 1455 | c->scsi_cmd = cmd; |
1488 | cp->Header.ReplyQueue = 0; // unused in simple mode | 1456 | c->Header.ReplyQueue = 0; /* unused in simple mode */ |
1489 | memcpy(&cp->Header.LUN.LunAddrBytes[0], &scsi3addr[0], 8); | 1457 | memcpy(&c->Header.LUN.LunAddrBytes[0], &scsi3addr[0], 8); |
1490 | cp->Header.Tag.lower = cp->busaddr; // Use k. address of cmd as tag | 1458 | c->Header.Tag.lower = c->busaddr; /* Use k. address of cmd as tag */ |
1491 | 1459 | ||
1492 | // Fill in the request block... | 1460 | // Fill in the request block... |
1493 | 1461 | ||
1494 | cp->Request.Timeout = 0; | 1462 | c->Request.Timeout = 0; |
1495 | memset(cp->Request.CDB, 0, sizeof(cp->Request.CDB)); | 1463 | memset(c->Request.CDB, 0, sizeof(c->Request.CDB)); |
1496 | BUG_ON(cmd->cmd_len > sizeof(cp->Request.CDB)); | 1464 | BUG_ON(cmd->cmd_len > sizeof(c->Request.CDB)); |
1497 | cp->Request.CDBLen = cmd->cmd_len; | 1465 | c->Request.CDBLen = cmd->cmd_len; |
1498 | memcpy(cp->Request.CDB, cmd->cmnd, cmd->cmd_len); | 1466 | memcpy(c->Request.CDB, cmd->cmnd, cmd->cmd_len); |
1499 | cp->Request.Type.Type = TYPE_CMD; | 1467 | c->Request.Type.Type = TYPE_CMD; |
1500 | cp->Request.Type.Attribute = ATTR_SIMPLE; | 1468 | c->Request.Type.Attribute = ATTR_SIMPLE; |
1501 | switch(cmd->sc_data_direction) | 1469 | switch(cmd->sc_data_direction) |
1502 | { | 1470 | { |
1503 | case DMA_TO_DEVICE: cp->Request.Type.Direction = XFER_WRITE; break; | 1471 | case DMA_TO_DEVICE: |
1504 | case DMA_FROM_DEVICE: cp->Request.Type.Direction = XFER_READ; break; | 1472 | c->Request.Type.Direction = XFER_WRITE; |
1505 | case DMA_NONE: cp->Request.Type.Direction = XFER_NONE; break; | 1473 | break; |
1474 | case DMA_FROM_DEVICE: | ||
1475 | c->Request.Type.Direction = XFER_READ; | ||
1476 | break; | ||
1477 | case DMA_NONE: | ||
1478 | c->Request.Type.Direction = XFER_NONE; | ||
1479 | break; | ||
1506 | case DMA_BIDIRECTIONAL: | 1480 | case DMA_BIDIRECTIONAL: |
1507 | // This can happen if a buggy application does a scsi passthru | 1481 | // This can happen if a buggy application does a scsi passthru |
1508 | // and sets both inlen and outlen to non-zero. ( see | 1482 | // and sets both inlen and outlen to non-zero. ( see |
1509 | // ../scsi/scsi_ioctl.c:scsi_ioctl_send_command() ) | 1483 | // ../scsi/scsi_ioctl.c:scsi_ioctl_send_command() ) |
1510 | 1484 | ||
1511 | cp->Request.Type.Direction = XFER_RSVD; | 1485 | c->Request.Type.Direction = XFER_RSVD; |
1512 | // This is technically wrong, and cciss controllers should | 1486 | // This is technically wrong, and cciss controllers should |
1513 | // reject it with CMD_INVALID, which is the most correct | 1487 | // reject it with CMD_INVALID, which is the most correct |
1514 | // response, but non-fibre backends appear to let it | 1488 | // response, but non-fibre backends appear to let it |
@@ -1519,27 +1493,18 @@ cciss_scsi_queue_command (struct scsi_cmnd *cmd, void (* done)(struct scsi_cmnd | |||
1519 | break; | 1493 | break; |
1520 | 1494 | ||
1521 | default: | 1495 | default: |
1522 | printk("cciss: unknown data direction: %d\n", | 1496 | dev_warn(&h->pdev->dev, "unknown data direction: %d\n", |
1523 | cmd->sc_data_direction); | 1497 | cmd->sc_data_direction); |
1524 | BUG(); | 1498 | BUG(); |
1525 | break; | 1499 | break; |
1526 | } | 1500 | } |
1527 | cciss_scatter_gather(c, cp, cmd); | 1501 | cciss_scatter_gather(h, c, cmd); |
1528 | 1502 | enqueue_cmd_and_start_io(h, c); | |
1529 | /* Put the request on the tail of the request queue */ | ||
1530 | |||
1531 | spin_lock_irqsave(CCISS_LOCK(ctlr), flags); | ||
1532 | addQ(&c->reqQ, cp); | ||
1533 | c->Qdepth++; | ||
1534 | start_io(c); | ||
1535 | spin_unlock_irqrestore(CCISS_LOCK(ctlr), flags); | ||
1536 | |||
1537 | /* the cmd'll come back via intr handler in complete_scsi_command() */ | 1503 | /* the cmd'll come back via intr handler in complete_scsi_command() */ |
1538 | return 0; | 1504 | return 0; |
1539 | } | 1505 | } |
1540 | 1506 | ||
1541 | static void | 1507 | static void cciss_unregister_scsi(ctlr_info_t *h) |
1542 | cciss_unregister_scsi(int ctlr) | ||
1543 | { | 1508 | { |
1544 | struct cciss_scsi_adapter_data_t *sa; | 1509 | struct cciss_scsi_adapter_data_t *sa; |
1545 | struct cciss_scsi_cmd_stack_t *stk; | 1510 | struct cciss_scsi_cmd_stack_t *stk; |
@@ -1547,59 +1512,58 @@ cciss_unregister_scsi(int ctlr) | |||
1547 | 1512 | ||
1548 | /* we are being forcibly unloaded, and may not refuse. */ | 1513 | /* we are being forcibly unloaded, and may not refuse. */ |
1549 | 1514 | ||
1550 | spin_lock_irqsave(CCISS_LOCK(ctlr), flags); | 1515 | spin_lock_irqsave(&h->lock, flags); |
1551 | sa = hba[ctlr]->scsi_ctlr; | 1516 | sa = h->scsi_ctlr; |
1552 | stk = &sa->cmd_stack; | 1517 | stk = &sa->cmd_stack; |
1553 | 1518 | ||
1554 | /* if we weren't ever actually registered, don't unregister */ | 1519 | /* if we weren't ever actually registered, don't unregister */ |
1555 | if (sa->registered) { | 1520 | if (sa->registered) { |
1556 | spin_unlock_irqrestore(CCISS_LOCK(ctlr), flags); | 1521 | spin_unlock_irqrestore(&h->lock, flags); |
1557 | scsi_remove_host(sa->scsi_host); | 1522 | scsi_remove_host(sa->scsi_host); |
1558 | scsi_host_put(sa->scsi_host); | 1523 | scsi_host_put(sa->scsi_host); |
1559 | spin_lock_irqsave(CCISS_LOCK(ctlr), flags); | 1524 | spin_lock_irqsave(&h->lock, flags); |
1560 | } | 1525 | } |
1561 | 1526 | ||
1562 | /* set scsi_host to NULL so our detect routine will | 1527 | /* set scsi_host to NULL so our detect routine will |
1563 | find us on register */ | 1528 | find us on register */ |
1564 | sa->scsi_host = NULL; | 1529 | sa->scsi_host = NULL; |
1565 | spin_unlock_irqrestore(CCISS_LOCK(ctlr), flags); | 1530 | spin_unlock_irqrestore(&h->lock, flags); |
1566 | scsi_cmd_stack_free(ctlr); | 1531 | scsi_cmd_stack_free(h); |
1567 | kfree(sa); | 1532 | kfree(sa); |
1568 | } | 1533 | } |
1569 | 1534 | ||
1570 | static int | 1535 | static int cciss_engage_scsi(ctlr_info_t *h) |
1571 | cciss_engage_scsi(int ctlr) | ||
1572 | { | 1536 | { |
1573 | struct cciss_scsi_adapter_data_t *sa; | 1537 | struct cciss_scsi_adapter_data_t *sa; |
1574 | struct cciss_scsi_cmd_stack_t *stk; | 1538 | struct cciss_scsi_cmd_stack_t *stk; |
1575 | unsigned long flags; | 1539 | unsigned long flags; |
1576 | 1540 | ||
1577 | spin_lock_irqsave(CCISS_LOCK(ctlr), flags); | 1541 | spin_lock_irqsave(&h->lock, flags); |
1578 | sa = hba[ctlr]->scsi_ctlr; | 1542 | sa = h->scsi_ctlr; |
1579 | stk = &sa->cmd_stack; | 1543 | stk = &sa->cmd_stack; |
1580 | 1544 | ||
1581 | if (sa->registered) { | 1545 | if (sa->registered) { |
1582 | printk("cciss%d: SCSI subsystem already engaged.\n", ctlr); | 1546 | dev_info(&h->pdev->dev, "SCSI subsystem already engaged.\n"); |
1583 | spin_unlock_irqrestore(CCISS_LOCK(ctlr), flags); | 1547 | spin_unlock_irqrestore(&h->lock, flags); |
1584 | return -ENXIO; | 1548 | return -ENXIO; |
1585 | } | 1549 | } |
1586 | sa->registered = 1; | 1550 | sa->registered = 1; |
1587 | spin_unlock_irqrestore(CCISS_LOCK(ctlr), flags); | 1551 | spin_unlock_irqrestore(&h->lock, flags); |
1588 | cciss_update_non_disk_devices(ctlr, -1); | 1552 | cciss_update_non_disk_devices(h, -1); |
1589 | cciss_scsi_detect(ctlr); | 1553 | cciss_scsi_detect(h); |
1590 | return 0; | 1554 | return 0; |
1591 | } | 1555 | } |
1592 | 1556 | ||
1593 | static void | 1557 | static void |
1594 | cciss_seq_tape_report(struct seq_file *seq, int ctlr) | 1558 | cciss_seq_tape_report(struct seq_file *seq, ctlr_info_t *h) |
1595 | { | 1559 | { |
1596 | unsigned long flags; | 1560 | unsigned long flags; |
1597 | 1561 | ||
1598 | CPQ_TAPE_LOCK(ctlr, flags); | 1562 | CPQ_TAPE_LOCK(h, flags); |
1599 | seq_printf(seq, | 1563 | seq_printf(seq, |
1600 | "Sequential access devices: %d\n\n", | 1564 | "Sequential access devices: %d\n\n", |
1601 | ccissscsi[ctlr].ndevices); | 1565 | ccissscsi[h->ctlr].ndevices); |
1602 | CPQ_TAPE_UNLOCK(ctlr, flags); | 1566 | CPQ_TAPE_UNLOCK(h, flags); |
1603 | } | 1567 | } |
1604 | 1568 | ||
1605 | static int wait_for_device_to_become_ready(ctlr_info_t *h, | 1569 | static int wait_for_device_to_become_ready(ctlr_info_t *h, |
@@ -1610,10 +1574,10 @@ static int wait_for_device_to_become_ready(ctlr_info_t *h, | |||
1610 | int waittime = HZ; | 1574 | int waittime = HZ; |
1611 | CommandList_struct *c; | 1575 | CommandList_struct *c; |
1612 | 1576 | ||
1613 | c = cmd_alloc(h, 1); | 1577 | c = cmd_alloc(h); |
1614 | if (!c) { | 1578 | if (!c) { |
1615 | printk(KERN_WARNING "cciss%d: out of memory in " | 1579 | dev_warn(&h->pdev->dev, "out of memory in " |
1616 | "wait_for_device_to_become_ready.\n", h->ctlr); | 1580 | "wait_for_device_to_become_ready.\n"); |
1617 | return IO_ERROR; | 1581 | return IO_ERROR; |
1618 | } | 1582 | } |
1619 | 1583 | ||
@@ -1631,7 +1595,7 @@ static int wait_for_device_to_become_ready(ctlr_info_t *h, | |||
1631 | waittime = waittime * 2; | 1595 | waittime = waittime * 2; |
1632 | 1596 | ||
1633 | /* Send the Test Unit Ready */ | 1597 | /* Send the Test Unit Ready */ |
1634 | rc = fill_cmd(c, TEST_UNIT_READY, h->ctlr, NULL, 0, 0, | 1598 | rc = fill_cmd(h, c, TEST_UNIT_READY, NULL, 0, 0, |
1635 | lunaddr, TYPE_CMD); | 1599 | lunaddr, TYPE_CMD); |
1636 | if (rc == 0) | 1600 | if (rc == 0) |
1637 | rc = sendcmd_withirq_core(h, c, 0); | 1601 | rc = sendcmd_withirq_core(h, c, 0); |
@@ -1657,18 +1621,18 @@ static int wait_for_device_to_become_ready(ctlr_info_t *h, | |||
1657 | } | 1621 | } |
1658 | } | 1622 | } |
1659 | retry_tur: | 1623 | retry_tur: |
1660 | printk(KERN_WARNING "cciss%d: Waiting %d secs " | 1624 | dev_warn(&h->pdev->dev, "Waiting %d secs " |
1661 | "for device to become ready.\n", | 1625 | "for device to become ready.\n", |
1662 | h->ctlr, waittime / HZ); | 1626 | waittime / HZ); |
1663 | rc = 1; /* device not ready. */ | 1627 | rc = 1; /* device not ready. */ |
1664 | } | 1628 | } |
1665 | 1629 | ||
1666 | if (rc) | 1630 | if (rc) |
1667 | printk("cciss%d: giving up on device.\n", h->ctlr); | 1631 | dev_warn(&h->pdev->dev, "giving up on device.\n"); |
1668 | else | 1632 | else |
1669 | printk(KERN_WARNING "cciss%d: device is ready.\n", h->ctlr); | 1633 | dev_warn(&h->pdev->dev, "device is ready.\n"); |
1670 | 1634 | ||
1671 | cmd_free(h, c, 1); | 1635 | cmd_free(h, c); |
1672 | return rc; | 1636 | return rc; |
1673 | } | 1637 | } |
1674 | 1638 | ||
@@ -1688,26 +1652,24 @@ static int cciss_eh_device_reset_handler(struct scsi_cmnd *scsicmd) | |||
1688 | int rc; | 1652 | int rc; |
1689 | CommandList_struct *cmd_in_trouble; | 1653 | CommandList_struct *cmd_in_trouble; |
1690 | unsigned char lunaddr[8]; | 1654 | unsigned char lunaddr[8]; |
1691 | ctlr_info_t *c; | 1655 | ctlr_info_t *h; |
1692 | int ctlr; | ||
1693 | 1656 | ||
1694 | /* find the controller to which the command to be aborted was sent */ | 1657 | /* find the controller to which the command to be aborted was sent */ |
1695 | c = (ctlr_info_t *) scsicmd->device->host->hostdata[0]; | 1658 | h = (ctlr_info_t *) scsicmd->device->host->hostdata[0]; |
1696 | if (c == NULL) /* paranoia */ | 1659 | if (h == NULL) /* paranoia */ |
1697 | return FAILED; | 1660 | return FAILED; |
1698 | ctlr = c->ctlr; | 1661 | dev_warn(&h->pdev->dev, "resetting tape drive or medium changer.\n"); |
1699 | printk(KERN_WARNING "cciss%d: resetting tape drive or medium changer.\n", ctlr); | ||
1700 | /* find the command that's giving us trouble */ | 1662 | /* find the command that's giving us trouble */ |
1701 | cmd_in_trouble = (CommandList_struct *) scsicmd->host_scribble; | 1663 | cmd_in_trouble = (CommandList_struct *) scsicmd->host_scribble; |
1702 | if (cmd_in_trouble == NULL) /* paranoia */ | 1664 | if (cmd_in_trouble == NULL) /* paranoia */ |
1703 | return FAILED; | 1665 | return FAILED; |
1704 | memcpy(lunaddr, &cmd_in_trouble->Header.LUN.LunAddrBytes[0], 8); | 1666 | memcpy(lunaddr, &cmd_in_trouble->Header.LUN.LunAddrBytes[0], 8); |
1705 | /* send a reset to the SCSI LUN which the command was sent to */ | 1667 | /* send a reset to the SCSI LUN which the command was sent to */ |
1706 | rc = sendcmd_withirq(CCISS_RESET_MSG, ctlr, NULL, 0, 0, lunaddr, | 1668 | rc = sendcmd_withirq(h, CCISS_RESET_MSG, NULL, 0, 0, lunaddr, |
1707 | TYPE_MSG); | 1669 | TYPE_MSG); |
1708 | if (rc == 0 && wait_for_device_to_become_ready(c, lunaddr) == 0) | 1670 | if (rc == 0 && wait_for_device_to_become_ready(h, lunaddr) == 0) |
1709 | return SUCCESS; | 1671 | return SUCCESS; |
1710 | printk(KERN_WARNING "cciss%d: resetting device failed.\n", ctlr); | 1672 | dev_warn(&h->pdev->dev, "resetting device failed.\n"); |
1711 | return FAILED; | 1673 | return FAILED; |
1712 | } | 1674 | } |
1713 | 1675 | ||
@@ -1716,22 +1678,20 @@ static int cciss_eh_abort_handler(struct scsi_cmnd *scsicmd) | |||
1716 | int rc; | 1678 | int rc; |
1717 | CommandList_struct *cmd_to_abort; | 1679 | CommandList_struct *cmd_to_abort; |
1718 | unsigned char lunaddr[8]; | 1680 | unsigned char lunaddr[8]; |
1719 | ctlr_info_t *c; | 1681 | ctlr_info_t *h; |
1720 | int ctlr; | ||
1721 | 1682 | ||
1722 | /* find the controller to which the command to be aborted was sent */ | 1683 | /* find the controller to which the command to be aborted was sent */ |
1723 | c = (ctlr_info_t *) scsicmd->device->host->hostdata[0]; | 1684 | h = (ctlr_info_t *) scsicmd->device->host->hostdata[0]; |
1724 | if (c == NULL) /* paranoia */ | 1685 | if (h == NULL) /* paranoia */ |
1725 | return FAILED; | 1686 | return FAILED; |
1726 | ctlr = c->ctlr; | 1687 | dev_warn(&h->pdev->dev, "aborting tardy SCSI cmd\n"); |
1727 | printk(KERN_WARNING "cciss%d: aborting tardy SCSI cmd\n", ctlr); | ||
1728 | 1688 | ||
1729 | /* find the command to be aborted */ | 1689 | /* find the command to be aborted */ |
1730 | cmd_to_abort = (CommandList_struct *) scsicmd->host_scribble; | 1690 | cmd_to_abort = (CommandList_struct *) scsicmd->host_scribble; |
1731 | if (cmd_to_abort == NULL) /* paranoia */ | 1691 | if (cmd_to_abort == NULL) /* paranoia */ |
1732 | return FAILED; | 1692 | return FAILED; |
1733 | memcpy(lunaddr, &cmd_to_abort->Header.LUN.LunAddrBytes[0], 8); | 1693 | memcpy(lunaddr, &cmd_to_abort->Header.LUN.LunAddrBytes[0], 8); |
1734 | rc = sendcmd_withirq(CCISS_ABORT_MSG, ctlr, &cmd_to_abort->Header.Tag, | 1694 | rc = sendcmd_withirq(h, CCISS_ABORT_MSG, &cmd_to_abort->Header.Tag, |
1735 | 0, 0, lunaddr, TYPE_MSG); | 1695 | 0, 0, lunaddr, TYPE_MSG); |
1736 | if (rc == 0) | 1696 | if (rc == 0) |
1737 | return SUCCESS; | 1697 | return SUCCESS; |
diff --git a/drivers/block/cpqarray.c b/drivers/block/cpqarray.c index abb4ec6690fc..d53b0291c44b 100644 --- a/drivers/block/cpqarray.c +++ b/drivers/block/cpqarray.c | |||
@@ -35,6 +35,7 @@ | |||
35 | #include <linux/seq_file.h> | 35 | #include <linux/seq_file.h> |
36 | #include <linux/init.h> | 36 | #include <linux/init.h> |
37 | #include <linux/hdreg.h> | 37 | #include <linux/hdreg.h> |
38 | #include <linux/smp_lock.h> | ||
38 | #include <linux/spinlock.h> | 39 | #include <linux/spinlock.h> |
39 | #include <linux/blkdev.h> | 40 | #include <linux/blkdev.h> |
40 | #include <linux/genhd.h> | 41 | #include <linux/genhd.h> |
@@ -157,7 +158,7 @@ static int sendcmd( | |||
157 | unsigned int blkcnt, | 158 | unsigned int blkcnt, |
158 | unsigned int log_unit ); | 159 | unsigned int log_unit ); |
159 | 160 | ||
160 | static int ida_open(struct block_device *bdev, fmode_t mode); | 161 | static int ida_unlocked_open(struct block_device *bdev, fmode_t mode); |
161 | static int ida_release(struct gendisk *disk, fmode_t mode); | 162 | static int ida_release(struct gendisk *disk, fmode_t mode); |
162 | static int ida_ioctl(struct block_device *bdev, fmode_t mode, unsigned int cmd, unsigned long arg); | 163 | static int ida_ioctl(struct block_device *bdev, fmode_t mode, unsigned int cmd, unsigned long arg); |
163 | static int ida_getgeo(struct block_device *bdev, struct hd_geometry *geo); | 164 | static int ida_getgeo(struct block_device *bdev, struct hd_geometry *geo); |
@@ -195,9 +196,9 @@ static inline ctlr_info_t *get_host(struct gendisk *disk) | |||
195 | 196 | ||
196 | static const struct block_device_operations ida_fops = { | 197 | static const struct block_device_operations ida_fops = { |
197 | .owner = THIS_MODULE, | 198 | .owner = THIS_MODULE, |
198 | .open = ida_open, | 199 | .open = ida_unlocked_open, |
199 | .release = ida_release, | 200 | .release = ida_release, |
200 | .locked_ioctl = ida_ioctl, | 201 | .ioctl = ida_ioctl, |
201 | .getgeo = ida_getgeo, | 202 | .getgeo = ida_getgeo, |
202 | .revalidate_disk= ida_revalidate, | 203 | .revalidate_disk= ida_revalidate, |
203 | }; | 204 | }; |
@@ -840,13 +841,29 @@ static int ida_open(struct block_device *bdev, fmode_t mode) | |||
840 | return 0; | 841 | return 0; |
841 | } | 842 | } |
842 | 843 | ||
844 | static int ida_unlocked_open(struct block_device *bdev, fmode_t mode) | ||
845 | { | ||
846 | int ret; | ||
847 | |||
848 | lock_kernel(); | ||
849 | ret = ida_open(bdev, mode); | ||
850 | unlock_kernel(); | ||
851 | |||
852 | return ret; | ||
853 | } | ||
854 | |||
843 | /* | 855 | /* |
844 | * Close. Sync first. | 856 | * Close. Sync first. |
845 | */ | 857 | */ |
846 | static int ida_release(struct gendisk *disk, fmode_t mode) | 858 | static int ida_release(struct gendisk *disk, fmode_t mode) |
847 | { | 859 | { |
848 | ctlr_info_t *host = get_host(disk); | 860 | ctlr_info_t *host; |
861 | |||
862 | lock_kernel(); | ||
863 | host = get_host(disk); | ||
849 | host->usage_count--; | 864 | host->usage_count--; |
865 | unlock_kernel(); | ||
866 | |||
850 | return 0; | 867 | return 0; |
851 | } | 868 | } |
852 | 869 | ||
@@ -1128,7 +1145,7 @@ static int ida_getgeo(struct block_device *bdev, struct hd_geometry *geo) | |||
1128 | * ida_ioctl does some miscellaneous stuff like reporting drive geometry, | 1145 | * ida_ioctl does some miscellaneous stuff like reporting drive geometry, |
1129 | * setting readahead and submitting commands from userspace to the controller. | 1146 | * setting readahead and submitting commands from userspace to the controller. |
1130 | */ | 1147 | */ |
1131 | static int ida_ioctl(struct block_device *bdev, fmode_t mode, unsigned int cmd, unsigned long arg) | 1148 | static int ida_locked_ioctl(struct block_device *bdev, fmode_t mode, unsigned int cmd, unsigned long arg) |
1132 | { | 1149 | { |
1133 | drv_info_t *drv = get_drv(bdev->bd_disk); | 1150 | drv_info_t *drv = get_drv(bdev->bd_disk); |
1134 | ctlr_info_t *host = get_host(bdev->bd_disk); | 1151 | ctlr_info_t *host = get_host(bdev->bd_disk); |
@@ -1162,7 +1179,8 @@ out_passthru: | |||
1162 | return error; | 1179 | return error; |
1163 | case IDAGETCTLRSIG: | 1180 | case IDAGETCTLRSIG: |
1164 | if (!arg) return -EINVAL; | 1181 | if (!arg) return -EINVAL; |
1165 | put_user(host->ctlr_sig, (int __user *)arg); | 1182 | if (put_user(host->ctlr_sig, (int __user *)arg)) |
1183 | return -EFAULT; | ||
1166 | return 0; | 1184 | return 0; |
1167 | case IDAREVALIDATEVOLS: | 1185 | case IDAREVALIDATEVOLS: |
1168 | if (MINOR(bdev->bd_dev) != 0) | 1186 | if (MINOR(bdev->bd_dev) != 0) |
@@ -1170,7 +1188,8 @@ out_passthru: | |||
1170 | return revalidate_allvol(host); | 1188 | return revalidate_allvol(host); |
1171 | case IDADRIVERVERSION: | 1189 | case IDADRIVERVERSION: |
1172 | if (!arg) return -EINVAL; | 1190 | if (!arg) return -EINVAL; |
1173 | put_user(DRIVER_VERSION, (unsigned long __user *)arg); | 1191 | if (put_user(DRIVER_VERSION, (unsigned long __user *)arg)) |
1192 | return -EFAULT; | ||
1174 | return 0; | 1193 | return 0; |
1175 | case IDAGETPCIINFO: | 1194 | case IDAGETPCIINFO: |
1176 | { | 1195 | { |
@@ -1192,6 +1211,19 @@ out_passthru: | |||
1192 | } | 1211 | } |
1193 | 1212 | ||
1194 | } | 1213 | } |
1214 | |||
1215 | static int ida_ioctl(struct block_device *bdev, fmode_t mode, | ||
1216 | unsigned int cmd, unsigned long param) | ||
1217 | { | ||
1218 | int ret; | ||
1219 | |||
1220 | lock_kernel(); | ||
1221 | ret = ida_locked_ioctl(bdev, mode, cmd, param); | ||
1222 | unlock_kernel(); | ||
1223 | |||
1224 | return ret; | ||
1225 | } | ||
1226 | |||
1195 | /* | 1227 | /* |
1196 | * ida_ctlr_ioctl is for passing commands to the controller from userspace. | 1228 | * ida_ctlr_ioctl is for passing commands to the controller from userspace. |
1197 | * The command block (io) has already been copied to kernel space for us, | 1229 | * The command block (io) has already been copied to kernel space for us, |
@@ -1225,17 +1257,11 @@ static int ida_ctlr_ioctl(ctlr_info_t *h, int dsk, ida_ioctl_t *io) | |||
1225 | /* Pre submit processing */ | 1257 | /* Pre submit processing */ |
1226 | switch(io->cmd) { | 1258 | switch(io->cmd) { |
1227 | case PASSTHRU_A: | 1259 | case PASSTHRU_A: |
1228 | p = kmalloc(io->sg[0].size, GFP_KERNEL); | 1260 | p = memdup_user(io->sg[0].addr, io->sg[0].size); |
1229 | if (!p) | 1261 | if (IS_ERR(p)) { |
1230 | { | 1262 | error = PTR_ERR(p); |
1231 | error = -ENOMEM; | 1263 | cmd_free(h, c, 0); |
1232 | cmd_free(h, c, 0); | 1264 | return error; |
1233 | return(error); | ||
1234 | } | ||
1235 | if (copy_from_user(p, io->sg[0].addr, io->sg[0].size)) { | ||
1236 | kfree(p); | ||
1237 | cmd_free(h, c, 0); | ||
1238 | return -EFAULT; | ||
1239 | } | 1265 | } |
1240 | c->req.hdr.blk = pci_map_single(h->pci_dev, &(io->c), | 1266 | c->req.hdr.blk = pci_map_single(h->pci_dev, &(io->c), |
1241 | sizeof(ida_ioctl_t), | 1267 | sizeof(ida_ioctl_t), |
@@ -1266,18 +1292,12 @@ static int ida_ctlr_ioctl(ctlr_info_t *h, int dsk, ida_ioctl_t *io) | |||
1266 | case DIAG_PASS_THRU: | 1292 | case DIAG_PASS_THRU: |
1267 | case COLLECT_BUFFER: | 1293 | case COLLECT_BUFFER: |
1268 | case WRITE_FLASH_ROM: | 1294 | case WRITE_FLASH_ROM: |
1269 | p = kmalloc(io->sg[0].size, GFP_KERNEL); | 1295 | p = memdup_user(io->sg[0].addr, io->sg[0].size); |
1270 | if (!p) | 1296 | if (IS_ERR(p)) { |
1271 | { | 1297 | error = PTR_ERR(p); |
1272 | error = -ENOMEM; | 1298 | cmd_free(h, c, 0); |
1273 | cmd_free(h, c, 0); | 1299 | return error; |
1274 | return(error); | ||
1275 | } | 1300 | } |
1276 | if (copy_from_user(p, io->sg[0].addr, io->sg[0].size)) { | ||
1277 | kfree(p); | ||
1278 | cmd_free(h, c, 0); | ||
1279 | return -EFAULT; | ||
1280 | } | ||
1281 | c->req.sg[0].size = io->sg[0].size; | 1301 | c->req.sg[0].size = io->sg[0].size; |
1282 | c->req.sg[0].addr = pci_map_single(h->pci_dev, p, | 1302 | c->req.sg[0].addr = pci_map_single(h->pci_dev, p, |
1283 | c->req.sg[0].size, PCI_DMA_BIDIRECTIONAL); | 1303 | c->req.sg[0].size, PCI_DMA_BIDIRECTIONAL); |
diff --git a/drivers/block/drbd/drbd_actlog.c b/drivers/block/drbd/drbd_actlog.c index df018990c422..9400845d602e 100644 --- a/drivers/block/drbd/drbd_actlog.c +++ b/drivers/block/drbd/drbd_actlog.c | |||
@@ -79,8 +79,8 @@ static int _drbd_md_sync_page_io(struct drbd_conf *mdev, | |||
79 | md_io.error = 0; | 79 | md_io.error = 0; |
80 | 80 | ||
81 | if ((rw & WRITE) && !test_bit(MD_NO_BARRIER, &mdev->flags)) | 81 | if ((rw & WRITE) && !test_bit(MD_NO_BARRIER, &mdev->flags)) |
82 | rw |= (1 << BIO_RW_BARRIER); | 82 | rw |= REQ_HARDBARRIER; |
83 | rw |= ((1<<BIO_RW_UNPLUG) | (1<<BIO_RW_SYNCIO)); | 83 | rw |= REQ_UNPLUG | REQ_SYNC; |
84 | 84 | ||
85 | retry: | 85 | retry: |
86 | bio = bio_alloc(GFP_NOIO, 1); | 86 | bio = bio_alloc(GFP_NOIO, 1); |
@@ -103,11 +103,11 @@ static int _drbd_md_sync_page_io(struct drbd_conf *mdev, | |||
103 | /* check for unsupported barrier op. | 103 | /* check for unsupported barrier op. |
104 | * would rather check on EOPNOTSUPP, but that is not reliable. | 104 | * would rather check on EOPNOTSUPP, but that is not reliable. |
105 | * don't try again for ANY return value != 0 */ | 105 | * don't try again for ANY return value != 0 */ |
106 | if (unlikely(bio_rw_flagged(bio, BIO_RW_BARRIER) && !ok)) { | 106 | if (unlikely((bio->bi_rw & REQ_HARDBARRIER) && !ok)) { |
107 | /* Try again with no barrier */ | 107 | /* Try again with no barrier */ |
108 | dev_warn(DEV, "Barriers not supported on meta data device - disabling\n"); | 108 | dev_warn(DEV, "Barriers not supported on meta data device - disabling\n"); |
109 | set_bit(MD_NO_BARRIER, &mdev->flags); | 109 | set_bit(MD_NO_BARRIER, &mdev->flags); |
110 | rw &= ~(1 << BIO_RW_BARRIER); | 110 | rw &= ~REQ_HARDBARRIER; |
111 | bio_put(bio); | 111 | bio_put(bio); |
112 | goto retry; | 112 | goto retry; |
113 | } | 113 | } |
diff --git a/drivers/block/drbd/drbd_int.h b/drivers/block/drbd/drbd_int.h index 485ed8c7d623..352441b0f92f 100644 --- a/drivers/block/drbd/drbd_int.h +++ b/drivers/block/drbd/drbd_int.h | |||
@@ -550,12 +550,6 @@ struct p_delay_probe { | |||
550 | u32 offset; /* usecs the probe got sent after the reference time point */ | 550 | u32 offset; /* usecs the probe got sent after the reference time point */ |
551 | } __packed; | 551 | } __packed; |
552 | 552 | ||
553 | struct delay_probe { | ||
554 | struct list_head list; | ||
555 | unsigned int seq_num; | ||
556 | struct timeval time; | ||
557 | }; | ||
558 | |||
559 | /* DCBP: Drbd Compressed Bitmap Packet ... */ | 553 | /* DCBP: Drbd Compressed Bitmap Packet ... */ |
560 | static inline enum drbd_bitmap_code | 554 | static inline enum drbd_bitmap_code |
561 | DCBP_get_code(struct p_compressed_bm *p) | 555 | DCBP_get_code(struct p_compressed_bm *p) |
@@ -942,11 +936,9 @@ struct drbd_conf { | |||
942 | unsigned int ko_count; | 936 | unsigned int ko_count; |
943 | struct drbd_work resync_work, | 937 | struct drbd_work resync_work, |
944 | unplug_work, | 938 | unplug_work, |
945 | md_sync_work, | 939 | md_sync_work; |
946 | delay_probe_work; | ||
947 | struct timer_list resync_timer; | 940 | struct timer_list resync_timer; |
948 | struct timer_list md_sync_timer; | 941 | struct timer_list md_sync_timer; |
949 | struct timer_list delay_probe_timer; | ||
950 | 942 | ||
951 | /* Used after attach while negotiating new disk state. */ | 943 | /* Used after attach while negotiating new disk state. */ |
952 | union drbd_state new_state_tmp; | 944 | union drbd_state new_state_tmp; |
@@ -1062,12 +1054,6 @@ struct drbd_conf { | |||
1062 | u64 ed_uuid; /* UUID of the exposed data */ | 1054 | u64 ed_uuid; /* UUID of the exposed data */ |
1063 | struct mutex state_mutex; | 1055 | struct mutex state_mutex; |
1064 | char congestion_reason; /* Why we where congested... */ | 1056 | char congestion_reason; /* Why we where congested... */ |
1065 | struct list_head delay_probes; /* protected by peer_seq_lock */ | ||
1066 | int data_delay; /* Delay of packets on the data-sock behind meta-sock */ | ||
1067 | unsigned int delay_seq; /* To generate sequence numbers of delay probes */ | ||
1068 | struct timeval dps_time; /* delay-probes-start-time */ | ||
1069 | unsigned int dp_volume_last; /* send_cnt of last delay probe */ | ||
1070 | int c_sync_rate; /* current resync rate after delay_probe magic */ | ||
1071 | }; | 1057 | }; |
1072 | 1058 | ||
1073 | static inline struct drbd_conf *minor_to_mdev(unsigned int minor) | 1059 | static inline struct drbd_conf *minor_to_mdev(unsigned int minor) |
diff --git a/drivers/block/drbd/drbd_main.c b/drivers/block/drbd/drbd_main.c index 7258c95e895e..fa650dd85b90 100644 --- a/drivers/block/drbd/drbd_main.c +++ b/drivers/block/drbd/drbd_main.c | |||
@@ -2184,43 +2184,6 @@ int drbd_send_ov_request(struct drbd_conf *mdev, sector_t sector, int size) | |||
2184 | return ok; | 2184 | return ok; |
2185 | } | 2185 | } |
2186 | 2186 | ||
2187 | static int drbd_send_delay_probe(struct drbd_conf *mdev, struct drbd_socket *ds) | ||
2188 | { | ||
2189 | struct p_delay_probe dp; | ||
2190 | int offset, ok = 0; | ||
2191 | struct timeval now; | ||
2192 | |||
2193 | mutex_lock(&ds->mutex); | ||
2194 | if (likely(ds->socket)) { | ||
2195 | do_gettimeofday(&now); | ||
2196 | offset = now.tv_usec - mdev->dps_time.tv_usec + | ||
2197 | (now.tv_sec - mdev->dps_time.tv_sec) * 1000000; | ||
2198 | dp.seq_num = cpu_to_be32(mdev->delay_seq); | ||
2199 | dp.offset = cpu_to_be32(offset); | ||
2200 | |||
2201 | ok = _drbd_send_cmd(mdev, ds->socket, P_DELAY_PROBE, | ||
2202 | (struct p_header *)&dp, sizeof(dp), 0); | ||
2203 | } | ||
2204 | mutex_unlock(&ds->mutex); | ||
2205 | |||
2206 | return ok; | ||
2207 | } | ||
2208 | |||
2209 | static int drbd_send_delay_probes(struct drbd_conf *mdev) | ||
2210 | { | ||
2211 | int ok; | ||
2212 | |||
2213 | mdev->delay_seq++; | ||
2214 | do_gettimeofday(&mdev->dps_time); | ||
2215 | ok = drbd_send_delay_probe(mdev, &mdev->meta); | ||
2216 | ok = ok && drbd_send_delay_probe(mdev, &mdev->data); | ||
2217 | |||
2218 | mdev->dp_volume_last = mdev->send_cnt; | ||
2219 | mod_timer(&mdev->delay_probe_timer, jiffies + mdev->sync_conf.dp_interval * HZ / 10); | ||
2220 | |||
2221 | return ok; | ||
2222 | } | ||
2223 | |||
2224 | /* called on sndtimeo | 2187 | /* called on sndtimeo |
2225 | * returns FALSE if we should retry, | 2188 | * returns FALSE if we should retry, |
2226 | * TRUE if we think connection is dead | 2189 | * TRUE if we think connection is dead |
@@ -2369,31 +2332,6 @@ static int _drbd_send_zc_ee(struct drbd_conf *mdev, struct drbd_epoch_entry *e) | |||
2369 | return 1; | 2332 | return 1; |
2370 | } | 2333 | } |
2371 | 2334 | ||
2372 | static void consider_delay_probes(struct drbd_conf *mdev) | ||
2373 | { | ||
2374 | if (mdev->state.conn != C_SYNC_SOURCE || mdev->agreed_pro_version < 93) | ||
2375 | return; | ||
2376 | |||
2377 | if (mdev->dp_volume_last + mdev->sync_conf.dp_volume * 2 < mdev->send_cnt) | ||
2378 | drbd_send_delay_probes(mdev); | ||
2379 | } | ||
2380 | |||
2381 | static int w_delay_probes(struct drbd_conf *mdev, struct drbd_work *w, int cancel) | ||
2382 | { | ||
2383 | if (!cancel && mdev->state.conn == C_SYNC_SOURCE) | ||
2384 | drbd_send_delay_probes(mdev); | ||
2385 | |||
2386 | return 1; | ||
2387 | } | ||
2388 | |||
2389 | static void delay_probe_timer_fn(unsigned long data) | ||
2390 | { | ||
2391 | struct drbd_conf *mdev = (struct drbd_conf *) data; | ||
2392 | |||
2393 | if (list_empty(&mdev->delay_probe_work.list)) | ||
2394 | drbd_queue_work(&mdev->data.work, &mdev->delay_probe_work); | ||
2395 | } | ||
2396 | |||
2397 | /* Used to send write requests | 2335 | /* Used to send write requests |
2398 | * R_PRIMARY -> Peer (P_DATA) | 2336 | * R_PRIMARY -> Peer (P_DATA) |
2399 | */ | 2337 | */ |
@@ -2425,15 +2363,15 @@ int drbd_send_dblock(struct drbd_conf *mdev, struct drbd_request *req) | |||
2425 | /* NOTE: no need to check if barriers supported here as we would | 2363 | /* NOTE: no need to check if barriers supported here as we would |
2426 | * not pass the test in make_request_common in that case | 2364 | * not pass the test in make_request_common in that case |
2427 | */ | 2365 | */ |
2428 | if (bio_rw_flagged(req->master_bio, BIO_RW_BARRIER)) { | 2366 | if (req->master_bio->bi_rw & REQ_HARDBARRIER) { |
2429 | dev_err(DEV, "ASSERT FAILED would have set DP_HARDBARRIER\n"); | 2367 | dev_err(DEV, "ASSERT FAILED would have set DP_HARDBARRIER\n"); |
2430 | /* dp_flags |= DP_HARDBARRIER; */ | 2368 | /* dp_flags |= DP_HARDBARRIER; */ |
2431 | } | 2369 | } |
2432 | if (bio_rw_flagged(req->master_bio, BIO_RW_SYNCIO)) | 2370 | if (req->master_bio->bi_rw & REQ_SYNC) |
2433 | dp_flags |= DP_RW_SYNC; | 2371 | dp_flags |= DP_RW_SYNC; |
2434 | /* for now handle SYNCIO and UNPLUG | 2372 | /* for now handle SYNCIO and UNPLUG |
2435 | * as if they still were one and the same flag */ | 2373 | * as if they still were one and the same flag */ |
2436 | if (bio_rw_flagged(req->master_bio, BIO_RW_UNPLUG)) | 2374 | if (req->master_bio->bi_rw & REQ_UNPLUG) |
2437 | dp_flags |= DP_RW_SYNC; | 2375 | dp_flags |= DP_RW_SYNC; |
2438 | if (mdev->state.conn >= C_SYNC_SOURCE && | 2376 | if (mdev->state.conn >= C_SYNC_SOURCE && |
2439 | mdev->state.conn <= C_PAUSED_SYNC_T) | 2377 | mdev->state.conn <= C_PAUSED_SYNC_T) |
@@ -2457,9 +2395,6 @@ int drbd_send_dblock(struct drbd_conf *mdev, struct drbd_request *req) | |||
2457 | 2395 | ||
2458 | drbd_put_data_sock(mdev); | 2396 | drbd_put_data_sock(mdev); |
2459 | 2397 | ||
2460 | if (ok) | ||
2461 | consider_delay_probes(mdev); | ||
2462 | |||
2463 | return ok; | 2398 | return ok; |
2464 | } | 2399 | } |
2465 | 2400 | ||
@@ -2506,9 +2441,6 @@ int drbd_send_block(struct drbd_conf *mdev, enum drbd_packets cmd, | |||
2506 | 2441 | ||
2507 | drbd_put_data_sock(mdev); | 2442 | drbd_put_data_sock(mdev); |
2508 | 2443 | ||
2509 | if (ok) | ||
2510 | consider_delay_probes(mdev); | ||
2511 | |||
2512 | return ok; | 2444 | return ok; |
2513 | } | 2445 | } |
2514 | 2446 | ||
@@ -2604,6 +2536,7 @@ static int drbd_open(struct block_device *bdev, fmode_t mode) | |||
2604 | unsigned long flags; | 2536 | unsigned long flags; |
2605 | int rv = 0; | 2537 | int rv = 0; |
2606 | 2538 | ||
2539 | lock_kernel(); | ||
2607 | spin_lock_irqsave(&mdev->req_lock, flags); | 2540 | spin_lock_irqsave(&mdev->req_lock, flags); |
2608 | /* to have a stable mdev->state.role | 2541 | /* to have a stable mdev->state.role |
2609 | * and no race with updating open_cnt */ | 2542 | * and no race with updating open_cnt */ |
@@ -2618,6 +2551,7 @@ static int drbd_open(struct block_device *bdev, fmode_t mode) | |||
2618 | if (!rv) | 2551 | if (!rv) |
2619 | mdev->open_cnt++; | 2552 | mdev->open_cnt++; |
2620 | spin_unlock_irqrestore(&mdev->req_lock, flags); | 2553 | spin_unlock_irqrestore(&mdev->req_lock, flags); |
2554 | unlock_kernel(); | ||
2621 | 2555 | ||
2622 | return rv; | 2556 | return rv; |
2623 | } | 2557 | } |
@@ -2625,7 +2559,9 @@ static int drbd_open(struct block_device *bdev, fmode_t mode) | |||
2625 | static int drbd_release(struct gendisk *gd, fmode_t mode) | 2559 | static int drbd_release(struct gendisk *gd, fmode_t mode) |
2626 | { | 2560 | { |
2627 | struct drbd_conf *mdev = gd->private_data; | 2561 | struct drbd_conf *mdev = gd->private_data; |
2562 | lock_kernel(); | ||
2628 | mdev->open_cnt--; | 2563 | mdev->open_cnt--; |
2564 | unlock_kernel(); | ||
2629 | return 0; | 2565 | return 0; |
2630 | } | 2566 | } |
2631 | 2567 | ||
@@ -2660,9 +2596,20 @@ static void drbd_unplug_fn(struct request_queue *q) | |||
2660 | 2596 | ||
2661 | static void drbd_set_defaults(struct drbd_conf *mdev) | 2597 | static void drbd_set_defaults(struct drbd_conf *mdev) |
2662 | { | 2598 | { |
2663 | mdev->sync_conf.after = DRBD_AFTER_DEF; | 2599 | /* This way we get a compile error when sync_conf grows, |
2664 | mdev->sync_conf.rate = DRBD_RATE_DEF; | 2600 | and we forgot to initialize it here */ |
2665 | mdev->sync_conf.al_extents = DRBD_AL_EXTENTS_DEF; | 2601 | mdev->sync_conf = (struct syncer_conf) { |
2602 | /* .rate = */ DRBD_RATE_DEF, | ||
2603 | /* .after = */ DRBD_AFTER_DEF, | ||
2604 | /* .al_extents = */ DRBD_AL_EXTENTS_DEF, | ||
2605 | /* .verify_alg = */ {}, 0, | ||
2606 | /* .cpu_mask = */ {}, 0, | ||
2607 | /* .csums_alg = */ {}, 0, | ||
2608 | /* .use_rle = */ 0 | ||
2609 | }; | ||
2610 | |||
2611 | /* Have to use that way, because the layout differs between | ||
2612 | big endian and little endian */ | ||
2666 | mdev->state = (union drbd_state) { | 2613 | mdev->state = (union drbd_state) { |
2667 | { .role = R_SECONDARY, | 2614 | { .role = R_SECONDARY, |
2668 | .peer = R_UNKNOWN, | 2615 | .peer = R_UNKNOWN, |
@@ -2721,24 +2668,17 @@ void drbd_init_set_defaults(struct drbd_conf *mdev) | |||
2721 | INIT_LIST_HEAD(&mdev->unplug_work.list); | 2668 | INIT_LIST_HEAD(&mdev->unplug_work.list); |
2722 | INIT_LIST_HEAD(&mdev->md_sync_work.list); | 2669 | INIT_LIST_HEAD(&mdev->md_sync_work.list); |
2723 | INIT_LIST_HEAD(&mdev->bm_io_work.w.list); | 2670 | INIT_LIST_HEAD(&mdev->bm_io_work.w.list); |
2724 | INIT_LIST_HEAD(&mdev->delay_probes); | ||
2725 | INIT_LIST_HEAD(&mdev->delay_probe_work.list); | ||
2726 | 2671 | ||
2727 | mdev->resync_work.cb = w_resync_inactive; | 2672 | mdev->resync_work.cb = w_resync_inactive; |
2728 | mdev->unplug_work.cb = w_send_write_hint; | 2673 | mdev->unplug_work.cb = w_send_write_hint; |
2729 | mdev->md_sync_work.cb = w_md_sync; | 2674 | mdev->md_sync_work.cb = w_md_sync; |
2730 | mdev->bm_io_work.w.cb = w_bitmap_io; | 2675 | mdev->bm_io_work.w.cb = w_bitmap_io; |
2731 | mdev->delay_probe_work.cb = w_delay_probes; | ||
2732 | init_timer(&mdev->resync_timer); | 2676 | init_timer(&mdev->resync_timer); |
2733 | init_timer(&mdev->md_sync_timer); | 2677 | init_timer(&mdev->md_sync_timer); |
2734 | init_timer(&mdev->delay_probe_timer); | ||
2735 | mdev->resync_timer.function = resync_timer_fn; | 2678 | mdev->resync_timer.function = resync_timer_fn; |
2736 | mdev->resync_timer.data = (unsigned long) mdev; | 2679 | mdev->resync_timer.data = (unsigned long) mdev; |
2737 | mdev->md_sync_timer.function = md_sync_timer_fn; | 2680 | mdev->md_sync_timer.function = md_sync_timer_fn; |
2738 | mdev->md_sync_timer.data = (unsigned long) mdev; | 2681 | mdev->md_sync_timer.data = (unsigned long) mdev; |
2739 | mdev->delay_probe_timer.function = delay_probe_timer_fn; | ||
2740 | mdev->delay_probe_timer.data = (unsigned long) mdev; | ||
2741 | |||
2742 | 2682 | ||
2743 | init_waitqueue_head(&mdev->misc_wait); | 2683 | init_waitqueue_head(&mdev->misc_wait); |
2744 | init_waitqueue_head(&mdev->state_wait); | 2684 | init_waitqueue_head(&mdev->state_wait); |
diff --git a/drivers/block/drbd/drbd_nl.c b/drivers/block/drbd/drbd_nl.c index 2151f18b21de..73131c5ae339 100644 --- a/drivers/block/drbd/drbd_nl.c +++ b/drivers/block/drbd/drbd_nl.c | |||
@@ -1557,10 +1557,6 @@ static int drbd_nl_syncer_conf(struct drbd_conf *mdev, struct drbd_nl_cfg_req *n | |||
1557 | sc.rate = DRBD_RATE_DEF; | 1557 | sc.rate = DRBD_RATE_DEF; |
1558 | sc.after = DRBD_AFTER_DEF; | 1558 | sc.after = DRBD_AFTER_DEF; |
1559 | sc.al_extents = DRBD_AL_EXTENTS_DEF; | 1559 | sc.al_extents = DRBD_AL_EXTENTS_DEF; |
1560 | sc.dp_volume = DRBD_DP_VOLUME_DEF; | ||
1561 | sc.dp_interval = DRBD_DP_INTERVAL_DEF; | ||
1562 | sc.throttle_th = DRBD_RS_THROTTLE_TH_DEF; | ||
1563 | sc.hold_off_th = DRBD_RS_HOLD_OFF_TH_DEF; | ||
1564 | } else | 1560 | } else |
1565 | memcpy(&sc, &mdev->sync_conf, sizeof(struct syncer_conf)); | 1561 | memcpy(&sc, &mdev->sync_conf, sizeof(struct syncer_conf)); |
1566 | 1562 | ||
diff --git a/drivers/block/drbd/drbd_proc.c b/drivers/block/drbd/drbd_proc.c index d0f1767ea4c3..be3374b68460 100644 --- a/drivers/block/drbd/drbd_proc.c +++ b/drivers/block/drbd/drbd_proc.c | |||
@@ -73,21 +73,14 @@ static void drbd_syncer_progress(struct drbd_conf *mdev, struct seq_file *seq) | |||
73 | seq_printf(seq, "sync'ed:%3u.%u%% ", res / 10, res % 10); | 73 | seq_printf(seq, "sync'ed:%3u.%u%% ", res / 10, res % 10); |
74 | /* if more than 1 GB display in MB */ | 74 | /* if more than 1 GB display in MB */ |
75 | if (mdev->rs_total > 0x100000L) | 75 | if (mdev->rs_total > 0x100000L) |
76 | seq_printf(seq, "(%lu/%lu)M", | 76 | seq_printf(seq, "(%lu/%lu)M\n\t", |
77 | (unsigned long) Bit2KB(rs_left >> 10), | 77 | (unsigned long) Bit2KB(rs_left >> 10), |
78 | (unsigned long) Bit2KB(mdev->rs_total >> 10)); | 78 | (unsigned long) Bit2KB(mdev->rs_total >> 10)); |
79 | else | 79 | else |
80 | seq_printf(seq, "(%lu/%lu)K", | 80 | seq_printf(seq, "(%lu/%lu)K\n\t", |
81 | (unsigned long) Bit2KB(rs_left), | 81 | (unsigned long) Bit2KB(rs_left), |
82 | (unsigned long) Bit2KB(mdev->rs_total)); | 82 | (unsigned long) Bit2KB(mdev->rs_total)); |
83 | 83 | ||
84 | if (mdev->state.conn == C_SYNC_TARGET) | ||
85 | seq_printf(seq, " queue_delay: %d.%d ms\n\t", | ||
86 | mdev->data_delay / 1000, | ||
87 | (mdev->data_delay % 1000) / 100); | ||
88 | else if (mdev->state.conn == C_SYNC_SOURCE) | ||
89 | seq_printf(seq, " delay_probe: %u\n\t", mdev->delay_seq); | ||
90 | |||
91 | /* see drivers/md/md.c | 84 | /* see drivers/md/md.c |
92 | * We do not want to overflow, so the order of operands and | 85 | * We do not want to overflow, so the order of operands and |
93 | * the * 100 / 100 trick are important. We do a +1 to be | 86 | * the * 100 / 100 trick are important. We do a +1 to be |
@@ -135,14 +128,6 @@ static void drbd_syncer_progress(struct drbd_conf *mdev, struct seq_file *seq) | |||
135 | else | 128 | else |
136 | seq_printf(seq, " (%ld)", dbdt); | 129 | seq_printf(seq, " (%ld)", dbdt); |
137 | 130 | ||
138 | if (mdev->state.conn == C_SYNC_TARGET) { | ||
139 | if (mdev->c_sync_rate > 1000) | ||
140 | seq_printf(seq, " want: %d,%03d", | ||
141 | mdev->c_sync_rate / 1000, mdev->c_sync_rate % 1000); | ||
142 | else | ||
143 | seq_printf(seq, " want: %d", mdev->c_sync_rate); | ||
144 | } | ||
145 | |||
146 | seq_printf(seq, " K/sec\n"); | 131 | seq_printf(seq, " K/sec\n"); |
147 | } | 132 | } |
148 | 133 | ||
diff --git a/drivers/block/drbd/drbd_receiver.c b/drivers/block/drbd/drbd_receiver.c index ec1711f7c5c5..081522d3c742 100644 --- a/drivers/block/drbd/drbd_receiver.c +++ b/drivers/block/drbd/drbd_receiver.c | |||
@@ -1180,7 +1180,7 @@ next_bio: | |||
1180 | bio->bi_sector = sector; | 1180 | bio->bi_sector = sector; |
1181 | bio->bi_bdev = mdev->ldev->backing_bdev; | 1181 | bio->bi_bdev = mdev->ldev->backing_bdev; |
1182 | /* we special case some flags in the multi-bio case, see below | 1182 | /* we special case some flags in the multi-bio case, see below |
1183 | * (BIO_RW_UNPLUG, BIO_RW_BARRIER) */ | 1183 | * (REQ_UNPLUG, REQ_HARDBARRIER) */ |
1184 | bio->bi_rw = rw; | 1184 | bio->bi_rw = rw; |
1185 | bio->bi_private = e; | 1185 | bio->bi_private = e; |
1186 | bio->bi_end_io = drbd_endio_sec; | 1186 | bio->bi_end_io = drbd_endio_sec; |
@@ -1209,16 +1209,16 @@ next_bio: | |||
1209 | bios = bios->bi_next; | 1209 | bios = bios->bi_next; |
1210 | bio->bi_next = NULL; | 1210 | bio->bi_next = NULL; |
1211 | 1211 | ||
1212 | /* strip off BIO_RW_UNPLUG unless it is the last bio */ | 1212 | /* strip off REQ_UNPLUG unless it is the last bio */ |
1213 | if (bios) | 1213 | if (bios) |
1214 | bio->bi_rw &= ~(1<<BIO_RW_UNPLUG); | 1214 | bio->bi_rw &= ~REQ_UNPLUG; |
1215 | 1215 | ||
1216 | drbd_generic_make_request(mdev, fault_type, bio); | 1216 | drbd_generic_make_request(mdev, fault_type, bio); |
1217 | 1217 | ||
1218 | /* strip off BIO_RW_BARRIER, | 1218 | /* strip off REQ_HARDBARRIER, |
1219 | * unless it is the first or last bio */ | 1219 | * unless it is the first or last bio */ |
1220 | if (bios && bios->bi_next) | 1220 | if (bios && bios->bi_next) |
1221 | bios->bi_rw &= ~(1<<BIO_RW_BARRIER); | 1221 | bios->bi_rw &= ~REQ_HARDBARRIER; |
1222 | } while (bios); | 1222 | } while (bios); |
1223 | maybe_kick_lo(mdev); | 1223 | maybe_kick_lo(mdev); |
1224 | return 0; | 1224 | return 0; |
@@ -1233,7 +1233,7 @@ fail: | |||
1233 | } | 1233 | } |
1234 | 1234 | ||
1235 | /** | 1235 | /** |
1236 | * w_e_reissue() - Worker callback; Resubmit a bio, without BIO_RW_BARRIER set | 1236 | * w_e_reissue() - Worker callback; Resubmit a bio, without REQ_HARDBARRIER set |
1237 | * @mdev: DRBD device. | 1237 | * @mdev: DRBD device. |
1238 | * @w: work object. | 1238 | * @w: work object. |
1239 | * @cancel: The connection will be closed anyways (unused in this callback) | 1239 | * @cancel: The connection will be closed anyways (unused in this callback) |
@@ -1245,7 +1245,7 @@ int w_e_reissue(struct drbd_conf *mdev, struct drbd_work *w, int cancel) __relea | |||
1245 | (and DE_BARRIER_IN_NEXT_EPOCH_ISSUED in the previous Epoch) | 1245 | (and DE_BARRIER_IN_NEXT_EPOCH_ISSUED in the previous Epoch) |
1246 | so that we can finish that epoch in drbd_may_finish_epoch(). | 1246 | so that we can finish that epoch in drbd_may_finish_epoch(). |
1247 | That is necessary if we already have a long chain of Epochs, before | 1247 | That is necessary if we already have a long chain of Epochs, before |
1248 | we realize that BIO_RW_BARRIER is actually not supported */ | 1248 | we realize that REQ_HARDBARRIER is actually not supported */ |
1249 | 1249 | ||
1250 | /* As long as the -ENOTSUPP on the barrier is reported immediately | 1250 | /* As long as the -ENOTSUPP on the barrier is reported immediately |
1251 | that will never trigger. If it is reported late, we will just | 1251 | that will never trigger. If it is reported late, we will just |
@@ -1824,14 +1824,14 @@ static int receive_Data(struct drbd_conf *mdev, struct p_header *h) | |||
1824 | epoch = list_entry(e->epoch->list.prev, struct drbd_epoch, list); | 1824 | epoch = list_entry(e->epoch->list.prev, struct drbd_epoch, list); |
1825 | if (epoch == e->epoch) { | 1825 | if (epoch == e->epoch) { |
1826 | set_bit(DE_CONTAINS_A_BARRIER, &e->epoch->flags); | 1826 | set_bit(DE_CONTAINS_A_BARRIER, &e->epoch->flags); |
1827 | rw |= (1<<BIO_RW_BARRIER); | 1827 | rw |= REQ_HARDBARRIER; |
1828 | e->flags |= EE_IS_BARRIER; | 1828 | e->flags |= EE_IS_BARRIER; |
1829 | } else { | 1829 | } else { |
1830 | if (atomic_read(&epoch->epoch_size) > 1 || | 1830 | if (atomic_read(&epoch->epoch_size) > 1 || |
1831 | !test_bit(DE_CONTAINS_A_BARRIER, &epoch->flags)) { | 1831 | !test_bit(DE_CONTAINS_A_BARRIER, &epoch->flags)) { |
1832 | set_bit(DE_BARRIER_IN_NEXT_EPOCH_ISSUED, &epoch->flags); | 1832 | set_bit(DE_BARRIER_IN_NEXT_EPOCH_ISSUED, &epoch->flags); |
1833 | set_bit(DE_CONTAINS_A_BARRIER, &e->epoch->flags); | 1833 | set_bit(DE_CONTAINS_A_BARRIER, &e->epoch->flags); |
1834 | rw |= (1<<BIO_RW_BARRIER); | 1834 | rw |= REQ_HARDBARRIER; |
1835 | e->flags |= EE_IS_BARRIER; | 1835 | e->flags |= EE_IS_BARRIER; |
1836 | } | 1836 | } |
1837 | } | 1837 | } |
@@ -1841,10 +1841,10 @@ static int receive_Data(struct drbd_conf *mdev, struct p_header *h) | |||
1841 | dp_flags = be32_to_cpu(p->dp_flags); | 1841 | dp_flags = be32_to_cpu(p->dp_flags); |
1842 | if (dp_flags & DP_HARDBARRIER) { | 1842 | if (dp_flags & DP_HARDBARRIER) { |
1843 | dev_err(DEV, "ASSERT FAILED would have submitted barrier request\n"); | 1843 | dev_err(DEV, "ASSERT FAILED would have submitted barrier request\n"); |
1844 | /* rw |= (1<<BIO_RW_BARRIER); */ | 1844 | /* rw |= REQ_HARDBARRIER; */ |
1845 | } | 1845 | } |
1846 | if (dp_flags & DP_RW_SYNC) | 1846 | if (dp_flags & DP_RW_SYNC) |
1847 | rw |= (1<<BIO_RW_SYNCIO) | (1<<BIO_RW_UNPLUG); | 1847 | rw |= REQ_SYNC | REQ_UNPLUG; |
1848 | if (dp_flags & DP_MAY_SET_IN_SYNC) | 1848 | if (dp_flags & DP_MAY_SET_IN_SYNC) |
1849 | e->flags |= EE_MAY_SET_IN_SYNC; | 1849 | e->flags |= EE_MAY_SET_IN_SYNC; |
1850 | 1850 | ||
@@ -3555,14 +3555,15 @@ static int receive_bitmap(struct drbd_conf *mdev, struct p_header *h) | |||
3555 | return ok; | 3555 | return ok; |
3556 | } | 3556 | } |
3557 | 3557 | ||
3558 | static int receive_skip(struct drbd_conf *mdev, struct p_header *h) | 3558 | static int receive_skip_(struct drbd_conf *mdev, struct p_header *h, int silent) |
3559 | { | 3559 | { |
3560 | /* TODO zero copy sink :) */ | 3560 | /* TODO zero copy sink :) */ |
3561 | static char sink[128]; | 3561 | static char sink[128]; |
3562 | int size, want, r; | 3562 | int size, want, r; |
3563 | 3563 | ||
3564 | dev_warn(DEV, "skipping unknown optional packet type %d, l: %d!\n", | 3564 | if (!silent) |
3565 | h->command, h->length); | 3565 | dev_warn(DEV, "skipping unknown optional packet type %d, l: %d!\n", |
3566 | h->command, h->length); | ||
3566 | 3567 | ||
3567 | size = h->length; | 3568 | size = h->length; |
3568 | while (size > 0) { | 3569 | while (size > 0) { |
@@ -3574,101 +3575,25 @@ static int receive_skip(struct drbd_conf *mdev, struct p_header *h) | |||
3574 | return size == 0; | 3575 | return size == 0; |
3575 | } | 3576 | } |
3576 | 3577 | ||
3577 | static int receive_UnplugRemote(struct drbd_conf *mdev, struct p_header *h) | 3578 | static int receive_skip(struct drbd_conf *mdev, struct p_header *h) |
3578 | { | ||
3579 | if (mdev->state.disk >= D_INCONSISTENT) | ||
3580 | drbd_kick_lo(mdev); | ||
3581 | |||
3582 | /* Make sure we've acked all the TCP data associated | ||
3583 | * with the data requests being unplugged */ | ||
3584 | drbd_tcp_quickack(mdev->data.socket); | ||
3585 | |||
3586 | return TRUE; | ||
3587 | } | ||
3588 | |||
3589 | static void timeval_sub_us(struct timeval* tv, unsigned int us) | ||
3590 | { | 3579 | { |
3591 | tv->tv_sec -= us / 1000000; | 3580 | return receive_skip_(mdev, h, 0); |
3592 | us = us % 1000000; | ||
3593 | if (tv->tv_usec > us) { | ||
3594 | tv->tv_usec += 1000000; | ||
3595 | tv->tv_sec--; | ||
3596 | } | ||
3597 | tv->tv_usec -= us; | ||
3598 | } | 3581 | } |
3599 | 3582 | ||
3600 | static void got_delay_probe(struct drbd_conf *mdev, int from, struct p_delay_probe *p) | 3583 | static int receive_skip_silent(struct drbd_conf *mdev, struct p_header *h) |
3601 | { | 3584 | { |
3602 | struct delay_probe *dp; | 3585 | return receive_skip_(mdev, h, 1); |
3603 | struct list_head *le; | ||
3604 | struct timeval now; | ||
3605 | int seq_num; | ||
3606 | int offset; | ||
3607 | int data_delay; | ||
3608 | |||
3609 | seq_num = be32_to_cpu(p->seq_num); | ||
3610 | offset = be32_to_cpu(p->offset); | ||
3611 | |||
3612 | spin_lock(&mdev->peer_seq_lock); | ||
3613 | if (!list_empty(&mdev->delay_probes)) { | ||
3614 | if (from == USE_DATA_SOCKET) | ||
3615 | le = mdev->delay_probes.next; | ||
3616 | else | ||
3617 | le = mdev->delay_probes.prev; | ||
3618 | |||
3619 | dp = list_entry(le, struct delay_probe, list); | ||
3620 | |||
3621 | if (dp->seq_num == seq_num) { | ||
3622 | list_del(le); | ||
3623 | spin_unlock(&mdev->peer_seq_lock); | ||
3624 | do_gettimeofday(&now); | ||
3625 | timeval_sub_us(&now, offset); | ||
3626 | data_delay = | ||
3627 | now.tv_usec - dp->time.tv_usec + | ||
3628 | (now.tv_sec - dp->time.tv_sec) * 1000000; | ||
3629 | |||
3630 | if (data_delay > 0) | ||
3631 | mdev->data_delay = data_delay; | ||
3632 | |||
3633 | kfree(dp); | ||
3634 | return; | ||
3635 | } | ||
3636 | |||
3637 | if (dp->seq_num > seq_num) { | ||
3638 | spin_unlock(&mdev->peer_seq_lock); | ||
3639 | dev_warn(DEV, "Previous allocation failure of struct delay_probe?\n"); | ||
3640 | return; /* Do not alloca a struct delay_probe.... */ | ||
3641 | } | ||
3642 | } | ||
3643 | spin_unlock(&mdev->peer_seq_lock); | ||
3644 | |||
3645 | dp = kmalloc(sizeof(struct delay_probe), GFP_NOIO); | ||
3646 | if (!dp) { | ||
3647 | dev_warn(DEV, "Failed to allocate a struct delay_probe, do not worry.\n"); | ||
3648 | return; | ||
3649 | } | ||
3650 | |||
3651 | dp->seq_num = seq_num; | ||
3652 | do_gettimeofday(&dp->time); | ||
3653 | timeval_sub_us(&dp->time, offset); | ||
3654 | |||
3655 | spin_lock(&mdev->peer_seq_lock); | ||
3656 | if (from == USE_DATA_SOCKET) | ||
3657 | list_add(&dp->list, &mdev->delay_probes); | ||
3658 | else | ||
3659 | list_add_tail(&dp->list, &mdev->delay_probes); | ||
3660 | spin_unlock(&mdev->peer_seq_lock); | ||
3661 | } | 3586 | } |
3662 | 3587 | ||
3663 | static int receive_delay_probe(struct drbd_conf *mdev, struct p_header *h) | 3588 | static int receive_UnplugRemote(struct drbd_conf *mdev, struct p_header *h) |
3664 | { | 3589 | { |
3665 | struct p_delay_probe *p = (struct p_delay_probe *)h; | 3590 | if (mdev->state.disk >= D_INCONSISTENT) |
3591 | drbd_kick_lo(mdev); | ||
3666 | 3592 | ||
3667 | ERR_IF(h->length != (sizeof(*p)-sizeof(*h))) return FALSE; | 3593 | /* Make sure we've acked all the TCP data associated |
3668 | if (drbd_recv(mdev, h->payload, h->length) != h->length) | 3594 | * with the data requests being unplugged */ |
3669 | return FALSE; | 3595 | drbd_tcp_quickack(mdev->data.socket); |
3670 | 3596 | ||
3671 | got_delay_probe(mdev, USE_DATA_SOCKET, p); | ||
3672 | return TRUE; | 3597 | return TRUE; |
3673 | } | 3598 | } |
3674 | 3599 | ||
@@ -3695,7 +3620,7 @@ static drbd_cmd_handler_f drbd_default_handler[] = { | |||
3695 | [P_OV_REQUEST] = receive_DataRequest, | 3620 | [P_OV_REQUEST] = receive_DataRequest, |
3696 | [P_OV_REPLY] = receive_DataRequest, | 3621 | [P_OV_REPLY] = receive_DataRequest, |
3697 | [P_CSUM_RS_REQUEST] = receive_DataRequest, | 3622 | [P_CSUM_RS_REQUEST] = receive_DataRequest, |
3698 | [P_DELAY_PROBE] = receive_delay_probe, | 3623 | [P_DELAY_PROBE] = receive_skip_silent, |
3699 | /* anything missing from this table is in | 3624 | /* anything missing from this table is in |
3700 | * the asender_tbl, see get_asender_cmd */ | 3625 | * the asender_tbl, see get_asender_cmd */ |
3701 | [P_MAX_CMD] = NULL, | 3626 | [P_MAX_CMD] = NULL, |
@@ -4472,11 +4397,9 @@ static int got_OVResult(struct drbd_conf *mdev, struct p_header *h) | |||
4472 | return TRUE; | 4397 | return TRUE; |
4473 | } | 4398 | } |
4474 | 4399 | ||
4475 | static int got_delay_probe_m(struct drbd_conf *mdev, struct p_header *h) | 4400 | static int got_something_to_ignore_m(struct drbd_conf *mdev, struct p_header *h) |
4476 | { | 4401 | { |
4477 | struct p_delay_probe *p = (struct p_delay_probe *)h; | 4402 | /* IGNORE */ |
4478 | |||
4479 | got_delay_probe(mdev, USE_META_SOCKET, p); | ||
4480 | return TRUE; | 4403 | return TRUE; |
4481 | } | 4404 | } |
4482 | 4405 | ||
@@ -4504,7 +4427,7 @@ static struct asender_cmd *get_asender_cmd(int cmd) | |||
4504 | [P_BARRIER_ACK] = { sizeof(struct p_barrier_ack), got_BarrierAck }, | 4427 | [P_BARRIER_ACK] = { sizeof(struct p_barrier_ack), got_BarrierAck }, |
4505 | [P_STATE_CHG_REPLY] = { sizeof(struct p_req_state_reply), got_RqSReply }, | 4428 | [P_STATE_CHG_REPLY] = { sizeof(struct p_req_state_reply), got_RqSReply }, |
4506 | [P_RS_IS_IN_SYNC] = { sizeof(struct p_block_ack), got_IsInSync }, | 4429 | [P_RS_IS_IN_SYNC] = { sizeof(struct p_block_ack), got_IsInSync }, |
4507 | [P_DELAY_PROBE] = { sizeof(struct p_delay_probe), got_delay_probe_m }, | 4430 | [P_DELAY_PROBE] = { sizeof(struct p_delay_probe), got_something_to_ignore_m }, |
4508 | [P_MAX_CMD] = { 0, NULL }, | 4431 | [P_MAX_CMD] = { 0, NULL }, |
4509 | }; | 4432 | }; |
4510 | if (cmd > P_MAX_CMD || asender_tbl[cmd].process == NULL) | 4433 | if (cmd > P_MAX_CMD || asender_tbl[cmd].process == NULL) |
diff --git a/drivers/block/drbd/drbd_req.c b/drivers/block/drbd/drbd_req.c index 654f1ef5cbb0..f761d98a4e90 100644 --- a/drivers/block/drbd/drbd_req.c +++ b/drivers/block/drbd/drbd_req.c | |||
@@ -997,7 +997,7 @@ int drbd_make_request_26(struct request_queue *q, struct bio *bio) | |||
997 | * because of those XXX, this is not yet enabled, | 997 | * because of those XXX, this is not yet enabled, |
998 | * i.e. in drbd_init_set_defaults we set the NO_BARRIER_SUPP bit. | 998 | * i.e. in drbd_init_set_defaults we set the NO_BARRIER_SUPP bit. |
999 | */ | 999 | */ |
1000 | if (unlikely(bio_rw_flagged(bio, BIO_RW_BARRIER) && test_bit(NO_BARRIER_SUPP, &mdev->flags))) { | 1000 | if (unlikely(bio->bi_rw & REQ_HARDBARRIER) && test_bit(NO_BARRIER_SUPP, &mdev->flags)) { |
1001 | /* dev_warn(DEV, "Rejecting barrier request as underlying device does not support\n"); */ | 1001 | /* dev_warn(DEV, "Rejecting barrier request as underlying device does not support\n"); */ |
1002 | bio_endio(bio, -EOPNOTSUPP); | 1002 | bio_endio(bio, -EOPNOTSUPP); |
1003 | return 0; | 1003 | return 0; |
diff --git a/drivers/block/drbd/drbd_worker.c b/drivers/block/drbd/drbd_worker.c index b623ceee2a4a..ca4a16cea2d8 100644 --- a/drivers/block/drbd/drbd_worker.c +++ b/drivers/block/drbd/drbd_worker.c | |||
@@ -424,18 +424,6 @@ void resync_timer_fn(unsigned long data) | |||
424 | drbd_queue_work(&mdev->data.work, &mdev->resync_work); | 424 | drbd_queue_work(&mdev->data.work, &mdev->resync_work); |
425 | } | 425 | } |
426 | 426 | ||
427 | static int calc_resync_rate(struct drbd_conf *mdev) | ||
428 | { | ||
429 | int d = mdev->data_delay / 1000; /* us -> ms */ | ||
430 | int td = mdev->sync_conf.throttle_th * 100; /* 0.1s -> ms */ | ||
431 | int hd = mdev->sync_conf.hold_off_th * 100; /* 0.1s -> ms */ | ||
432 | int cr = mdev->sync_conf.rate; | ||
433 | |||
434 | return d <= td ? cr : | ||
435 | d >= hd ? 0 : | ||
436 | cr + (cr * (td - d) / (hd - td)); | ||
437 | } | ||
438 | |||
439 | int w_make_resync_request(struct drbd_conf *mdev, | 427 | int w_make_resync_request(struct drbd_conf *mdev, |
440 | struct drbd_work *w, int cancel) | 428 | struct drbd_work *w, int cancel) |
441 | { | 429 | { |
@@ -473,8 +461,7 @@ int w_make_resync_request(struct drbd_conf *mdev, | |||
473 | max_segment_size = mdev->agreed_pro_version < 94 ? | 461 | max_segment_size = mdev->agreed_pro_version < 94 ? |
474 | queue_max_segment_size(mdev->rq_queue) : DRBD_MAX_SEGMENT_SIZE; | 462 | queue_max_segment_size(mdev->rq_queue) : DRBD_MAX_SEGMENT_SIZE; |
475 | 463 | ||
476 | mdev->c_sync_rate = calc_resync_rate(mdev); | 464 | number = SLEEP_TIME * mdev->sync_conf.rate / ((BM_BLOCK_SIZE / 1024) * HZ); |
477 | number = SLEEP_TIME * mdev->c_sync_rate / ((BM_BLOCK_SIZE / 1024) * HZ); | ||
478 | pe = atomic_read(&mdev->rs_pending_cnt); | 465 | pe = atomic_read(&mdev->rs_pending_cnt); |
479 | 466 | ||
480 | mutex_lock(&mdev->data.mutex); | 467 | mutex_lock(&mdev->data.mutex); |
diff --git a/drivers/block/floppy.c b/drivers/block/floppy.c index 90c4038702da..cf04c1b234ed 100644 --- a/drivers/block/floppy.c +++ b/drivers/block/floppy.c | |||
@@ -178,6 +178,7 @@ static int print_unex = 1; | |||
178 | #include <linux/slab.h> | 178 | #include <linux/slab.h> |
179 | #include <linux/mm.h> | 179 | #include <linux/mm.h> |
180 | #include <linux/bio.h> | 180 | #include <linux/bio.h> |
181 | #include <linux/smp_lock.h> | ||
181 | #include <linux/string.h> | 182 | #include <linux/string.h> |
182 | #include <linux/jiffies.h> | 183 | #include <linux/jiffies.h> |
183 | #include <linux/fcntl.h> | 184 | #include <linux/fcntl.h> |
@@ -514,8 +515,6 @@ static unsigned long fdc_busy; | |||
514 | static DECLARE_WAIT_QUEUE_HEAD(fdc_wait); | 515 | static DECLARE_WAIT_QUEUE_HEAD(fdc_wait); |
515 | static DECLARE_WAIT_QUEUE_HEAD(command_done); | 516 | static DECLARE_WAIT_QUEUE_HEAD(command_done); |
516 | 517 | ||
517 | #define NO_SIGNAL (!interruptible || !signal_pending(current)) | ||
518 | |||
519 | /* Errors during formatting are counted here. */ | 518 | /* Errors during formatting are counted here. */ |
520 | static int format_errors; | 519 | static int format_errors; |
521 | 520 | ||
@@ -539,7 +538,7 @@ static int max_buffer_sectors; | |||
539 | 538 | ||
540 | static int *errors; | 539 | static int *errors; |
541 | typedef void (*done_f)(int); | 540 | typedef void (*done_f)(int); |
542 | static struct cont_t { | 541 | static const struct cont_t { |
543 | void (*interrupt)(void); | 542 | void (*interrupt)(void); |
544 | /* this is called after the interrupt of the | 543 | /* this is called after the interrupt of the |
545 | * main command */ | 544 | * main command */ |
@@ -578,7 +577,7 @@ static void reset_fdc(void); | |||
578 | #define NEED_1_RECAL -2 | 577 | #define NEED_1_RECAL -2 |
579 | #define NEED_2_RECAL -3 | 578 | #define NEED_2_RECAL -3 |
580 | 579 | ||
581 | static int usage_count; | 580 | static atomic_t usage_count = ATOMIC_INIT(0); |
582 | 581 | ||
583 | /* buffer related variables */ | 582 | /* buffer related variables */ |
584 | static int buffer_track = -1; | 583 | static int buffer_track = -1; |
@@ -858,36 +857,15 @@ static void set_fdc(int drive) | |||
858 | } | 857 | } |
859 | 858 | ||
860 | /* locks the driver */ | 859 | /* locks the driver */ |
861 | static int _lock_fdc(int drive, bool interruptible, int line) | 860 | static int lock_fdc(int drive, bool interruptible) |
862 | { | 861 | { |
863 | if (!usage_count) { | 862 | if (WARN(atomic_read(&usage_count) == 0, |
864 | pr_err("Trying to lock fdc while usage count=0 at line %d\n", | 863 | "Trying to lock fdc while usage count=0\n")) |
865 | line); | ||
866 | return -1; | 864 | return -1; |
867 | } | ||
868 | |||
869 | if (test_and_set_bit(0, &fdc_busy)) { | ||
870 | DECLARE_WAITQUEUE(wait, current); | ||
871 | add_wait_queue(&fdc_wait, &wait); | ||
872 | |||
873 | for (;;) { | ||
874 | set_current_state(TASK_INTERRUPTIBLE); | ||
875 | |||
876 | if (!test_and_set_bit(0, &fdc_busy)) | ||
877 | break; | ||
878 | 865 | ||
879 | schedule(); | 866 | if (wait_event_interruptible(fdc_wait, !test_and_set_bit(0, &fdc_busy))) |
880 | 867 | return -EINTR; | |
881 | if (!NO_SIGNAL) { | ||
882 | remove_wait_queue(&fdc_wait, &wait); | ||
883 | return -EINTR; | ||
884 | } | ||
885 | } | ||
886 | 868 | ||
887 | set_current_state(TASK_RUNNING); | ||
888 | remove_wait_queue(&fdc_wait, &wait); | ||
889 | flush_scheduled_work(); | ||
890 | } | ||
891 | command_status = FD_COMMAND_NONE; | 869 | command_status = FD_COMMAND_NONE; |
892 | 870 | ||
893 | __reschedule_timeout(drive, "lock fdc"); | 871 | __reschedule_timeout(drive, "lock fdc"); |
@@ -895,11 +873,8 @@ static int _lock_fdc(int drive, bool interruptible, int line) | |||
895 | return 0; | 873 | return 0; |
896 | } | 874 | } |
897 | 875 | ||
898 | #define lock_fdc(drive, interruptible) \ | ||
899 | _lock_fdc(drive, interruptible, __LINE__) | ||
900 | |||
901 | /* unlocks the driver */ | 876 | /* unlocks the driver */ |
902 | static inline void unlock_fdc(void) | 877 | static void unlock_fdc(void) |
903 | { | 878 | { |
904 | unsigned long flags; | 879 | unsigned long flags; |
905 | 880 | ||
@@ -1224,7 +1199,7 @@ static int need_more_output(void) | |||
1224 | /* Set perpendicular mode as required, based on data rate, if supported. | 1199 | /* Set perpendicular mode as required, based on data rate, if supported. |
1225 | * 82077 Now tested. 1Mbps data rate only possible with 82077-1. | 1200 | * 82077 Now tested. 1Mbps data rate only possible with 82077-1. |
1226 | */ | 1201 | */ |
1227 | static inline void perpendicular_mode(void) | 1202 | static void perpendicular_mode(void) |
1228 | { | 1203 | { |
1229 | unsigned char perp_mode; | 1204 | unsigned char perp_mode; |
1230 | 1205 | ||
@@ -1995,14 +1970,14 @@ static void do_wakeup(void) | |||
1995 | wake_up(&command_done); | 1970 | wake_up(&command_done); |
1996 | } | 1971 | } |
1997 | 1972 | ||
1998 | static struct cont_t wakeup_cont = { | 1973 | static const struct cont_t wakeup_cont = { |
1999 | .interrupt = empty, | 1974 | .interrupt = empty, |
2000 | .redo = do_wakeup, | 1975 | .redo = do_wakeup, |
2001 | .error = empty, | 1976 | .error = empty, |
2002 | .done = (done_f)empty | 1977 | .done = (done_f)empty |
2003 | }; | 1978 | }; |
2004 | 1979 | ||
2005 | static struct cont_t intr_cont = { | 1980 | static const struct cont_t intr_cont = { |
2006 | .interrupt = empty, | 1981 | .interrupt = empty, |
2007 | .redo = process_fd_request, | 1982 | .redo = process_fd_request, |
2008 | .error = empty, | 1983 | .error = empty, |
@@ -2015,25 +1990,10 @@ static int wait_til_done(void (*handler)(void), bool interruptible) | |||
2015 | 1990 | ||
2016 | schedule_bh(handler); | 1991 | schedule_bh(handler); |
2017 | 1992 | ||
2018 | if (command_status < 2 && NO_SIGNAL) { | 1993 | if (interruptible) |
2019 | DECLARE_WAITQUEUE(wait, current); | 1994 | wait_event_interruptible(command_done, command_status >= 2); |
2020 | 1995 | else | |
2021 | add_wait_queue(&command_done, &wait); | 1996 | wait_event(command_done, command_status >= 2); |
2022 | for (;;) { | ||
2023 | set_current_state(interruptible ? | ||
2024 | TASK_INTERRUPTIBLE : | ||
2025 | TASK_UNINTERRUPTIBLE); | ||
2026 | |||
2027 | if (command_status >= 2 || !NO_SIGNAL) | ||
2028 | break; | ||
2029 | |||
2030 | is_alive(__func__, ""); | ||
2031 | schedule(); | ||
2032 | } | ||
2033 | |||
2034 | set_current_state(TASK_RUNNING); | ||
2035 | remove_wait_queue(&command_done, &wait); | ||
2036 | } | ||
2037 | 1997 | ||
2038 | if (command_status < 2) { | 1998 | if (command_status < 2) { |
2039 | cancel_activity(); | 1999 | cancel_activity(); |
@@ -2223,7 +2183,7 @@ static void redo_format(void) | |||
2223 | debugt(__func__, "queue format request"); | 2183 | debugt(__func__, "queue format request"); |
2224 | } | 2184 | } |
2225 | 2185 | ||
2226 | static struct cont_t format_cont = { | 2186 | static const struct cont_t format_cont = { |
2227 | .interrupt = format_interrupt, | 2187 | .interrupt = format_interrupt, |
2228 | .redo = redo_format, | 2188 | .redo = redo_format, |
2229 | .error = bad_flp_intr, | 2189 | .error = bad_flp_intr, |
@@ -2583,10 +2543,8 @@ static int make_raw_rw_request(void) | |||
2583 | int tracksize; | 2543 | int tracksize; |
2584 | int ssize; | 2544 | int ssize; |
2585 | 2545 | ||
2586 | if (max_buffer_sectors == 0) { | 2546 | if (WARN(max_buffer_sectors == 0, "VFS: Block I/O scheduled on unopened device\n")) |
2587 | pr_info("VFS: Block I/O scheduled on unopened device\n"); | ||
2588 | return 0; | 2547 | return 0; |
2589 | } | ||
2590 | 2548 | ||
2591 | set_fdc((long)current_req->rq_disk->private_data); | 2549 | set_fdc((long)current_req->rq_disk->private_data); |
2592 | 2550 | ||
@@ -2921,7 +2879,7 @@ do_request: | |||
2921 | return; | 2879 | return; |
2922 | } | 2880 | } |
2923 | 2881 | ||
2924 | static struct cont_t rw_cont = { | 2882 | static const struct cont_t rw_cont = { |
2925 | .interrupt = rw_interrupt, | 2883 | .interrupt = rw_interrupt, |
2926 | .redo = redo_fd_request, | 2884 | .redo = redo_fd_request, |
2927 | .error = bad_flp_intr, | 2885 | .error = bad_flp_intr, |
@@ -2936,19 +2894,16 @@ static void process_fd_request(void) | |||
2936 | 2894 | ||
2937 | static void do_fd_request(struct request_queue *q) | 2895 | static void do_fd_request(struct request_queue *q) |
2938 | { | 2896 | { |
2939 | if (max_buffer_sectors == 0) { | 2897 | if (WARN(max_buffer_sectors == 0, |
2940 | pr_info("VFS: %s called on non-open device\n", __func__); | 2898 | "VFS: %s called on non-open device\n", __func__)) |
2941 | return; | 2899 | return; |
2942 | } | ||
2943 | 2900 | ||
2944 | if (usage_count == 0) { | 2901 | if (WARN(atomic_read(&usage_count) == 0, |
2945 | pr_info("warning: usage count=0, current_req=%p exiting\n", | 2902 | "warning: usage count=0, current_req=%p sect=%ld type=%x flags=%x\n", |
2946 | current_req); | 2903 | current_req, (long)blk_rq_pos(current_req), current_req->cmd_type, |
2947 | pr_info("sect=%ld type=%x flags=%x\n", | 2904 | current_req->cmd_flags)) |
2948 | (long)blk_rq_pos(current_req), current_req->cmd_type, | ||
2949 | current_req->cmd_flags); | ||
2950 | return; | 2905 | return; |
2951 | } | 2906 | |
2952 | if (test_bit(0, &fdc_busy)) { | 2907 | if (test_bit(0, &fdc_busy)) { |
2953 | /* fdc busy, this new request will be treated when the | 2908 | /* fdc busy, this new request will be treated when the |
2954 | current one is done */ | 2909 | current one is done */ |
@@ -2960,7 +2915,7 @@ static void do_fd_request(struct request_queue *q) | |||
2960 | is_alive(__func__, ""); | 2915 | is_alive(__func__, ""); |
2961 | } | 2916 | } |
2962 | 2917 | ||
2963 | static struct cont_t poll_cont = { | 2918 | static const struct cont_t poll_cont = { |
2964 | .interrupt = success_and_wakeup, | 2919 | .interrupt = success_and_wakeup, |
2965 | .redo = floppy_ready, | 2920 | .redo = floppy_ready, |
2966 | .error = generic_failure, | 2921 | .error = generic_failure, |
@@ -2991,7 +2946,7 @@ static void reset_intr(void) | |||
2991 | pr_info("weird, reset interrupt called\n"); | 2946 | pr_info("weird, reset interrupt called\n"); |
2992 | } | 2947 | } |
2993 | 2948 | ||
2994 | static struct cont_t reset_cont = { | 2949 | static const struct cont_t reset_cont = { |
2995 | .interrupt = reset_intr, | 2950 | .interrupt = reset_intr, |
2996 | .redo = success_and_wakeup, | 2951 | .redo = success_and_wakeup, |
2997 | .error = generic_failure, | 2952 | .error = generic_failure, |
@@ -3033,7 +2988,7 @@ static inline int fd_copyin(void __user *param, void *address, | |||
3033 | return copy_from_user(address, param, size) ? -EFAULT : 0; | 2988 | return copy_from_user(address, param, size) ? -EFAULT : 0; |
3034 | } | 2989 | } |
3035 | 2990 | ||
3036 | static inline const char *drive_name(int type, int drive) | 2991 | static const char *drive_name(int type, int drive) |
3037 | { | 2992 | { |
3038 | struct floppy_struct *floppy; | 2993 | struct floppy_struct *floppy; |
3039 | 2994 | ||
@@ -3096,14 +3051,14 @@ static void raw_cmd_done(int flag) | |||
3096 | generic_done(flag); | 3051 | generic_done(flag); |
3097 | } | 3052 | } |
3098 | 3053 | ||
3099 | static struct cont_t raw_cmd_cont = { | 3054 | static const struct cont_t raw_cmd_cont = { |
3100 | .interrupt = success_and_wakeup, | 3055 | .interrupt = success_and_wakeup, |
3101 | .redo = floppy_start, | 3056 | .redo = floppy_start, |
3102 | .error = generic_failure, | 3057 | .error = generic_failure, |
3103 | .done = raw_cmd_done | 3058 | .done = raw_cmd_done |
3104 | }; | 3059 | }; |
3105 | 3060 | ||
3106 | static inline int raw_cmd_copyout(int cmd, void __user *param, | 3061 | static int raw_cmd_copyout(int cmd, void __user *param, |
3107 | struct floppy_raw_cmd *ptr) | 3062 | struct floppy_raw_cmd *ptr) |
3108 | { | 3063 | { |
3109 | int ret; | 3064 | int ret; |
@@ -3148,7 +3103,7 @@ static void raw_cmd_free(struct floppy_raw_cmd **ptr) | |||
3148 | } | 3103 | } |
3149 | } | 3104 | } |
3150 | 3105 | ||
3151 | static inline int raw_cmd_copyin(int cmd, void __user *param, | 3106 | static int raw_cmd_copyin(int cmd, void __user *param, |
3152 | struct floppy_raw_cmd **rcmd) | 3107 | struct floppy_raw_cmd **rcmd) |
3153 | { | 3108 | { |
3154 | struct floppy_raw_cmd *ptr; | 3109 | struct floppy_raw_cmd *ptr; |
@@ -3266,7 +3221,7 @@ static int invalidate_drive(struct block_device *bdev) | |||
3266 | return 0; | 3221 | return 0; |
3267 | } | 3222 | } |
3268 | 3223 | ||
3269 | static inline int set_geometry(unsigned int cmd, struct floppy_struct *g, | 3224 | static int set_geometry(unsigned int cmd, struct floppy_struct *g, |
3270 | int drive, int type, struct block_device *bdev) | 3225 | int drive, int type, struct block_device *bdev) |
3271 | { | 3226 | { |
3272 | int cnt; | 3227 | int cnt; |
@@ -3337,7 +3292,7 @@ static inline int set_geometry(unsigned int cmd, struct floppy_struct *g, | |||
3337 | } | 3292 | } |
3338 | 3293 | ||
3339 | /* handle obsolete ioctl's */ | 3294 | /* handle obsolete ioctl's */ |
3340 | static int ioctl_table[] = { | 3295 | static unsigned int ioctl_table[] = { |
3341 | FDCLRPRM, | 3296 | FDCLRPRM, |
3342 | FDSETPRM, | 3297 | FDSETPRM, |
3343 | FDDEFPRM, | 3298 | FDDEFPRM, |
@@ -3365,7 +3320,7 @@ static int ioctl_table[] = { | |||
3365 | FDTWADDLE | 3320 | FDTWADDLE |
3366 | }; | 3321 | }; |
3367 | 3322 | ||
3368 | static inline int normalize_ioctl(int *cmd, int *size) | 3323 | static int normalize_ioctl(unsigned int *cmd, int *size) |
3369 | { | 3324 | { |
3370 | int i; | 3325 | int i; |
3371 | 3326 | ||
@@ -3417,7 +3372,7 @@ static int fd_getgeo(struct block_device *bdev, struct hd_geometry *geo) | |||
3417 | return 0; | 3372 | return 0; |
3418 | } | 3373 | } |
3419 | 3374 | ||
3420 | static int fd_ioctl(struct block_device *bdev, fmode_t mode, unsigned int cmd, | 3375 | static int fd_locked_ioctl(struct block_device *bdev, fmode_t mode, unsigned int cmd, |
3421 | unsigned long param) | 3376 | unsigned long param) |
3422 | { | 3377 | { |
3423 | int drive = (long)bdev->bd_disk->private_data; | 3378 | int drive = (long)bdev->bd_disk->private_data; |
@@ -3593,6 +3548,18 @@ static int fd_ioctl(struct block_device *bdev, fmode_t mode, unsigned int cmd, | |||
3593 | return 0; | 3548 | return 0; |
3594 | } | 3549 | } |
3595 | 3550 | ||
3551 | static int fd_ioctl(struct block_device *bdev, fmode_t mode, | ||
3552 | unsigned int cmd, unsigned long param) | ||
3553 | { | ||
3554 | int ret; | ||
3555 | |||
3556 | lock_kernel(); | ||
3557 | ret = fd_locked_ioctl(bdev, mode, cmd, param); | ||
3558 | unlock_kernel(); | ||
3559 | |||
3560 | return ret; | ||
3561 | } | ||
3562 | |||
3596 | static void __init config_types(void) | 3563 | static void __init config_types(void) |
3597 | { | 3564 | { |
3598 | bool has_drive = false; | 3565 | bool has_drive = false; |
@@ -3649,6 +3616,7 @@ static int floppy_release(struct gendisk *disk, fmode_t mode) | |||
3649 | { | 3616 | { |
3650 | int drive = (long)disk->private_data; | 3617 | int drive = (long)disk->private_data; |
3651 | 3618 | ||
3619 | lock_kernel(); | ||
3652 | mutex_lock(&open_lock); | 3620 | mutex_lock(&open_lock); |
3653 | if (UDRS->fd_ref < 0) | 3621 | if (UDRS->fd_ref < 0) |
3654 | UDRS->fd_ref = 0; | 3622 | UDRS->fd_ref = 0; |
@@ -3659,6 +3627,7 @@ static int floppy_release(struct gendisk *disk, fmode_t mode) | |||
3659 | if (!UDRS->fd_ref) | 3627 | if (!UDRS->fd_ref) |
3660 | opened_bdev[drive] = NULL; | 3628 | opened_bdev[drive] = NULL; |
3661 | mutex_unlock(&open_lock); | 3629 | mutex_unlock(&open_lock); |
3630 | unlock_kernel(); | ||
3662 | 3631 | ||
3663 | return 0; | 3632 | return 0; |
3664 | } | 3633 | } |
@@ -3676,6 +3645,7 @@ static int floppy_open(struct block_device *bdev, fmode_t mode) | |||
3676 | int res = -EBUSY; | 3645 | int res = -EBUSY; |
3677 | char *tmp; | 3646 | char *tmp; |
3678 | 3647 | ||
3648 | lock_kernel(); | ||
3679 | mutex_lock(&open_lock); | 3649 | mutex_lock(&open_lock); |
3680 | old_dev = UDRS->fd_device; | 3650 | old_dev = UDRS->fd_device; |
3681 | if (opened_bdev[drive] && opened_bdev[drive] != bdev) | 3651 | if (opened_bdev[drive] && opened_bdev[drive] != bdev) |
@@ -3752,6 +3722,7 @@ static int floppy_open(struct block_device *bdev, fmode_t mode) | |||
3752 | goto out; | 3722 | goto out; |
3753 | } | 3723 | } |
3754 | mutex_unlock(&open_lock); | 3724 | mutex_unlock(&open_lock); |
3725 | unlock_kernel(); | ||
3755 | return 0; | 3726 | return 0; |
3756 | out: | 3727 | out: |
3757 | if (UDRS->fd_ref < 0) | 3728 | if (UDRS->fd_ref < 0) |
@@ -3762,6 +3733,7 @@ out: | |||
3762 | opened_bdev[drive] = NULL; | 3733 | opened_bdev[drive] = NULL; |
3763 | out2: | 3734 | out2: |
3764 | mutex_unlock(&open_lock); | 3735 | mutex_unlock(&open_lock); |
3736 | unlock_kernel(); | ||
3765 | return res; | 3737 | return res; |
3766 | } | 3738 | } |
3767 | 3739 | ||
@@ -3829,6 +3801,7 @@ static int __floppy_read_block_0(struct block_device *bdev) | |||
3829 | bio.bi_size = size; | 3801 | bio.bi_size = size; |
3830 | bio.bi_bdev = bdev; | 3802 | bio.bi_bdev = bdev; |
3831 | bio.bi_sector = 0; | 3803 | bio.bi_sector = 0; |
3804 | bio.bi_flags = BIO_QUIET; | ||
3832 | init_completion(&complete); | 3805 | init_completion(&complete); |
3833 | bio.bi_private = &complete; | 3806 | bio.bi_private = &complete; |
3834 | bio.bi_end_io = floppy_rb0_complete; | 3807 | bio.bi_end_io = floppy_rb0_complete; |
@@ -3857,10 +3830,10 @@ static int floppy_revalidate(struct gendisk *disk) | |||
3857 | if (test_bit(FD_DISK_CHANGED_BIT, &UDRS->flags) || | 3830 | if (test_bit(FD_DISK_CHANGED_BIT, &UDRS->flags) || |
3858 | test_bit(FD_VERIFY_BIT, &UDRS->flags) || | 3831 | test_bit(FD_VERIFY_BIT, &UDRS->flags) || |
3859 | test_bit(drive, &fake_change) || NO_GEOM) { | 3832 | test_bit(drive, &fake_change) || NO_GEOM) { |
3860 | if (usage_count == 0) { | 3833 | if (WARN(atomic_read(&usage_count) == 0, |
3861 | pr_info("VFS: revalidate called on non-open device.\n"); | 3834 | "VFS: revalidate called on non-open device.\n")) |
3862 | return -EFAULT; | 3835 | return -EFAULT; |
3863 | } | 3836 | |
3864 | lock_fdc(drive, false); | 3837 | lock_fdc(drive, false); |
3865 | cf = (test_bit(FD_DISK_CHANGED_BIT, &UDRS->flags) || | 3838 | cf = (test_bit(FD_DISK_CHANGED_BIT, &UDRS->flags) || |
3866 | test_bit(FD_VERIFY_BIT, &UDRS->flags)); | 3839 | test_bit(FD_VERIFY_BIT, &UDRS->flags)); |
@@ -3893,7 +3866,7 @@ static const struct block_device_operations floppy_fops = { | |||
3893 | .owner = THIS_MODULE, | 3866 | .owner = THIS_MODULE, |
3894 | .open = floppy_open, | 3867 | .open = floppy_open, |
3895 | .release = floppy_release, | 3868 | .release = floppy_release, |
3896 | .locked_ioctl = fd_ioctl, | 3869 | .ioctl = fd_ioctl, |
3897 | .getgeo = fd_getgeo, | 3870 | .getgeo = fd_getgeo, |
3898 | .media_changed = check_floppy_change, | 3871 | .media_changed = check_floppy_change, |
3899 | .revalidate_disk = floppy_revalidate, | 3872 | .revalidate_disk = floppy_revalidate, |
@@ -4126,7 +4099,7 @@ static ssize_t floppy_cmos_show(struct device *dev, | |||
4126 | return sprintf(buf, "%X\n", UDP->cmos); | 4099 | return sprintf(buf, "%X\n", UDP->cmos); |
4127 | } | 4100 | } |
4128 | 4101 | ||
4129 | DEVICE_ATTR(cmos, S_IRUGO, floppy_cmos_show, NULL); | 4102 | static DEVICE_ATTR(cmos, S_IRUGO, floppy_cmos_show, NULL); |
4130 | 4103 | ||
4131 | static void floppy_device_release(struct device *dev) | 4104 | static void floppy_device_release(struct device *dev) |
4132 | { | 4105 | { |
@@ -4175,6 +4148,9 @@ static int __init floppy_init(void) | |||
4175 | int i, unit, drive; | 4148 | int i, unit, drive; |
4176 | int err, dr; | 4149 | int err, dr; |
4177 | 4150 | ||
4151 | set_debugt(); | ||
4152 | interruptjiffies = resultjiffies = jiffies; | ||
4153 | |||
4178 | #if defined(CONFIG_PPC) | 4154 | #if defined(CONFIG_PPC) |
4179 | if (check_legacy_ioport(FDC1)) | 4155 | if (check_legacy_ioport(FDC1)) |
4180 | return -ENODEV; | 4156 | return -ENODEV; |
@@ -4353,7 +4329,7 @@ out_unreg_platform_dev: | |||
4353 | platform_device_unregister(&floppy_device[drive]); | 4329 | platform_device_unregister(&floppy_device[drive]); |
4354 | out_flush_work: | 4330 | out_flush_work: |
4355 | flush_scheduled_work(); | 4331 | flush_scheduled_work(); |
4356 | if (usage_count) | 4332 | if (atomic_read(&usage_count)) |
4357 | floppy_release_irq_and_dma(); | 4333 | floppy_release_irq_and_dma(); |
4358 | out_unreg_region: | 4334 | out_unreg_region: |
4359 | blk_unregister_region(MKDEV(FLOPPY_MAJOR, 0), 256); | 4335 | blk_unregister_region(MKDEV(FLOPPY_MAJOR, 0), 256); |
@@ -4370,8 +4346,6 @@ out_put_disk: | |||
4370 | return err; | 4346 | return err; |
4371 | } | 4347 | } |
4372 | 4348 | ||
4373 | static DEFINE_SPINLOCK(floppy_usage_lock); | ||
4374 | |||
4375 | static const struct io_region { | 4349 | static const struct io_region { |
4376 | int offset; | 4350 | int offset; |
4377 | int size; | 4351 | int size; |
@@ -4417,14 +4391,8 @@ static void floppy_release_regions(int fdc) | |||
4417 | 4391 | ||
4418 | static int floppy_grab_irq_and_dma(void) | 4392 | static int floppy_grab_irq_and_dma(void) |
4419 | { | 4393 | { |
4420 | unsigned long flags; | 4394 | if (atomic_inc_return(&usage_count) > 1) |
4421 | |||
4422 | spin_lock_irqsave(&floppy_usage_lock, flags); | ||
4423 | if (usage_count++) { | ||
4424 | spin_unlock_irqrestore(&floppy_usage_lock, flags); | ||
4425 | return 0; | 4395 | return 0; |
4426 | } | ||
4427 | spin_unlock_irqrestore(&floppy_usage_lock, flags); | ||
4428 | 4396 | ||
4429 | /* | 4397 | /* |
4430 | * We might have scheduled a free_irq(), wait it to | 4398 | * We might have scheduled a free_irq(), wait it to |
@@ -4435,9 +4403,7 @@ static int floppy_grab_irq_and_dma(void) | |||
4435 | if (fd_request_irq()) { | 4403 | if (fd_request_irq()) { |
4436 | DPRINT("Unable to grab IRQ%d for the floppy driver\n", | 4404 | DPRINT("Unable to grab IRQ%d for the floppy driver\n", |
4437 | FLOPPY_IRQ); | 4405 | FLOPPY_IRQ); |
4438 | spin_lock_irqsave(&floppy_usage_lock, flags); | 4406 | atomic_dec(&usage_count); |
4439 | usage_count--; | ||
4440 | spin_unlock_irqrestore(&floppy_usage_lock, flags); | ||
4441 | return -1; | 4407 | return -1; |
4442 | } | 4408 | } |
4443 | if (fd_request_dma()) { | 4409 | if (fd_request_dma()) { |
@@ -4447,9 +4413,7 @@ static int floppy_grab_irq_and_dma(void) | |||
4447 | use_virtual_dma = can_use_virtual_dma = 1; | 4413 | use_virtual_dma = can_use_virtual_dma = 1; |
4448 | if (!(can_use_virtual_dma & 1)) { | 4414 | if (!(can_use_virtual_dma & 1)) { |
4449 | fd_free_irq(); | 4415 | fd_free_irq(); |
4450 | spin_lock_irqsave(&floppy_usage_lock, flags); | 4416 | atomic_dec(&usage_count); |
4451 | usage_count--; | ||
4452 | spin_unlock_irqrestore(&floppy_usage_lock, flags); | ||
4453 | return -1; | 4417 | return -1; |
4454 | } | 4418 | } |
4455 | } | 4419 | } |
@@ -4484,9 +4448,7 @@ cleanup: | |||
4484 | fd_free_dma(); | 4448 | fd_free_dma(); |
4485 | while (--fdc >= 0) | 4449 | while (--fdc >= 0) |
4486 | floppy_release_regions(fdc); | 4450 | floppy_release_regions(fdc); |
4487 | spin_lock_irqsave(&floppy_usage_lock, flags); | 4451 | atomic_dec(&usage_count); |
4488 | usage_count--; | ||
4489 | spin_unlock_irqrestore(&floppy_usage_lock, flags); | ||
4490 | return -1; | 4452 | return -1; |
4491 | } | 4453 | } |
4492 | 4454 | ||
@@ -4498,14 +4460,10 @@ static void floppy_release_irq_and_dma(void) | |||
4498 | #endif | 4460 | #endif |
4499 | long tmpsize; | 4461 | long tmpsize; |
4500 | unsigned long tmpaddr; | 4462 | unsigned long tmpaddr; |
4501 | unsigned long flags; | ||
4502 | 4463 | ||
4503 | spin_lock_irqsave(&floppy_usage_lock, flags); | 4464 | if (!atomic_dec_and_test(&usage_count)) |
4504 | if (--usage_count) { | ||
4505 | spin_unlock_irqrestore(&floppy_usage_lock, flags); | ||
4506 | return; | 4465 | return; |
4507 | } | 4466 | |
4508 | spin_unlock_irqrestore(&floppy_usage_lock, flags); | ||
4509 | if (irqdma_allocated) { | 4467 | if (irqdma_allocated) { |
4510 | fd_disable_dma(); | 4468 | fd_disable_dma(); |
4511 | fd_free_dma(); | 4469 | fd_free_dma(); |
@@ -4598,7 +4556,7 @@ static void __exit floppy_module_exit(void) | |||
4598 | del_timer_sync(&fd_timer); | 4556 | del_timer_sync(&fd_timer); |
4599 | blk_cleanup_queue(floppy_queue); | 4557 | blk_cleanup_queue(floppy_queue); |
4600 | 4558 | ||
4601 | if (usage_count) | 4559 | if (atomic_read(&usage_count)) |
4602 | floppy_release_irq_and_dma(); | 4560 | floppy_release_irq_and_dma(); |
4603 | 4561 | ||
4604 | /* eject disk, if any */ | 4562 | /* eject disk, if any */ |
diff --git a/drivers/block/hd.c b/drivers/block/hd.c index 81c78b3ce2df..30ec6b37424e 100644 --- a/drivers/block/hd.c +++ b/drivers/block/hd.c | |||
@@ -627,7 +627,7 @@ repeat: | |||
627 | req_data_dir(req) == READ ? "read" : "writ", | 627 | req_data_dir(req) == READ ? "read" : "writ", |
628 | cyl, head, sec, nsect, req->buffer); | 628 | cyl, head, sec, nsect, req->buffer); |
629 | #endif | 629 | #endif |
630 | if (blk_fs_request(req)) { | 630 | if (req->cmd_type == REQ_TYPE_FS) { |
631 | switch (rq_data_dir(req)) { | 631 | switch (rq_data_dir(req)) { |
632 | case READ: | 632 | case READ: |
633 | hd_out(disk, nsect, sec, head, cyl, ATA_CMD_PIO_READ, | 633 | hd_out(disk, nsect, sec, head, cyl, ATA_CMD_PIO_READ, |
diff --git a/drivers/block/loop.c b/drivers/block/loop.c index 6120922f459f..f3c636d23718 100644 --- a/drivers/block/loop.c +++ b/drivers/block/loop.c | |||
@@ -67,6 +67,7 @@ | |||
67 | #include <linux/compat.h> | 67 | #include <linux/compat.h> |
68 | #include <linux/suspend.h> | 68 | #include <linux/suspend.h> |
69 | #include <linux/freezer.h> | 69 | #include <linux/freezer.h> |
70 | #include <linux/smp_lock.h> | ||
70 | #include <linux/writeback.h> | 71 | #include <linux/writeback.h> |
71 | #include <linux/buffer_head.h> /* for invalidate_bdev() */ | 72 | #include <linux/buffer_head.h> /* for invalidate_bdev() */ |
72 | #include <linux/completion.h> | 73 | #include <linux/completion.h> |
@@ -476,7 +477,7 @@ static int do_bio_filebacked(struct loop_device *lo, struct bio *bio) | |||
476 | pos = ((loff_t) bio->bi_sector << 9) + lo->lo_offset; | 477 | pos = ((loff_t) bio->bi_sector << 9) + lo->lo_offset; |
477 | 478 | ||
478 | if (bio_rw(bio) == WRITE) { | 479 | if (bio_rw(bio) == WRITE) { |
479 | bool barrier = bio_rw_flagged(bio, BIO_RW_BARRIER); | 480 | bool barrier = (bio->bi_rw & REQ_HARDBARRIER); |
480 | struct file *file = lo->lo_backing_file; | 481 | struct file *file = lo->lo_backing_file; |
481 | 482 | ||
482 | if (barrier) { | 483 | if (barrier) { |
@@ -831,7 +832,7 @@ static int loop_set_fd(struct loop_device *lo, fmode_t mode, | |||
831 | lo->lo_queue->unplug_fn = loop_unplug; | 832 | lo->lo_queue->unplug_fn = loop_unplug; |
832 | 833 | ||
833 | if (!(lo_flags & LO_FLAGS_READ_ONLY) && file->f_op->fsync) | 834 | if (!(lo_flags & LO_FLAGS_READ_ONLY) && file->f_op->fsync) |
834 | blk_queue_ordered(lo->lo_queue, QUEUE_ORDERED_DRAIN, NULL); | 835 | blk_queue_ordered(lo->lo_queue, QUEUE_ORDERED_DRAIN); |
835 | 836 | ||
836 | set_capacity(lo->lo_disk, size); | 837 | set_capacity(lo->lo_disk, size); |
837 | bd_set_size(bdev, size << 9); | 838 | bd_set_size(bdev, size << 9); |
@@ -1408,9 +1409,11 @@ static int lo_open(struct block_device *bdev, fmode_t mode) | |||
1408 | { | 1409 | { |
1409 | struct loop_device *lo = bdev->bd_disk->private_data; | 1410 | struct loop_device *lo = bdev->bd_disk->private_data; |
1410 | 1411 | ||
1412 | lock_kernel(); | ||
1411 | mutex_lock(&lo->lo_ctl_mutex); | 1413 | mutex_lock(&lo->lo_ctl_mutex); |
1412 | lo->lo_refcnt++; | 1414 | lo->lo_refcnt++; |
1413 | mutex_unlock(&lo->lo_ctl_mutex); | 1415 | mutex_unlock(&lo->lo_ctl_mutex); |
1416 | unlock_kernel(); | ||
1414 | 1417 | ||
1415 | return 0; | 1418 | return 0; |
1416 | } | 1419 | } |
@@ -1420,6 +1423,7 @@ static int lo_release(struct gendisk *disk, fmode_t mode) | |||
1420 | struct loop_device *lo = disk->private_data; | 1423 | struct loop_device *lo = disk->private_data; |
1421 | int err; | 1424 | int err; |
1422 | 1425 | ||
1426 | lock_kernel(); | ||
1423 | mutex_lock(&lo->lo_ctl_mutex); | 1427 | mutex_lock(&lo->lo_ctl_mutex); |
1424 | 1428 | ||
1425 | if (--lo->lo_refcnt) | 1429 | if (--lo->lo_refcnt) |
@@ -1444,6 +1448,7 @@ static int lo_release(struct gendisk *disk, fmode_t mode) | |||
1444 | out: | 1448 | out: |
1445 | mutex_unlock(&lo->lo_ctl_mutex); | 1449 | mutex_unlock(&lo->lo_ctl_mutex); |
1446 | out_unlocked: | 1450 | out_unlocked: |
1451 | lock_kernel(); | ||
1447 | return 0; | 1452 | return 0; |
1448 | } | 1453 | } |
1449 | 1454 | ||
diff --git a/drivers/block/mg_disk.c b/drivers/block/mg_disk.c index 28db925dbdad..b82c5ce5e9df 100644 --- a/drivers/block/mg_disk.c +++ b/drivers/block/mg_disk.c | |||
@@ -670,7 +670,7 @@ static void mg_request_poll(struct request_queue *q) | |||
670 | break; | 670 | break; |
671 | } | 671 | } |
672 | 672 | ||
673 | if (unlikely(!blk_fs_request(host->req))) { | 673 | if (unlikely(host->req->cmd_type != REQ_TYPE_FS)) { |
674 | mg_end_request_cur(host, -EIO); | 674 | mg_end_request_cur(host, -EIO); |
675 | continue; | 675 | continue; |
676 | } | 676 | } |
@@ -756,7 +756,7 @@ static void mg_request(struct request_queue *q) | |||
756 | continue; | 756 | continue; |
757 | } | 757 | } |
758 | 758 | ||
759 | if (unlikely(!blk_fs_request(req))) { | 759 | if (unlikely(req->cmd_type != REQ_TYPE_FS)) { |
760 | mg_end_request_cur(host, -EIO); | 760 | mg_end_request_cur(host, -EIO); |
761 | continue; | 761 | continue; |
762 | } | 762 | } |
diff --git a/drivers/block/nbd.c b/drivers/block/nbd.c index 16c3c8613cd3..0daa422aa281 100644 --- a/drivers/block/nbd.c +++ b/drivers/block/nbd.c | |||
@@ -24,6 +24,7 @@ | |||
24 | #include <linux/errno.h> | 24 | #include <linux/errno.h> |
25 | #include <linux/file.h> | 25 | #include <linux/file.h> |
26 | #include <linux/ioctl.h> | 26 | #include <linux/ioctl.h> |
27 | #include <linux/smp_lock.h> | ||
27 | #include <linux/compiler.h> | 28 | #include <linux/compiler.h> |
28 | #include <linux/err.h> | 29 | #include <linux/err.h> |
29 | #include <linux/kernel.h> | 30 | #include <linux/kernel.h> |
@@ -448,7 +449,7 @@ static void nbd_clear_que(struct nbd_device *lo) | |||
448 | 449 | ||
449 | static void nbd_handle_req(struct nbd_device *lo, struct request *req) | 450 | static void nbd_handle_req(struct nbd_device *lo, struct request *req) |
450 | { | 451 | { |
451 | if (!blk_fs_request(req)) | 452 | if (req->cmd_type != REQ_TYPE_FS) |
452 | goto error_out; | 453 | goto error_out; |
453 | 454 | ||
454 | nbd_cmd(req) = NBD_CMD_READ; | 455 | nbd_cmd(req) = NBD_CMD_READ; |
@@ -716,9 +717,11 @@ static int nbd_ioctl(struct block_device *bdev, fmode_t mode, | |||
716 | dprintk(DBG_IOCTL, "%s: nbd_ioctl cmd=%s(0x%x) arg=%lu\n", | 717 | dprintk(DBG_IOCTL, "%s: nbd_ioctl cmd=%s(0x%x) arg=%lu\n", |
717 | lo->disk->disk_name, ioctl_cmd_to_ascii(cmd), cmd, arg); | 718 | lo->disk->disk_name, ioctl_cmd_to_ascii(cmd), cmd, arg); |
718 | 719 | ||
720 | lock_kernel(); | ||
719 | mutex_lock(&lo->tx_lock); | 721 | mutex_lock(&lo->tx_lock); |
720 | error = __nbd_ioctl(bdev, lo, cmd, arg); | 722 | error = __nbd_ioctl(bdev, lo, cmd, arg); |
721 | mutex_unlock(&lo->tx_lock); | 723 | mutex_unlock(&lo->tx_lock); |
724 | unlock_kernel(); | ||
722 | 725 | ||
723 | return error; | 726 | return error; |
724 | } | 727 | } |
@@ -726,7 +729,7 @@ static int nbd_ioctl(struct block_device *bdev, fmode_t mode, | |||
726 | static const struct block_device_operations nbd_fops = | 729 | static const struct block_device_operations nbd_fops = |
727 | { | 730 | { |
728 | .owner = THIS_MODULE, | 731 | .owner = THIS_MODULE, |
729 | .locked_ioctl = nbd_ioctl, | 732 | .ioctl = nbd_ioctl, |
730 | }; | 733 | }; |
731 | 734 | ||
732 | /* | 735 | /* |
diff --git a/drivers/block/osdblk.c b/drivers/block/osdblk.c index 6cd8b705b11b..2284b4f05c62 100644 --- a/drivers/block/osdblk.c +++ b/drivers/block/osdblk.c | |||
@@ -310,7 +310,8 @@ static void osdblk_rq_fn(struct request_queue *q) | |||
310 | break; | 310 | break; |
311 | 311 | ||
312 | /* filter out block requests we don't understand */ | 312 | /* filter out block requests we don't understand */ |
313 | if (!blk_fs_request(rq) && !blk_barrier_rq(rq)) { | 313 | if (rq->cmd_type != REQ_TYPE_FS && |
314 | !(rq->cmd_flags & REQ_HARDBARRIER)) { | ||
314 | blk_end_request_all(rq, 0); | 315 | blk_end_request_all(rq, 0); |
315 | continue; | 316 | continue; |
316 | } | 317 | } |
@@ -322,7 +323,7 @@ static void osdblk_rq_fn(struct request_queue *q) | |||
322 | * driver-specific, etc. | 323 | * driver-specific, etc. |
323 | */ | 324 | */ |
324 | 325 | ||
325 | do_flush = (rq->special == (void *) 0xdeadbeefUL); | 326 | do_flush = rq->cmd_flags & REQ_FLUSH; |
326 | do_write = (rq_data_dir(rq) == WRITE); | 327 | do_write = (rq_data_dir(rq) == WRITE); |
327 | 328 | ||
328 | if (!do_flush) { /* osd_flush does not use a bio */ | 329 | if (!do_flush) { /* osd_flush does not use a bio */ |
@@ -379,14 +380,6 @@ static void osdblk_rq_fn(struct request_queue *q) | |||
379 | } | 380 | } |
380 | } | 381 | } |
381 | 382 | ||
382 | static void osdblk_prepare_flush(struct request_queue *q, struct request *rq) | ||
383 | { | ||
384 | /* add driver-specific marker, to indicate that this request | ||
385 | * is a flush command | ||
386 | */ | ||
387 | rq->special = (void *) 0xdeadbeefUL; | ||
388 | } | ||
389 | |||
390 | static void osdblk_free_disk(struct osdblk_device *osdev) | 383 | static void osdblk_free_disk(struct osdblk_device *osdev) |
391 | { | 384 | { |
392 | struct gendisk *disk = osdev->disk; | 385 | struct gendisk *disk = osdev->disk; |
@@ -446,7 +439,7 @@ static int osdblk_init_disk(struct osdblk_device *osdev) | |||
446 | blk_queue_stack_limits(q, osd_request_queue(osdev->osd)); | 439 | blk_queue_stack_limits(q, osd_request_queue(osdev->osd)); |
447 | 440 | ||
448 | blk_queue_prep_rq(q, blk_queue_start_tag); | 441 | blk_queue_prep_rq(q, blk_queue_start_tag); |
449 | blk_queue_ordered(q, QUEUE_ORDERED_DRAIN_FLUSH, osdblk_prepare_flush); | 442 | blk_queue_ordered(q, QUEUE_ORDERED_DRAIN_FLUSH); |
450 | 443 | ||
451 | disk->queue = q; | 444 | disk->queue = q; |
452 | 445 | ||
diff --git a/drivers/block/paride/pcd.c b/drivers/block/paride/pcd.c index 71acf4e53356..76f8565e1e8d 100644 --- a/drivers/block/paride/pcd.c +++ b/drivers/block/paride/pcd.c | |||
@@ -138,6 +138,7 @@ enum {D_PRT, D_PRO, D_UNI, D_MOD, D_SLV, D_DLY}; | |||
138 | #include <linux/cdrom.h> | 138 | #include <linux/cdrom.h> |
139 | #include <linux/spinlock.h> | 139 | #include <linux/spinlock.h> |
140 | #include <linux/blkdev.h> | 140 | #include <linux/blkdev.h> |
141 | #include <linux/smp_lock.h> | ||
141 | #include <asm/uaccess.h> | 142 | #include <asm/uaccess.h> |
142 | 143 | ||
143 | static DEFINE_SPINLOCK(pcd_lock); | 144 | static DEFINE_SPINLOCK(pcd_lock); |
@@ -224,13 +225,21 @@ static char *pcd_buf; /* buffer for request in progress */ | |||
224 | static int pcd_block_open(struct block_device *bdev, fmode_t mode) | 225 | static int pcd_block_open(struct block_device *bdev, fmode_t mode) |
225 | { | 226 | { |
226 | struct pcd_unit *cd = bdev->bd_disk->private_data; | 227 | struct pcd_unit *cd = bdev->bd_disk->private_data; |
227 | return cdrom_open(&cd->info, bdev, mode); | 228 | int ret; |
229 | |||
230 | lock_kernel(); | ||
231 | ret = cdrom_open(&cd->info, bdev, mode); | ||
232 | unlock_kernel(); | ||
233 | |||
234 | return ret; | ||
228 | } | 235 | } |
229 | 236 | ||
230 | static int pcd_block_release(struct gendisk *disk, fmode_t mode) | 237 | static int pcd_block_release(struct gendisk *disk, fmode_t mode) |
231 | { | 238 | { |
232 | struct pcd_unit *cd = disk->private_data; | 239 | struct pcd_unit *cd = disk->private_data; |
240 | lock_kernel(); | ||
233 | cdrom_release(&cd->info, mode); | 241 | cdrom_release(&cd->info, mode); |
242 | unlock_kernel(); | ||
234 | return 0; | 243 | return 0; |
235 | } | 244 | } |
236 | 245 | ||
@@ -238,7 +247,13 @@ static int pcd_block_ioctl(struct block_device *bdev, fmode_t mode, | |||
238 | unsigned cmd, unsigned long arg) | 247 | unsigned cmd, unsigned long arg) |
239 | { | 248 | { |
240 | struct pcd_unit *cd = bdev->bd_disk->private_data; | 249 | struct pcd_unit *cd = bdev->bd_disk->private_data; |
241 | return cdrom_ioctl(&cd->info, bdev, mode, cmd, arg); | 250 | int ret; |
251 | |||
252 | lock_kernel(); | ||
253 | ret = cdrom_ioctl(&cd->info, bdev, mode, cmd, arg); | ||
254 | unlock_kernel(); | ||
255 | |||
256 | return ret; | ||
242 | } | 257 | } |
243 | 258 | ||
244 | static int pcd_block_media_changed(struct gendisk *disk) | 259 | static int pcd_block_media_changed(struct gendisk *disk) |
@@ -251,7 +266,7 @@ static const struct block_device_operations pcd_bdops = { | |||
251 | .owner = THIS_MODULE, | 266 | .owner = THIS_MODULE, |
252 | .open = pcd_block_open, | 267 | .open = pcd_block_open, |
253 | .release = pcd_block_release, | 268 | .release = pcd_block_release, |
254 | .locked_ioctl = pcd_block_ioctl, | 269 | .ioctl = pcd_block_ioctl, |
255 | .media_changed = pcd_block_media_changed, | 270 | .media_changed = pcd_block_media_changed, |
256 | }; | 271 | }; |
257 | 272 | ||
diff --git a/drivers/block/paride/pd.c b/drivers/block/paride/pd.c index c1e5cd029b23..985f0d4f1d1e 100644 --- a/drivers/block/paride/pd.c +++ b/drivers/block/paride/pd.c | |||
@@ -153,6 +153,7 @@ enum {D_PRT, D_PRO, D_UNI, D_MOD, D_GEO, D_SBY, D_DLY, D_SLV}; | |||
153 | #include <linux/blkdev.h> | 153 | #include <linux/blkdev.h> |
154 | #include <linux/blkpg.h> | 154 | #include <linux/blkpg.h> |
155 | #include <linux/kernel.h> | 155 | #include <linux/kernel.h> |
156 | #include <linux/smp_lock.h> | ||
156 | #include <asm/uaccess.h> | 157 | #include <asm/uaccess.h> |
157 | #include <linux/workqueue.h> | 158 | #include <linux/workqueue.h> |
158 | 159 | ||
@@ -439,7 +440,7 @@ static char *pd_buf; /* buffer for request in progress */ | |||
439 | 440 | ||
440 | static enum action do_pd_io_start(void) | 441 | static enum action do_pd_io_start(void) |
441 | { | 442 | { |
442 | if (blk_special_request(pd_req)) { | 443 | if (pd_req->cmd_type == REQ_TYPE_SPECIAL) { |
443 | phase = pd_special; | 444 | phase = pd_special; |
444 | return pd_special(); | 445 | return pd_special(); |
445 | } | 446 | } |
@@ -735,12 +736,14 @@ static int pd_open(struct block_device *bdev, fmode_t mode) | |||
735 | { | 736 | { |
736 | struct pd_unit *disk = bdev->bd_disk->private_data; | 737 | struct pd_unit *disk = bdev->bd_disk->private_data; |
737 | 738 | ||
739 | lock_kernel(); | ||
738 | disk->access++; | 740 | disk->access++; |
739 | 741 | ||
740 | if (disk->removable) { | 742 | if (disk->removable) { |
741 | pd_special_command(disk, pd_media_check); | 743 | pd_special_command(disk, pd_media_check); |
742 | pd_special_command(disk, pd_door_lock); | 744 | pd_special_command(disk, pd_door_lock); |
743 | } | 745 | } |
746 | unlock_kernel(); | ||
744 | return 0; | 747 | return 0; |
745 | } | 748 | } |
746 | 749 | ||
@@ -768,8 +771,10 @@ static int pd_ioctl(struct block_device *bdev, fmode_t mode, | |||
768 | 771 | ||
769 | switch (cmd) { | 772 | switch (cmd) { |
770 | case CDROMEJECT: | 773 | case CDROMEJECT: |
774 | lock_kernel(); | ||
771 | if (disk->access == 1) | 775 | if (disk->access == 1) |
772 | pd_special_command(disk, pd_eject); | 776 | pd_special_command(disk, pd_eject); |
777 | unlock_kernel(); | ||
773 | return 0; | 778 | return 0; |
774 | default: | 779 | default: |
775 | return -EINVAL; | 780 | return -EINVAL; |
@@ -780,8 +785,10 @@ static int pd_release(struct gendisk *p, fmode_t mode) | |||
780 | { | 785 | { |
781 | struct pd_unit *disk = p->private_data; | 786 | struct pd_unit *disk = p->private_data; |
782 | 787 | ||
788 | lock_kernel(); | ||
783 | if (!--disk->access && disk->removable) | 789 | if (!--disk->access && disk->removable) |
784 | pd_special_command(disk, pd_door_unlock); | 790 | pd_special_command(disk, pd_door_unlock); |
791 | unlock_kernel(); | ||
785 | 792 | ||
786 | return 0; | 793 | return 0; |
787 | } | 794 | } |
@@ -812,7 +819,7 @@ static const struct block_device_operations pd_fops = { | |||
812 | .owner = THIS_MODULE, | 819 | .owner = THIS_MODULE, |
813 | .open = pd_open, | 820 | .open = pd_open, |
814 | .release = pd_release, | 821 | .release = pd_release, |
815 | .locked_ioctl = pd_ioctl, | 822 | .ioctl = pd_ioctl, |
816 | .getgeo = pd_getgeo, | 823 | .getgeo = pd_getgeo, |
817 | .media_changed = pd_check_media, | 824 | .media_changed = pd_check_media, |
818 | .revalidate_disk= pd_revalidate | 825 | .revalidate_disk= pd_revalidate |
diff --git a/drivers/block/paride/pf.c b/drivers/block/paride/pf.c index c059aab3006b..4457b494882a 100644 --- a/drivers/block/paride/pf.c +++ b/drivers/block/paride/pf.c | |||
@@ -152,6 +152,7 @@ enum {D_PRT, D_PRO, D_UNI, D_MOD, D_SLV, D_LUN, D_DLY}; | |||
152 | #include <linux/spinlock.h> | 152 | #include <linux/spinlock.h> |
153 | #include <linux/blkdev.h> | 153 | #include <linux/blkdev.h> |
154 | #include <linux/blkpg.h> | 154 | #include <linux/blkpg.h> |
155 | #include <linux/smp_lock.h> | ||
155 | #include <asm/uaccess.h> | 156 | #include <asm/uaccess.h> |
156 | 157 | ||
157 | static DEFINE_SPINLOCK(pf_spin_lock); | 158 | static DEFINE_SPINLOCK(pf_spin_lock); |
@@ -266,7 +267,7 @@ static const struct block_device_operations pf_fops = { | |||
266 | .owner = THIS_MODULE, | 267 | .owner = THIS_MODULE, |
267 | .open = pf_open, | 268 | .open = pf_open, |
268 | .release = pf_release, | 269 | .release = pf_release, |
269 | .locked_ioctl = pf_ioctl, | 270 | .ioctl = pf_ioctl, |
270 | .getgeo = pf_getgeo, | 271 | .getgeo = pf_getgeo, |
271 | .media_changed = pf_check_media, | 272 | .media_changed = pf_check_media, |
272 | }; | 273 | }; |
@@ -299,20 +300,26 @@ static void __init pf_init_units(void) | |||
299 | static int pf_open(struct block_device *bdev, fmode_t mode) | 300 | static int pf_open(struct block_device *bdev, fmode_t mode) |
300 | { | 301 | { |
301 | struct pf_unit *pf = bdev->bd_disk->private_data; | 302 | struct pf_unit *pf = bdev->bd_disk->private_data; |
303 | int ret; | ||
302 | 304 | ||
305 | lock_kernel(); | ||
303 | pf_identify(pf); | 306 | pf_identify(pf); |
304 | 307 | ||
308 | ret = -ENODEV; | ||
305 | if (pf->media_status == PF_NM) | 309 | if (pf->media_status == PF_NM) |
306 | return -ENODEV; | 310 | goto out; |
307 | 311 | ||
312 | ret = -EROFS; | ||
308 | if ((pf->media_status == PF_RO) && (mode & FMODE_WRITE)) | 313 | if ((pf->media_status == PF_RO) && (mode & FMODE_WRITE)) |
309 | return -EROFS; | 314 | goto out; |
310 | 315 | ||
316 | ret = 0; | ||
311 | pf->access++; | 317 | pf->access++; |
312 | if (pf->removable) | 318 | if (pf->removable) |
313 | pf_lock(pf, 1); | 319 | pf_lock(pf, 1); |
314 | 320 | out: | |
315 | return 0; | 321 | unlock_kernel(); |
322 | return ret; | ||
316 | } | 323 | } |
317 | 324 | ||
318 | static int pf_getgeo(struct block_device *bdev, struct hd_geometry *geo) | 325 | static int pf_getgeo(struct block_device *bdev, struct hd_geometry *geo) |
@@ -342,7 +349,10 @@ static int pf_ioctl(struct block_device *bdev, fmode_t mode, unsigned int cmd, u | |||
342 | 349 | ||
343 | if (pf->access != 1) | 350 | if (pf->access != 1) |
344 | return -EBUSY; | 351 | return -EBUSY; |
352 | lock_kernel(); | ||
345 | pf_eject(pf); | 353 | pf_eject(pf); |
354 | unlock_kernel(); | ||
355 | |||
346 | return 0; | 356 | return 0; |
347 | } | 357 | } |
348 | 358 | ||
@@ -350,14 +360,18 @@ static int pf_release(struct gendisk *disk, fmode_t mode) | |||
350 | { | 360 | { |
351 | struct pf_unit *pf = disk->private_data; | 361 | struct pf_unit *pf = disk->private_data; |
352 | 362 | ||
353 | if (pf->access <= 0) | 363 | lock_kernel(); |
364 | if (pf->access <= 0) { | ||
365 | unlock_kernel(); | ||
354 | return -EINVAL; | 366 | return -EINVAL; |
367 | } | ||
355 | 368 | ||
356 | pf->access--; | 369 | pf->access--; |
357 | 370 | ||
358 | if (!pf->access && pf->removable) | 371 | if (!pf->access && pf->removable) |
359 | pf_lock(pf, 0); | 372 | pf_lock(pf, 0); |
360 | 373 | ||
374 | unlock_kernel(); | ||
361 | return 0; | 375 | return 0; |
362 | 376 | ||
363 | } | 377 | } |
diff --git a/drivers/block/pktcdvd.c b/drivers/block/pktcdvd.c index 8a549db2aa78..b1cbeb59bb76 100644 --- a/drivers/block/pktcdvd.c +++ b/drivers/block/pktcdvd.c | |||
@@ -57,6 +57,7 @@ | |||
57 | #include <linux/seq_file.h> | 57 | #include <linux/seq_file.h> |
58 | #include <linux/miscdevice.h> | 58 | #include <linux/miscdevice.h> |
59 | #include <linux/freezer.h> | 59 | #include <linux/freezer.h> |
60 | #include <linux/smp_lock.h> | ||
60 | #include <linux/mutex.h> | 61 | #include <linux/mutex.h> |
61 | #include <linux/slab.h> | 62 | #include <linux/slab.h> |
62 | #include <scsi/scsi_cmnd.h> | 63 | #include <scsi/scsi_cmnd.h> |
@@ -1221,7 +1222,7 @@ static int pkt_start_recovery(struct packet_data *pkt) | |||
1221 | pkt->bio->bi_flags = 1 << BIO_UPTODATE; | 1222 | pkt->bio->bi_flags = 1 << BIO_UPTODATE; |
1222 | pkt->bio->bi_idx = 0; | 1223 | pkt->bio->bi_idx = 0; |
1223 | 1224 | ||
1224 | BUG_ON(pkt->bio->bi_rw != (1 << BIO_RW)); | 1225 | BUG_ON(pkt->bio->bi_rw != REQ_WRITE); |
1225 | BUG_ON(pkt->bio->bi_vcnt != pkt->frames); | 1226 | BUG_ON(pkt->bio->bi_vcnt != pkt->frames); |
1226 | BUG_ON(pkt->bio->bi_size != pkt->frames * CD_FRAMESIZE); | 1227 | BUG_ON(pkt->bio->bi_size != pkt->frames * CD_FRAMESIZE); |
1227 | BUG_ON(pkt->bio->bi_end_io != pkt_end_io_packet_write); | 1228 | BUG_ON(pkt->bio->bi_end_io != pkt_end_io_packet_write); |
@@ -2382,6 +2383,7 @@ static int pkt_open(struct block_device *bdev, fmode_t mode) | |||
2382 | 2383 | ||
2383 | VPRINTK(DRIVER_NAME": entering open\n"); | 2384 | VPRINTK(DRIVER_NAME": entering open\n"); |
2384 | 2385 | ||
2386 | lock_kernel(); | ||
2385 | mutex_lock(&ctl_mutex); | 2387 | mutex_lock(&ctl_mutex); |
2386 | pd = pkt_find_dev_from_minor(MINOR(bdev->bd_dev)); | 2388 | pd = pkt_find_dev_from_minor(MINOR(bdev->bd_dev)); |
2387 | if (!pd) { | 2389 | if (!pd) { |
@@ -2409,6 +2411,7 @@ static int pkt_open(struct block_device *bdev, fmode_t mode) | |||
2409 | } | 2411 | } |
2410 | 2412 | ||
2411 | mutex_unlock(&ctl_mutex); | 2413 | mutex_unlock(&ctl_mutex); |
2414 | unlock_kernel(); | ||
2412 | return 0; | 2415 | return 0; |
2413 | 2416 | ||
2414 | out_dec: | 2417 | out_dec: |
@@ -2416,6 +2419,7 @@ out_dec: | |||
2416 | out: | 2419 | out: |
2417 | VPRINTK(DRIVER_NAME": failed open (%d)\n", ret); | 2420 | VPRINTK(DRIVER_NAME": failed open (%d)\n", ret); |
2418 | mutex_unlock(&ctl_mutex); | 2421 | mutex_unlock(&ctl_mutex); |
2422 | unlock_kernel(); | ||
2419 | return ret; | 2423 | return ret; |
2420 | } | 2424 | } |
2421 | 2425 | ||
@@ -2424,6 +2428,7 @@ static int pkt_close(struct gendisk *disk, fmode_t mode) | |||
2424 | struct pktcdvd_device *pd = disk->private_data; | 2428 | struct pktcdvd_device *pd = disk->private_data; |
2425 | int ret = 0; | 2429 | int ret = 0; |
2426 | 2430 | ||
2431 | lock_kernel(); | ||
2427 | mutex_lock(&ctl_mutex); | 2432 | mutex_lock(&ctl_mutex); |
2428 | pd->refcnt--; | 2433 | pd->refcnt--; |
2429 | BUG_ON(pd->refcnt < 0); | 2434 | BUG_ON(pd->refcnt < 0); |
@@ -2432,6 +2437,7 @@ static int pkt_close(struct gendisk *disk, fmode_t mode) | |||
2432 | pkt_release_dev(pd, flush); | 2437 | pkt_release_dev(pd, flush); |
2433 | } | 2438 | } |
2434 | mutex_unlock(&ctl_mutex); | 2439 | mutex_unlock(&ctl_mutex); |
2440 | unlock_kernel(); | ||
2435 | return ret; | 2441 | return ret; |
2436 | } | 2442 | } |
2437 | 2443 | ||
@@ -2762,10 +2768,12 @@ out_mem: | |||
2762 | static int pkt_ioctl(struct block_device *bdev, fmode_t mode, unsigned int cmd, unsigned long arg) | 2768 | static int pkt_ioctl(struct block_device *bdev, fmode_t mode, unsigned int cmd, unsigned long arg) |
2763 | { | 2769 | { |
2764 | struct pktcdvd_device *pd = bdev->bd_disk->private_data; | 2770 | struct pktcdvd_device *pd = bdev->bd_disk->private_data; |
2771 | int ret; | ||
2765 | 2772 | ||
2766 | VPRINTK("pkt_ioctl: cmd %x, dev %d:%d\n", cmd, | 2773 | VPRINTK("pkt_ioctl: cmd %x, dev %d:%d\n", cmd, |
2767 | MAJOR(bdev->bd_dev), MINOR(bdev->bd_dev)); | 2774 | MAJOR(bdev->bd_dev), MINOR(bdev->bd_dev)); |
2768 | 2775 | ||
2776 | lock_kernel(); | ||
2769 | switch (cmd) { | 2777 | switch (cmd) { |
2770 | case CDROMEJECT: | 2778 | case CDROMEJECT: |
2771 | /* | 2779 | /* |
@@ -2783,14 +2791,16 @@ static int pkt_ioctl(struct block_device *bdev, fmode_t mode, unsigned int cmd, | |||
2783 | case CDROM_LAST_WRITTEN: | 2791 | case CDROM_LAST_WRITTEN: |
2784 | case CDROM_SEND_PACKET: | 2792 | case CDROM_SEND_PACKET: |
2785 | case SCSI_IOCTL_SEND_COMMAND: | 2793 | case SCSI_IOCTL_SEND_COMMAND: |
2786 | return __blkdev_driver_ioctl(pd->bdev, mode, cmd, arg); | 2794 | ret = __blkdev_driver_ioctl(pd->bdev, mode, cmd, arg); |
2795 | break; | ||
2787 | 2796 | ||
2788 | default: | 2797 | default: |
2789 | VPRINTK(DRIVER_NAME": Unknown ioctl for %s (%x)\n", pd->name, cmd); | 2798 | VPRINTK(DRIVER_NAME": Unknown ioctl for %s (%x)\n", pd->name, cmd); |
2790 | return -ENOTTY; | 2799 | ret = -ENOTTY; |
2791 | } | 2800 | } |
2801 | unlock_kernel(); | ||
2792 | 2802 | ||
2793 | return 0; | 2803 | return ret; |
2794 | } | 2804 | } |
2795 | 2805 | ||
2796 | static int pkt_media_changed(struct gendisk *disk) | 2806 | static int pkt_media_changed(struct gendisk *disk) |
@@ -2812,7 +2822,7 @@ static const struct block_device_operations pktcdvd_ops = { | |||
2812 | .owner = THIS_MODULE, | 2822 | .owner = THIS_MODULE, |
2813 | .open = pkt_open, | 2823 | .open = pkt_open, |
2814 | .release = pkt_close, | 2824 | .release = pkt_close, |
2815 | .locked_ioctl = pkt_ioctl, | 2825 | .ioctl = pkt_ioctl, |
2816 | .media_changed = pkt_media_changed, | 2826 | .media_changed = pkt_media_changed, |
2817 | }; | 2827 | }; |
2818 | 2828 | ||
diff --git a/drivers/block/ps3disk.c b/drivers/block/ps3disk.c index 3b419e3fffa1..e9da874d0419 100644 --- a/drivers/block/ps3disk.c +++ b/drivers/block/ps3disk.c | |||
@@ -196,13 +196,12 @@ static void ps3disk_do_request(struct ps3_storage_device *dev, | |||
196 | dev_dbg(&dev->sbd.core, "%s:%u\n", __func__, __LINE__); | 196 | dev_dbg(&dev->sbd.core, "%s:%u\n", __func__, __LINE__); |
197 | 197 | ||
198 | while ((req = blk_fetch_request(q))) { | 198 | while ((req = blk_fetch_request(q))) { |
199 | if (blk_fs_request(req)) { | 199 | if (req->cmd_flags & REQ_FLUSH) { |
200 | if (ps3disk_submit_request_sg(dev, req)) | ||
201 | break; | ||
202 | } else if (req->cmd_type == REQ_TYPE_LINUX_BLOCK && | ||
203 | req->cmd[0] == REQ_LB_OP_FLUSH) { | ||
204 | if (ps3disk_submit_flush_request(dev, req)) | 200 | if (ps3disk_submit_flush_request(dev, req)) |
205 | break; | 201 | break; |
202 | } else if (req->cmd_type == REQ_TYPE_FS) { | ||
203 | if (ps3disk_submit_request_sg(dev, req)) | ||
204 | break; | ||
206 | } else { | 205 | } else { |
207 | blk_dump_rq_flags(req, DEVICE_NAME " bad request"); | 206 | blk_dump_rq_flags(req, DEVICE_NAME " bad request"); |
208 | __blk_end_request_all(req, -EIO); | 207 | __blk_end_request_all(req, -EIO); |
@@ -257,8 +256,7 @@ static irqreturn_t ps3disk_interrupt(int irq, void *data) | |||
257 | return IRQ_HANDLED; | 256 | return IRQ_HANDLED; |
258 | } | 257 | } |
259 | 258 | ||
260 | if (req->cmd_type == REQ_TYPE_LINUX_BLOCK && | 259 | if (req->cmd_flags & REQ_FLUSH) { |
261 | req->cmd[0] == REQ_LB_OP_FLUSH) { | ||
262 | read = 0; | 260 | read = 0; |
263 | op = "flush"; | 261 | op = "flush"; |
264 | } else { | 262 | } else { |
@@ -398,16 +396,6 @@ static int ps3disk_identify(struct ps3_storage_device *dev) | |||
398 | return 0; | 396 | return 0; |
399 | } | 397 | } |
400 | 398 | ||
401 | static void ps3disk_prepare_flush(struct request_queue *q, struct request *req) | ||
402 | { | ||
403 | struct ps3_storage_device *dev = q->queuedata; | ||
404 | |||
405 | dev_dbg(&dev->sbd.core, "%s:%u\n", __func__, __LINE__); | ||
406 | |||
407 | req->cmd_type = REQ_TYPE_LINUX_BLOCK; | ||
408 | req->cmd[0] = REQ_LB_OP_FLUSH; | ||
409 | } | ||
410 | |||
411 | static unsigned long ps3disk_mask; | 399 | static unsigned long ps3disk_mask; |
412 | 400 | ||
413 | static DEFINE_MUTEX(ps3disk_mask_mutex); | 401 | static DEFINE_MUTEX(ps3disk_mask_mutex); |
@@ -480,8 +468,7 @@ static int __devinit ps3disk_probe(struct ps3_system_bus_device *_dev) | |||
480 | blk_queue_dma_alignment(queue, dev->blk_size-1); | 468 | blk_queue_dma_alignment(queue, dev->blk_size-1); |
481 | blk_queue_logical_block_size(queue, dev->blk_size); | 469 | blk_queue_logical_block_size(queue, dev->blk_size); |
482 | 470 | ||
483 | blk_queue_ordered(queue, QUEUE_ORDERED_DRAIN_FLUSH, | 471 | blk_queue_ordered(queue, QUEUE_ORDERED_DRAIN_FLUSH); |
484 | ps3disk_prepare_flush); | ||
485 | 472 | ||
486 | blk_queue_max_segments(queue, -1); | 473 | blk_queue_max_segments(queue, -1); |
487 | blk_queue_max_segment_size(queue, dev->bounce_size); | 474 | blk_queue_max_segment_size(queue, dev->bounce_size); |
diff --git a/drivers/block/swim.c b/drivers/block/swim.c index e463657569ff..2e46815876df 100644 --- a/drivers/block/swim.c +++ b/drivers/block/swim.c | |||
@@ -20,6 +20,7 @@ | |||
20 | #include <linux/fd.h> | 20 | #include <linux/fd.h> |
21 | #include <linux/slab.h> | 21 | #include <linux/slab.h> |
22 | #include <linux/blkdev.h> | 22 | #include <linux/blkdev.h> |
23 | #include <linux/smp_lock.h> | ||
23 | #include <linux/hdreg.h> | 24 | #include <linux/hdreg.h> |
24 | #include <linux/kernel.h> | 25 | #include <linux/kernel.h> |
25 | #include <linux/delay.h> | 26 | #include <linux/delay.h> |
@@ -661,11 +662,23 @@ out: | |||
661 | return err; | 662 | return err; |
662 | } | 663 | } |
663 | 664 | ||
665 | static int floppy_unlocked_open(struct block_device *bdev, fmode_t mode) | ||
666 | { | ||
667 | int ret; | ||
668 | |||
669 | lock_kernel(); | ||
670 | ret = floppy_open(bdev, mode); | ||
671 | unlock_kernel(); | ||
672 | |||
673 | return ret; | ||
674 | } | ||
675 | |||
664 | static int floppy_release(struct gendisk *disk, fmode_t mode) | 676 | static int floppy_release(struct gendisk *disk, fmode_t mode) |
665 | { | 677 | { |
666 | struct floppy_state *fs = disk->private_data; | 678 | struct floppy_state *fs = disk->private_data; |
667 | struct swim __iomem *base = fs->swd->base; | 679 | struct swim __iomem *base = fs->swd->base; |
668 | 680 | ||
681 | lock_kernel(); | ||
669 | if (fs->ref_count < 0) | 682 | if (fs->ref_count < 0) |
670 | fs->ref_count = 0; | 683 | fs->ref_count = 0; |
671 | else if (fs->ref_count > 0) | 684 | else if (fs->ref_count > 0) |
@@ -673,6 +686,7 @@ static int floppy_release(struct gendisk *disk, fmode_t mode) | |||
673 | 686 | ||
674 | if (fs->ref_count == 0) | 687 | if (fs->ref_count == 0) |
675 | swim_motor(base, OFF); | 688 | swim_motor(base, OFF); |
689 | unlock_kernel(); | ||
676 | 690 | ||
677 | return 0; | 691 | return 0; |
678 | } | 692 | } |
@@ -690,7 +704,9 @@ static int floppy_ioctl(struct block_device *bdev, fmode_t mode, | |||
690 | case FDEJECT: | 704 | case FDEJECT: |
691 | if (fs->ref_count != 1) | 705 | if (fs->ref_count != 1) |
692 | return -EBUSY; | 706 | return -EBUSY; |
707 | lock_kernel(); | ||
693 | err = floppy_eject(fs); | 708 | err = floppy_eject(fs); |
709 | unlock_kernel(); | ||
694 | return err; | 710 | return err; |
695 | 711 | ||
696 | case FDGETPRM: | 712 | case FDGETPRM: |
@@ -751,9 +767,9 @@ static int floppy_revalidate(struct gendisk *disk) | |||
751 | 767 | ||
752 | static const struct block_device_operations floppy_fops = { | 768 | static const struct block_device_operations floppy_fops = { |
753 | .owner = THIS_MODULE, | 769 | .owner = THIS_MODULE, |
754 | .open = floppy_open, | 770 | .open = floppy_unlocked_open, |
755 | .release = floppy_release, | 771 | .release = floppy_release, |
756 | .locked_ioctl = floppy_ioctl, | 772 | .ioctl = floppy_ioctl, |
757 | .getgeo = floppy_getgeo, | 773 | .getgeo = floppy_getgeo, |
758 | .media_changed = floppy_check_change, | 774 | .media_changed = floppy_check_change, |
759 | .revalidate_disk = floppy_revalidate, | 775 | .revalidate_disk = floppy_revalidate, |
diff --git a/drivers/block/swim3.c b/drivers/block/swim3.c index ed6fb91123ab..cc6a3864822c 100644 --- a/drivers/block/swim3.c +++ b/drivers/block/swim3.c | |||
@@ -25,6 +25,7 @@ | |||
25 | #include <linux/ioctl.h> | 25 | #include <linux/ioctl.h> |
26 | #include <linux/blkdev.h> | 26 | #include <linux/blkdev.h> |
27 | #include <linux/interrupt.h> | 27 | #include <linux/interrupt.h> |
28 | #include <linux/smp_lock.h> | ||
28 | #include <linux/module.h> | 29 | #include <linux/module.h> |
29 | #include <linux/spinlock.h> | 30 | #include <linux/spinlock.h> |
30 | #include <asm/io.h> | 31 | #include <asm/io.h> |
@@ -839,7 +840,7 @@ static int fd_eject(struct floppy_state *fs) | |||
839 | static struct floppy_struct floppy_type = | 840 | static struct floppy_struct floppy_type = |
840 | { 2880,18,2,80,0,0x1B,0x00,0xCF,0x6C,NULL }; /* 7 1.44MB 3.5" */ | 841 | { 2880,18,2,80,0,0x1B,0x00,0xCF,0x6C,NULL }; /* 7 1.44MB 3.5" */ |
841 | 842 | ||
842 | static int floppy_ioctl(struct block_device *bdev, fmode_t mode, | 843 | static int floppy_locked_ioctl(struct block_device *bdev, fmode_t mode, |
843 | unsigned int cmd, unsigned long param) | 844 | unsigned int cmd, unsigned long param) |
844 | { | 845 | { |
845 | struct floppy_state *fs = bdev->bd_disk->private_data; | 846 | struct floppy_state *fs = bdev->bd_disk->private_data; |
@@ -867,6 +868,18 @@ static int floppy_ioctl(struct block_device *bdev, fmode_t mode, | |||
867 | return -ENOTTY; | 868 | return -ENOTTY; |
868 | } | 869 | } |
869 | 870 | ||
871 | static int floppy_ioctl(struct block_device *bdev, fmode_t mode, | ||
872 | unsigned int cmd, unsigned long param) | ||
873 | { | ||
874 | int ret; | ||
875 | |||
876 | lock_kernel(); | ||
877 | ret = floppy_locked_ioctl(bdev, mode, cmd, param); | ||
878 | unlock_kernel(); | ||
879 | |||
880 | return ret; | ||
881 | } | ||
882 | |||
870 | static int floppy_open(struct block_device *bdev, fmode_t mode) | 883 | static int floppy_open(struct block_device *bdev, fmode_t mode) |
871 | { | 884 | { |
872 | struct floppy_state *fs = bdev->bd_disk->private_data; | 885 | struct floppy_state *fs = bdev->bd_disk->private_data; |
@@ -936,15 +949,28 @@ static int floppy_open(struct block_device *bdev, fmode_t mode) | |||
936 | return 0; | 949 | return 0; |
937 | } | 950 | } |
938 | 951 | ||
952 | static int floppy_unlocked_open(struct block_device *bdev, fmode_t mode) | ||
953 | { | ||
954 | int ret; | ||
955 | |||
956 | lock_kernel(); | ||
957 | ret = floppy_open(bdev, mode); | ||
958 | unlock_kernel(); | ||
959 | |||
960 | return ret; | ||
961 | } | ||
962 | |||
939 | static int floppy_release(struct gendisk *disk, fmode_t mode) | 963 | static int floppy_release(struct gendisk *disk, fmode_t mode) |
940 | { | 964 | { |
941 | struct floppy_state *fs = disk->private_data; | 965 | struct floppy_state *fs = disk->private_data; |
942 | struct swim3 __iomem *sw = fs->swim3; | 966 | struct swim3 __iomem *sw = fs->swim3; |
967 | lock_kernel(); | ||
943 | if (fs->ref_count > 0 && --fs->ref_count == 0) { | 968 | if (fs->ref_count > 0 && --fs->ref_count == 0) { |
944 | swim3_action(fs, MOTOR_OFF); | 969 | swim3_action(fs, MOTOR_OFF); |
945 | out_8(&sw->control_bic, 0xff); | 970 | out_8(&sw->control_bic, 0xff); |
946 | swim3_select(fs, RELAX); | 971 | swim3_select(fs, RELAX); |
947 | } | 972 | } |
973 | unlock_kernel(); | ||
948 | return 0; | 974 | return 0; |
949 | } | 975 | } |
950 | 976 | ||
@@ -995,9 +1021,9 @@ static int floppy_revalidate(struct gendisk *disk) | |||
995 | } | 1021 | } |
996 | 1022 | ||
997 | static const struct block_device_operations floppy_fops = { | 1023 | static const struct block_device_operations floppy_fops = { |
998 | .open = floppy_open, | 1024 | .open = floppy_unlocked_open, |
999 | .release = floppy_release, | 1025 | .release = floppy_release, |
1000 | .locked_ioctl = floppy_ioctl, | 1026 | .ioctl = floppy_ioctl, |
1001 | .media_changed = floppy_check_change, | 1027 | .media_changed = floppy_check_change, |
1002 | .revalidate_disk= floppy_revalidate, | 1028 | .revalidate_disk= floppy_revalidate, |
1003 | }; | 1029 | }; |
diff --git a/drivers/block/ub.c b/drivers/block/ub.c index 0536b5b29adc..c48e14878582 100644 --- a/drivers/block/ub.c +++ b/drivers/block/ub.c | |||
@@ -28,6 +28,7 @@ | |||
28 | #include <linux/timer.h> | 28 | #include <linux/timer.h> |
29 | #include <linux/scatterlist.h> | 29 | #include <linux/scatterlist.h> |
30 | #include <linux/slab.h> | 30 | #include <linux/slab.h> |
31 | #include <linux/smp_lock.h> | ||
31 | #include <scsi/scsi.h> | 32 | #include <scsi/scsi.h> |
32 | 33 | ||
33 | #define DRV_NAME "ub" | 34 | #define DRV_NAME "ub" |
@@ -648,7 +649,7 @@ static int ub_request_fn_1(struct ub_lun *lun, struct request *rq) | |||
648 | return 0; | 649 | return 0; |
649 | } | 650 | } |
650 | 651 | ||
651 | if (lun->changed && !blk_pc_request(rq)) { | 652 | if (lun->changed && rq->cmd_type != REQ_TYPE_BLOCK_PC) { |
652 | blk_start_request(rq); | 653 | blk_start_request(rq); |
653 | ub_end_rq(rq, SAM_STAT_CHECK_CONDITION); | 654 | ub_end_rq(rq, SAM_STAT_CHECK_CONDITION); |
654 | return 0; | 655 | return 0; |
@@ -684,7 +685,7 @@ static int ub_request_fn_1(struct ub_lun *lun, struct request *rq) | |||
684 | } | 685 | } |
685 | urq->nsg = n_elem; | 686 | urq->nsg = n_elem; |
686 | 687 | ||
687 | if (blk_pc_request(rq)) { | 688 | if (rq->cmd_type == REQ_TYPE_BLOCK_PC) { |
688 | ub_cmd_build_packet(sc, lun, cmd, urq); | 689 | ub_cmd_build_packet(sc, lun, cmd, urq); |
689 | } else { | 690 | } else { |
690 | ub_cmd_build_block(sc, lun, cmd, urq); | 691 | ub_cmd_build_block(sc, lun, cmd, urq); |
@@ -781,7 +782,7 @@ static void ub_rw_cmd_done(struct ub_dev *sc, struct ub_scsi_cmd *cmd) | |||
781 | rq = urq->rq; | 782 | rq = urq->rq; |
782 | 783 | ||
783 | if (cmd->error == 0) { | 784 | if (cmd->error == 0) { |
784 | if (blk_pc_request(rq)) { | 785 | if (rq->cmd_type == REQ_TYPE_BLOCK_PC) { |
785 | if (cmd->act_len >= rq->resid_len) | 786 | if (cmd->act_len >= rq->resid_len) |
786 | rq->resid_len = 0; | 787 | rq->resid_len = 0; |
787 | else | 788 | else |
@@ -795,7 +796,7 @@ static void ub_rw_cmd_done(struct ub_dev *sc, struct ub_scsi_cmd *cmd) | |||
795 | } | 796 | } |
796 | } | 797 | } |
797 | } else { | 798 | } else { |
798 | if (blk_pc_request(rq)) { | 799 | if (rq->cmd_type == REQ_TYPE_BLOCK_PC) { |
799 | /* UB_SENSE_SIZE is smaller than SCSI_SENSE_BUFFERSIZE */ | 800 | /* UB_SENSE_SIZE is smaller than SCSI_SENSE_BUFFERSIZE */ |
800 | memcpy(rq->sense, sc->top_sense, UB_SENSE_SIZE); | 801 | memcpy(rq->sense, sc->top_sense, UB_SENSE_SIZE); |
801 | rq->sense_len = UB_SENSE_SIZE; | 802 | rq->sense_len = UB_SENSE_SIZE; |
@@ -1710,6 +1711,18 @@ err_open: | |||
1710 | return rc; | 1711 | return rc; |
1711 | } | 1712 | } |
1712 | 1713 | ||
1714 | static int ub_bd_unlocked_open(struct block_device *bdev, fmode_t mode) | ||
1715 | { | ||
1716 | int ret; | ||
1717 | |||
1718 | lock_kernel(); | ||
1719 | ret = ub_bd_open(bdev, mode); | ||
1720 | unlock_kernel(); | ||
1721 | |||
1722 | return ret; | ||
1723 | } | ||
1724 | |||
1725 | |||
1713 | /* | 1726 | /* |
1714 | */ | 1727 | */ |
1715 | static int ub_bd_release(struct gendisk *disk, fmode_t mode) | 1728 | static int ub_bd_release(struct gendisk *disk, fmode_t mode) |
@@ -1717,7 +1730,10 @@ static int ub_bd_release(struct gendisk *disk, fmode_t mode) | |||
1717 | struct ub_lun *lun = disk->private_data; | 1730 | struct ub_lun *lun = disk->private_data; |
1718 | struct ub_dev *sc = lun->udev; | 1731 | struct ub_dev *sc = lun->udev; |
1719 | 1732 | ||
1733 | lock_kernel(); | ||
1720 | ub_put(sc); | 1734 | ub_put(sc); |
1735 | unlock_kernel(); | ||
1736 | |||
1721 | return 0; | 1737 | return 0; |
1722 | } | 1738 | } |
1723 | 1739 | ||
@@ -1729,8 +1745,13 @@ static int ub_bd_ioctl(struct block_device *bdev, fmode_t mode, | |||
1729 | { | 1745 | { |
1730 | struct gendisk *disk = bdev->bd_disk; | 1746 | struct gendisk *disk = bdev->bd_disk; |
1731 | void __user *usermem = (void __user *) arg; | 1747 | void __user *usermem = (void __user *) arg; |
1748 | int ret; | ||
1749 | |||
1750 | lock_kernel(); | ||
1751 | ret = scsi_cmd_ioctl(disk->queue, disk, mode, cmd, usermem); | ||
1752 | unlock_kernel(); | ||
1732 | 1753 | ||
1733 | return scsi_cmd_ioctl(disk->queue, disk, mode, cmd, usermem); | 1754 | return ret; |
1734 | } | 1755 | } |
1735 | 1756 | ||
1736 | /* | 1757 | /* |
@@ -1792,9 +1813,9 @@ static int ub_bd_media_changed(struct gendisk *disk) | |||
1792 | 1813 | ||
1793 | static const struct block_device_operations ub_bd_fops = { | 1814 | static const struct block_device_operations ub_bd_fops = { |
1794 | .owner = THIS_MODULE, | 1815 | .owner = THIS_MODULE, |
1795 | .open = ub_bd_open, | 1816 | .open = ub_bd_unlocked_open, |
1796 | .release = ub_bd_release, | 1817 | .release = ub_bd_release, |
1797 | .locked_ioctl = ub_bd_ioctl, | 1818 | .ioctl = ub_bd_ioctl, |
1798 | .media_changed = ub_bd_media_changed, | 1819 | .media_changed = ub_bd_media_changed, |
1799 | .revalidate_disk = ub_bd_revalidate, | 1820 | .revalidate_disk = ub_bd_revalidate, |
1800 | }; | 1821 | }; |
diff --git a/drivers/block/umem.c b/drivers/block/umem.c index 2f9470ff8f7c..8be57151f5d6 100644 --- a/drivers/block/umem.c +++ b/drivers/block/umem.c | |||
@@ -478,7 +478,7 @@ static void process_page(unsigned long data) | |||
478 | le32_to_cpu(desc->local_addr)>>9, | 478 | le32_to_cpu(desc->local_addr)>>9, |
479 | le32_to_cpu(desc->transfer_size)); | 479 | le32_to_cpu(desc->transfer_size)); |
480 | dump_dmastat(card, control); | 480 | dump_dmastat(card, control); |
481 | } else if (test_bit(BIO_RW, &bio->bi_rw) && | 481 | } else if ((bio->bi_rw & REQ_WRITE) && |
482 | le32_to_cpu(desc->local_addr) >> 9 == | 482 | le32_to_cpu(desc->local_addr) >> 9 == |
483 | card->init_size) { | 483 | card->init_size) { |
484 | card->init_size += le32_to_cpu(desc->transfer_size) >> 9; | 484 | card->init_size += le32_to_cpu(desc->transfer_size) >> 9; |
diff --git a/drivers/block/viodasd.c b/drivers/block/viodasd.c index 788d93882ab9..f651e51a3319 100644 --- a/drivers/block/viodasd.c +++ b/drivers/block/viodasd.c | |||
@@ -41,6 +41,7 @@ | |||
41 | #include <linux/errno.h> | 41 | #include <linux/errno.h> |
42 | #include <linux/init.h> | 42 | #include <linux/init.h> |
43 | #include <linux/string.h> | 43 | #include <linux/string.h> |
44 | #include <linux/smp_lock.h> | ||
44 | #include <linux/dma-mapping.h> | 45 | #include <linux/dma-mapping.h> |
45 | #include <linux/completion.h> | 46 | #include <linux/completion.h> |
46 | #include <linux/device.h> | 47 | #include <linux/device.h> |
@@ -175,6 +176,18 @@ static int viodasd_open(struct block_device *bdev, fmode_t mode) | |||
175 | return 0; | 176 | return 0; |
176 | } | 177 | } |
177 | 178 | ||
179 | static int viodasd_unlocked_open(struct block_device *bdev, fmode_t mode) | ||
180 | { | ||
181 | int ret; | ||
182 | |||
183 | lock_kernel(); | ||
184 | ret = viodasd_open(bdev, mode); | ||
185 | unlock_kernel(); | ||
186 | |||
187 | return ret; | ||
188 | } | ||
189 | |||
190 | |||
178 | /* | 191 | /* |
179 | * External release entry point. | 192 | * External release entry point. |
180 | */ | 193 | */ |
@@ -183,6 +196,7 @@ static int viodasd_release(struct gendisk *disk, fmode_t mode) | |||
183 | struct viodasd_device *d = disk->private_data; | 196 | struct viodasd_device *d = disk->private_data; |
184 | HvLpEvent_Rc hvrc; | 197 | HvLpEvent_Rc hvrc; |
185 | 198 | ||
199 | lock_kernel(); | ||
186 | /* Send the event to OS/400. We DON'T expect a response */ | 200 | /* Send the event to OS/400. We DON'T expect a response */ |
187 | hvrc = HvCallEvent_signalLpEventFast(viopath_hostLp, | 201 | hvrc = HvCallEvent_signalLpEventFast(viopath_hostLp, |
188 | HvLpEvent_Type_VirtualIo, | 202 | HvLpEvent_Type_VirtualIo, |
@@ -195,6 +209,9 @@ static int viodasd_release(struct gendisk *disk, fmode_t mode) | |||
195 | 0, 0, 0); | 209 | 0, 0, 0); |
196 | if (hvrc != 0) | 210 | if (hvrc != 0) |
197 | pr_warning("HV close call failed %d\n", (int)hvrc); | 211 | pr_warning("HV close call failed %d\n", (int)hvrc); |
212 | |||
213 | unlock_kernel(); | ||
214 | |||
198 | return 0; | 215 | return 0; |
199 | } | 216 | } |
200 | 217 | ||
@@ -219,7 +236,7 @@ static int viodasd_getgeo(struct block_device *bdev, struct hd_geometry *geo) | |||
219 | */ | 236 | */ |
220 | static const struct block_device_operations viodasd_fops = { | 237 | static const struct block_device_operations viodasd_fops = { |
221 | .owner = THIS_MODULE, | 238 | .owner = THIS_MODULE, |
222 | .open = viodasd_open, | 239 | .open = viodasd_unlocked_open, |
223 | .release = viodasd_release, | 240 | .release = viodasd_release, |
224 | .getgeo = viodasd_getgeo, | 241 | .getgeo = viodasd_getgeo, |
225 | }; | 242 | }; |
@@ -361,7 +378,7 @@ static void do_viodasd_request(struct request_queue *q) | |||
361 | if (req == NULL) | 378 | if (req == NULL) |
362 | return; | 379 | return; |
363 | /* check that request contains a valid command */ | 380 | /* check that request contains a valid command */ |
364 | if (!blk_fs_request(req)) { | 381 | if (req->cmd_type != REQ_TYPE_FS) { |
365 | viodasd_end_request(req, -EIO, blk_rq_sectors(req)); | 382 | viodasd_end_request(req, -EIO, blk_rq_sectors(req)); |
366 | continue; | 383 | continue; |
367 | } | 384 | } |
diff --git a/drivers/block/virtio_blk.c b/drivers/block/virtio_blk.c index 23b7c48df843..2aafafca2b13 100644 --- a/drivers/block/virtio_blk.c +++ b/drivers/block/virtio_blk.c | |||
@@ -2,6 +2,7 @@ | |||
2 | #include <linux/spinlock.h> | 2 | #include <linux/spinlock.h> |
3 | #include <linux/slab.h> | 3 | #include <linux/slab.h> |
4 | #include <linux/blkdev.h> | 4 | #include <linux/blkdev.h> |
5 | #include <linux/smp_lock.h> | ||
5 | #include <linux/hdreg.h> | 6 | #include <linux/hdreg.h> |
6 | #include <linux/virtio.h> | 7 | #include <linux/virtio.h> |
7 | #include <linux/virtio_blk.h> | 8 | #include <linux/virtio_blk.h> |
@@ -65,13 +66,18 @@ static void blk_done(struct virtqueue *vq) | |||
65 | break; | 66 | break; |
66 | } | 67 | } |
67 | 68 | ||
68 | if (blk_pc_request(vbr->req)) { | 69 | switch (vbr->req->cmd_type) { |
70 | case REQ_TYPE_BLOCK_PC: | ||
69 | vbr->req->resid_len = vbr->in_hdr.residual; | 71 | vbr->req->resid_len = vbr->in_hdr.residual; |
70 | vbr->req->sense_len = vbr->in_hdr.sense_len; | 72 | vbr->req->sense_len = vbr->in_hdr.sense_len; |
71 | vbr->req->errors = vbr->in_hdr.errors; | 73 | vbr->req->errors = vbr->in_hdr.errors; |
72 | } | 74 | break; |
73 | if (blk_special_request(vbr->req)) | 75 | case REQ_TYPE_SPECIAL: |
74 | vbr->req->errors = (error != 0); | 76 | vbr->req->errors = (error != 0); |
77 | break; | ||
78 | default: | ||
79 | break; | ||
80 | } | ||
75 | 81 | ||
76 | __blk_end_request_all(vbr->req, error); | 82 | __blk_end_request_all(vbr->req, error); |
77 | list_del(&vbr->list); | 83 | list_del(&vbr->list); |
@@ -94,36 +100,35 @@ static bool do_req(struct request_queue *q, struct virtio_blk *vblk, | |||
94 | return false; | 100 | return false; |
95 | 101 | ||
96 | vbr->req = req; | 102 | vbr->req = req; |
97 | switch (req->cmd_type) { | 103 | |
98 | case REQ_TYPE_FS: | 104 | if (req->cmd_flags & REQ_FLUSH) { |
99 | vbr->out_hdr.type = 0; | 105 | vbr->out_hdr.type = VIRTIO_BLK_T_FLUSH; |
100 | vbr->out_hdr.sector = blk_rq_pos(vbr->req); | ||
101 | vbr->out_hdr.ioprio = req_get_ioprio(vbr->req); | ||
102 | break; | ||
103 | case REQ_TYPE_BLOCK_PC: | ||
104 | vbr->out_hdr.type = VIRTIO_BLK_T_SCSI_CMD; | ||
105 | vbr->out_hdr.sector = 0; | ||
106 | vbr->out_hdr.ioprio = req_get_ioprio(vbr->req); | ||
107 | break; | ||
108 | case REQ_TYPE_SPECIAL: | ||
109 | vbr->out_hdr.type = VIRTIO_BLK_T_GET_ID; | ||
110 | vbr->out_hdr.sector = 0; | 106 | vbr->out_hdr.sector = 0; |
111 | vbr->out_hdr.ioprio = req_get_ioprio(vbr->req); | 107 | vbr->out_hdr.ioprio = req_get_ioprio(vbr->req); |
112 | break; | 108 | } else { |
113 | case REQ_TYPE_LINUX_BLOCK: | 109 | switch (req->cmd_type) { |
114 | if (req->cmd[0] == REQ_LB_OP_FLUSH) { | 110 | case REQ_TYPE_FS: |
115 | vbr->out_hdr.type = VIRTIO_BLK_T_FLUSH; | 111 | vbr->out_hdr.type = 0; |
112 | vbr->out_hdr.sector = blk_rq_pos(vbr->req); | ||
113 | vbr->out_hdr.ioprio = req_get_ioprio(vbr->req); | ||
114 | break; | ||
115 | case REQ_TYPE_BLOCK_PC: | ||
116 | vbr->out_hdr.type = VIRTIO_BLK_T_SCSI_CMD; | ||
116 | vbr->out_hdr.sector = 0; | 117 | vbr->out_hdr.sector = 0; |
117 | vbr->out_hdr.ioprio = req_get_ioprio(vbr->req); | 118 | vbr->out_hdr.ioprio = req_get_ioprio(vbr->req); |
118 | break; | 119 | break; |
120 | case REQ_TYPE_SPECIAL: | ||
121 | vbr->out_hdr.type = VIRTIO_BLK_T_GET_ID; | ||
122 | vbr->out_hdr.sector = 0; | ||
123 | vbr->out_hdr.ioprio = req_get_ioprio(vbr->req); | ||
124 | break; | ||
125 | default: | ||
126 | /* We don't put anything else in the queue. */ | ||
127 | BUG(); | ||
119 | } | 128 | } |
120 | /*FALLTHRU*/ | ||
121 | default: | ||
122 | /* We don't put anything else in the queue. */ | ||
123 | BUG(); | ||
124 | } | 129 | } |
125 | 130 | ||
126 | if (blk_barrier_rq(vbr->req)) | 131 | if (vbr->req->cmd_flags & REQ_HARDBARRIER) |
127 | vbr->out_hdr.type |= VIRTIO_BLK_T_BARRIER; | 132 | vbr->out_hdr.type |= VIRTIO_BLK_T_BARRIER; |
128 | 133 | ||
129 | sg_set_buf(&vblk->sg[out++], &vbr->out_hdr, sizeof(vbr->out_hdr)); | 134 | sg_set_buf(&vblk->sg[out++], &vbr->out_hdr, sizeof(vbr->out_hdr)); |
@@ -134,12 +139,12 @@ static bool do_req(struct request_queue *q, struct virtio_blk *vblk, | |||
134 | * block, and before the normal inhdr we put the sense data and the | 139 | * block, and before the normal inhdr we put the sense data and the |
135 | * inhdr with additional status information before the normal inhdr. | 140 | * inhdr with additional status information before the normal inhdr. |
136 | */ | 141 | */ |
137 | if (blk_pc_request(vbr->req)) | 142 | if (vbr->req->cmd_type == REQ_TYPE_BLOCK_PC) |
138 | sg_set_buf(&vblk->sg[out++], vbr->req->cmd, vbr->req->cmd_len); | 143 | sg_set_buf(&vblk->sg[out++], vbr->req->cmd, vbr->req->cmd_len); |
139 | 144 | ||
140 | num = blk_rq_map_sg(q, vbr->req, vblk->sg + out); | 145 | num = blk_rq_map_sg(q, vbr->req, vblk->sg + out); |
141 | 146 | ||
142 | if (blk_pc_request(vbr->req)) { | 147 | if (vbr->req->cmd_type == REQ_TYPE_BLOCK_PC) { |
143 | sg_set_buf(&vblk->sg[num + out + in++], vbr->req->sense, 96); | 148 | sg_set_buf(&vblk->sg[num + out + in++], vbr->req->sense, 96); |
144 | sg_set_buf(&vblk->sg[num + out + in++], &vbr->in_hdr, | 149 | sg_set_buf(&vblk->sg[num + out + in++], &vbr->in_hdr, |
145 | sizeof(vbr->in_hdr)); | 150 | sizeof(vbr->in_hdr)); |
@@ -190,12 +195,6 @@ static void do_virtblk_request(struct request_queue *q) | |||
190 | virtqueue_kick(vblk->vq); | 195 | virtqueue_kick(vblk->vq); |
191 | } | 196 | } |
192 | 197 | ||
193 | static void virtblk_prepare_flush(struct request_queue *q, struct request *req) | ||
194 | { | ||
195 | req->cmd_type = REQ_TYPE_LINUX_BLOCK; | ||
196 | req->cmd[0] = REQ_LB_OP_FLUSH; | ||
197 | } | ||
198 | |||
199 | /* return id (s/n) string for *disk to *id_str | 198 | /* return id (s/n) string for *disk to *id_str |
200 | */ | 199 | */ |
201 | static int virtblk_get_id(struct gendisk *disk, char *id_str) | 200 | static int virtblk_get_id(struct gendisk *disk, char *id_str) |
@@ -219,7 +218,7 @@ static int virtblk_get_id(struct gendisk *disk, char *id_str) | |||
219 | return blk_execute_rq(vblk->disk->queue, vblk->disk, req, false); | 218 | return blk_execute_rq(vblk->disk->queue, vblk->disk, req, false); |
220 | } | 219 | } |
221 | 220 | ||
222 | static int virtblk_ioctl(struct block_device *bdev, fmode_t mode, | 221 | static int virtblk_locked_ioctl(struct block_device *bdev, fmode_t mode, |
223 | unsigned cmd, unsigned long data) | 222 | unsigned cmd, unsigned long data) |
224 | { | 223 | { |
225 | struct gendisk *disk = bdev->bd_disk; | 224 | struct gendisk *disk = bdev->bd_disk; |
@@ -235,6 +234,18 @@ static int virtblk_ioctl(struct block_device *bdev, fmode_t mode, | |||
235 | (void __user *)data); | 234 | (void __user *)data); |
236 | } | 235 | } |
237 | 236 | ||
237 | static int virtblk_ioctl(struct block_device *bdev, fmode_t mode, | ||
238 | unsigned int cmd, unsigned long param) | ||
239 | { | ||
240 | int ret; | ||
241 | |||
242 | lock_kernel(); | ||
243 | ret = virtblk_locked_ioctl(bdev, mode, cmd, param); | ||
244 | unlock_kernel(); | ||
245 | |||
246 | return ret; | ||
247 | } | ||
248 | |||
238 | /* We provide getgeo only to please some old bootloader/partitioning tools */ | 249 | /* We provide getgeo only to please some old bootloader/partitioning tools */ |
239 | static int virtblk_getgeo(struct block_device *bd, struct hd_geometry *geo) | 250 | static int virtblk_getgeo(struct block_device *bd, struct hd_geometry *geo) |
240 | { | 251 | { |
@@ -261,7 +272,7 @@ static int virtblk_getgeo(struct block_device *bd, struct hd_geometry *geo) | |||
261 | } | 272 | } |
262 | 273 | ||
263 | static const struct block_device_operations virtblk_fops = { | 274 | static const struct block_device_operations virtblk_fops = { |
264 | .locked_ioctl = virtblk_ioctl, | 275 | .ioctl = virtblk_ioctl, |
265 | .owner = THIS_MODULE, | 276 | .owner = THIS_MODULE, |
266 | .getgeo = virtblk_getgeo, | 277 | .getgeo = virtblk_getgeo, |
267 | }; | 278 | }; |
@@ -383,8 +394,7 @@ static int __devinit virtblk_probe(struct virtio_device *vdev) | |||
383 | * flushing a volatile write cache on the host. Use that | 394 | * flushing a volatile write cache on the host. Use that |
384 | * to implement write barrier support. | 395 | * to implement write barrier support. |
385 | */ | 396 | */ |
386 | blk_queue_ordered(q, QUEUE_ORDERED_DRAIN_FLUSH, | 397 | blk_queue_ordered(q, QUEUE_ORDERED_DRAIN_FLUSH); |
387 | virtblk_prepare_flush); | ||
388 | } else if (virtio_has_feature(vdev, VIRTIO_BLK_F_BARRIER)) { | 398 | } else if (virtio_has_feature(vdev, VIRTIO_BLK_F_BARRIER)) { |
389 | /* | 399 | /* |
390 | * If the BARRIER feature is supported the host expects us | 400 | * If the BARRIER feature is supported the host expects us |
@@ -393,7 +403,7 @@ static int __devinit virtblk_probe(struct virtio_device *vdev) | |||
393 | * never re-orders outstanding I/O. This feature is not | 403 | * never re-orders outstanding I/O. This feature is not |
394 | * useful for real life scenarious and deprecated. | 404 | * useful for real life scenarious and deprecated. |
395 | */ | 405 | */ |
396 | blk_queue_ordered(q, QUEUE_ORDERED_TAG, NULL); | 406 | blk_queue_ordered(q, QUEUE_ORDERED_TAG); |
397 | } else { | 407 | } else { |
398 | /* | 408 | /* |
399 | * If the FLUSH feature is not supported we must assume that | 409 | * If the FLUSH feature is not supported we must assume that |
@@ -401,7 +411,7 @@ static int __devinit virtblk_probe(struct virtio_device *vdev) | |||
401 | * caching. We still need to drain the queue to provider | 411 | * caching. We still need to drain the queue to provider |
402 | * proper barrier semantics. | 412 | * proper barrier semantics. |
403 | */ | 413 | */ |
404 | blk_queue_ordered(q, QUEUE_ORDERED_DRAIN, NULL); | 414 | blk_queue_ordered(q, QUEUE_ORDERED_DRAIN); |
405 | } | 415 | } |
406 | 416 | ||
407 | /* If disk is read-only in the host, the guest should obey */ | 417 | /* If disk is read-only in the host, the guest should obey */ |
diff --git a/drivers/block/xd.c b/drivers/block/xd.c index 18a80ff57ce8..d5a3cd750561 100644 --- a/drivers/block/xd.c +++ b/drivers/block/xd.c | |||
@@ -46,6 +46,7 @@ | |||
46 | #include <linux/init.h> | 46 | #include <linux/init.h> |
47 | #include <linux/wait.h> | 47 | #include <linux/wait.h> |
48 | #include <linux/blkdev.h> | 48 | #include <linux/blkdev.h> |
49 | #include <linux/smp_lock.h> | ||
49 | #include <linux/blkpg.h> | 50 | #include <linux/blkpg.h> |
50 | #include <linux/delay.h> | 51 | #include <linux/delay.h> |
51 | #include <linux/io.h> | 52 | #include <linux/io.h> |
@@ -133,7 +134,7 @@ static int xd_getgeo(struct block_device *bdev, struct hd_geometry *geo); | |||
133 | 134 | ||
134 | static const struct block_device_operations xd_fops = { | 135 | static const struct block_device_operations xd_fops = { |
135 | .owner = THIS_MODULE, | 136 | .owner = THIS_MODULE, |
136 | .locked_ioctl = xd_ioctl, | 137 | .ioctl = xd_ioctl, |
137 | .getgeo = xd_getgeo, | 138 | .getgeo = xd_getgeo, |
138 | }; | 139 | }; |
139 | static DECLARE_WAIT_QUEUE_HEAD(xd_wait_int); | 140 | static DECLARE_WAIT_QUEUE_HEAD(xd_wait_int); |
@@ -322,7 +323,7 @@ static void do_xd_request (struct request_queue * q) | |||
322 | int res = -EIO; | 323 | int res = -EIO; |
323 | int retry; | 324 | int retry; |
324 | 325 | ||
325 | if (!blk_fs_request(req)) | 326 | if (req->cmd_type != REQ_TYPE_FS) |
326 | goto done; | 327 | goto done; |
327 | if (block + count > get_capacity(req->rq_disk)) | 328 | if (block + count > get_capacity(req->rq_disk)) |
328 | goto done; | 329 | goto done; |
@@ -347,7 +348,7 @@ static int xd_getgeo(struct block_device *bdev, struct hd_geometry *geo) | |||
347 | } | 348 | } |
348 | 349 | ||
349 | /* xd_ioctl: handle device ioctl's */ | 350 | /* xd_ioctl: handle device ioctl's */ |
350 | static int xd_ioctl(struct block_device *bdev, fmode_t mode, u_int cmd, u_long arg) | 351 | static int xd_locked_ioctl(struct block_device *bdev, fmode_t mode, u_int cmd, u_long arg) |
351 | { | 352 | { |
352 | switch (cmd) { | 353 | switch (cmd) { |
353 | case HDIO_SET_DMA: | 354 | case HDIO_SET_DMA: |
@@ -375,6 +376,18 @@ static int xd_ioctl(struct block_device *bdev, fmode_t mode, u_int cmd, u_long a | |||
375 | } | 376 | } |
376 | } | 377 | } |
377 | 378 | ||
379 | static int xd_ioctl(struct block_device *bdev, fmode_t mode, | ||
380 | unsigned int cmd, unsigned long param) | ||
381 | { | ||
382 | int ret; | ||
383 | |||
384 | lock_kernel(); | ||
385 | ret = xd_locked_ioctl(bdev, mode, cmd, param); | ||
386 | unlock_kernel(); | ||
387 | |||
388 | return ret; | ||
389 | } | ||
390 | |||
378 | /* xd_readwrite: handle a read/write request */ | 391 | /* xd_readwrite: handle a read/write request */ |
379 | static int xd_readwrite (u_char operation,XD_INFO *p,char *buffer,u_int block,u_int count) | 392 | static int xd_readwrite (u_char operation,XD_INFO *p,char *buffer,u_int block,u_int count) |
380 | { | 393 | { |
diff --git a/drivers/block/xen-blkfront.c b/drivers/block/xen-blkfront.c index f63ac3d1f8a4..ac1b682edecb 100644 --- a/drivers/block/xen-blkfront.c +++ b/drivers/block/xen-blkfront.c | |||
@@ -41,6 +41,7 @@ | |||
41 | #include <linux/cdrom.h> | 41 | #include <linux/cdrom.h> |
42 | #include <linux/module.h> | 42 | #include <linux/module.h> |
43 | #include <linux/slab.h> | 43 | #include <linux/slab.h> |
44 | #include <linux/smp_lock.h> | ||
44 | #include <linux/scatterlist.h> | 45 | #include <linux/scatterlist.h> |
45 | 46 | ||
46 | #include <xen/xen.h> | 47 | #include <xen/xen.h> |
@@ -79,6 +80,7 @@ static const struct block_device_operations xlvbd_block_fops; | |||
79 | */ | 80 | */ |
80 | struct blkfront_info | 81 | struct blkfront_info |
81 | { | 82 | { |
83 | struct mutex mutex; | ||
82 | struct xenbus_device *xbdev; | 84 | struct xenbus_device *xbdev; |
83 | struct gendisk *gd; | 85 | struct gendisk *gd; |
84 | int vdevice; | 86 | int vdevice; |
@@ -95,16 +97,14 @@ struct blkfront_info | |||
95 | unsigned long shadow_free; | 97 | unsigned long shadow_free; |
96 | int feature_barrier; | 98 | int feature_barrier; |
97 | int is_ready; | 99 | int is_ready; |
98 | |||
99 | /** | ||
100 | * The number of people holding this device open. We won't allow a | ||
101 | * hot-unplug unless this is 0. | ||
102 | */ | ||
103 | int users; | ||
104 | }; | 100 | }; |
105 | 101 | ||
106 | static DEFINE_SPINLOCK(blkif_io_lock); | 102 | static DEFINE_SPINLOCK(blkif_io_lock); |
107 | 103 | ||
104 | static unsigned int nr_minors; | ||
105 | static unsigned long *minors; | ||
106 | static DEFINE_SPINLOCK(minor_lock); | ||
107 | |||
108 | #define MAXIMUM_OUTSTANDING_BLOCK_REQS \ | 108 | #define MAXIMUM_OUTSTANDING_BLOCK_REQS \ |
109 | (BLKIF_MAX_SEGMENTS_PER_REQUEST * BLK_RING_SIZE) | 109 | (BLKIF_MAX_SEGMENTS_PER_REQUEST * BLK_RING_SIZE) |
110 | #define GRANT_INVALID_REF 0 | 110 | #define GRANT_INVALID_REF 0 |
@@ -139,6 +139,55 @@ static void add_id_to_freelist(struct blkfront_info *info, | |||
139 | info->shadow_free = id; | 139 | info->shadow_free = id; |
140 | } | 140 | } |
141 | 141 | ||
142 | static int xlbd_reserve_minors(unsigned int minor, unsigned int nr) | ||
143 | { | ||
144 | unsigned int end = minor + nr; | ||
145 | int rc; | ||
146 | |||
147 | if (end > nr_minors) { | ||
148 | unsigned long *bitmap, *old; | ||
149 | |||
150 | bitmap = kzalloc(BITS_TO_LONGS(end) * sizeof(*bitmap), | ||
151 | GFP_KERNEL); | ||
152 | if (bitmap == NULL) | ||
153 | return -ENOMEM; | ||
154 | |||
155 | spin_lock(&minor_lock); | ||
156 | if (end > nr_minors) { | ||
157 | old = minors; | ||
158 | memcpy(bitmap, minors, | ||
159 | BITS_TO_LONGS(nr_minors) * sizeof(*bitmap)); | ||
160 | minors = bitmap; | ||
161 | nr_minors = BITS_TO_LONGS(end) * BITS_PER_LONG; | ||
162 | } else | ||
163 | old = bitmap; | ||
164 | spin_unlock(&minor_lock); | ||
165 | kfree(old); | ||
166 | } | ||
167 | |||
168 | spin_lock(&minor_lock); | ||
169 | if (find_next_bit(minors, end, minor) >= end) { | ||
170 | for (; minor < end; ++minor) | ||
171 | __set_bit(minor, minors); | ||
172 | rc = 0; | ||
173 | } else | ||
174 | rc = -EBUSY; | ||
175 | spin_unlock(&minor_lock); | ||
176 | |||
177 | return rc; | ||
178 | } | ||
179 | |||
180 | static void xlbd_release_minors(unsigned int minor, unsigned int nr) | ||
181 | { | ||
182 | unsigned int end = minor + nr; | ||
183 | |||
184 | BUG_ON(end > nr_minors); | ||
185 | spin_lock(&minor_lock); | ||
186 | for (; minor < end; ++minor) | ||
187 | __clear_bit(minor, minors); | ||
188 | spin_unlock(&minor_lock); | ||
189 | } | ||
190 | |||
142 | static void blkif_restart_queue_callback(void *arg) | 191 | static void blkif_restart_queue_callback(void *arg) |
143 | { | 192 | { |
144 | struct blkfront_info *info = (struct blkfront_info *)arg; | 193 | struct blkfront_info *info = (struct blkfront_info *)arg; |
@@ -239,7 +288,7 @@ static int blkif_queue_request(struct request *req) | |||
239 | 288 | ||
240 | ring_req->operation = rq_data_dir(req) ? | 289 | ring_req->operation = rq_data_dir(req) ? |
241 | BLKIF_OP_WRITE : BLKIF_OP_READ; | 290 | BLKIF_OP_WRITE : BLKIF_OP_READ; |
242 | if (blk_barrier_rq(req)) | 291 | if (req->cmd_flags & REQ_HARDBARRIER) |
243 | ring_req->operation = BLKIF_OP_WRITE_BARRIER; | 292 | ring_req->operation = BLKIF_OP_WRITE_BARRIER; |
244 | 293 | ||
245 | ring_req->nr_segments = blk_rq_map_sg(req->q, req, info->sg); | 294 | ring_req->nr_segments = blk_rq_map_sg(req->q, req, info->sg); |
@@ -310,7 +359,7 @@ static void do_blkif_request(struct request_queue *rq) | |||
310 | 359 | ||
311 | blk_start_request(req); | 360 | blk_start_request(req); |
312 | 361 | ||
313 | if (!blk_fs_request(req)) { | 362 | if (req->cmd_type != REQ_TYPE_FS) { |
314 | __blk_end_request_all(req, -EIO); | 363 | __blk_end_request_all(req, -EIO); |
315 | continue; | 364 | continue; |
316 | } | 365 | } |
@@ -372,17 +421,22 @@ static int xlvbd_init_blk_queue(struct gendisk *gd, u16 sector_size) | |||
372 | static int xlvbd_barrier(struct blkfront_info *info) | 421 | static int xlvbd_barrier(struct blkfront_info *info) |
373 | { | 422 | { |
374 | int err; | 423 | int err; |
424 | const char *barrier; | ||
375 | 425 | ||
376 | err = blk_queue_ordered(info->rq, | 426 | switch (info->feature_barrier) { |
377 | info->feature_barrier ? QUEUE_ORDERED_DRAIN : QUEUE_ORDERED_NONE, | 427 | case QUEUE_ORDERED_DRAIN: barrier = "enabled (drain)"; break; |
378 | NULL); | 428 | case QUEUE_ORDERED_TAG: barrier = "enabled (tag)"; break; |
429 | case QUEUE_ORDERED_NONE: barrier = "disabled"; break; | ||
430 | default: return -EINVAL; | ||
431 | } | ||
432 | |||
433 | err = blk_queue_ordered(info->rq, info->feature_barrier); | ||
379 | 434 | ||
380 | if (err) | 435 | if (err) |
381 | return err; | 436 | return err; |
382 | 437 | ||
383 | printk(KERN_INFO "blkfront: %s: barriers %s\n", | 438 | printk(KERN_INFO "blkfront: %s: barriers %s\n", |
384 | info->gd->disk_name, | 439 | info->gd->disk_name, barrier); |
385 | info->feature_barrier ? "enabled" : "disabled"); | ||
386 | return 0; | 440 | return 0; |
387 | } | 441 | } |
388 | 442 | ||
@@ -418,9 +472,14 @@ static int xlvbd_alloc_gendisk(blkif_sector_t capacity, | |||
418 | if ((minor % nr_parts) == 0) | 472 | if ((minor % nr_parts) == 0) |
419 | nr_minors = nr_parts; | 473 | nr_minors = nr_parts; |
420 | 474 | ||
475 | err = xlbd_reserve_minors(minor, nr_minors); | ||
476 | if (err) | ||
477 | goto out; | ||
478 | err = -ENODEV; | ||
479 | |||
421 | gd = alloc_disk(nr_minors); | 480 | gd = alloc_disk(nr_minors); |
422 | if (gd == NULL) | 481 | if (gd == NULL) |
423 | goto out; | 482 | goto release; |
424 | 483 | ||
425 | offset = minor / nr_parts; | 484 | offset = minor / nr_parts; |
426 | 485 | ||
@@ -451,14 +510,13 @@ static int xlvbd_alloc_gendisk(blkif_sector_t capacity, | |||
451 | 510 | ||
452 | if (xlvbd_init_blk_queue(gd, sector_size)) { | 511 | if (xlvbd_init_blk_queue(gd, sector_size)) { |
453 | del_gendisk(gd); | 512 | del_gendisk(gd); |
454 | goto out; | 513 | goto release; |
455 | } | 514 | } |
456 | 515 | ||
457 | info->rq = gd->queue; | 516 | info->rq = gd->queue; |
458 | info->gd = gd; | 517 | info->gd = gd; |
459 | 518 | ||
460 | if (info->feature_barrier) | 519 | xlvbd_barrier(info); |
461 | xlvbd_barrier(info); | ||
462 | 520 | ||
463 | if (vdisk_info & VDISK_READONLY) | 521 | if (vdisk_info & VDISK_READONLY) |
464 | set_disk_ro(gd, 1); | 522 | set_disk_ro(gd, 1); |
@@ -471,10 +529,45 @@ static int xlvbd_alloc_gendisk(blkif_sector_t capacity, | |||
471 | 529 | ||
472 | return 0; | 530 | return 0; |
473 | 531 | ||
532 | release: | ||
533 | xlbd_release_minors(minor, nr_minors); | ||
474 | out: | 534 | out: |
475 | return err; | 535 | return err; |
476 | } | 536 | } |
477 | 537 | ||
538 | static void xlvbd_release_gendisk(struct blkfront_info *info) | ||
539 | { | ||
540 | unsigned int minor, nr_minors; | ||
541 | unsigned long flags; | ||
542 | |||
543 | if (info->rq == NULL) | ||
544 | return; | ||
545 | |||
546 | spin_lock_irqsave(&blkif_io_lock, flags); | ||
547 | |||
548 | /* No more blkif_request(). */ | ||
549 | blk_stop_queue(info->rq); | ||
550 | |||
551 | /* No more gnttab callback work. */ | ||
552 | gnttab_cancel_free_callback(&info->callback); | ||
553 | spin_unlock_irqrestore(&blkif_io_lock, flags); | ||
554 | |||
555 | /* Flush gnttab callback work. Must be done with no locks held. */ | ||
556 | flush_scheduled_work(); | ||
557 | |||
558 | del_gendisk(info->gd); | ||
559 | |||
560 | minor = info->gd->first_minor; | ||
561 | nr_minors = info->gd->minors; | ||
562 | xlbd_release_minors(minor, nr_minors); | ||
563 | |||
564 | blk_cleanup_queue(info->rq); | ||
565 | info->rq = NULL; | ||
566 | |||
567 | put_disk(info->gd); | ||
568 | info->gd = NULL; | ||
569 | } | ||
570 | |||
478 | static void kick_pending_request_queues(struct blkfront_info *info) | 571 | static void kick_pending_request_queues(struct blkfront_info *info) |
479 | { | 572 | { |
480 | if (!RING_FULL(&info->ring)) { | 573 | if (!RING_FULL(&info->ring)) { |
@@ -569,7 +662,7 @@ static irqreturn_t blkif_interrupt(int irq, void *dev_id) | |||
569 | printk(KERN_WARNING "blkfront: %s: write barrier op failed\n", | 662 | printk(KERN_WARNING "blkfront: %s: write barrier op failed\n", |
570 | info->gd->disk_name); | 663 | info->gd->disk_name); |
571 | error = -EOPNOTSUPP; | 664 | error = -EOPNOTSUPP; |
572 | info->feature_barrier = 0; | 665 | info->feature_barrier = QUEUE_ORDERED_NONE; |
573 | xlvbd_barrier(info); | 666 | xlvbd_barrier(info); |
574 | } | 667 | } |
575 | /* fall through */ | 668 | /* fall through */ |
@@ -652,7 +745,7 @@ fail: | |||
652 | 745 | ||
653 | 746 | ||
654 | /* Common code used when first setting up, and when resuming. */ | 747 | /* Common code used when first setting up, and when resuming. */ |
655 | static int talk_to_backend(struct xenbus_device *dev, | 748 | static int talk_to_blkback(struct xenbus_device *dev, |
656 | struct blkfront_info *info) | 749 | struct blkfront_info *info) |
657 | { | 750 | { |
658 | const char *message = NULL; | 751 | const char *message = NULL; |
@@ -712,7 +805,6 @@ again: | |||
712 | return err; | 805 | return err; |
713 | } | 806 | } |
714 | 807 | ||
715 | |||
716 | /** | 808 | /** |
717 | * Entry point to this code when a new device is created. Allocate the basic | 809 | * Entry point to this code when a new device is created. Allocate the basic |
718 | * structures and the ring buffer for communication with the backend, and | 810 | * structures and the ring buffer for communication with the backend, and |
@@ -773,6 +865,7 @@ static int blkfront_probe(struct xenbus_device *dev, | |||
773 | return -ENOMEM; | 865 | return -ENOMEM; |
774 | } | 866 | } |
775 | 867 | ||
868 | mutex_init(&info->mutex); | ||
776 | info->xbdev = dev; | 869 | info->xbdev = dev; |
777 | info->vdevice = vdevice; | 870 | info->vdevice = vdevice; |
778 | info->connected = BLKIF_STATE_DISCONNECTED; | 871 | info->connected = BLKIF_STATE_DISCONNECTED; |
@@ -786,7 +879,7 @@ static int blkfront_probe(struct xenbus_device *dev, | |||
786 | info->handle = simple_strtoul(strrchr(dev->nodename, '/')+1, NULL, 0); | 879 | info->handle = simple_strtoul(strrchr(dev->nodename, '/')+1, NULL, 0); |
787 | dev_set_drvdata(&dev->dev, info); | 880 | dev_set_drvdata(&dev->dev, info); |
788 | 881 | ||
789 | err = talk_to_backend(dev, info); | 882 | err = talk_to_blkback(dev, info); |
790 | if (err) { | 883 | if (err) { |
791 | kfree(info); | 884 | kfree(info); |
792 | dev_set_drvdata(&dev->dev, NULL); | 885 | dev_set_drvdata(&dev->dev, NULL); |
@@ -881,13 +974,50 @@ static int blkfront_resume(struct xenbus_device *dev) | |||
881 | 974 | ||
882 | blkif_free(info, info->connected == BLKIF_STATE_CONNECTED); | 975 | blkif_free(info, info->connected == BLKIF_STATE_CONNECTED); |
883 | 976 | ||
884 | err = talk_to_backend(dev, info); | 977 | err = talk_to_blkback(dev, info); |
885 | if (info->connected == BLKIF_STATE_SUSPENDED && !err) | 978 | if (info->connected == BLKIF_STATE_SUSPENDED && !err) |
886 | err = blkif_recover(info); | 979 | err = blkif_recover(info); |
887 | 980 | ||
888 | return err; | 981 | return err; |
889 | } | 982 | } |
890 | 983 | ||
984 | static void | ||
985 | blkfront_closing(struct blkfront_info *info) | ||
986 | { | ||
987 | struct xenbus_device *xbdev = info->xbdev; | ||
988 | struct block_device *bdev = NULL; | ||
989 | |||
990 | mutex_lock(&info->mutex); | ||
991 | |||
992 | if (xbdev->state == XenbusStateClosing) { | ||
993 | mutex_unlock(&info->mutex); | ||
994 | return; | ||
995 | } | ||
996 | |||
997 | if (info->gd) | ||
998 | bdev = bdget_disk(info->gd, 0); | ||
999 | |||
1000 | mutex_unlock(&info->mutex); | ||
1001 | |||
1002 | if (!bdev) { | ||
1003 | xenbus_frontend_closed(xbdev); | ||
1004 | return; | ||
1005 | } | ||
1006 | |||
1007 | mutex_lock(&bdev->bd_mutex); | ||
1008 | |||
1009 | if (bdev->bd_openers) { | ||
1010 | xenbus_dev_error(xbdev, -EBUSY, | ||
1011 | "Device in use; refusing to close"); | ||
1012 | xenbus_switch_state(xbdev, XenbusStateClosing); | ||
1013 | } else { | ||
1014 | xlvbd_release_gendisk(info); | ||
1015 | xenbus_frontend_closed(xbdev); | ||
1016 | } | ||
1017 | |||
1018 | mutex_unlock(&bdev->bd_mutex); | ||
1019 | bdput(bdev); | ||
1020 | } | ||
891 | 1021 | ||
892 | /* | 1022 | /* |
893 | * Invoked when the backend is finally 'ready' (and has told produced | 1023 | * Invoked when the backend is finally 'ready' (and has told produced |
@@ -899,11 +1029,31 @@ static void blkfront_connect(struct blkfront_info *info) | |||
899 | unsigned long sector_size; | 1029 | unsigned long sector_size; |
900 | unsigned int binfo; | 1030 | unsigned int binfo; |
901 | int err; | 1031 | int err; |
902 | 1032 | int barrier; | |
903 | if ((info->connected == BLKIF_STATE_CONNECTED) || | 1033 | |
904 | (info->connected == BLKIF_STATE_SUSPENDED) ) | 1034 | switch (info->connected) { |
1035 | case BLKIF_STATE_CONNECTED: | ||
1036 | /* | ||
1037 | * Potentially, the back-end may be signalling | ||
1038 | * a capacity change; update the capacity. | ||
1039 | */ | ||
1040 | err = xenbus_scanf(XBT_NIL, info->xbdev->otherend, | ||
1041 | "sectors", "%Lu", §ors); | ||
1042 | if (XENBUS_EXIST_ERR(err)) | ||
1043 | return; | ||
1044 | printk(KERN_INFO "Setting capacity to %Lu\n", | ||
1045 | sectors); | ||
1046 | set_capacity(info->gd, sectors); | ||
1047 | revalidate_disk(info->gd); | ||
1048 | |||
1049 | /* fall through */ | ||
1050 | case BLKIF_STATE_SUSPENDED: | ||
905 | return; | 1051 | return; |
906 | 1052 | ||
1053 | default: | ||
1054 | break; | ||
1055 | } | ||
1056 | |||
907 | dev_dbg(&info->xbdev->dev, "%s:%s.\n", | 1057 | dev_dbg(&info->xbdev->dev, "%s:%s.\n", |
908 | __func__, info->xbdev->otherend); | 1058 | __func__, info->xbdev->otherend); |
909 | 1059 | ||
@@ -920,10 +1070,26 @@ static void blkfront_connect(struct blkfront_info *info) | |||
920 | } | 1070 | } |
921 | 1071 | ||
922 | err = xenbus_gather(XBT_NIL, info->xbdev->otherend, | 1072 | err = xenbus_gather(XBT_NIL, info->xbdev->otherend, |
923 | "feature-barrier", "%lu", &info->feature_barrier, | 1073 | "feature-barrier", "%lu", &barrier, |
924 | NULL); | 1074 | NULL); |
1075 | |||
1076 | /* | ||
1077 | * If there's no "feature-barrier" defined, then it means | ||
1078 | * we're dealing with a very old backend which writes | ||
1079 | * synchronously; draining will do what needs to get done. | ||
1080 | * | ||
1081 | * If there are barriers, then we can do full queued writes | ||
1082 | * with tagged barriers. | ||
1083 | * | ||
1084 | * If barriers are not supported, then there's no much we can | ||
1085 | * do, so just set ordering to NONE. | ||
1086 | */ | ||
925 | if (err) | 1087 | if (err) |
926 | info->feature_barrier = 0; | 1088 | info->feature_barrier = QUEUE_ORDERED_DRAIN; |
1089 | else if (barrier) | ||
1090 | info->feature_barrier = QUEUE_ORDERED_TAG; | ||
1091 | else | ||
1092 | info->feature_barrier = QUEUE_ORDERED_NONE; | ||
927 | 1093 | ||
928 | err = xlvbd_alloc_gendisk(sectors, info, binfo, sector_size); | 1094 | err = xlvbd_alloc_gendisk(sectors, info, binfo, sector_size); |
929 | if (err) { | 1095 | if (err) { |
@@ -946,52 +1112,14 @@ static void blkfront_connect(struct blkfront_info *info) | |||
946 | } | 1112 | } |
947 | 1113 | ||
948 | /** | 1114 | /** |
949 | * Handle the change of state of the backend to Closing. We must delete our | ||
950 | * device-layer structures now, to ensure that writes are flushed through to | ||
951 | * the backend. Once is this done, we can switch to Closed in | ||
952 | * acknowledgement. | ||
953 | */ | ||
954 | static void blkfront_closing(struct xenbus_device *dev) | ||
955 | { | ||
956 | struct blkfront_info *info = dev_get_drvdata(&dev->dev); | ||
957 | unsigned long flags; | ||
958 | |||
959 | dev_dbg(&dev->dev, "blkfront_closing: %s removed\n", dev->nodename); | ||
960 | |||
961 | if (info->rq == NULL) | ||
962 | goto out; | ||
963 | |||
964 | spin_lock_irqsave(&blkif_io_lock, flags); | ||
965 | |||
966 | /* No more blkif_request(). */ | ||
967 | blk_stop_queue(info->rq); | ||
968 | |||
969 | /* No more gnttab callback work. */ | ||
970 | gnttab_cancel_free_callback(&info->callback); | ||
971 | spin_unlock_irqrestore(&blkif_io_lock, flags); | ||
972 | |||
973 | /* Flush gnttab callback work. Must be done with no locks held. */ | ||
974 | flush_scheduled_work(); | ||
975 | |||
976 | blk_cleanup_queue(info->rq); | ||
977 | info->rq = NULL; | ||
978 | |||
979 | del_gendisk(info->gd); | ||
980 | |||
981 | out: | ||
982 | xenbus_frontend_closed(dev); | ||
983 | } | ||
984 | |||
985 | /** | ||
986 | * Callback received when the backend's state changes. | 1115 | * Callback received when the backend's state changes. |
987 | */ | 1116 | */ |
988 | static void backend_changed(struct xenbus_device *dev, | 1117 | static void blkback_changed(struct xenbus_device *dev, |
989 | enum xenbus_state backend_state) | 1118 | enum xenbus_state backend_state) |
990 | { | 1119 | { |
991 | struct blkfront_info *info = dev_get_drvdata(&dev->dev); | 1120 | struct blkfront_info *info = dev_get_drvdata(&dev->dev); |
992 | struct block_device *bd; | ||
993 | 1121 | ||
994 | dev_dbg(&dev->dev, "blkfront:backend_changed.\n"); | 1122 | dev_dbg(&dev->dev, "blkfront:blkback_changed to state %d.\n", backend_state); |
995 | 1123 | ||
996 | switch (backend_state) { | 1124 | switch (backend_state) { |
997 | case XenbusStateInitialising: | 1125 | case XenbusStateInitialising: |
@@ -1006,35 +1134,56 @@ static void backend_changed(struct xenbus_device *dev, | |||
1006 | break; | 1134 | break; |
1007 | 1135 | ||
1008 | case XenbusStateClosing: | 1136 | case XenbusStateClosing: |
1009 | if (info->gd == NULL) { | 1137 | blkfront_closing(info); |
1010 | xenbus_frontend_closed(dev); | ||
1011 | break; | ||
1012 | } | ||
1013 | bd = bdget_disk(info->gd, 0); | ||
1014 | if (bd == NULL) | ||
1015 | xenbus_dev_fatal(dev, -ENODEV, "bdget failed"); | ||
1016 | |||
1017 | mutex_lock(&bd->bd_mutex); | ||
1018 | if (info->users > 0) | ||
1019 | xenbus_dev_error(dev, -EBUSY, | ||
1020 | "Device in use; refusing to close"); | ||
1021 | else | ||
1022 | blkfront_closing(dev); | ||
1023 | mutex_unlock(&bd->bd_mutex); | ||
1024 | bdput(bd); | ||
1025 | break; | 1138 | break; |
1026 | } | 1139 | } |
1027 | } | 1140 | } |
1028 | 1141 | ||
1029 | static int blkfront_remove(struct xenbus_device *dev) | 1142 | static int blkfront_remove(struct xenbus_device *xbdev) |
1030 | { | 1143 | { |
1031 | struct blkfront_info *info = dev_get_drvdata(&dev->dev); | 1144 | struct blkfront_info *info = dev_get_drvdata(&xbdev->dev); |
1145 | struct block_device *bdev = NULL; | ||
1146 | struct gendisk *disk; | ||
1032 | 1147 | ||
1033 | dev_dbg(&dev->dev, "blkfront_remove: %s removed\n", dev->nodename); | 1148 | dev_dbg(&xbdev->dev, "%s removed", xbdev->nodename); |
1034 | 1149 | ||
1035 | blkif_free(info, 0); | 1150 | blkif_free(info, 0); |
1036 | 1151 | ||
1037 | kfree(info); | 1152 | mutex_lock(&info->mutex); |
1153 | |||
1154 | disk = info->gd; | ||
1155 | if (disk) | ||
1156 | bdev = bdget_disk(disk, 0); | ||
1157 | |||
1158 | info->xbdev = NULL; | ||
1159 | mutex_unlock(&info->mutex); | ||
1160 | |||
1161 | if (!bdev) { | ||
1162 | kfree(info); | ||
1163 | return 0; | ||
1164 | } | ||
1165 | |||
1166 | /* | ||
1167 | * The xbdev was removed before we reached the Closed | ||
1168 | * state. See if it's safe to remove the disk. If the bdev | ||
1169 | * isn't closed yet, we let release take care of it. | ||
1170 | */ | ||
1171 | |||
1172 | mutex_lock(&bdev->bd_mutex); | ||
1173 | info = disk->private_data; | ||
1174 | |||
1175 | dev_warn(disk_to_dev(disk), | ||
1176 | "%s was hot-unplugged, %d stale handles\n", | ||
1177 | xbdev->nodename, bdev->bd_openers); | ||
1178 | |||
1179 | if (info && !bdev->bd_openers) { | ||
1180 | xlvbd_release_gendisk(info); | ||
1181 | disk->private_data = NULL; | ||
1182 | kfree(info); | ||
1183 | } | ||
1184 | |||
1185 | mutex_unlock(&bdev->bd_mutex); | ||
1186 | bdput(bdev); | ||
1038 | 1187 | ||
1039 | return 0; | 1188 | return 0; |
1040 | } | 1189 | } |
@@ -1043,30 +1192,78 @@ static int blkfront_is_ready(struct xenbus_device *dev) | |||
1043 | { | 1192 | { |
1044 | struct blkfront_info *info = dev_get_drvdata(&dev->dev); | 1193 | struct blkfront_info *info = dev_get_drvdata(&dev->dev); |
1045 | 1194 | ||
1046 | return info->is_ready; | 1195 | return info->is_ready && info->xbdev; |
1047 | } | 1196 | } |
1048 | 1197 | ||
1049 | static int blkif_open(struct block_device *bdev, fmode_t mode) | 1198 | static int blkif_open(struct block_device *bdev, fmode_t mode) |
1050 | { | 1199 | { |
1051 | struct blkfront_info *info = bdev->bd_disk->private_data; | 1200 | struct gendisk *disk = bdev->bd_disk; |
1052 | info->users++; | 1201 | struct blkfront_info *info; |
1053 | return 0; | 1202 | int err = 0; |
1203 | |||
1204 | lock_kernel(); | ||
1205 | |||
1206 | info = disk->private_data; | ||
1207 | if (!info) { | ||
1208 | /* xbdev gone */ | ||
1209 | err = -ERESTARTSYS; | ||
1210 | goto out; | ||
1211 | } | ||
1212 | |||
1213 | mutex_lock(&info->mutex); | ||
1214 | |||
1215 | if (!info->gd) | ||
1216 | /* xbdev is closed */ | ||
1217 | err = -ERESTARTSYS; | ||
1218 | |||
1219 | mutex_unlock(&info->mutex); | ||
1220 | |||
1221 | out: | ||
1222 | unlock_kernel(); | ||
1223 | return err; | ||
1054 | } | 1224 | } |
1055 | 1225 | ||
1056 | static int blkif_release(struct gendisk *disk, fmode_t mode) | 1226 | static int blkif_release(struct gendisk *disk, fmode_t mode) |
1057 | { | 1227 | { |
1058 | struct blkfront_info *info = disk->private_data; | 1228 | struct blkfront_info *info = disk->private_data; |
1059 | info->users--; | 1229 | struct block_device *bdev; |
1060 | if (info->users == 0) { | 1230 | struct xenbus_device *xbdev; |
1061 | /* Check whether we have been instructed to close. We will | 1231 | |
1062 | have ignored this request initially, as the device was | 1232 | lock_kernel(); |
1063 | still mounted. */ | 1233 | |
1064 | struct xenbus_device *dev = info->xbdev; | 1234 | bdev = bdget_disk(disk, 0); |
1065 | enum xenbus_state state = xenbus_read_driver_state(dev->otherend); | 1235 | bdput(bdev); |
1066 | 1236 | ||
1067 | if (state == XenbusStateClosing && info->is_ready) | 1237 | if (bdev->bd_openers) |
1068 | blkfront_closing(dev); | 1238 | goto out; |
1239 | |||
1240 | /* | ||
1241 | * Check if we have been instructed to close. We will have | ||
1242 | * deferred this request, because the bdev was still open. | ||
1243 | */ | ||
1244 | |||
1245 | mutex_lock(&info->mutex); | ||
1246 | xbdev = info->xbdev; | ||
1247 | |||
1248 | if (xbdev && xbdev->state == XenbusStateClosing) { | ||
1249 | /* pending switch to state closed */ | ||
1250 | dev_info(disk_to_dev(bdev->bd_disk), "releasing disk\n"); | ||
1251 | xlvbd_release_gendisk(info); | ||
1252 | xenbus_frontend_closed(info->xbdev); | ||
1253 | } | ||
1254 | |||
1255 | mutex_unlock(&info->mutex); | ||
1256 | |||
1257 | if (!xbdev) { | ||
1258 | /* sudden device removal */ | ||
1259 | dev_info(disk_to_dev(bdev->bd_disk), "releasing disk\n"); | ||
1260 | xlvbd_release_gendisk(info); | ||
1261 | disk->private_data = NULL; | ||
1262 | kfree(info); | ||
1069 | } | 1263 | } |
1264 | |||
1265 | out: | ||
1266 | unlock_kernel(); | ||
1070 | return 0; | 1267 | return 0; |
1071 | } | 1268 | } |
1072 | 1269 | ||
@@ -1076,7 +1273,7 @@ static const struct block_device_operations xlvbd_block_fops = | |||
1076 | .open = blkif_open, | 1273 | .open = blkif_open, |
1077 | .release = blkif_release, | 1274 | .release = blkif_release, |
1078 | .getgeo = blkif_getgeo, | 1275 | .getgeo = blkif_getgeo, |
1079 | .locked_ioctl = blkif_ioctl, | 1276 | .ioctl = blkif_ioctl, |
1080 | }; | 1277 | }; |
1081 | 1278 | ||
1082 | 1279 | ||
@@ -1092,7 +1289,7 @@ static struct xenbus_driver blkfront = { | |||
1092 | .probe = blkfront_probe, | 1289 | .probe = blkfront_probe, |
1093 | .remove = blkfront_remove, | 1290 | .remove = blkfront_remove, |
1094 | .resume = blkfront_resume, | 1291 | .resume = blkfront_resume, |
1095 | .otherend_changed = backend_changed, | 1292 | .otherend_changed = blkback_changed, |
1096 | .is_ready = blkfront_is_ready, | 1293 | .is_ready = blkfront_is_ready, |
1097 | }; | 1294 | }; |
1098 | 1295 | ||
diff --git a/drivers/block/xsysace.c b/drivers/block/xsysace.c index a7b83c0a7eb5..b71888b909a0 100644 --- a/drivers/block/xsysace.c +++ b/drivers/block/xsysace.c | |||
@@ -89,6 +89,7 @@ | |||
89 | #include <linux/delay.h> | 89 | #include <linux/delay.h> |
90 | #include <linux/slab.h> | 90 | #include <linux/slab.h> |
91 | #include <linux/blkdev.h> | 91 | #include <linux/blkdev.h> |
92 | #include <linux/smp_lock.h> | ||
92 | #include <linux/ata.h> | 93 | #include <linux/ata.h> |
93 | #include <linux/hdreg.h> | 94 | #include <linux/hdreg.h> |
94 | #include <linux/platform_device.h> | 95 | #include <linux/platform_device.h> |
@@ -465,7 +466,7 @@ struct request *ace_get_next_request(struct request_queue * q) | |||
465 | struct request *req; | 466 | struct request *req; |
466 | 467 | ||
467 | while ((req = blk_peek_request(q)) != NULL) { | 468 | while ((req = blk_peek_request(q)) != NULL) { |
468 | if (blk_fs_request(req)) | 469 | if (req->cmd_type == REQ_TYPE_FS) |
469 | break; | 470 | break; |
470 | blk_start_request(req); | 471 | blk_start_request(req); |
471 | __blk_end_request_all(req, -EIO); | 472 | __blk_end_request_all(req, -EIO); |
@@ -901,11 +902,14 @@ static int ace_open(struct block_device *bdev, fmode_t mode) | |||
901 | 902 | ||
902 | dev_dbg(ace->dev, "ace_open() users=%i\n", ace->users + 1); | 903 | dev_dbg(ace->dev, "ace_open() users=%i\n", ace->users + 1); |
903 | 904 | ||
905 | lock_kernel(); | ||
904 | spin_lock_irqsave(&ace->lock, flags); | 906 | spin_lock_irqsave(&ace->lock, flags); |
905 | ace->users++; | 907 | ace->users++; |
906 | spin_unlock_irqrestore(&ace->lock, flags); | 908 | spin_unlock_irqrestore(&ace->lock, flags); |
907 | 909 | ||
908 | check_disk_change(bdev); | 910 | check_disk_change(bdev); |
911 | unlock_kernel(); | ||
912 | |||
909 | return 0; | 913 | return 0; |
910 | } | 914 | } |
911 | 915 | ||
@@ -917,6 +921,7 @@ static int ace_release(struct gendisk *disk, fmode_t mode) | |||
917 | 921 | ||
918 | dev_dbg(ace->dev, "ace_release() users=%i\n", ace->users - 1); | 922 | dev_dbg(ace->dev, "ace_release() users=%i\n", ace->users - 1); |
919 | 923 | ||
924 | lock_kernel(); | ||
920 | spin_lock_irqsave(&ace->lock, flags); | 925 | spin_lock_irqsave(&ace->lock, flags); |
921 | ace->users--; | 926 | ace->users--; |
922 | if (ace->users == 0) { | 927 | if (ace->users == 0) { |
@@ -924,6 +929,7 @@ static int ace_release(struct gendisk *disk, fmode_t mode) | |||
924 | ace_out(ace, ACE_CTRL, val & ~ACE_CTRL_LOCKREQ); | 929 | ace_out(ace, ACE_CTRL, val & ~ACE_CTRL_LOCKREQ); |
925 | } | 930 | } |
926 | spin_unlock_irqrestore(&ace->lock, flags); | 931 | spin_unlock_irqrestore(&ace->lock, flags); |
932 | unlock_kernel(); | ||
927 | return 0; | 933 | return 0; |
928 | } | 934 | } |
929 | 935 | ||
diff --git a/drivers/block/z2ram.c b/drivers/block/z2ram.c index 9114654b54d9..d75b2bb601ad 100644 --- a/drivers/block/z2ram.c +++ b/drivers/block/z2ram.c | |||
@@ -33,6 +33,7 @@ | |||
33 | #include <linux/module.h> | 33 | #include <linux/module.h> |
34 | #include <linux/blkdev.h> | 34 | #include <linux/blkdev.h> |
35 | #include <linux/bitops.h> | 35 | #include <linux/bitops.h> |
36 | #include <linux/smp_lock.h> | ||
36 | #include <linux/slab.h> | 37 | #include <linux/slab.h> |
37 | 38 | ||
38 | #include <asm/setup.h> | 39 | #include <asm/setup.h> |
@@ -153,6 +154,7 @@ static int z2_open(struct block_device *bdev, fmode_t mode) | |||
153 | 154 | ||
154 | device = MINOR(bdev->bd_dev); | 155 | device = MINOR(bdev->bd_dev); |
155 | 156 | ||
157 | lock_kernel(); | ||
156 | if ( current_device != -1 && current_device != device ) | 158 | if ( current_device != -1 && current_device != device ) |
157 | { | 159 | { |
158 | rc = -EBUSY; | 160 | rc = -EBUSY; |
@@ -294,20 +296,25 @@ static int z2_open(struct block_device *bdev, fmode_t mode) | |||
294 | set_capacity(z2ram_gendisk, z2ram_size >> 9); | 296 | set_capacity(z2ram_gendisk, z2ram_size >> 9); |
295 | } | 297 | } |
296 | 298 | ||
299 | unlock_kernel(); | ||
297 | return 0; | 300 | return 0; |
298 | 301 | ||
299 | err_out_kfree: | 302 | err_out_kfree: |
300 | kfree(z2ram_map); | 303 | kfree(z2ram_map); |
301 | err_out: | 304 | err_out: |
305 | unlock_kernel(); | ||
302 | return rc; | 306 | return rc; |
303 | } | 307 | } |
304 | 308 | ||
305 | static int | 309 | static int |
306 | z2_release(struct gendisk *disk, fmode_t mode) | 310 | z2_release(struct gendisk *disk, fmode_t mode) |
307 | { | 311 | { |
308 | if ( current_device == -1 ) | 312 | lock_kernel(); |
309 | return 0; | 313 | if ( current_device == -1 ) { |
310 | 314 | unlock_kernel(); | |
315 | return 0; | ||
316 | } | ||
317 | unlock_kernel(); | ||
311 | /* | 318 | /* |
312 | * FIXME: unmap memory | 319 | * FIXME: unmap memory |
313 | */ | 320 | */ |
diff --git a/drivers/cdrom/cdrom.c b/drivers/cdrom/cdrom.c index e3749d0ba68b..af13c62dc473 100644 --- a/drivers/cdrom/cdrom.c +++ b/drivers/cdrom/cdrom.c | |||
@@ -242,6 +242,8 @@ | |||
242 | 242 | ||
243 | -------------------------------------------------------------------------*/ | 243 | -------------------------------------------------------------------------*/ |
244 | 244 | ||
245 | #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt | ||
246 | |||
245 | #define REVISION "Revision: 3.20" | 247 | #define REVISION "Revision: 3.20" |
246 | #define VERSION "Id: cdrom.c 3.20 2003/12/17" | 248 | #define VERSION "Id: cdrom.c 3.20 2003/12/17" |
247 | 249 | ||
@@ -314,11 +316,17 @@ static const char *mrw_format_status[] = { | |||
314 | static const char *mrw_address_space[] = { "DMA", "GAA" }; | 316 | static const char *mrw_address_space[] = { "DMA", "GAA" }; |
315 | 317 | ||
316 | #if (ERRLOGMASK!=CD_NOTHING) | 318 | #if (ERRLOGMASK!=CD_NOTHING) |
317 | #define cdinfo(type, fmt, args...) \ | 319 | #define cdinfo(type, fmt, args...) \ |
318 | if ((ERRLOGMASK & type) || debug==1 ) \ | 320 | do { \ |
319 | printk(KERN_INFO "cdrom: " fmt, ## args) | 321 | if ((ERRLOGMASK & type) || debug == 1) \ |
322 | pr_info(fmt, ##args); \ | ||
323 | } while (0) | ||
320 | #else | 324 | #else |
321 | #define cdinfo(type, fmt, args...) | 325 | #define cdinfo(type, fmt, args...) \ |
326 | do { \ | ||
327 | if (0 && (ERRLOGMASK & type) || debug == 1) \ | ||
328 | pr_info(fmt, ##args); \ | ||
329 | } while (0) | ||
322 | #endif | 330 | #endif |
323 | 331 | ||
324 | /* These are used to simplify getting data in from and back to user land */ | 332 | /* These are used to simplify getting data in from and back to user land */ |
@@ -395,7 +403,7 @@ int register_cdrom(struct cdrom_device_info *cdi) | |||
395 | if (cdo->open == NULL || cdo->release == NULL) | 403 | if (cdo->open == NULL || cdo->release == NULL) |
396 | return -EINVAL; | 404 | return -EINVAL; |
397 | if (!banner_printed) { | 405 | if (!banner_printed) { |
398 | printk(KERN_INFO "Uniform CD-ROM driver " REVISION "\n"); | 406 | pr_info("Uniform CD-ROM driver " REVISION "\n"); |
399 | banner_printed = 1; | 407 | banner_printed = 1; |
400 | cdrom_sysctl_register(); | 408 | cdrom_sysctl_register(); |
401 | } | 409 | } |
@@ -546,7 +554,7 @@ static int cdrom_mrw_bgformat(struct cdrom_device_info *cdi, int cont) | |||
546 | unsigned char buffer[12]; | 554 | unsigned char buffer[12]; |
547 | int ret; | 555 | int ret; |
548 | 556 | ||
549 | printk(KERN_INFO "cdrom: %sstarting format\n", cont ? "Re" : ""); | 557 | pr_info("%sstarting format\n", cont ? "Re" : ""); |
550 | 558 | ||
551 | /* | 559 | /* |
552 | * FmtData bit set (bit 4), format type is 1 | 560 | * FmtData bit set (bit 4), format type is 1 |
@@ -576,7 +584,7 @@ static int cdrom_mrw_bgformat(struct cdrom_device_info *cdi, int cont) | |||
576 | 584 | ||
577 | ret = cdi->ops->generic_packet(cdi, &cgc); | 585 | ret = cdi->ops->generic_packet(cdi, &cgc); |
578 | if (ret) | 586 | if (ret) |
579 | printk(KERN_INFO "cdrom: bgformat failed\n"); | 587 | pr_info("bgformat failed\n"); |
580 | 588 | ||
581 | return ret; | 589 | return ret; |
582 | } | 590 | } |
@@ -622,8 +630,7 @@ static int cdrom_mrw_exit(struct cdrom_device_info *cdi) | |||
622 | 630 | ||
623 | ret = 0; | 631 | ret = 0; |
624 | if (di.mrw_status == CDM_MRW_BGFORMAT_ACTIVE) { | 632 | if (di.mrw_status == CDM_MRW_BGFORMAT_ACTIVE) { |
625 | printk(KERN_INFO "cdrom: issuing MRW back ground " | 633 | pr_info("issuing MRW background format suspend\n"); |
626 | "format suspend\n"); | ||
627 | ret = cdrom_mrw_bgformat_susp(cdi, 0); | 634 | ret = cdrom_mrw_bgformat_susp(cdi, 0); |
628 | } | 635 | } |
629 | 636 | ||
@@ -658,7 +665,8 @@ static int cdrom_mrw_set_lba_space(struct cdrom_device_info *cdi, int space) | |||
658 | if ((ret = cdrom_mode_select(cdi, &cgc))) | 665 | if ((ret = cdrom_mode_select(cdi, &cgc))) |
659 | return ret; | 666 | return ret; |
660 | 667 | ||
661 | printk(KERN_INFO "cdrom: %s: mrw address space %s selected\n", cdi->name, mrw_address_space[space]); | 668 | pr_info("%s: mrw address space %s selected\n", |
669 | cdi->name, mrw_address_space[space]); | ||
662 | return 0; | 670 | return 0; |
663 | } | 671 | } |
664 | 672 | ||
@@ -762,7 +770,7 @@ static int cdrom_mrw_open_write(struct cdrom_device_info *cdi) | |||
762 | * always reset to DMA lba space on open | 770 | * always reset to DMA lba space on open |
763 | */ | 771 | */ |
764 | if (cdrom_mrw_set_lba_space(cdi, MRW_LBA_DMA)) { | 772 | if (cdrom_mrw_set_lba_space(cdi, MRW_LBA_DMA)) { |
765 | printk(KERN_ERR "cdrom: failed setting lba address space\n"); | 773 | pr_err("failed setting lba address space\n"); |
766 | return 1; | 774 | return 1; |
767 | } | 775 | } |
768 | 776 | ||
@@ -781,8 +789,7 @@ static int cdrom_mrw_open_write(struct cdrom_device_info *cdi) | |||
781 | * 3 - MRW formatting complete | 789 | * 3 - MRW formatting complete |
782 | */ | 790 | */ |
783 | ret = 0; | 791 | ret = 0; |
784 | printk(KERN_INFO "cdrom open: mrw_status '%s'\n", | 792 | pr_info("open: mrw_status '%s'\n", mrw_format_status[di.mrw_status]); |
785 | mrw_format_status[di.mrw_status]); | ||
786 | if (!di.mrw_status) | 793 | if (!di.mrw_status) |
787 | ret = 1; | 794 | ret = 1; |
788 | else if (di.mrw_status == CDM_MRW_BGFORMAT_INACTIVE && | 795 | else if (di.mrw_status == CDM_MRW_BGFORMAT_INACTIVE && |
@@ -932,8 +939,7 @@ static void cdrom_dvd_rw_close_write(struct cdrom_device_info *cdi) | |||
932 | return; | 939 | return; |
933 | } | 940 | } |
934 | 941 | ||
935 | printk(KERN_INFO "cdrom: %s: dirty DVD+RW media, \"finalizing\"\n", | 942 | pr_info("%s: dirty DVD+RW media, \"finalizing\"\n", cdi->name); |
936 | cdi->name); | ||
937 | 943 | ||
938 | init_cdrom_command(&cgc, NULL, 0, CGC_DATA_NONE); | 944 | init_cdrom_command(&cgc, NULL, 0, CGC_DATA_NONE); |
939 | cgc.cmd[0] = GPCMD_FLUSH_CACHE; | 945 | cgc.cmd[0] = GPCMD_FLUSH_CACHE; |
@@ -2176,7 +2182,7 @@ retry: | |||
2176 | * frame dma, so drop to single frame dma if we need to | 2182 | * frame dma, so drop to single frame dma if we need to |
2177 | */ | 2183 | */ |
2178 | if (cdi->cdda_method == CDDA_BPC_FULL && nframes > 1) { | 2184 | if (cdi->cdda_method == CDDA_BPC_FULL && nframes > 1) { |
2179 | printk("cdrom: dropping to single frame dma\n"); | 2185 | pr_info("dropping to single frame dma\n"); |
2180 | cdi->cdda_method = CDDA_BPC_SINGLE; | 2186 | cdi->cdda_method = CDDA_BPC_SINGLE; |
2181 | goto retry; | 2187 | goto retry; |
2182 | } | 2188 | } |
@@ -2189,7 +2195,7 @@ retry: | |||
2189 | if (cdi->last_sense != 0x04 && cdi->last_sense != 0x0b) | 2195 | if (cdi->last_sense != 0x04 && cdi->last_sense != 0x0b) |
2190 | return ret; | 2196 | return ret; |
2191 | 2197 | ||
2192 | printk("cdrom: dropping to old style cdda (sense=%x)\n", cdi->last_sense); | 2198 | pr_info("dropping to old style cdda (sense=%x)\n", cdi->last_sense); |
2193 | cdi->cdda_method = CDDA_OLD; | 2199 | cdi->cdda_method = CDDA_OLD; |
2194 | return cdrom_read_cdda_old(cdi, ubuf, lba, nframes); | 2200 | return cdrom_read_cdda_old(cdi, ubuf, lba, nframes); |
2195 | } | 2201 | } |
@@ -3401,7 +3407,7 @@ static int cdrom_print_info(const char *header, int val, char *info, | |||
3401 | "\t%d", CDROM_CAN(val) != 0); | 3407 | "\t%d", CDROM_CAN(val) != 0); |
3402 | break; | 3408 | break; |
3403 | default: | 3409 | default: |
3404 | printk(KERN_INFO "cdrom: invalid option%d\n", option); | 3410 | pr_info("invalid option%d\n", option); |
3405 | return 1; | 3411 | return 1; |
3406 | } | 3412 | } |
3407 | if (!ret) | 3413 | if (!ret) |
@@ -3491,7 +3497,7 @@ doit: | |||
3491 | mutex_unlock(&cdrom_mutex); | 3497 | mutex_unlock(&cdrom_mutex); |
3492 | return proc_dostring(ctl, write, buffer, lenp, ppos); | 3498 | return proc_dostring(ctl, write, buffer, lenp, ppos); |
3493 | done: | 3499 | done: |
3494 | printk(KERN_INFO "cdrom: info buffer too small\n"); | 3500 | pr_info("info buffer too small\n"); |
3495 | goto doit; | 3501 | goto doit; |
3496 | } | 3502 | } |
3497 | 3503 | ||
@@ -3665,7 +3671,7 @@ static int __init cdrom_init(void) | |||
3665 | 3671 | ||
3666 | static void __exit cdrom_exit(void) | 3672 | static void __exit cdrom_exit(void) |
3667 | { | 3673 | { |
3668 | printk(KERN_INFO "Uniform CD-ROM driver unloaded\n"); | 3674 | pr_info("Uniform CD-ROM driver unloaded\n"); |
3669 | cdrom_sysctl_unregister(); | 3675 | cdrom_sysctl_unregister(); |
3670 | } | 3676 | } |
3671 | 3677 | ||
diff --git a/drivers/cdrom/gdrom.c b/drivers/cdrom/gdrom.c index 03c71f7698cb..261107d1457c 100644 --- a/drivers/cdrom/gdrom.c +++ b/drivers/cdrom/gdrom.c | |||
@@ -19,6 +19,8 @@ | |||
19 | * | 19 | * |
20 | */ | 20 | */ |
21 | 21 | ||
22 | #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt | ||
23 | |||
22 | #include <linux/init.h> | 24 | #include <linux/init.h> |
23 | #include <linux/module.h> | 25 | #include <linux/module.h> |
24 | #include <linux/fs.h> | 26 | #include <linux/fs.h> |
@@ -32,6 +34,7 @@ | |||
32 | #include <linux/blkdev.h> | 34 | #include <linux/blkdev.h> |
33 | #include <linux/interrupt.h> | 35 | #include <linux/interrupt.h> |
34 | #include <linux/device.h> | 36 | #include <linux/device.h> |
37 | #include <linux/smp_lock.h> | ||
35 | #include <linux/wait.h> | 38 | #include <linux/wait.h> |
36 | #include <linux/workqueue.h> | 39 | #include <linux/workqueue.h> |
37 | #include <linux/platform_device.h> | 40 | #include <linux/platform_device.h> |
@@ -339,8 +342,7 @@ static int gdrom_get_last_session(struct cdrom_device_info *cd_info, | |||
339 | tocuse = 0; | 342 | tocuse = 0; |
340 | err = gdrom_readtoc_cmd(gd.toc, 0); | 343 | err = gdrom_readtoc_cmd(gd.toc, 0); |
341 | if (err) { | 344 | if (err) { |
342 | printk(KERN_INFO "GDROM: Could not get CD " | 345 | pr_info("Could not get CD table of contents\n"); |
343 | "table of contents\n"); | ||
344 | return -ENXIO; | 346 | return -ENXIO; |
345 | } | 347 | } |
346 | } | 348 | } |
@@ -357,8 +359,7 @@ static int gdrom_get_last_session(struct cdrom_device_info *cd_info, | |||
357 | } while (track >= fentry); | 359 | } while (track >= fentry); |
358 | 360 | ||
359 | if ((track > 100) || (track < get_entry_track(gd.toc->first))) { | 361 | if ((track > 100) || (track < get_entry_track(gd.toc->first))) { |
360 | printk(KERN_INFO "GDROM: No data on the last " | 362 | pr_info("No data on the last session of the CD\n"); |
361 | "session of the CD\n"); | ||
362 | gdrom_getsense(NULL); | 363 | gdrom_getsense(NULL); |
363 | return -ENXIO; | 364 | return -ENXIO; |
364 | } | 365 | } |
@@ -451,14 +452,14 @@ static int gdrom_getsense(short *bufstring) | |||
451 | goto cleanup_sense; | 452 | goto cleanup_sense; |
452 | insw(GDROM_DATA_REG, &sense, sense_command->buflen/2); | 453 | insw(GDROM_DATA_REG, &sense, sense_command->buflen/2); |
453 | if (sense[1] & 40) { | 454 | if (sense[1] & 40) { |
454 | printk(KERN_INFO "GDROM: Drive not ready - command aborted\n"); | 455 | pr_info("Drive not ready - command aborted\n"); |
455 | goto cleanup_sense; | 456 | goto cleanup_sense; |
456 | } | 457 | } |
457 | sense_key = sense[1] & 0x0F; | 458 | sense_key = sense[1] & 0x0F; |
458 | if (sense_key < ARRAY_SIZE(sense_texts)) | 459 | if (sense_key < ARRAY_SIZE(sense_texts)) |
459 | printk(KERN_INFO "GDROM: %s\n", sense_texts[sense_key].text); | 460 | pr_info("%s\n", sense_texts[sense_key].text); |
460 | else | 461 | else |
461 | printk(KERN_ERR "GDROM: Unknown sense key: %d\n", sense_key); | 462 | pr_err("Unknown sense key: %d\n", sense_key); |
462 | if (bufstring) /* return addional sense data */ | 463 | if (bufstring) /* return addional sense data */ |
463 | memcpy(bufstring, &sense[4], 2); | 464 | memcpy(bufstring, &sense[4], 2); |
464 | if (sense_key < 2) | 465 | if (sense_key < 2) |
@@ -492,12 +493,18 @@ static struct cdrom_device_ops gdrom_ops = { | |||
492 | 493 | ||
493 | static int gdrom_bdops_open(struct block_device *bdev, fmode_t mode) | 494 | static int gdrom_bdops_open(struct block_device *bdev, fmode_t mode) |
494 | { | 495 | { |
495 | return cdrom_open(gd.cd_info, bdev, mode); | 496 | int ret; |
497 | lock_kernel(); | ||
498 | ret = cdrom_open(gd.cd_info, bdev, mode); | ||
499 | unlock_kernel(); | ||
500 | return ret; | ||
496 | } | 501 | } |
497 | 502 | ||
498 | static int gdrom_bdops_release(struct gendisk *disk, fmode_t mode) | 503 | static int gdrom_bdops_release(struct gendisk *disk, fmode_t mode) |
499 | { | 504 | { |
505 | lock_kernel(); | ||
500 | cdrom_release(gd.cd_info, mode); | 506 | cdrom_release(gd.cd_info, mode); |
507 | unlock_kernel(); | ||
501 | return 0; | 508 | return 0; |
502 | } | 509 | } |
503 | 510 | ||
@@ -509,7 +516,13 @@ static int gdrom_bdops_mediachanged(struct gendisk *disk) | |||
509 | static int gdrom_bdops_ioctl(struct block_device *bdev, fmode_t mode, | 516 | static int gdrom_bdops_ioctl(struct block_device *bdev, fmode_t mode, |
510 | unsigned cmd, unsigned long arg) | 517 | unsigned cmd, unsigned long arg) |
511 | { | 518 | { |
512 | return cdrom_ioctl(gd.cd_info, bdev, mode, cmd, arg); | 519 | int ret; |
520 | |||
521 | lock_kernel(); | ||
522 | ret = cdrom_ioctl(gd.cd_info, bdev, mode, cmd, arg); | ||
523 | unlock_kernel(); | ||
524 | |||
525 | return ret; | ||
513 | } | 526 | } |
514 | 527 | ||
515 | static const struct block_device_operations gdrom_bdops = { | 528 | static const struct block_device_operations gdrom_bdops = { |
@@ -517,7 +530,7 @@ static const struct block_device_operations gdrom_bdops = { | |||
517 | .open = gdrom_bdops_open, | 530 | .open = gdrom_bdops_open, |
518 | .release = gdrom_bdops_release, | 531 | .release = gdrom_bdops_release, |
519 | .media_changed = gdrom_bdops_mediachanged, | 532 | .media_changed = gdrom_bdops_mediachanged, |
520 | .locked_ioctl = gdrom_bdops_ioctl, | 533 | .ioctl = gdrom_bdops_ioctl, |
521 | }; | 534 | }; |
522 | 535 | ||
523 | static irqreturn_t gdrom_command_interrupt(int irq, void *dev_id) | 536 | static irqreturn_t gdrom_command_interrupt(int irq, void *dev_id) |
@@ -643,14 +656,13 @@ static void gdrom_request(struct request_queue *rq) | |||
643 | struct request *req; | 656 | struct request *req; |
644 | 657 | ||
645 | while ((req = blk_fetch_request(rq)) != NULL) { | 658 | while ((req = blk_fetch_request(rq)) != NULL) { |
646 | if (!blk_fs_request(req)) { | 659 | if (req->cmd_type != REQ_TYPE_FS) { |
647 | printk(KERN_DEBUG "GDROM: Non-fs request ignored\n"); | 660 | printk(KERN_DEBUG "gdrom: Non-fs request ignored\n"); |
648 | __blk_end_request_all(req, -EIO); | 661 | __blk_end_request_all(req, -EIO); |
649 | continue; | 662 | continue; |
650 | } | 663 | } |
651 | if (rq_data_dir(req) != READ) { | 664 | if (rq_data_dir(req) != READ) { |
652 | printk(KERN_NOTICE "GDROM: Read only device -"); | 665 | pr_notice("Read only device - write request ignored\n"); |
653 | printk(" write request ignored\n"); | ||
654 | __blk_end_request_all(req, -EIO); | 666 | __blk_end_request_all(req, -EIO); |
655 | continue; | 667 | continue; |
656 | } | 668 | } |
@@ -685,7 +697,7 @@ static int __devinit gdrom_outputversion(void) | |||
685 | firmw_ver = kstrndup(id->firmver, 16, GFP_KERNEL); | 697 | firmw_ver = kstrndup(id->firmver, 16, GFP_KERNEL); |
686 | if (!firmw_ver) | 698 | if (!firmw_ver) |
687 | goto free_manuf_name; | 699 | goto free_manuf_name; |
688 | printk(KERN_INFO "GDROM: %s from %s with firmware %s\n", | 700 | pr_info("%s from %s with firmware %s\n", |
689 | model_name, manuf_name, firmw_ver); | 701 | model_name, manuf_name, firmw_ver); |
690 | err = 0; | 702 | err = 0; |
691 | kfree(firmw_ver); | 703 | kfree(firmw_ver); |
@@ -757,7 +769,7 @@ static int __devinit probe_gdrom(struct platform_device *devptr) | |||
757 | int err; | 769 | int err; |
758 | /* Start the device */ | 770 | /* Start the device */ |
759 | if (gdrom_execute_diagnostic() != 1) { | 771 | if (gdrom_execute_diagnostic() != 1) { |
760 | printk(KERN_WARNING "GDROM: ATA Probe for GDROM failed.\n"); | 772 | pr_warning("ATA Probe for GDROM failed\n"); |
761 | return -ENODEV; | 773 | return -ENODEV; |
762 | } | 774 | } |
763 | /* Print out firmware ID */ | 775 | /* Print out firmware ID */ |
@@ -767,7 +779,7 @@ static int __devinit probe_gdrom(struct platform_device *devptr) | |||
767 | gdrom_major = register_blkdev(0, GDROM_DEV_NAME); | 779 | gdrom_major = register_blkdev(0, GDROM_DEV_NAME); |
768 | if (gdrom_major <= 0) | 780 | if (gdrom_major <= 0) |
769 | return gdrom_major; | 781 | return gdrom_major; |
770 | printk(KERN_INFO "GDROM: Registered with major number %d\n", | 782 | pr_info("Registered with major number %d\n", |
771 | gdrom_major); | 783 | gdrom_major); |
772 | /* Specify basic properties of drive */ | 784 | /* Specify basic properties of drive */ |
773 | gd.cd_info = kzalloc(sizeof(struct cdrom_device_info), GFP_KERNEL); | 785 | gd.cd_info = kzalloc(sizeof(struct cdrom_device_info), GFP_KERNEL); |
@@ -818,7 +830,7 @@ probe_fail_no_disk: | |||
818 | unregister_blkdev(gdrom_major, GDROM_DEV_NAME); | 830 | unregister_blkdev(gdrom_major, GDROM_DEV_NAME); |
819 | gdrom_major = 0; | 831 | gdrom_major = 0; |
820 | probe_fail_no_mem: | 832 | probe_fail_no_mem: |
821 | printk(KERN_WARNING "GDROM: Probe failed - error is 0x%X\n", err); | 833 | pr_warning("Probe failed - error is 0x%X\n", err); |
822 | return err; | 834 | return err; |
823 | } | 835 | } |
824 | 836 | ||
diff --git a/drivers/cdrom/viocd.c b/drivers/cdrom/viocd.c index 451cd7071b1d..56bf9f44700c 100644 --- a/drivers/cdrom/viocd.c +++ b/drivers/cdrom/viocd.c | |||
@@ -31,6 +31,8 @@ | |||
31 | * the OS/400 partition. | 31 | * the OS/400 partition. |
32 | */ | 32 | */ |
33 | 33 | ||
34 | #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt | ||
35 | |||
34 | #include <linux/major.h> | 36 | #include <linux/major.h> |
35 | #include <linux/blkdev.h> | 37 | #include <linux/blkdev.h> |
36 | #include <linux/cdrom.h> | 38 | #include <linux/cdrom.h> |
@@ -40,6 +42,7 @@ | |||
40 | #include <linux/module.h> | 42 | #include <linux/module.h> |
41 | #include <linux/completion.h> | 43 | #include <linux/completion.h> |
42 | #include <linux/proc_fs.h> | 44 | #include <linux/proc_fs.h> |
45 | #include <linux/smp_lock.h> | ||
43 | #include <linux/seq_file.h> | 46 | #include <linux/seq_file.h> |
44 | #include <linux/scatterlist.h> | 47 | #include <linux/scatterlist.h> |
45 | 48 | ||
@@ -53,9 +56,6 @@ | |||
53 | 56 | ||
54 | #define VIOCD_VERS "1.06" | 57 | #define VIOCD_VERS "1.06" |
55 | 58 | ||
56 | #define VIOCD_KERN_WARNING KERN_WARNING "viocd: " | ||
57 | #define VIOCD_KERN_INFO KERN_INFO "viocd: " | ||
58 | |||
59 | /* | 59 | /* |
60 | * Should probably make this a module parameter....sigh | 60 | * Should probably make this a module parameter....sigh |
61 | */ | 61 | */ |
@@ -154,13 +154,21 @@ static const struct file_operations proc_viocd_operations = { | |||
154 | static int viocd_blk_open(struct block_device *bdev, fmode_t mode) | 154 | static int viocd_blk_open(struct block_device *bdev, fmode_t mode) |
155 | { | 155 | { |
156 | struct disk_info *di = bdev->bd_disk->private_data; | 156 | struct disk_info *di = bdev->bd_disk->private_data; |
157 | return cdrom_open(&di->viocd_info, bdev, mode); | 157 | int ret; |
158 | |||
159 | lock_kernel(); | ||
160 | ret = cdrom_open(&di->viocd_info, bdev, mode); | ||
161 | unlock_kernel(); | ||
162 | |||
163 | return ret; | ||
158 | } | 164 | } |
159 | 165 | ||
160 | static int viocd_blk_release(struct gendisk *disk, fmode_t mode) | 166 | static int viocd_blk_release(struct gendisk *disk, fmode_t mode) |
161 | { | 167 | { |
162 | struct disk_info *di = disk->private_data; | 168 | struct disk_info *di = disk->private_data; |
169 | lock_kernel(); | ||
163 | cdrom_release(&di->viocd_info, mode); | 170 | cdrom_release(&di->viocd_info, mode); |
171 | unlock_kernel(); | ||
164 | return 0; | 172 | return 0; |
165 | } | 173 | } |
166 | 174 | ||
@@ -168,7 +176,13 @@ static int viocd_blk_ioctl(struct block_device *bdev, fmode_t mode, | |||
168 | unsigned cmd, unsigned long arg) | 176 | unsigned cmd, unsigned long arg) |
169 | { | 177 | { |
170 | struct disk_info *di = bdev->bd_disk->private_data; | 178 | struct disk_info *di = bdev->bd_disk->private_data; |
171 | return cdrom_ioctl(&di->viocd_info, bdev, mode, cmd, arg); | 179 | int ret; |
180 | |||
181 | lock_kernel(); | ||
182 | ret = cdrom_ioctl(&di->viocd_info, bdev, mode, cmd, arg); | ||
183 | unlock_kernel(); | ||
184 | |||
185 | return ret; | ||
172 | } | 186 | } |
173 | 187 | ||
174 | static int viocd_blk_media_changed(struct gendisk *disk) | 188 | static int viocd_blk_media_changed(struct gendisk *disk) |
@@ -181,7 +195,7 @@ static const struct block_device_operations viocd_fops = { | |||
181 | .owner = THIS_MODULE, | 195 | .owner = THIS_MODULE, |
182 | .open = viocd_blk_open, | 196 | .open = viocd_blk_open, |
183 | .release = viocd_blk_release, | 197 | .release = viocd_blk_release, |
184 | .locked_ioctl = viocd_blk_ioctl, | 198 | .ioctl = viocd_blk_ioctl, |
185 | .media_changed = viocd_blk_media_changed, | 199 | .media_changed = viocd_blk_media_changed, |
186 | }; | 200 | }; |
187 | 201 | ||
@@ -202,9 +216,8 @@ static int viocd_open(struct cdrom_device_info *cdi, int purpose) | |||
202 | (u64)&we, VIOVERSION << 16, ((u64)device_no << 48), | 216 | (u64)&we, VIOVERSION << 16, ((u64)device_no << 48), |
203 | 0, 0, 0); | 217 | 0, 0, 0); |
204 | if (hvrc != 0) { | 218 | if (hvrc != 0) { |
205 | printk(VIOCD_KERN_WARNING | 219 | pr_warning("bad rc on HvCallEvent_signalLpEventFast %d\n", |
206 | "bad rc on HvCallEvent_signalLpEventFast %d\n", | 220 | (int)hvrc); |
207 | (int)hvrc); | ||
208 | return -EIO; | 221 | return -EIO; |
209 | } | 222 | } |
210 | 223 | ||
@@ -213,8 +226,8 @@ static int viocd_open(struct cdrom_device_info *cdi, int purpose) | |||
213 | if (we.rc) { | 226 | if (we.rc) { |
214 | const struct vio_error_entry *err = | 227 | const struct vio_error_entry *err = |
215 | vio_lookup_rc(viocd_err_table, we.sub_result); | 228 | vio_lookup_rc(viocd_err_table, we.sub_result); |
216 | printk(VIOCD_KERN_WARNING "bad rc %d:0x%04X on open: %s\n", | 229 | pr_warning("bad rc %d:0x%04X on open: %s\n", |
217 | we.rc, we.sub_result, err->msg); | 230 | we.rc, we.sub_result, err->msg); |
218 | return -err->errno; | 231 | return -err->errno; |
219 | } | 232 | } |
220 | 233 | ||
@@ -234,9 +247,8 @@ static void viocd_release(struct cdrom_device_info *cdi) | |||
234 | viopath_targetinst(viopath_hostLp), 0, | 247 | viopath_targetinst(viopath_hostLp), 0, |
235 | VIOVERSION << 16, ((u64)device_no << 48), 0, 0, 0); | 248 | VIOVERSION << 16, ((u64)device_no << 48), 0, 0, 0); |
236 | if (hvrc != 0) | 249 | if (hvrc != 0) |
237 | printk(VIOCD_KERN_WARNING | 250 | pr_warning("bad rc on HvCallEvent_signalLpEventFast %d\n", |
238 | "bad rc on HvCallEvent_signalLpEventFast %d\n", | 251 | (int)hvrc); |
239 | (int)hvrc); | ||
240 | } | 252 | } |
241 | 253 | ||
242 | /* Send a read or write request to OS/400 */ | 254 | /* Send a read or write request to OS/400 */ |
@@ -262,13 +274,12 @@ static int send_request(struct request *req) | |||
262 | 274 | ||
263 | sg_init_table(&sg, 1); | 275 | sg_init_table(&sg, 1); |
264 | if (blk_rq_map_sg(req->q, req, &sg) == 0) { | 276 | if (blk_rq_map_sg(req->q, req, &sg) == 0) { |
265 | printk(VIOCD_KERN_WARNING | 277 | pr_warning("error setting up scatter/gather list\n"); |
266 | "error setting up scatter/gather list\n"); | ||
267 | return -1; | 278 | return -1; |
268 | } | 279 | } |
269 | 280 | ||
270 | if (dma_map_sg(diskinfo->dev, &sg, 1, direction) == 0) { | 281 | if (dma_map_sg(diskinfo->dev, &sg, 1, direction) == 0) { |
271 | printk(VIOCD_KERN_WARNING "error allocating sg tce\n"); | 282 | pr_warning("error allocating sg tce\n"); |
272 | return -1; | 283 | return -1; |
273 | } | 284 | } |
274 | dmaaddr = sg_dma_address(&sg); | 285 | dmaaddr = sg_dma_address(&sg); |
@@ -284,7 +295,7 @@ static int send_request(struct request *req) | |||
284 | ((u64)DEVICE_NR(diskinfo) << 48) | dmaaddr, | 295 | ((u64)DEVICE_NR(diskinfo) << 48) | dmaaddr, |
285 | (u64)blk_rq_pos(req) * 512, len, 0); | 296 | (u64)blk_rq_pos(req) * 512, len, 0); |
286 | if (hvrc != HvLpEvent_Rc_Good) { | 297 | if (hvrc != HvLpEvent_Rc_Good) { |
287 | printk(VIOCD_KERN_WARNING "hv error on op %d\n", (int)hvrc); | 298 | pr_warning("hv error on op %d\n", (int)hvrc); |
288 | return -1; | 299 | return -1; |
289 | } | 300 | } |
290 | 301 | ||
@@ -298,11 +309,10 @@ static void do_viocd_request(struct request_queue *q) | |||
298 | struct request *req; | 309 | struct request *req; |
299 | 310 | ||
300 | while ((rwreq == 0) && ((req = blk_fetch_request(q)) != NULL)) { | 311 | while ((rwreq == 0) && ((req = blk_fetch_request(q)) != NULL)) { |
301 | if (!blk_fs_request(req)) | 312 | if (req->cmd_type != REQ_TYPE_FS) |
302 | __blk_end_request_all(req, -EIO); | 313 | __blk_end_request_all(req, -EIO); |
303 | else if (send_request(req) < 0) { | 314 | else if (send_request(req) < 0) { |
304 | printk(VIOCD_KERN_WARNING | 315 | pr_warning("unable to send message to OS/400!\n"); |
305 | "unable to send message to OS/400!"); | ||
306 | __blk_end_request_all(req, -EIO); | 316 | __blk_end_request_all(req, -EIO); |
307 | } else | 317 | } else |
308 | rwreq++; | 318 | rwreq++; |
@@ -327,8 +337,8 @@ static int viocd_media_changed(struct cdrom_device_info *cdi, int disc_nr) | |||
327 | (u64)&we, VIOVERSION << 16, ((u64)device_no << 48), | 337 | (u64)&we, VIOVERSION << 16, ((u64)device_no << 48), |
328 | 0, 0, 0); | 338 | 0, 0, 0); |
329 | if (hvrc != 0) { | 339 | if (hvrc != 0) { |
330 | printk(VIOCD_KERN_WARNING "bad rc on HvCallEvent_signalLpEventFast %d\n", | 340 | pr_warning("bad rc on HvCallEvent_signalLpEventFast %d\n", |
331 | (int)hvrc); | 341 | (int)hvrc); |
332 | return -EIO; | 342 | return -EIO; |
333 | } | 343 | } |
334 | 344 | ||
@@ -338,9 +348,8 @@ static int viocd_media_changed(struct cdrom_device_info *cdi, int disc_nr) | |||
338 | if (we.rc) { | 348 | if (we.rc) { |
339 | const struct vio_error_entry *err = | 349 | const struct vio_error_entry *err = |
340 | vio_lookup_rc(viocd_err_table, we.sub_result); | 350 | vio_lookup_rc(viocd_err_table, we.sub_result); |
341 | printk(VIOCD_KERN_WARNING | 351 | pr_warning("bad rc %d:0x%04X on check_change: %s; Assuming no change\n", |
342 | "bad rc %d:0x%04X on check_change: %s; Assuming no change\n", | 352 | we.rc, we.sub_result, err->msg); |
343 | we.rc, we.sub_result, err->msg); | ||
344 | return 0; | 353 | return 0; |
345 | } | 354 | } |
346 | 355 | ||
@@ -367,8 +376,8 @@ static int viocd_lock_door(struct cdrom_device_info *cdi, int locking) | |||
367 | (u64)&we, VIOVERSION << 16, | 376 | (u64)&we, VIOVERSION << 16, |
368 | (device_no << 48) | (flags << 32), 0, 0, 0); | 377 | (device_no << 48) | (flags << 32), 0, 0, 0); |
369 | if (hvrc != 0) { | 378 | if (hvrc != 0) { |
370 | printk(VIOCD_KERN_WARNING "bad rc on HvCallEvent_signalLpEventFast %d\n", | 379 | pr_warning("bad rc on HvCallEvent_signalLpEventFast %d\n", |
371 | (int)hvrc); | 380 | (int)hvrc); |
372 | return -EIO; | 381 | return -EIO; |
373 | } | 382 | } |
374 | 383 | ||
@@ -455,8 +464,7 @@ static void vio_handle_cd_event(struct HvLpEvent *event) | |||
455 | return; | 464 | return; |
456 | /* First, we should NEVER get an int here...only acks */ | 465 | /* First, we should NEVER get an int here...only acks */ |
457 | if (hvlpevent_is_int(event)) { | 466 | if (hvlpevent_is_int(event)) { |
458 | printk(VIOCD_KERN_WARNING | 467 | pr_warning("Yikes! got an int in viocd event handler!\n"); |
459 | "Yikes! got an int in viocd event handler!\n"); | ||
460 | if (hvlpevent_need_ack(event)) { | 468 | if (hvlpevent_need_ack(event)) { |
461 | event->xRc = HvLpEvent_Rc_InvalidSubtype; | 469 | event->xRc = HvLpEvent_Rc_InvalidSubtype; |
462 | HvCallEvent_ackLpEvent(event); | 470 | HvCallEvent_ackLpEvent(event); |
@@ -510,10 +518,9 @@ return_complete: | |||
510 | const struct vio_error_entry *err = | 518 | const struct vio_error_entry *err = |
511 | vio_lookup_rc(viocd_err_table, | 519 | vio_lookup_rc(viocd_err_table, |
512 | bevent->sub_result); | 520 | bevent->sub_result); |
513 | printk(VIOCD_KERN_WARNING "request %p failed " | 521 | pr_warning("request %p failed with rc %d:0x%04X: %s\n", |
514 | "with rc %d:0x%04X: %s\n", | 522 | req, event->xRc, |
515 | req, event->xRc, | 523 | bevent->sub_result, err->msg); |
516 | bevent->sub_result, err->msg); | ||
517 | __blk_end_request_all(req, -EIO); | 524 | __blk_end_request_all(req, -EIO); |
518 | } else | 525 | } else |
519 | __blk_end_request_all(req, 0); | 526 | __blk_end_request_all(req, 0); |
@@ -524,9 +531,8 @@ return_complete: | |||
524 | break; | 531 | break; |
525 | 532 | ||
526 | default: | 533 | default: |
527 | printk(VIOCD_KERN_WARNING | 534 | pr_warning("message with invalid subtype %0x04X!\n", |
528 | "message with invalid subtype %0x04X!\n", | 535 | event->xSubtype & VIOMINOR_SUBTYPE_MASK); |
529 | event->xSubtype & VIOMINOR_SUBTYPE_MASK); | ||
530 | if (hvlpevent_need_ack(event)) { | 536 | if (hvlpevent_need_ack(event)) { |
531 | event->xRc = HvLpEvent_Rc_InvalidSubtype; | 537 | event->xRc = HvLpEvent_Rc_InvalidSubtype; |
532 | HvCallEvent_ackLpEvent(event); | 538 | HvCallEvent_ackLpEvent(event); |
@@ -593,23 +599,19 @@ static int viocd_probe(struct vio_dev *vdev, const struct vio_device_id *id) | |||
593 | sprintf(c->name, VIOCD_DEVICE "%c", 'a' + deviceno); | 599 | sprintf(c->name, VIOCD_DEVICE "%c", 'a' + deviceno); |
594 | 600 | ||
595 | if (register_cdrom(c) != 0) { | 601 | if (register_cdrom(c) != 0) { |
596 | printk(VIOCD_KERN_WARNING "Cannot register viocd CD-ROM %s!\n", | 602 | pr_warning("Cannot register viocd CD-ROM %s!\n", c->name); |
597 | c->name); | ||
598 | goto out; | 603 | goto out; |
599 | } | 604 | } |
600 | printk(VIOCD_KERN_INFO "cd %s is iSeries resource %10.10s " | 605 | pr_info("cd %s is iSeries resource %10.10s type %4.4s, model %3.3s\n", |
601 | "type %4.4s, model %3.3s\n", | 606 | c->name, d->rsrcname, d->type, d->model); |
602 | c->name, d->rsrcname, d->type, d->model); | ||
603 | q = blk_init_queue(do_viocd_request, &viocd_reqlock); | 607 | q = blk_init_queue(do_viocd_request, &viocd_reqlock); |
604 | if (q == NULL) { | 608 | if (q == NULL) { |
605 | printk(VIOCD_KERN_WARNING "Cannot allocate queue for %s!\n", | 609 | pr_warning("Cannot allocate queue for %s!\n", c->name); |
606 | c->name); | ||
607 | goto out_unregister_cdrom; | 610 | goto out_unregister_cdrom; |
608 | } | 611 | } |
609 | gendisk = alloc_disk(1); | 612 | gendisk = alloc_disk(1); |
610 | if (gendisk == NULL) { | 613 | if (gendisk == NULL) { |
611 | printk(VIOCD_KERN_WARNING "Cannot create gendisk for %s!\n", | 614 | pr_warning("Cannot create gendisk for %s!\n", c->name); |
612 | c->name); | ||
613 | goto out_cleanup_queue; | 615 | goto out_cleanup_queue; |
614 | } | 616 | } |
615 | gendisk->major = VIOCD_MAJOR; | 617 | gendisk->major = VIOCD_MAJOR; |
@@ -682,21 +684,19 @@ static int __init viocd_init(void) | |||
682 | return -ENODEV; | 684 | return -ENODEV; |
683 | } | 685 | } |
684 | 686 | ||
685 | printk(VIOCD_KERN_INFO "vers " VIOCD_VERS ", hosting partition %d\n", | 687 | pr_info("vers " VIOCD_VERS ", hosting partition %d\n", viopath_hostLp); |
686 | viopath_hostLp); | ||
687 | 688 | ||
688 | if (register_blkdev(VIOCD_MAJOR, VIOCD_DEVICE) != 0) { | 689 | if (register_blkdev(VIOCD_MAJOR, VIOCD_DEVICE) != 0) { |
689 | printk(VIOCD_KERN_WARNING "Unable to get major %d for %s\n", | 690 | pr_warning("Unable to get major %d for %s\n", |
690 | VIOCD_MAJOR, VIOCD_DEVICE); | 691 | VIOCD_MAJOR, VIOCD_DEVICE); |
691 | return -EIO; | 692 | return -EIO; |
692 | } | 693 | } |
693 | 694 | ||
694 | ret = viopath_open(viopath_hostLp, viomajorsubtype_cdio, | 695 | ret = viopath_open(viopath_hostLp, viomajorsubtype_cdio, |
695 | MAX_CD_REQ + 2); | 696 | MAX_CD_REQ + 2); |
696 | if (ret) { | 697 | if (ret) { |
697 | printk(VIOCD_KERN_WARNING | 698 | pr_warning("error opening path to host partition %d\n", |
698 | "error opening path to host partition %d\n", | 699 | viopath_hostLp); |
699 | viopath_hostLp); | ||
700 | goto out_unregister; | 700 | goto out_unregister; |
701 | } | 701 | } |
702 | 702 | ||
diff --git a/drivers/ide/ide-atapi.c b/drivers/ide/ide-atapi.c index f9daffd7d0e3..e88a2cf17711 100644 --- a/drivers/ide/ide-atapi.c +++ b/drivers/ide/ide-atapi.c | |||
@@ -190,7 +190,7 @@ void ide_prep_sense(ide_drive_t *drive, struct request *rq) | |||
190 | 190 | ||
191 | BUG_ON(sense_len > sizeof(*sense)); | 191 | BUG_ON(sense_len > sizeof(*sense)); |
192 | 192 | ||
193 | if (blk_sense_request(rq) || drive->sense_rq_armed) | 193 | if (rq->cmd_type == REQ_TYPE_SENSE || drive->sense_rq_armed) |
194 | return; | 194 | return; |
195 | 195 | ||
196 | memset(sense, 0, sizeof(*sense)); | 196 | memset(sense, 0, sizeof(*sense)); |
@@ -307,13 +307,16 @@ EXPORT_SYMBOL_GPL(ide_cd_expiry); | |||
307 | 307 | ||
308 | int ide_cd_get_xferlen(struct request *rq) | 308 | int ide_cd_get_xferlen(struct request *rq) |
309 | { | 309 | { |
310 | if (blk_fs_request(rq)) | 310 | switch (rq->cmd_type) { |
311 | case REQ_TYPE_FS: | ||
311 | return 32768; | 312 | return 32768; |
312 | else if (blk_sense_request(rq) || blk_pc_request(rq) || | 313 | case REQ_TYPE_SENSE: |
313 | rq->cmd_type == REQ_TYPE_ATA_PC) | 314 | case REQ_TYPE_BLOCK_PC: |
315 | case REQ_TYPE_ATA_PC: | ||
314 | return blk_rq_bytes(rq); | 316 | return blk_rq_bytes(rq); |
315 | else | 317 | default: |
316 | return 0; | 318 | return 0; |
319 | } | ||
317 | } | 320 | } |
318 | EXPORT_SYMBOL_GPL(ide_cd_get_xferlen); | 321 | EXPORT_SYMBOL_GPL(ide_cd_get_xferlen); |
319 | 322 | ||
@@ -474,12 +477,12 @@ static ide_startstop_t ide_pc_intr(ide_drive_t *drive) | |||
474 | if (uptodate == 0) | 477 | if (uptodate == 0) |
475 | drive->failed_pc = NULL; | 478 | drive->failed_pc = NULL; |
476 | 479 | ||
477 | if (blk_special_request(rq)) { | 480 | if (rq->cmd_type == REQ_TYPE_SPECIAL) { |
478 | rq->errors = 0; | 481 | rq->errors = 0; |
479 | error = 0; | 482 | error = 0; |
480 | } else { | 483 | } else { |
481 | 484 | ||
482 | if (blk_fs_request(rq) == 0 && uptodate <= 0) { | 485 | if (rq->cmd_type != REQ_TYPE_FS && uptodate <= 0) { |
483 | if (rq->errors == 0) | 486 | if (rq->errors == 0) |
484 | rq->errors = -EIO; | 487 | rq->errors = -EIO; |
485 | } | 488 | } |
diff --git a/drivers/ide/ide-cd.c b/drivers/ide/ide-cd.c index 2de76cc08f61..31fc76960a8f 100644 --- a/drivers/ide/ide-cd.c +++ b/drivers/ide/ide-cd.c | |||
@@ -31,6 +31,7 @@ | |||
31 | #include <linux/delay.h> | 31 | #include <linux/delay.h> |
32 | #include <linux/timer.h> | 32 | #include <linux/timer.h> |
33 | #include <linux/seq_file.h> | 33 | #include <linux/seq_file.h> |
34 | #include <linux/smp_lock.h> | ||
34 | #include <linux/slab.h> | 35 | #include <linux/slab.h> |
35 | #include <linux/interrupt.h> | 36 | #include <linux/interrupt.h> |
36 | #include <linux/errno.h> | 37 | #include <linux/errno.h> |
@@ -176,7 +177,7 @@ static void cdrom_analyze_sense_data(ide_drive_t *drive, | |||
176 | if (!sense->valid) | 177 | if (!sense->valid) |
177 | break; | 178 | break; |
178 | if (failed_command == NULL || | 179 | if (failed_command == NULL || |
179 | !blk_fs_request(failed_command)) | 180 | failed_command->cmd_type != REQ_TYPE_FS) |
180 | break; | 181 | break; |
181 | sector = (sense->information[0] << 24) | | 182 | sector = (sense->information[0] << 24) | |
182 | (sense->information[1] << 16) | | 183 | (sense->information[1] << 16) | |
@@ -292,7 +293,7 @@ static int cdrom_decode_status(ide_drive_t *drive, u8 stat) | |||
292 | "stat 0x%x", | 293 | "stat 0x%x", |
293 | rq->cmd[0], rq->cmd_type, err, stat); | 294 | rq->cmd[0], rq->cmd_type, err, stat); |
294 | 295 | ||
295 | if (blk_sense_request(rq)) { | 296 | if (rq->cmd_type == REQ_TYPE_SENSE) { |
296 | /* | 297 | /* |
297 | * We got an error trying to get sense info from the drive | 298 | * We got an error trying to get sense info from the drive |
298 | * (probably while trying to recover from a former error). | 299 | * (probably while trying to recover from a former error). |
@@ -303,7 +304,7 @@ static int cdrom_decode_status(ide_drive_t *drive, u8 stat) | |||
303 | } | 304 | } |
304 | 305 | ||
305 | /* if we have an error, pass CHECK_CONDITION as the SCSI status byte */ | 306 | /* if we have an error, pass CHECK_CONDITION as the SCSI status byte */ |
306 | if (blk_pc_request(rq) && !rq->errors) | 307 | if (rq->cmd_type == REQ_TYPE_BLOCK_PC && !rq->errors) |
307 | rq->errors = SAM_STAT_CHECK_CONDITION; | 308 | rq->errors = SAM_STAT_CHECK_CONDITION; |
308 | 309 | ||
309 | if (blk_noretry_request(rq)) | 310 | if (blk_noretry_request(rq)) |
@@ -311,13 +312,14 @@ static int cdrom_decode_status(ide_drive_t *drive, u8 stat) | |||
311 | 312 | ||
312 | switch (sense_key) { | 313 | switch (sense_key) { |
313 | case NOT_READY: | 314 | case NOT_READY: |
314 | if (blk_fs_request(rq) && rq_data_dir(rq) == WRITE) { | 315 | if (rq->cmd_type == REQ_TYPE_FS && rq_data_dir(rq) == WRITE) { |
315 | if (ide_cd_breathe(drive, rq)) | 316 | if (ide_cd_breathe(drive, rq)) |
316 | return 1; | 317 | return 1; |
317 | } else { | 318 | } else { |
318 | cdrom_saw_media_change(drive); | 319 | cdrom_saw_media_change(drive); |
319 | 320 | ||
320 | if (blk_fs_request(rq) && !blk_rq_quiet(rq)) | 321 | if (rq->cmd_type == REQ_TYPE_FS && |
322 | !(rq->cmd_flags & REQ_QUIET)) | ||
321 | printk(KERN_ERR PFX "%s: tray open\n", | 323 | printk(KERN_ERR PFX "%s: tray open\n", |
322 | drive->name); | 324 | drive->name); |
323 | } | 325 | } |
@@ -326,7 +328,7 @@ static int cdrom_decode_status(ide_drive_t *drive, u8 stat) | |||
326 | case UNIT_ATTENTION: | 328 | case UNIT_ATTENTION: |
327 | cdrom_saw_media_change(drive); | 329 | cdrom_saw_media_change(drive); |
328 | 330 | ||
329 | if (blk_fs_request(rq) == 0) | 331 | if (rq->cmd_type != REQ_TYPE_FS) |
330 | return 0; | 332 | return 0; |
331 | 333 | ||
332 | /* | 334 | /* |
@@ -352,7 +354,7 @@ static int cdrom_decode_status(ide_drive_t *drive, u8 stat) | |||
352 | * No point in retrying after an illegal request or data | 354 | * No point in retrying after an illegal request or data |
353 | * protect error. | 355 | * protect error. |
354 | */ | 356 | */ |
355 | if (!blk_rq_quiet(rq)) | 357 | if (!(rq->cmd_flags & REQ_QUIET)) |
356 | ide_dump_status(drive, "command error", stat); | 358 | ide_dump_status(drive, "command error", stat); |
357 | do_end_request = 1; | 359 | do_end_request = 1; |
358 | break; | 360 | break; |
@@ -361,20 +363,20 @@ static int cdrom_decode_status(ide_drive_t *drive, u8 stat) | |||
361 | * No point in re-trying a zillion times on a bad sector. | 363 | * No point in re-trying a zillion times on a bad sector. |
362 | * If we got here the error is not correctable. | 364 | * If we got here the error is not correctable. |
363 | */ | 365 | */ |
364 | if (!blk_rq_quiet(rq)) | 366 | if (!(rq->cmd_flags & REQ_QUIET)) |
365 | ide_dump_status(drive, "media error " | 367 | ide_dump_status(drive, "media error " |
366 | "(bad sector)", stat); | 368 | "(bad sector)", stat); |
367 | do_end_request = 1; | 369 | do_end_request = 1; |
368 | break; | 370 | break; |
369 | case BLANK_CHECK: | 371 | case BLANK_CHECK: |
370 | /* disk appears blank? */ | 372 | /* disk appears blank? */ |
371 | if (!blk_rq_quiet(rq)) | 373 | if (!(rq->cmd_flags & REQ_QUIET)) |
372 | ide_dump_status(drive, "media error (blank)", | 374 | ide_dump_status(drive, "media error (blank)", |
373 | stat); | 375 | stat); |
374 | do_end_request = 1; | 376 | do_end_request = 1; |
375 | break; | 377 | break; |
376 | default: | 378 | default: |
377 | if (blk_fs_request(rq) == 0) | 379 | if (rq->cmd_type != REQ_TYPE_FS) |
378 | break; | 380 | break; |
379 | if (err & ~ATA_ABORTED) { | 381 | if (err & ~ATA_ABORTED) { |
380 | /* go to the default handler for other errors */ | 382 | /* go to the default handler for other errors */ |
@@ -385,7 +387,7 @@ static int cdrom_decode_status(ide_drive_t *drive, u8 stat) | |||
385 | do_end_request = 1; | 387 | do_end_request = 1; |
386 | } | 388 | } |
387 | 389 | ||
388 | if (blk_fs_request(rq) == 0) { | 390 | if (rq->cmd_type != REQ_TYPE_FS) { |
389 | rq->cmd_flags |= REQ_FAILED; | 391 | rq->cmd_flags |= REQ_FAILED; |
390 | do_end_request = 1; | 392 | do_end_request = 1; |
391 | } | 393 | } |
@@ -532,7 +534,7 @@ static ide_startstop_t cdrom_newpc_intr(ide_drive_t *drive) | |||
532 | ide_expiry_t *expiry = NULL; | 534 | ide_expiry_t *expiry = NULL; |
533 | int dma_error = 0, dma, thislen, uptodate = 0; | 535 | int dma_error = 0, dma, thislen, uptodate = 0; |
534 | int write = (rq_data_dir(rq) == WRITE) ? 1 : 0, rc = 0; | 536 | int write = (rq_data_dir(rq) == WRITE) ? 1 : 0, rc = 0; |
535 | int sense = blk_sense_request(rq); | 537 | int sense = (rq->cmd_type == REQ_TYPE_SENSE); |
536 | unsigned int timeout; | 538 | unsigned int timeout; |
537 | u16 len; | 539 | u16 len; |
538 | u8 ireason, stat; | 540 | u8 ireason, stat; |
@@ -575,7 +577,7 @@ static ide_startstop_t cdrom_newpc_intr(ide_drive_t *drive) | |||
575 | 577 | ||
576 | ide_read_bcount_and_ireason(drive, &len, &ireason); | 578 | ide_read_bcount_and_ireason(drive, &len, &ireason); |
577 | 579 | ||
578 | thislen = blk_fs_request(rq) ? len : cmd->nleft; | 580 | thislen = (rq->cmd_type == REQ_TYPE_FS) ? len : cmd->nleft; |
579 | if (thislen > len) | 581 | if (thislen > len) |
580 | thislen = len; | 582 | thislen = len; |
581 | 583 | ||
@@ -584,7 +586,7 @@ static ide_startstop_t cdrom_newpc_intr(ide_drive_t *drive) | |||
584 | 586 | ||
585 | /* If DRQ is clear, the command has completed. */ | 587 | /* If DRQ is clear, the command has completed. */ |
586 | if ((stat & ATA_DRQ) == 0) { | 588 | if ((stat & ATA_DRQ) == 0) { |
587 | if (blk_fs_request(rq)) { | 589 | if (rq->cmd_type == REQ_TYPE_FS) { |
588 | /* | 590 | /* |
589 | * If we're not done reading/writing, complain. | 591 | * If we're not done reading/writing, complain. |
590 | * Otherwise, complete the command normally. | 592 | * Otherwise, complete the command normally. |
@@ -598,7 +600,7 @@ static ide_startstop_t cdrom_newpc_intr(ide_drive_t *drive) | |||
598 | rq->cmd_flags |= REQ_FAILED; | 600 | rq->cmd_flags |= REQ_FAILED; |
599 | uptodate = 0; | 601 | uptodate = 0; |
600 | } | 602 | } |
601 | } else if (!blk_pc_request(rq)) { | 603 | } else if (rq->cmd_type != REQ_TYPE_BLOCK_PC) { |
602 | ide_cd_request_sense_fixup(drive, cmd); | 604 | ide_cd_request_sense_fixup(drive, cmd); |
603 | 605 | ||
604 | uptodate = cmd->nleft ? 0 : 1; | 606 | uptodate = cmd->nleft ? 0 : 1; |
@@ -647,7 +649,7 @@ static ide_startstop_t cdrom_newpc_intr(ide_drive_t *drive) | |||
647 | 649 | ||
648 | /* pad, if necessary */ | 650 | /* pad, if necessary */ |
649 | if (len > 0) { | 651 | if (len > 0) { |
650 | if (blk_fs_request(rq) == 0 || write == 0) | 652 | if (rq->cmd_type != REQ_TYPE_FS || write == 0) |
651 | ide_pad_transfer(drive, write, len); | 653 | ide_pad_transfer(drive, write, len); |
652 | else { | 654 | else { |
653 | printk(KERN_ERR PFX "%s: confused, missing data\n", | 655 | printk(KERN_ERR PFX "%s: confused, missing data\n", |
@@ -656,11 +658,11 @@ static ide_startstop_t cdrom_newpc_intr(ide_drive_t *drive) | |||
656 | } | 658 | } |
657 | } | 659 | } |
658 | 660 | ||
659 | if (blk_pc_request(rq)) { | 661 | if (rq->cmd_type == REQ_TYPE_BLOCK_PC) { |
660 | timeout = rq->timeout; | 662 | timeout = rq->timeout; |
661 | } else { | 663 | } else { |
662 | timeout = ATAPI_WAIT_PC; | 664 | timeout = ATAPI_WAIT_PC; |
663 | if (!blk_fs_request(rq)) | 665 | if (rq->cmd_type != REQ_TYPE_FS) |
664 | expiry = ide_cd_expiry; | 666 | expiry = ide_cd_expiry; |
665 | } | 667 | } |
666 | 668 | ||
@@ -669,7 +671,7 @@ static ide_startstop_t cdrom_newpc_intr(ide_drive_t *drive) | |||
669 | return ide_started; | 671 | return ide_started; |
670 | 672 | ||
671 | out_end: | 673 | out_end: |
672 | if (blk_pc_request(rq) && rc == 0) { | 674 | if (rq->cmd_type == REQ_TYPE_BLOCK_PC && rc == 0) { |
673 | rq->resid_len = 0; | 675 | rq->resid_len = 0; |
674 | blk_end_request_all(rq, 0); | 676 | blk_end_request_all(rq, 0); |
675 | hwif->rq = NULL; | 677 | hwif->rq = NULL; |
@@ -677,7 +679,7 @@ out_end: | |||
677 | if (sense && uptodate) | 679 | if (sense && uptodate) |
678 | ide_cd_complete_failed_rq(drive, rq); | 680 | ide_cd_complete_failed_rq(drive, rq); |
679 | 681 | ||
680 | if (blk_fs_request(rq)) { | 682 | if (rq->cmd_type == REQ_TYPE_FS) { |
681 | if (cmd->nleft == 0) | 683 | if (cmd->nleft == 0) |
682 | uptodate = 1; | 684 | uptodate = 1; |
683 | } else { | 685 | } else { |
@@ -690,7 +692,7 @@ out_end: | |||
690 | return ide_stopped; | 692 | return ide_stopped; |
691 | 693 | ||
692 | /* make sure it's fully ended */ | 694 | /* make sure it's fully ended */ |
693 | if (blk_fs_request(rq) == 0) { | 695 | if (rq->cmd_type != REQ_TYPE_FS) { |
694 | rq->resid_len -= cmd->nbytes - cmd->nleft; | 696 | rq->resid_len -= cmd->nbytes - cmd->nleft; |
695 | if (uptodate == 0 && (cmd->tf_flags & IDE_TFLAG_WRITE)) | 697 | if (uptodate == 0 && (cmd->tf_flags & IDE_TFLAG_WRITE)) |
696 | rq->resid_len += cmd->last_xfer_len; | 698 | rq->resid_len += cmd->last_xfer_len; |
@@ -750,7 +752,7 @@ static void cdrom_do_block_pc(ide_drive_t *drive, struct request *rq) | |||
750 | ide_debug_log(IDE_DBG_PC, "rq->cmd[0]: 0x%x, rq->cmd_type: 0x%x", | 752 | ide_debug_log(IDE_DBG_PC, "rq->cmd[0]: 0x%x, rq->cmd_type: 0x%x", |
751 | rq->cmd[0], rq->cmd_type); | 753 | rq->cmd[0], rq->cmd_type); |
752 | 754 | ||
753 | if (blk_pc_request(rq)) | 755 | if (rq->cmd_type == REQ_TYPE_BLOCK_PC) |
754 | rq->cmd_flags |= REQ_QUIET; | 756 | rq->cmd_flags |= REQ_QUIET; |
755 | else | 757 | else |
756 | rq->cmd_flags &= ~REQ_FAILED; | 758 | rq->cmd_flags &= ~REQ_FAILED; |
@@ -791,21 +793,26 @@ static ide_startstop_t ide_cd_do_request(ide_drive_t *drive, struct request *rq, | |||
791 | if (drive->debug_mask & IDE_DBG_RQ) | 793 | if (drive->debug_mask & IDE_DBG_RQ) |
792 | blk_dump_rq_flags(rq, "ide_cd_do_request"); | 794 | blk_dump_rq_flags(rq, "ide_cd_do_request"); |
793 | 795 | ||
794 | if (blk_fs_request(rq)) { | 796 | switch (rq->cmd_type) { |
797 | case REQ_TYPE_FS: | ||
795 | if (cdrom_start_rw(drive, rq) == ide_stopped) | 798 | if (cdrom_start_rw(drive, rq) == ide_stopped) |
796 | goto out_end; | 799 | goto out_end; |
797 | } else if (blk_sense_request(rq) || blk_pc_request(rq) || | 800 | break; |
798 | rq->cmd_type == REQ_TYPE_ATA_PC) { | 801 | case REQ_TYPE_SENSE: |
802 | case REQ_TYPE_BLOCK_PC: | ||
803 | case REQ_TYPE_ATA_PC: | ||
799 | if (!rq->timeout) | 804 | if (!rq->timeout) |
800 | rq->timeout = ATAPI_WAIT_PC; | 805 | rq->timeout = ATAPI_WAIT_PC; |
801 | 806 | ||
802 | cdrom_do_block_pc(drive, rq); | 807 | cdrom_do_block_pc(drive, rq); |
803 | } else if (blk_special_request(rq)) { | 808 | break; |
809 | case REQ_TYPE_SPECIAL: | ||
804 | /* right now this can only be a reset... */ | 810 | /* right now this can only be a reset... */ |
805 | uptodate = 1; | 811 | uptodate = 1; |
806 | goto out_end; | 812 | goto out_end; |
807 | } else | 813 | default: |
808 | BUG(); | 814 | BUG(); |
815 | } | ||
809 | 816 | ||
810 | /* prepare sense request for this command */ | 817 | /* prepare sense request for this command */ |
811 | ide_prep_sense(drive, rq); | 818 | ide_prep_sense(drive, rq); |
@@ -817,7 +824,7 @@ static ide_startstop_t ide_cd_do_request(ide_drive_t *drive, struct request *rq, | |||
817 | 824 | ||
818 | cmd.rq = rq; | 825 | cmd.rq = rq; |
819 | 826 | ||
820 | if (blk_fs_request(rq) || blk_rq_bytes(rq)) { | 827 | if (rq->cmd_type == REQ_TYPE_FS || blk_rq_bytes(rq)) { |
821 | ide_init_sg_cmd(&cmd, blk_rq_bytes(rq)); | 828 | ide_init_sg_cmd(&cmd, blk_rq_bytes(rq)); |
822 | ide_map_sg(drive, &cmd); | 829 | ide_map_sg(drive, &cmd); |
823 | } | 830 | } |
@@ -1373,9 +1380,9 @@ static int ide_cdrom_prep_pc(struct request *rq) | |||
1373 | 1380 | ||
1374 | static int ide_cdrom_prep_fn(struct request_queue *q, struct request *rq) | 1381 | static int ide_cdrom_prep_fn(struct request_queue *q, struct request *rq) |
1375 | { | 1382 | { |
1376 | if (blk_fs_request(rq)) | 1383 | if (rq->cmd_type == REQ_TYPE_FS) |
1377 | return ide_cdrom_prep_fs(q, rq); | 1384 | return ide_cdrom_prep_fs(q, rq); |
1378 | else if (blk_pc_request(rq)) | 1385 | else if (rq->cmd_type == REQ_TYPE_BLOCK_PC) |
1379 | return ide_cdrom_prep_pc(rq); | 1386 | return ide_cdrom_prep_pc(rq); |
1380 | 1387 | ||
1381 | return 0; | 1388 | return 0; |
@@ -1592,17 +1599,19 @@ static struct ide_driver ide_cdrom_driver = { | |||
1592 | 1599 | ||
1593 | static int idecd_open(struct block_device *bdev, fmode_t mode) | 1600 | static int idecd_open(struct block_device *bdev, fmode_t mode) |
1594 | { | 1601 | { |
1595 | struct cdrom_info *info = ide_cd_get(bdev->bd_disk); | 1602 | struct cdrom_info *info; |
1596 | int rc = -ENOMEM; | 1603 | int rc = -ENXIO; |
1597 | 1604 | ||
1605 | lock_kernel(); | ||
1606 | info = ide_cd_get(bdev->bd_disk); | ||
1598 | if (!info) | 1607 | if (!info) |
1599 | return -ENXIO; | 1608 | goto out; |
1600 | 1609 | ||
1601 | rc = cdrom_open(&info->devinfo, bdev, mode); | 1610 | rc = cdrom_open(&info->devinfo, bdev, mode); |
1602 | |||
1603 | if (rc < 0) | 1611 | if (rc < 0) |
1604 | ide_cd_put(info); | 1612 | ide_cd_put(info); |
1605 | 1613 | out: | |
1614 | unlock_kernel(); | ||
1606 | return rc; | 1615 | return rc; |
1607 | } | 1616 | } |
1608 | 1617 | ||
@@ -1610,9 +1619,11 @@ static int idecd_release(struct gendisk *disk, fmode_t mode) | |||
1610 | { | 1619 | { |
1611 | struct cdrom_info *info = ide_drv_g(disk, cdrom_info); | 1620 | struct cdrom_info *info = ide_drv_g(disk, cdrom_info); |
1612 | 1621 | ||
1622 | lock_kernel(); | ||
1613 | cdrom_release(&info->devinfo, mode); | 1623 | cdrom_release(&info->devinfo, mode); |
1614 | 1624 | ||
1615 | ide_cd_put(info); | 1625 | ide_cd_put(info); |
1626 | unlock_kernel(); | ||
1616 | 1627 | ||
1617 | return 0; | 1628 | return 0; |
1618 | } | 1629 | } |
@@ -1656,7 +1667,7 @@ static int idecd_get_spindown(struct cdrom_device_info *cdi, unsigned long arg) | |||
1656 | return 0; | 1667 | return 0; |
1657 | } | 1668 | } |
1658 | 1669 | ||
1659 | static int idecd_ioctl(struct block_device *bdev, fmode_t mode, | 1670 | static int idecd_locked_ioctl(struct block_device *bdev, fmode_t mode, |
1660 | unsigned int cmd, unsigned long arg) | 1671 | unsigned int cmd, unsigned long arg) |
1661 | { | 1672 | { |
1662 | struct cdrom_info *info = ide_drv_g(bdev->bd_disk, cdrom_info); | 1673 | struct cdrom_info *info = ide_drv_g(bdev->bd_disk, cdrom_info); |
@@ -1678,6 +1689,19 @@ static int idecd_ioctl(struct block_device *bdev, fmode_t mode, | |||
1678 | return err; | 1689 | return err; |
1679 | } | 1690 | } |
1680 | 1691 | ||
1692 | static int idecd_ioctl(struct block_device *bdev, fmode_t mode, | ||
1693 | unsigned int cmd, unsigned long arg) | ||
1694 | { | ||
1695 | int ret; | ||
1696 | |||
1697 | lock_kernel(); | ||
1698 | ret = idecd_locked_ioctl(bdev, mode, cmd, arg); | ||
1699 | unlock_kernel(); | ||
1700 | |||
1701 | return ret; | ||
1702 | } | ||
1703 | |||
1704 | |||
1681 | static int idecd_media_changed(struct gendisk *disk) | 1705 | static int idecd_media_changed(struct gendisk *disk) |
1682 | { | 1706 | { |
1683 | struct cdrom_info *info = ide_drv_g(disk, cdrom_info); | 1707 | struct cdrom_info *info = ide_drv_g(disk, cdrom_info); |
@@ -1698,7 +1722,7 @@ static const struct block_device_operations idecd_ops = { | |||
1698 | .owner = THIS_MODULE, | 1722 | .owner = THIS_MODULE, |
1699 | .open = idecd_open, | 1723 | .open = idecd_open, |
1700 | .release = idecd_release, | 1724 | .release = idecd_release, |
1701 | .locked_ioctl = idecd_ioctl, | 1725 | .ioctl = idecd_ioctl, |
1702 | .media_changed = idecd_media_changed, | 1726 | .media_changed = idecd_media_changed, |
1703 | .revalidate_disk = idecd_revalidate_disk | 1727 | .revalidate_disk = idecd_revalidate_disk |
1704 | }; | 1728 | }; |
diff --git a/drivers/ide/ide-cd_ioctl.c b/drivers/ide/ide-cd_ioctl.c index 02712bf045c1..766b3deeb23c 100644 --- a/drivers/ide/ide-cd_ioctl.c +++ b/drivers/ide/ide-cd_ioctl.c | |||
@@ -454,7 +454,7 @@ int ide_cdrom_packet(struct cdrom_device_info *cdi, | |||
454 | touch it at all. */ | 454 | touch it at all. */ |
455 | 455 | ||
456 | if (cgc->data_direction == CGC_DATA_WRITE) | 456 | if (cgc->data_direction == CGC_DATA_WRITE) |
457 | flags |= REQ_RW; | 457 | flags |= REQ_WRITE; |
458 | 458 | ||
459 | if (cgc->sense) | 459 | if (cgc->sense) |
460 | memset(cgc->sense, 0, sizeof(struct request_sense)); | 460 | memset(cgc->sense, 0, sizeof(struct request_sense)); |
diff --git a/drivers/ide/ide-disk.c b/drivers/ide/ide-disk.c index 33d65039cce9..7433e07de30e 100644 --- a/drivers/ide/ide-disk.c +++ b/drivers/ide/ide-disk.c | |||
@@ -184,7 +184,7 @@ static ide_startstop_t ide_do_rw_disk(ide_drive_t *drive, struct request *rq, | |||
184 | ide_hwif_t *hwif = drive->hwif; | 184 | ide_hwif_t *hwif = drive->hwif; |
185 | 185 | ||
186 | BUG_ON(drive->dev_flags & IDE_DFLAG_BLOCKED); | 186 | BUG_ON(drive->dev_flags & IDE_DFLAG_BLOCKED); |
187 | BUG_ON(!blk_fs_request(rq)); | 187 | BUG_ON(rq->cmd_type != REQ_TYPE_FS); |
188 | 188 | ||
189 | ledtrig_ide_activity(); | 189 | ledtrig_ide_activity(); |
190 | 190 | ||
@@ -427,10 +427,15 @@ static void ide_disk_unlock_native_capacity(ide_drive_t *drive) | |||
427 | drive->dev_flags |= IDE_DFLAG_NOHPA; /* disable HPA on resume */ | 427 | drive->dev_flags |= IDE_DFLAG_NOHPA; /* disable HPA on resume */ |
428 | } | 428 | } |
429 | 429 | ||
430 | static void idedisk_prepare_flush(struct request_queue *q, struct request *rq) | 430 | static int idedisk_prep_fn(struct request_queue *q, struct request *rq) |
431 | { | 431 | { |
432 | ide_drive_t *drive = q->queuedata; | 432 | ide_drive_t *drive = q->queuedata; |
433 | struct ide_cmd *cmd = kmalloc(sizeof(*cmd), GFP_ATOMIC); | 433 | struct ide_cmd *cmd; |
434 | |||
435 | if (!(rq->cmd_flags & REQ_FLUSH)) | ||
436 | return BLKPREP_OK; | ||
437 | |||
438 | cmd = kmalloc(sizeof(*cmd), GFP_ATOMIC); | ||
434 | 439 | ||
435 | /* FIXME: map struct ide_taskfile on rq->cmd[] */ | 440 | /* FIXME: map struct ide_taskfile on rq->cmd[] */ |
436 | BUG_ON(cmd == NULL); | 441 | BUG_ON(cmd == NULL); |
@@ -448,6 +453,8 @@ static void idedisk_prepare_flush(struct request_queue *q, struct request *rq) | |||
448 | rq->cmd_type = REQ_TYPE_ATA_TASKFILE; | 453 | rq->cmd_type = REQ_TYPE_ATA_TASKFILE; |
449 | rq->special = cmd; | 454 | rq->special = cmd; |
450 | cmd->rq = rq; | 455 | cmd->rq = rq; |
456 | |||
457 | return BLKPREP_OK; | ||
451 | } | 458 | } |
452 | 459 | ||
453 | ide_devset_get(multcount, mult_count); | 460 | ide_devset_get(multcount, mult_count); |
@@ -513,7 +520,6 @@ static void update_ordered(ide_drive_t *drive) | |||
513 | { | 520 | { |
514 | u16 *id = drive->id; | 521 | u16 *id = drive->id; |
515 | unsigned ordered = QUEUE_ORDERED_NONE; | 522 | unsigned ordered = QUEUE_ORDERED_NONE; |
516 | prepare_flush_fn *prep_fn = NULL; | ||
517 | 523 | ||
518 | if (drive->dev_flags & IDE_DFLAG_WCACHE) { | 524 | if (drive->dev_flags & IDE_DFLAG_WCACHE) { |
519 | unsigned long long capacity; | 525 | unsigned long long capacity; |
@@ -538,12 +544,12 @@ static void update_ordered(ide_drive_t *drive) | |||
538 | 544 | ||
539 | if (barrier) { | 545 | if (barrier) { |
540 | ordered = QUEUE_ORDERED_DRAIN_FLUSH; | 546 | ordered = QUEUE_ORDERED_DRAIN_FLUSH; |
541 | prep_fn = idedisk_prepare_flush; | 547 | blk_queue_prep_rq(drive->queue, idedisk_prep_fn); |
542 | } | 548 | } |
543 | } else | 549 | } else |
544 | ordered = QUEUE_ORDERED_DRAIN; | 550 | ordered = QUEUE_ORDERED_DRAIN; |
545 | 551 | ||
546 | blk_queue_ordered(drive->queue, ordered, prep_fn); | 552 | blk_queue_ordered(drive->queue, ordered); |
547 | } | 553 | } |
548 | 554 | ||
549 | ide_devset_get_flag(wcache, IDE_DFLAG_WCACHE); | 555 | ide_devset_get_flag(wcache, IDE_DFLAG_WCACHE); |
diff --git a/drivers/ide/ide-disk_ioctl.c b/drivers/ide/ide-disk_ioctl.c index 7b783dd7c0be..ec94c66918f6 100644 --- a/drivers/ide/ide-disk_ioctl.c +++ b/drivers/ide/ide-disk_ioctl.c | |||
@@ -1,6 +1,7 @@ | |||
1 | #include <linux/kernel.h> | 1 | #include <linux/kernel.h> |
2 | #include <linux/ide.h> | 2 | #include <linux/ide.h> |
3 | #include <linux/hdreg.h> | 3 | #include <linux/hdreg.h> |
4 | #include <linux/smp_lock.h> | ||
4 | 5 | ||
5 | #include "ide-disk.h" | 6 | #include "ide-disk.h" |
6 | 7 | ||
@@ -18,9 +19,13 @@ int ide_disk_ioctl(ide_drive_t *drive, struct block_device *bdev, fmode_t mode, | |||
18 | { | 19 | { |
19 | int err; | 20 | int err; |
20 | 21 | ||
22 | lock_kernel(); | ||
21 | err = ide_setting_ioctl(drive, bdev, cmd, arg, ide_disk_ioctl_settings); | 23 | err = ide_setting_ioctl(drive, bdev, cmd, arg, ide_disk_ioctl_settings); |
22 | if (err != -EOPNOTSUPP) | 24 | if (err != -EOPNOTSUPP) |
23 | return err; | 25 | goto out; |
24 | 26 | ||
25 | return generic_ide_ioctl(drive, bdev, cmd, arg); | 27 | err = generic_ide_ioctl(drive, bdev, cmd, arg); |
28 | out: | ||
29 | unlock_kernel(); | ||
30 | return err; | ||
26 | } | 31 | } |
diff --git a/drivers/ide/ide-eh.c b/drivers/ide/ide-eh.c index e9abf2c3c335..c0aa93fb7a60 100644 --- a/drivers/ide/ide-eh.c +++ b/drivers/ide/ide-eh.c | |||
@@ -122,7 +122,7 @@ ide_startstop_t ide_error(ide_drive_t *drive, const char *msg, u8 stat) | |||
122 | return ide_stopped; | 122 | return ide_stopped; |
123 | 123 | ||
124 | /* retry only "normal" I/O: */ | 124 | /* retry only "normal" I/O: */ |
125 | if (!blk_fs_request(rq)) { | 125 | if (rq->cmd_type != REQ_TYPE_FS) { |
126 | if (rq->cmd_type == REQ_TYPE_ATA_TASKFILE) { | 126 | if (rq->cmd_type == REQ_TYPE_ATA_TASKFILE) { |
127 | struct ide_cmd *cmd = rq->special; | 127 | struct ide_cmd *cmd = rq->special; |
128 | 128 | ||
@@ -146,7 +146,8 @@ static inline void ide_complete_drive_reset(ide_drive_t *drive, int err) | |||
146 | { | 146 | { |
147 | struct request *rq = drive->hwif->rq; | 147 | struct request *rq = drive->hwif->rq; |
148 | 148 | ||
149 | if (rq && blk_special_request(rq) && rq->cmd[0] == REQ_DRIVE_RESET) { | 149 | if (rq && rq->cmd_type == REQ_TYPE_SPECIAL && |
150 | rq->cmd[0] == REQ_DRIVE_RESET) { | ||
150 | if (err <= 0 && rq->errors == 0) | 151 | if (err <= 0 && rq->errors == 0) |
151 | rq->errors = -EIO; | 152 | rq->errors = -EIO; |
152 | ide_complete_rq(drive, err ? err : 0, blk_rq_bytes(rq)); | 153 | ide_complete_rq(drive, err ? err : 0, blk_rq_bytes(rq)); |
diff --git a/drivers/ide/ide-floppy.c b/drivers/ide/ide-floppy.c index 4713bdca20b6..5406b6ea3ad1 100644 --- a/drivers/ide/ide-floppy.c +++ b/drivers/ide/ide-floppy.c | |||
@@ -73,7 +73,7 @@ static int ide_floppy_callback(ide_drive_t *drive, int dsc) | |||
73 | drive->failed_pc = NULL; | 73 | drive->failed_pc = NULL; |
74 | 74 | ||
75 | if (pc->c[0] == GPCMD_READ_10 || pc->c[0] == GPCMD_WRITE_10 || | 75 | if (pc->c[0] == GPCMD_READ_10 || pc->c[0] == GPCMD_WRITE_10 || |
76 | (rq && blk_pc_request(rq))) | 76 | (rq && rq->cmd_type == REQ_TYPE_BLOCK_PC)) |
77 | uptodate = 1; /* FIXME */ | 77 | uptodate = 1; /* FIXME */ |
78 | else if (pc->c[0] == GPCMD_REQUEST_SENSE) { | 78 | else if (pc->c[0] == GPCMD_REQUEST_SENSE) { |
79 | 79 | ||
@@ -98,7 +98,7 @@ static int ide_floppy_callback(ide_drive_t *drive, int dsc) | |||
98 | "Aborting request!\n"); | 98 | "Aborting request!\n"); |
99 | } | 99 | } |
100 | 100 | ||
101 | if (blk_special_request(rq)) | 101 | if (rq->cmd_type == REQ_TYPE_SPECIAL) |
102 | rq->errors = uptodate ? 0 : IDE_DRV_ERROR_GENERAL; | 102 | rq->errors = uptodate ? 0 : IDE_DRV_ERROR_GENERAL; |
103 | 103 | ||
104 | return uptodate; | 104 | return uptodate; |
@@ -207,7 +207,7 @@ static void idefloppy_create_rw_cmd(ide_drive_t *drive, | |||
207 | memcpy(rq->cmd, pc->c, 12); | 207 | memcpy(rq->cmd, pc->c, 12); |
208 | 208 | ||
209 | pc->rq = rq; | 209 | pc->rq = rq; |
210 | if (rq->cmd_flags & REQ_RW) | 210 | if (rq->cmd_flags & REQ_WRITE) |
211 | pc->flags |= PC_FLAG_WRITING; | 211 | pc->flags |= PC_FLAG_WRITING; |
212 | 212 | ||
213 | pc->flags |= PC_FLAG_DMA_OK; | 213 | pc->flags |= PC_FLAG_DMA_OK; |
@@ -247,14 +247,16 @@ static ide_startstop_t ide_floppy_do_request(ide_drive_t *drive, | |||
247 | } else | 247 | } else |
248 | printk(KERN_ERR PFX "%s: I/O error\n", drive->name); | 248 | printk(KERN_ERR PFX "%s: I/O error\n", drive->name); |
249 | 249 | ||
250 | if (blk_special_request(rq)) { | 250 | if (rq->cmd_type == REQ_TYPE_SPECIAL) { |
251 | rq->errors = 0; | 251 | rq->errors = 0; |
252 | ide_complete_rq(drive, 0, blk_rq_bytes(rq)); | 252 | ide_complete_rq(drive, 0, blk_rq_bytes(rq)); |
253 | return ide_stopped; | 253 | return ide_stopped; |
254 | } else | 254 | } else |
255 | goto out_end; | 255 | goto out_end; |
256 | } | 256 | } |
257 | if (blk_fs_request(rq)) { | 257 | |
258 | switch (rq->cmd_type) { | ||
259 | case REQ_TYPE_FS: | ||
258 | if (((long)blk_rq_pos(rq) % floppy->bs_factor) || | 260 | if (((long)blk_rq_pos(rq) % floppy->bs_factor) || |
259 | (blk_rq_sectors(rq) % floppy->bs_factor)) { | 261 | (blk_rq_sectors(rq) % floppy->bs_factor)) { |
260 | printk(KERN_ERR PFX "%s: unsupported r/w rq size\n", | 262 | printk(KERN_ERR PFX "%s: unsupported r/w rq size\n", |
@@ -263,13 +265,18 @@ static ide_startstop_t ide_floppy_do_request(ide_drive_t *drive, | |||
263 | } | 265 | } |
264 | pc = &floppy->queued_pc; | 266 | pc = &floppy->queued_pc; |
265 | idefloppy_create_rw_cmd(drive, pc, rq, (unsigned long)block); | 267 | idefloppy_create_rw_cmd(drive, pc, rq, (unsigned long)block); |
266 | } else if (blk_special_request(rq) || blk_sense_request(rq)) { | 268 | break; |
269 | case REQ_TYPE_SPECIAL: | ||
270 | case REQ_TYPE_SENSE: | ||
267 | pc = (struct ide_atapi_pc *)rq->special; | 271 | pc = (struct ide_atapi_pc *)rq->special; |
268 | } else if (blk_pc_request(rq)) { | 272 | break; |
273 | case REQ_TYPE_BLOCK_PC: | ||
269 | pc = &floppy->queued_pc; | 274 | pc = &floppy->queued_pc; |
270 | idefloppy_blockpc_cmd(floppy, pc, rq); | 275 | idefloppy_blockpc_cmd(floppy, pc, rq); |
271 | } else | 276 | break; |
277 | default: | ||
272 | BUG(); | 278 | BUG(); |
279 | } | ||
273 | 280 | ||
274 | ide_prep_sense(drive, rq); | 281 | ide_prep_sense(drive, rq); |
275 | 282 | ||
@@ -280,7 +287,7 @@ static ide_startstop_t ide_floppy_do_request(ide_drive_t *drive, | |||
280 | 287 | ||
281 | cmd.rq = rq; | 288 | cmd.rq = rq; |
282 | 289 | ||
283 | if (blk_fs_request(rq) || blk_rq_bytes(rq)) { | 290 | if (rq->cmd_type == REQ_TYPE_FS || blk_rq_bytes(rq)) { |
284 | ide_init_sg_cmd(&cmd, blk_rq_bytes(rq)); | 291 | ide_init_sg_cmd(&cmd, blk_rq_bytes(rq)); |
285 | ide_map_sg(drive, &cmd); | 292 | ide_map_sg(drive, &cmd); |
286 | } | 293 | } |
@@ -290,7 +297,7 @@ static ide_startstop_t ide_floppy_do_request(ide_drive_t *drive, | |||
290 | return ide_floppy_issue_pc(drive, &cmd, pc); | 297 | return ide_floppy_issue_pc(drive, &cmd, pc); |
291 | out_end: | 298 | out_end: |
292 | drive->failed_pc = NULL; | 299 | drive->failed_pc = NULL; |
293 | if (blk_fs_request(rq) == 0 && rq->errors == 0) | 300 | if (rq->cmd_type != REQ_TYPE_FS && rq->errors == 0) |
294 | rq->errors = -EIO; | 301 | rq->errors = -EIO; |
295 | ide_complete_rq(drive, -EIO, blk_rq_bytes(rq)); | 302 | ide_complete_rq(drive, -EIO, blk_rq_bytes(rq)); |
296 | return ide_stopped; | 303 | return ide_stopped; |
diff --git a/drivers/ide/ide-floppy_ioctl.c b/drivers/ide/ide-floppy_ioctl.c index 9c2288234dea..fd3d05ab3417 100644 --- a/drivers/ide/ide-floppy_ioctl.c +++ b/drivers/ide/ide-floppy_ioctl.c | |||
@@ -5,6 +5,7 @@ | |||
5 | #include <linux/kernel.h> | 5 | #include <linux/kernel.h> |
6 | #include <linux/ide.h> | 6 | #include <linux/ide.h> |
7 | #include <linux/cdrom.h> | 7 | #include <linux/cdrom.h> |
8 | #include <linux/smp_lock.h> | ||
8 | 9 | ||
9 | #include <asm/unaligned.h> | 10 | #include <asm/unaligned.h> |
10 | 11 | ||
@@ -275,12 +276,15 @@ int ide_floppy_ioctl(ide_drive_t *drive, struct block_device *bdev, | |||
275 | void __user *argp = (void __user *)arg; | 276 | void __user *argp = (void __user *)arg; |
276 | int err; | 277 | int err; |
277 | 278 | ||
278 | if (cmd == CDROMEJECT || cmd == CDROM_LOCKDOOR) | 279 | lock_kernel(); |
279 | return ide_floppy_lockdoor(drive, &pc, arg, cmd); | 280 | if (cmd == CDROMEJECT || cmd == CDROM_LOCKDOOR) { |
281 | err = ide_floppy_lockdoor(drive, &pc, arg, cmd); | ||
282 | goto out; | ||
283 | } | ||
280 | 284 | ||
281 | err = ide_floppy_format_ioctl(drive, &pc, mode, cmd, argp); | 285 | err = ide_floppy_format_ioctl(drive, &pc, mode, cmd, argp); |
282 | if (err != -ENOTTY) | 286 | if (err != -ENOTTY) |
283 | return err; | 287 | goto out; |
284 | 288 | ||
285 | /* | 289 | /* |
286 | * skip SCSI_IOCTL_SEND_COMMAND (deprecated) | 290 | * skip SCSI_IOCTL_SEND_COMMAND (deprecated) |
@@ -293,5 +297,7 @@ int ide_floppy_ioctl(ide_drive_t *drive, struct block_device *bdev, | |||
293 | if (err == -ENOTTY) | 297 | if (err == -ENOTTY) |
294 | err = generic_ide_ioctl(drive, bdev, cmd, arg); | 298 | err = generic_ide_ioctl(drive, bdev, cmd, arg); |
295 | 299 | ||
300 | out: | ||
301 | unlock_kernel(); | ||
296 | return err; | 302 | return err; |
297 | } | 303 | } |
diff --git a/drivers/ide/ide-gd.c b/drivers/ide/ide-gd.c index 79399534782c..70aeeb18833e 100644 --- a/drivers/ide/ide-gd.c +++ b/drivers/ide/ide-gd.c | |||
@@ -1,3 +1,4 @@ | |||
1 | #include <linux/smp_lock.h> | ||
1 | #include <linux/module.h> | 2 | #include <linux/module.h> |
2 | #include <linux/types.h> | 3 | #include <linux/types.h> |
3 | #include <linux/string.h> | 4 | #include <linux/string.h> |
@@ -237,6 +238,18 @@ out_put_idkp: | |||
237 | return ret; | 238 | return ret; |
238 | } | 239 | } |
239 | 240 | ||
241 | static int ide_gd_unlocked_open(struct block_device *bdev, fmode_t mode) | ||
242 | { | ||
243 | int ret; | ||
244 | |||
245 | lock_kernel(); | ||
246 | ret = ide_gd_open(bdev, mode); | ||
247 | unlock_kernel(); | ||
248 | |||
249 | return ret; | ||
250 | } | ||
251 | |||
252 | |||
240 | static int ide_gd_release(struct gendisk *disk, fmode_t mode) | 253 | static int ide_gd_release(struct gendisk *disk, fmode_t mode) |
241 | { | 254 | { |
242 | struct ide_disk_obj *idkp = ide_drv_g(disk, ide_disk_obj); | 255 | struct ide_disk_obj *idkp = ide_drv_g(disk, ide_disk_obj); |
@@ -244,6 +257,7 @@ static int ide_gd_release(struct gendisk *disk, fmode_t mode) | |||
244 | 257 | ||
245 | ide_debug_log(IDE_DBG_FUNC, "enter"); | 258 | ide_debug_log(IDE_DBG_FUNC, "enter"); |
246 | 259 | ||
260 | lock_kernel(); | ||
247 | if (idkp->openers == 1) | 261 | if (idkp->openers == 1) |
248 | drive->disk_ops->flush(drive); | 262 | drive->disk_ops->flush(drive); |
249 | 263 | ||
@@ -255,6 +269,7 @@ static int ide_gd_release(struct gendisk *disk, fmode_t mode) | |||
255 | idkp->openers--; | 269 | idkp->openers--; |
256 | 270 | ||
257 | ide_disk_put(idkp); | 271 | ide_disk_put(idkp); |
272 | unlock_kernel(); | ||
258 | 273 | ||
259 | return 0; | 274 | return 0; |
260 | } | 275 | } |
@@ -321,9 +336,9 @@ static int ide_gd_ioctl(struct block_device *bdev, fmode_t mode, | |||
321 | 336 | ||
322 | static const struct block_device_operations ide_gd_ops = { | 337 | static const struct block_device_operations ide_gd_ops = { |
323 | .owner = THIS_MODULE, | 338 | .owner = THIS_MODULE, |
324 | .open = ide_gd_open, | 339 | .open = ide_gd_unlocked_open, |
325 | .release = ide_gd_release, | 340 | .release = ide_gd_release, |
326 | .locked_ioctl = ide_gd_ioctl, | 341 | .ioctl = ide_gd_ioctl, |
327 | .getgeo = ide_gd_getgeo, | 342 | .getgeo = ide_gd_getgeo, |
328 | .media_changed = ide_gd_media_changed, | 343 | .media_changed = ide_gd_media_changed, |
329 | .unlock_native_capacity = ide_gd_unlock_native_capacity, | 344 | .unlock_native_capacity = ide_gd_unlock_native_capacity, |
diff --git a/drivers/ide/ide-io.c b/drivers/ide/ide-io.c index 172ac9218154..a381be814070 100644 --- a/drivers/ide/ide-io.c +++ b/drivers/ide/ide-io.c | |||
@@ -135,7 +135,7 @@ EXPORT_SYMBOL(ide_complete_rq); | |||
135 | 135 | ||
136 | void ide_kill_rq(ide_drive_t *drive, struct request *rq) | 136 | void ide_kill_rq(ide_drive_t *drive, struct request *rq) |
137 | { | 137 | { |
138 | u8 drv_req = blk_special_request(rq) && rq->rq_disk; | 138 | u8 drv_req = (rq->cmd_type == REQ_TYPE_SPECIAL) && rq->rq_disk; |
139 | u8 media = drive->media; | 139 | u8 media = drive->media; |
140 | 140 | ||
141 | drive->failed_pc = NULL; | 141 | drive->failed_pc = NULL; |
@@ -145,7 +145,7 @@ void ide_kill_rq(ide_drive_t *drive, struct request *rq) | |||
145 | } else { | 145 | } else { |
146 | if (media == ide_tape) | 146 | if (media == ide_tape) |
147 | rq->errors = IDE_DRV_ERROR_GENERAL; | 147 | rq->errors = IDE_DRV_ERROR_GENERAL; |
148 | else if (blk_fs_request(rq) == 0 && rq->errors == 0) | 148 | else if (rq->cmd_type != REQ_TYPE_FS && rq->errors == 0) |
149 | rq->errors = -EIO; | 149 | rq->errors = -EIO; |
150 | } | 150 | } |
151 | 151 | ||
@@ -307,7 +307,7 @@ static ide_startstop_t start_request (ide_drive_t *drive, struct request *rq) | |||
307 | { | 307 | { |
308 | ide_startstop_t startstop; | 308 | ide_startstop_t startstop; |
309 | 309 | ||
310 | BUG_ON(!blk_rq_started(rq)); | 310 | BUG_ON(!(rq->cmd_flags & REQ_STARTED)); |
311 | 311 | ||
312 | #ifdef DEBUG | 312 | #ifdef DEBUG |
313 | printk("%s: start_request: current=0x%08lx\n", | 313 | printk("%s: start_request: current=0x%08lx\n", |
@@ -353,7 +353,7 @@ static ide_startstop_t start_request (ide_drive_t *drive, struct request *rq) | |||
353 | pm->pm_step == IDE_PM_COMPLETED) | 353 | pm->pm_step == IDE_PM_COMPLETED) |
354 | ide_complete_pm_rq(drive, rq); | 354 | ide_complete_pm_rq(drive, rq); |
355 | return startstop; | 355 | return startstop; |
356 | } else if (!rq->rq_disk && blk_special_request(rq)) | 356 | } else if (!rq->rq_disk && rq->cmd_type == REQ_TYPE_SPECIAL) |
357 | /* | 357 | /* |
358 | * TODO: Once all ULDs have been modified to | 358 | * TODO: Once all ULDs have been modified to |
359 | * check for specific op codes rather than | 359 | * check for specific op codes rather than |
diff --git a/drivers/ide/ide-pm.c b/drivers/ide/ide-pm.c index 1c08311b0a0e..92406097efeb 100644 --- a/drivers/ide/ide-pm.c +++ b/drivers/ide/ide-pm.c | |||
@@ -191,10 +191,10 @@ void ide_complete_pm_rq(ide_drive_t *drive, struct request *rq) | |||
191 | 191 | ||
192 | #ifdef DEBUG_PM | 192 | #ifdef DEBUG_PM |
193 | printk("%s: completing PM request, %s\n", drive->name, | 193 | printk("%s: completing PM request, %s\n", drive->name, |
194 | blk_pm_suspend_request(rq) ? "suspend" : "resume"); | 194 | (rq->cmd_type == REQ_TYPE_PM_SUSPEND) ? "suspend" : "resume"); |
195 | #endif | 195 | #endif |
196 | spin_lock_irqsave(q->queue_lock, flags); | 196 | spin_lock_irqsave(q->queue_lock, flags); |
197 | if (blk_pm_suspend_request(rq)) | 197 | if (rq->cmd_type == REQ_TYPE_PM_SUSPEND) |
198 | blk_stop_queue(q); | 198 | blk_stop_queue(q); |
199 | else | 199 | else |
200 | drive->dev_flags &= ~IDE_DFLAG_BLOCKED; | 200 | drive->dev_flags &= ~IDE_DFLAG_BLOCKED; |
@@ -210,11 +210,11 @@ void ide_check_pm_state(ide_drive_t *drive, struct request *rq) | |||
210 | { | 210 | { |
211 | struct request_pm_state *pm = rq->special; | 211 | struct request_pm_state *pm = rq->special; |
212 | 212 | ||
213 | if (blk_pm_suspend_request(rq) && | 213 | if (rq->cmd_type == REQ_TYPE_PM_SUSPEND && |
214 | pm->pm_step == IDE_PM_START_SUSPEND) | 214 | pm->pm_step == IDE_PM_START_SUSPEND) |
215 | /* Mark drive blocked when starting the suspend sequence. */ | 215 | /* Mark drive blocked when starting the suspend sequence. */ |
216 | drive->dev_flags |= IDE_DFLAG_BLOCKED; | 216 | drive->dev_flags |= IDE_DFLAG_BLOCKED; |
217 | else if (blk_pm_resume_request(rq) && | 217 | else if (rq->cmd_type == REQ_TYPE_PM_RESUME && |
218 | pm->pm_step == IDE_PM_START_RESUME) { | 218 | pm->pm_step == IDE_PM_START_RESUME) { |
219 | /* | 219 | /* |
220 | * The first thing we do on wakeup is to wait for BSY bit to | 220 | * The first thing we do on wakeup is to wait for BSY bit to |
diff --git a/drivers/ide/ide-tape.c b/drivers/ide/ide-tape.c index b07232880ec9..6d622cb5ac81 100644 --- a/drivers/ide/ide-tape.c +++ b/drivers/ide/ide-tape.c | |||
@@ -32,6 +32,7 @@ | |||
32 | #include <linux/errno.h> | 32 | #include <linux/errno.h> |
33 | #include <linux/genhd.h> | 33 | #include <linux/genhd.h> |
34 | #include <linux/seq_file.h> | 34 | #include <linux/seq_file.h> |
35 | #include <linux/smp_lock.h> | ||
35 | #include <linux/slab.h> | 36 | #include <linux/slab.h> |
36 | #include <linux/pci.h> | 37 | #include <linux/pci.h> |
37 | #include <linux/ide.h> | 38 | #include <linux/ide.h> |
@@ -577,7 +578,8 @@ static ide_startstop_t idetape_do_request(ide_drive_t *drive, | |||
577 | rq->cmd[0], (unsigned long long)blk_rq_pos(rq), | 578 | rq->cmd[0], (unsigned long long)blk_rq_pos(rq), |
578 | blk_rq_sectors(rq)); | 579 | blk_rq_sectors(rq)); |
579 | 580 | ||
580 | BUG_ON(!(blk_special_request(rq) || blk_sense_request(rq))); | 581 | BUG_ON(!(rq->cmd_type == REQ_TYPE_SPECIAL || |
582 | rq->cmd_type == REQ_TYPE_SENSE)); | ||
581 | 583 | ||
582 | /* Retry a failed packet command */ | 584 | /* Retry a failed packet command */ |
583 | if (drive->failed_pc && drive->pc->c[0] == REQUEST_SENSE) { | 585 | if (drive->failed_pc && drive->pc->c[0] == REQUEST_SENSE) { |
@@ -1905,7 +1907,11 @@ static const struct file_operations idetape_fops = { | |||
1905 | 1907 | ||
1906 | static int idetape_open(struct block_device *bdev, fmode_t mode) | 1908 | static int idetape_open(struct block_device *bdev, fmode_t mode) |
1907 | { | 1909 | { |
1908 | struct ide_tape_obj *tape = ide_tape_get(bdev->bd_disk, false, 0); | 1910 | struct ide_tape_obj *tape; |
1911 | |||
1912 | lock_kernel(); | ||
1913 | tape = ide_tape_get(bdev->bd_disk, false, 0); | ||
1914 | unlock_kernel(); | ||
1909 | 1915 | ||
1910 | if (!tape) | 1916 | if (!tape) |
1911 | return -ENXIO; | 1917 | return -ENXIO; |
@@ -1917,7 +1923,10 @@ static int idetape_release(struct gendisk *disk, fmode_t mode) | |||
1917 | { | 1923 | { |
1918 | struct ide_tape_obj *tape = ide_drv_g(disk, ide_tape_obj); | 1924 | struct ide_tape_obj *tape = ide_drv_g(disk, ide_tape_obj); |
1919 | 1925 | ||
1926 | lock_kernel(); | ||
1920 | ide_tape_put(tape); | 1927 | ide_tape_put(tape); |
1928 | unlock_kernel(); | ||
1929 | |||
1921 | return 0; | 1930 | return 0; |
1922 | } | 1931 | } |
1923 | 1932 | ||
@@ -1926,9 +1935,14 @@ static int idetape_ioctl(struct block_device *bdev, fmode_t mode, | |||
1926 | { | 1935 | { |
1927 | struct ide_tape_obj *tape = ide_drv_g(bdev->bd_disk, ide_tape_obj); | 1936 | struct ide_tape_obj *tape = ide_drv_g(bdev->bd_disk, ide_tape_obj); |
1928 | ide_drive_t *drive = tape->drive; | 1937 | ide_drive_t *drive = tape->drive; |
1929 | int err = generic_ide_ioctl(drive, bdev, cmd, arg); | 1938 | int err; |
1939 | |||
1940 | lock_kernel(); | ||
1941 | err = generic_ide_ioctl(drive, bdev, cmd, arg); | ||
1930 | if (err == -EINVAL) | 1942 | if (err == -EINVAL) |
1931 | err = idetape_blkdev_ioctl(drive, cmd, arg); | 1943 | err = idetape_blkdev_ioctl(drive, cmd, arg); |
1944 | unlock_kernel(); | ||
1945 | |||
1932 | return err; | 1946 | return err; |
1933 | } | 1947 | } |
1934 | 1948 | ||
@@ -1936,7 +1950,7 @@ static const struct block_device_operations idetape_block_ops = { | |||
1936 | .owner = THIS_MODULE, | 1950 | .owner = THIS_MODULE, |
1937 | .open = idetape_open, | 1951 | .open = idetape_open, |
1938 | .release = idetape_release, | 1952 | .release = idetape_release, |
1939 | .locked_ioctl = idetape_ioctl, | 1953 | .ioctl = idetape_ioctl, |
1940 | }; | 1954 | }; |
1941 | 1955 | ||
1942 | static int ide_tape_probe(ide_drive_t *drive) | 1956 | static int ide_tape_probe(ide_drive_t *drive) |
diff --git a/drivers/md/dm-io.c b/drivers/md/dm-io.c index 10f457ca6af2..0590c75b0ab6 100644 --- a/drivers/md/dm-io.c +++ b/drivers/md/dm-io.c | |||
@@ -356,7 +356,7 @@ static void dispatch_io(int rw, unsigned int num_regions, | |||
356 | BUG_ON(num_regions > DM_IO_MAX_REGIONS); | 356 | BUG_ON(num_regions > DM_IO_MAX_REGIONS); |
357 | 357 | ||
358 | if (sync) | 358 | if (sync) |
359 | rw |= (1 << BIO_RW_SYNCIO) | (1 << BIO_RW_UNPLUG); | 359 | rw |= REQ_SYNC | REQ_UNPLUG; |
360 | 360 | ||
361 | /* | 361 | /* |
362 | * For multiple regions we need to be careful to rewind | 362 | * For multiple regions we need to be careful to rewind |
@@ -364,7 +364,7 @@ static void dispatch_io(int rw, unsigned int num_regions, | |||
364 | */ | 364 | */ |
365 | for (i = 0; i < num_regions; i++) { | 365 | for (i = 0; i < num_regions; i++) { |
366 | *dp = old_pages; | 366 | *dp = old_pages; |
367 | if (where[i].count || (rw & (1 << BIO_RW_BARRIER))) | 367 | if (where[i].count || (rw & REQ_HARDBARRIER)) |
368 | do_region(rw, i, where + i, dp, io); | 368 | do_region(rw, i, where + i, dp, io); |
369 | } | 369 | } |
370 | 370 | ||
@@ -412,8 +412,8 @@ retry: | |||
412 | } | 412 | } |
413 | set_current_state(TASK_RUNNING); | 413 | set_current_state(TASK_RUNNING); |
414 | 414 | ||
415 | if (io->eopnotsupp_bits && (rw & (1 << BIO_RW_BARRIER))) { | 415 | if (io->eopnotsupp_bits && (rw & REQ_HARDBARRIER)) { |
416 | rw &= ~(1 << BIO_RW_BARRIER); | 416 | rw &= ~REQ_HARDBARRIER; |
417 | goto retry; | 417 | goto retry; |
418 | } | 418 | } |
419 | 419 | ||
@@ -479,8 +479,8 @@ static int dp_init(struct dm_io_request *io_req, struct dpages *dp) | |||
479 | * New collapsed (a)synchronous interface. | 479 | * New collapsed (a)synchronous interface. |
480 | * | 480 | * |
481 | * If the IO is asynchronous (i.e. it has notify.fn), you must either unplug | 481 | * If the IO is asynchronous (i.e. it has notify.fn), you must either unplug |
482 | * the queue with blk_unplug() some time later or set the BIO_RW_SYNC bit in | 482 | * the queue with blk_unplug() some time later or set REQ_SYNC in |
483 | * io_req->bi_rw. If you fail to do one of these, the IO will be submitted to | 483 | io_req->bi_rw. If you fail to do one of these, the IO will be submitted to |
484 | * the disk after q->unplug_delay, which defaults to 3ms in blk-settings.c. | 484 | * the disk after q->unplug_delay, which defaults to 3ms in blk-settings.c. |
485 | */ | 485 | */ |
486 | int dm_io(struct dm_io_request *io_req, unsigned num_regions, | 486 | int dm_io(struct dm_io_request *io_req, unsigned num_regions, |
diff --git a/drivers/md/dm-kcopyd.c b/drivers/md/dm-kcopyd.c index addf83475040..d8587bac5682 100644 --- a/drivers/md/dm-kcopyd.c +++ b/drivers/md/dm-kcopyd.c | |||
@@ -345,7 +345,7 @@ static int run_io_job(struct kcopyd_job *job) | |||
345 | { | 345 | { |
346 | int r; | 346 | int r; |
347 | struct dm_io_request io_req = { | 347 | struct dm_io_request io_req = { |
348 | .bi_rw = job->rw | (1 << BIO_RW_SYNCIO) | (1 << BIO_RW_UNPLUG), | 348 | .bi_rw = job->rw | REQ_SYNC | REQ_UNPLUG, |
349 | .mem.type = DM_IO_PAGE_LIST, | 349 | .mem.type = DM_IO_PAGE_LIST, |
350 | .mem.ptr.pl = job->pages, | 350 | .mem.ptr.pl = job->pages, |
351 | .mem.offset = job->offset, | 351 | .mem.offset = job->offset, |
diff --git a/drivers/md/dm-raid1.c b/drivers/md/dm-raid1.c index ddda531723dc..74136262d654 100644 --- a/drivers/md/dm-raid1.c +++ b/drivers/md/dm-raid1.c | |||
@@ -1211,7 +1211,7 @@ static int mirror_end_io(struct dm_target *ti, struct bio *bio, | |||
1211 | if (error == -EOPNOTSUPP) | 1211 | if (error == -EOPNOTSUPP) |
1212 | goto out; | 1212 | goto out; |
1213 | 1213 | ||
1214 | if ((error == -EWOULDBLOCK) && bio_rw_flagged(bio, BIO_RW_AHEAD)) | 1214 | if ((error == -EWOULDBLOCK) && (bio->bi_rw & REQ_RAHEAD)) |
1215 | goto out; | 1215 | goto out; |
1216 | 1216 | ||
1217 | if (unlikely(error)) { | 1217 | if (unlikely(error)) { |
diff --git a/drivers/md/dm-stripe.c b/drivers/md/dm-stripe.c index e610725db766..d6e28d732b4d 100644 --- a/drivers/md/dm-stripe.c +++ b/drivers/md/dm-stripe.c | |||
@@ -284,7 +284,7 @@ static int stripe_end_io(struct dm_target *ti, struct bio *bio, | |||
284 | if (!error) | 284 | if (!error) |
285 | return 0; /* I/O complete */ | 285 | return 0; /* I/O complete */ |
286 | 286 | ||
287 | if ((error == -EWOULDBLOCK) && bio_rw_flagged(bio, BIO_RW_AHEAD)) | 287 | if ((error == -EWOULDBLOCK) && (bio->bi_rw & REQ_RAHEAD)) |
288 | return error; | 288 | return error; |
289 | 289 | ||
290 | if (error == -EOPNOTSUPP) | 290 | if (error == -EOPNOTSUPP) |
diff --git a/drivers/md/dm.c b/drivers/md/dm.c index d21e1284604f..a3f21dc02bd8 100644 --- a/drivers/md/dm.c +++ b/drivers/md/dm.c | |||
@@ -15,6 +15,7 @@ | |||
15 | #include <linux/blkpg.h> | 15 | #include <linux/blkpg.h> |
16 | #include <linux/bio.h> | 16 | #include <linux/bio.h> |
17 | #include <linux/buffer_head.h> | 17 | #include <linux/buffer_head.h> |
18 | #include <linux/smp_lock.h> | ||
18 | #include <linux/mempool.h> | 19 | #include <linux/mempool.h> |
19 | #include <linux/slab.h> | 20 | #include <linux/slab.h> |
20 | #include <linux/idr.h> | 21 | #include <linux/idr.h> |
@@ -338,6 +339,7 @@ static int dm_blk_open(struct block_device *bdev, fmode_t mode) | |||
338 | { | 339 | { |
339 | struct mapped_device *md; | 340 | struct mapped_device *md; |
340 | 341 | ||
342 | lock_kernel(); | ||
341 | spin_lock(&_minor_lock); | 343 | spin_lock(&_minor_lock); |
342 | 344 | ||
343 | md = bdev->bd_disk->private_data; | 345 | md = bdev->bd_disk->private_data; |
@@ -355,6 +357,7 @@ static int dm_blk_open(struct block_device *bdev, fmode_t mode) | |||
355 | 357 | ||
356 | out: | 358 | out: |
357 | spin_unlock(&_minor_lock); | 359 | spin_unlock(&_minor_lock); |
360 | unlock_kernel(); | ||
358 | 361 | ||
359 | return md ? 0 : -ENXIO; | 362 | return md ? 0 : -ENXIO; |
360 | } | 363 | } |
@@ -362,8 +365,12 @@ out: | |||
362 | static int dm_blk_close(struct gendisk *disk, fmode_t mode) | 365 | static int dm_blk_close(struct gendisk *disk, fmode_t mode) |
363 | { | 366 | { |
364 | struct mapped_device *md = disk->private_data; | 367 | struct mapped_device *md = disk->private_data; |
368 | |||
369 | lock_kernel(); | ||
365 | atomic_dec(&md->open_count); | 370 | atomic_dec(&md->open_count); |
366 | dm_put(md); | 371 | dm_put(md); |
372 | unlock_kernel(); | ||
373 | |||
367 | return 0; | 374 | return 0; |
368 | } | 375 | } |
369 | 376 | ||
@@ -614,7 +621,7 @@ static void dec_pending(struct dm_io *io, int error) | |||
614 | */ | 621 | */ |
615 | spin_lock_irqsave(&md->deferred_lock, flags); | 622 | spin_lock_irqsave(&md->deferred_lock, flags); |
616 | if (__noflush_suspending(md)) { | 623 | if (__noflush_suspending(md)) { |
617 | if (!bio_rw_flagged(io->bio, BIO_RW_BARRIER)) | 624 | if (!(io->bio->bi_rw & REQ_HARDBARRIER)) |
618 | bio_list_add_head(&md->deferred, | 625 | bio_list_add_head(&md->deferred, |
619 | io->bio); | 626 | io->bio); |
620 | } else | 627 | } else |
@@ -626,7 +633,7 @@ static void dec_pending(struct dm_io *io, int error) | |||
626 | io_error = io->error; | 633 | io_error = io->error; |
627 | bio = io->bio; | 634 | bio = io->bio; |
628 | 635 | ||
629 | if (bio_rw_flagged(bio, BIO_RW_BARRIER)) { | 636 | if (bio->bi_rw & REQ_HARDBARRIER) { |
630 | /* | 637 | /* |
631 | * There can be just one barrier request so we use | 638 | * There can be just one barrier request so we use |
632 | * a per-device variable for error reporting. | 639 | * a per-device variable for error reporting. |
@@ -792,12 +799,12 @@ static void dm_end_request(struct request *clone, int error) | |||
792 | { | 799 | { |
793 | int rw = rq_data_dir(clone); | 800 | int rw = rq_data_dir(clone); |
794 | int run_queue = 1; | 801 | int run_queue = 1; |
795 | bool is_barrier = blk_barrier_rq(clone); | 802 | bool is_barrier = clone->cmd_flags & REQ_HARDBARRIER; |
796 | struct dm_rq_target_io *tio = clone->end_io_data; | 803 | struct dm_rq_target_io *tio = clone->end_io_data; |
797 | struct mapped_device *md = tio->md; | 804 | struct mapped_device *md = tio->md; |
798 | struct request *rq = tio->orig; | 805 | struct request *rq = tio->orig; |
799 | 806 | ||
800 | if (blk_pc_request(rq) && !is_barrier) { | 807 | if (rq->cmd_type == REQ_TYPE_BLOCK_PC && !is_barrier) { |
801 | rq->errors = clone->errors; | 808 | rq->errors = clone->errors; |
802 | rq->resid_len = clone->resid_len; | 809 | rq->resid_len = clone->resid_len; |
803 | 810 | ||
@@ -844,7 +851,7 @@ void dm_requeue_unmapped_request(struct request *clone) | |||
844 | struct request_queue *q = rq->q; | 851 | struct request_queue *q = rq->q; |
845 | unsigned long flags; | 852 | unsigned long flags; |
846 | 853 | ||
847 | if (unlikely(blk_barrier_rq(clone))) { | 854 | if (unlikely(clone->cmd_flags & REQ_HARDBARRIER)) { |
848 | /* | 855 | /* |
849 | * Barrier clones share an original request. | 856 | * Barrier clones share an original request. |
850 | * Leave it to dm_end_request(), which handles this special | 857 | * Leave it to dm_end_request(), which handles this special |
@@ -943,7 +950,7 @@ static void dm_complete_request(struct request *clone, int error) | |||
943 | struct dm_rq_target_io *tio = clone->end_io_data; | 950 | struct dm_rq_target_io *tio = clone->end_io_data; |
944 | struct request *rq = tio->orig; | 951 | struct request *rq = tio->orig; |
945 | 952 | ||
946 | if (unlikely(blk_barrier_rq(clone))) { | 953 | if (unlikely(clone->cmd_flags & REQ_HARDBARRIER)) { |
947 | /* | 954 | /* |
948 | * Barrier clones share an original request. So can't use | 955 | * Barrier clones share an original request. So can't use |
949 | * softirq_done with the original. | 956 | * softirq_done with the original. |
@@ -972,7 +979,7 @@ void dm_kill_unmapped_request(struct request *clone, int error) | |||
972 | struct dm_rq_target_io *tio = clone->end_io_data; | 979 | struct dm_rq_target_io *tio = clone->end_io_data; |
973 | struct request *rq = tio->orig; | 980 | struct request *rq = tio->orig; |
974 | 981 | ||
975 | if (unlikely(blk_barrier_rq(clone))) { | 982 | if (unlikely(clone->cmd_flags & REQ_HARDBARRIER)) { |
976 | /* | 983 | /* |
977 | * Barrier clones share an original request. | 984 | * Barrier clones share an original request. |
978 | * Leave it to dm_end_request(), which handles this special | 985 | * Leave it to dm_end_request(), which handles this special |
@@ -1106,7 +1113,7 @@ static struct bio *split_bvec(struct bio *bio, sector_t sector, | |||
1106 | 1113 | ||
1107 | clone->bi_sector = sector; | 1114 | clone->bi_sector = sector; |
1108 | clone->bi_bdev = bio->bi_bdev; | 1115 | clone->bi_bdev = bio->bi_bdev; |
1109 | clone->bi_rw = bio->bi_rw & ~(1 << BIO_RW_BARRIER); | 1116 | clone->bi_rw = bio->bi_rw & ~REQ_HARDBARRIER; |
1110 | clone->bi_vcnt = 1; | 1117 | clone->bi_vcnt = 1; |
1111 | clone->bi_size = to_bytes(len); | 1118 | clone->bi_size = to_bytes(len); |
1112 | clone->bi_io_vec->bv_offset = offset; | 1119 | clone->bi_io_vec->bv_offset = offset; |
@@ -1133,7 +1140,7 @@ static struct bio *clone_bio(struct bio *bio, sector_t sector, | |||
1133 | 1140 | ||
1134 | clone = bio_alloc_bioset(GFP_NOIO, bio->bi_max_vecs, bs); | 1141 | clone = bio_alloc_bioset(GFP_NOIO, bio->bi_max_vecs, bs); |
1135 | __bio_clone(clone, bio); | 1142 | __bio_clone(clone, bio); |
1136 | clone->bi_rw &= ~(1 << BIO_RW_BARRIER); | 1143 | clone->bi_rw &= ~REQ_HARDBARRIER; |
1137 | clone->bi_destructor = dm_bio_destructor; | 1144 | clone->bi_destructor = dm_bio_destructor; |
1138 | clone->bi_sector = sector; | 1145 | clone->bi_sector = sector; |
1139 | clone->bi_idx = idx; | 1146 | clone->bi_idx = idx; |
@@ -1301,7 +1308,7 @@ static void __split_and_process_bio(struct mapped_device *md, struct bio *bio) | |||
1301 | 1308 | ||
1302 | ci.map = dm_get_live_table(md); | 1309 | ci.map = dm_get_live_table(md); |
1303 | if (unlikely(!ci.map)) { | 1310 | if (unlikely(!ci.map)) { |
1304 | if (!bio_rw_flagged(bio, BIO_RW_BARRIER)) | 1311 | if (!(bio->bi_rw & REQ_HARDBARRIER)) |
1305 | bio_io_error(bio); | 1312 | bio_io_error(bio); |
1306 | else | 1313 | else |
1307 | if (!md->barrier_error) | 1314 | if (!md->barrier_error) |
@@ -1414,7 +1421,7 @@ static int _dm_request(struct request_queue *q, struct bio *bio) | |||
1414 | * we have to queue this io for later. | 1421 | * we have to queue this io for later. |
1415 | */ | 1422 | */ |
1416 | if (unlikely(test_bit(DMF_QUEUE_IO_TO_THREAD, &md->flags)) || | 1423 | if (unlikely(test_bit(DMF_QUEUE_IO_TO_THREAD, &md->flags)) || |
1417 | unlikely(bio_rw_flagged(bio, BIO_RW_BARRIER))) { | 1424 | unlikely(bio->bi_rw & REQ_HARDBARRIER)) { |
1418 | up_read(&md->io_lock); | 1425 | up_read(&md->io_lock); |
1419 | 1426 | ||
1420 | if (unlikely(test_bit(DMF_BLOCK_IO_FOR_SUSPEND, &md->flags)) && | 1427 | if (unlikely(test_bit(DMF_BLOCK_IO_FOR_SUSPEND, &md->flags)) && |
@@ -1455,20 +1462,9 @@ static int dm_request(struct request_queue *q, struct bio *bio) | |||
1455 | return _dm_request(q, bio); | 1462 | return _dm_request(q, bio); |
1456 | } | 1463 | } |
1457 | 1464 | ||
1458 | /* | ||
1459 | * Mark this request as flush request, so that dm_request_fn() can | ||
1460 | * recognize. | ||
1461 | */ | ||
1462 | static void dm_rq_prepare_flush(struct request_queue *q, struct request *rq) | ||
1463 | { | ||
1464 | rq->cmd_type = REQ_TYPE_LINUX_BLOCK; | ||
1465 | rq->cmd[0] = REQ_LB_OP_FLUSH; | ||
1466 | } | ||
1467 | |||
1468 | static bool dm_rq_is_flush_request(struct request *rq) | 1465 | static bool dm_rq_is_flush_request(struct request *rq) |
1469 | { | 1466 | { |
1470 | if (rq->cmd_type == REQ_TYPE_LINUX_BLOCK && | 1467 | if (rq->cmd_flags & REQ_FLUSH) |
1471 | rq->cmd[0] == REQ_LB_OP_FLUSH) | ||
1472 | return true; | 1468 | return true; |
1473 | else | 1469 | else |
1474 | return false; | 1470 | return false; |
@@ -1912,8 +1908,7 @@ static struct mapped_device *alloc_dev(int minor) | |||
1912 | blk_queue_softirq_done(md->queue, dm_softirq_done); | 1908 | blk_queue_softirq_done(md->queue, dm_softirq_done); |
1913 | blk_queue_prep_rq(md->queue, dm_prep_fn); | 1909 | blk_queue_prep_rq(md->queue, dm_prep_fn); |
1914 | blk_queue_lld_busy(md->queue, dm_lld_busy); | 1910 | blk_queue_lld_busy(md->queue, dm_lld_busy); |
1915 | blk_queue_ordered(md->queue, QUEUE_ORDERED_DRAIN_FLUSH, | 1911 | blk_queue_ordered(md->queue, QUEUE_ORDERED_DRAIN_FLUSH); |
1916 | dm_rq_prepare_flush); | ||
1917 | 1912 | ||
1918 | md->disk = alloc_disk(1); | 1913 | md->disk = alloc_disk(1); |
1919 | if (!md->disk) | 1914 | if (!md->disk) |
@@ -2296,7 +2291,7 @@ static void dm_wq_work(struct work_struct *work) | |||
2296 | if (dm_request_based(md)) | 2291 | if (dm_request_based(md)) |
2297 | generic_make_request(c); | 2292 | generic_make_request(c); |
2298 | else { | 2293 | else { |
2299 | if (bio_rw_flagged(c, BIO_RW_BARRIER)) | 2294 | if (c->bi_rw & REQ_HARDBARRIER) |
2300 | process_barrier(md, c); | 2295 | process_barrier(md, c); |
2301 | else | 2296 | else |
2302 | __split_and_process_bio(md, c); | 2297 | __split_and_process_bio(md, c); |
diff --git a/drivers/md/linear.c b/drivers/md/linear.c index 7e0e057db9a7..ba19060bcf3f 100644 --- a/drivers/md/linear.c +++ b/drivers/md/linear.c | |||
@@ -294,7 +294,7 @@ static int linear_make_request (mddev_t *mddev, struct bio *bio) | |||
294 | dev_info_t *tmp_dev; | 294 | dev_info_t *tmp_dev; |
295 | sector_t start_sector; | 295 | sector_t start_sector; |
296 | 296 | ||
297 | if (unlikely(bio_rw_flagged(bio, BIO_RW_BARRIER))) { | 297 | if (unlikely(bio->bi_rw & REQ_HARDBARRIER)) { |
298 | md_barrier_request(mddev, bio); | 298 | md_barrier_request(mddev, bio); |
299 | return 0; | 299 | return 0; |
300 | } | 300 | } |
diff --git a/drivers/md/md.c b/drivers/md/md.c index cb20d0b0555a..700c96edf9b2 100644 --- a/drivers/md/md.c +++ b/drivers/md/md.c | |||
@@ -36,6 +36,7 @@ | |||
36 | #include <linux/blkdev.h> | 36 | #include <linux/blkdev.h> |
37 | #include <linux/sysctl.h> | 37 | #include <linux/sysctl.h> |
38 | #include <linux/seq_file.h> | 38 | #include <linux/seq_file.h> |
39 | #include <linux/smp_lock.h> | ||
39 | #include <linux/buffer_head.h> /* for invalidate_bdev */ | 40 | #include <linux/buffer_head.h> /* for invalidate_bdev */ |
40 | #include <linux/poll.h> | 41 | #include <linux/poll.h> |
41 | #include <linux/ctype.h> | 42 | #include <linux/ctype.h> |
@@ -353,7 +354,7 @@ static void md_submit_barrier(struct work_struct *ws) | |||
353 | /* an empty barrier - all done */ | 354 | /* an empty barrier - all done */ |
354 | bio_endio(bio, 0); | 355 | bio_endio(bio, 0); |
355 | else { | 356 | else { |
356 | bio->bi_rw &= ~(1<<BIO_RW_BARRIER); | 357 | bio->bi_rw &= ~REQ_HARDBARRIER; |
357 | if (mddev->pers->make_request(mddev, bio)) | 358 | if (mddev->pers->make_request(mddev, bio)) |
358 | generic_make_request(bio); | 359 | generic_make_request(bio); |
359 | mddev->barrier = POST_REQUEST_BARRIER; | 360 | mddev->barrier = POST_REQUEST_BARRIER; |
@@ -675,11 +676,11 @@ void md_super_write(mddev_t *mddev, mdk_rdev_t *rdev, | |||
675 | * if zero is reached. | 676 | * if zero is reached. |
676 | * If an error occurred, call md_error | 677 | * If an error occurred, call md_error |
677 | * | 678 | * |
678 | * As we might need to resubmit the request if BIO_RW_BARRIER | 679 | * As we might need to resubmit the request if REQ_HARDBARRIER |
679 | * causes ENOTSUPP, we allocate a spare bio... | 680 | * causes ENOTSUPP, we allocate a spare bio... |
680 | */ | 681 | */ |
681 | struct bio *bio = bio_alloc(GFP_NOIO, 1); | 682 | struct bio *bio = bio_alloc(GFP_NOIO, 1); |
682 | int rw = (1<<BIO_RW) | (1<<BIO_RW_SYNCIO) | (1<<BIO_RW_UNPLUG); | 683 | int rw = REQ_WRITE | REQ_SYNC | REQ_UNPLUG; |
683 | 684 | ||
684 | bio->bi_bdev = rdev->bdev; | 685 | bio->bi_bdev = rdev->bdev; |
685 | bio->bi_sector = sector; | 686 | bio->bi_sector = sector; |
@@ -691,7 +692,7 @@ void md_super_write(mddev_t *mddev, mdk_rdev_t *rdev, | |||
691 | atomic_inc(&mddev->pending_writes); | 692 | atomic_inc(&mddev->pending_writes); |
692 | if (!test_bit(BarriersNotsupp, &rdev->flags)) { | 693 | if (!test_bit(BarriersNotsupp, &rdev->flags)) { |
693 | struct bio *rbio; | 694 | struct bio *rbio; |
694 | rw |= (1<<BIO_RW_BARRIER); | 695 | rw |= REQ_HARDBARRIER; |
695 | rbio = bio_clone(bio, GFP_NOIO); | 696 | rbio = bio_clone(bio, GFP_NOIO); |
696 | rbio->bi_private = bio; | 697 | rbio->bi_private = bio; |
697 | rbio->bi_end_io = super_written_barrier; | 698 | rbio->bi_end_io = super_written_barrier; |
@@ -736,7 +737,7 @@ int sync_page_io(struct block_device *bdev, sector_t sector, int size, | |||
736 | struct completion event; | 737 | struct completion event; |
737 | int ret; | 738 | int ret; |
738 | 739 | ||
739 | rw |= (1 << BIO_RW_SYNCIO) | (1 << BIO_RW_UNPLUG); | 740 | rw |= REQ_SYNC | REQ_UNPLUG; |
740 | 741 | ||
741 | bio->bi_bdev = bdev; | 742 | bio->bi_bdev = bdev; |
742 | bio->bi_sector = sector; | 743 | bio->bi_sector = sector; |
@@ -5902,6 +5903,7 @@ static int md_open(struct block_device *bdev, fmode_t mode) | |||
5902 | mddev_t *mddev = mddev_find(bdev->bd_dev); | 5903 | mddev_t *mddev = mddev_find(bdev->bd_dev); |
5903 | int err; | 5904 | int err; |
5904 | 5905 | ||
5906 | lock_kernel(); | ||
5905 | if (mddev->gendisk != bdev->bd_disk) { | 5907 | if (mddev->gendisk != bdev->bd_disk) { |
5906 | /* we are racing with mddev_put which is discarding this | 5908 | /* we are racing with mddev_put which is discarding this |
5907 | * bd_disk. | 5909 | * bd_disk. |
@@ -5910,6 +5912,7 @@ static int md_open(struct block_device *bdev, fmode_t mode) | |||
5910 | /* Wait until bdev->bd_disk is definitely gone */ | 5912 | /* Wait until bdev->bd_disk is definitely gone */ |
5911 | flush_scheduled_work(); | 5913 | flush_scheduled_work(); |
5912 | /* Then retry the open from the top */ | 5914 | /* Then retry the open from the top */ |
5915 | unlock_kernel(); | ||
5913 | return -ERESTARTSYS; | 5916 | return -ERESTARTSYS; |
5914 | } | 5917 | } |
5915 | BUG_ON(mddev != bdev->bd_disk->private_data); | 5918 | BUG_ON(mddev != bdev->bd_disk->private_data); |
@@ -5923,6 +5926,7 @@ static int md_open(struct block_device *bdev, fmode_t mode) | |||
5923 | 5926 | ||
5924 | check_disk_size_change(mddev->gendisk, bdev); | 5927 | check_disk_size_change(mddev->gendisk, bdev); |
5925 | out: | 5928 | out: |
5929 | unlock_kernel(); | ||
5926 | return err; | 5930 | return err; |
5927 | } | 5931 | } |
5928 | 5932 | ||
@@ -5931,8 +5935,10 @@ static int md_release(struct gendisk *disk, fmode_t mode) | |||
5931 | mddev_t *mddev = disk->private_data; | 5935 | mddev_t *mddev = disk->private_data; |
5932 | 5936 | ||
5933 | BUG_ON(!mddev); | 5937 | BUG_ON(!mddev); |
5938 | lock_kernel(); | ||
5934 | atomic_dec(&mddev->openers); | 5939 | atomic_dec(&mddev->openers); |
5935 | mddev_put(mddev); | 5940 | mddev_put(mddev); |
5941 | unlock_kernel(); | ||
5936 | 5942 | ||
5937 | return 0; | 5943 | return 0; |
5938 | } | 5944 | } |
diff --git a/drivers/md/md.h b/drivers/md/md.h index 10597bfec000..fc56e0f21c80 100644 --- a/drivers/md/md.h +++ b/drivers/md/md.h | |||
@@ -67,7 +67,7 @@ struct mdk_rdev_s | |||
67 | #define Faulty 1 /* device is known to have a fault */ | 67 | #define Faulty 1 /* device is known to have a fault */ |
68 | #define In_sync 2 /* device is in_sync with rest of array */ | 68 | #define In_sync 2 /* device is in_sync with rest of array */ |
69 | #define WriteMostly 4 /* Avoid reading if at all possible */ | 69 | #define WriteMostly 4 /* Avoid reading if at all possible */ |
70 | #define BarriersNotsupp 5 /* BIO_RW_BARRIER is not supported */ | 70 | #define BarriersNotsupp 5 /* REQ_HARDBARRIER is not supported */ |
71 | #define AllReserved 6 /* If whole device is reserved for | 71 | #define AllReserved 6 /* If whole device is reserved for |
72 | * one array */ | 72 | * one array */ |
73 | #define AutoDetected 7 /* added by auto-detect */ | 73 | #define AutoDetected 7 /* added by auto-detect */ |
@@ -254,7 +254,7 @@ struct mddev_s | |||
254 | * fails. Only supported | 254 | * fails. Only supported |
255 | */ | 255 | */ |
256 | struct bio *biolist; /* bios that need to be retried | 256 | struct bio *biolist; /* bios that need to be retried |
257 | * because BIO_RW_BARRIER is not supported | 257 | * because REQ_HARDBARRIER is not supported |
258 | */ | 258 | */ |
259 | 259 | ||
260 | atomic_t recovery_active; /* blocks scheduled, but not written */ | 260 | atomic_t recovery_active; /* blocks scheduled, but not written */ |
diff --git a/drivers/md/multipath.c b/drivers/md/multipath.c index 410fb60699ac..0307d217e7a4 100644 --- a/drivers/md/multipath.c +++ b/drivers/md/multipath.c | |||
@@ -91,7 +91,7 @@ static void multipath_end_request(struct bio *bio, int error) | |||
91 | 91 | ||
92 | if (uptodate) | 92 | if (uptodate) |
93 | multipath_end_bh_io(mp_bh, 0); | 93 | multipath_end_bh_io(mp_bh, 0); |
94 | else if (!bio_rw_flagged(bio, BIO_RW_AHEAD)) { | 94 | else if (!(bio->bi_rw & REQ_RAHEAD)) { |
95 | /* | 95 | /* |
96 | * oops, IO error: | 96 | * oops, IO error: |
97 | */ | 97 | */ |
@@ -142,7 +142,7 @@ static int multipath_make_request(mddev_t *mddev, struct bio * bio) | |||
142 | struct multipath_bh * mp_bh; | 142 | struct multipath_bh * mp_bh; |
143 | struct multipath_info *multipath; | 143 | struct multipath_info *multipath; |
144 | 144 | ||
145 | if (unlikely(bio_rw_flagged(bio, BIO_RW_BARRIER))) { | 145 | if (unlikely(bio->bi_rw & REQ_HARDBARRIER)) { |
146 | md_barrier_request(mddev, bio); | 146 | md_barrier_request(mddev, bio); |
147 | return 0; | 147 | return 0; |
148 | } | 148 | } |
@@ -163,7 +163,7 @@ static int multipath_make_request(mddev_t *mddev, struct bio * bio) | |||
163 | mp_bh->bio = *bio; | 163 | mp_bh->bio = *bio; |
164 | mp_bh->bio.bi_sector += multipath->rdev->data_offset; | 164 | mp_bh->bio.bi_sector += multipath->rdev->data_offset; |
165 | mp_bh->bio.bi_bdev = multipath->rdev->bdev; | 165 | mp_bh->bio.bi_bdev = multipath->rdev->bdev; |
166 | mp_bh->bio.bi_rw |= (1 << BIO_RW_FAILFAST_TRANSPORT); | 166 | mp_bh->bio.bi_rw |= REQ_FAILFAST_TRANSPORT; |
167 | mp_bh->bio.bi_end_io = multipath_end_request; | 167 | mp_bh->bio.bi_end_io = multipath_end_request; |
168 | mp_bh->bio.bi_private = mp_bh; | 168 | mp_bh->bio.bi_private = mp_bh; |
169 | generic_make_request(&mp_bh->bio); | 169 | generic_make_request(&mp_bh->bio); |
@@ -398,7 +398,7 @@ static void multipathd (mddev_t *mddev) | |||
398 | *bio = *(mp_bh->master_bio); | 398 | *bio = *(mp_bh->master_bio); |
399 | bio->bi_sector += conf->multipaths[mp_bh->path].rdev->data_offset; | 399 | bio->bi_sector += conf->multipaths[mp_bh->path].rdev->data_offset; |
400 | bio->bi_bdev = conf->multipaths[mp_bh->path].rdev->bdev; | 400 | bio->bi_bdev = conf->multipaths[mp_bh->path].rdev->bdev; |
401 | bio->bi_rw |= (1 << BIO_RW_FAILFAST_TRANSPORT); | 401 | bio->bi_rw |= REQ_FAILFAST_TRANSPORT; |
402 | bio->bi_end_io = multipath_end_request; | 402 | bio->bi_end_io = multipath_end_request; |
403 | bio->bi_private = mp_bh; | 403 | bio->bi_private = mp_bh; |
404 | generic_make_request(bio); | 404 | generic_make_request(bio); |
diff --git a/drivers/md/raid0.c b/drivers/md/raid0.c index 563abed5a2cb..6f7af46d623c 100644 --- a/drivers/md/raid0.c +++ b/drivers/md/raid0.c | |||
@@ -483,7 +483,7 @@ static int raid0_make_request(mddev_t *mddev, struct bio *bio) | |||
483 | struct strip_zone *zone; | 483 | struct strip_zone *zone; |
484 | mdk_rdev_t *tmp_dev; | 484 | mdk_rdev_t *tmp_dev; |
485 | 485 | ||
486 | if (unlikely(bio_rw_flagged(bio, BIO_RW_BARRIER))) { | 486 | if (unlikely(bio->bi_rw & REQ_HARDBARRIER)) { |
487 | md_barrier_request(mddev, bio); | 487 | md_barrier_request(mddev, bio); |
488 | return 0; | 488 | return 0; |
489 | } | 489 | } |
diff --git a/drivers/md/raid1.c b/drivers/md/raid1.c index a948da8012de..73cc74ffc26b 100644 --- a/drivers/md/raid1.c +++ b/drivers/md/raid1.c | |||
@@ -787,7 +787,7 @@ static int make_request(mddev_t *mddev, struct bio * bio) | |||
787 | struct bio_list bl; | 787 | struct bio_list bl; |
788 | struct page **behind_pages = NULL; | 788 | struct page **behind_pages = NULL; |
789 | const int rw = bio_data_dir(bio); | 789 | const int rw = bio_data_dir(bio); |
790 | const bool do_sync = bio_rw_flagged(bio, BIO_RW_SYNCIO); | 790 | const bool do_sync = (bio->bi_rw & REQ_SYNC); |
791 | bool do_barriers; | 791 | bool do_barriers; |
792 | mdk_rdev_t *blocked_rdev; | 792 | mdk_rdev_t *blocked_rdev; |
793 | 793 | ||
@@ -822,7 +822,7 @@ static int make_request(mddev_t *mddev, struct bio * bio) | |||
822 | finish_wait(&conf->wait_barrier, &w); | 822 | finish_wait(&conf->wait_barrier, &w); |
823 | } | 823 | } |
824 | if (unlikely(!mddev->barriers_work && | 824 | if (unlikely(!mddev->barriers_work && |
825 | bio_rw_flagged(bio, BIO_RW_BARRIER))) { | 825 | (bio->bi_rw & REQ_HARDBARRIER))) { |
826 | if (rw == WRITE) | 826 | if (rw == WRITE) |
827 | md_write_end(mddev); | 827 | md_write_end(mddev); |
828 | bio_endio(bio, -EOPNOTSUPP); | 828 | bio_endio(bio, -EOPNOTSUPP); |
@@ -877,7 +877,7 @@ static int make_request(mddev_t *mddev, struct bio * bio) | |||
877 | read_bio->bi_sector = r1_bio->sector + mirror->rdev->data_offset; | 877 | read_bio->bi_sector = r1_bio->sector + mirror->rdev->data_offset; |
878 | read_bio->bi_bdev = mirror->rdev->bdev; | 878 | read_bio->bi_bdev = mirror->rdev->bdev; |
879 | read_bio->bi_end_io = raid1_end_read_request; | 879 | read_bio->bi_end_io = raid1_end_read_request; |
880 | read_bio->bi_rw = READ | (do_sync << BIO_RW_SYNCIO); | 880 | read_bio->bi_rw = READ | do_sync; |
881 | read_bio->bi_private = r1_bio; | 881 | read_bio->bi_private = r1_bio; |
882 | 882 | ||
883 | generic_make_request(read_bio); | 883 | generic_make_request(read_bio); |
@@ -959,7 +959,7 @@ static int make_request(mddev_t *mddev, struct bio * bio) | |||
959 | atomic_set(&r1_bio->remaining, 0); | 959 | atomic_set(&r1_bio->remaining, 0); |
960 | atomic_set(&r1_bio->behind_remaining, 0); | 960 | atomic_set(&r1_bio->behind_remaining, 0); |
961 | 961 | ||
962 | do_barriers = bio_rw_flagged(bio, BIO_RW_BARRIER); | 962 | do_barriers = bio->bi_rw & REQ_HARDBARRIER; |
963 | if (do_barriers) | 963 | if (do_barriers) |
964 | set_bit(R1BIO_Barrier, &r1_bio->state); | 964 | set_bit(R1BIO_Barrier, &r1_bio->state); |
965 | 965 | ||
@@ -975,8 +975,7 @@ static int make_request(mddev_t *mddev, struct bio * bio) | |||
975 | mbio->bi_sector = r1_bio->sector + conf->mirrors[i].rdev->data_offset; | 975 | mbio->bi_sector = r1_bio->sector + conf->mirrors[i].rdev->data_offset; |
976 | mbio->bi_bdev = conf->mirrors[i].rdev->bdev; | 976 | mbio->bi_bdev = conf->mirrors[i].rdev->bdev; |
977 | mbio->bi_end_io = raid1_end_write_request; | 977 | mbio->bi_end_io = raid1_end_write_request; |
978 | mbio->bi_rw = WRITE | (do_barriers << BIO_RW_BARRIER) | | 978 | mbio->bi_rw = WRITE | do_barriers | do_sync; |
979 | (do_sync << BIO_RW_SYNCIO); | ||
980 | mbio->bi_private = r1_bio; | 979 | mbio->bi_private = r1_bio; |
981 | 980 | ||
982 | if (behind_pages) { | 981 | if (behind_pages) { |
@@ -1633,7 +1632,7 @@ static void raid1d(mddev_t *mddev) | |||
1633 | sync_request_write(mddev, r1_bio); | 1632 | sync_request_write(mddev, r1_bio); |
1634 | unplug = 1; | 1633 | unplug = 1; |
1635 | } else if (test_bit(R1BIO_BarrierRetry, &r1_bio->state)) { | 1634 | } else if (test_bit(R1BIO_BarrierRetry, &r1_bio->state)) { |
1636 | /* some requests in the r1bio were BIO_RW_BARRIER | 1635 | /* some requests in the r1bio were REQ_HARDBARRIER |
1637 | * requests which failed with -EOPNOTSUPP. Hohumm.. | 1636 | * requests which failed with -EOPNOTSUPP. Hohumm.. |
1638 | * Better resubmit without the barrier. | 1637 | * Better resubmit without the barrier. |
1639 | * We know which devices to resubmit for, because | 1638 | * We know which devices to resubmit for, because |
@@ -1641,7 +1640,7 @@ static void raid1d(mddev_t *mddev) | |||
1641 | * We already have a nr_pending reference on these rdevs. | 1640 | * We already have a nr_pending reference on these rdevs. |
1642 | */ | 1641 | */ |
1643 | int i; | 1642 | int i; |
1644 | const bool do_sync = bio_rw_flagged(r1_bio->master_bio, BIO_RW_SYNCIO); | 1643 | const bool do_sync = (r1_bio->master_bio->bi_rw & REQ_SYNC); |
1645 | clear_bit(R1BIO_BarrierRetry, &r1_bio->state); | 1644 | clear_bit(R1BIO_BarrierRetry, &r1_bio->state); |
1646 | clear_bit(R1BIO_Barrier, &r1_bio->state); | 1645 | clear_bit(R1BIO_Barrier, &r1_bio->state); |
1647 | for (i=0; i < conf->raid_disks; i++) | 1646 | for (i=0; i < conf->raid_disks; i++) |
@@ -1662,8 +1661,7 @@ static void raid1d(mddev_t *mddev) | |||
1662 | conf->mirrors[i].rdev->data_offset; | 1661 | conf->mirrors[i].rdev->data_offset; |
1663 | bio->bi_bdev = conf->mirrors[i].rdev->bdev; | 1662 | bio->bi_bdev = conf->mirrors[i].rdev->bdev; |
1664 | bio->bi_end_io = raid1_end_write_request; | 1663 | bio->bi_end_io = raid1_end_write_request; |
1665 | bio->bi_rw = WRITE | | 1664 | bio->bi_rw = WRITE | do_sync; |
1666 | (do_sync << BIO_RW_SYNCIO); | ||
1667 | bio->bi_private = r1_bio; | 1665 | bio->bi_private = r1_bio; |
1668 | r1_bio->bios[i] = bio; | 1666 | r1_bio->bios[i] = bio; |
1669 | generic_make_request(bio); | 1667 | generic_make_request(bio); |
@@ -1698,7 +1696,7 @@ static void raid1d(mddev_t *mddev) | |||
1698 | (unsigned long long)r1_bio->sector); | 1696 | (unsigned long long)r1_bio->sector); |
1699 | raid_end_bio_io(r1_bio); | 1697 | raid_end_bio_io(r1_bio); |
1700 | } else { | 1698 | } else { |
1701 | const bool do_sync = bio_rw_flagged(r1_bio->master_bio, BIO_RW_SYNCIO); | 1699 | const bool do_sync = r1_bio->master_bio->bi_rw & REQ_SYNC; |
1702 | r1_bio->bios[r1_bio->read_disk] = | 1700 | r1_bio->bios[r1_bio->read_disk] = |
1703 | mddev->ro ? IO_BLOCKED : NULL; | 1701 | mddev->ro ? IO_BLOCKED : NULL; |
1704 | r1_bio->read_disk = disk; | 1702 | r1_bio->read_disk = disk; |
@@ -1715,7 +1713,7 @@ static void raid1d(mddev_t *mddev) | |||
1715 | bio->bi_sector = r1_bio->sector + rdev->data_offset; | 1713 | bio->bi_sector = r1_bio->sector + rdev->data_offset; |
1716 | bio->bi_bdev = rdev->bdev; | 1714 | bio->bi_bdev = rdev->bdev; |
1717 | bio->bi_end_io = raid1_end_read_request; | 1715 | bio->bi_end_io = raid1_end_read_request; |
1718 | bio->bi_rw = READ | (do_sync << BIO_RW_SYNCIO); | 1716 | bio->bi_rw = READ | do_sync; |
1719 | bio->bi_private = r1_bio; | 1717 | bio->bi_private = r1_bio; |
1720 | unplug = 1; | 1718 | unplug = 1; |
1721 | generic_make_request(bio); | 1719 | generic_make_request(bio); |
diff --git a/drivers/md/raid10.c b/drivers/md/raid10.c index 42e64e4e5e25..62ecb6650fd0 100644 --- a/drivers/md/raid10.c +++ b/drivers/md/raid10.c | |||
@@ -799,12 +799,12 @@ static int make_request(mddev_t *mddev, struct bio * bio) | |||
799 | int i; | 799 | int i; |
800 | int chunk_sects = conf->chunk_mask + 1; | 800 | int chunk_sects = conf->chunk_mask + 1; |
801 | const int rw = bio_data_dir(bio); | 801 | const int rw = bio_data_dir(bio); |
802 | const bool do_sync = bio_rw_flagged(bio, BIO_RW_SYNCIO); | 802 | const bool do_sync = (bio->bi_rw & REQ_SYNC); |
803 | struct bio_list bl; | 803 | struct bio_list bl; |
804 | unsigned long flags; | 804 | unsigned long flags; |
805 | mdk_rdev_t *blocked_rdev; | 805 | mdk_rdev_t *blocked_rdev; |
806 | 806 | ||
807 | if (unlikely(bio_rw_flagged(bio, BIO_RW_BARRIER))) { | 807 | if (unlikely(bio->bi_rw & REQ_HARDBARRIER)) { |
808 | md_barrier_request(mddev, bio); | 808 | md_barrier_request(mddev, bio); |
809 | return 0; | 809 | return 0; |
810 | } | 810 | } |
@@ -879,7 +879,7 @@ static int make_request(mddev_t *mddev, struct bio * bio) | |||
879 | mirror->rdev->data_offset; | 879 | mirror->rdev->data_offset; |
880 | read_bio->bi_bdev = mirror->rdev->bdev; | 880 | read_bio->bi_bdev = mirror->rdev->bdev; |
881 | read_bio->bi_end_io = raid10_end_read_request; | 881 | read_bio->bi_end_io = raid10_end_read_request; |
882 | read_bio->bi_rw = READ | (do_sync << BIO_RW_SYNCIO); | 882 | read_bio->bi_rw = READ | do_sync; |
883 | read_bio->bi_private = r10_bio; | 883 | read_bio->bi_private = r10_bio; |
884 | 884 | ||
885 | generic_make_request(read_bio); | 885 | generic_make_request(read_bio); |
@@ -947,7 +947,7 @@ static int make_request(mddev_t *mddev, struct bio * bio) | |||
947 | conf->mirrors[d].rdev->data_offset; | 947 | conf->mirrors[d].rdev->data_offset; |
948 | mbio->bi_bdev = conf->mirrors[d].rdev->bdev; | 948 | mbio->bi_bdev = conf->mirrors[d].rdev->bdev; |
949 | mbio->bi_end_io = raid10_end_write_request; | 949 | mbio->bi_end_io = raid10_end_write_request; |
950 | mbio->bi_rw = WRITE | (do_sync << BIO_RW_SYNCIO); | 950 | mbio->bi_rw = WRITE | do_sync; |
951 | mbio->bi_private = r10_bio; | 951 | mbio->bi_private = r10_bio; |
952 | 952 | ||
953 | atomic_inc(&r10_bio->remaining); | 953 | atomic_inc(&r10_bio->remaining); |
@@ -1716,7 +1716,7 @@ static void raid10d(mddev_t *mddev) | |||
1716 | raid_end_bio_io(r10_bio); | 1716 | raid_end_bio_io(r10_bio); |
1717 | bio_put(bio); | 1717 | bio_put(bio); |
1718 | } else { | 1718 | } else { |
1719 | const bool do_sync = bio_rw_flagged(r10_bio->master_bio, BIO_RW_SYNCIO); | 1719 | const bool do_sync = (r10_bio->master_bio->bi_rw & REQ_SYNC); |
1720 | bio_put(bio); | 1720 | bio_put(bio); |
1721 | rdev = conf->mirrors[mirror].rdev; | 1721 | rdev = conf->mirrors[mirror].rdev; |
1722 | if (printk_ratelimit()) | 1722 | if (printk_ratelimit()) |
@@ -1730,7 +1730,7 @@ static void raid10d(mddev_t *mddev) | |||
1730 | bio->bi_sector = r10_bio->devs[r10_bio->read_slot].addr | 1730 | bio->bi_sector = r10_bio->devs[r10_bio->read_slot].addr |
1731 | + rdev->data_offset; | 1731 | + rdev->data_offset; |
1732 | bio->bi_bdev = rdev->bdev; | 1732 | bio->bi_bdev = rdev->bdev; |
1733 | bio->bi_rw = READ | (do_sync << BIO_RW_SYNCIO); | 1733 | bio->bi_rw = READ | do_sync; |
1734 | bio->bi_private = r10_bio; | 1734 | bio->bi_private = r10_bio; |
1735 | bio->bi_end_io = raid10_end_read_request; | 1735 | bio->bi_end_io = raid10_end_read_request; |
1736 | unplug = 1; | 1736 | unplug = 1; |
diff --git a/drivers/md/raid5.c b/drivers/md/raid5.c index 96c690279fc6..20ac2f14376a 100644 --- a/drivers/md/raid5.c +++ b/drivers/md/raid5.c | |||
@@ -3958,7 +3958,7 @@ static int make_request(mddev_t *mddev, struct bio * bi) | |||
3958 | const int rw = bio_data_dir(bi); | 3958 | const int rw = bio_data_dir(bi); |
3959 | int remaining; | 3959 | int remaining; |
3960 | 3960 | ||
3961 | if (unlikely(bio_rw_flagged(bi, BIO_RW_BARRIER))) { | 3961 | if (unlikely(bi->bi_rw & REQ_HARDBARRIER)) { |
3962 | /* Drain all pending writes. We only really need | 3962 | /* Drain all pending writes. We only really need |
3963 | * to ensure they have been submitted, but this is | 3963 | * to ensure they have been submitted, but this is |
3964 | * easier. | 3964 | * easier. |
diff --git a/drivers/memstick/core/mspro_block.c b/drivers/memstick/core/mspro_block.c index 8327e248520a..eef78a068fd1 100644 --- a/drivers/memstick/core/mspro_block.c +++ b/drivers/memstick/core/mspro_block.c | |||
@@ -18,6 +18,7 @@ | |||
18 | #include <linux/kthread.h> | 18 | #include <linux/kthread.h> |
19 | #include <linux/delay.h> | 19 | #include <linux/delay.h> |
20 | #include <linux/slab.h> | 20 | #include <linux/slab.h> |
21 | #include <linux/smp_lock.h> | ||
21 | #include <linux/memstick.h> | 22 | #include <linux/memstick.h> |
22 | 23 | ||
23 | #define DRIVER_NAME "mspro_block" | 24 | #define DRIVER_NAME "mspro_block" |
@@ -179,6 +180,7 @@ static int mspro_block_bd_open(struct block_device *bdev, fmode_t mode) | |||
179 | struct mspro_block_data *msb = disk->private_data; | 180 | struct mspro_block_data *msb = disk->private_data; |
180 | int rc = -ENXIO; | 181 | int rc = -ENXIO; |
181 | 182 | ||
183 | lock_kernel(); | ||
182 | mutex_lock(&mspro_block_disk_lock); | 184 | mutex_lock(&mspro_block_disk_lock); |
183 | 185 | ||
184 | if (msb && msb->card) { | 186 | if (msb && msb->card) { |
@@ -190,6 +192,7 @@ static int mspro_block_bd_open(struct block_device *bdev, fmode_t mode) | |||
190 | } | 192 | } |
191 | 193 | ||
192 | mutex_unlock(&mspro_block_disk_lock); | 194 | mutex_unlock(&mspro_block_disk_lock); |
195 | unlock_kernel(); | ||
193 | 196 | ||
194 | return rc; | 197 | return rc; |
195 | } | 198 | } |
@@ -221,7 +224,11 @@ static int mspro_block_disk_release(struct gendisk *disk) | |||
221 | 224 | ||
222 | static int mspro_block_bd_release(struct gendisk *disk, fmode_t mode) | 225 | static int mspro_block_bd_release(struct gendisk *disk, fmode_t mode) |
223 | { | 226 | { |
224 | return mspro_block_disk_release(disk); | 227 | int ret; |
228 | lock_kernel(); | ||
229 | ret = mspro_block_disk_release(disk); | ||
230 | unlock_kernel(); | ||
231 | return ret; | ||
225 | } | 232 | } |
226 | 233 | ||
227 | static int mspro_block_bd_getgeo(struct block_device *bdev, | 234 | static int mspro_block_bd_getgeo(struct block_device *bdev, |
@@ -805,7 +812,8 @@ static void mspro_block_start(struct memstick_dev *card) | |||
805 | 812 | ||
806 | static int mspro_block_prepare_req(struct request_queue *q, struct request *req) | 813 | static int mspro_block_prepare_req(struct request_queue *q, struct request *req) |
807 | { | 814 | { |
808 | if (!blk_fs_request(req) && !blk_pc_request(req)) { | 815 | if (req->cmd_type != REQ_TYPE_FS && |
816 | req->cmd_type != REQ_TYPE_BLOCK_PC) { | ||
809 | blk_dump_rq_flags(req, "MSPro unsupported request"); | 817 | blk_dump_rq_flags(req, "MSPro unsupported request"); |
810 | return BLKPREP_KILL; | 818 | return BLKPREP_KILL; |
811 | } | 819 | } |
diff --git a/drivers/message/i2o/i2o_block.c b/drivers/message/i2o/i2o_block.c index fc593fbab696..e6733bc99724 100644 --- a/drivers/message/i2o/i2o_block.c +++ b/drivers/message/i2o/i2o_block.c | |||
@@ -53,6 +53,7 @@ | |||
53 | #include <linux/module.h> | 53 | #include <linux/module.h> |
54 | #include <linux/slab.h> | 54 | #include <linux/slab.h> |
55 | #include <linux/i2o.h> | 55 | #include <linux/i2o.h> |
56 | #include <linux/smp_lock.h> | ||
56 | 57 | ||
57 | #include <linux/mempool.h> | 58 | #include <linux/mempool.h> |
58 | 59 | ||
@@ -577,6 +578,7 @@ static int i2o_block_open(struct block_device *bdev, fmode_t mode) | |||
577 | if (!dev->i2o_dev) | 578 | if (!dev->i2o_dev) |
578 | return -ENODEV; | 579 | return -ENODEV; |
579 | 580 | ||
581 | lock_kernel(); | ||
580 | if (dev->power > 0x1f) | 582 | if (dev->power > 0x1f) |
581 | i2o_block_device_power(dev, 0x02); | 583 | i2o_block_device_power(dev, 0x02); |
582 | 584 | ||
@@ -585,6 +587,7 @@ static int i2o_block_open(struct block_device *bdev, fmode_t mode) | |||
585 | i2o_block_device_lock(dev->i2o_dev, -1); | 587 | i2o_block_device_lock(dev->i2o_dev, -1); |
586 | 588 | ||
587 | osm_debug("Ready.\n"); | 589 | osm_debug("Ready.\n"); |
590 | unlock_kernel(); | ||
588 | 591 | ||
589 | return 0; | 592 | return 0; |
590 | }; | 593 | }; |
@@ -615,6 +618,7 @@ static int i2o_block_release(struct gendisk *disk, fmode_t mode) | |||
615 | if (!dev->i2o_dev) | 618 | if (!dev->i2o_dev) |
616 | return 0; | 619 | return 0; |
617 | 620 | ||
621 | lock_kernel(); | ||
618 | i2o_block_device_flush(dev->i2o_dev); | 622 | i2o_block_device_flush(dev->i2o_dev); |
619 | 623 | ||
620 | i2o_block_device_unlock(dev->i2o_dev, -1); | 624 | i2o_block_device_unlock(dev->i2o_dev, -1); |
@@ -625,6 +629,7 @@ static int i2o_block_release(struct gendisk *disk, fmode_t mode) | |||
625 | operation = 0x24; | 629 | operation = 0x24; |
626 | 630 | ||
627 | i2o_block_device_power(dev, operation); | 631 | i2o_block_device_power(dev, operation); |
632 | unlock_kernel(); | ||
628 | 633 | ||
629 | return 0; | 634 | return 0; |
630 | } | 635 | } |
@@ -652,30 +657,40 @@ static int i2o_block_ioctl(struct block_device *bdev, fmode_t mode, | |||
652 | { | 657 | { |
653 | struct gendisk *disk = bdev->bd_disk; | 658 | struct gendisk *disk = bdev->bd_disk; |
654 | struct i2o_block_device *dev = disk->private_data; | 659 | struct i2o_block_device *dev = disk->private_data; |
660 | int ret = -ENOTTY; | ||
655 | 661 | ||
656 | /* Anyone capable of this syscall can do *real bad* things */ | 662 | /* Anyone capable of this syscall can do *real bad* things */ |
657 | 663 | ||
658 | if (!capable(CAP_SYS_ADMIN)) | 664 | if (!capable(CAP_SYS_ADMIN)) |
659 | return -EPERM; | 665 | return -EPERM; |
660 | 666 | ||
667 | lock_kernel(); | ||
661 | switch (cmd) { | 668 | switch (cmd) { |
662 | case BLKI2OGRSTRAT: | 669 | case BLKI2OGRSTRAT: |
663 | return put_user(dev->rcache, (int __user *)arg); | 670 | ret = put_user(dev->rcache, (int __user *)arg); |
671 | break; | ||
664 | case BLKI2OGWSTRAT: | 672 | case BLKI2OGWSTRAT: |
665 | return put_user(dev->wcache, (int __user *)arg); | 673 | ret = put_user(dev->wcache, (int __user *)arg); |
674 | break; | ||
666 | case BLKI2OSRSTRAT: | 675 | case BLKI2OSRSTRAT: |
676 | ret = -EINVAL; | ||
667 | if (arg < 0 || arg > CACHE_SMARTFETCH) | 677 | if (arg < 0 || arg > CACHE_SMARTFETCH) |
668 | return -EINVAL; | 678 | break; |
669 | dev->rcache = arg; | 679 | dev->rcache = arg; |
680 | ret = 0; | ||
670 | break; | 681 | break; |
671 | case BLKI2OSWSTRAT: | 682 | case BLKI2OSWSTRAT: |
683 | ret = -EINVAL; | ||
672 | if (arg != 0 | 684 | if (arg != 0 |
673 | && (arg < CACHE_WRITETHROUGH || arg > CACHE_SMARTBACK)) | 685 | && (arg < CACHE_WRITETHROUGH || arg > CACHE_SMARTBACK)) |
674 | return -EINVAL; | 686 | break; |
675 | dev->wcache = arg; | 687 | dev->wcache = arg; |
688 | ret = 0; | ||
676 | break; | 689 | break; |
677 | } | 690 | } |
678 | return -ENOTTY; | 691 | unlock_kernel(); |
692 | |||
693 | return ret; | ||
679 | }; | 694 | }; |
680 | 695 | ||
681 | /** | 696 | /** |
@@ -883,7 +898,7 @@ static void i2o_block_request_fn(struct request_queue *q) | |||
883 | if (!req) | 898 | if (!req) |
884 | break; | 899 | break; |
885 | 900 | ||
886 | if (blk_fs_request(req)) { | 901 | if (req->cmd_type == REQ_TYPE_FS) { |
887 | struct i2o_block_delayed_request *dreq; | 902 | struct i2o_block_delayed_request *dreq; |
888 | struct i2o_block_request *ireq = req->special; | 903 | struct i2o_block_request *ireq = req->special; |
889 | unsigned int queue_depth; | 904 | unsigned int queue_depth; |
@@ -930,7 +945,8 @@ static const struct block_device_operations i2o_block_fops = { | |||
930 | .owner = THIS_MODULE, | 945 | .owner = THIS_MODULE, |
931 | .open = i2o_block_open, | 946 | .open = i2o_block_open, |
932 | .release = i2o_block_release, | 947 | .release = i2o_block_release, |
933 | .locked_ioctl = i2o_block_ioctl, | 948 | .ioctl = i2o_block_ioctl, |
949 | .compat_ioctl = i2o_block_ioctl, | ||
934 | .getgeo = i2o_block_getgeo, | 950 | .getgeo = i2o_block_getgeo, |
935 | .media_changed = i2o_block_media_changed | 951 | .media_changed = i2o_block_media_changed |
936 | }; | 952 | }; |
diff --git a/drivers/mmc/card/block.c b/drivers/mmc/card/block.c index cb9fbc83b090..8433cde29c8b 100644 --- a/drivers/mmc/card/block.c +++ b/drivers/mmc/card/block.c | |||
@@ -29,6 +29,7 @@ | |||
29 | #include <linux/kdev_t.h> | 29 | #include <linux/kdev_t.h> |
30 | #include <linux/blkdev.h> | 30 | #include <linux/blkdev.h> |
31 | #include <linux/mutex.h> | 31 | #include <linux/mutex.h> |
32 | #include <linux/smp_lock.h> | ||
32 | #include <linux/scatterlist.h> | 33 | #include <linux/scatterlist.h> |
33 | #include <linux/string_helpers.h> | 34 | #include <linux/string_helpers.h> |
34 | 35 | ||
@@ -107,6 +108,7 @@ static int mmc_blk_open(struct block_device *bdev, fmode_t mode) | |||
107 | struct mmc_blk_data *md = mmc_blk_get(bdev->bd_disk); | 108 | struct mmc_blk_data *md = mmc_blk_get(bdev->bd_disk); |
108 | int ret = -ENXIO; | 109 | int ret = -ENXIO; |
109 | 110 | ||
111 | lock_kernel(); | ||
110 | if (md) { | 112 | if (md) { |
111 | if (md->usage == 2) | 113 | if (md->usage == 2) |
112 | check_disk_change(bdev); | 114 | check_disk_change(bdev); |
@@ -117,6 +119,7 @@ static int mmc_blk_open(struct block_device *bdev, fmode_t mode) | |||
117 | ret = -EROFS; | 119 | ret = -EROFS; |
118 | } | 120 | } |
119 | } | 121 | } |
122 | unlock_kernel(); | ||
120 | 123 | ||
121 | return ret; | 124 | return ret; |
122 | } | 125 | } |
@@ -125,7 +128,9 @@ static int mmc_blk_release(struct gendisk *disk, fmode_t mode) | |||
125 | { | 128 | { |
126 | struct mmc_blk_data *md = disk->private_data; | 129 | struct mmc_blk_data *md = disk->private_data; |
127 | 130 | ||
131 | lock_kernel(); | ||
128 | mmc_blk_put(md); | 132 | mmc_blk_put(md); |
133 | unlock_kernel(); | ||
129 | return 0; | 134 | return 0; |
130 | } | 135 | } |
131 | 136 | ||
diff --git a/drivers/mmc/card/queue.c b/drivers/mmc/card/queue.c index d6ded247d941..c77eb49eda0e 100644 --- a/drivers/mmc/card/queue.c +++ b/drivers/mmc/card/queue.c | |||
@@ -32,7 +32,7 @@ static int mmc_prep_request(struct request_queue *q, struct request *req) | |||
32 | /* | 32 | /* |
33 | * We only like normal block requests. | 33 | * We only like normal block requests. |
34 | */ | 34 | */ |
35 | if (!blk_fs_request(req)) { | 35 | if (req->cmd_type != REQ_TYPE_FS) { |
36 | blk_dump_rq_flags(req, "MMC bad request"); | 36 | blk_dump_rq_flags(req, "MMC bad request"); |
37 | return BLKPREP_KILL; | 37 | return BLKPREP_KILL; |
38 | } | 38 | } |
@@ -128,7 +128,7 @@ int mmc_init_queue(struct mmc_queue *mq, struct mmc_card *card, spinlock_t *lock | |||
128 | mq->req = NULL; | 128 | mq->req = NULL; |
129 | 129 | ||
130 | blk_queue_prep_rq(mq->queue, mmc_prep_request); | 130 | blk_queue_prep_rq(mq->queue, mmc_prep_request); |
131 | blk_queue_ordered(mq->queue, QUEUE_ORDERED_DRAIN, NULL); | 131 | blk_queue_ordered(mq->queue, QUEUE_ORDERED_DRAIN); |
132 | queue_flag_set_unlocked(QUEUE_FLAG_NONROT, mq->queue); | 132 | queue_flag_set_unlocked(QUEUE_FLAG_NONROT, mq->queue); |
133 | 133 | ||
134 | #ifdef CONFIG_MMC_BLOCK_BOUNCE | 134 | #ifdef CONFIG_MMC_BLOCK_BOUNCE |
diff --git a/drivers/mtd/mtd_blkdevs.c b/drivers/mtd/mtd_blkdevs.c index 1d2144d77470..62e68707b07f 100644 --- a/drivers/mtd/mtd_blkdevs.c +++ b/drivers/mtd/mtd_blkdevs.c | |||
@@ -29,6 +29,7 @@ | |||
29 | #include <linux/blkdev.h> | 29 | #include <linux/blkdev.h> |
30 | #include <linux/blkpg.h> | 30 | #include <linux/blkpg.h> |
31 | #include <linux/spinlock.h> | 31 | #include <linux/spinlock.h> |
32 | #include <linux/smp_lock.h> | ||
32 | #include <linux/hdreg.h> | 33 | #include <linux/hdreg.h> |
33 | #include <linux/init.h> | 34 | #include <linux/init.h> |
34 | #include <linux/mutex.h> | 35 | #include <linux/mutex.h> |
@@ -87,14 +88,14 @@ static int do_blktrans_request(struct mtd_blktrans_ops *tr, | |||
87 | 88 | ||
88 | buf = req->buffer; | 89 | buf = req->buffer; |
89 | 90 | ||
90 | if (!blk_fs_request(req)) | 91 | if (req->cmd_type != REQ_TYPE_FS) |
91 | return -EIO; | 92 | return -EIO; |
92 | 93 | ||
93 | if (blk_rq_pos(req) + blk_rq_cur_sectors(req) > | 94 | if (blk_rq_pos(req) + blk_rq_cur_sectors(req) > |
94 | get_capacity(req->rq_disk)) | 95 | get_capacity(req->rq_disk)) |
95 | return -EIO; | 96 | return -EIO; |
96 | 97 | ||
97 | if (blk_discard_rq(req)) | 98 | if (req->cmd_flags & REQ_DISCARD) |
98 | return tr->discard(dev, block, nsect); | 99 | return tr->discard(dev, block, nsect); |
99 | 100 | ||
100 | switch(rq_data_dir(req)) { | 101 | switch(rq_data_dir(req)) { |
@@ -178,8 +179,9 @@ static int blktrans_open(struct block_device *bdev, fmode_t mode) | |||
178 | int ret; | 179 | int ret; |
179 | 180 | ||
180 | if (!dev) | 181 | if (!dev) |
181 | return -ERESTARTSYS; | 182 | return -ERESTARTSYS; /* FIXME: busy loop! -arnd*/ |
182 | 183 | ||
184 | lock_kernel(); | ||
183 | mutex_lock(&dev->lock); | 185 | mutex_lock(&dev->lock); |
184 | 186 | ||
185 | if (!dev->mtd) { | 187 | if (!dev->mtd) { |
@@ -196,6 +198,7 @@ static int blktrans_open(struct block_device *bdev, fmode_t mode) | |||
196 | unlock: | 198 | unlock: |
197 | mutex_unlock(&dev->lock); | 199 | mutex_unlock(&dev->lock); |
198 | blktrans_dev_put(dev); | 200 | blktrans_dev_put(dev); |
201 | unlock_kernel(); | ||
199 | return ret; | 202 | return ret; |
200 | } | 203 | } |
201 | 204 | ||
@@ -207,6 +210,7 @@ static int blktrans_release(struct gendisk *disk, fmode_t mode) | |||
207 | if (!dev) | 210 | if (!dev) |
208 | return ret; | 211 | return ret; |
209 | 212 | ||
213 | lock_kernel(); | ||
210 | mutex_lock(&dev->lock); | 214 | mutex_lock(&dev->lock); |
211 | 215 | ||
212 | /* Release one reference, we sure its not the last one here*/ | 216 | /* Release one reference, we sure its not the last one here*/ |
@@ -219,6 +223,7 @@ static int blktrans_release(struct gendisk *disk, fmode_t mode) | |||
219 | unlock: | 223 | unlock: |
220 | mutex_unlock(&dev->lock); | 224 | mutex_unlock(&dev->lock); |
221 | blktrans_dev_put(dev); | 225 | blktrans_dev_put(dev); |
226 | unlock_kernel(); | ||
222 | return ret; | 227 | return ret; |
223 | } | 228 | } |
224 | 229 | ||
@@ -251,6 +256,7 @@ static int blktrans_ioctl(struct block_device *bdev, fmode_t mode, | |||
251 | if (!dev) | 256 | if (!dev) |
252 | return ret; | 257 | return ret; |
253 | 258 | ||
259 | lock_kernel(); | ||
254 | mutex_lock(&dev->lock); | 260 | mutex_lock(&dev->lock); |
255 | 261 | ||
256 | if (!dev->mtd) | 262 | if (!dev->mtd) |
@@ -265,6 +271,7 @@ static int blktrans_ioctl(struct block_device *bdev, fmode_t mode, | |||
265 | } | 271 | } |
266 | unlock: | 272 | unlock: |
267 | mutex_unlock(&dev->lock); | 273 | mutex_unlock(&dev->lock); |
274 | unlock_kernel(); | ||
268 | blktrans_dev_put(dev); | 275 | blktrans_dev_put(dev); |
269 | return ret; | 276 | return ret; |
270 | } | 277 | } |
@@ -273,7 +280,7 @@ static const struct block_device_operations mtd_blktrans_ops = { | |||
273 | .owner = THIS_MODULE, | 280 | .owner = THIS_MODULE, |
274 | .open = blktrans_open, | 281 | .open = blktrans_open, |
275 | .release = blktrans_release, | 282 | .release = blktrans_release, |
276 | .locked_ioctl = blktrans_ioctl, | 283 | .ioctl = blktrans_ioctl, |
277 | .getgeo = blktrans_getgeo, | 284 | .getgeo = blktrans_getgeo, |
278 | }; | 285 | }; |
279 | 286 | ||
diff --git a/drivers/s390/block/dasd.c b/drivers/s390/block/dasd.c index 33975e922d65..1a84fae155e1 100644 --- a/drivers/s390/block/dasd.c +++ b/drivers/s390/block/dasd.c | |||
@@ -21,6 +21,7 @@ | |||
21 | #include <linux/hdreg.h> | 21 | #include <linux/hdreg.h> |
22 | #include <linux/async.h> | 22 | #include <linux/async.h> |
23 | #include <linux/mutex.h> | 23 | #include <linux/mutex.h> |
24 | #include <linux/smp_lock.h> | ||
24 | 25 | ||
25 | #include <asm/ccwdev.h> | 26 | #include <asm/ccwdev.h> |
26 | #include <asm/ebcdic.h> | 27 | #include <asm/ebcdic.h> |
@@ -2196,7 +2197,7 @@ static void dasd_setup_queue(struct dasd_block *block) | |||
2196 | */ | 2197 | */ |
2197 | blk_queue_max_segment_size(block->request_queue, PAGE_SIZE); | 2198 | blk_queue_max_segment_size(block->request_queue, PAGE_SIZE); |
2198 | blk_queue_segment_boundary(block->request_queue, PAGE_SIZE - 1); | 2199 | blk_queue_segment_boundary(block->request_queue, PAGE_SIZE - 1); |
2199 | blk_queue_ordered(block->request_queue, QUEUE_ORDERED_DRAIN, NULL); | 2200 | blk_queue_ordered(block->request_queue, QUEUE_ORDERED_DRAIN); |
2200 | } | 2201 | } |
2201 | 2202 | ||
2202 | /* | 2203 | /* |
@@ -2235,6 +2236,7 @@ static int dasd_open(struct block_device *bdev, fmode_t mode) | |||
2235 | if (!block) | 2236 | if (!block) |
2236 | return -ENODEV; | 2237 | return -ENODEV; |
2237 | 2238 | ||
2239 | lock_kernel(); | ||
2238 | base = block->base; | 2240 | base = block->base; |
2239 | atomic_inc(&block->open_count); | 2241 | atomic_inc(&block->open_count); |
2240 | if (test_bit(DASD_FLAG_OFFLINE, &base->flags)) { | 2242 | if (test_bit(DASD_FLAG_OFFLINE, &base->flags)) { |
@@ -2269,12 +2271,14 @@ static int dasd_open(struct block_device *bdev, fmode_t mode) | |||
2269 | goto out; | 2271 | goto out; |
2270 | } | 2272 | } |
2271 | 2273 | ||
2274 | unlock_kernel(); | ||
2272 | return 0; | 2275 | return 0; |
2273 | 2276 | ||
2274 | out: | 2277 | out: |
2275 | module_put(base->discipline->owner); | 2278 | module_put(base->discipline->owner); |
2276 | unlock: | 2279 | unlock: |
2277 | atomic_dec(&block->open_count); | 2280 | atomic_dec(&block->open_count); |
2281 | unlock_kernel(); | ||
2278 | return rc; | 2282 | return rc; |
2279 | } | 2283 | } |
2280 | 2284 | ||
@@ -2282,8 +2286,10 @@ static int dasd_release(struct gendisk *disk, fmode_t mode) | |||
2282 | { | 2286 | { |
2283 | struct dasd_block *block = disk->private_data; | 2287 | struct dasd_block *block = disk->private_data; |
2284 | 2288 | ||
2289 | lock_kernel(); | ||
2285 | atomic_dec(&block->open_count); | 2290 | atomic_dec(&block->open_count); |
2286 | module_put(block->base->discipline->owner); | 2291 | module_put(block->base->discipline->owner); |
2292 | unlock_kernel(); | ||
2287 | return 0; | 2293 | return 0; |
2288 | } | 2294 | } |
2289 | 2295 | ||
diff --git a/drivers/s390/block/dcssblk.c b/drivers/s390/block/dcssblk.c index 9b43ae94beba..2bd72aa34c59 100644 --- a/drivers/s390/block/dcssblk.c +++ b/drivers/s390/block/dcssblk.c | |||
@@ -14,6 +14,7 @@ | |||
14 | #include <linux/init.h> | 14 | #include <linux/init.h> |
15 | #include <linux/slab.h> | 15 | #include <linux/slab.h> |
16 | #include <linux/blkdev.h> | 16 | #include <linux/blkdev.h> |
17 | #include <linux/smp_lock.h> | ||
17 | #include <linux/completion.h> | 18 | #include <linux/completion.h> |
18 | #include <linux/interrupt.h> | 19 | #include <linux/interrupt.h> |
19 | #include <linux/platform_device.h> | 20 | #include <linux/platform_device.h> |
@@ -775,6 +776,7 @@ dcssblk_open(struct block_device *bdev, fmode_t mode) | |||
775 | struct dcssblk_dev_info *dev_info; | 776 | struct dcssblk_dev_info *dev_info; |
776 | int rc; | 777 | int rc; |
777 | 778 | ||
779 | lock_kernel(); | ||
778 | dev_info = bdev->bd_disk->private_data; | 780 | dev_info = bdev->bd_disk->private_data; |
779 | if (NULL == dev_info) { | 781 | if (NULL == dev_info) { |
780 | rc = -ENODEV; | 782 | rc = -ENODEV; |
@@ -784,6 +786,7 @@ dcssblk_open(struct block_device *bdev, fmode_t mode) | |||
784 | bdev->bd_block_size = 4096; | 786 | bdev->bd_block_size = 4096; |
785 | rc = 0; | 787 | rc = 0; |
786 | out: | 788 | out: |
789 | unlock_kernel(); | ||
787 | return rc; | 790 | return rc; |
788 | } | 791 | } |
789 | 792 | ||
@@ -794,6 +797,7 @@ dcssblk_release(struct gendisk *disk, fmode_t mode) | |||
794 | struct segment_info *entry; | 797 | struct segment_info *entry; |
795 | int rc; | 798 | int rc; |
796 | 799 | ||
800 | lock_kernel(); | ||
797 | if (!dev_info) { | 801 | if (!dev_info) { |
798 | rc = -ENODEV; | 802 | rc = -ENODEV; |
799 | goto out; | 803 | goto out; |
@@ -811,6 +815,7 @@ dcssblk_release(struct gendisk *disk, fmode_t mode) | |||
811 | up_write(&dcssblk_devices_sem); | 815 | up_write(&dcssblk_devices_sem); |
812 | rc = 0; | 816 | rc = 0; |
813 | out: | 817 | out: |
818 | unlock_kernel(); | ||
814 | return rc; | 819 | return rc; |
815 | } | 820 | } |
816 | 821 | ||
diff --git a/drivers/s390/char/tape_block.c b/drivers/s390/char/tape_block.c index 097da8ce6be6..b7de02525ec9 100644 --- a/drivers/s390/char/tape_block.c +++ b/drivers/s390/char/tape_block.c | |||
@@ -16,6 +16,7 @@ | |||
16 | #include <linux/fs.h> | 16 | #include <linux/fs.h> |
17 | #include <linux/module.h> | 17 | #include <linux/module.h> |
18 | #include <linux/blkdev.h> | 18 | #include <linux/blkdev.h> |
19 | #include <linux/smp_lock.h> | ||
19 | #include <linux/interrupt.h> | 20 | #include <linux/interrupt.h> |
20 | #include <linux/buffer_head.h> | 21 | #include <linux/buffer_head.h> |
21 | #include <linux/kernel.h> | 22 | #include <linux/kernel.h> |
@@ -361,6 +362,7 @@ tapeblock_open(struct block_device *bdev, fmode_t mode) | |||
361 | struct tape_device * device; | 362 | struct tape_device * device; |
362 | int rc; | 363 | int rc; |
363 | 364 | ||
365 | lock_kernel(); | ||
364 | device = tape_get_device(disk->private_data); | 366 | device = tape_get_device(disk->private_data); |
365 | 367 | ||
366 | if (device->required_tapemarks) { | 368 | if (device->required_tapemarks) { |
@@ -384,12 +386,14 @@ tapeblock_open(struct block_device *bdev, fmode_t mode) | |||
384 | * is called. | 386 | * is called. |
385 | */ | 387 | */ |
386 | tape_state_set(device, TS_BLKUSE); | 388 | tape_state_set(device, TS_BLKUSE); |
389 | unlock_kernel(); | ||
387 | return 0; | 390 | return 0; |
388 | 391 | ||
389 | release: | 392 | release: |
390 | tape_release(device); | 393 | tape_release(device); |
391 | put_device: | 394 | put_device: |
392 | tape_put_device(device); | 395 | tape_put_device(device); |
396 | unlock_kernel(); | ||
393 | return rc; | 397 | return rc; |
394 | } | 398 | } |
395 | 399 | ||
@@ -403,10 +407,12 @@ static int | |||
403 | tapeblock_release(struct gendisk *disk, fmode_t mode) | 407 | tapeblock_release(struct gendisk *disk, fmode_t mode) |
404 | { | 408 | { |
405 | struct tape_device *device = disk->private_data; | 409 | struct tape_device *device = disk->private_data; |
406 | 410 | ||
411 | lock_kernel(); | ||
407 | tape_state_set(device, TS_IN_USE); | 412 | tape_state_set(device, TS_IN_USE); |
408 | tape_release(device); | 413 | tape_release(device); |
409 | tape_put_device(device); | 414 | tape_put_device(device); |
415 | unlock_kernel(); | ||
410 | 416 | ||
411 | return 0; | 417 | return 0; |
412 | } | 418 | } |
diff --git a/drivers/scsi/aha1542.c b/drivers/scsi/aha1542.c index 2a8cf137f609..4f785f254c1f 100644 --- a/drivers/scsi/aha1542.c +++ b/drivers/scsi/aha1542.c | |||
@@ -52,22 +52,6 @@ | |||
52 | #define SCSI_BUF_PA(address) isa_virt_to_bus(address) | 52 | #define SCSI_BUF_PA(address) isa_virt_to_bus(address) |
53 | #define SCSI_SG_PA(sgent) (isa_page_to_bus(sg_page((sgent))) + (sgent)->offset) | 53 | #define SCSI_SG_PA(sgent) (isa_page_to_bus(sg_page((sgent))) + (sgent)->offset) |
54 | 54 | ||
55 | static void BAD_SG_DMA(Scsi_Cmnd * SCpnt, | ||
56 | struct scatterlist *sgp, | ||
57 | int nseg, | ||
58 | int badseg) | ||
59 | { | ||
60 | printk(KERN_CRIT "sgpnt[%d:%d] page %p/0x%llx length %u\n", | ||
61 | badseg, nseg, sg_virt(sgp), | ||
62 | (unsigned long long)SCSI_SG_PA(sgp), | ||
63 | sgp->length); | ||
64 | |||
65 | /* | ||
66 | * Not safe to continue. | ||
67 | */ | ||
68 | panic("Buffer at physical address > 16Mb used for aha1542"); | ||
69 | } | ||
70 | |||
71 | #include<linux/stat.h> | 55 | #include<linux/stat.h> |
72 | 56 | ||
73 | #ifdef DEBUG | 57 | #ifdef DEBUG |
@@ -691,8 +675,6 @@ static int aha1542_queuecommand(Scsi_Cmnd * SCpnt, void (*done) (Scsi_Cmnd *)) | |||
691 | } | 675 | } |
692 | scsi_for_each_sg(SCpnt, sg, sg_count, i) { | 676 | scsi_for_each_sg(SCpnt, sg, sg_count, i) { |
693 | any2scsi(cptr[i].dataptr, SCSI_SG_PA(sg)); | 677 | any2scsi(cptr[i].dataptr, SCSI_SG_PA(sg)); |
694 | if (SCSI_SG_PA(sg) + sg->length - 1 > ISA_DMA_THRESHOLD) | ||
695 | BAD_SG_DMA(SCpnt, scsi_sglist(SCpnt), sg_count, i); | ||
696 | any2scsi(cptr[i].datalen, sg->length); | 678 | any2scsi(cptr[i].datalen, sg->length); |
697 | }; | 679 | }; |
698 | any2scsi(ccb[mbo].datalen, sg_count * sizeof(struct chain)); | 680 | any2scsi(ccb[mbo].datalen, sg_count * sizeof(struct chain)); |
@@ -1133,16 +1115,9 @@ static int __init aha1542_detect(struct scsi_host_template * tpnt) | |||
1133 | release_region(bases[indx], 4); | 1115 | release_region(bases[indx], 4); |
1134 | continue; | 1116 | continue; |
1135 | } | 1117 | } |
1136 | /* For now we do this - until kmalloc is more intelligent | ||
1137 | we are resigned to stupid hacks like this */ | ||
1138 | if (SCSI_BUF_PA(shpnt) >= ISA_DMA_THRESHOLD) { | ||
1139 | printk(KERN_ERR "Invalid address for shpnt with 1542.\n"); | ||
1140 | goto unregister; | ||
1141 | } | ||
1142 | if (!aha1542_test_port(bases[indx], shpnt)) | 1118 | if (!aha1542_test_port(bases[indx], shpnt)) |
1143 | goto unregister; | 1119 | goto unregister; |
1144 | 1120 | ||
1145 | |||
1146 | base_io = bases[indx]; | 1121 | base_io = bases[indx]; |
1147 | 1122 | ||
1148 | /* Set the Bus on/off-times as not to ruin floppy performance */ | 1123 | /* Set the Bus on/off-times as not to ruin floppy performance */ |
diff --git a/drivers/scsi/osd/osd_initiator.c b/drivers/scsi/osd/osd_initiator.c index ee4b6914667f..fda4de3440c4 100644 --- a/drivers/scsi/osd/osd_initiator.c +++ b/drivers/scsi/osd/osd_initiator.c | |||
@@ -716,7 +716,7 @@ static int _osd_req_list_objects(struct osd_request *or, | |||
716 | return PTR_ERR(bio); | 716 | return PTR_ERR(bio); |
717 | } | 717 | } |
718 | 718 | ||
719 | bio->bi_rw &= ~(1 << BIO_RW); | 719 | bio->bi_rw &= ~REQ_WRITE; |
720 | or->in.bio = bio; | 720 | or->in.bio = bio; |
721 | or->in.total_bytes = bio->bi_size; | 721 | or->in.total_bytes = bio->bi_size; |
722 | return 0; | 722 | return 0; |
@@ -814,7 +814,7 @@ void osd_req_write(struct osd_request *or, | |||
814 | { | 814 | { |
815 | _osd_req_encode_common(or, OSD_ACT_WRITE, obj, offset, len); | 815 | _osd_req_encode_common(or, OSD_ACT_WRITE, obj, offset, len); |
816 | WARN_ON(or->out.bio || or->out.total_bytes); | 816 | WARN_ON(or->out.bio || or->out.total_bytes); |
817 | WARN_ON(0 == bio_rw_flagged(bio, BIO_RW)); | 817 | WARN_ON(0 == (bio->bi_rw & REQ_WRITE)); |
818 | or->out.bio = bio; | 818 | or->out.bio = bio; |
819 | or->out.total_bytes = len; | 819 | or->out.total_bytes = len; |
820 | } | 820 | } |
@@ -829,7 +829,7 @@ int osd_req_write_kern(struct osd_request *or, | |||
829 | if (IS_ERR(bio)) | 829 | if (IS_ERR(bio)) |
830 | return PTR_ERR(bio); | 830 | return PTR_ERR(bio); |
831 | 831 | ||
832 | bio->bi_rw |= (1 << BIO_RW); /* FIXME: bio_set_dir() */ | 832 | bio->bi_rw |= REQ_WRITE; /* FIXME: bio_set_dir() */ |
833 | osd_req_write(or, obj, offset, bio, len); | 833 | osd_req_write(or, obj, offset, bio, len); |
834 | return 0; | 834 | return 0; |
835 | } | 835 | } |
@@ -865,7 +865,7 @@ void osd_req_read(struct osd_request *or, | |||
865 | { | 865 | { |
866 | _osd_req_encode_common(or, OSD_ACT_READ, obj, offset, len); | 866 | _osd_req_encode_common(or, OSD_ACT_READ, obj, offset, len); |
867 | WARN_ON(or->in.bio || or->in.total_bytes); | 867 | WARN_ON(or->in.bio || or->in.total_bytes); |
868 | WARN_ON(1 == bio_rw_flagged(bio, BIO_RW)); | 868 | WARN_ON(1 == (bio->bi_rw & REQ_WRITE)); |
869 | or->in.bio = bio; | 869 | or->in.bio = bio; |
870 | or->in.total_bytes = len; | 870 | or->in.total_bytes = len; |
871 | } | 871 | } |
diff --git a/drivers/scsi/scsi_error.c b/drivers/scsi/scsi_error.c index 2bf98469dc4c..bbbc186dbc1a 100644 --- a/drivers/scsi/scsi_error.c +++ b/drivers/scsi/scsi_error.c | |||
@@ -320,7 +320,7 @@ static int scsi_check_sense(struct scsi_cmnd *scmd) | |||
320 | "changed. The Linux SCSI layer does not " | 320 | "changed. The Linux SCSI layer does not " |
321 | "automatically adjust these parameters.\n"); | 321 | "automatically adjust these parameters.\n"); |
322 | 322 | ||
323 | if (blk_barrier_rq(scmd->request)) | 323 | if (scmd->request->cmd_flags & REQ_HARDBARRIER) |
324 | /* | 324 | /* |
325 | * barrier requests should always retry on UA | 325 | * barrier requests should always retry on UA |
326 | * otherwise block will get a spurious error | 326 | * otherwise block will get a spurious error |
@@ -1331,16 +1331,16 @@ int scsi_noretry_cmd(struct scsi_cmnd *scmd) | |||
1331 | case DID_OK: | 1331 | case DID_OK: |
1332 | break; | 1332 | break; |
1333 | case DID_BUS_BUSY: | 1333 | case DID_BUS_BUSY: |
1334 | return blk_failfast_transport(scmd->request); | 1334 | return (scmd->request->cmd_flags & REQ_FAILFAST_TRANSPORT); |
1335 | case DID_PARITY: | 1335 | case DID_PARITY: |
1336 | return blk_failfast_dev(scmd->request); | 1336 | return (scmd->request->cmd_flags & REQ_FAILFAST_DEV); |
1337 | case DID_ERROR: | 1337 | case DID_ERROR: |
1338 | if (msg_byte(scmd->result) == COMMAND_COMPLETE && | 1338 | if (msg_byte(scmd->result) == COMMAND_COMPLETE && |
1339 | status_byte(scmd->result) == RESERVATION_CONFLICT) | 1339 | status_byte(scmd->result) == RESERVATION_CONFLICT) |
1340 | return 0; | 1340 | return 0; |
1341 | /* fall through */ | 1341 | /* fall through */ |
1342 | case DID_SOFT_ERROR: | 1342 | case DID_SOFT_ERROR: |
1343 | return blk_failfast_driver(scmd->request); | 1343 | return (scmd->request->cmd_flags & REQ_FAILFAST_DRIVER); |
1344 | } | 1344 | } |
1345 | 1345 | ||
1346 | switch (status_byte(scmd->result)) { | 1346 | switch (status_byte(scmd->result)) { |
@@ -1349,7 +1349,9 @@ int scsi_noretry_cmd(struct scsi_cmnd *scmd) | |||
1349 | * assume caller has checked sense and determinted | 1349 | * assume caller has checked sense and determinted |
1350 | * the check condition was retryable. | 1350 | * the check condition was retryable. |
1351 | */ | 1351 | */ |
1352 | return blk_failfast_dev(scmd->request); | 1352 | if (scmd->request->cmd_flags & REQ_FAILFAST_DEV || |
1353 | scmd->request->cmd_type == REQ_TYPE_BLOCK_PC) | ||
1354 | return 1; | ||
1353 | } | 1355 | } |
1354 | 1356 | ||
1355 | return 0; | 1357 | return 0; |
diff --git a/drivers/scsi/scsi_lib.c b/drivers/scsi/scsi_lib.c index 1646fe7cbd4b..b8de389636f8 100644 --- a/drivers/scsi/scsi_lib.c +++ b/drivers/scsi/scsi_lib.c | |||
@@ -85,7 +85,7 @@ static void scsi_unprep_request(struct request *req) | |||
85 | { | 85 | { |
86 | struct scsi_cmnd *cmd = req->special; | 86 | struct scsi_cmnd *cmd = req->special; |
87 | 87 | ||
88 | req->cmd_flags &= ~REQ_DONTPREP; | 88 | blk_unprep_request(req); |
89 | req->special = NULL; | 89 | req->special = NULL; |
90 | 90 | ||
91 | scsi_put_command(cmd); | 91 | scsi_put_command(cmd); |
@@ -722,7 +722,7 @@ void scsi_io_completion(struct scsi_cmnd *cmd, unsigned int good_bytes) | |||
722 | sense_deferred = scsi_sense_is_deferred(&sshdr); | 722 | sense_deferred = scsi_sense_is_deferred(&sshdr); |
723 | } | 723 | } |
724 | 724 | ||
725 | if (blk_pc_request(req)) { /* SG_IO ioctl from block level */ | 725 | if (req->cmd_type == REQ_TYPE_BLOCK_PC) { /* SG_IO ioctl from block level */ |
726 | req->errors = result; | 726 | req->errors = result; |
727 | if (result) { | 727 | if (result) { |
728 | if (sense_valid && req->sense) { | 728 | if (sense_valid && req->sense) { |
@@ -757,7 +757,8 @@ void scsi_io_completion(struct scsi_cmnd *cmd, unsigned int good_bytes) | |||
757 | } | 757 | } |
758 | } | 758 | } |
759 | 759 | ||
760 | BUG_ON(blk_bidi_rq(req)); /* bidi not support for !blk_pc_request yet */ | 760 | /* no bidi support for !REQ_TYPE_BLOCK_PC yet */ |
761 | BUG_ON(blk_bidi_rq(req)); | ||
761 | 762 | ||
762 | /* | 763 | /* |
763 | * Next deal with any sectors which we were able to correctly | 764 | * Next deal with any sectors which we were able to correctly |
@@ -1010,11 +1011,8 @@ int scsi_init_io(struct scsi_cmnd *cmd, gfp_t gfp_mask) | |||
1010 | 1011 | ||
1011 | err_exit: | 1012 | err_exit: |
1012 | scsi_release_buffers(cmd); | 1013 | scsi_release_buffers(cmd); |
1013 | if (error == BLKPREP_KILL) | 1014 | scsi_put_command(cmd); |
1014 | scsi_put_command(cmd); | 1015 | cmd->request->special = NULL; |
1015 | else /* BLKPREP_DEFER */ | ||
1016 | scsi_unprep_request(cmd->request); | ||
1017 | |||
1018 | return error; | 1016 | return error; |
1019 | } | 1017 | } |
1020 | EXPORT_SYMBOL(scsi_init_io); | 1018 | EXPORT_SYMBOL(scsi_init_io); |
diff --git a/drivers/scsi/sd.c b/drivers/scsi/sd.c index cc8a1d1d915a..8e2e893db9e7 100644 --- a/drivers/scsi/sd.c +++ b/drivers/scsi/sd.c | |||
@@ -46,6 +46,7 @@ | |||
46 | #include <linux/blkdev.h> | 46 | #include <linux/blkdev.h> |
47 | #include <linux/blkpg.h> | 47 | #include <linux/blkpg.h> |
48 | #include <linux/delay.h> | 48 | #include <linux/delay.h> |
49 | #include <linux/smp_lock.h> | ||
49 | #include <linux/mutex.h> | 50 | #include <linux/mutex.h> |
50 | #include <linux/string_helpers.h> | 51 | #include <linux/string_helpers.h> |
51 | #include <linux/async.h> | 52 | #include <linux/async.h> |
@@ -411,54 +412,85 @@ static void sd_prot_op(struct scsi_cmnd *scmd, unsigned int dif) | |||
411 | } | 412 | } |
412 | 413 | ||
413 | /** | 414 | /** |
414 | * sd_prepare_discard - unmap blocks on thinly provisioned device | 415 | * scsi_setup_discard_cmnd - unmap blocks on thinly provisioned device |
416 | * @sdp: scsi device to operate one | ||
415 | * @rq: Request to prepare | 417 | * @rq: Request to prepare |
416 | * | 418 | * |
417 | * Will issue either UNMAP or WRITE SAME(16) depending on preference | 419 | * Will issue either UNMAP or WRITE SAME(16) depending on preference |
418 | * indicated by target device. | 420 | * indicated by target device. |
419 | **/ | 421 | **/ |
420 | static int sd_prepare_discard(struct request *rq) | 422 | static int scsi_setup_discard_cmnd(struct scsi_device *sdp, struct request *rq) |
421 | { | 423 | { |
422 | struct scsi_disk *sdkp = scsi_disk(rq->rq_disk); | 424 | struct scsi_disk *sdkp = scsi_disk(rq->rq_disk); |
423 | struct bio *bio = rq->bio; | 425 | struct bio *bio = rq->bio; |
424 | sector_t sector = bio->bi_sector; | 426 | sector_t sector = bio->bi_sector; |
425 | unsigned int num = bio_sectors(bio); | 427 | unsigned int nr_sectors = bio_sectors(bio); |
428 | unsigned int len; | ||
429 | int ret; | ||
430 | struct page *page; | ||
426 | 431 | ||
427 | if (sdkp->device->sector_size == 4096) { | 432 | if (sdkp->device->sector_size == 4096) { |
428 | sector >>= 3; | 433 | sector >>= 3; |
429 | num >>= 3; | 434 | nr_sectors >>= 3; |
430 | } | 435 | } |
431 | 436 | ||
432 | rq->cmd_type = REQ_TYPE_BLOCK_PC; | ||
433 | rq->timeout = SD_TIMEOUT; | 437 | rq->timeout = SD_TIMEOUT; |
434 | 438 | ||
435 | memset(rq->cmd, 0, rq->cmd_len); | 439 | memset(rq->cmd, 0, rq->cmd_len); |
436 | 440 | ||
441 | page = alloc_page(GFP_ATOMIC | __GFP_ZERO); | ||
442 | if (!page) | ||
443 | return BLKPREP_DEFER; | ||
444 | |||
437 | if (sdkp->unmap) { | 445 | if (sdkp->unmap) { |
438 | char *buf = kmap_atomic(bio_page(bio), KM_USER0); | 446 | char *buf = page_address(page); |
439 | 447 | ||
448 | rq->cmd_len = 10; | ||
440 | rq->cmd[0] = UNMAP; | 449 | rq->cmd[0] = UNMAP; |
441 | rq->cmd[8] = 24; | 450 | rq->cmd[8] = 24; |
442 | rq->cmd_len = 10; | ||
443 | |||
444 | /* Ensure that data length matches payload */ | ||
445 | rq->__data_len = bio->bi_size = bio->bi_io_vec->bv_len = 24; | ||
446 | 451 | ||
447 | put_unaligned_be16(6 + 16, &buf[0]); | 452 | put_unaligned_be16(6 + 16, &buf[0]); |
448 | put_unaligned_be16(16, &buf[2]); | 453 | put_unaligned_be16(16, &buf[2]); |
449 | put_unaligned_be64(sector, &buf[8]); | 454 | put_unaligned_be64(sector, &buf[8]); |
450 | put_unaligned_be32(num, &buf[16]); | 455 | put_unaligned_be32(nr_sectors, &buf[16]); |
451 | 456 | ||
452 | kunmap_atomic(buf, KM_USER0); | 457 | len = 24; |
453 | } else { | 458 | } else { |
459 | rq->cmd_len = 16; | ||
454 | rq->cmd[0] = WRITE_SAME_16; | 460 | rq->cmd[0] = WRITE_SAME_16; |
455 | rq->cmd[1] = 0x8; /* UNMAP */ | 461 | rq->cmd[1] = 0x8; /* UNMAP */ |
456 | put_unaligned_be64(sector, &rq->cmd[2]); | 462 | put_unaligned_be64(sector, &rq->cmd[2]); |
457 | put_unaligned_be32(num, &rq->cmd[10]); | 463 | put_unaligned_be32(nr_sectors, &rq->cmd[10]); |
458 | rq->cmd_len = 16; | 464 | |
465 | len = sdkp->device->sector_size; | ||
459 | } | 466 | } |
460 | 467 | ||
461 | return BLKPREP_OK; | 468 | blk_add_request_payload(rq, page, len); |
469 | ret = scsi_setup_blk_pc_cmnd(sdp, rq); | ||
470 | rq->buffer = page_address(page); | ||
471 | if (ret != BLKPREP_OK) { | ||
472 | __free_page(page); | ||
473 | rq->buffer = NULL; | ||
474 | } | ||
475 | return ret; | ||
476 | } | ||
477 | |||
478 | static int scsi_setup_flush_cmnd(struct scsi_device *sdp, struct request *rq) | ||
479 | { | ||
480 | rq->timeout = SD_TIMEOUT; | ||
481 | rq->retries = SD_MAX_RETRIES; | ||
482 | rq->cmd[0] = SYNCHRONIZE_CACHE; | ||
483 | rq->cmd_len = 10; | ||
484 | |||
485 | return scsi_setup_blk_pc_cmnd(sdp, rq); | ||
486 | } | ||
487 | |||
488 | static void sd_unprep_fn(struct request_queue *q, struct request *rq) | ||
489 | { | ||
490 | if (rq->cmd_flags & REQ_DISCARD) { | ||
491 | free_page((unsigned long)rq->buffer); | ||
492 | rq->buffer = NULL; | ||
493 | } | ||
462 | } | 494 | } |
463 | 495 | ||
464 | /** | 496 | /** |
@@ -485,10 +517,13 @@ static int sd_prep_fn(struct request_queue *q, struct request *rq) | |||
485 | * Discard request come in as REQ_TYPE_FS but we turn them into | 517 | * Discard request come in as REQ_TYPE_FS but we turn them into |
486 | * block PC requests to make life easier. | 518 | * block PC requests to make life easier. |
487 | */ | 519 | */ |
488 | if (blk_discard_rq(rq)) | 520 | if (rq->cmd_flags & REQ_DISCARD) { |
489 | ret = sd_prepare_discard(rq); | 521 | ret = scsi_setup_discard_cmnd(sdp, rq); |
490 | 522 | goto out; | |
491 | if (rq->cmd_type == REQ_TYPE_BLOCK_PC) { | 523 | } else if (rq->cmd_flags & REQ_FLUSH) { |
524 | ret = scsi_setup_flush_cmnd(sdp, rq); | ||
525 | goto out; | ||
526 | } else if (rq->cmd_type == REQ_TYPE_BLOCK_PC) { | ||
492 | ret = scsi_setup_blk_pc_cmnd(sdp, rq); | 527 | ret = scsi_setup_blk_pc_cmnd(sdp, rq); |
493 | goto out; | 528 | goto out; |
494 | } else if (rq->cmd_type != REQ_TYPE_FS) { | 529 | } else if (rq->cmd_type != REQ_TYPE_FS) { |
@@ -636,7 +671,7 @@ static int sd_prep_fn(struct request_queue *q, struct request *rq) | |||
636 | SCpnt->cmnd[0] = VARIABLE_LENGTH_CMD; | 671 | SCpnt->cmnd[0] = VARIABLE_LENGTH_CMD; |
637 | SCpnt->cmnd[7] = 0x18; | 672 | SCpnt->cmnd[7] = 0x18; |
638 | SCpnt->cmnd[9] = (rq_data_dir(rq) == READ) ? READ_32 : WRITE_32; | 673 | SCpnt->cmnd[9] = (rq_data_dir(rq) == READ) ? READ_32 : WRITE_32; |
639 | SCpnt->cmnd[10] = protect | (blk_fua_rq(rq) ? 0x8 : 0); | 674 | SCpnt->cmnd[10] = protect | ((rq->cmd_flags & REQ_FUA) ? 0x8 : 0); |
640 | 675 | ||
641 | /* LBA */ | 676 | /* LBA */ |
642 | SCpnt->cmnd[12] = sizeof(block) > 4 ? (unsigned char) (block >> 56) & 0xff : 0; | 677 | SCpnt->cmnd[12] = sizeof(block) > 4 ? (unsigned char) (block >> 56) & 0xff : 0; |
@@ -661,7 +696,7 @@ static int sd_prep_fn(struct request_queue *q, struct request *rq) | |||
661 | SCpnt->cmnd[31] = (unsigned char) this_count & 0xff; | 696 | SCpnt->cmnd[31] = (unsigned char) this_count & 0xff; |
662 | } else if (block > 0xffffffff) { | 697 | } else if (block > 0xffffffff) { |
663 | SCpnt->cmnd[0] += READ_16 - READ_6; | 698 | SCpnt->cmnd[0] += READ_16 - READ_6; |
664 | SCpnt->cmnd[1] = protect | (blk_fua_rq(rq) ? 0x8 : 0); | 699 | SCpnt->cmnd[1] = protect | ((rq->cmd_flags & REQ_FUA) ? 0x8 : 0); |
665 | SCpnt->cmnd[2] = sizeof(block) > 4 ? (unsigned char) (block >> 56) & 0xff : 0; | 700 | SCpnt->cmnd[2] = sizeof(block) > 4 ? (unsigned char) (block >> 56) & 0xff : 0; |
666 | SCpnt->cmnd[3] = sizeof(block) > 4 ? (unsigned char) (block >> 48) & 0xff : 0; | 701 | SCpnt->cmnd[3] = sizeof(block) > 4 ? (unsigned char) (block >> 48) & 0xff : 0; |
667 | SCpnt->cmnd[4] = sizeof(block) > 4 ? (unsigned char) (block >> 40) & 0xff : 0; | 702 | SCpnt->cmnd[4] = sizeof(block) > 4 ? (unsigned char) (block >> 40) & 0xff : 0; |
@@ -682,7 +717,7 @@ static int sd_prep_fn(struct request_queue *q, struct request *rq) | |||
682 | this_count = 0xffff; | 717 | this_count = 0xffff; |
683 | 718 | ||
684 | SCpnt->cmnd[0] += READ_10 - READ_6; | 719 | SCpnt->cmnd[0] += READ_10 - READ_6; |
685 | SCpnt->cmnd[1] = protect | (blk_fua_rq(rq) ? 0x8 : 0); | 720 | SCpnt->cmnd[1] = protect | ((rq->cmd_flags & REQ_FUA) ? 0x8 : 0); |
686 | SCpnt->cmnd[2] = (unsigned char) (block >> 24) & 0xff; | 721 | SCpnt->cmnd[2] = (unsigned char) (block >> 24) & 0xff; |
687 | SCpnt->cmnd[3] = (unsigned char) (block >> 16) & 0xff; | 722 | SCpnt->cmnd[3] = (unsigned char) (block >> 16) & 0xff; |
688 | SCpnt->cmnd[4] = (unsigned char) (block >> 8) & 0xff; | 723 | SCpnt->cmnd[4] = (unsigned char) (block >> 8) & 0xff; |
@@ -691,7 +726,7 @@ static int sd_prep_fn(struct request_queue *q, struct request *rq) | |||
691 | SCpnt->cmnd[7] = (unsigned char) (this_count >> 8) & 0xff; | 726 | SCpnt->cmnd[7] = (unsigned char) (this_count >> 8) & 0xff; |
692 | SCpnt->cmnd[8] = (unsigned char) this_count & 0xff; | 727 | SCpnt->cmnd[8] = (unsigned char) this_count & 0xff; |
693 | } else { | 728 | } else { |
694 | if (unlikely(blk_fua_rq(rq))) { | 729 | if (unlikely(rq->cmd_flags & REQ_FUA)) { |
695 | /* | 730 | /* |
696 | * This happens only if this drive failed | 731 | * This happens only if this drive failed |
697 | * 10byte rw command with ILLEGAL_REQUEST | 732 | * 10byte rw command with ILLEGAL_REQUEST |
@@ -745,6 +780,8 @@ static int sd_prep_fn(struct request_queue *q, struct request *rq) | |||
745 | * or from within the kernel (e.g. as a result of a mount(1) ). | 780 | * or from within the kernel (e.g. as a result of a mount(1) ). |
746 | * In the latter case @inode and @filp carry an abridged amount | 781 | * In the latter case @inode and @filp carry an abridged amount |
747 | * of information as noted above. | 782 | * of information as noted above. |
783 | * | ||
784 | * Locking: called with bdev->bd_mutex held. | ||
748 | **/ | 785 | **/ |
749 | static int sd_open(struct block_device *bdev, fmode_t mode) | 786 | static int sd_open(struct block_device *bdev, fmode_t mode) |
750 | { | 787 | { |
@@ -799,7 +836,7 @@ static int sd_open(struct block_device *bdev, fmode_t mode) | |||
799 | if (!scsi_device_online(sdev)) | 836 | if (!scsi_device_online(sdev)) |
800 | goto error_out; | 837 | goto error_out; |
801 | 838 | ||
802 | if (!sdkp->openers++ && sdev->removable) { | 839 | if ((atomic_inc_return(&sdkp->openers) == 1) && sdev->removable) { |
803 | if (scsi_block_when_processing_errors(sdev)) | 840 | if (scsi_block_when_processing_errors(sdev)) |
804 | scsi_set_medium_removal(sdev, SCSI_REMOVAL_PREVENT); | 841 | scsi_set_medium_removal(sdev, SCSI_REMOVAL_PREVENT); |
805 | } | 842 | } |
@@ -823,6 +860,8 @@ error_autopm: | |||
823 | * | 860 | * |
824 | * Note: may block (uninterruptible) if error recovery is underway | 861 | * Note: may block (uninterruptible) if error recovery is underway |
825 | * on this disk. | 862 | * on this disk. |
863 | * | ||
864 | * Locking: called with bdev->bd_mutex held. | ||
826 | **/ | 865 | **/ |
827 | static int sd_release(struct gendisk *disk, fmode_t mode) | 866 | static int sd_release(struct gendisk *disk, fmode_t mode) |
828 | { | 867 | { |
@@ -831,7 +870,7 @@ static int sd_release(struct gendisk *disk, fmode_t mode) | |||
831 | 870 | ||
832 | SCSI_LOG_HLQUEUE(3, sd_printk(KERN_INFO, sdkp, "sd_release\n")); | 871 | SCSI_LOG_HLQUEUE(3, sd_printk(KERN_INFO, sdkp, "sd_release\n")); |
833 | 872 | ||
834 | if (!--sdkp->openers && sdev->removable) { | 873 | if (atomic_dec_return(&sdkp->openers) && sdev->removable) { |
835 | if (scsi_block_when_processing_errors(sdev)) | 874 | if (scsi_block_when_processing_errors(sdev)) |
836 | scsi_set_medium_removal(sdev, SCSI_REMOVAL_ALLOW); | 875 | scsi_set_medium_removal(sdev, SCSI_REMOVAL_ALLOW); |
837 | } | 876 | } |
@@ -904,7 +943,7 @@ static int sd_ioctl(struct block_device *bdev, fmode_t mode, | |||
904 | error = scsi_nonblockable_ioctl(sdp, cmd, p, | 943 | error = scsi_nonblockable_ioctl(sdp, cmd, p, |
905 | (mode & FMODE_NDELAY) != 0); | 944 | (mode & FMODE_NDELAY) != 0); |
906 | if (!scsi_block_when_processing_errors(sdp) || !error) | 945 | if (!scsi_block_when_processing_errors(sdp) || !error) |
907 | return error; | 946 | goto out; |
908 | 947 | ||
909 | /* | 948 | /* |
910 | * Send SCSI addressing ioctls directly to mid level, send other | 949 | * Send SCSI addressing ioctls directly to mid level, send other |
@@ -914,13 +953,17 @@ static int sd_ioctl(struct block_device *bdev, fmode_t mode, | |||
914 | switch (cmd) { | 953 | switch (cmd) { |
915 | case SCSI_IOCTL_GET_IDLUN: | 954 | case SCSI_IOCTL_GET_IDLUN: |
916 | case SCSI_IOCTL_GET_BUS_NUMBER: | 955 | case SCSI_IOCTL_GET_BUS_NUMBER: |
917 | return scsi_ioctl(sdp, cmd, p); | 956 | error = scsi_ioctl(sdp, cmd, p); |
957 | break; | ||
918 | default: | 958 | default: |
919 | error = scsi_cmd_ioctl(disk->queue, disk, mode, cmd, p); | 959 | error = scsi_cmd_ioctl(disk->queue, disk, mode, cmd, p); |
920 | if (error != -ENOTTY) | 960 | if (error != -ENOTTY) |
921 | return error; | 961 | break; |
962 | error = scsi_ioctl(sdp, cmd, p); | ||
963 | break; | ||
922 | } | 964 | } |
923 | return scsi_ioctl(sdp, cmd, p); | 965 | out: |
966 | return error; | ||
924 | } | 967 | } |
925 | 968 | ||
926 | static void set_media_not_present(struct scsi_disk *sdkp) | 969 | static void set_media_not_present(struct scsi_disk *sdkp) |
@@ -1045,15 +1088,6 @@ static int sd_sync_cache(struct scsi_disk *sdkp) | |||
1045 | return 0; | 1088 | return 0; |
1046 | } | 1089 | } |
1047 | 1090 | ||
1048 | static void sd_prepare_flush(struct request_queue *q, struct request *rq) | ||
1049 | { | ||
1050 | rq->cmd_type = REQ_TYPE_BLOCK_PC; | ||
1051 | rq->timeout = SD_TIMEOUT; | ||
1052 | rq->retries = SD_MAX_RETRIES; | ||
1053 | rq->cmd[0] = SYNCHRONIZE_CACHE; | ||
1054 | rq->cmd_len = 10; | ||
1055 | } | ||
1056 | |||
1057 | static void sd_rescan(struct device *dev) | 1091 | static void sd_rescan(struct device *dev) |
1058 | { | 1092 | { |
1059 | struct scsi_disk *sdkp = scsi_disk_get_from_dev(dev); | 1093 | struct scsi_disk *sdkp = scsi_disk_get_from_dev(dev); |
@@ -1103,7 +1137,7 @@ static const struct block_device_operations sd_fops = { | |||
1103 | .owner = THIS_MODULE, | 1137 | .owner = THIS_MODULE, |
1104 | .open = sd_open, | 1138 | .open = sd_open, |
1105 | .release = sd_release, | 1139 | .release = sd_release, |
1106 | .locked_ioctl = sd_ioctl, | 1140 | .ioctl = sd_ioctl, |
1107 | .getgeo = sd_getgeo, | 1141 | .getgeo = sd_getgeo, |
1108 | #ifdef CONFIG_COMPAT | 1142 | #ifdef CONFIG_COMPAT |
1109 | .compat_ioctl = sd_compat_ioctl, | 1143 | .compat_ioctl = sd_compat_ioctl, |
@@ -1120,7 +1154,7 @@ static unsigned int sd_completed_bytes(struct scsi_cmnd *scmd) | |||
1120 | u64 bad_lba; | 1154 | u64 bad_lba; |
1121 | int info_valid; | 1155 | int info_valid; |
1122 | 1156 | ||
1123 | if (!blk_fs_request(scmd->request)) | 1157 | if (scmd->request->cmd_type != REQ_TYPE_FS) |
1124 | return 0; | 1158 | return 0; |
1125 | 1159 | ||
1126 | info_valid = scsi_get_sense_info_fld(scmd->sense_buffer, | 1160 | info_valid = scsi_get_sense_info_fld(scmd->sense_buffer, |
@@ -1171,6 +1205,12 @@ static int sd_done(struct scsi_cmnd *SCpnt) | |||
1171 | int sense_valid = 0; | 1205 | int sense_valid = 0; |
1172 | int sense_deferred = 0; | 1206 | int sense_deferred = 0; |
1173 | 1207 | ||
1208 | if (SCpnt->request->cmd_flags & REQ_DISCARD) { | ||
1209 | if (!result) | ||
1210 | scsi_set_resid(SCpnt, 0); | ||
1211 | return good_bytes; | ||
1212 | } | ||
1213 | |||
1174 | if (result) { | 1214 | if (result) { |
1175 | sense_valid = scsi_command_normalize_sense(SCpnt, &sshdr); | 1215 | sense_valid = scsi_command_normalize_sense(SCpnt, &sshdr); |
1176 | if (sense_valid) | 1216 | if (sense_valid) |
@@ -2121,7 +2161,7 @@ static int sd_revalidate_disk(struct gendisk *disk) | |||
2121 | else | 2161 | else |
2122 | ordered = QUEUE_ORDERED_DRAIN; | 2162 | ordered = QUEUE_ORDERED_DRAIN; |
2123 | 2163 | ||
2124 | blk_queue_ordered(sdkp->disk->queue, ordered, sd_prepare_flush); | 2164 | blk_queue_ordered(sdkp->disk->queue, ordered); |
2125 | 2165 | ||
2126 | set_capacity(disk, sdkp->capacity); | 2166 | set_capacity(disk, sdkp->capacity); |
2127 | kfree(buffer); | 2167 | kfree(buffer); |
@@ -2234,6 +2274,7 @@ static void sd_probe_async(void *data, async_cookie_t cookie) | |||
2234 | sd_revalidate_disk(gd); | 2274 | sd_revalidate_disk(gd); |
2235 | 2275 | ||
2236 | blk_queue_prep_rq(sdp->request_queue, sd_prep_fn); | 2276 | blk_queue_prep_rq(sdp->request_queue, sd_prep_fn); |
2277 | blk_queue_unprep_rq(sdp->request_queue, sd_unprep_fn); | ||
2237 | 2278 | ||
2238 | gd->driverfs_dev = &sdp->sdev_gendev; | 2279 | gd->driverfs_dev = &sdp->sdev_gendev; |
2239 | gd->flags = GENHD_FL_EXT_DEVT; | 2280 | gd->flags = GENHD_FL_EXT_DEVT; |
@@ -2313,7 +2354,7 @@ static int sd_probe(struct device *dev) | |||
2313 | sdkp->driver = &sd_template; | 2354 | sdkp->driver = &sd_template; |
2314 | sdkp->disk = gd; | 2355 | sdkp->disk = gd; |
2315 | sdkp->index = index; | 2356 | sdkp->index = index; |
2316 | sdkp->openers = 0; | 2357 | atomic_set(&sdkp->openers, 0); |
2317 | sdkp->previous_state = 1; | 2358 | sdkp->previous_state = 1; |
2318 | 2359 | ||
2319 | if (!sdp->request_queue->rq_timeout) { | 2360 | if (!sdp->request_queue->rq_timeout) { |
@@ -2372,6 +2413,7 @@ static int sd_remove(struct device *dev) | |||
2372 | 2413 | ||
2373 | async_synchronize_full(); | 2414 | async_synchronize_full(); |
2374 | blk_queue_prep_rq(sdkp->device->request_queue, scsi_prep_fn); | 2415 | blk_queue_prep_rq(sdkp->device->request_queue, scsi_prep_fn); |
2416 | blk_queue_unprep_rq(sdkp->device->request_queue, NULL); | ||
2375 | device_del(&sdkp->dev); | 2417 | device_del(&sdkp->dev); |
2376 | del_gendisk(sdkp->disk); | 2418 | del_gendisk(sdkp->disk); |
2377 | sd_shutdown(dev); | 2419 | sd_shutdown(dev); |
diff --git a/drivers/scsi/sd.h b/drivers/scsi/sd.h index 43d3caf268ef..f81a9309e6de 100644 --- a/drivers/scsi/sd.h +++ b/drivers/scsi/sd.h | |||
@@ -47,7 +47,7 @@ struct scsi_disk { | |||
47 | struct scsi_device *device; | 47 | struct scsi_device *device; |
48 | struct device dev; | 48 | struct device dev; |
49 | struct gendisk *disk; | 49 | struct gendisk *disk; |
50 | unsigned int openers; /* protected by BKL for now, yuck */ | 50 | atomic_t openers; |
51 | sector_t capacity; /* size in 512-byte sectors */ | 51 | sector_t capacity; /* size in 512-byte sectors */ |
52 | u32 index; | 52 | u32 index; |
53 | unsigned short hw_sector_size; | 53 | unsigned short hw_sector_size; |
diff --git a/drivers/scsi/sr.c b/drivers/scsi/sr.c index 0a90abc7f140..ba9c3e0387ce 100644 --- a/drivers/scsi/sr.c +++ b/drivers/scsi/sr.c | |||
@@ -44,6 +44,7 @@ | |||
44 | #include <linux/init.h> | 44 | #include <linux/init.h> |
45 | #include <linux/blkdev.h> | 45 | #include <linux/blkdev.h> |
46 | #include <linux/mutex.h> | 46 | #include <linux/mutex.h> |
47 | #include <linux/smp_lock.h> | ||
47 | #include <linux/slab.h> | 48 | #include <linux/slab.h> |
48 | #include <asm/uaccess.h> | 49 | #include <asm/uaccess.h> |
49 | 50 | ||
@@ -466,22 +467,27 @@ static int sr_prep_fn(struct request_queue *q, struct request *rq) | |||
466 | 467 | ||
467 | static int sr_block_open(struct block_device *bdev, fmode_t mode) | 468 | static int sr_block_open(struct block_device *bdev, fmode_t mode) |
468 | { | 469 | { |
469 | struct scsi_cd *cd = scsi_cd_get(bdev->bd_disk); | 470 | struct scsi_cd *cd; |
470 | int ret = -ENXIO; | 471 | int ret = -ENXIO; |
471 | 472 | ||
473 | lock_kernel(); | ||
474 | cd = scsi_cd_get(bdev->bd_disk); | ||
472 | if (cd) { | 475 | if (cd) { |
473 | ret = cdrom_open(&cd->cdi, bdev, mode); | 476 | ret = cdrom_open(&cd->cdi, bdev, mode); |
474 | if (ret) | 477 | if (ret) |
475 | scsi_cd_put(cd); | 478 | scsi_cd_put(cd); |
476 | } | 479 | } |
480 | unlock_kernel(); | ||
477 | return ret; | 481 | return ret; |
478 | } | 482 | } |
479 | 483 | ||
480 | static int sr_block_release(struct gendisk *disk, fmode_t mode) | 484 | static int sr_block_release(struct gendisk *disk, fmode_t mode) |
481 | { | 485 | { |
482 | struct scsi_cd *cd = scsi_cd(disk); | 486 | struct scsi_cd *cd = scsi_cd(disk); |
487 | lock_kernel(); | ||
483 | cdrom_release(&cd->cdi, mode); | 488 | cdrom_release(&cd->cdi, mode); |
484 | scsi_cd_put(cd); | 489 | scsi_cd_put(cd); |
490 | unlock_kernel(); | ||
485 | return 0; | 491 | return 0; |
486 | } | 492 | } |
487 | 493 | ||
@@ -493,6 +499,8 @@ static int sr_block_ioctl(struct block_device *bdev, fmode_t mode, unsigned cmd, | |||
493 | void __user *argp = (void __user *)arg; | 499 | void __user *argp = (void __user *)arg; |
494 | int ret; | 500 | int ret; |
495 | 501 | ||
502 | lock_kernel(); | ||
503 | |||
496 | /* | 504 | /* |
497 | * Send SCSI addressing ioctls directly to mid level, send other | 505 | * Send SCSI addressing ioctls directly to mid level, send other |
498 | * ioctls to cdrom/block level. | 506 | * ioctls to cdrom/block level. |
@@ -500,12 +508,13 @@ static int sr_block_ioctl(struct block_device *bdev, fmode_t mode, unsigned cmd, | |||
500 | switch (cmd) { | 508 | switch (cmd) { |
501 | case SCSI_IOCTL_GET_IDLUN: | 509 | case SCSI_IOCTL_GET_IDLUN: |
502 | case SCSI_IOCTL_GET_BUS_NUMBER: | 510 | case SCSI_IOCTL_GET_BUS_NUMBER: |
503 | return scsi_ioctl(sdev, cmd, argp); | 511 | ret = scsi_ioctl(sdev, cmd, argp); |
512 | goto out; | ||
504 | } | 513 | } |
505 | 514 | ||
506 | ret = cdrom_ioctl(&cd->cdi, bdev, mode, cmd, arg); | 515 | ret = cdrom_ioctl(&cd->cdi, bdev, mode, cmd, arg); |
507 | if (ret != -ENOSYS) | 516 | if (ret != -ENOSYS) |
508 | return ret; | 517 | goto out; |
509 | 518 | ||
510 | /* | 519 | /* |
511 | * ENODEV means that we didn't recognise the ioctl, or that we | 520 | * ENODEV means that we didn't recognise the ioctl, or that we |
@@ -516,8 +525,12 @@ static int sr_block_ioctl(struct block_device *bdev, fmode_t mode, unsigned cmd, | |||
516 | ret = scsi_nonblockable_ioctl(sdev, cmd, argp, | 525 | ret = scsi_nonblockable_ioctl(sdev, cmd, argp, |
517 | (mode & FMODE_NDELAY) != 0); | 526 | (mode & FMODE_NDELAY) != 0); |
518 | if (ret != -ENODEV) | 527 | if (ret != -ENODEV) |
519 | return ret; | 528 | goto out; |
520 | return scsi_ioctl(sdev, cmd, argp); | 529 | ret = scsi_ioctl(sdev, cmd, argp); |
530 | |||
531 | out: | ||
532 | unlock_kernel(); | ||
533 | return ret; | ||
521 | } | 534 | } |
522 | 535 | ||
523 | static int sr_block_media_changed(struct gendisk *disk) | 536 | static int sr_block_media_changed(struct gendisk *disk) |
@@ -531,7 +544,7 @@ static const struct block_device_operations sr_bdops = | |||
531 | .owner = THIS_MODULE, | 544 | .owner = THIS_MODULE, |
532 | .open = sr_block_open, | 545 | .open = sr_block_open, |
533 | .release = sr_block_release, | 546 | .release = sr_block_release, |
534 | .locked_ioctl = sr_block_ioctl, | 547 | .ioctl = sr_block_ioctl, |
535 | .media_changed = sr_block_media_changed, | 548 | .media_changed = sr_block_media_changed, |
536 | /* | 549 | /* |
537 | * No compat_ioctl for now because sr_block_ioctl never | 550 | * No compat_ioctl for now because sr_block_ioctl never |
diff --git a/drivers/scsi/sun3_NCR5380.c b/drivers/scsi/sun3_NCR5380.c index b5838d547c68..713620ed70d9 100644 --- a/drivers/scsi/sun3_NCR5380.c +++ b/drivers/scsi/sun3_NCR5380.c | |||
@@ -2022,7 +2022,7 @@ static void NCR5380_information_transfer (struct Scsi_Host *instance) | |||
2022 | if((count > SUN3_DMA_MINSIZE) && (sun3_dma_setup_done | 2022 | if((count > SUN3_DMA_MINSIZE) && (sun3_dma_setup_done |
2023 | != cmd)) | 2023 | != cmd)) |
2024 | { | 2024 | { |
2025 | if(blk_fs_request(cmd->request)) { | 2025 | if (cmd->request->cmd_type == REQ_TYPE_FS) { |
2026 | sun3scsi_dma_setup(d, count, | 2026 | sun3scsi_dma_setup(d, count, |
2027 | rq_data_dir(cmd->request)); | 2027 | rq_data_dir(cmd->request)); |
2028 | sun3_dma_setup_done = cmd; | 2028 | sun3_dma_setup_done = cmd; |
diff --git a/drivers/scsi/sun3_scsi.c b/drivers/scsi/sun3_scsi.c index e606cf0a2eb7..613f5880d135 100644 --- a/drivers/scsi/sun3_scsi.c +++ b/drivers/scsi/sun3_scsi.c | |||
@@ -524,7 +524,7 @@ static inline unsigned long sun3scsi_dma_xfer_len(unsigned long wanted, | |||
524 | struct scsi_cmnd *cmd, | 524 | struct scsi_cmnd *cmd, |
525 | int write_flag) | 525 | int write_flag) |
526 | { | 526 | { |
527 | if(blk_fs_request(cmd->request)) | 527 | if (cmd->request->cmd_type == REQ_TYPE_FS) |
528 | return wanted; | 528 | return wanted; |
529 | else | 529 | else |
530 | return 0; | 530 | return 0; |
diff --git a/drivers/scsi/sun3_scsi_vme.c b/drivers/scsi/sun3_scsi_vme.c index aaa4fd0dd1b9..7c526b8e30ac 100644 --- a/drivers/scsi/sun3_scsi_vme.c +++ b/drivers/scsi/sun3_scsi_vme.c | |||
@@ -458,7 +458,7 @@ static inline unsigned long sun3scsi_dma_xfer_len(unsigned long wanted, | |||
458 | struct scsi_cmnd *cmd, | 458 | struct scsi_cmnd *cmd, |
459 | int write_flag) | 459 | int write_flag) |
460 | { | 460 | { |
461 | if(blk_fs_request(cmd->request)) | 461 | if (cmd->request->cmd_type == REQ_TYPE_FS) |
462 | return wanted; | 462 | return wanted; |
463 | else | 463 | else |
464 | return 0; | 464 | return 0; |
diff --git a/drivers/staging/hv/blkvsc_drv.c b/drivers/staging/hv/blkvsc_drv.c index f7ea2a3efed7..ff1d24720f11 100644 --- a/drivers/staging/hv/blkvsc_drv.c +++ b/drivers/staging/hv/blkvsc_drv.c | |||
@@ -25,6 +25,7 @@ | |||
25 | #include <linux/major.h> | 25 | #include <linux/major.h> |
26 | #include <linux/delay.h> | 26 | #include <linux/delay.h> |
27 | #include <linux/hdreg.h> | 27 | #include <linux/hdreg.h> |
28 | #include <linux/smp_lock.h> | ||
28 | #include <linux/slab.h> | 29 | #include <linux/slab.h> |
29 | #include <scsi/scsi.h> | 30 | #include <scsi/scsi.h> |
30 | #include <scsi/scsi_cmnd.h> | 31 | #include <scsi/scsi_cmnd.h> |
@@ -805,7 +806,8 @@ static void blkvsc_init_rw(struct blkvsc_request *blkvsc_req) | |||
805 | blkvsc_req->cmnd[0] = READ_16; | 806 | blkvsc_req->cmnd[0] = READ_16; |
806 | } | 807 | } |
807 | 808 | ||
808 | blkvsc_req->cmnd[1] |= blk_fua_rq(blkvsc_req->req) ? 0x8 : 0; | 809 | blkvsc_req->cmnd[1] |= |
810 | (blkvsc_req->req->cmd_flags & REQ_FUA) ? 0x8 : 0; | ||
809 | 811 | ||
810 | *(unsigned long long *)&blkvsc_req->cmnd[2] = | 812 | *(unsigned long long *)&blkvsc_req->cmnd[2] = |
811 | cpu_to_be64(blkvsc_req->sector_start); | 813 | cpu_to_be64(blkvsc_req->sector_start); |
@@ -821,7 +823,8 @@ static void blkvsc_init_rw(struct blkvsc_request *blkvsc_req) | |||
821 | blkvsc_req->cmnd[0] = READ_10; | 823 | blkvsc_req->cmnd[0] = READ_10; |
822 | } | 824 | } |
823 | 825 | ||
824 | blkvsc_req->cmnd[1] |= blk_fua_rq(blkvsc_req->req) ? 0x8 : 0; | 826 | blkvsc_req->cmnd[1] |= |
827 | (blkvsc_req->req->cmd_flags & REQ_FUA) ? 0x8 : 0; | ||
825 | 828 | ||
826 | *(unsigned int *)&blkvsc_req->cmnd[2] = | 829 | *(unsigned int *)&blkvsc_req->cmnd[2] = |
827 | cpu_to_be32(blkvsc_req->sector_start); | 830 | cpu_to_be32(blkvsc_req->sector_start); |
@@ -1268,7 +1271,7 @@ static void blkvsc_request(struct request_queue *queue) | |||
1268 | DPRINT_DBG(BLKVSC_DRV, "- req %p\n", req); | 1271 | DPRINT_DBG(BLKVSC_DRV, "- req %p\n", req); |
1269 | 1272 | ||
1270 | blkdev = req->rq_disk->private_data; | 1273 | blkdev = req->rq_disk->private_data; |
1271 | if (blkdev->shutting_down || !blk_fs_request(req) || | 1274 | if (blkdev->shutting_down || req->cmd_type != REQ_TYPE_FS || |
1272 | blkdev->media_not_present) { | 1275 | blkdev->media_not_present) { |
1273 | __blk_end_request_cur(req, 0); | 1276 | __blk_end_request_cur(req, 0); |
1274 | continue; | 1277 | continue; |
@@ -1306,6 +1309,7 @@ static int blkvsc_open(struct block_device *bdev, fmode_t mode) | |||
1306 | DPRINT_DBG(BLKVSC_DRV, "- users %d disk %s\n", blkdev->users, | 1309 | DPRINT_DBG(BLKVSC_DRV, "- users %d disk %s\n", blkdev->users, |
1307 | blkdev->gd->disk_name); | 1310 | blkdev->gd->disk_name); |
1308 | 1311 | ||
1312 | lock_kernel(); | ||
1309 | spin_lock(&blkdev->lock); | 1313 | spin_lock(&blkdev->lock); |
1310 | 1314 | ||
1311 | if (!blkdev->users && blkdev->device_type == DVD_TYPE) { | 1315 | if (!blkdev->users && blkdev->device_type == DVD_TYPE) { |
@@ -1317,6 +1321,7 @@ static int blkvsc_open(struct block_device *bdev, fmode_t mode) | |||
1317 | blkdev->users++; | 1321 | blkdev->users++; |
1318 | 1322 | ||
1319 | spin_unlock(&blkdev->lock); | 1323 | spin_unlock(&blkdev->lock); |
1324 | unlock_kernel(); | ||
1320 | return 0; | 1325 | return 0; |
1321 | } | 1326 | } |
1322 | 1327 | ||
@@ -1327,6 +1332,7 @@ static int blkvsc_release(struct gendisk *disk, fmode_t mode) | |||
1327 | DPRINT_DBG(BLKVSC_DRV, "- users %d disk %s\n", blkdev->users, | 1332 | DPRINT_DBG(BLKVSC_DRV, "- users %d disk %s\n", blkdev->users, |
1328 | blkdev->gd->disk_name); | 1333 | blkdev->gd->disk_name); |
1329 | 1334 | ||
1335 | lock_kernel(); | ||
1330 | spin_lock(&blkdev->lock); | 1336 | spin_lock(&blkdev->lock); |
1331 | if (blkdev->users == 1) { | 1337 | if (blkdev->users == 1) { |
1332 | spin_unlock(&blkdev->lock); | 1338 | spin_unlock(&blkdev->lock); |
@@ -1337,6 +1343,7 @@ static int blkvsc_release(struct gendisk *disk, fmode_t mode) | |||
1337 | blkdev->users--; | 1343 | blkdev->users--; |
1338 | 1344 | ||
1339 | spin_unlock(&blkdev->lock); | 1345 | spin_unlock(&blkdev->lock); |
1346 | unlock_kernel(); | ||
1340 | return 0; | 1347 | return 0; |
1341 | } | 1348 | } |
1342 | 1349 | ||
diff --git a/drivers/xen/xenbus/xenbus_client.c b/drivers/xen/xenbus/xenbus_client.c index 7b3e973a1aee..7e49527189b6 100644 --- a/drivers/xen/xenbus/xenbus_client.c +++ b/drivers/xen/xenbus/xenbus_client.c | |||
@@ -133,17 +133,12 @@ int xenbus_watch_pathfmt(struct xenbus_device *dev, | |||
133 | } | 133 | } |
134 | EXPORT_SYMBOL_GPL(xenbus_watch_pathfmt); | 134 | EXPORT_SYMBOL_GPL(xenbus_watch_pathfmt); |
135 | 135 | ||
136 | static void xenbus_switch_fatal(struct xenbus_device *, int, int, | ||
137 | const char *, ...); | ||
136 | 138 | ||
137 | /** | 139 | static int |
138 | * xenbus_switch_state | 140 | __xenbus_switch_state(struct xenbus_device *dev, |
139 | * @dev: xenbus device | 141 | enum xenbus_state state, int depth) |
140 | * @state: new state | ||
141 | * | ||
142 | * Advertise in the store a change of the given driver to the given new_state. | ||
143 | * Return 0 on success, or -errno on error. On error, the device will switch | ||
144 | * to XenbusStateClosing, and the error will be saved in the store. | ||
145 | */ | ||
146 | int xenbus_switch_state(struct xenbus_device *dev, enum xenbus_state state) | ||
147 | { | 142 | { |
148 | /* We check whether the state is currently set to the given value, and | 143 | /* We check whether the state is currently set to the given value, and |
149 | if not, then the state is set. We don't want to unconditionally | 144 | if not, then the state is set. We don't want to unconditionally |
@@ -152,35 +147,65 @@ int xenbus_switch_state(struct xenbus_device *dev, enum xenbus_state state) | |||
152 | to it, as the device will be tearing down, and we don't want to | 147 | to it, as the device will be tearing down, and we don't want to |
153 | resurrect that directory. | 148 | resurrect that directory. |
154 | 149 | ||
155 | Note that, because of this cached value of our state, this function | 150 | Note that, because of this cached value of our state, this |
156 | will not work inside a Xenstore transaction (something it was | 151 | function will not take a caller's Xenstore transaction |
157 | trying to in the past) because dev->state would not get reset if | 152 | (something it was trying to in the past) because dev->state |
158 | the transaction was aborted. | 153 | would not get reset if the transaction was aborted. |
159 | |||
160 | */ | 154 | */ |
161 | 155 | ||
156 | struct xenbus_transaction xbt; | ||
162 | int current_state; | 157 | int current_state; |
163 | int err; | 158 | int err, abort; |
164 | 159 | ||
165 | if (state == dev->state) | 160 | if (state == dev->state) |
166 | return 0; | 161 | return 0; |
167 | 162 | ||
168 | err = xenbus_scanf(XBT_NIL, dev->nodename, "state", "%d", | 163 | again: |
169 | ¤t_state); | 164 | abort = 1; |
170 | if (err != 1) | 165 | |
166 | err = xenbus_transaction_start(&xbt); | ||
167 | if (err) { | ||
168 | xenbus_switch_fatal(dev, depth, err, "starting transaction"); | ||
171 | return 0; | 169 | return 0; |
170 | } | ||
171 | |||
172 | err = xenbus_scanf(xbt, dev->nodename, "state", "%d", ¤t_state); | ||
173 | if (err != 1) | ||
174 | goto abort; | ||
172 | 175 | ||
173 | err = xenbus_printf(XBT_NIL, dev->nodename, "state", "%d", state); | 176 | err = xenbus_printf(xbt, dev->nodename, "state", "%d", state); |
174 | if (err) { | 177 | if (err) { |
175 | if (state != XenbusStateClosing) /* Avoid looping */ | 178 | xenbus_switch_fatal(dev, depth, err, "writing new state"); |
176 | xenbus_dev_fatal(dev, err, "writing new state"); | 179 | goto abort; |
177 | return err; | ||
178 | } | 180 | } |
179 | 181 | ||
180 | dev->state = state; | 182 | abort = 0; |
183 | abort: | ||
184 | err = xenbus_transaction_end(xbt, abort); | ||
185 | if (err) { | ||
186 | if (err == -EAGAIN && !abort) | ||
187 | goto again; | ||
188 | xenbus_switch_fatal(dev, depth, err, "ending transaction"); | ||
189 | } else | ||
190 | dev->state = state; | ||
181 | 191 | ||
182 | return 0; | 192 | return 0; |
183 | } | 193 | } |
194 | |||
195 | /** | ||
196 | * xenbus_switch_state | ||
197 | * @dev: xenbus device | ||
198 | * @state: new state | ||
199 | * | ||
200 | * Advertise in the store a change of the given driver to the given new_state. | ||
201 | * Return 0 on success, or -errno on error. On error, the device will switch | ||
202 | * to XenbusStateClosing, and the error will be saved in the store. | ||
203 | */ | ||
204 | int xenbus_switch_state(struct xenbus_device *dev, enum xenbus_state state) | ||
205 | { | ||
206 | return __xenbus_switch_state(dev, state, 0); | ||
207 | } | ||
208 | |||
184 | EXPORT_SYMBOL_GPL(xenbus_switch_state); | 209 | EXPORT_SYMBOL_GPL(xenbus_switch_state); |
185 | 210 | ||
186 | int xenbus_frontend_closed(struct xenbus_device *dev) | 211 | int xenbus_frontend_closed(struct xenbus_device *dev) |
@@ -284,6 +309,23 @@ void xenbus_dev_fatal(struct xenbus_device *dev, int err, const char *fmt, ...) | |||
284 | EXPORT_SYMBOL_GPL(xenbus_dev_fatal); | 309 | EXPORT_SYMBOL_GPL(xenbus_dev_fatal); |
285 | 310 | ||
286 | /** | 311 | /** |
312 | * Equivalent to xenbus_dev_fatal(dev, err, fmt, args), but helps | ||
313 | * avoiding recursion within xenbus_switch_state. | ||
314 | */ | ||
315 | static void xenbus_switch_fatal(struct xenbus_device *dev, int depth, int err, | ||
316 | const char *fmt, ...) | ||
317 | { | ||
318 | va_list ap; | ||
319 | |||
320 | va_start(ap, fmt); | ||
321 | xenbus_va_dev_error(dev, err, fmt, ap); | ||
322 | va_end(ap); | ||
323 | |||
324 | if (!depth) | ||
325 | __xenbus_switch_state(dev, XenbusStateClosing, 1); | ||
326 | } | ||
327 | |||
328 | /** | ||
287 | * xenbus_grant_ring | 329 | * xenbus_grant_ring |
288 | * @dev: xenbus device | 330 | * @dev: xenbus device |
289 | * @ring_mfn: mfn of ring to grant | 331 | * @ring_mfn: mfn of ring to grant |
@@ -843,7 +843,8 @@ struct bio *bio_copy_user_iov(struct request_queue *q, | |||
843 | if (!bio) | 843 | if (!bio) |
844 | goto out_bmd; | 844 | goto out_bmd; |
845 | 845 | ||
846 | bio->bi_rw |= (!write_to_vm << BIO_RW); | 846 | if (!write_to_vm) |
847 | bio->bi_rw |= REQ_WRITE; | ||
847 | 848 | ||
848 | ret = 0; | 849 | ret = 0; |
849 | 850 | ||
@@ -1024,7 +1025,7 @@ static struct bio *__bio_map_user_iov(struct request_queue *q, | |||
1024 | * set data direction, and check if mapped pages need bouncing | 1025 | * set data direction, and check if mapped pages need bouncing |
1025 | */ | 1026 | */ |
1026 | if (!write_to_vm) | 1027 | if (!write_to_vm) |
1027 | bio->bi_rw |= (1 << BIO_RW); | 1028 | bio->bi_rw |= REQ_WRITE; |
1028 | 1029 | ||
1029 | bio->bi_bdev = bdev; | 1030 | bio->bi_bdev = bdev; |
1030 | bio->bi_flags |= (1 << BIO_USER_MAPPED); | 1031 | bio->bi_flags |= (1 << BIO_USER_MAPPED); |
diff --git a/fs/block_dev.c b/fs/block_dev.c index 451afbd543b5..66411463b734 100644 --- a/fs/block_dev.c +++ b/fs/block_dev.c | |||
@@ -1346,13 +1346,12 @@ static int __blkdev_get(struct block_device *bdev, fmode_t mode, int for_part) | |||
1346 | return ret; | 1346 | return ret; |
1347 | } | 1347 | } |
1348 | 1348 | ||
1349 | lock_kernel(); | ||
1350 | restart: | 1349 | restart: |
1351 | 1350 | ||
1352 | ret = -ENXIO; | 1351 | ret = -ENXIO; |
1353 | disk = get_gendisk(bdev->bd_dev, &partno); | 1352 | disk = get_gendisk(bdev->bd_dev, &partno); |
1354 | if (!disk) | 1353 | if (!disk) |
1355 | goto out_unlock_kernel; | 1354 | goto out; |
1356 | 1355 | ||
1357 | mutex_lock_nested(&bdev->bd_mutex, for_part); | 1356 | mutex_lock_nested(&bdev->bd_mutex, for_part); |
1358 | if (!bdev->bd_openers) { | 1357 | if (!bdev->bd_openers) { |
@@ -1432,7 +1431,6 @@ static int __blkdev_get(struct block_device *bdev, fmode_t mode, int for_part) | |||
1432 | if (for_part) | 1431 | if (for_part) |
1433 | bdev->bd_part_count++; | 1432 | bdev->bd_part_count++; |
1434 | mutex_unlock(&bdev->bd_mutex); | 1433 | mutex_unlock(&bdev->bd_mutex); |
1435 | unlock_kernel(); | ||
1436 | return 0; | 1434 | return 0; |
1437 | 1435 | ||
1438 | out_clear: | 1436 | out_clear: |
@@ -1445,9 +1443,7 @@ static int __blkdev_get(struct block_device *bdev, fmode_t mode, int for_part) | |||
1445 | bdev->bd_contains = NULL; | 1443 | bdev->bd_contains = NULL; |
1446 | out_unlock_bdev: | 1444 | out_unlock_bdev: |
1447 | mutex_unlock(&bdev->bd_mutex); | 1445 | mutex_unlock(&bdev->bd_mutex); |
1448 | out_unlock_kernel: | 1446 | out: |
1449 | unlock_kernel(); | ||
1450 | |||
1451 | if (disk) | 1447 | if (disk) |
1452 | module_put(disk->fops->owner); | 1448 | module_put(disk->fops->owner); |
1453 | put_disk(disk); | 1449 | put_disk(disk); |
@@ -1516,7 +1512,6 @@ static int __blkdev_put(struct block_device *bdev, fmode_t mode, int for_part) | |||
1516 | struct block_device *victim = NULL; | 1512 | struct block_device *victim = NULL; |
1517 | 1513 | ||
1518 | mutex_lock_nested(&bdev->bd_mutex, for_part); | 1514 | mutex_lock_nested(&bdev->bd_mutex, for_part); |
1519 | lock_kernel(); | ||
1520 | if (for_part) | 1515 | if (for_part) |
1521 | bdev->bd_part_count--; | 1516 | bdev->bd_part_count--; |
1522 | 1517 | ||
@@ -1541,7 +1536,6 @@ static int __blkdev_put(struct block_device *bdev, fmode_t mode, int for_part) | |||
1541 | victim = bdev->bd_contains; | 1536 | victim = bdev->bd_contains; |
1542 | bdev->bd_contains = NULL; | 1537 | bdev->bd_contains = NULL; |
1543 | } | 1538 | } |
1544 | unlock_kernel(); | ||
1545 | mutex_unlock(&bdev->bd_mutex); | 1539 | mutex_unlock(&bdev->bd_mutex); |
1546 | bdput(bdev); | 1540 | bdput(bdev); |
1547 | if (victim) | 1541 | if (victim) |
diff --git a/fs/btrfs/disk-io.c b/fs/btrfs/disk-io.c index 34f7c375567e..64f10082f048 100644 --- a/fs/btrfs/disk-io.c +++ b/fs/btrfs/disk-io.c | |||
@@ -480,7 +480,7 @@ static void end_workqueue_bio(struct bio *bio, int err) | |||
480 | end_io_wq->work.func = end_workqueue_fn; | 480 | end_io_wq->work.func = end_workqueue_fn; |
481 | end_io_wq->work.flags = 0; | 481 | end_io_wq->work.flags = 0; |
482 | 482 | ||
483 | if (bio->bi_rw & (1 << BIO_RW)) { | 483 | if (bio->bi_rw & REQ_WRITE) { |
484 | if (end_io_wq->metadata) | 484 | if (end_io_wq->metadata) |
485 | btrfs_queue_worker(&fs_info->endio_meta_write_workers, | 485 | btrfs_queue_worker(&fs_info->endio_meta_write_workers, |
486 | &end_io_wq->work); | 486 | &end_io_wq->work); |
@@ -604,7 +604,7 @@ int btrfs_wq_submit_bio(struct btrfs_fs_info *fs_info, struct inode *inode, | |||
604 | 604 | ||
605 | atomic_inc(&fs_info->nr_async_submits); | 605 | atomic_inc(&fs_info->nr_async_submits); |
606 | 606 | ||
607 | if (rw & (1 << BIO_RW_SYNCIO)) | 607 | if (rw & REQ_SYNC) |
608 | btrfs_set_work_high_prio(&async->work); | 608 | btrfs_set_work_high_prio(&async->work); |
609 | 609 | ||
610 | btrfs_queue_worker(&fs_info->workers, &async->work); | 610 | btrfs_queue_worker(&fs_info->workers, &async->work); |
@@ -668,7 +668,7 @@ static int btree_submit_bio_hook(struct inode *inode, int rw, struct bio *bio, | |||
668 | bio, 1); | 668 | bio, 1); |
669 | BUG_ON(ret); | 669 | BUG_ON(ret); |
670 | 670 | ||
671 | if (!(rw & (1 << BIO_RW))) { | 671 | if (!(rw & REQ_WRITE)) { |
672 | /* | 672 | /* |
673 | * called for a read, do the setup so that checksum validation | 673 | * called for a read, do the setup so that checksum validation |
674 | * can happen in the async kernel threads | 674 | * can happen in the async kernel threads |
@@ -1427,7 +1427,7 @@ static void end_workqueue_fn(struct btrfs_work *work) | |||
1427 | * ram and up to date before trying to verify things. For | 1427 | * ram and up to date before trying to verify things. For |
1428 | * blocksize <= pagesize, it is basically a noop | 1428 | * blocksize <= pagesize, it is basically a noop |
1429 | */ | 1429 | */ |
1430 | if (!(bio->bi_rw & (1 << BIO_RW)) && end_io_wq->metadata && | 1430 | if (!(bio->bi_rw & REQ_WRITE) && end_io_wq->metadata && |
1431 | !bio_ready_for_csum(bio)) { | 1431 | !bio_ready_for_csum(bio)) { |
1432 | btrfs_queue_worker(&fs_info->endio_meta_workers, | 1432 | btrfs_queue_worker(&fs_info->endio_meta_workers, |
1433 | &end_io_wq->work); | 1433 | &end_io_wq->work); |
diff --git a/fs/btrfs/inode.c b/fs/btrfs/inode.c index 8976c3343a96..c03864406af3 100644 --- a/fs/btrfs/inode.c +++ b/fs/btrfs/inode.c | |||
@@ -1429,7 +1429,7 @@ static int btrfs_submit_bio_hook(struct inode *inode, int rw, struct bio *bio, | |||
1429 | ret = btrfs_bio_wq_end_io(root->fs_info, bio, 0); | 1429 | ret = btrfs_bio_wq_end_io(root->fs_info, bio, 0); |
1430 | BUG_ON(ret); | 1430 | BUG_ON(ret); |
1431 | 1431 | ||
1432 | if (!(rw & (1 << BIO_RW))) { | 1432 | if (!(rw & REQ_WRITE)) { |
1433 | if (bio_flags & EXTENT_BIO_COMPRESSED) { | 1433 | if (bio_flags & EXTENT_BIO_COMPRESSED) { |
1434 | return btrfs_submit_compressed_read(inode, bio, | 1434 | return btrfs_submit_compressed_read(inode, bio, |
1435 | mirror_num, bio_flags); | 1435 | mirror_num, bio_flags); |
@@ -1841,7 +1841,7 @@ static int btrfs_io_failed_hook(struct bio *failed_bio, | |||
1841 | bio->bi_size = 0; | 1841 | bio->bi_size = 0; |
1842 | 1842 | ||
1843 | bio_add_page(bio, page, failrec->len, start - page_offset(page)); | 1843 | bio_add_page(bio, page, failrec->len, start - page_offset(page)); |
1844 | if (failed_bio->bi_rw & (1 << BIO_RW)) | 1844 | if (failed_bio->bi_rw & REQ_WRITE) |
1845 | rw = WRITE; | 1845 | rw = WRITE; |
1846 | else | 1846 | else |
1847 | rw = READ; | 1847 | rw = READ; |
@@ -5647,7 +5647,7 @@ static void btrfs_submit_direct(int rw, struct bio *bio, struct inode *inode, | |||
5647 | struct bio_vec *bvec = bio->bi_io_vec; | 5647 | struct bio_vec *bvec = bio->bi_io_vec; |
5648 | u64 start; | 5648 | u64 start; |
5649 | int skip_sum; | 5649 | int skip_sum; |
5650 | int write = rw & (1 << BIO_RW); | 5650 | int write = rw & REQ_WRITE; |
5651 | int ret = 0; | 5651 | int ret = 0; |
5652 | 5652 | ||
5653 | skip_sum = BTRFS_I(inode)->flags & BTRFS_INODE_NODATASUM; | 5653 | skip_sum = BTRFS_I(inode)->flags & BTRFS_INODE_NODATASUM; |
diff --git a/fs/btrfs/volumes.c b/fs/btrfs/volumes.c index d6e3af8be95b..dd318ff280b2 100644 --- a/fs/btrfs/volumes.c +++ b/fs/btrfs/volumes.c | |||
@@ -258,7 +258,7 @@ loop_lock: | |||
258 | 258 | ||
259 | BUG_ON(atomic_read(&cur->bi_cnt) == 0); | 259 | BUG_ON(atomic_read(&cur->bi_cnt) == 0); |
260 | 260 | ||
261 | if (bio_rw_flagged(cur, BIO_RW_SYNCIO)) | 261 | if (cur->bi_rw & REQ_SYNC) |
262 | num_sync_run++; | 262 | num_sync_run++; |
263 | 263 | ||
264 | submit_bio(cur->bi_rw, cur); | 264 | submit_bio(cur->bi_rw, cur); |
@@ -2651,7 +2651,7 @@ static int __btrfs_map_block(struct btrfs_mapping_tree *map_tree, int rw, | |||
2651 | int max_errors = 0; | 2651 | int max_errors = 0; |
2652 | struct btrfs_multi_bio *multi = NULL; | 2652 | struct btrfs_multi_bio *multi = NULL; |
2653 | 2653 | ||
2654 | if (multi_ret && !(rw & (1 << BIO_RW))) | 2654 | if (multi_ret && !(rw & REQ_WRITE)) |
2655 | stripes_allocated = 1; | 2655 | stripes_allocated = 1; |
2656 | again: | 2656 | again: |
2657 | if (multi_ret) { | 2657 | if (multi_ret) { |
@@ -2687,7 +2687,7 @@ again: | |||
2687 | mirror_num = 0; | 2687 | mirror_num = 0; |
2688 | 2688 | ||
2689 | /* if our multi bio struct is too small, back off and try again */ | 2689 | /* if our multi bio struct is too small, back off and try again */ |
2690 | if (rw & (1 << BIO_RW)) { | 2690 | if (rw & REQ_WRITE) { |
2691 | if (map->type & (BTRFS_BLOCK_GROUP_RAID1 | | 2691 | if (map->type & (BTRFS_BLOCK_GROUP_RAID1 | |
2692 | BTRFS_BLOCK_GROUP_DUP)) { | 2692 | BTRFS_BLOCK_GROUP_DUP)) { |
2693 | stripes_required = map->num_stripes; | 2693 | stripes_required = map->num_stripes; |
@@ -2697,7 +2697,7 @@ again: | |||
2697 | max_errors = 1; | 2697 | max_errors = 1; |
2698 | } | 2698 | } |
2699 | } | 2699 | } |
2700 | if (multi_ret && (rw & (1 << BIO_RW)) && | 2700 | if (multi_ret && (rw & REQ_WRITE) && |
2701 | stripes_allocated < stripes_required) { | 2701 | stripes_allocated < stripes_required) { |
2702 | stripes_allocated = map->num_stripes; | 2702 | stripes_allocated = map->num_stripes; |
2703 | free_extent_map(em); | 2703 | free_extent_map(em); |
@@ -2733,7 +2733,7 @@ again: | |||
2733 | num_stripes = 1; | 2733 | num_stripes = 1; |
2734 | stripe_index = 0; | 2734 | stripe_index = 0; |
2735 | if (map->type & BTRFS_BLOCK_GROUP_RAID1) { | 2735 | if (map->type & BTRFS_BLOCK_GROUP_RAID1) { |
2736 | if (unplug_page || (rw & (1 << BIO_RW))) | 2736 | if (unplug_page || (rw & REQ_WRITE)) |
2737 | num_stripes = map->num_stripes; | 2737 | num_stripes = map->num_stripes; |
2738 | else if (mirror_num) | 2738 | else if (mirror_num) |
2739 | stripe_index = mirror_num - 1; | 2739 | stripe_index = mirror_num - 1; |
@@ -2744,7 +2744,7 @@ again: | |||
2744 | } | 2744 | } |
2745 | 2745 | ||
2746 | } else if (map->type & BTRFS_BLOCK_GROUP_DUP) { | 2746 | } else if (map->type & BTRFS_BLOCK_GROUP_DUP) { |
2747 | if (rw & (1 << BIO_RW)) | 2747 | if (rw & REQ_WRITE) |
2748 | num_stripes = map->num_stripes; | 2748 | num_stripes = map->num_stripes; |
2749 | else if (mirror_num) | 2749 | else if (mirror_num) |
2750 | stripe_index = mirror_num - 1; | 2750 | stripe_index = mirror_num - 1; |
@@ -2755,7 +2755,7 @@ again: | |||
2755 | stripe_index = do_div(stripe_nr, factor); | 2755 | stripe_index = do_div(stripe_nr, factor); |
2756 | stripe_index *= map->sub_stripes; | 2756 | stripe_index *= map->sub_stripes; |
2757 | 2757 | ||
2758 | if (unplug_page || (rw & (1 << BIO_RW))) | 2758 | if (unplug_page || (rw & REQ_WRITE)) |
2759 | num_stripes = map->sub_stripes; | 2759 | num_stripes = map->sub_stripes; |
2760 | else if (mirror_num) | 2760 | else if (mirror_num) |
2761 | stripe_index += mirror_num - 1; | 2761 | stripe_index += mirror_num - 1; |
@@ -2945,7 +2945,7 @@ static noinline int schedule_bio(struct btrfs_root *root, | |||
2945 | struct btrfs_pending_bios *pending_bios; | 2945 | struct btrfs_pending_bios *pending_bios; |
2946 | 2946 | ||
2947 | /* don't bother with additional async steps for reads, right now */ | 2947 | /* don't bother with additional async steps for reads, right now */ |
2948 | if (!(rw & (1 << BIO_RW))) { | 2948 | if (!(rw & REQ_WRITE)) { |
2949 | bio_get(bio); | 2949 | bio_get(bio); |
2950 | submit_bio(rw, bio); | 2950 | submit_bio(rw, bio); |
2951 | bio_put(bio); | 2951 | bio_put(bio); |
@@ -2964,7 +2964,7 @@ static noinline int schedule_bio(struct btrfs_root *root, | |||
2964 | bio->bi_rw |= rw; | 2964 | bio->bi_rw |= rw; |
2965 | 2965 | ||
2966 | spin_lock(&device->io_lock); | 2966 | spin_lock(&device->io_lock); |
2967 | if (bio_rw_flagged(bio, BIO_RW_SYNCIO)) | 2967 | if (bio->bi_rw & REQ_SYNC) |
2968 | pending_bios = &device->pending_sync_bios; | 2968 | pending_bios = &device->pending_sync_bios; |
2969 | else | 2969 | else |
2970 | pending_bios = &device->pending_bios; | 2970 | pending_bios = &device->pending_bios; |
diff --git a/fs/coda/psdev.c b/fs/coda/psdev.c index 66b9cf79c5ba..de89645777c7 100644 --- a/fs/coda/psdev.c +++ b/fs/coda/psdev.c | |||
@@ -177,7 +177,7 @@ static ssize_t coda_psdev_write(struct file *file, const char __user *buf, | |||
177 | nbytes = req->uc_outSize; /* don't have more space! */ | 177 | nbytes = req->uc_outSize; /* don't have more space! */ |
178 | } | 178 | } |
179 | if (copy_from_user(req->uc_data, buf, nbytes)) { | 179 | if (copy_from_user(req->uc_data, buf, nbytes)) { |
180 | req->uc_flags |= REQ_ABORT; | 180 | req->uc_flags |= CODA_REQ_ABORT; |
181 | wake_up(&req->uc_sleep); | 181 | wake_up(&req->uc_sleep); |
182 | retval = -EFAULT; | 182 | retval = -EFAULT; |
183 | goto out; | 183 | goto out; |
@@ -254,8 +254,8 @@ static ssize_t coda_psdev_read(struct file * file, char __user * buf, | |||
254 | retval = -EFAULT; | 254 | retval = -EFAULT; |
255 | 255 | ||
256 | /* If request was not a signal, enqueue and don't free */ | 256 | /* If request was not a signal, enqueue and don't free */ |
257 | if (!(req->uc_flags & REQ_ASYNC)) { | 257 | if (!(req->uc_flags & CODA_REQ_ASYNC)) { |
258 | req->uc_flags |= REQ_READ; | 258 | req->uc_flags |= CODA_REQ_READ; |
259 | list_add_tail(&(req->uc_chain), &vcp->vc_processing); | 259 | list_add_tail(&(req->uc_chain), &vcp->vc_processing); |
260 | goto out; | 260 | goto out; |
261 | } | 261 | } |
@@ -315,19 +315,19 @@ static int coda_psdev_release(struct inode * inode, struct file * file) | |||
315 | list_del(&req->uc_chain); | 315 | list_del(&req->uc_chain); |
316 | 316 | ||
317 | /* Async requests need to be freed here */ | 317 | /* Async requests need to be freed here */ |
318 | if (req->uc_flags & REQ_ASYNC) { | 318 | if (req->uc_flags & CODA_REQ_ASYNC) { |
319 | CODA_FREE(req->uc_data, sizeof(struct coda_in_hdr)); | 319 | CODA_FREE(req->uc_data, sizeof(struct coda_in_hdr)); |
320 | kfree(req); | 320 | kfree(req); |
321 | continue; | 321 | continue; |
322 | } | 322 | } |
323 | req->uc_flags |= REQ_ABORT; | 323 | req->uc_flags |= CODA_REQ_ABORT; |
324 | wake_up(&req->uc_sleep); | 324 | wake_up(&req->uc_sleep); |
325 | } | 325 | } |
326 | 326 | ||
327 | list_for_each_entry_safe(req, tmp, &vcp->vc_processing, uc_chain) { | 327 | list_for_each_entry_safe(req, tmp, &vcp->vc_processing, uc_chain) { |
328 | list_del(&req->uc_chain); | 328 | list_del(&req->uc_chain); |
329 | 329 | ||
330 | req->uc_flags |= REQ_ABORT; | 330 | req->uc_flags |= CODA_REQ_ABORT; |
331 | wake_up(&req->uc_sleep); | 331 | wake_up(&req->uc_sleep); |
332 | } | 332 | } |
333 | 333 | ||
diff --git a/fs/coda/upcall.c b/fs/coda/upcall.c index f09c5ed76f6c..b8893ab6f9e6 100644 --- a/fs/coda/upcall.c +++ b/fs/coda/upcall.c | |||
@@ -604,7 +604,7 @@ static void coda_unblock_signals(sigset_t *old) | |||
604 | (((r)->uc_opcode != CODA_CLOSE && \ | 604 | (((r)->uc_opcode != CODA_CLOSE && \ |
605 | (r)->uc_opcode != CODA_STORE && \ | 605 | (r)->uc_opcode != CODA_STORE && \ |
606 | (r)->uc_opcode != CODA_RELEASE) || \ | 606 | (r)->uc_opcode != CODA_RELEASE) || \ |
607 | (r)->uc_flags & REQ_READ)) | 607 | (r)->uc_flags & CODA_REQ_READ)) |
608 | 608 | ||
609 | static inline void coda_waitfor_upcall(struct upc_req *req) | 609 | static inline void coda_waitfor_upcall(struct upc_req *req) |
610 | { | 610 | { |
@@ -624,7 +624,7 @@ static inline void coda_waitfor_upcall(struct upc_req *req) | |||
624 | set_current_state(TASK_UNINTERRUPTIBLE); | 624 | set_current_state(TASK_UNINTERRUPTIBLE); |
625 | 625 | ||
626 | /* got a reply */ | 626 | /* got a reply */ |
627 | if (req->uc_flags & (REQ_WRITE | REQ_ABORT)) | 627 | if (req->uc_flags & (CODA_REQ_WRITE | CODA_REQ_ABORT)) |
628 | break; | 628 | break; |
629 | 629 | ||
630 | if (blocked && time_after(jiffies, timeout) && | 630 | if (blocked && time_after(jiffies, timeout) && |
@@ -708,7 +708,7 @@ static int coda_upcall(struct venus_comm *vcp, | |||
708 | coda_waitfor_upcall(req); | 708 | coda_waitfor_upcall(req); |
709 | 709 | ||
710 | /* Op went through, interrupt or not... */ | 710 | /* Op went through, interrupt or not... */ |
711 | if (req->uc_flags & REQ_WRITE) { | 711 | if (req->uc_flags & CODA_REQ_WRITE) { |
712 | out = (union outputArgs *)req->uc_data; | 712 | out = (union outputArgs *)req->uc_data; |
713 | /* here we map positive Venus errors to kernel errors */ | 713 | /* here we map positive Venus errors to kernel errors */ |
714 | error = -out->oh.result; | 714 | error = -out->oh.result; |
@@ -717,13 +717,13 @@ static int coda_upcall(struct venus_comm *vcp, | |||
717 | } | 717 | } |
718 | 718 | ||
719 | error = -EINTR; | 719 | error = -EINTR; |
720 | if ((req->uc_flags & REQ_ABORT) || !signal_pending(current)) { | 720 | if ((req->uc_flags & CODA_REQ_ABORT) || !signal_pending(current)) { |
721 | printk(KERN_WARNING "coda: Unexpected interruption.\n"); | 721 | printk(KERN_WARNING "coda: Unexpected interruption.\n"); |
722 | goto exit; | 722 | goto exit; |
723 | } | 723 | } |
724 | 724 | ||
725 | /* Interrupted before venus read it. */ | 725 | /* Interrupted before venus read it. */ |
726 | if (!(req->uc_flags & REQ_READ)) | 726 | if (!(req->uc_flags & CODA_REQ_READ)) |
727 | goto exit; | 727 | goto exit; |
728 | 728 | ||
729 | /* Venus saw the upcall, make sure we can send interrupt signal */ | 729 | /* Venus saw the upcall, make sure we can send interrupt signal */ |
@@ -747,7 +747,7 @@ static int coda_upcall(struct venus_comm *vcp, | |||
747 | sig_inputArgs->ih.opcode = CODA_SIGNAL; | 747 | sig_inputArgs->ih.opcode = CODA_SIGNAL; |
748 | sig_inputArgs->ih.unique = req->uc_unique; | 748 | sig_inputArgs->ih.unique = req->uc_unique; |
749 | 749 | ||
750 | sig_req->uc_flags = REQ_ASYNC; | 750 | sig_req->uc_flags = CODA_REQ_ASYNC; |
751 | sig_req->uc_opcode = sig_inputArgs->ih.opcode; | 751 | sig_req->uc_opcode = sig_inputArgs->ih.opcode; |
752 | sig_req->uc_unique = sig_inputArgs->ih.unique; | 752 | sig_req->uc_unique = sig_inputArgs->ih.unique; |
753 | sig_req->uc_inSize = sizeof(struct coda_in_hdr); | 753 | sig_req->uc_inSize = sizeof(struct coda_in_hdr); |
diff --git a/fs/exofs/ios.c b/fs/exofs/ios.c index 4337cad7777b..e2732203fa93 100644 --- a/fs/exofs/ios.c +++ b/fs/exofs/ios.c | |||
@@ -599,7 +599,7 @@ static int _sbi_write_mirror(struct exofs_io_state *ios, int cur_comp) | |||
599 | } else { | 599 | } else { |
600 | bio = master_dev->bio; | 600 | bio = master_dev->bio; |
601 | /* FIXME: bio_set_dir() */ | 601 | /* FIXME: bio_set_dir() */ |
602 | bio->bi_rw |= (1 << BIO_RW); | 602 | bio->bi_rw |= REQ_WRITE; |
603 | } | 603 | } |
604 | 604 | ||
605 | osd_req_write(or, &ios->obj, per_dev->offset, bio, | 605 | osd_req_write(or, &ios->obj, per_dev->offset, bio, |
diff --git a/fs/fs-writeback.c b/fs/fs-writeback.c index b7c7586caea1..2f76c4a081a2 100644 --- a/fs/fs-writeback.c +++ b/fs/fs-writeback.c | |||
@@ -26,15 +26,9 @@ | |||
26 | #include <linux/blkdev.h> | 26 | #include <linux/blkdev.h> |
27 | #include <linux/backing-dev.h> | 27 | #include <linux/backing-dev.h> |
28 | #include <linux/buffer_head.h> | 28 | #include <linux/buffer_head.h> |
29 | #include <linux/tracepoint.h> | ||
29 | #include "internal.h" | 30 | #include "internal.h" |
30 | 31 | ||
31 | #define inode_to_bdi(inode) ((inode)->i_mapping->backing_dev_info) | ||
32 | |||
33 | /* | ||
34 | * We don't actually have pdflush, but this one is exported though /proc... | ||
35 | */ | ||
36 | int nr_pdflush_threads; | ||
37 | |||
38 | /* | 32 | /* |
39 | * Passed into wb_writeback(), essentially a subset of writeback_control | 33 | * Passed into wb_writeback(), essentially a subset of writeback_control |
40 | */ | 34 | */ |
@@ -50,6 +44,21 @@ struct wb_writeback_work { | |||
50 | struct completion *done; /* set if the caller waits */ | 44 | struct completion *done; /* set if the caller waits */ |
51 | }; | 45 | }; |
52 | 46 | ||
47 | /* | ||
48 | * Include the creation of the trace points after defining the | ||
49 | * wb_writeback_work structure so that the definition remains local to this | ||
50 | * file. | ||
51 | */ | ||
52 | #define CREATE_TRACE_POINTS | ||
53 | #include <trace/events/writeback.h> | ||
54 | |||
55 | #define inode_to_bdi(inode) ((inode)->i_mapping->backing_dev_info) | ||
56 | |||
57 | /* | ||
58 | * We don't actually have pdflush, but this one is exported though /proc... | ||
59 | */ | ||
60 | int nr_pdflush_threads; | ||
61 | |||
53 | /** | 62 | /** |
54 | * writeback_in_progress - determine whether there is writeback in progress | 63 | * writeback_in_progress - determine whether there is writeback in progress |
55 | * @bdi: the device's backing_dev_info structure. | 64 | * @bdi: the device's backing_dev_info structure. |
@@ -65,22 +74,21 @@ int writeback_in_progress(struct backing_dev_info *bdi) | |||
65 | static void bdi_queue_work(struct backing_dev_info *bdi, | 74 | static void bdi_queue_work(struct backing_dev_info *bdi, |
66 | struct wb_writeback_work *work) | 75 | struct wb_writeback_work *work) |
67 | { | 76 | { |
68 | spin_lock(&bdi->wb_lock); | 77 | trace_writeback_queue(bdi, work); |
69 | list_add_tail(&work->list, &bdi->work_list); | ||
70 | spin_unlock(&bdi->wb_lock); | ||
71 | 78 | ||
72 | /* | 79 | spin_lock_bh(&bdi->wb_lock); |
73 | * If the default thread isn't there, make sure we add it. When | 80 | list_add_tail(&work->list, &bdi->work_list); |
74 | * it gets created and wakes up, we'll run this work. | 81 | if (bdi->wb.task) { |
75 | */ | 82 | wake_up_process(bdi->wb.task); |
76 | if (unlikely(list_empty_careful(&bdi->wb_list))) | 83 | } else { |
84 | /* | ||
85 | * The bdi thread isn't there, wake up the forker thread which | ||
86 | * will create and run it. | ||
87 | */ | ||
88 | trace_writeback_nothread(bdi, work); | ||
77 | wake_up_process(default_backing_dev_info.wb.task); | 89 | wake_up_process(default_backing_dev_info.wb.task); |
78 | else { | ||
79 | struct bdi_writeback *wb = &bdi->wb; | ||
80 | |||
81 | if (wb->task) | ||
82 | wake_up_process(wb->task); | ||
83 | } | 90 | } |
91 | spin_unlock_bh(&bdi->wb_lock); | ||
84 | } | 92 | } |
85 | 93 | ||
86 | static void | 94 | static void |
@@ -95,8 +103,10 @@ __bdi_start_writeback(struct backing_dev_info *bdi, long nr_pages, | |||
95 | */ | 103 | */ |
96 | work = kzalloc(sizeof(*work), GFP_ATOMIC); | 104 | work = kzalloc(sizeof(*work), GFP_ATOMIC); |
97 | if (!work) { | 105 | if (!work) { |
98 | if (bdi->wb.task) | 106 | if (bdi->wb.task) { |
107 | trace_writeback_nowork(bdi); | ||
99 | wake_up_process(bdi->wb.task); | 108 | wake_up_process(bdi->wb.task); |
109 | } | ||
100 | return; | 110 | return; |
101 | } | 111 | } |
102 | 112 | ||
@@ -643,10 +653,14 @@ static long wb_writeback(struct bdi_writeback *wb, | |||
643 | wbc.more_io = 0; | 653 | wbc.more_io = 0; |
644 | wbc.nr_to_write = MAX_WRITEBACK_PAGES; | 654 | wbc.nr_to_write = MAX_WRITEBACK_PAGES; |
645 | wbc.pages_skipped = 0; | 655 | wbc.pages_skipped = 0; |
656 | |||
657 | trace_wbc_writeback_start(&wbc, wb->bdi); | ||
646 | if (work->sb) | 658 | if (work->sb) |
647 | __writeback_inodes_sb(work->sb, wb, &wbc); | 659 | __writeback_inodes_sb(work->sb, wb, &wbc); |
648 | else | 660 | else |
649 | writeback_inodes_wb(wb, &wbc); | 661 | writeback_inodes_wb(wb, &wbc); |
662 | trace_wbc_writeback_written(&wbc, wb->bdi); | ||
663 | |||
650 | work->nr_pages -= MAX_WRITEBACK_PAGES - wbc.nr_to_write; | 664 | work->nr_pages -= MAX_WRITEBACK_PAGES - wbc.nr_to_write; |
651 | wrote += MAX_WRITEBACK_PAGES - wbc.nr_to_write; | 665 | wrote += MAX_WRITEBACK_PAGES - wbc.nr_to_write; |
652 | 666 | ||
@@ -674,6 +688,7 @@ static long wb_writeback(struct bdi_writeback *wb, | |||
674 | if (!list_empty(&wb->b_more_io)) { | 688 | if (!list_empty(&wb->b_more_io)) { |
675 | inode = list_entry(wb->b_more_io.prev, | 689 | inode = list_entry(wb->b_more_io.prev, |
676 | struct inode, i_list); | 690 | struct inode, i_list); |
691 | trace_wbc_writeback_wait(&wbc, wb->bdi); | ||
677 | inode_wait_for_writeback(inode); | 692 | inode_wait_for_writeback(inode); |
678 | } | 693 | } |
679 | spin_unlock(&inode_lock); | 694 | spin_unlock(&inode_lock); |
@@ -686,17 +701,17 @@ static long wb_writeback(struct bdi_writeback *wb, | |||
686 | * Return the next wb_writeback_work struct that hasn't been processed yet. | 701 | * Return the next wb_writeback_work struct that hasn't been processed yet. |
687 | */ | 702 | */ |
688 | static struct wb_writeback_work * | 703 | static struct wb_writeback_work * |
689 | get_next_work_item(struct backing_dev_info *bdi, struct bdi_writeback *wb) | 704 | get_next_work_item(struct backing_dev_info *bdi) |
690 | { | 705 | { |
691 | struct wb_writeback_work *work = NULL; | 706 | struct wb_writeback_work *work = NULL; |
692 | 707 | ||
693 | spin_lock(&bdi->wb_lock); | 708 | spin_lock_bh(&bdi->wb_lock); |
694 | if (!list_empty(&bdi->work_list)) { | 709 | if (!list_empty(&bdi->work_list)) { |
695 | work = list_entry(bdi->work_list.next, | 710 | work = list_entry(bdi->work_list.next, |
696 | struct wb_writeback_work, list); | 711 | struct wb_writeback_work, list); |
697 | list_del_init(&work->list); | 712 | list_del_init(&work->list); |
698 | } | 713 | } |
699 | spin_unlock(&bdi->wb_lock); | 714 | spin_unlock_bh(&bdi->wb_lock); |
700 | return work; | 715 | return work; |
701 | } | 716 | } |
702 | 717 | ||
@@ -744,7 +759,7 @@ long wb_do_writeback(struct bdi_writeback *wb, int force_wait) | |||
744 | struct wb_writeback_work *work; | 759 | struct wb_writeback_work *work; |
745 | long wrote = 0; | 760 | long wrote = 0; |
746 | 761 | ||
747 | while ((work = get_next_work_item(bdi, wb)) != NULL) { | 762 | while ((work = get_next_work_item(bdi)) != NULL) { |
748 | /* | 763 | /* |
749 | * Override sync mode, in case we must wait for completion | 764 | * Override sync mode, in case we must wait for completion |
750 | * because this thread is exiting now. | 765 | * because this thread is exiting now. |
@@ -752,6 +767,8 @@ long wb_do_writeback(struct bdi_writeback *wb, int force_wait) | |||
752 | if (force_wait) | 767 | if (force_wait) |
753 | work->sync_mode = WB_SYNC_ALL; | 768 | work->sync_mode = WB_SYNC_ALL; |
754 | 769 | ||
770 | trace_writeback_exec(bdi, work); | ||
771 | |||
755 | wrote += wb_writeback(wb, work); | 772 | wrote += wb_writeback(wb, work); |
756 | 773 | ||
757 | /* | 774 | /* |
@@ -776,47 +793,66 @@ long wb_do_writeback(struct bdi_writeback *wb, int force_wait) | |||
776 | * Handle writeback of dirty data for the device backed by this bdi. Also | 793 | * Handle writeback of dirty data for the device backed by this bdi. Also |
777 | * wakes up periodically and does kupdated style flushing. | 794 | * wakes up periodically and does kupdated style flushing. |
778 | */ | 795 | */ |
779 | int bdi_writeback_task(struct bdi_writeback *wb) | 796 | int bdi_writeback_thread(void *data) |
780 | { | 797 | { |
781 | unsigned long last_active = jiffies; | 798 | struct bdi_writeback *wb = data; |
782 | unsigned long wait_jiffies = -1UL; | 799 | struct backing_dev_info *bdi = wb->bdi; |
783 | long pages_written; | 800 | long pages_written; |
784 | 801 | ||
802 | current->flags |= PF_FLUSHER | PF_SWAPWRITE; | ||
803 | set_freezable(); | ||
804 | wb->last_active = jiffies; | ||
805 | |||
806 | /* | ||
807 | * Our parent may run at a different priority, just set us to normal | ||
808 | */ | ||
809 | set_user_nice(current, 0); | ||
810 | |||
811 | trace_writeback_thread_start(bdi); | ||
812 | |||
785 | while (!kthread_should_stop()) { | 813 | while (!kthread_should_stop()) { |
814 | /* | ||
815 | * Remove own delayed wake-up timer, since we are already awake | ||
816 | * and we'll take care of the preriodic write-back. | ||
817 | */ | ||
818 | del_timer(&wb->wakeup_timer); | ||
819 | |||
786 | pages_written = wb_do_writeback(wb, 0); | 820 | pages_written = wb_do_writeback(wb, 0); |
787 | 821 | ||
822 | trace_writeback_pages_written(pages_written); | ||
823 | |||
788 | if (pages_written) | 824 | if (pages_written) |
789 | last_active = jiffies; | 825 | wb->last_active = jiffies; |
790 | else if (wait_jiffies != -1UL) { | ||
791 | unsigned long max_idle; | ||
792 | 826 | ||
793 | /* | 827 | set_current_state(TASK_INTERRUPTIBLE); |
794 | * Longest period of inactivity that we tolerate. If we | 828 | if (!list_empty(&bdi->work_list)) { |
795 | * see dirty data again later, the task will get | 829 | __set_current_state(TASK_RUNNING); |
796 | * recreated automatically. | 830 | continue; |
797 | */ | ||
798 | max_idle = max(5UL * 60 * HZ, wait_jiffies); | ||
799 | if (time_after(jiffies, max_idle + last_active)) | ||
800 | break; | ||
801 | } | 831 | } |
802 | 832 | ||
803 | if (dirty_writeback_interval) { | 833 | if (wb_has_dirty_io(wb) && dirty_writeback_interval) |
804 | wait_jiffies = msecs_to_jiffies(dirty_writeback_interval * 10); | 834 | schedule_timeout(msecs_to_jiffies(dirty_writeback_interval * 10)); |
805 | schedule_timeout_interruptible(wait_jiffies); | 835 | else { |
806 | } else { | 836 | /* |
807 | set_current_state(TASK_INTERRUPTIBLE); | 837 | * We have nothing to do, so can go sleep without any |
808 | if (list_empty_careful(&wb->bdi->work_list) && | 838 | * timeout and save power. When a work is queued or |
809 | !kthread_should_stop()) | 839 | * something is made dirty - we will be woken up. |
810 | schedule(); | 840 | */ |
811 | __set_current_state(TASK_RUNNING); | 841 | schedule(); |
812 | } | 842 | } |
813 | 843 | ||
814 | try_to_freeze(); | 844 | try_to_freeze(); |
815 | } | 845 | } |
816 | 846 | ||
847 | /* Flush any work that raced with us exiting */ | ||
848 | if (!list_empty(&bdi->work_list)) | ||
849 | wb_do_writeback(wb, 1); | ||
850 | |||
851 | trace_writeback_thread_stop(bdi); | ||
817 | return 0; | 852 | return 0; |
818 | } | 853 | } |
819 | 854 | ||
855 | |||
820 | /* | 856 | /* |
821 | * Start writeback of `nr_pages' pages. If `nr_pages' is zero, write back | 857 | * Start writeback of `nr_pages' pages. If `nr_pages' is zero, write back |
822 | * the whole world. | 858 | * the whole world. |
@@ -891,6 +927,8 @@ static noinline void block_dump___mark_inode_dirty(struct inode *inode) | |||
891 | void __mark_inode_dirty(struct inode *inode, int flags) | 927 | void __mark_inode_dirty(struct inode *inode, int flags) |
892 | { | 928 | { |
893 | struct super_block *sb = inode->i_sb; | 929 | struct super_block *sb = inode->i_sb; |
930 | struct backing_dev_info *bdi = NULL; | ||
931 | bool wakeup_bdi = false; | ||
894 | 932 | ||
895 | /* | 933 | /* |
896 | * Don't do this for I_DIRTY_PAGES - that doesn't actually | 934 | * Don't do this for I_DIRTY_PAGES - that doesn't actually |
@@ -944,22 +982,31 @@ void __mark_inode_dirty(struct inode *inode, int flags) | |||
944 | * reposition it (that would break b_dirty time-ordering). | 982 | * reposition it (that would break b_dirty time-ordering). |
945 | */ | 983 | */ |
946 | if (!was_dirty) { | 984 | if (!was_dirty) { |
947 | struct bdi_writeback *wb = &inode_to_bdi(inode)->wb; | 985 | bdi = inode_to_bdi(inode); |
948 | struct backing_dev_info *bdi = wb->bdi; | 986 | |
949 | 987 | if (bdi_cap_writeback_dirty(bdi)) { | |
950 | if (bdi_cap_writeback_dirty(bdi) && | 988 | WARN(!test_bit(BDI_registered, &bdi->state), |
951 | !test_bit(BDI_registered, &bdi->state)) { | 989 | "bdi-%s not registered\n", bdi->name); |
952 | WARN_ON(1); | 990 | |
953 | printk(KERN_ERR "bdi-%s not registered\n", | 991 | /* |
954 | bdi->name); | 992 | * If this is the first dirty inode for this |
993 | * bdi, we have to wake-up the corresponding | ||
994 | * bdi thread to make sure background | ||
995 | * write-back happens later. | ||
996 | */ | ||
997 | if (!wb_has_dirty_io(&bdi->wb)) | ||
998 | wakeup_bdi = true; | ||
955 | } | 999 | } |
956 | 1000 | ||
957 | inode->dirtied_when = jiffies; | 1001 | inode->dirtied_when = jiffies; |
958 | list_move(&inode->i_list, &wb->b_dirty); | 1002 | list_move(&inode->i_list, &bdi->wb.b_dirty); |
959 | } | 1003 | } |
960 | } | 1004 | } |
961 | out: | 1005 | out: |
962 | spin_unlock(&inode_lock); | 1006 | spin_unlock(&inode_lock); |
1007 | |||
1008 | if (wakeup_bdi) | ||
1009 | bdi_wakeup_thread_delayed(bdi); | ||
963 | } | 1010 | } |
964 | EXPORT_SYMBOL(__mark_inode_dirty); | 1011 | EXPORT_SYMBOL(__mark_inode_dirty); |
965 | 1012 | ||
diff --git a/fs/gfs2/log.c b/fs/gfs2/log.c index 6a857e24f947..cde1248a6225 100644 --- a/fs/gfs2/log.c +++ b/fs/gfs2/log.c | |||
@@ -595,7 +595,7 @@ static void log_write_header(struct gfs2_sbd *sdp, u32 flags, int pull) | |||
595 | if (test_bit(SDF_NOBARRIERS, &sdp->sd_flags)) | 595 | if (test_bit(SDF_NOBARRIERS, &sdp->sd_flags)) |
596 | goto skip_barrier; | 596 | goto skip_barrier; |
597 | get_bh(bh); | 597 | get_bh(bh); |
598 | submit_bh(WRITE_SYNC | (1 << BIO_RW_BARRIER) | (1 << BIO_RW_META), bh); | 598 | submit_bh(WRITE_BARRIER | REQ_META, bh); |
599 | wait_on_buffer(bh); | 599 | wait_on_buffer(bh); |
600 | if (buffer_eopnotsupp(bh)) { | 600 | if (buffer_eopnotsupp(bh)) { |
601 | clear_buffer_eopnotsupp(bh); | 601 | clear_buffer_eopnotsupp(bh); |
@@ -605,7 +605,7 @@ static void log_write_header(struct gfs2_sbd *sdp, u32 flags, int pull) | |||
605 | lock_buffer(bh); | 605 | lock_buffer(bh); |
606 | skip_barrier: | 606 | skip_barrier: |
607 | get_bh(bh); | 607 | get_bh(bh); |
608 | submit_bh(WRITE_SYNC | (1 << BIO_RW_META), bh); | 608 | submit_bh(WRITE_SYNC | REQ_META, bh); |
609 | wait_on_buffer(bh); | 609 | wait_on_buffer(bh); |
610 | } | 610 | } |
611 | if (!buffer_uptodate(bh)) | 611 | if (!buffer_uptodate(bh)) |
diff --git a/fs/gfs2/meta_io.c b/fs/gfs2/meta_io.c index 18176d0b75d7..f3b071f921aa 100644 --- a/fs/gfs2/meta_io.c +++ b/fs/gfs2/meta_io.c | |||
@@ -36,8 +36,8 @@ static int gfs2_aspace_writepage(struct page *page, struct writeback_control *wb | |||
36 | { | 36 | { |
37 | struct buffer_head *bh, *head; | 37 | struct buffer_head *bh, *head; |
38 | int nr_underway = 0; | 38 | int nr_underway = 0; |
39 | int write_op = (1 << BIO_RW_META) | ((wbc->sync_mode == WB_SYNC_ALL ? | 39 | int write_op = REQ_META | |
40 | WRITE_SYNC_PLUG : WRITE)); | 40 | (wbc->sync_mode == WB_SYNC_ALL ? WRITE_SYNC_PLUG : WRITE); |
41 | 41 | ||
42 | BUG_ON(!PageLocked(page)); | 42 | BUG_ON(!PageLocked(page)); |
43 | BUG_ON(!page_has_buffers(page)); | 43 | BUG_ON(!page_has_buffers(page)); |
@@ -225,7 +225,7 @@ int gfs2_meta_read(struct gfs2_glock *gl, u64 blkno, int flags, | |||
225 | } | 225 | } |
226 | bh->b_end_io = end_buffer_read_sync; | 226 | bh->b_end_io = end_buffer_read_sync; |
227 | get_bh(bh); | 227 | get_bh(bh); |
228 | submit_bh(READ_SYNC | (1 << BIO_RW_META), bh); | 228 | submit_bh(READ_SYNC | REQ_META, bh); |
229 | if (!(flags & DIO_WAIT)) | 229 | if (!(flags & DIO_WAIT)) |
230 | return 0; | 230 | return 0; |
231 | 231 | ||
@@ -432,7 +432,7 @@ struct buffer_head *gfs2_meta_ra(struct gfs2_glock *gl, u64 dblock, u32 extlen) | |||
432 | if (buffer_uptodate(first_bh)) | 432 | if (buffer_uptodate(first_bh)) |
433 | goto out; | 433 | goto out; |
434 | if (!buffer_locked(first_bh)) | 434 | if (!buffer_locked(first_bh)) |
435 | ll_rw_block(READ_SYNC | (1 << BIO_RW_META), 1, &first_bh); | 435 | ll_rw_block(READ_SYNC | REQ_META, 1, &first_bh); |
436 | 436 | ||
437 | dblock++; | 437 | dblock++; |
438 | extlen--; | 438 | extlen--; |
diff --git a/fs/gfs2/ops_fstype.c b/fs/gfs2/ops_fstype.c index 4f44bdeb2f03..4d4b1e8ac64c 100644 --- a/fs/gfs2/ops_fstype.c +++ b/fs/gfs2/ops_fstype.c | |||
@@ -274,7 +274,7 @@ static int gfs2_read_super(struct gfs2_sbd *sdp, sector_t sector) | |||
274 | 274 | ||
275 | bio->bi_end_io = end_bio_io_page; | 275 | bio->bi_end_io = end_bio_io_page; |
276 | bio->bi_private = page; | 276 | bio->bi_private = page; |
277 | submit_bio(READ_SYNC | (1 << BIO_RW_META), bio); | 277 | submit_bio(READ_SYNC | REQ_META, bio); |
278 | wait_on_page_locked(page); | 278 | wait_on_page_locked(page); |
279 | bio_put(bio); | 279 | bio_put(bio); |
280 | if (!PageUptodate(page)) { | 280 | if (!PageUptodate(page)) { |
diff --git a/fs/nilfs2/segbuf.c b/fs/nilfs2/segbuf.c index 2e6a2723b8fa..4588fb9e93df 100644 --- a/fs/nilfs2/segbuf.c +++ b/fs/nilfs2/segbuf.c | |||
@@ -508,7 +508,7 @@ static int nilfs_segbuf_write(struct nilfs_segment_buffer *segbuf, | |||
508 | * Last BIO is always sent through the following | 508 | * Last BIO is always sent through the following |
509 | * submission. | 509 | * submission. |
510 | */ | 510 | */ |
511 | rw |= (1 << BIO_RW_SYNCIO) | (1 << BIO_RW_UNPLUG); | 511 | rw |= REQ_SYNC | REQ_UNPLUG; |
512 | res = nilfs_segbuf_submit_bio(segbuf, &wi, rw); | 512 | res = nilfs_segbuf_submit_bio(segbuf, &wi, rw); |
513 | } | 513 | } |
514 | 514 | ||
diff --git a/fs/splice.c b/fs/splice.c index efdbfece9932..8f1dfaecc8f0 100644 --- a/fs/splice.c +++ b/fs/splice.c | |||
@@ -399,17 +399,7 @@ __generic_file_splice_read(struct file *in, loff_t *ppos, | |||
399 | * If the page isn't uptodate, we may need to start io on it | 399 | * If the page isn't uptodate, we may need to start io on it |
400 | */ | 400 | */ |
401 | if (!PageUptodate(page)) { | 401 | if (!PageUptodate(page)) { |
402 | /* | 402 | lock_page(page); |
403 | * If in nonblock mode then dont block on waiting | ||
404 | * for an in-flight io page | ||
405 | */ | ||
406 | if (flags & SPLICE_F_NONBLOCK) { | ||
407 | if (!trylock_page(page)) { | ||
408 | error = -EAGAIN; | ||
409 | break; | ||
410 | } | ||
411 | } else | ||
412 | lock_page(page); | ||
413 | 403 | ||
414 | /* | 404 | /* |
415 | * Page was truncated, or invalidated by the | 405 | * Page was truncated, or invalidated by the |
@@ -597,7 +587,6 @@ ssize_t default_file_splice_read(struct file *in, loff_t *ppos, | |||
597 | struct page *pages[PIPE_DEF_BUFFERS]; | 587 | struct page *pages[PIPE_DEF_BUFFERS]; |
598 | struct partial_page partial[PIPE_DEF_BUFFERS]; | 588 | struct partial_page partial[PIPE_DEF_BUFFERS]; |
599 | struct iovec *vec, __vec[PIPE_DEF_BUFFERS]; | 589 | struct iovec *vec, __vec[PIPE_DEF_BUFFERS]; |
600 | pgoff_t index; | ||
601 | ssize_t res; | 590 | ssize_t res; |
602 | size_t this_len; | 591 | size_t this_len; |
603 | int error; | 592 | int error; |
@@ -621,7 +610,6 @@ ssize_t default_file_splice_read(struct file *in, loff_t *ppos, | |||
621 | goto shrink_ret; | 610 | goto shrink_ret; |
622 | } | 611 | } |
623 | 612 | ||
624 | index = *ppos >> PAGE_CACHE_SHIFT; | ||
625 | offset = *ppos & ~PAGE_CACHE_MASK; | 613 | offset = *ppos & ~PAGE_CACHE_MASK; |
626 | nr_pages = (len + offset + PAGE_CACHE_SIZE - 1) >> PAGE_CACHE_SHIFT; | 614 | nr_pages = (len + offset + PAGE_CACHE_SIZE - 1) >> PAGE_CACHE_SHIFT; |
627 | 615 | ||
diff --git a/include/linux/Kbuild b/include/linux/Kbuild index 2547daf2aef2..9d65d4d0bd9c 100644 --- a/include/linux/Kbuild +++ b/include/linux/Kbuild | |||
@@ -39,6 +39,7 @@ header-y += ax25.h | |||
39 | header-y += b1lli.h | 39 | header-y += b1lli.h |
40 | header-y += baycom.h | 40 | header-y += baycom.h |
41 | header-y += bfs_fs.h | 41 | header-y += bfs_fs.h |
42 | header-y += blk_types.h | ||
42 | header-y += blkpg.h | 43 | header-y += blkpg.h |
43 | header-y += bpqether.h | 44 | header-y += bpqether.h |
44 | header-y += bsg.h | 45 | header-y += bsg.h |
diff --git a/include/linux/audit.h b/include/linux/audit.h index f391d45c8aea..e24afabc548f 100644 --- a/include/linux/audit.h +++ b/include/linux/audit.h | |||
@@ -544,7 +544,7 @@ extern int audit_signals; | |||
544 | #define audit_putname(n) do { ; } while (0) | 544 | #define audit_putname(n) do { ; } while (0) |
545 | #define __audit_inode(n,d) do { ; } while (0) | 545 | #define __audit_inode(n,d) do { ; } while (0) |
546 | #define __audit_inode_child(i,p) do { ; } while (0) | 546 | #define __audit_inode_child(i,p) do { ; } while (0) |
547 | #define audit_inode(n,d) do { ; } while (0) | 547 | #define audit_inode(n,d) do { (void)(d); } while (0) |
548 | #define audit_inode_child(i,p) do { ; } while (0) | 548 | #define audit_inode_child(i,p) do { ; } while (0) |
549 | #define audit_core_dumps(i) do { ; } while (0) | 549 | #define audit_core_dumps(i) do { ; } while (0) |
550 | #define auditsc_get_stamp(c,t,s) (0) | 550 | #define auditsc_get_stamp(c,t,s) (0) |
diff --git a/include/linux/backing-dev.h b/include/linux/backing-dev.h index e9aec0d099df..7628219e5386 100644 --- a/include/linux/backing-dev.h +++ b/include/linux/backing-dev.h | |||
@@ -45,22 +45,21 @@ enum bdi_stat_item { | |||
45 | #define BDI_STAT_BATCH (8*(1+ilog2(nr_cpu_ids))) | 45 | #define BDI_STAT_BATCH (8*(1+ilog2(nr_cpu_ids))) |
46 | 46 | ||
47 | struct bdi_writeback { | 47 | struct bdi_writeback { |
48 | struct list_head list; /* hangs off the bdi */ | 48 | struct backing_dev_info *bdi; /* our parent bdi */ |
49 | |||
50 | struct backing_dev_info *bdi; /* our parent bdi */ | ||
51 | unsigned int nr; | 49 | unsigned int nr; |
52 | 50 | ||
53 | unsigned long last_old_flush; /* last old data flush */ | 51 | unsigned long last_old_flush; /* last old data flush */ |
52 | unsigned long last_active; /* last time bdi thread was active */ | ||
54 | 53 | ||
55 | struct task_struct *task; /* writeback task */ | 54 | struct task_struct *task; /* writeback thread */ |
56 | struct list_head b_dirty; /* dirty inodes */ | 55 | struct timer_list wakeup_timer; /* used for delayed bdi thread wakeup */ |
57 | struct list_head b_io; /* parked for writeback */ | 56 | struct list_head b_dirty; /* dirty inodes */ |
58 | struct list_head b_more_io; /* parked for more writeback */ | 57 | struct list_head b_io; /* parked for writeback */ |
58 | struct list_head b_more_io; /* parked for more writeback */ | ||
59 | }; | 59 | }; |
60 | 60 | ||
61 | struct backing_dev_info { | 61 | struct backing_dev_info { |
62 | struct list_head bdi_list; | 62 | struct list_head bdi_list; |
63 | struct rcu_head rcu_head; | ||
64 | unsigned long ra_pages; /* max readahead in PAGE_CACHE_SIZE units */ | 63 | unsigned long ra_pages; /* max readahead in PAGE_CACHE_SIZE units */ |
65 | unsigned long state; /* Always use atomic bitops on this */ | 64 | unsigned long state; /* Always use atomic bitops on this */ |
66 | unsigned int capabilities; /* Device capabilities */ | 65 | unsigned int capabilities; /* Device capabilities */ |
@@ -80,8 +79,7 @@ struct backing_dev_info { | |||
80 | unsigned int max_ratio, max_prop_frac; | 79 | unsigned int max_ratio, max_prop_frac; |
81 | 80 | ||
82 | struct bdi_writeback wb; /* default writeback info for this bdi */ | 81 | struct bdi_writeback wb; /* default writeback info for this bdi */ |
83 | spinlock_t wb_lock; /* protects update side of wb_list */ | 82 | spinlock_t wb_lock; /* protects work_list */ |
84 | struct list_head wb_list; /* the flusher threads hanging off this bdi */ | ||
85 | 83 | ||
86 | struct list_head work_list; | 84 | struct list_head work_list; |
87 | 85 | ||
@@ -105,9 +103,10 @@ void bdi_unregister(struct backing_dev_info *bdi); | |||
105 | int bdi_setup_and_register(struct backing_dev_info *, char *, unsigned int); | 103 | int bdi_setup_and_register(struct backing_dev_info *, char *, unsigned int); |
106 | void bdi_start_writeback(struct backing_dev_info *bdi, long nr_pages); | 104 | void bdi_start_writeback(struct backing_dev_info *bdi, long nr_pages); |
107 | void bdi_start_background_writeback(struct backing_dev_info *bdi); | 105 | void bdi_start_background_writeback(struct backing_dev_info *bdi); |
108 | int bdi_writeback_task(struct bdi_writeback *wb); | 106 | int bdi_writeback_thread(void *data); |
109 | int bdi_has_dirty_io(struct backing_dev_info *bdi); | 107 | int bdi_has_dirty_io(struct backing_dev_info *bdi); |
110 | void bdi_arm_supers_timer(void); | 108 | void bdi_arm_supers_timer(void); |
109 | void bdi_wakeup_thread_delayed(struct backing_dev_info *bdi); | ||
111 | 110 | ||
112 | extern spinlock_t bdi_lock; | 111 | extern spinlock_t bdi_lock; |
113 | extern struct list_head bdi_list; | 112 | extern struct list_head bdi_list; |
diff --git a/include/linux/bio.h b/include/linux/bio.h index 7fc5606e6ea5..5274103434ad 100644 --- a/include/linux/bio.h +++ b/include/linux/bio.h | |||
@@ -9,7 +9,7 @@ | |||
9 | * | 9 | * |
10 | * This program is distributed in the hope that it will be useful, | 10 | * This program is distributed in the hope that it will be useful, |
11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of |
12 | 12 | * | |
13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
14 | * GNU General Public License for more details. | 14 | * GNU General Public License for more details. |
15 | * | 15 | * |
@@ -28,6 +28,9 @@ | |||
28 | 28 | ||
29 | #include <asm/io.h> | 29 | #include <asm/io.h> |
30 | 30 | ||
31 | /* struct bio, bio_vec and BIO_* flags are defined in blk_types.h */ | ||
32 | #include <linux/blk_types.h> | ||
33 | |||
31 | #define BIO_DEBUG | 34 | #define BIO_DEBUG |
32 | 35 | ||
33 | #ifdef BIO_DEBUG | 36 | #ifdef BIO_DEBUG |
@@ -41,154 +44,6 @@ | |||
41 | #define BIO_MAX_SECTORS (BIO_MAX_SIZE >> 9) | 44 | #define BIO_MAX_SECTORS (BIO_MAX_SIZE >> 9) |
42 | 45 | ||
43 | /* | 46 | /* |
44 | * was unsigned short, but we might as well be ready for > 64kB I/O pages | ||
45 | */ | ||
46 | struct bio_vec { | ||
47 | struct page *bv_page; | ||
48 | unsigned int bv_len; | ||
49 | unsigned int bv_offset; | ||
50 | }; | ||
51 | |||
52 | struct bio_set; | ||
53 | struct bio; | ||
54 | struct bio_integrity_payload; | ||
55 | typedef void (bio_end_io_t) (struct bio *, int); | ||
56 | typedef void (bio_destructor_t) (struct bio *); | ||
57 | |||
58 | /* | ||
59 | * main unit of I/O for the block layer and lower layers (ie drivers and | ||
60 | * stacking drivers) | ||
61 | */ | ||
62 | struct bio { | ||
63 | sector_t bi_sector; /* device address in 512 byte | ||
64 | sectors */ | ||
65 | struct bio *bi_next; /* request queue link */ | ||
66 | struct block_device *bi_bdev; | ||
67 | unsigned long bi_flags; /* status, command, etc */ | ||
68 | unsigned long bi_rw; /* bottom bits READ/WRITE, | ||
69 | * top bits priority | ||
70 | */ | ||
71 | |||
72 | unsigned short bi_vcnt; /* how many bio_vec's */ | ||
73 | unsigned short bi_idx; /* current index into bvl_vec */ | ||
74 | |||
75 | /* Number of segments in this BIO after | ||
76 | * physical address coalescing is performed. | ||
77 | */ | ||
78 | unsigned int bi_phys_segments; | ||
79 | |||
80 | unsigned int bi_size; /* residual I/O count */ | ||
81 | |||
82 | /* | ||
83 | * To keep track of the max segment size, we account for the | ||
84 | * sizes of the first and last mergeable segments in this bio. | ||
85 | */ | ||
86 | unsigned int bi_seg_front_size; | ||
87 | unsigned int bi_seg_back_size; | ||
88 | |||
89 | unsigned int bi_max_vecs; /* max bvl_vecs we can hold */ | ||
90 | |||
91 | unsigned int bi_comp_cpu; /* completion CPU */ | ||
92 | |||
93 | atomic_t bi_cnt; /* pin count */ | ||
94 | |||
95 | struct bio_vec *bi_io_vec; /* the actual vec list */ | ||
96 | |||
97 | bio_end_io_t *bi_end_io; | ||
98 | |||
99 | void *bi_private; | ||
100 | #if defined(CONFIG_BLK_DEV_INTEGRITY) | ||
101 | struct bio_integrity_payload *bi_integrity; /* data integrity */ | ||
102 | #endif | ||
103 | |||
104 | bio_destructor_t *bi_destructor; /* destructor */ | ||
105 | |||
106 | /* | ||
107 | * We can inline a number of vecs at the end of the bio, to avoid | ||
108 | * double allocations for a small number of bio_vecs. This member | ||
109 | * MUST obviously be kept at the very end of the bio. | ||
110 | */ | ||
111 | struct bio_vec bi_inline_vecs[0]; | ||
112 | }; | ||
113 | |||
114 | /* | ||
115 | * bio flags | ||
116 | */ | ||
117 | #define BIO_UPTODATE 0 /* ok after I/O completion */ | ||
118 | #define BIO_RW_BLOCK 1 /* RW_AHEAD set, and read/write would block */ | ||
119 | #define BIO_EOF 2 /* out-out-bounds error */ | ||
120 | #define BIO_SEG_VALID 3 /* bi_phys_segments valid */ | ||
121 | #define BIO_CLONED 4 /* doesn't own data */ | ||
122 | #define BIO_BOUNCED 5 /* bio is a bounce bio */ | ||
123 | #define BIO_USER_MAPPED 6 /* contains user pages */ | ||
124 | #define BIO_EOPNOTSUPP 7 /* not supported */ | ||
125 | #define BIO_CPU_AFFINE 8 /* complete bio on same CPU as submitted */ | ||
126 | #define BIO_NULL_MAPPED 9 /* contains invalid user pages */ | ||
127 | #define BIO_FS_INTEGRITY 10 /* fs owns integrity data, not block layer */ | ||
128 | #define BIO_QUIET 11 /* Make BIO Quiet */ | ||
129 | #define bio_flagged(bio, flag) ((bio)->bi_flags & (1 << (flag))) | ||
130 | |||
131 | /* | ||
132 | * top 4 bits of bio flags indicate the pool this bio came from | ||
133 | */ | ||
134 | #define BIO_POOL_BITS (4) | ||
135 | #define BIO_POOL_NONE ((1UL << BIO_POOL_BITS) - 1) | ||
136 | #define BIO_POOL_OFFSET (BITS_PER_LONG - BIO_POOL_BITS) | ||
137 | #define BIO_POOL_MASK (1UL << BIO_POOL_OFFSET) | ||
138 | #define BIO_POOL_IDX(bio) ((bio)->bi_flags >> BIO_POOL_OFFSET) | ||
139 | |||
140 | /* | ||
141 | * bio bi_rw flags | ||
142 | * | ||
143 | * bit 0 -- data direction | ||
144 | * If not set, bio is a read from device. If set, it's a write to device. | ||
145 | * bit 1 -- fail fast device errors | ||
146 | * bit 2 -- fail fast transport errors | ||
147 | * bit 3 -- fail fast driver errors | ||
148 | * bit 4 -- rw-ahead when set | ||
149 | * bit 5 -- barrier | ||
150 | * Insert a serialization point in the IO queue, forcing previously | ||
151 | * submitted IO to be completed before this one is issued. | ||
152 | * bit 6 -- synchronous I/O hint. | ||
153 | * bit 7 -- Unplug the device immediately after submitting this bio. | ||
154 | * bit 8 -- metadata request | ||
155 | * Used for tracing to differentiate metadata and data IO. May also | ||
156 | * get some preferential treatment in the IO scheduler | ||
157 | * bit 9 -- discard sectors | ||
158 | * Informs the lower level device that this range of sectors is no longer | ||
159 | * used by the file system and may thus be freed by the device. Used | ||
160 | * for flash based storage. | ||
161 | * Don't want driver retries for any fast fail whatever the reason. | ||
162 | * bit 10 -- Tell the IO scheduler not to wait for more requests after this | ||
163 | one has been submitted, even if it is a SYNC request. | ||
164 | */ | ||
165 | enum bio_rw_flags { | ||
166 | BIO_RW, | ||
167 | BIO_RW_FAILFAST_DEV, | ||
168 | BIO_RW_FAILFAST_TRANSPORT, | ||
169 | BIO_RW_FAILFAST_DRIVER, | ||
170 | /* above flags must match REQ_* */ | ||
171 | BIO_RW_AHEAD, | ||
172 | BIO_RW_BARRIER, | ||
173 | BIO_RW_SYNCIO, | ||
174 | BIO_RW_UNPLUG, | ||
175 | BIO_RW_META, | ||
176 | BIO_RW_DISCARD, | ||
177 | BIO_RW_NOIDLE, | ||
178 | }; | ||
179 | |||
180 | /* | ||
181 | * First four bits must match between bio->bi_rw and rq->cmd_flags, make | ||
182 | * that explicit here. | ||
183 | */ | ||
184 | #define BIO_RW_RQ_MASK 0xf | ||
185 | |||
186 | static inline bool bio_rw_flagged(struct bio *bio, enum bio_rw_flags flag) | ||
187 | { | ||
188 | return (bio->bi_rw & (1 << flag)) != 0; | ||
189 | } | ||
190 | |||
191 | /* | ||
192 | * upper 16 bits of bi_rw define the io priority of this bio | 47 | * upper 16 bits of bi_rw define the io priority of this bio |
193 | */ | 48 | */ |
194 | #define BIO_PRIO_SHIFT (8 * sizeof(unsigned long) - IOPRIO_BITS) | 49 | #define BIO_PRIO_SHIFT (8 * sizeof(unsigned long) - IOPRIO_BITS) |
@@ -211,7 +66,10 @@ static inline bool bio_rw_flagged(struct bio *bio, enum bio_rw_flags flag) | |||
211 | #define bio_offset(bio) bio_iovec((bio))->bv_offset | 66 | #define bio_offset(bio) bio_iovec((bio))->bv_offset |
212 | #define bio_segments(bio) ((bio)->bi_vcnt - (bio)->bi_idx) | 67 | #define bio_segments(bio) ((bio)->bi_vcnt - (bio)->bi_idx) |
213 | #define bio_sectors(bio) ((bio)->bi_size >> 9) | 68 | #define bio_sectors(bio) ((bio)->bi_size >> 9) |
214 | #define bio_empty_barrier(bio) (bio_rw_flagged(bio, BIO_RW_BARRIER) && !bio_has_data(bio) && !bio_rw_flagged(bio, BIO_RW_DISCARD)) | 69 | #define bio_empty_barrier(bio) \ |
70 | ((bio->bi_rw & REQ_HARDBARRIER) && \ | ||
71 | !bio_has_data(bio) && \ | ||
72 | !(bio->bi_rw & REQ_DISCARD)) | ||
215 | 73 | ||
216 | static inline unsigned int bio_cur_bytes(struct bio *bio) | 74 | static inline unsigned int bio_cur_bytes(struct bio *bio) |
217 | { | 75 | { |
diff --git a/include/linux/blk_types.h b/include/linux/blk_types.h new file mode 100644 index 000000000000..53691774d34e --- /dev/null +++ b/include/linux/blk_types.h | |||
@@ -0,0 +1,194 @@ | |||
1 | /* | ||
2 | * Block data types and constants. Directly include this file only to | ||
3 | * break include dependency loop. | ||
4 | */ | ||
5 | #ifndef __LINUX_BLK_TYPES_H | ||
6 | #define __LINUX_BLK_TYPES_H | ||
7 | |||
8 | #ifdef CONFIG_BLOCK | ||
9 | |||
10 | #include <linux/types.h> | ||
11 | |||
12 | struct bio_set; | ||
13 | struct bio; | ||
14 | struct bio_integrity_payload; | ||
15 | struct page; | ||
16 | struct block_device; | ||
17 | typedef void (bio_end_io_t) (struct bio *, int); | ||
18 | typedef void (bio_destructor_t) (struct bio *); | ||
19 | |||
20 | /* | ||
21 | * was unsigned short, but we might as well be ready for > 64kB I/O pages | ||
22 | */ | ||
23 | struct bio_vec { | ||
24 | struct page *bv_page; | ||
25 | unsigned int bv_len; | ||
26 | unsigned int bv_offset; | ||
27 | }; | ||
28 | |||
29 | /* | ||
30 | * main unit of I/O for the block layer and lower layers (ie drivers and | ||
31 | * stacking drivers) | ||
32 | */ | ||
33 | struct bio { | ||
34 | sector_t bi_sector; /* device address in 512 byte | ||
35 | sectors */ | ||
36 | struct bio *bi_next; /* request queue link */ | ||
37 | struct block_device *bi_bdev; | ||
38 | unsigned long bi_flags; /* status, command, etc */ | ||
39 | unsigned long bi_rw; /* bottom bits READ/WRITE, | ||
40 | * top bits priority | ||
41 | */ | ||
42 | |||
43 | unsigned short bi_vcnt; /* how many bio_vec's */ | ||
44 | unsigned short bi_idx; /* current index into bvl_vec */ | ||
45 | |||
46 | /* Number of segments in this BIO after | ||
47 | * physical address coalescing is performed. | ||
48 | */ | ||
49 | unsigned int bi_phys_segments; | ||
50 | |||
51 | unsigned int bi_size; /* residual I/O count */ | ||
52 | |||
53 | /* | ||
54 | * To keep track of the max segment size, we account for the | ||
55 | * sizes of the first and last mergeable segments in this bio. | ||
56 | */ | ||
57 | unsigned int bi_seg_front_size; | ||
58 | unsigned int bi_seg_back_size; | ||
59 | |||
60 | unsigned int bi_max_vecs; /* max bvl_vecs we can hold */ | ||
61 | |||
62 | unsigned int bi_comp_cpu; /* completion CPU */ | ||
63 | |||
64 | atomic_t bi_cnt; /* pin count */ | ||
65 | |||
66 | struct bio_vec *bi_io_vec; /* the actual vec list */ | ||
67 | |||
68 | bio_end_io_t *bi_end_io; | ||
69 | |||
70 | void *bi_private; | ||
71 | #if defined(CONFIG_BLK_DEV_INTEGRITY) | ||
72 | struct bio_integrity_payload *bi_integrity; /* data integrity */ | ||
73 | #endif | ||
74 | |||
75 | bio_destructor_t *bi_destructor; /* destructor */ | ||
76 | |||
77 | /* | ||
78 | * We can inline a number of vecs at the end of the bio, to avoid | ||
79 | * double allocations for a small number of bio_vecs. This member | ||
80 | * MUST obviously be kept at the very end of the bio. | ||
81 | */ | ||
82 | struct bio_vec bi_inline_vecs[0]; | ||
83 | }; | ||
84 | |||
85 | /* | ||
86 | * bio flags | ||
87 | */ | ||
88 | #define BIO_UPTODATE 0 /* ok after I/O completion */ | ||
89 | #define BIO_RW_BLOCK 1 /* RW_AHEAD set, and read/write would block */ | ||
90 | #define BIO_EOF 2 /* out-out-bounds error */ | ||
91 | #define BIO_SEG_VALID 3 /* bi_phys_segments valid */ | ||
92 | #define BIO_CLONED 4 /* doesn't own data */ | ||
93 | #define BIO_BOUNCED 5 /* bio is a bounce bio */ | ||
94 | #define BIO_USER_MAPPED 6 /* contains user pages */ | ||
95 | #define BIO_EOPNOTSUPP 7 /* not supported */ | ||
96 | #define BIO_CPU_AFFINE 8 /* complete bio on same CPU as submitted */ | ||
97 | #define BIO_NULL_MAPPED 9 /* contains invalid user pages */ | ||
98 | #define BIO_FS_INTEGRITY 10 /* fs owns integrity data, not block layer */ | ||
99 | #define BIO_QUIET 11 /* Make BIO Quiet */ | ||
100 | #define bio_flagged(bio, flag) ((bio)->bi_flags & (1 << (flag))) | ||
101 | |||
102 | /* | ||
103 | * top 4 bits of bio flags indicate the pool this bio came from | ||
104 | */ | ||
105 | #define BIO_POOL_BITS (4) | ||
106 | #define BIO_POOL_NONE ((1UL << BIO_POOL_BITS) - 1) | ||
107 | #define BIO_POOL_OFFSET (BITS_PER_LONG - BIO_POOL_BITS) | ||
108 | #define BIO_POOL_MASK (1UL << BIO_POOL_OFFSET) | ||
109 | #define BIO_POOL_IDX(bio) ((bio)->bi_flags >> BIO_POOL_OFFSET) | ||
110 | |||
111 | #endif /* CONFIG_BLOCK */ | ||
112 | |||
113 | /* | ||
114 | * Request flags. For use in the cmd_flags field of struct request, and in | ||
115 | * bi_rw of struct bio. Note that some flags are only valid in either one. | ||
116 | */ | ||
117 | enum rq_flag_bits { | ||
118 | /* common flags */ | ||
119 | __REQ_WRITE, /* not set, read. set, write */ | ||
120 | __REQ_FAILFAST_DEV, /* no driver retries of device errors */ | ||
121 | __REQ_FAILFAST_TRANSPORT, /* no driver retries of transport errors */ | ||
122 | __REQ_FAILFAST_DRIVER, /* no driver retries of driver errors */ | ||
123 | |||
124 | __REQ_HARDBARRIER, /* may not be passed by drive either */ | ||
125 | __REQ_SYNC, /* request is sync (sync write or read) */ | ||
126 | __REQ_META, /* metadata io request */ | ||
127 | __REQ_DISCARD, /* request to discard sectors */ | ||
128 | __REQ_NOIDLE, /* don't anticipate more IO after this one */ | ||
129 | |||
130 | /* bio only flags */ | ||
131 | __REQ_UNPLUG, /* unplug the immediately after submission */ | ||
132 | __REQ_RAHEAD, /* read ahead, can fail anytime */ | ||
133 | |||
134 | /* request only flags */ | ||
135 | __REQ_SORTED, /* elevator knows about this request */ | ||
136 | __REQ_SOFTBARRIER, /* may not be passed by ioscheduler */ | ||
137 | __REQ_FUA, /* forced unit access */ | ||
138 | __REQ_NOMERGE, /* don't touch this for merging */ | ||
139 | __REQ_STARTED, /* drive already may have started this one */ | ||
140 | __REQ_DONTPREP, /* don't call prep for this one */ | ||
141 | __REQ_QUEUED, /* uses queueing */ | ||
142 | __REQ_ELVPRIV, /* elevator private data attached */ | ||
143 | __REQ_FAILED, /* set if the request failed */ | ||
144 | __REQ_QUIET, /* don't worry about errors */ | ||
145 | __REQ_PREEMPT, /* set for "ide_preempt" requests */ | ||
146 | __REQ_ORDERED_COLOR, /* is before or after barrier */ | ||
147 | __REQ_ALLOCED, /* request came from our alloc pool */ | ||
148 | __REQ_COPY_USER, /* contains copies of user pages */ | ||
149 | __REQ_INTEGRITY, /* integrity metadata has been remapped */ | ||
150 | __REQ_FLUSH, /* request for cache flush */ | ||
151 | __REQ_IO_STAT, /* account I/O stat */ | ||
152 | __REQ_MIXED_MERGE, /* merge of different types, fail separately */ | ||
153 | __REQ_NR_BITS, /* stops here */ | ||
154 | }; | ||
155 | |||
156 | #define REQ_WRITE (1 << __REQ_WRITE) | ||
157 | #define REQ_FAILFAST_DEV (1 << __REQ_FAILFAST_DEV) | ||
158 | #define REQ_FAILFAST_TRANSPORT (1 << __REQ_FAILFAST_TRANSPORT) | ||
159 | #define REQ_FAILFAST_DRIVER (1 << __REQ_FAILFAST_DRIVER) | ||
160 | #define REQ_HARDBARRIER (1 << __REQ_HARDBARRIER) | ||
161 | #define REQ_SYNC (1 << __REQ_SYNC) | ||
162 | #define REQ_META (1 << __REQ_META) | ||
163 | #define REQ_DISCARD (1 << __REQ_DISCARD) | ||
164 | #define REQ_NOIDLE (1 << __REQ_NOIDLE) | ||
165 | |||
166 | #define REQ_FAILFAST_MASK \ | ||
167 | (REQ_FAILFAST_DEV | REQ_FAILFAST_TRANSPORT | REQ_FAILFAST_DRIVER) | ||
168 | #define REQ_COMMON_MASK \ | ||
169 | (REQ_WRITE | REQ_FAILFAST_MASK | REQ_HARDBARRIER | REQ_SYNC | \ | ||
170 | REQ_META| REQ_DISCARD | REQ_NOIDLE) | ||
171 | |||
172 | #define REQ_UNPLUG (1 << __REQ_UNPLUG) | ||
173 | #define REQ_RAHEAD (1 << __REQ_RAHEAD) | ||
174 | |||
175 | #define REQ_SORTED (1 << __REQ_SORTED) | ||
176 | #define REQ_SOFTBARRIER (1 << __REQ_SOFTBARRIER) | ||
177 | #define REQ_FUA (1 << __REQ_FUA) | ||
178 | #define REQ_NOMERGE (1 << __REQ_NOMERGE) | ||
179 | #define REQ_STARTED (1 << __REQ_STARTED) | ||
180 | #define REQ_DONTPREP (1 << __REQ_DONTPREP) | ||
181 | #define REQ_QUEUED (1 << __REQ_QUEUED) | ||
182 | #define REQ_ELVPRIV (1 << __REQ_ELVPRIV) | ||
183 | #define REQ_FAILED (1 << __REQ_FAILED) | ||
184 | #define REQ_QUIET (1 << __REQ_QUIET) | ||
185 | #define REQ_PREEMPT (1 << __REQ_PREEMPT) | ||
186 | #define REQ_ORDERED_COLOR (1 << __REQ_ORDERED_COLOR) | ||
187 | #define REQ_ALLOCED (1 << __REQ_ALLOCED) | ||
188 | #define REQ_COPY_USER (1 << __REQ_COPY_USER) | ||
189 | #define REQ_INTEGRITY (1 << __REQ_INTEGRITY) | ||
190 | #define REQ_FLUSH (1 << __REQ_FLUSH) | ||
191 | #define REQ_IO_STAT (1 << __REQ_IO_STAT) | ||
192 | #define REQ_MIXED_MERGE (1 << __REQ_MIXED_MERGE) | ||
193 | |||
194 | #endif /* __LINUX_BLK_TYPES_H */ | ||
diff --git a/include/linux/blkdev.h b/include/linux/blkdev.h index 09a840264d6f..89c855c5655c 100644 --- a/include/linux/blkdev.h +++ b/include/linux/blkdev.h | |||
@@ -60,7 +60,6 @@ enum rq_cmd_type_bits { | |||
60 | REQ_TYPE_PM_RESUME, /* resume request */ | 60 | REQ_TYPE_PM_RESUME, /* resume request */ |
61 | REQ_TYPE_PM_SHUTDOWN, /* shutdown request */ | 61 | REQ_TYPE_PM_SHUTDOWN, /* shutdown request */ |
62 | REQ_TYPE_SPECIAL, /* driver defined type */ | 62 | REQ_TYPE_SPECIAL, /* driver defined type */ |
63 | REQ_TYPE_LINUX_BLOCK, /* generic block layer message */ | ||
64 | /* | 63 | /* |
65 | * for ATA/ATAPI devices. this really doesn't belong here, ide should | 64 | * for ATA/ATAPI devices. this really doesn't belong here, ide should |
66 | * use REQ_TYPE_SPECIAL and use rq->cmd[0] with the range of driver | 65 | * use REQ_TYPE_SPECIAL and use rq->cmd[0] with the range of driver |
@@ -70,84 +69,6 @@ enum rq_cmd_type_bits { | |||
70 | REQ_TYPE_ATA_PC, | 69 | REQ_TYPE_ATA_PC, |
71 | }; | 70 | }; |
72 | 71 | ||
73 | /* | ||
74 | * For request of type REQ_TYPE_LINUX_BLOCK, rq->cmd[0] is the opcode being | ||
75 | * sent down (similar to how REQ_TYPE_BLOCK_PC means that ->cmd[] holds a | ||
76 | * SCSI cdb. | ||
77 | * | ||
78 | * 0x00 -> 0x3f are driver private, to be used for whatever purpose they need, | ||
79 | * typically to differentiate REQ_TYPE_SPECIAL requests. | ||
80 | * | ||
81 | */ | ||
82 | enum { | ||
83 | REQ_LB_OP_EJECT = 0x40, /* eject request */ | ||
84 | REQ_LB_OP_FLUSH = 0x41, /* flush request */ | ||
85 | }; | ||
86 | |||
87 | /* | ||
88 | * request type modified bits. first four bits match BIO_RW* bits, important | ||
89 | */ | ||
90 | enum rq_flag_bits { | ||
91 | __REQ_RW, /* not set, read. set, write */ | ||
92 | __REQ_FAILFAST_DEV, /* no driver retries of device errors */ | ||
93 | __REQ_FAILFAST_TRANSPORT, /* no driver retries of transport errors */ | ||
94 | __REQ_FAILFAST_DRIVER, /* no driver retries of driver errors */ | ||
95 | /* above flags must match BIO_RW_* */ | ||
96 | __REQ_DISCARD, /* request to discard sectors */ | ||
97 | __REQ_SORTED, /* elevator knows about this request */ | ||
98 | __REQ_SOFTBARRIER, /* may not be passed by ioscheduler */ | ||
99 | __REQ_HARDBARRIER, /* may not be passed by drive either */ | ||
100 | __REQ_FUA, /* forced unit access */ | ||
101 | __REQ_NOMERGE, /* don't touch this for merging */ | ||
102 | __REQ_STARTED, /* drive already may have started this one */ | ||
103 | __REQ_DONTPREP, /* don't call prep for this one */ | ||
104 | __REQ_QUEUED, /* uses queueing */ | ||
105 | __REQ_ELVPRIV, /* elevator private data attached */ | ||
106 | __REQ_FAILED, /* set if the request failed */ | ||
107 | __REQ_QUIET, /* don't worry about errors */ | ||
108 | __REQ_PREEMPT, /* set for "ide_preempt" requests */ | ||
109 | __REQ_ORDERED_COLOR, /* is before or after barrier */ | ||
110 | __REQ_RW_SYNC, /* request is sync (sync write or read) */ | ||
111 | __REQ_ALLOCED, /* request came from our alloc pool */ | ||
112 | __REQ_RW_META, /* metadata io request */ | ||
113 | __REQ_COPY_USER, /* contains copies of user pages */ | ||
114 | __REQ_INTEGRITY, /* integrity metadata has been remapped */ | ||
115 | __REQ_NOIDLE, /* Don't anticipate more IO after this one */ | ||
116 | __REQ_IO_STAT, /* account I/O stat */ | ||
117 | __REQ_MIXED_MERGE, /* merge of different types, fail separately */ | ||
118 | __REQ_NR_BITS, /* stops here */ | ||
119 | }; | ||
120 | |||
121 | #define REQ_RW (1 << __REQ_RW) | ||
122 | #define REQ_FAILFAST_DEV (1 << __REQ_FAILFAST_DEV) | ||
123 | #define REQ_FAILFAST_TRANSPORT (1 << __REQ_FAILFAST_TRANSPORT) | ||
124 | #define REQ_FAILFAST_DRIVER (1 << __REQ_FAILFAST_DRIVER) | ||
125 | #define REQ_DISCARD (1 << __REQ_DISCARD) | ||
126 | #define REQ_SORTED (1 << __REQ_SORTED) | ||
127 | #define REQ_SOFTBARRIER (1 << __REQ_SOFTBARRIER) | ||
128 | #define REQ_HARDBARRIER (1 << __REQ_HARDBARRIER) | ||
129 | #define REQ_FUA (1 << __REQ_FUA) | ||
130 | #define REQ_NOMERGE (1 << __REQ_NOMERGE) | ||
131 | #define REQ_STARTED (1 << __REQ_STARTED) | ||
132 | #define REQ_DONTPREP (1 << __REQ_DONTPREP) | ||
133 | #define REQ_QUEUED (1 << __REQ_QUEUED) | ||
134 | #define REQ_ELVPRIV (1 << __REQ_ELVPRIV) | ||
135 | #define REQ_FAILED (1 << __REQ_FAILED) | ||
136 | #define REQ_QUIET (1 << __REQ_QUIET) | ||
137 | #define REQ_PREEMPT (1 << __REQ_PREEMPT) | ||
138 | #define REQ_ORDERED_COLOR (1 << __REQ_ORDERED_COLOR) | ||
139 | #define REQ_RW_SYNC (1 << __REQ_RW_SYNC) | ||
140 | #define REQ_ALLOCED (1 << __REQ_ALLOCED) | ||
141 | #define REQ_RW_META (1 << __REQ_RW_META) | ||
142 | #define REQ_COPY_USER (1 << __REQ_COPY_USER) | ||
143 | #define REQ_INTEGRITY (1 << __REQ_INTEGRITY) | ||
144 | #define REQ_NOIDLE (1 << __REQ_NOIDLE) | ||
145 | #define REQ_IO_STAT (1 << __REQ_IO_STAT) | ||
146 | #define REQ_MIXED_MERGE (1 << __REQ_MIXED_MERGE) | ||
147 | |||
148 | #define REQ_FAILFAST_MASK (REQ_FAILFAST_DEV | REQ_FAILFAST_TRANSPORT | \ | ||
149 | REQ_FAILFAST_DRIVER) | ||
150 | |||
151 | #define BLK_MAX_CDB 16 | 72 | #define BLK_MAX_CDB 16 |
152 | 73 | ||
153 | /* | 74 | /* |
@@ -264,6 +185,7 @@ struct request_pm_state | |||
264 | typedef void (request_fn_proc) (struct request_queue *q); | 185 | typedef void (request_fn_proc) (struct request_queue *q); |
265 | typedef int (make_request_fn) (struct request_queue *q, struct bio *bio); | 186 | typedef int (make_request_fn) (struct request_queue *q, struct bio *bio); |
266 | typedef int (prep_rq_fn) (struct request_queue *, struct request *); | 187 | typedef int (prep_rq_fn) (struct request_queue *, struct request *); |
188 | typedef void (unprep_rq_fn) (struct request_queue *, struct request *); | ||
267 | typedef void (unplug_fn) (struct request_queue *); | 189 | typedef void (unplug_fn) (struct request_queue *); |
268 | 190 | ||
269 | struct bio_vec; | 191 | struct bio_vec; |
@@ -275,7 +197,6 @@ struct bvec_merge_data { | |||
275 | }; | 197 | }; |
276 | typedef int (merge_bvec_fn) (struct request_queue *, struct bvec_merge_data *, | 198 | typedef int (merge_bvec_fn) (struct request_queue *, struct bvec_merge_data *, |
277 | struct bio_vec *); | 199 | struct bio_vec *); |
278 | typedef void (prepare_flush_fn) (struct request_queue *, struct request *); | ||
279 | typedef void (softirq_done_fn)(struct request *); | 200 | typedef void (softirq_done_fn)(struct request *); |
280 | typedef int (dma_drain_needed_fn)(struct request *); | 201 | typedef int (dma_drain_needed_fn)(struct request *); |
281 | typedef int (lld_busy_fn) (struct request_queue *q); | 202 | typedef int (lld_busy_fn) (struct request_queue *q); |
@@ -346,9 +267,9 @@ struct request_queue | |||
346 | request_fn_proc *request_fn; | 267 | request_fn_proc *request_fn; |
347 | make_request_fn *make_request_fn; | 268 | make_request_fn *make_request_fn; |
348 | prep_rq_fn *prep_rq_fn; | 269 | prep_rq_fn *prep_rq_fn; |
270 | unprep_rq_fn *unprep_rq_fn; | ||
349 | unplug_fn *unplug_fn; | 271 | unplug_fn *unplug_fn; |
350 | merge_bvec_fn *merge_bvec_fn; | 272 | merge_bvec_fn *merge_bvec_fn; |
351 | prepare_flush_fn *prepare_flush_fn; | ||
352 | softirq_done_fn *softirq_done_fn; | 273 | softirq_done_fn *softirq_done_fn; |
353 | rq_timed_out_fn *rq_timed_out_fn; | 274 | rq_timed_out_fn *rq_timed_out_fn; |
354 | dma_drain_needed_fn *dma_drain_needed; | 275 | dma_drain_needed_fn *dma_drain_needed; |
@@ -467,11 +388,13 @@ struct request_queue | |||
467 | #define QUEUE_FLAG_IO_STAT 15 /* do IO stats */ | 388 | #define QUEUE_FLAG_IO_STAT 15 /* do IO stats */ |
468 | #define QUEUE_FLAG_DISCARD 16 /* supports DISCARD */ | 389 | #define QUEUE_FLAG_DISCARD 16 /* supports DISCARD */ |
469 | #define QUEUE_FLAG_NOXMERGES 17 /* No extended merges */ | 390 | #define QUEUE_FLAG_NOXMERGES 17 /* No extended merges */ |
391 | #define QUEUE_FLAG_ADD_RANDOM 18 /* Contributes to random pool */ | ||
470 | 392 | ||
471 | #define QUEUE_FLAG_DEFAULT ((1 << QUEUE_FLAG_IO_STAT) | \ | 393 | #define QUEUE_FLAG_DEFAULT ((1 << QUEUE_FLAG_IO_STAT) | \ |
472 | (1 << QUEUE_FLAG_CLUSTER) | \ | 394 | (1 << QUEUE_FLAG_CLUSTER) | \ |
473 | (1 << QUEUE_FLAG_STACKABLE) | \ | 395 | (1 << QUEUE_FLAG_STACKABLE) | \ |
474 | (1 << QUEUE_FLAG_SAME_COMP)) | 396 | (1 << QUEUE_FLAG_SAME_COMP) | \ |
397 | (1 << QUEUE_FLAG_ADD_RANDOM)) | ||
475 | 398 | ||
476 | static inline int queue_is_locked(struct request_queue *q) | 399 | static inline int queue_is_locked(struct request_queue *q) |
477 | { | 400 | { |
@@ -596,38 +519,26 @@ enum { | |||
596 | test_bit(QUEUE_FLAG_NOXMERGES, &(q)->queue_flags) | 519 | test_bit(QUEUE_FLAG_NOXMERGES, &(q)->queue_flags) |
597 | #define blk_queue_nonrot(q) test_bit(QUEUE_FLAG_NONROT, &(q)->queue_flags) | 520 | #define blk_queue_nonrot(q) test_bit(QUEUE_FLAG_NONROT, &(q)->queue_flags) |
598 | #define blk_queue_io_stat(q) test_bit(QUEUE_FLAG_IO_STAT, &(q)->queue_flags) | 521 | #define blk_queue_io_stat(q) test_bit(QUEUE_FLAG_IO_STAT, &(q)->queue_flags) |
522 | #define blk_queue_add_random(q) test_bit(QUEUE_FLAG_ADD_RANDOM, &(q)->queue_flags) | ||
599 | #define blk_queue_flushing(q) ((q)->ordseq) | 523 | #define blk_queue_flushing(q) ((q)->ordseq) |
600 | #define blk_queue_stackable(q) \ | 524 | #define blk_queue_stackable(q) \ |
601 | test_bit(QUEUE_FLAG_STACKABLE, &(q)->queue_flags) | 525 | test_bit(QUEUE_FLAG_STACKABLE, &(q)->queue_flags) |
602 | #define blk_queue_discard(q) test_bit(QUEUE_FLAG_DISCARD, &(q)->queue_flags) | 526 | #define blk_queue_discard(q) test_bit(QUEUE_FLAG_DISCARD, &(q)->queue_flags) |
603 | 527 | ||
604 | #define blk_fs_request(rq) ((rq)->cmd_type == REQ_TYPE_FS) | 528 | #define blk_noretry_request(rq) \ |
605 | #define blk_pc_request(rq) ((rq)->cmd_type == REQ_TYPE_BLOCK_PC) | 529 | ((rq)->cmd_flags & (REQ_FAILFAST_DEV|REQ_FAILFAST_TRANSPORT| \ |
606 | #define blk_special_request(rq) ((rq)->cmd_type == REQ_TYPE_SPECIAL) | 530 | REQ_FAILFAST_DRIVER)) |
607 | #define blk_sense_request(rq) ((rq)->cmd_type == REQ_TYPE_SENSE) | 531 | |
608 | 532 | #define blk_account_rq(rq) \ | |
609 | #define blk_failfast_dev(rq) ((rq)->cmd_flags & REQ_FAILFAST_DEV) | 533 | (((rq)->cmd_flags & REQ_STARTED) && \ |
610 | #define blk_failfast_transport(rq) ((rq)->cmd_flags & REQ_FAILFAST_TRANSPORT) | 534 | ((rq)->cmd_type == REQ_TYPE_FS || \ |
611 | #define blk_failfast_driver(rq) ((rq)->cmd_flags & REQ_FAILFAST_DRIVER) | 535 | ((rq)->cmd_flags & REQ_DISCARD))) |
612 | #define blk_noretry_request(rq) (blk_failfast_dev(rq) || \ | 536 | |
613 | blk_failfast_transport(rq) || \ | ||
614 | blk_failfast_driver(rq)) | ||
615 | #define blk_rq_started(rq) ((rq)->cmd_flags & REQ_STARTED) | ||
616 | #define blk_rq_io_stat(rq) ((rq)->cmd_flags & REQ_IO_STAT) | ||
617 | #define blk_rq_quiet(rq) ((rq)->cmd_flags & REQ_QUIET) | ||
618 | |||
619 | #define blk_account_rq(rq) (blk_rq_started(rq) && (blk_fs_request(rq) || blk_discard_rq(rq))) | ||
620 | |||
621 | #define blk_pm_suspend_request(rq) ((rq)->cmd_type == REQ_TYPE_PM_SUSPEND) | ||
622 | #define blk_pm_resume_request(rq) ((rq)->cmd_type == REQ_TYPE_PM_RESUME) | ||
623 | #define blk_pm_request(rq) \ | 537 | #define blk_pm_request(rq) \ |
624 | (blk_pm_suspend_request(rq) || blk_pm_resume_request(rq)) | 538 | ((rq)->cmd_type == REQ_TYPE_PM_SUSPEND || \ |
539 | (rq)->cmd_type == REQ_TYPE_PM_RESUME) | ||
625 | 540 | ||
626 | #define blk_rq_cpu_valid(rq) ((rq)->cpu != -1) | 541 | #define blk_rq_cpu_valid(rq) ((rq)->cpu != -1) |
627 | #define blk_sorted_rq(rq) ((rq)->cmd_flags & REQ_SORTED) | ||
628 | #define blk_barrier_rq(rq) ((rq)->cmd_flags & REQ_HARDBARRIER) | ||
629 | #define blk_fua_rq(rq) ((rq)->cmd_flags & REQ_FUA) | ||
630 | #define blk_discard_rq(rq) ((rq)->cmd_flags & REQ_DISCARD) | ||
631 | #define blk_bidi_rq(rq) ((rq)->next_rq != NULL) | 542 | #define blk_bidi_rq(rq) ((rq)->next_rq != NULL) |
632 | /* rq->queuelist of dequeued request must be list_empty() */ | 543 | /* rq->queuelist of dequeued request must be list_empty() */ |
633 | #define blk_queued_rq(rq) (!list_empty(&(rq)->queuelist)) | 544 | #define blk_queued_rq(rq) (!list_empty(&(rq)->queuelist)) |
@@ -641,7 +552,7 @@ enum { | |||
641 | */ | 552 | */ |
642 | static inline bool rw_is_sync(unsigned int rw_flags) | 553 | static inline bool rw_is_sync(unsigned int rw_flags) |
643 | { | 554 | { |
644 | return !(rw_flags & REQ_RW) || (rw_flags & REQ_RW_SYNC); | 555 | return !(rw_flags & REQ_WRITE) || (rw_flags & REQ_SYNC); |
645 | } | 556 | } |
646 | 557 | ||
647 | static inline bool rq_is_sync(struct request *rq) | 558 | static inline bool rq_is_sync(struct request *rq) |
@@ -649,9 +560,6 @@ static inline bool rq_is_sync(struct request *rq) | |||
649 | return rw_is_sync(rq->cmd_flags); | 560 | return rw_is_sync(rq->cmd_flags); |
650 | } | 561 | } |
651 | 562 | ||
652 | #define rq_is_meta(rq) ((rq)->cmd_flags & REQ_RW_META) | ||
653 | #define rq_noidle(rq) ((rq)->cmd_flags & REQ_NOIDLE) | ||
654 | |||
655 | static inline int blk_queue_full(struct request_queue *q, int sync) | 563 | static inline int blk_queue_full(struct request_queue *q, int sync) |
656 | { | 564 | { |
657 | if (sync) | 565 | if (sync) |
@@ -684,7 +592,8 @@ static inline void blk_clear_queue_full(struct request_queue *q, int sync) | |||
684 | (REQ_NOMERGE | REQ_STARTED | REQ_HARDBARRIER | REQ_SOFTBARRIER) | 592 | (REQ_NOMERGE | REQ_STARTED | REQ_HARDBARRIER | REQ_SOFTBARRIER) |
685 | #define rq_mergeable(rq) \ | 593 | #define rq_mergeable(rq) \ |
686 | (!((rq)->cmd_flags & RQ_NOMERGE_FLAGS) && \ | 594 | (!((rq)->cmd_flags & RQ_NOMERGE_FLAGS) && \ |
687 | (blk_discard_rq(rq) || blk_fs_request((rq)))) | 595 | (((rq)->cmd_flags & REQ_DISCARD) || \ |
596 | (rq)->cmd_type == REQ_TYPE_FS)) | ||
688 | 597 | ||
689 | /* | 598 | /* |
690 | * q->prep_rq_fn return values | 599 | * q->prep_rq_fn return values |
@@ -709,7 +618,7 @@ extern unsigned long blk_max_low_pfn, blk_max_pfn; | |||
709 | #define BLK_BOUNCE_HIGH -1ULL | 618 | #define BLK_BOUNCE_HIGH -1ULL |
710 | #endif | 619 | #endif |
711 | #define BLK_BOUNCE_ANY (-1ULL) | 620 | #define BLK_BOUNCE_ANY (-1ULL) |
712 | #define BLK_BOUNCE_ISA (ISA_DMA_THRESHOLD) | 621 | #define BLK_BOUNCE_ISA (DMA_BIT_MASK(24)) |
713 | 622 | ||
714 | /* | 623 | /* |
715 | * default timeout for SG_IO if none specified | 624 | * default timeout for SG_IO if none specified |
@@ -781,6 +690,8 @@ extern struct request *blk_make_request(struct request_queue *, struct bio *, | |||
781 | gfp_t); | 690 | gfp_t); |
782 | extern void blk_insert_request(struct request_queue *, struct request *, int, void *); | 691 | extern void blk_insert_request(struct request_queue *, struct request *, int, void *); |
783 | extern void blk_requeue_request(struct request_queue *, struct request *); | 692 | extern void blk_requeue_request(struct request_queue *, struct request *); |
693 | extern void blk_add_request_payload(struct request *rq, struct page *page, | ||
694 | unsigned int len); | ||
784 | extern int blk_rq_check_limits(struct request_queue *q, struct request *rq); | 695 | extern int blk_rq_check_limits(struct request_queue *q, struct request *rq); |
785 | extern int blk_lld_busy(struct request_queue *q); | 696 | extern int blk_lld_busy(struct request_queue *q); |
786 | extern int blk_rq_prep_clone(struct request *rq, struct request *rq_src, | 697 | extern int blk_rq_prep_clone(struct request *rq, struct request *rq_src, |
@@ -915,6 +826,7 @@ extern void blk_complete_request(struct request *); | |||
915 | extern void __blk_complete_request(struct request *); | 826 | extern void __blk_complete_request(struct request *); |
916 | extern void blk_abort_request(struct request *); | 827 | extern void blk_abort_request(struct request *); |
917 | extern void blk_abort_queue(struct request_queue *); | 828 | extern void blk_abort_queue(struct request_queue *); |
829 | extern void blk_unprep_request(struct request *); | ||
918 | 830 | ||
919 | /* | 831 | /* |
920 | * Access functions for manipulating queue properties | 832 | * Access functions for manipulating queue properties |
@@ -959,6 +871,7 @@ extern int blk_queue_dma_drain(struct request_queue *q, | |||
959 | extern void blk_queue_lld_busy(struct request_queue *q, lld_busy_fn *fn); | 871 | extern void blk_queue_lld_busy(struct request_queue *q, lld_busy_fn *fn); |
960 | extern void blk_queue_segment_boundary(struct request_queue *, unsigned long); | 872 | extern void blk_queue_segment_boundary(struct request_queue *, unsigned long); |
961 | extern void blk_queue_prep_rq(struct request_queue *, prep_rq_fn *pfn); | 873 | extern void blk_queue_prep_rq(struct request_queue *, prep_rq_fn *pfn); |
874 | extern void blk_queue_unprep_rq(struct request_queue *, unprep_rq_fn *ufn); | ||
962 | extern void blk_queue_merge_bvec(struct request_queue *, merge_bvec_fn *); | 875 | extern void blk_queue_merge_bvec(struct request_queue *, merge_bvec_fn *); |
963 | extern void blk_queue_dma_alignment(struct request_queue *, int); | 876 | extern void blk_queue_dma_alignment(struct request_queue *, int); |
964 | extern void blk_queue_update_dma_alignment(struct request_queue *, int); | 877 | extern void blk_queue_update_dma_alignment(struct request_queue *, int); |
@@ -966,7 +879,7 @@ extern void blk_queue_softirq_done(struct request_queue *, softirq_done_fn *); | |||
966 | extern void blk_queue_rq_timed_out(struct request_queue *, rq_timed_out_fn *); | 879 | extern void blk_queue_rq_timed_out(struct request_queue *, rq_timed_out_fn *); |
967 | extern void blk_queue_rq_timeout(struct request_queue *, unsigned int); | 880 | extern void blk_queue_rq_timeout(struct request_queue *, unsigned int); |
968 | extern struct backing_dev_info *blk_get_backing_dev_info(struct block_device *bdev); | 881 | extern struct backing_dev_info *blk_get_backing_dev_info(struct block_device *bdev); |
969 | extern int blk_queue_ordered(struct request_queue *, unsigned, prepare_flush_fn *); | 882 | extern int blk_queue_ordered(struct request_queue *, unsigned); |
970 | extern bool blk_do_ordered(struct request_queue *, struct request **); | 883 | extern bool blk_do_ordered(struct request_queue *, struct request **); |
971 | extern unsigned blk_ordered_cur_seq(struct request_queue *); | 884 | extern unsigned blk_ordered_cur_seq(struct request_queue *); |
972 | extern unsigned blk_ordered_req_seq(struct request *); | 885 | extern unsigned blk_ordered_req_seq(struct request *); |
@@ -1020,7 +933,7 @@ static inline int sb_issue_discard(struct super_block *sb, | |||
1020 | { | 933 | { |
1021 | block <<= (sb->s_blocksize_bits - 9); | 934 | block <<= (sb->s_blocksize_bits - 9); |
1022 | nr_blocks <<= (sb->s_blocksize_bits - 9); | 935 | nr_blocks <<= (sb->s_blocksize_bits - 9); |
1023 | return blkdev_issue_discard(sb->s_bdev, block, nr_blocks, GFP_KERNEL, | 936 | return blkdev_issue_discard(sb->s_bdev, block, nr_blocks, GFP_NOFS, |
1024 | BLKDEV_IFL_WAIT | BLKDEV_IFL_BARRIER); | 937 | BLKDEV_IFL_WAIT | BLKDEV_IFL_BARRIER); |
1025 | } | 938 | } |
1026 | 939 | ||
@@ -1333,7 +1246,6 @@ static inline int blk_integrity_rq(struct request *rq) | |||
1333 | struct block_device_operations { | 1246 | struct block_device_operations { |
1334 | int (*open) (struct block_device *, fmode_t); | 1247 | int (*open) (struct block_device *, fmode_t); |
1335 | int (*release) (struct gendisk *, fmode_t); | 1248 | int (*release) (struct gendisk *, fmode_t); |
1336 | int (*locked_ioctl) (struct block_device *, fmode_t, unsigned, unsigned long); | ||
1337 | int (*ioctl) (struct block_device *, fmode_t, unsigned, unsigned long); | 1249 | int (*ioctl) (struct block_device *, fmode_t, unsigned, unsigned long); |
1338 | int (*compat_ioctl) (struct block_device *, fmode_t, unsigned, unsigned long); | 1250 | int (*compat_ioctl) (struct block_device *, fmode_t, unsigned, unsigned long); |
1339 | int (*direct_access) (struct block_device *, sector_t, | 1251 | int (*direct_access) (struct block_device *, sector_t, |
diff --git a/include/linux/blktrace_api.h b/include/linux/blktrace_api.h index 416bf62d6d46..3395cf7130f5 100644 --- a/include/linux/blktrace_api.h +++ b/include/linux/blktrace_api.h | |||
@@ -5,6 +5,7 @@ | |||
5 | #ifdef __KERNEL__ | 5 | #ifdef __KERNEL__ |
6 | #include <linux/blkdev.h> | 6 | #include <linux/blkdev.h> |
7 | #include <linux/relay.h> | 7 | #include <linux/relay.h> |
8 | #include <linux/compat.h> | ||
8 | #endif | 9 | #endif |
9 | 10 | ||
10 | /* | 11 | /* |
@@ -220,11 +221,26 @@ static inline int blk_trace_init_sysfs(struct device *dev) | |||
220 | 221 | ||
221 | #endif /* CONFIG_BLK_DEV_IO_TRACE */ | 222 | #endif /* CONFIG_BLK_DEV_IO_TRACE */ |
222 | 223 | ||
224 | #ifdef CONFIG_COMPAT | ||
225 | |||
226 | struct compat_blk_user_trace_setup { | ||
227 | char name[32]; | ||
228 | u16 act_mask; | ||
229 | u32 buf_size; | ||
230 | u32 buf_nr; | ||
231 | compat_u64 start_lba; | ||
232 | compat_u64 end_lba; | ||
233 | u32 pid; | ||
234 | }; | ||
235 | #define BLKTRACESETUP32 _IOWR(0x12, 115, struct compat_blk_user_trace_setup) | ||
236 | |||
237 | #endif | ||
238 | |||
223 | #if defined(CONFIG_EVENT_TRACING) && defined(CONFIG_BLOCK) | 239 | #if defined(CONFIG_EVENT_TRACING) && defined(CONFIG_BLOCK) |
224 | 240 | ||
225 | static inline int blk_cmd_buf_len(struct request *rq) | 241 | static inline int blk_cmd_buf_len(struct request *rq) |
226 | { | 242 | { |
227 | return blk_pc_request(rq) ? rq->cmd_len * 3 : 1; | 243 | return (rq->cmd_type == REQ_TYPE_BLOCK_PC) ? rq->cmd_len * 3 : 1; |
228 | } | 244 | } |
229 | 245 | ||
230 | extern void blk_dump_cmd(char *buf, struct request *rq); | 246 | extern void blk_dump_cmd(char *buf, struct request *rq); |
diff --git a/include/linux/coda_psdev.h b/include/linux/coda_psdev.h index 8859e2ede9fe..284b520934a0 100644 --- a/include/linux/coda_psdev.h +++ b/include/linux/coda_psdev.h | |||
@@ -86,9 +86,9 @@ struct upc_req { | |||
86 | wait_queue_head_t uc_sleep; /* process' wait queue */ | 86 | wait_queue_head_t uc_sleep; /* process' wait queue */ |
87 | }; | 87 | }; |
88 | 88 | ||
89 | #define REQ_ASYNC 0x1 | 89 | #define CODA_REQ_ASYNC 0x1 |
90 | #define REQ_READ 0x2 | 90 | #define CODA_REQ_READ 0x2 |
91 | #define REQ_WRITE 0x4 | 91 | #define CODA_REQ_WRITE 0x4 |
92 | #define REQ_ABORT 0x8 | 92 | #define CODA_REQ_ABORT 0x8 |
93 | 93 | ||
94 | #endif | 94 | #endif |
diff --git a/include/linux/drbd.h b/include/linux/drbd.h index b8d2516668aa..479ee3a1d901 100644 --- a/include/linux/drbd.h +++ b/include/linux/drbd.h | |||
@@ -53,7 +53,7 @@ | |||
53 | 53 | ||
54 | 54 | ||
55 | extern const char *drbd_buildtag(void); | 55 | extern const char *drbd_buildtag(void); |
56 | #define REL_VERSION "8.3.8" | 56 | #define REL_VERSION "8.3.8.1" |
57 | #define API_VERSION 88 | 57 | #define API_VERSION 88 |
58 | #define PRO_VERSION_MIN 86 | 58 | #define PRO_VERSION_MIN 86 |
59 | #define PRO_VERSION_MAX 94 | 59 | #define PRO_VERSION_MAX 94 |
diff --git a/include/linux/drbd_nl.h b/include/linux/drbd_nl.h index ce77a746fc9d..5f042810a56c 100644 --- a/include/linux/drbd_nl.h +++ b/include/linux/drbd_nl.h | |||
@@ -78,10 +78,11 @@ NL_PACKET(syncer_conf, 8, | |||
78 | NL_INTEGER( 30, T_MAY_IGNORE, rate) | 78 | NL_INTEGER( 30, T_MAY_IGNORE, rate) |
79 | NL_INTEGER( 31, T_MAY_IGNORE, after) | 79 | NL_INTEGER( 31, T_MAY_IGNORE, after) |
80 | NL_INTEGER( 32, T_MAY_IGNORE, al_extents) | 80 | NL_INTEGER( 32, T_MAY_IGNORE, al_extents) |
81 | NL_INTEGER( 71, T_MAY_IGNORE, dp_volume) | 81 | /* NL_INTEGER( 71, T_MAY_IGNORE, dp_volume) |
82 | NL_INTEGER( 72, T_MAY_IGNORE, dp_interval) | 82 | * NL_INTEGER( 72, T_MAY_IGNORE, dp_interval) |
83 | NL_INTEGER( 73, T_MAY_IGNORE, throttle_th) | 83 | * NL_INTEGER( 73, T_MAY_IGNORE, throttle_th) |
84 | NL_INTEGER( 74, T_MAY_IGNORE, hold_off_th) | 84 | * NL_INTEGER( 74, T_MAY_IGNORE, hold_off_th) |
85 | * feature will be reimplemented differently with 8.3.9 */ | ||
85 | NL_STRING( 52, T_MAY_IGNORE, verify_alg, SHARED_SECRET_MAX) | 86 | NL_STRING( 52, T_MAY_IGNORE, verify_alg, SHARED_SECRET_MAX) |
86 | NL_STRING( 51, T_MAY_IGNORE, cpu_mask, 32) | 87 | NL_STRING( 51, T_MAY_IGNORE, cpu_mask, 32) |
87 | NL_STRING( 64, T_MAY_IGNORE, csums_alg, SHARED_SECRET_MAX) | 88 | NL_STRING( 64, T_MAY_IGNORE, csums_alg, SHARED_SECRET_MAX) |
diff --git a/include/linux/fs.h b/include/linux/fs.h index a8ccf85b8691..1542e0e52b2e 100644 --- a/include/linux/fs.h +++ b/include/linux/fs.h | |||
@@ -8,6 +8,7 @@ | |||
8 | 8 | ||
9 | #include <linux/limits.h> | 9 | #include <linux/limits.h> |
10 | #include <linux/ioctl.h> | 10 | #include <linux/ioctl.h> |
11 | #include <linux/blk_types.h> | ||
11 | 12 | ||
12 | /* | 13 | /* |
13 | * It's silly to have NR_OPEN bigger than NR_FILE, but you can change | 14 | * It's silly to have NR_OPEN bigger than NR_FILE, but you can change |
@@ -121,7 +122,7 @@ struct inodes_stat_t { | |||
121 | * immediately wait on this read without caring about | 122 | * immediately wait on this read without caring about |
122 | * unplugging. | 123 | * unplugging. |
123 | * READA Used for read-ahead operations. Lower priority, and the | 124 | * READA Used for read-ahead operations. Lower priority, and the |
124 | * block layer could (in theory) choose to ignore this | 125 | * block layer could (in theory) choose to ignore this |
125 | * request if it runs into resource problems. | 126 | * request if it runs into resource problems. |
126 | * WRITE A normal async write. Device will be plugged. | 127 | * WRITE A normal async write. Device will be plugged. |
127 | * SWRITE Like WRITE, but a special case for ll_rw_block() that | 128 | * SWRITE Like WRITE, but a special case for ll_rw_block() that |
@@ -140,7 +141,7 @@ struct inodes_stat_t { | |||
140 | * SWRITE_SYNC | 141 | * SWRITE_SYNC |
141 | * SWRITE_SYNC_PLUG Like WRITE_SYNC/WRITE_SYNC_PLUG, but locks the buffer. | 142 | * SWRITE_SYNC_PLUG Like WRITE_SYNC/WRITE_SYNC_PLUG, but locks the buffer. |
142 | * See SWRITE. | 143 | * See SWRITE. |
143 | * WRITE_BARRIER Like WRITE, but tells the block layer that all | 144 | * WRITE_BARRIER Like WRITE_SYNC, but tells the block layer that all |
144 | * previously submitted writes must be safely on storage | 145 | * previously submitted writes must be safely on storage |
145 | * before this one is started. Also guarantees that when | 146 | * before this one is started. Also guarantees that when |
146 | * this write is complete, it itself is also safely on | 147 | * this write is complete, it itself is also safely on |
@@ -148,29 +149,31 @@ struct inodes_stat_t { | |||
148 | * of this IO. | 149 | * of this IO. |
149 | * | 150 | * |
150 | */ | 151 | */ |
151 | #define RW_MASK 1 | 152 | #define RW_MASK REQ_WRITE |
152 | #define RWA_MASK 2 | 153 | #define RWA_MASK REQ_RAHEAD |
153 | #define READ 0 | 154 | |
154 | #define WRITE 1 | 155 | #define READ 0 |
155 | #define READA 2 /* read-ahead - don't block if no resources */ | 156 | #define WRITE RW_MASK |
156 | #define SWRITE 3 /* for ll_rw_block() - wait for buffer lock */ | 157 | #define READA RWA_MASK |
157 | #define READ_SYNC (READ | (1 << BIO_RW_SYNCIO) | (1 << BIO_RW_UNPLUG)) | 158 | #define SWRITE (WRITE | READA) |
158 | #define READ_META (READ | (1 << BIO_RW_META)) | 159 | |
159 | #define WRITE_SYNC_PLUG (WRITE | (1 << BIO_RW_SYNCIO) | (1 << BIO_RW_NOIDLE)) | 160 | #define READ_SYNC (READ | REQ_SYNC | REQ_UNPLUG) |
160 | #define WRITE_SYNC (WRITE_SYNC_PLUG | (1 << BIO_RW_UNPLUG)) | 161 | #define READ_META (READ | REQ_META) |
161 | #define WRITE_ODIRECT_PLUG (WRITE | (1 << BIO_RW_SYNCIO)) | 162 | #define WRITE_SYNC_PLUG (WRITE | REQ_SYNC | REQ_NOIDLE) |
162 | #define WRITE_META (WRITE | (1 << BIO_RW_META)) | 163 | #define WRITE_SYNC (WRITE | REQ_SYNC | REQ_NOIDLE | REQ_UNPLUG) |
163 | #define SWRITE_SYNC_PLUG \ | 164 | #define WRITE_ODIRECT_PLUG (WRITE | REQ_SYNC) |
164 | (SWRITE | (1 << BIO_RW_SYNCIO) | (1 << BIO_RW_NOIDLE)) | 165 | #define WRITE_META (WRITE | REQ_META) |
165 | #define SWRITE_SYNC (SWRITE_SYNC_PLUG | (1 << BIO_RW_UNPLUG)) | 166 | #define WRITE_BARRIER (WRITE | REQ_SYNC | REQ_NOIDLE | REQ_UNPLUG | \ |
166 | #define WRITE_BARRIER (WRITE | (1 << BIO_RW_BARRIER)) | 167 | REQ_HARDBARRIER) |
168 | #define SWRITE_SYNC_PLUG (SWRITE | REQ_SYNC | REQ_NOIDLE) | ||
169 | #define SWRITE_SYNC (SWRITE | REQ_SYNC | REQ_NOIDLE | REQ_UNPLUG) | ||
167 | 170 | ||
168 | /* | 171 | /* |
169 | * These aren't really reads or writes, they pass down information about | 172 | * These aren't really reads or writes, they pass down information about |
170 | * parts of device that are now unused by the file system. | 173 | * parts of device that are now unused by the file system. |
171 | */ | 174 | */ |
172 | #define DISCARD_NOBARRIER (WRITE | (1 << BIO_RW_DISCARD)) | 175 | #define DISCARD_NOBARRIER (WRITE | REQ_DISCARD) |
173 | #define DISCARD_BARRIER (DISCARD_NOBARRIER | (1 << BIO_RW_BARRIER)) | 176 | #define DISCARD_BARRIER (WRITE | REQ_DISCARD | REQ_HARDBARRIER) |
174 | 177 | ||
175 | #define SEL_IN 1 | 178 | #define SEL_IN 1 |
176 | #define SEL_OUT 2 | 179 | #define SEL_OUT 2 |
@@ -2196,7 +2199,6 @@ static inline void insert_inode_hash(struct inode *inode) { | |||
2196 | extern void file_move(struct file *f, struct list_head *list); | 2199 | extern void file_move(struct file *f, struct list_head *list); |
2197 | extern void file_kill(struct file *f); | 2200 | extern void file_kill(struct file *f); |
2198 | #ifdef CONFIG_BLOCK | 2201 | #ifdef CONFIG_BLOCK |
2199 | struct bio; | ||
2200 | extern void submit_bio(int, struct bio *); | 2202 | extern void submit_bio(int, struct bio *); |
2201 | extern int bdev_read_only(struct block_device *); | 2203 | extern int bdev_read_only(struct block_device *); |
2202 | #endif | 2204 | #endif |
@@ -2263,7 +2265,6 @@ static inline int xip_truncate_page(struct address_space *mapping, loff_t from) | |||
2263 | #endif | 2265 | #endif |
2264 | 2266 | ||
2265 | #ifdef CONFIG_BLOCK | 2267 | #ifdef CONFIG_BLOCK |
2266 | struct bio; | ||
2267 | typedef void (dio_submit_t)(int rw, struct bio *bio, struct inode *inode, | 2268 | typedef void (dio_submit_t)(int rw, struct bio *bio, struct inode *inode, |
2268 | loff_t file_offset); | 2269 | loff_t file_offset); |
2269 | 2270 | ||
diff --git a/include/trace/events/block.h b/include/trace/events/block.h index d870a918559c..d8ce278515c3 100644 --- a/include/trace/events/block.h +++ b/include/trace/events/block.h | |||
@@ -25,8 +25,10 @@ DECLARE_EVENT_CLASS(block_rq_with_error, | |||
25 | 25 | ||
26 | TP_fast_assign( | 26 | TP_fast_assign( |
27 | __entry->dev = rq->rq_disk ? disk_devt(rq->rq_disk) : 0; | 27 | __entry->dev = rq->rq_disk ? disk_devt(rq->rq_disk) : 0; |
28 | __entry->sector = blk_pc_request(rq) ? 0 : blk_rq_pos(rq); | 28 | __entry->sector = (rq->cmd_type == REQ_TYPE_BLOCK_PC) ? |
29 | __entry->nr_sector = blk_pc_request(rq) ? 0 : blk_rq_sectors(rq); | 29 | 0 : blk_rq_pos(rq); |
30 | __entry->nr_sector = (rq->cmd_type == REQ_TYPE_BLOCK_PC) ? | ||
31 | 0 : blk_rq_sectors(rq); | ||
30 | __entry->errors = rq->errors; | 32 | __entry->errors = rq->errors; |
31 | 33 | ||
32 | blk_fill_rwbs_rq(__entry->rwbs, rq); | 34 | blk_fill_rwbs_rq(__entry->rwbs, rq); |
@@ -109,9 +111,12 @@ DECLARE_EVENT_CLASS(block_rq, | |||
109 | 111 | ||
110 | TP_fast_assign( | 112 | TP_fast_assign( |
111 | __entry->dev = rq->rq_disk ? disk_devt(rq->rq_disk) : 0; | 113 | __entry->dev = rq->rq_disk ? disk_devt(rq->rq_disk) : 0; |
112 | __entry->sector = blk_pc_request(rq) ? 0 : blk_rq_pos(rq); | 114 | __entry->sector = (rq->cmd_type == REQ_TYPE_BLOCK_PC) ? |
113 | __entry->nr_sector = blk_pc_request(rq) ? 0 : blk_rq_sectors(rq); | 115 | 0 : blk_rq_pos(rq); |
114 | __entry->bytes = blk_pc_request(rq) ? blk_rq_bytes(rq) : 0; | 116 | __entry->nr_sector = (rq->cmd_type == REQ_TYPE_BLOCK_PC) ? |
117 | 0 : blk_rq_sectors(rq); | ||
118 | __entry->bytes = (rq->cmd_type == REQ_TYPE_BLOCK_PC) ? | ||
119 | blk_rq_bytes(rq) : 0; | ||
115 | 120 | ||
116 | blk_fill_rwbs_rq(__entry->rwbs, rq); | 121 | blk_fill_rwbs_rq(__entry->rwbs, rq); |
117 | blk_dump_cmd(__get_str(cmd), rq); | 122 | blk_dump_cmd(__get_str(cmd), rq); |
diff --git a/include/trace/events/writeback.h b/include/trace/events/writeback.h new file mode 100644 index 000000000000..f345f66ae9d1 --- /dev/null +++ b/include/trace/events/writeback.h | |||
@@ -0,0 +1,159 @@ | |||
1 | #undef TRACE_SYSTEM | ||
2 | #define TRACE_SYSTEM writeback | ||
3 | |||
4 | #if !defined(_TRACE_WRITEBACK_H) || defined(TRACE_HEADER_MULTI_READ) | ||
5 | #define _TRACE_WRITEBACK_H | ||
6 | |||
7 | #include <linux/backing-dev.h> | ||
8 | #include <linux/device.h> | ||
9 | #include <linux/writeback.h> | ||
10 | |||
11 | struct wb_writeback_work; | ||
12 | |||
13 | DECLARE_EVENT_CLASS(writeback_work_class, | ||
14 | TP_PROTO(struct backing_dev_info *bdi, struct wb_writeback_work *work), | ||
15 | TP_ARGS(bdi, work), | ||
16 | TP_STRUCT__entry( | ||
17 | __array(char, name, 32) | ||
18 | __field(long, nr_pages) | ||
19 | __field(dev_t, sb_dev) | ||
20 | __field(int, sync_mode) | ||
21 | __field(int, for_kupdate) | ||
22 | __field(int, range_cyclic) | ||
23 | __field(int, for_background) | ||
24 | ), | ||
25 | TP_fast_assign( | ||
26 | strncpy(__entry->name, dev_name(bdi->dev), 32); | ||
27 | __entry->nr_pages = work->nr_pages; | ||
28 | __entry->sb_dev = work->sb ? work->sb->s_dev : 0; | ||
29 | __entry->sync_mode = work->sync_mode; | ||
30 | __entry->for_kupdate = work->for_kupdate; | ||
31 | __entry->range_cyclic = work->range_cyclic; | ||
32 | __entry->for_background = work->for_background; | ||
33 | ), | ||
34 | TP_printk("bdi %s: sb_dev %d:%d nr_pages=%ld sync_mode=%d " | ||
35 | "kupdate=%d range_cyclic=%d background=%d", | ||
36 | __entry->name, | ||
37 | MAJOR(__entry->sb_dev), MINOR(__entry->sb_dev), | ||
38 | __entry->nr_pages, | ||
39 | __entry->sync_mode, | ||
40 | __entry->for_kupdate, | ||
41 | __entry->range_cyclic, | ||
42 | __entry->for_background | ||
43 | ) | ||
44 | ); | ||
45 | #define DEFINE_WRITEBACK_WORK_EVENT(name) \ | ||
46 | DEFINE_EVENT(writeback_work_class, name, \ | ||
47 | TP_PROTO(struct backing_dev_info *bdi, struct wb_writeback_work *work), \ | ||
48 | TP_ARGS(bdi, work)) | ||
49 | DEFINE_WRITEBACK_WORK_EVENT(writeback_nothread); | ||
50 | DEFINE_WRITEBACK_WORK_EVENT(writeback_queue); | ||
51 | DEFINE_WRITEBACK_WORK_EVENT(writeback_exec); | ||
52 | |||
53 | TRACE_EVENT(writeback_pages_written, | ||
54 | TP_PROTO(long pages_written), | ||
55 | TP_ARGS(pages_written), | ||
56 | TP_STRUCT__entry( | ||
57 | __field(long, pages) | ||
58 | ), | ||
59 | TP_fast_assign( | ||
60 | __entry->pages = pages_written; | ||
61 | ), | ||
62 | TP_printk("%ld", __entry->pages) | ||
63 | ); | ||
64 | |||
65 | DECLARE_EVENT_CLASS(writeback_class, | ||
66 | TP_PROTO(struct backing_dev_info *bdi), | ||
67 | TP_ARGS(bdi), | ||
68 | TP_STRUCT__entry( | ||
69 | __array(char, name, 32) | ||
70 | ), | ||
71 | TP_fast_assign( | ||
72 | strncpy(__entry->name, dev_name(bdi->dev), 32); | ||
73 | ), | ||
74 | TP_printk("bdi %s", | ||
75 | __entry->name | ||
76 | ) | ||
77 | ); | ||
78 | #define DEFINE_WRITEBACK_EVENT(name) \ | ||
79 | DEFINE_EVENT(writeback_class, name, \ | ||
80 | TP_PROTO(struct backing_dev_info *bdi), \ | ||
81 | TP_ARGS(bdi)) | ||
82 | |||
83 | DEFINE_WRITEBACK_EVENT(writeback_nowork); | ||
84 | DEFINE_WRITEBACK_EVENT(writeback_wake_thread); | ||
85 | DEFINE_WRITEBACK_EVENT(writeback_wake_forker_thread); | ||
86 | DEFINE_WRITEBACK_EVENT(writeback_bdi_register); | ||
87 | DEFINE_WRITEBACK_EVENT(writeback_bdi_unregister); | ||
88 | DEFINE_WRITEBACK_EVENT(writeback_thread_start); | ||
89 | DEFINE_WRITEBACK_EVENT(writeback_thread_stop); | ||
90 | |||
91 | DECLARE_EVENT_CLASS(wbc_class, | ||
92 | TP_PROTO(struct writeback_control *wbc, struct backing_dev_info *bdi), | ||
93 | TP_ARGS(wbc, bdi), | ||
94 | TP_STRUCT__entry( | ||
95 | __array(char, name, 32) | ||
96 | __field(long, nr_to_write) | ||
97 | __field(long, pages_skipped) | ||
98 | __field(int, sync_mode) | ||
99 | __field(int, nonblocking) | ||
100 | __field(int, encountered_congestion) | ||
101 | __field(int, for_kupdate) | ||
102 | __field(int, for_background) | ||
103 | __field(int, for_reclaim) | ||
104 | __field(int, range_cyclic) | ||
105 | __field(int, more_io) | ||
106 | __field(unsigned long, older_than_this) | ||
107 | __field(long, range_start) | ||
108 | __field(long, range_end) | ||
109 | ), | ||
110 | |||
111 | TP_fast_assign( | ||
112 | strncpy(__entry->name, dev_name(bdi->dev), 32); | ||
113 | __entry->nr_to_write = wbc->nr_to_write; | ||
114 | __entry->pages_skipped = wbc->pages_skipped; | ||
115 | __entry->sync_mode = wbc->sync_mode; | ||
116 | __entry->for_kupdate = wbc->for_kupdate; | ||
117 | __entry->for_background = wbc->for_background; | ||
118 | __entry->for_reclaim = wbc->for_reclaim; | ||
119 | __entry->range_cyclic = wbc->range_cyclic; | ||
120 | __entry->more_io = wbc->more_io; | ||
121 | __entry->older_than_this = wbc->older_than_this ? | ||
122 | *wbc->older_than_this : 0; | ||
123 | __entry->range_start = (long)wbc->range_start; | ||
124 | __entry->range_end = (long)wbc->range_end; | ||
125 | ), | ||
126 | |||
127 | TP_printk("bdi %s: towrt=%ld skip=%ld mode=%d kupd=%d " | ||
128 | "bgrd=%d reclm=%d cyclic=%d more=%d older=0x%lx " | ||
129 | "start=0x%lx end=0x%lx", | ||
130 | __entry->name, | ||
131 | __entry->nr_to_write, | ||
132 | __entry->pages_skipped, | ||
133 | __entry->sync_mode, | ||
134 | __entry->for_kupdate, | ||
135 | __entry->for_background, | ||
136 | __entry->for_reclaim, | ||
137 | __entry->range_cyclic, | ||
138 | __entry->more_io, | ||
139 | __entry->older_than_this, | ||
140 | __entry->range_start, | ||
141 | __entry->range_end) | ||
142 | ) | ||
143 | |||
144 | #define DEFINE_WBC_EVENT(name) \ | ||
145 | DEFINE_EVENT(wbc_class, name, \ | ||
146 | TP_PROTO(struct writeback_control *wbc, struct backing_dev_info *bdi), \ | ||
147 | TP_ARGS(wbc, bdi)) | ||
148 | DEFINE_WBC_EVENT(wbc_writeback_start); | ||
149 | DEFINE_WBC_EVENT(wbc_writeback_written); | ||
150 | DEFINE_WBC_EVENT(wbc_writeback_wait); | ||
151 | DEFINE_WBC_EVENT(wbc_balance_dirty_start); | ||
152 | DEFINE_WBC_EVENT(wbc_balance_dirty_written); | ||
153 | DEFINE_WBC_EVENT(wbc_balance_dirty_wait); | ||
154 | DEFINE_WBC_EVENT(wbc_writepage); | ||
155 | |||
156 | #endif /* _TRACE_WRITEBACK_H */ | ||
157 | |||
158 | /* This part must be outside protection */ | ||
159 | #include <trace/define_trace.h> | ||
diff --git a/kernel/power/block_io.c b/kernel/power/block_io.c index 97024fd40cd5..83bbc7c02df9 100644 --- a/kernel/power/block_io.c +++ b/kernel/power/block_io.c | |||
@@ -28,7 +28,7 @@ | |||
28 | static int submit(int rw, struct block_device *bdev, sector_t sector, | 28 | static int submit(int rw, struct block_device *bdev, sector_t sector, |
29 | struct page *page, struct bio **bio_chain) | 29 | struct page *page, struct bio **bio_chain) |
30 | { | 30 | { |
31 | const int bio_rw = rw | (1 << BIO_RW_SYNCIO) | (1 << BIO_RW_UNPLUG); | 31 | const int bio_rw = rw | REQ_SYNC | REQ_UNPLUG; |
32 | struct bio *bio; | 32 | struct bio *bio; |
33 | 33 | ||
34 | bio = bio_alloc(__GFP_WAIT | __GFP_HIGH, 1); | 34 | bio = bio_alloc(__GFP_WAIT | __GFP_HIGH, 1); |
diff --git a/kernel/trace/blktrace.c b/kernel/trace/blktrace.c index 638711c17504..82499a5bdcb7 100644 --- a/kernel/trace/blktrace.c +++ b/kernel/trace/blktrace.c | |||
@@ -169,9 +169,12 @@ static int act_log_check(struct blk_trace *bt, u32 what, sector_t sector, | |||
169 | static const u32 ddir_act[2] = { BLK_TC_ACT(BLK_TC_READ), | 169 | static const u32 ddir_act[2] = { BLK_TC_ACT(BLK_TC_READ), |
170 | BLK_TC_ACT(BLK_TC_WRITE) }; | 170 | BLK_TC_ACT(BLK_TC_WRITE) }; |
171 | 171 | ||
172 | #define BLK_TC_HARDBARRIER BLK_TC_BARRIER | ||
173 | #define BLK_TC_RAHEAD BLK_TC_AHEAD | ||
174 | |||
172 | /* The ilog2() calls fall out because they're constant */ | 175 | /* The ilog2() calls fall out because they're constant */ |
173 | #define MASK_TC_BIT(rw, __name) ((rw & (1 << BIO_RW_ ## __name)) << \ | 176 | #define MASK_TC_BIT(rw, __name) ((rw & REQ_ ## __name) << \ |
174 | (ilog2(BLK_TC_ ## __name) + BLK_TC_SHIFT - BIO_RW_ ## __name)) | 177 | (ilog2(BLK_TC_ ## __name) + BLK_TC_SHIFT - __REQ_ ## __name)) |
175 | 178 | ||
176 | /* | 179 | /* |
177 | * The worker for the various blk_add_trace*() types. Fills out a | 180 | * The worker for the various blk_add_trace*() types. Fills out a |
@@ -194,9 +197,9 @@ static void __blk_add_trace(struct blk_trace *bt, sector_t sector, int bytes, | |||
194 | return; | 197 | return; |
195 | 198 | ||
196 | what |= ddir_act[rw & WRITE]; | 199 | what |= ddir_act[rw & WRITE]; |
197 | what |= MASK_TC_BIT(rw, BARRIER); | 200 | what |= MASK_TC_BIT(rw, HARDBARRIER); |
198 | what |= MASK_TC_BIT(rw, SYNCIO); | 201 | what |= MASK_TC_BIT(rw, SYNC); |
199 | what |= MASK_TC_BIT(rw, AHEAD); | 202 | what |= MASK_TC_BIT(rw, RAHEAD); |
200 | what |= MASK_TC_BIT(rw, META); | 203 | what |= MASK_TC_BIT(rw, META); |
201 | what |= MASK_TC_BIT(rw, DISCARD); | 204 | what |= MASK_TC_BIT(rw, DISCARD); |
202 | 205 | ||
@@ -549,6 +552,41 @@ int blk_trace_setup(struct request_queue *q, char *name, dev_t dev, | |||
549 | } | 552 | } |
550 | EXPORT_SYMBOL_GPL(blk_trace_setup); | 553 | EXPORT_SYMBOL_GPL(blk_trace_setup); |
551 | 554 | ||
555 | #if defined(CONFIG_COMPAT) && defined(CONFIG_X86_64) | ||
556 | static int compat_blk_trace_setup(struct request_queue *q, char *name, | ||
557 | dev_t dev, struct block_device *bdev, | ||
558 | char __user *arg) | ||
559 | { | ||
560 | struct blk_user_trace_setup buts; | ||
561 | struct compat_blk_user_trace_setup cbuts; | ||
562 | int ret; | ||
563 | |||
564 | if (copy_from_user(&cbuts, arg, sizeof(cbuts))) | ||
565 | return -EFAULT; | ||
566 | |||
567 | buts = (struct blk_user_trace_setup) { | ||
568 | .act_mask = cbuts.act_mask, | ||
569 | .buf_size = cbuts.buf_size, | ||
570 | .buf_nr = cbuts.buf_nr, | ||
571 | .start_lba = cbuts.start_lba, | ||
572 | .end_lba = cbuts.end_lba, | ||
573 | .pid = cbuts.pid, | ||
574 | }; | ||
575 | memcpy(&buts.name, &cbuts.name, 32); | ||
576 | |||
577 | ret = do_blk_trace_setup(q, name, dev, bdev, &buts); | ||
578 | if (ret) | ||
579 | return ret; | ||
580 | |||
581 | if (copy_to_user(arg, &buts.name, 32)) { | ||
582 | blk_trace_remove(q); | ||
583 | return -EFAULT; | ||
584 | } | ||
585 | |||
586 | return 0; | ||
587 | } | ||
588 | #endif | ||
589 | |||
552 | int blk_trace_startstop(struct request_queue *q, int start) | 590 | int blk_trace_startstop(struct request_queue *q, int start) |
553 | { | 591 | { |
554 | int ret; | 592 | int ret; |
@@ -601,6 +639,7 @@ int blk_trace_ioctl(struct block_device *bdev, unsigned cmd, char __user *arg) | |||
601 | if (!q) | 639 | if (!q) |
602 | return -ENXIO; | 640 | return -ENXIO; |
603 | 641 | ||
642 | lock_kernel(); | ||
604 | mutex_lock(&bdev->bd_mutex); | 643 | mutex_lock(&bdev->bd_mutex); |
605 | 644 | ||
606 | switch (cmd) { | 645 | switch (cmd) { |
@@ -608,6 +647,12 @@ int blk_trace_ioctl(struct block_device *bdev, unsigned cmd, char __user *arg) | |||
608 | bdevname(bdev, b); | 647 | bdevname(bdev, b); |
609 | ret = blk_trace_setup(q, b, bdev->bd_dev, bdev, arg); | 648 | ret = blk_trace_setup(q, b, bdev->bd_dev, bdev, arg); |
610 | break; | 649 | break; |
650 | #if defined(CONFIG_COMPAT) && defined(CONFIG_X86_64) | ||
651 | case BLKTRACESETUP32: | ||
652 | bdevname(bdev, b); | ||
653 | ret = compat_blk_trace_setup(q, b, bdev->bd_dev, bdev, arg); | ||
654 | break; | ||
655 | #endif | ||
611 | case BLKTRACESTART: | 656 | case BLKTRACESTART: |
612 | start = 1; | 657 | start = 1; |
613 | case BLKTRACESTOP: | 658 | case BLKTRACESTOP: |
@@ -622,6 +667,7 @@ int blk_trace_ioctl(struct block_device *bdev, unsigned cmd, char __user *arg) | |||
622 | } | 667 | } |
623 | 668 | ||
624 | mutex_unlock(&bdev->bd_mutex); | 669 | mutex_unlock(&bdev->bd_mutex); |
670 | unlock_kernel(); | ||
625 | return ret; | 671 | return ret; |
626 | } | 672 | } |
627 | 673 | ||
@@ -661,10 +707,10 @@ static void blk_add_trace_rq(struct request_queue *q, struct request *rq, | |||
661 | if (likely(!bt)) | 707 | if (likely(!bt)) |
662 | return; | 708 | return; |
663 | 709 | ||
664 | if (blk_discard_rq(rq)) | 710 | if (rq->cmd_flags & REQ_DISCARD) |
665 | rw |= (1 << BIO_RW_DISCARD); | 711 | rw |= REQ_DISCARD; |
666 | 712 | ||
667 | if (blk_pc_request(rq)) { | 713 | if (rq->cmd_type == REQ_TYPE_BLOCK_PC) { |
668 | what |= BLK_TC_ACT(BLK_TC_PC); | 714 | what |= BLK_TC_ACT(BLK_TC_PC); |
669 | __blk_add_trace(bt, 0, blk_rq_bytes(rq), rw, | 715 | __blk_add_trace(bt, 0, blk_rq_bytes(rq), rw, |
670 | what, rq->errors, rq->cmd_len, rq->cmd); | 716 | what, rq->errors, rq->cmd_len, rq->cmd); |
@@ -925,7 +971,7 @@ void blk_add_driver_data(struct request_queue *q, | |||
925 | if (likely(!bt)) | 971 | if (likely(!bt)) |
926 | return; | 972 | return; |
927 | 973 | ||
928 | if (blk_pc_request(rq)) | 974 | if (rq->cmd_type == REQ_TYPE_BLOCK_PC) |
929 | __blk_add_trace(bt, 0, blk_rq_bytes(rq), 0, | 975 | __blk_add_trace(bt, 0, blk_rq_bytes(rq), 0, |
930 | BLK_TA_DRV_DATA, rq->errors, len, data); | 976 | BLK_TA_DRV_DATA, rq->errors, len, data); |
931 | else | 977 | else |
@@ -1730,7 +1776,7 @@ void blk_dump_cmd(char *buf, struct request *rq) | |||
1730 | int len = rq->cmd_len; | 1776 | int len = rq->cmd_len; |
1731 | unsigned char *cmd = rq->cmd; | 1777 | unsigned char *cmd = rq->cmd; |
1732 | 1778 | ||
1733 | if (!blk_pc_request(rq)) { | 1779 | if (rq->cmd_type != REQ_TYPE_BLOCK_PC) { |
1734 | buf[0] = '\0'; | 1780 | buf[0] = '\0'; |
1735 | return; | 1781 | return; |
1736 | } | 1782 | } |
@@ -1755,20 +1801,20 @@ void blk_fill_rwbs(char *rwbs, u32 rw, int bytes) | |||
1755 | 1801 | ||
1756 | if (rw & WRITE) | 1802 | if (rw & WRITE) |
1757 | rwbs[i++] = 'W'; | 1803 | rwbs[i++] = 'W'; |
1758 | else if (rw & 1 << BIO_RW_DISCARD) | 1804 | else if (rw & REQ_DISCARD) |
1759 | rwbs[i++] = 'D'; | 1805 | rwbs[i++] = 'D'; |
1760 | else if (bytes) | 1806 | else if (bytes) |
1761 | rwbs[i++] = 'R'; | 1807 | rwbs[i++] = 'R'; |
1762 | else | 1808 | else |
1763 | rwbs[i++] = 'N'; | 1809 | rwbs[i++] = 'N'; |
1764 | 1810 | ||
1765 | if (rw & 1 << BIO_RW_AHEAD) | 1811 | if (rw & REQ_RAHEAD) |
1766 | rwbs[i++] = 'A'; | 1812 | rwbs[i++] = 'A'; |
1767 | if (rw & 1 << BIO_RW_BARRIER) | 1813 | if (rw & REQ_HARDBARRIER) |
1768 | rwbs[i++] = 'B'; | 1814 | rwbs[i++] = 'B'; |
1769 | if (rw & 1 << BIO_RW_SYNCIO) | 1815 | if (rw & REQ_SYNC) |
1770 | rwbs[i++] = 'S'; | 1816 | rwbs[i++] = 'S'; |
1771 | if (rw & 1 << BIO_RW_META) | 1817 | if (rw & REQ_META) |
1772 | rwbs[i++] = 'M'; | 1818 | rwbs[i++] = 'M'; |
1773 | 1819 | ||
1774 | rwbs[i] = '\0'; | 1820 | rwbs[i] = '\0'; |
@@ -1779,8 +1825,8 @@ void blk_fill_rwbs_rq(char *rwbs, struct request *rq) | |||
1779 | int rw = rq->cmd_flags & 0x03; | 1825 | int rw = rq->cmd_flags & 0x03; |
1780 | int bytes; | 1826 | int bytes; |
1781 | 1827 | ||
1782 | if (blk_discard_rq(rq)) | 1828 | if (rq->cmd_flags & REQ_DISCARD) |
1783 | rw |= (1 << BIO_RW_DISCARD); | 1829 | rw |= REQ_DISCARD; |
1784 | 1830 | ||
1785 | bytes = blk_rq_bytes(rq); | 1831 | bytes = blk_rq_bytes(rq); |
1786 | 1832 | ||
diff --git a/mm/backing-dev.c b/mm/backing-dev.c index f9fd3dd3916b..08d357522e78 100644 --- a/mm/backing-dev.c +++ b/mm/backing-dev.c | |||
@@ -10,6 +10,7 @@ | |||
10 | #include <linux/module.h> | 10 | #include <linux/module.h> |
11 | #include <linux/writeback.h> | 11 | #include <linux/writeback.h> |
12 | #include <linux/device.h> | 12 | #include <linux/device.h> |
13 | #include <trace/events/writeback.h> | ||
13 | 14 | ||
14 | static atomic_long_t bdi_seq = ATOMIC_LONG_INIT(0); | 15 | static atomic_long_t bdi_seq = ATOMIC_LONG_INIT(0); |
15 | 16 | ||
@@ -49,8 +50,6 @@ static struct timer_list sync_supers_timer; | |||
49 | static int bdi_sync_supers(void *); | 50 | static int bdi_sync_supers(void *); |
50 | static void sync_supers_timer_fn(unsigned long); | 51 | static void sync_supers_timer_fn(unsigned long); |
51 | 52 | ||
52 | static void bdi_add_default_flusher_task(struct backing_dev_info *bdi); | ||
53 | |||
54 | #ifdef CONFIG_DEBUG_FS | 53 | #ifdef CONFIG_DEBUG_FS |
55 | #include <linux/debugfs.h> | 54 | #include <linux/debugfs.h> |
56 | #include <linux/seq_file.h> | 55 | #include <linux/seq_file.h> |
@@ -65,28 +64,21 @@ static void bdi_debug_init(void) | |||
65 | static int bdi_debug_stats_show(struct seq_file *m, void *v) | 64 | static int bdi_debug_stats_show(struct seq_file *m, void *v) |
66 | { | 65 | { |
67 | struct backing_dev_info *bdi = m->private; | 66 | struct backing_dev_info *bdi = m->private; |
68 | struct bdi_writeback *wb; | 67 | struct bdi_writeback *wb = &bdi->wb; |
69 | unsigned long background_thresh; | 68 | unsigned long background_thresh; |
70 | unsigned long dirty_thresh; | 69 | unsigned long dirty_thresh; |
71 | unsigned long bdi_thresh; | 70 | unsigned long bdi_thresh; |
72 | unsigned long nr_dirty, nr_io, nr_more_io, nr_wb; | 71 | unsigned long nr_dirty, nr_io, nr_more_io, nr_wb; |
73 | struct inode *inode; | 72 | struct inode *inode; |
74 | 73 | ||
75 | /* | ||
76 | * inode lock is enough here, the bdi->wb_list is protected by | ||
77 | * RCU on the reader side | ||
78 | */ | ||
79 | nr_wb = nr_dirty = nr_io = nr_more_io = 0; | 74 | nr_wb = nr_dirty = nr_io = nr_more_io = 0; |
80 | spin_lock(&inode_lock); | 75 | spin_lock(&inode_lock); |
81 | list_for_each_entry(wb, &bdi->wb_list, list) { | 76 | list_for_each_entry(inode, &wb->b_dirty, i_list) |
82 | nr_wb++; | 77 | nr_dirty++; |
83 | list_for_each_entry(inode, &wb->b_dirty, i_list) | 78 | list_for_each_entry(inode, &wb->b_io, i_list) |
84 | nr_dirty++; | 79 | nr_io++; |
85 | list_for_each_entry(inode, &wb->b_io, i_list) | 80 | list_for_each_entry(inode, &wb->b_more_io, i_list) |
86 | nr_io++; | 81 | nr_more_io++; |
87 | list_for_each_entry(inode, &wb->b_more_io, i_list) | ||
88 | nr_more_io++; | ||
89 | } | ||
90 | spin_unlock(&inode_lock); | 82 | spin_unlock(&inode_lock); |
91 | 83 | ||
92 | get_dirty_limits(&background_thresh, &dirty_thresh, &bdi_thresh, bdi); | 84 | get_dirty_limits(&background_thresh, &dirty_thresh, &bdi_thresh, bdi); |
@@ -98,19 +90,16 @@ static int bdi_debug_stats_show(struct seq_file *m, void *v) | |||
98 | "BdiDirtyThresh: %8lu kB\n" | 90 | "BdiDirtyThresh: %8lu kB\n" |
99 | "DirtyThresh: %8lu kB\n" | 91 | "DirtyThresh: %8lu kB\n" |
100 | "BackgroundThresh: %8lu kB\n" | 92 | "BackgroundThresh: %8lu kB\n" |
101 | "WritebackThreads: %8lu\n" | ||
102 | "b_dirty: %8lu\n" | 93 | "b_dirty: %8lu\n" |
103 | "b_io: %8lu\n" | 94 | "b_io: %8lu\n" |
104 | "b_more_io: %8lu\n" | 95 | "b_more_io: %8lu\n" |
105 | "bdi_list: %8u\n" | 96 | "bdi_list: %8u\n" |
106 | "state: %8lx\n" | 97 | "state: %8lx\n", |
107 | "wb_list: %8u\n", | ||
108 | (unsigned long) K(bdi_stat(bdi, BDI_WRITEBACK)), | 98 | (unsigned long) K(bdi_stat(bdi, BDI_WRITEBACK)), |
109 | (unsigned long) K(bdi_stat(bdi, BDI_RECLAIMABLE)), | 99 | (unsigned long) K(bdi_stat(bdi, BDI_RECLAIMABLE)), |
110 | K(bdi_thresh), K(dirty_thresh), | 100 | K(bdi_thresh), K(dirty_thresh), |
111 | K(background_thresh), nr_wb, nr_dirty, nr_io, nr_more_io, | 101 | K(background_thresh), nr_dirty, nr_io, nr_more_io, |
112 | !list_empty(&bdi->bdi_list), bdi->state, | 102 | !list_empty(&bdi->bdi_list), bdi->state); |
113 | !list_empty(&bdi->wb_list)); | ||
114 | #undef K | 103 | #undef K |
115 | 104 | ||
116 | return 0; | 105 | return 0; |
@@ -247,7 +236,6 @@ static int __init default_bdi_init(void) | |||
247 | sync_supers_tsk = kthread_run(bdi_sync_supers, NULL, "sync_supers"); | 236 | sync_supers_tsk = kthread_run(bdi_sync_supers, NULL, "sync_supers"); |
248 | BUG_ON(IS_ERR(sync_supers_tsk)); | 237 | BUG_ON(IS_ERR(sync_supers_tsk)); |
249 | 238 | ||
250 | init_timer(&sync_supers_timer); | ||
251 | setup_timer(&sync_supers_timer, sync_supers_timer_fn, 0); | 239 | setup_timer(&sync_supers_timer, sync_supers_timer_fn, 0); |
252 | bdi_arm_supers_timer(); | 240 | bdi_arm_supers_timer(); |
253 | 241 | ||
@@ -259,77 +247,6 @@ static int __init default_bdi_init(void) | |||
259 | } | 247 | } |
260 | subsys_initcall(default_bdi_init); | 248 | subsys_initcall(default_bdi_init); |
261 | 249 | ||
262 | static void bdi_wb_init(struct bdi_writeback *wb, struct backing_dev_info *bdi) | ||
263 | { | ||
264 | memset(wb, 0, sizeof(*wb)); | ||
265 | |||
266 | wb->bdi = bdi; | ||
267 | wb->last_old_flush = jiffies; | ||
268 | INIT_LIST_HEAD(&wb->b_dirty); | ||
269 | INIT_LIST_HEAD(&wb->b_io); | ||
270 | INIT_LIST_HEAD(&wb->b_more_io); | ||
271 | } | ||
272 | |||
273 | static void bdi_task_init(struct backing_dev_info *bdi, | ||
274 | struct bdi_writeback *wb) | ||
275 | { | ||
276 | struct task_struct *tsk = current; | ||
277 | |||
278 | spin_lock(&bdi->wb_lock); | ||
279 | list_add_tail_rcu(&wb->list, &bdi->wb_list); | ||
280 | spin_unlock(&bdi->wb_lock); | ||
281 | |||
282 | tsk->flags |= PF_FLUSHER | PF_SWAPWRITE; | ||
283 | set_freezable(); | ||
284 | |||
285 | /* | ||
286 | * Our parent may run at a different priority, just set us to normal | ||
287 | */ | ||
288 | set_user_nice(tsk, 0); | ||
289 | } | ||
290 | |||
291 | static int bdi_start_fn(void *ptr) | ||
292 | { | ||
293 | struct bdi_writeback *wb = ptr; | ||
294 | struct backing_dev_info *bdi = wb->bdi; | ||
295 | int ret; | ||
296 | |||
297 | /* | ||
298 | * Add us to the active bdi_list | ||
299 | */ | ||
300 | spin_lock_bh(&bdi_lock); | ||
301 | list_add_rcu(&bdi->bdi_list, &bdi_list); | ||
302 | spin_unlock_bh(&bdi_lock); | ||
303 | |||
304 | bdi_task_init(bdi, wb); | ||
305 | |||
306 | /* | ||
307 | * Clear pending bit and wakeup anybody waiting to tear us down | ||
308 | */ | ||
309 | clear_bit(BDI_pending, &bdi->state); | ||
310 | smp_mb__after_clear_bit(); | ||
311 | wake_up_bit(&bdi->state, BDI_pending); | ||
312 | |||
313 | ret = bdi_writeback_task(wb); | ||
314 | |||
315 | /* | ||
316 | * Remove us from the list | ||
317 | */ | ||
318 | spin_lock(&bdi->wb_lock); | ||
319 | list_del_rcu(&wb->list); | ||
320 | spin_unlock(&bdi->wb_lock); | ||
321 | |||
322 | /* | ||
323 | * Flush any work that raced with us exiting. No new work | ||
324 | * will be added, since this bdi isn't discoverable anymore. | ||
325 | */ | ||
326 | if (!list_empty(&bdi->work_list)) | ||
327 | wb_do_writeback(wb, 1); | ||
328 | |||
329 | wb->task = NULL; | ||
330 | return ret; | ||
331 | } | ||
332 | |||
333 | int bdi_has_dirty_io(struct backing_dev_info *bdi) | 250 | int bdi_has_dirty_io(struct backing_dev_info *bdi) |
334 | { | 251 | { |
335 | return wb_has_dirty_io(&bdi->wb); | 252 | return wb_has_dirty_io(&bdi->wb); |
@@ -348,10 +265,10 @@ static void bdi_flush_io(struct backing_dev_info *bdi) | |||
348 | } | 265 | } |
349 | 266 | ||
350 | /* | 267 | /* |
351 | * kupdated() used to do this. We cannot do it from the bdi_forker_task() | 268 | * kupdated() used to do this. We cannot do it from the bdi_forker_thread() |
352 | * or we risk deadlocking on ->s_umount. The longer term solution would be | 269 | * or we risk deadlocking on ->s_umount. The longer term solution would be |
353 | * to implement sync_supers_bdi() or similar and simply do it from the | 270 | * to implement sync_supers_bdi() or similar and simply do it from the |
354 | * bdi writeback tasks individually. | 271 | * bdi writeback thread individually. |
355 | */ | 272 | */ |
356 | static int bdi_sync_supers(void *unused) | 273 | static int bdi_sync_supers(void *unused) |
357 | { | 274 | { |
@@ -387,144 +304,198 @@ static void sync_supers_timer_fn(unsigned long unused) | |||
387 | bdi_arm_supers_timer(); | 304 | bdi_arm_supers_timer(); |
388 | } | 305 | } |
389 | 306 | ||
390 | static int bdi_forker_task(void *ptr) | 307 | static void wakeup_timer_fn(unsigned long data) |
308 | { | ||
309 | struct backing_dev_info *bdi = (struct backing_dev_info *)data; | ||
310 | |||
311 | spin_lock_bh(&bdi->wb_lock); | ||
312 | if (bdi->wb.task) { | ||
313 | trace_writeback_wake_thread(bdi); | ||
314 | wake_up_process(bdi->wb.task); | ||
315 | } else { | ||
316 | /* | ||
317 | * When bdi tasks are inactive for long time, they are killed. | ||
318 | * In this case we have to wake-up the forker thread which | ||
319 | * should create and run the bdi thread. | ||
320 | */ | ||
321 | trace_writeback_wake_forker_thread(bdi); | ||
322 | wake_up_process(default_backing_dev_info.wb.task); | ||
323 | } | ||
324 | spin_unlock_bh(&bdi->wb_lock); | ||
325 | } | ||
326 | |||
327 | /* | ||
328 | * This function is used when the first inode for this bdi is marked dirty. It | ||
329 | * wakes-up the corresponding bdi thread which should then take care of the | ||
330 | * periodic background write-out of dirty inodes. Since the write-out would | ||
331 | * starts only 'dirty_writeback_interval' centisecs from now anyway, we just | ||
332 | * set up a timer which wakes the bdi thread up later. | ||
333 | * | ||
334 | * Note, we wouldn't bother setting up the timer, but this function is on the | ||
335 | * fast-path (used by '__mark_inode_dirty()'), so we save few context switches | ||
336 | * by delaying the wake-up. | ||
337 | */ | ||
338 | void bdi_wakeup_thread_delayed(struct backing_dev_info *bdi) | ||
339 | { | ||
340 | unsigned long timeout; | ||
341 | |||
342 | timeout = msecs_to_jiffies(dirty_writeback_interval * 10); | ||
343 | mod_timer(&bdi->wb.wakeup_timer, jiffies + timeout); | ||
344 | } | ||
345 | |||
346 | /* | ||
347 | * Calculate the longest interval (jiffies) bdi threads are allowed to be | ||
348 | * inactive. | ||
349 | */ | ||
350 | static unsigned long bdi_longest_inactive(void) | ||
351 | { | ||
352 | unsigned long interval; | ||
353 | |||
354 | interval = msecs_to_jiffies(dirty_writeback_interval * 10); | ||
355 | return max(5UL * 60 * HZ, interval); | ||
356 | } | ||
357 | |||
358 | static int bdi_forker_thread(void *ptr) | ||
391 | { | 359 | { |
392 | struct bdi_writeback *me = ptr; | 360 | struct bdi_writeback *me = ptr; |
393 | 361 | ||
394 | bdi_task_init(me->bdi, me); | 362 | current->flags |= PF_FLUSHER | PF_SWAPWRITE; |
363 | set_freezable(); | ||
364 | |||
365 | /* | ||
366 | * Our parent may run at a different priority, just set us to normal | ||
367 | */ | ||
368 | set_user_nice(current, 0); | ||
395 | 369 | ||
396 | for (;;) { | 370 | for (;;) { |
397 | struct backing_dev_info *bdi, *tmp; | 371 | struct task_struct *task = NULL; |
398 | struct bdi_writeback *wb; | 372 | struct backing_dev_info *bdi; |
373 | enum { | ||
374 | NO_ACTION, /* Nothing to do */ | ||
375 | FORK_THREAD, /* Fork bdi thread */ | ||
376 | KILL_THREAD, /* Kill inactive bdi thread */ | ||
377 | } action = NO_ACTION; | ||
399 | 378 | ||
400 | /* | 379 | /* |
401 | * Temporary measure, we want to make sure we don't see | 380 | * Temporary measure, we want to make sure we don't see |
402 | * dirty data on the default backing_dev_info | 381 | * dirty data on the default backing_dev_info |
403 | */ | 382 | */ |
404 | if (wb_has_dirty_io(me) || !list_empty(&me->bdi->work_list)) | 383 | if (wb_has_dirty_io(me) || !list_empty(&me->bdi->work_list)) { |
384 | del_timer(&me->wakeup_timer); | ||
405 | wb_do_writeback(me, 0); | 385 | wb_do_writeback(me, 0); |
386 | } | ||
406 | 387 | ||
407 | spin_lock_bh(&bdi_lock); | 388 | spin_lock_bh(&bdi_lock); |
389 | set_current_state(TASK_INTERRUPTIBLE); | ||
408 | 390 | ||
409 | /* | 391 | list_for_each_entry(bdi, &bdi_list, bdi_list) { |
410 | * Check if any existing bdi's have dirty data without | 392 | bool have_dirty_io; |
411 | * a thread registered. If so, set that up. | 393 | |
412 | */ | 394 | if (!bdi_cap_writeback_dirty(bdi) || |
413 | list_for_each_entry_safe(bdi, tmp, &bdi_list, bdi_list) { | 395 | bdi_cap_flush_forker(bdi)) |
414 | if (bdi->wb.task) | ||
415 | continue; | ||
416 | if (list_empty(&bdi->work_list) && | ||
417 | !bdi_has_dirty_io(bdi)) | ||
418 | continue; | 396 | continue; |
419 | 397 | ||
420 | bdi_add_default_flusher_task(bdi); | 398 | WARN(!test_bit(BDI_registered, &bdi->state), |
421 | } | 399 | "bdi %p/%s is not registered!\n", bdi, bdi->name); |
422 | 400 | ||
423 | set_current_state(TASK_INTERRUPTIBLE); | 401 | have_dirty_io = !list_empty(&bdi->work_list) || |
402 | wb_has_dirty_io(&bdi->wb); | ||
424 | 403 | ||
425 | if (list_empty(&bdi_pending_list)) { | 404 | /* |
426 | unsigned long wait; | 405 | * If the bdi has work to do, but the thread does not |
406 | * exist - create it. | ||
407 | */ | ||
408 | if (!bdi->wb.task && have_dirty_io) { | ||
409 | /* | ||
410 | * Set the pending bit - if someone will try to | ||
411 | * unregister this bdi - it'll wait on this bit. | ||
412 | */ | ||
413 | set_bit(BDI_pending, &bdi->state); | ||
414 | action = FORK_THREAD; | ||
415 | break; | ||
416 | } | ||
417 | |||
418 | spin_lock(&bdi->wb_lock); | ||
419 | |||
420 | /* | ||
421 | * If there is no work to do and the bdi thread was | ||
422 | * inactive long enough - kill it. The wb_lock is taken | ||
423 | * to make sure no-one adds more work to this bdi and | ||
424 | * wakes the bdi thread up. | ||
425 | */ | ||
426 | if (bdi->wb.task && !have_dirty_io && | ||
427 | time_after(jiffies, bdi->wb.last_active + | ||
428 | bdi_longest_inactive())) { | ||
429 | task = bdi->wb.task; | ||
430 | bdi->wb.task = NULL; | ||
431 | spin_unlock(&bdi->wb_lock); | ||
432 | set_bit(BDI_pending, &bdi->state); | ||
433 | action = KILL_THREAD; | ||
434 | break; | ||
435 | } | ||
436 | spin_unlock(&bdi->wb_lock); | ||
437 | } | ||
438 | spin_unlock_bh(&bdi_lock); | ||
427 | 439 | ||
428 | spin_unlock_bh(&bdi_lock); | 440 | /* Keep working if default bdi still has things to do */ |
429 | wait = msecs_to_jiffies(dirty_writeback_interval * 10); | 441 | if (!list_empty(&me->bdi->work_list)) |
430 | if (wait) | 442 | __set_current_state(TASK_RUNNING); |
431 | schedule_timeout(wait); | 443 | |
444 | switch (action) { | ||
445 | case FORK_THREAD: | ||
446 | __set_current_state(TASK_RUNNING); | ||
447 | task = kthread_run(bdi_writeback_thread, &bdi->wb, "flush-%s", | ||
448 | dev_name(bdi->dev)); | ||
449 | if (IS_ERR(task)) { | ||
450 | /* | ||
451 | * If thread creation fails, force writeout of | ||
452 | * the bdi from the thread. | ||
453 | */ | ||
454 | bdi_flush_io(bdi); | ||
455 | } else { | ||
456 | /* | ||
457 | * The spinlock makes sure we do not lose | ||
458 | * wake-ups when racing with 'bdi_queue_work()'. | ||
459 | */ | ||
460 | spin_lock_bh(&bdi->wb_lock); | ||
461 | bdi->wb.task = task; | ||
462 | spin_unlock_bh(&bdi->wb_lock); | ||
463 | } | ||
464 | break; | ||
465 | |||
466 | case KILL_THREAD: | ||
467 | __set_current_state(TASK_RUNNING); | ||
468 | kthread_stop(task); | ||
469 | break; | ||
470 | |||
471 | case NO_ACTION: | ||
472 | if (!wb_has_dirty_io(me) || !dirty_writeback_interval) | ||
473 | /* | ||
474 | * There are no dirty data. The only thing we | ||
475 | * should now care about is checking for | ||
476 | * inactive bdi threads and killing them. Thus, | ||
477 | * let's sleep for longer time, save energy and | ||
478 | * be friendly for battery-driven devices. | ||
479 | */ | ||
480 | schedule_timeout(bdi_longest_inactive()); | ||
432 | else | 481 | else |
433 | schedule(); | 482 | schedule_timeout(msecs_to_jiffies(dirty_writeback_interval * 10)); |
434 | try_to_freeze(); | 483 | try_to_freeze(); |
484 | /* Back to the main loop */ | ||
435 | continue; | 485 | continue; |
436 | } | 486 | } |
437 | 487 | ||
438 | __set_current_state(TASK_RUNNING); | ||
439 | |||
440 | /* | ||
441 | * This is our real job - check for pending entries in | ||
442 | * bdi_pending_list, and create the tasks that got added | ||
443 | */ | ||
444 | bdi = list_entry(bdi_pending_list.next, struct backing_dev_info, | ||
445 | bdi_list); | ||
446 | list_del_init(&bdi->bdi_list); | ||
447 | spin_unlock_bh(&bdi_lock); | ||
448 | |||
449 | wb = &bdi->wb; | ||
450 | wb->task = kthread_run(bdi_start_fn, wb, "flush-%s", | ||
451 | dev_name(bdi->dev)); | ||
452 | /* | 488 | /* |
453 | * If task creation fails, then readd the bdi to | 489 | * Clear pending bit and wakeup anybody waiting to tear us down. |
454 | * the pending list and force writeout of the bdi | ||
455 | * from this forker thread. That will free some memory | ||
456 | * and we can try again. | ||
457 | */ | 490 | */ |
458 | if (IS_ERR(wb->task)) { | 491 | clear_bit(BDI_pending, &bdi->state); |
459 | wb->task = NULL; | 492 | smp_mb__after_clear_bit(); |
460 | 493 | wake_up_bit(&bdi->state, BDI_pending); | |
461 | /* | ||
462 | * Add this 'bdi' to the back, so we get | ||
463 | * a chance to flush other bdi's to free | ||
464 | * memory. | ||
465 | */ | ||
466 | spin_lock_bh(&bdi_lock); | ||
467 | list_add_tail(&bdi->bdi_list, &bdi_pending_list); | ||
468 | spin_unlock_bh(&bdi_lock); | ||
469 | |||
470 | bdi_flush_io(bdi); | ||
471 | } | ||
472 | } | 494 | } |
473 | 495 | ||
474 | return 0; | 496 | return 0; |
475 | } | 497 | } |
476 | 498 | ||
477 | static void bdi_add_to_pending(struct rcu_head *head) | ||
478 | { | ||
479 | struct backing_dev_info *bdi; | ||
480 | |||
481 | bdi = container_of(head, struct backing_dev_info, rcu_head); | ||
482 | INIT_LIST_HEAD(&bdi->bdi_list); | ||
483 | |||
484 | spin_lock(&bdi_lock); | ||
485 | list_add_tail(&bdi->bdi_list, &bdi_pending_list); | ||
486 | spin_unlock(&bdi_lock); | ||
487 | |||
488 | /* | ||
489 | * We are now on the pending list, wake up bdi_forker_task() | ||
490 | * to finish the job and add us back to the active bdi_list | ||
491 | */ | ||
492 | wake_up_process(default_backing_dev_info.wb.task); | ||
493 | } | ||
494 | |||
495 | /* | ||
496 | * Add the default flusher task that gets created for any bdi | ||
497 | * that has dirty data pending writeout | ||
498 | */ | ||
499 | void static bdi_add_default_flusher_task(struct backing_dev_info *bdi) | ||
500 | { | ||
501 | if (!bdi_cap_writeback_dirty(bdi)) | ||
502 | return; | ||
503 | |||
504 | if (WARN_ON(!test_bit(BDI_registered, &bdi->state))) { | ||
505 | printk(KERN_ERR "bdi %p/%s is not registered!\n", | ||
506 | bdi, bdi->name); | ||
507 | return; | ||
508 | } | ||
509 | |||
510 | /* | ||
511 | * Check with the helper whether to proceed adding a task. Will only | ||
512 | * abort if we two or more simultanous calls to | ||
513 | * bdi_add_default_flusher_task() occured, further additions will block | ||
514 | * waiting for previous additions to finish. | ||
515 | */ | ||
516 | if (!test_and_set_bit(BDI_pending, &bdi->state)) { | ||
517 | list_del_rcu(&bdi->bdi_list); | ||
518 | |||
519 | /* | ||
520 | * We must wait for the current RCU period to end before | ||
521 | * moving to the pending list. So schedule that operation | ||
522 | * from an RCU callback. | ||
523 | */ | ||
524 | call_rcu(&bdi->rcu_head, bdi_add_to_pending); | ||
525 | } | ||
526 | } | ||
527 | |||
528 | /* | 499 | /* |
529 | * Remove bdi from bdi_list, and ensure that it is no longer visible | 500 | * Remove bdi from bdi_list, and ensure that it is no longer visible |
530 | */ | 501 | */ |
@@ -541,23 +512,16 @@ int bdi_register(struct backing_dev_info *bdi, struct device *parent, | |||
541 | const char *fmt, ...) | 512 | const char *fmt, ...) |
542 | { | 513 | { |
543 | va_list args; | 514 | va_list args; |
544 | int ret = 0; | ||
545 | struct device *dev; | 515 | struct device *dev; |
546 | 516 | ||
547 | if (bdi->dev) /* The driver needs to use separate queues per device */ | 517 | if (bdi->dev) /* The driver needs to use separate queues per device */ |
548 | goto exit; | 518 | return 0; |
549 | 519 | ||
550 | va_start(args, fmt); | 520 | va_start(args, fmt); |
551 | dev = device_create_vargs(bdi_class, parent, MKDEV(0, 0), bdi, fmt, args); | 521 | dev = device_create_vargs(bdi_class, parent, MKDEV(0, 0), bdi, fmt, args); |
552 | va_end(args); | 522 | va_end(args); |
553 | if (IS_ERR(dev)) { | 523 | if (IS_ERR(dev)) |
554 | ret = PTR_ERR(dev); | 524 | return PTR_ERR(dev); |
555 | goto exit; | ||
556 | } | ||
557 | |||
558 | spin_lock_bh(&bdi_lock); | ||
559 | list_add_tail_rcu(&bdi->bdi_list, &bdi_list); | ||
560 | spin_unlock_bh(&bdi_lock); | ||
561 | 525 | ||
562 | bdi->dev = dev; | 526 | bdi->dev = dev; |
563 | 527 | ||
@@ -569,21 +533,21 @@ int bdi_register(struct backing_dev_info *bdi, struct device *parent, | |||
569 | if (bdi_cap_flush_forker(bdi)) { | 533 | if (bdi_cap_flush_forker(bdi)) { |
570 | struct bdi_writeback *wb = &bdi->wb; | 534 | struct bdi_writeback *wb = &bdi->wb; |
571 | 535 | ||
572 | wb->task = kthread_run(bdi_forker_task, wb, "bdi-%s", | 536 | wb->task = kthread_run(bdi_forker_thread, wb, "bdi-%s", |
573 | dev_name(dev)); | 537 | dev_name(dev)); |
574 | if (IS_ERR(wb->task)) { | 538 | if (IS_ERR(wb->task)) |
575 | wb->task = NULL; | 539 | return PTR_ERR(wb->task); |
576 | ret = -ENOMEM; | ||
577 | |||
578 | bdi_remove_from_list(bdi); | ||
579 | goto exit; | ||
580 | } | ||
581 | } | 540 | } |
582 | 541 | ||
583 | bdi_debug_register(bdi, dev_name(dev)); | 542 | bdi_debug_register(bdi, dev_name(dev)); |
584 | set_bit(BDI_registered, &bdi->state); | 543 | set_bit(BDI_registered, &bdi->state); |
585 | exit: | 544 | |
586 | return ret; | 545 | spin_lock_bh(&bdi_lock); |
546 | list_add_tail_rcu(&bdi->bdi_list, &bdi_list); | ||
547 | spin_unlock_bh(&bdi_lock); | ||
548 | |||
549 | trace_writeback_bdi_register(bdi); | ||
550 | return 0; | ||
587 | } | 551 | } |
588 | EXPORT_SYMBOL(bdi_register); | 552 | EXPORT_SYMBOL(bdi_register); |
589 | 553 | ||
@@ -598,31 +562,29 @@ EXPORT_SYMBOL(bdi_register_dev); | |||
598 | */ | 562 | */ |
599 | static void bdi_wb_shutdown(struct backing_dev_info *bdi) | 563 | static void bdi_wb_shutdown(struct backing_dev_info *bdi) |
600 | { | 564 | { |
601 | struct bdi_writeback *wb; | ||
602 | |||
603 | if (!bdi_cap_writeback_dirty(bdi)) | 565 | if (!bdi_cap_writeback_dirty(bdi)) |
604 | return; | 566 | return; |
605 | 567 | ||
606 | /* | 568 | /* |
607 | * If setup is pending, wait for that to complete first | 569 | * Make sure nobody finds us on the bdi_list anymore |
608 | */ | 570 | */ |
609 | wait_on_bit(&bdi->state, BDI_pending, bdi_sched_wait, | 571 | bdi_remove_from_list(bdi); |
610 | TASK_UNINTERRUPTIBLE); | ||
611 | 572 | ||
612 | /* | 573 | /* |
613 | * Make sure nobody finds us on the bdi_list anymore | 574 | * If setup is pending, wait for that to complete first |
614 | */ | 575 | */ |
615 | bdi_remove_from_list(bdi); | 576 | wait_on_bit(&bdi->state, BDI_pending, bdi_sched_wait, |
577 | TASK_UNINTERRUPTIBLE); | ||
616 | 578 | ||
617 | /* | 579 | /* |
618 | * Finally, kill the kernel threads. We don't need to be RCU | 580 | * Finally, kill the kernel thread. We don't need to be RCU |
619 | * safe anymore, since the bdi is gone from visibility. Force | 581 | * safe anymore, since the bdi is gone from visibility. Force |
620 | * unfreeze of the thread before calling kthread_stop(), otherwise | 582 | * unfreeze of the thread before calling kthread_stop(), otherwise |
621 | * it would never exet if it is currently stuck in the refrigerator. | 583 | * it would never exet if it is currently stuck in the refrigerator. |
622 | */ | 584 | */ |
623 | list_for_each_entry(wb, &bdi->wb_list, list) { | 585 | if (bdi->wb.task) { |
624 | thaw_process(wb->task); | 586 | thaw_process(bdi->wb.task); |
625 | kthread_stop(wb->task); | 587 | kthread_stop(bdi->wb.task); |
626 | } | 588 | } |
627 | } | 589 | } |
628 | 590 | ||
@@ -644,7 +606,9 @@ static void bdi_prune_sb(struct backing_dev_info *bdi) | |||
644 | void bdi_unregister(struct backing_dev_info *bdi) | 606 | void bdi_unregister(struct backing_dev_info *bdi) |
645 | { | 607 | { |
646 | if (bdi->dev) { | 608 | if (bdi->dev) { |
609 | trace_writeback_bdi_unregister(bdi); | ||
647 | bdi_prune_sb(bdi); | 610 | bdi_prune_sb(bdi); |
611 | del_timer_sync(&bdi->wb.wakeup_timer); | ||
648 | 612 | ||
649 | if (!bdi_cap_flush_forker(bdi)) | 613 | if (!bdi_cap_flush_forker(bdi)) |
650 | bdi_wb_shutdown(bdi); | 614 | bdi_wb_shutdown(bdi); |
@@ -655,6 +619,18 @@ void bdi_unregister(struct backing_dev_info *bdi) | |||
655 | } | 619 | } |
656 | EXPORT_SYMBOL(bdi_unregister); | 620 | EXPORT_SYMBOL(bdi_unregister); |
657 | 621 | ||
622 | static void bdi_wb_init(struct bdi_writeback *wb, struct backing_dev_info *bdi) | ||
623 | { | ||
624 | memset(wb, 0, sizeof(*wb)); | ||
625 | |||
626 | wb->bdi = bdi; | ||
627 | wb->last_old_flush = jiffies; | ||
628 | INIT_LIST_HEAD(&wb->b_dirty); | ||
629 | INIT_LIST_HEAD(&wb->b_io); | ||
630 | INIT_LIST_HEAD(&wb->b_more_io); | ||
631 | setup_timer(&wb->wakeup_timer, wakeup_timer_fn, (unsigned long)bdi); | ||
632 | } | ||
633 | |||
658 | int bdi_init(struct backing_dev_info *bdi) | 634 | int bdi_init(struct backing_dev_info *bdi) |
659 | { | 635 | { |
660 | int i, err; | 636 | int i, err; |
@@ -666,7 +642,6 @@ int bdi_init(struct backing_dev_info *bdi) | |||
666 | bdi->max_prop_frac = PROP_FRAC_BASE; | 642 | bdi->max_prop_frac = PROP_FRAC_BASE; |
667 | spin_lock_init(&bdi->wb_lock); | 643 | spin_lock_init(&bdi->wb_lock); |
668 | INIT_LIST_HEAD(&bdi->bdi_list); | 644 | INIT_LIST_HEAD(&bdi->bdi_list); |
669 | INIT_LIST_HEAD(&bdi->wb_list); | ||
670 | INIT_LIST_HEAD(&bdi->work_list); | 645 | INIT_LIST_HEAD(&bdi->work_list); |
671 | 646 | ||
672 | bdi_wb_init(&bdi->wb, bdi); | 647 | bdi_wb_init(&bdi->wb, bdi); |
diff --git a/mm/page-writeback.c b/mm/page-writeback.c index df8202ebc7b8..0c6258bd1ba3 100644 --- a/mm/page-writeback.c +++ b/mm/page-writeback.c | |||
@@ -34,6 +34,7 @@ | |||
34 | #include <linux/syscalls.h> | 34 | #include <linux/syscalls.h> |
35 | #include <linux/buffer_head.h> | 35 | #include <linux/buffer_head.h> |
36 | #include <linux/pagevec.h> | 36 | #include <linux/pagevec.h> |
37 | #include <trace/events/writeback.h> | ||
37 | 38 | ||
38 | /* | 39 | /* |
39 | * After a CPU has dirtied this many pages, balance_dirty_pages_ratelimited | 40 | * After a CPU has dirtied this many pages, balance_dirty_pages_ratelimited |
@@ -535,11 +536,13 @@ static void balance_dirty_pages(struct address_space *mapping, | |||
535 | * threshold otherwise wait until the disk writes catch | 536 | * threshold otherwise wait until the disk writes catch |
536 | * up. | 537 | * up. |
537 | */ | 538 | */ |
539 | trace_wbc_balance_dirty_start(&wbc, bdi); | ||
538 | if (bdi_nr_reclaimable > bdi_thresh) { | 540 | if (bdi_nr_reclaimable > bdi_thresh) { |
539 | writeback_inodes_wb(&bdi->wb, &wbc); | 541 | writeback_inodes_wb(&bdi->wb, &wbc); |
540 | pages_written += write_chunk - wbc.nr_to_write; | 542 | pages_written += write_chunk - wbc.nr_to_write; |
541 | get_dirty_limits(&background_thresh, &dirty_thresh, | 543 | get_dirty_limits(&background_thresh, &dirty_thresh, |
542 | &bdi_thresh, bdi); | 544 | &bdi_thresh, bdi); |
545 | trace_wbc_balance_dirty_written(&wbc, bdi); | ||
543 | } | 546 | } |
544 | 547 | ||
545 | /* | 548 | /* |
@@ -565,6 +568,7 @@ static void balance_dirty_pages(struct address_space *mapping, | |||
565 | if (pages_written >= write_chunk) | 568 | if (pages_written >= write_chunk) |
566 | break; /* We've done our duty */ | 569 | break; /* We've done our duty */ |
567 | 570 | ||
571 | trace_wbc_balance_dirty_wait(&wbc, bdi); | ||
568 | __set_current_state(TASK_INTERRUPTIBLE); | 572 | __set_current_state(TASK_INTERRUPTIBLE); |
569 | io_schedule_timeout(pause); | 573 | io_schedule_timeout(pause); |
570 | 574 | ||
@@ -962,6 +966,7 @@ continue_unlock: | |||
962 | if (!clear_page_dirty_for_io(page)) | 966 | if (!clear_page_dirty_for_io(page)) |
963 | goto continue_unlock; | 967 | goto continue_unlock; |
964 | 968 | ||
969 | trace_wbc_writepage(wbc, mapping->backing_dev_info); | ||
965 | ret = (*writepage)(page, wbc, data); | 970 | ret = (*writepage)(page, wbc, data); |
966 | if (unlikely(ret)) { | 971 | if (unlikely(ret)) { |
967 | if (ret == AOP_WRITEPAGE_ACTIVATE) { | 972 | if (ret == AOP_WRITEPAGE_ACTIVATE) { |
diff --git a/mm/page_io.c b/mm/page_io.c index 31a3b962230a..2dee975bf469 100644 --- a/mm/page_io.c +++ b/mm/page_io.c | |||
@@ -106,7 +106,7 @@ int swap_writepage(struct page *page, struct writeback_control *wbc) | |||
106 | goto out; | 106 | goto out; |
107 | } | 107 | } |
108 | if (wbc->sync_mode == WB_SYNC_ALL) | 108 | if (wbc->sync_mode == WB_SYNC_ALL) |
109 | rw |= (1 << BIO_RW_SYNCIO) | (1 << BIO_RW_UNPLUG); | 109 | rw |= REQ_SYNC | REQ_UNPLUG; |
110 | count_vm_event(PSWPOUT); | 110 | count_vm_event(PSWPOUT); |
111 | set_page_writeback(page); | 111 | set_page_writeback(page); |
112 | unlock_page(page); | 112 | unlock_page(page); |