diff options
Diffstat (limited to 'block')
-rw-r--r-- | block/blk-core.c | 23 | ||||
-rw-r--r-- | block/blk-lib.c | 19 |
2 files changed, 27 insertions, 15 deletions
diff --git a/block/blk-core.c b/block/blk-core.c index 525693237a4a..59b5c00c0126 100644 --- a/block/blk-core.c +++ b/block/blk-core.c | |||
@@ -2046,9 +2046,26 @@ bool blk_update_request(struct request *req, int error, unsigned int nr_bytes) | |||
2046 | 2046 | ||
2047 | if (error && req->cmd_type == REQ_TYPE_FS && | 2047 | if (error && req->cmd_type == REQ_TYPE_FS && |
2048 | !(req->cmd_flags & REQ_QUIET)) { | 2048 | !(req->cmd_flags & REQ_QUIET)) { |
2049 | printk(KERN_ERR "end_request: I/O error, dev %s, sector %llu\n", | 2049 | char *error_type; |
2050 | req->rq_disk ? req->rq_disk->disk_name : "?", | 2050 | |
2051 | (unsigned long long)blk_rq_pos(req)); | 2051 | switch (error) { |
2052 | case -ENOLINK: | ||
2053 | error_type = "recoverable transport"; | ||
2054 | break; | ||
2055 | case -EREMOTEIO: | ||
2056 | error_type = "critical target"; | ||
2057 | break; | ||
2058 | case -EBADE: | ||
2059 | error_type = "critical nexus"; | ||
2060 | break; | ||
2061 | case -EIO: | ||
2062 | default: | ||
2063 | error_type = "I/O"; | ||
2064 | break; | ||
2065 | } | ||
2066 | printk(KERN_ERR "end_request: %s error, dev %s, sector %llu\n", | ||
2067 | error_type, req->rq_disk ? req->rq_disk->disk_name : "?", | ||
2068 | (unsigned long long)blk_rq_pos(req)); | ||
2052 | } | 2069 | } |
2053 | 2070 | ||
2054 | blk_account_io_completion(req, nr_bytes); | 2071 | blk_account_io_completion(req, nr_bytes); |
diff --git a/block/blk-lib.c b/block/blk-lib.c index cb56c4e5b494..25de73e4759b 100644 --- a/block/blk-lib.c +++ b/block/blk-lib.c | |||
@@ -109,7 +109,6 @@ struct bio_batch | |||
109 | atomic_t done; | 109 | atomic_t done; |
110 | unsigned long flags; | 110 | unsigned long flags; |
111 | struct completion *wait; | 111 | struct completion *wait; |
112 | bio_end_io_t *end_io; | ||
113 | }; | 112 | }; |
114 | 113 | ||
115 | static void bio_batch_end_io(struct bio *bio, int err) | 114 | static void bio_batch_end_io(struct bio *bio, int err) |
@@ -122,12 +121,9 @@ static void bio_batch_end_io(struct bio *bio, int err) | |||
122 | else | 121 | else |
123 | clear_bit(BIO_UPTODATE, &bb->flags); | 122 | clear_bit(BIO_UPTODATE, &bb->flags); |
124 | } | 123 | } |
125 | if (bb) { | 124 | if (bb) |
126 | if (bb->end_io) | 125 | if (atomic_dec_and_test(&bb->done)) |
127 | bb->end_io(bio, err); | 126 | complete(bb->wait); |
128 | atomic_inc(&bb->done); | ||
129 | complete(bb->wait); | ||
130 | } | ||
131 | bio_put(bio); | 127 | bio_put(bio); |
132 | } | 128 | } |
133 | 129 | ||
@@ -148,13 +144,12 @@ int blkdev_issue_zeroout(struct block_device *bdev, sector_t sector, | |||
148 | int ret; | 144 | int ret; |
149 | struct bio *bio; | 145 | struct bio *bio; |
150 | struct bio_batch bb; | 146 | struct bio_batch bb; |
151 | unsigned int sz, issued = 0; | 147 | unsigned int sz; |
152 | DECLARE_COMPLETION_ONSTACK(wait); | 148 | DECLARE_COMPLETION_ONSTACK(wait); |
153 | 149 | ||
154 | atomic_set(&bb.done, 0); | 150 | atomic_set(&bb.done, 1); |
155 | bb.flags = 1 << BIO_UPTODATE; | 151 | bb.flags = 1 << BIO_UPTODATE; |
156 | bb.wait = &wait; | 152 | bb.wait = &wait; |
157 | bb.end_io = NULL; | ||
158 | 153 | ||
159 | submit: | 154 | submit: |
160 | ret = 0; | 155 | ret = 0; |
@@ -183,12 +178,12 @@ submit: | |||
183 | break; | 178 | break; |
184 | } | 179 | } |
185 | ret = 0; | 180 | ret = 0; |
186 | issued++; | 181 | atomic_inc(&bb.done); |
187 | submit_bio(WRITE, bio); | 182 | submit_bio(WRITE, bio); |
188 | } | 183 | } |
189 | 184 | ||
190 | /* Wait for bios in-flight */ | 185 | /* Wait for bios in-flight */ |
191 | while (issued != atomic_read(&bb.done)) | 186 | if (!atomic_dec_and_test(&bb.done)) |
192 | wait_for_completion(&wait); | 187 | wait_for_completion(&wait); |
193 | 188 | ||
194 | if (!test_bit(BIO_UPTODATE, &bb.flags)) | 189 | if (!test_bit(BIO_UPTODATE, &bb.flags)) |