Messages in this thread Patch in this message | | | Subject | Re: ext2 on a CD-RW | From | Peter Osterlund <> | Date | 02 Jan 2004 17:12:43 +0100 |
| |
Jens Axboe <axboe@suse.de> writes:
> On Fri, Jan 02 2004, Peter Osterlund wrote: > > > > Old versions of the packet writing code did just that, but Jens told > > me that bio splitting was evil, so when the merge_bvec_fn > > functionality was added to the kernel, I started to use it. > > > > http://lists.suse.com/archive/packet-writing/2002-Aug/0044.html > > Splitting is evil, but unfortunately it's a necessary evil... There are > a few kernel helpers to make supporting it easier (see bio_split()). Not > so sure how well that'll work for you, you may have to do the grunt work > yourself.
It seems like bio_split() does exactly what I need. The patch below makes 2kb blocksize ext2 work and also fixes the performance problem compared to 4kb blocksize ext2. Thanks to everyone involved for their help.
--- linux/drivers/block/pktcdvd.c.old 2004-01-02 16:58:52.000000000 +0100 +++ linux/drivers/block/pktcdvd.c 2004-01-02 16:59:26.000000000 +0100 @@ -2083,11 +2083,23 @@ (unsigned long long)bio->bi_sector, (unsigned long long)(bio->bi_sector + bio_sectors(bio))); - /* Some debug code to make sure the merge_bvec_fn function is working. */ + /* Check if we have to split the bio */ { + struct bio_pair *bp; sector_t last_zone; + int first_sectors; + last_zone = ZONE(bio->bi_sector + bio_sectors(bio) - 1, pd); - BUG_ON(last_zone != zone); + if (last_zone != zone) { + BUG_ON(last_zone != zone + pd->settings.size); + first_sectors = last_zone - bio->bi_sector; + bp = bio_split(bio, bio_split_pool, first_sectors); + BUG_ON(!bp); + pkt_make_request(q, &bp->bio1); + pkt_make_request(q, &bp->bio2); + bio_pair_release(bp); + return 0; + } } /* @@ -2153,6 +2165,15 @@ sector_t zone = ZONE(bio->bi_sector, pd); int used = ((bio->bi_sector - zone) << 9) + bio->bi_size; int remaining = (pd->settings.size << 9) - used; + int remaining2; + + /* + * A bio <= PAGE_SIZE must be allowed. If it crosses a packet + * boundary, pkt_make_request() will split the bio. + */ + remaining2 = PAGE_SIZE - bio->bi_size; + remaining = max_t(int, remaining, remaining2); + BUG_ON(remaining < 0); return remaining; } -- Peter Osterlund - petero2@telia.com http://w1.894.telia.com/~u89404340 - To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/
| |