aboutsummaryrefslogtreecommitdiffstats
path: root/fs/ext4/resize.c
diff options
context:
space:
mode:
authorFrank Mayhar <fmayhar@google.com>2009-01-07 00:06:22 -0500
committerTheodore Ts'o <tytso@mit.edu>2009-01-07 00:06:22 -0500
commit0390131ba84fd3f726f9e24fc4553828125700bb (patch)
tree4c90afad4e8690e25aec0ce069fd450e92ab5f96 /fs/ext4/resize.c
parentff7ef329b268b603ea4a2303241ef1c3829fd574 (diff)
ext4: Allow ext4 to run without a journal
A few weeks ago I posted a patch for discussion that allowed ext4 to run without a journal. Since that time I've integrated the excellent comments from Andreas and fixed several serious bugs. We're currently running with this patch and generating some performance numbers against both ext2 (with backported reservations code) and ext4 with and without a journal. It just so happens that running without a journal is slightly faster for most everything. We did iozone -T -t 4 s 2g -r 256k -T -I -i0 -i1 -i2 which creates 4 threads, each of which create and do reads and writes on a 2G file, with a buffer size of 256K, using O_DIRECT for all file opens to bypass the page cache. Results: ext2 ext4, default ext4, no journal initial writes 13.0 MB/s 15.4 MB/s 15.7 MB/s rewrites 13.1 MB/s 15.6 MB/s 15.9 MB/s reads 15.2 MB/s 16.9 MB/s 17.2 MB/s re-reads 15.3 MB/s 16.9 MB/s 17.2 MB/s random readers 5.6 MB/s 5.6 MB/s 5.7 MB/s random writers 5.1 MB/s 5.3 MB/s 5.4 MB/s So it seems that, so far, this was a useful exercise. Signed-off-by: Frank Mayhar <fmayhar@google.com> Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>
Diffstat (limited to 'fs/ext4/resize.c')
-rw-r--r--fs/ext4/resize.c31
1 files changed, 16 insertions, 15 deletions
diff --git a/fs/ext4/resize.c b/fs/ext4/resize.c
index d448eb1d9ba..1665aa131d1 100644
--- a/fs/ext4/resize.c
+++ b/fs/ext4/resize.c
@@ -149,7 +149,7 @@ static int extend_or_restart_transaction(handle_t *handle, int thresh,
149{ 149{
150 int err; 150 int err;
151 151
152 if (handle->h_buffer_credits >= thresh) 152 if (ext4_handle_has_enough_credits(handle, thresh))
153 return 0; 153 return 0;
154 154
155 err = ext4_journal_extend(handle, EXT4_MAX_TRANS_DATA); 155 err = ext4_journal_extend(handle, EXT4_MAX_TRANS_DATA);
@@ -232,7 +232,7 @@ static int setup_new_group_blocks(struct super_block *sb,
232 memcpy(gdb->b_data, sbi->s_group_desc[i]->b_data, gdb->b_size); 232 memcpy(gdb->b_data, sbi->s_group_desc[i]->b_data, gdb->b_size);
233 set_buffer_uptodate(gdb); 233 set_buffer_uptodate(gdb);
234 unlock_buffer(gdb); 234 unlock_buffer(gdb);
235 ext4_journal_dirty_metadata(handle, gdb); 235 ext4_handle_dirty_metadata(handle, NULL, gdb);
236 ext4_set_bit(bit, bh->b_data); 236 ext4_set_bit(bit, bh->b_data);
237 brelse(gdb); 237 brelse(gdb);
238 } 238 }
@@ -251,7 +251,7 @@ static int setup_new_group_blocks(struct super_block *sb,
251 err = PTR_ERR(bh); 251 err = PTR_ERR(bh);
252 goto exit_bh; 252 goto exit_bh;
253 } 253 }
254 ext4_journal_dirty_metadata(handle, gdb); 254 ext4_handle_dirty_metadata(handle, NULL, gdb);
255 ext4_set_bit(bit, bh->b_data); 255 ext4_set_bit(bit, bh->b_data);
256 brelse(gdb); 256 brelse(gdb);
257 } 257 }
@@ -276,7 +276,7 @@ static int setup_new_group_blocks(struct super_block *sb,
276 err = PTR_ERR(it); 276 err = PTR_ERR(it);
277 goto exit_bh; 277 goto exit_bh;
278 } 278 }
279 ext4_journal_dirty_metadata(handle, it); 279 ext4_handle_dirty_metadata(handle, NULL, it);
280 brelse(it); 280 brelse(it);
281 ext4_set_bit(bit, bh->b_data); 281 ext4_set_bit(bit, bh->b_data);
282 } 282 }
@@ -286,7 +286,7 @@ static int setup_new_group_blocks(struct super_block *sb,
286 286
287 mark_bitmap_end(input->blocks_count, EXT4_BLOCKS_PER_GROUP(sb), 287 mark_bitmap_end(input->blocks_count, EXT4_BLOCKS_PER_GROUP(sb),
288 bh->b_data); 288 bh->b_data);
289 ext4_journal_dirty_metadata(handle, bh); 289 ext4_handle_dirty_metadata(handle, NULL, bh);
290 brelse(bh); 290 brelse(bh);
291 291
292 /* Mark unused entries in inode bitmap used */ 292 /* Mark unused entries in inode bitmap used */
@@ -299,7 +299,7 @@ static int setup_new_group_blocks(struct super_block *sb,
299 299
300 mark_bitmap_end(EXT4_INODES_PER_GROUP(sb), EXT4_BLOCKS_PER_GROUP(sb), 300 mark_bitmap_end(EXT4_INODES_PER_GROUP(sb), EXT4_BLOCKS_PER_GROUP(sb),
301 bh->b_data); 301 bh->b_data);
302 ext4_journal_dirty_metadata(handle, bh); 302 ext4_handle_dirty_metadata(handle, NULL, bh);
303exit_bh: 303exit_bh:
304 brelse(bh); 304 brelse(bh);
305 305
@@ -486,12 +486,12 @@ static int add_new_gdb(handle_t *handle, struct inode *inode,
486 * reserved inode, and will become GDT blocks (primary and backup). 486 * reserved inode, and will become GDT blocks (primary and backup).
487 */ 487 */
488 data[gdb_num % EXT4_ADDR_PER_BLOCK(sb)] = 0; 488 data[gdb_num % EXT4_ADDR_PER_BLOCK(sb)] = 0;
489 ext4_journal_dirty_metadata(handle, dind); 489 ext4_handle_dirty_metadata(handle, NULL, dind);
490 brelse(dind); 490 brelse(dind);
491 inode->i_blocks -= (gdbackups + 1) * sb->s_blocksize >> 9; 491 inode->i_blocks -= (gdbackups + 1) * sb->s_blocksize >> 9;
492 ext4_mark_iloc_dirty(handle, inode, &iloc); 492 ext4_mark_iloc_dirty(handle, inode, &iloc);
493 memset((*primary)->b_data, 0, sb->s_blocksize); 493 memset((*primary)->b_data, 0, sb->s_blocksize);
494 ext4_journal_dirty_metadata(handle, *primary); 494 ext4_handle_dirty_metadata(handle, NULL, *primary);
495 495
496 o_group_desc = EXT4_SB(sb)->s_group_desc; 496 o_group_desc = EXT4_SB(sb)->s_group_desc;
497 memcpy(n_group_desc, o_group_desc, 497 memcpy(n_group_desc, o_group_desc,
@@ -502,7 +502,7 @@ static int add_new_gdb(handle_t *handle, struct inode *inode,
502 kfree(o_group_desc); 502 kfree(o_group_desc);
503 503
504 le16_add_cpu(&es->s_reserved_gdt_blocks, -1); 504 le16_add_cpu(&es->s_reserved_gdt_blocks, -1);
505 ext4_journal_dirty_metadata(handle, EXT4_SB(sb)->s_sbh); 505 ext4_handle_dirty_metadata(handle, NULL, EXT4_SB(sb)->s_sbh);
506 506
507 return 0; 507 return 0;
508 508
@@ -618,7 +618,7 @@ static int reserve_backup_gdb(handle_t *handle, struct inode *inode,
618 primary[i]->b_blocknr, gdbackups, 618 primary[i]->b_blocknr, gdbackups,
619 blk + primary[i]->b_blocknr); */ 619 blk + primary[i]->b_blocknr); */
620 data[gdbackups] = cpu_to_le32(blk + primary[i]->b_blocknr); 620 data[gdbackups] = cpu_to_le32(blk + primary[i]->b_blocknr);
621 err2 = ext4_journal_dirty_metadata(handle, primary[i]); 621 err2 = ext4_handle_dirty_metadata(handle, NULL, primary[i]);
622 if (!err) 622 if (!err)
623 err = err2; 623 err = err2;
624 } 624 }
@@ -676,7 +676,8 @@ static void update_backups(struct super_block *sb,
676 struct buffer_head *bh; 676 struct buffer_head *bh;
677 677
678 /* Out of journal space, and can't get more - abort - so sad */ 678 /* Out of journal space, and can't get more - abort - so sad */
679 if (handle->h_buffer_credits == 0 && 679 if (ext4_handle_valid(handle) &&
680 handle->h_buffer_credits == 0 &&
680 ext4_journal_extend(handle, EXT4_MAX_TRANS_DATA) && 681 ext4_journal_extend(handle, EXT4_MAX_TRANS_DATA) &&
681 (err = ext4_journal_restart(handle, EXT4_MAX_TRANS_DATA))) 682 (err = ext4_journal_restart(handle, EXT4_MAX_TRANS_DATA)))
682 break; 683 break;
@@ -696,7 +697,7 @@ static void update_backups(struct super_block *sb,
696 memset(bh->b_data + size, 0, rest); 697 memset(bh->b_data + size, 0, rest);
697 set_buffer_uptodate(bh); 698 set_buffer_uptodate(bh);
698 unlock_buffer(bh); 699 unlock_buffer(bh);
699 ext4_journal_dirty_metadata(handle, bh); 700 ext4_handle_dirty_metadata(handle, NULL, bh);
700 brelse(bh); 701 brelse(bh);
701 } 702 }
702 if ((err2 = ext4_journal_stop(handle)) && !err) 703 if ((err2 = ext4_journal_stop(handle)) && !err)
@@ -916,7 +917,7 @@ int ext4_group_add(struct super_block *sb, struct ext4_new_group_data *input)
916 /* Update the global fs size fields */ 917 /* Update the global fs size fields */
917 sbi->s_groups_count++; 918 sbi->s_groups_count++;
918 919
919 ext4_journal_dirty_metadata(handle, primary); 920 ext4_handle_dirty_metadata(handle, NULL, primary);
920 921
921 /* Update the reserved block counts only once the new group is 922 /* Update the reserved block counts only once the new group is
922 * active. */ 923 * active. */
@@ -938,7 +939,7 @@ int ext4_group_add(struct super_block *sb, struct ext4_new_group_data *input)
938 EXT4_INODES_PER_GROUP(sb); 939 EXT4_INODES_PER_GROUP(sb);
939 } 940 }
940 941
941 ext4_journal_dirty_metadata(handle, sbi->s_sbh); 942 ext4_handle_dirty_metadata(handle, NULL, sbi->s_sbh);
942 sb->s_dirt = 1; 943 sb->s_dirt = 1;
943 944
944exit_journal: 945exit_journal:
@@ -1072,7 +1073,7 @@ int ext4_group_extend(struct super_block *sb, struct ext4_super_block *es,
1072 goto exit_put; 1073 goto exit_put;
1073 } 1074 }
1074 ext4_blocks_count_set(es, o_blocks_count + add); 1075 ext4_blocks_count_set(es, o_blocks_count + add);
1075 ext4_journal_dirty_metadata(handle, EXT4_SB(sb)->s_sbh); 1076 ext4_handle_dirty_metadata(handle, NULL, EXT4_SB(sb)->s_sbh);
1076 sb->s_dirt = 1; 1077 sb->s_dirt = 1;
1077 unlock_super(sb); 1078 unlock_super(sb);
1078 ext4_debug("freeing blocks %llu through %llu\n", o_blocks_count, 1079 ext4_debug("freeing blocks %llu through %llu\n", o_blocks_count,