# This is a BitKeeper generated patch for the following project: # Project Name: Linux kernel tree # This patch format is intended for GNU patch command version 2.5 or higher. # This patch includes the following deltas: # ChangeSet 1.573 -> 1.574 # fs/bio.c 1.25 -> 1.26 # # The following is the BitKeeper ChangeSet Log # -------------------------------------------- # 02/09/18 axboe@burns.home.kernel.dk 1.574 # Make BIO_UPTODATE a sticky good flag, only clearing it on error. # -------------------------------------------- # diff -Nru a/fs/bio.c b/fs/bio.c --- a/fs/bio.c Wed Sep 18 19:50:08 2002 +++ b/fs/bio.c Wed Sep 18 19:50:08 2002 @@ -110,7 +110,7 @@ inline void bio_init(struct bio *bio) { bio->bi_next = NULL; - bio->bi_flags = 0; + bio->bi_flags = 1 << BIO_UPTODATE; bio->bi_rw = 0; bio->bi_vcnt = 0; bio->bi_idx = 0; @@ -523,12 +523,30 @@ end_kio_request(kio, !err); } +/** + * bio_endio - end I/O on a bio + * @bio: bio + * @bytes_done: number of bytes completed + * @error: error, if any + * + * Description: + * bio_endio() will end I/O @bytes_done number of bytes. This may be just + * a partial part of the bio, or it may be the whole bio. bio_endio() is + * the preferred way to end I/O on a bio, it takes care of decrementing + * bi_size and clearing BIO_UPTODATE on error. @error is 0 on success, and + * and one of the established -Exxxx (-EIO, for instance) error values in + * case something went wrong. + **/ int bio_endio(struct bio *bio, unsigned int bytes_done, int error) { - if (!error) - set_bit(BIO_UPTODATE, &bio->bi_flags); - else + if (error) clear_bit(BIO_UPTODATE, &bio->bi_flags); + + if (unlikely(bytes_done > bio->bi_size)) { + printk("%s: want %u bytes done, only %u left\n", __FUNCTION__, + bytes_done, bio->bi_size); + bytes_done = bio->bi_size; + } bio->bi_size -= bytes_done; return bio->bi_end_io(bio, bytes_done, error);