Commit 7d39db14a42cbd719c7515b9da8f85a2eb6a0633

Authored by Theodore Ts'o
1 parent 9f24e4208f

ext4: Use struct flex_groups to calculate get_orlov_stats()

Instead of looping over all of the block groups in a flex group
summing their summary statistics, start tracking used_dirs in struct
flex_groups, and use struct flex_groups instead.  This should save a
bit of CPU for mkdir-heavy workloads.

Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>

Showing 3 changed files with 31 additions and 17 deletions Side-by-side Diff

... ... @@ -172,6 +172,7 @@
172 172 struct flex_groups {
173 173 atomic_t free_inodes;
174 174 atomic_t free_blocks;
  175 + atomic_t used_dirs;
175 176 };
176 177  
177 178 #define EXT4_BG_INODE_UNINIT 0x0001 /* Inode table/bitmap not in use */
... ... @@ -267,6 +267,13 @@
267 267 if (is_directory) {
268 268 count = ext4_used_dirs_count(sb, gdp) - 1;
269 269 ext4_used_dirs_set(sb, gdp, count);
  270 + if (sbi->s_log_groups_per_flex) {
  271 + ext4_group_t f;
  272 +
  273 + f = ext4_flex_group(sbi, block_group);
  274 + atomic_dec(&sbi->s_flex_groups[f].free_inodes);
  275 + }
  276 +
270 277 }
271 278 gdp->bg_checksum = ext4_group_desc_csum(sbi,
272 279 block_group, gdp);
273 280  
274 281  
... ... @@ -424,25 +431,24 @@
424 431 int flex_size, struct orlov_stats *stats)
425 432 {
426 433 struct ext4_group_desc *desc;
427   - ext4_group_t ngroups = EXT4_SB(sb)->s_groups_count;
428   - int i;
  434 + struct flex_groups *flex_group = EXT4_SB(sb)->s_flex_groups;
429 435  
430   - stats->free_inodes = 0;
431   - stats->free_blocks = 0;
432   - stats->used_dirs = 0;
  436 + if (flex_size > 1) {
  437 + stats->free_inodes = atomic_read(&flex_group[g].free_inodes);
  438 + stats->free_blocks = atomic_read(&flex_group[g].free_blocks);
  439 + stats->used_dirs = atomic_read(&flex_group[g].used_dirs);
  440 + return;
  441 + }
433 442  
434   - g *= flex_size;
435   -
436   - for (i = 0; i < flex_size; i++) {
437   - if (g >= ngroups)
438   - break;
439   - desc = ext4_get_group_desc(sb, g++, NULL);
440   - if (!desc)
441   - continue;
442   -
443   - stats->free_inodes += ext4_free_inodes_count(sb, desc);
444   - stats->free_blocks += ext4_free_blks_count(sb, desc);
445   - stats->used_dirs += ext4_used_dirs_count(sb, desc);
  443 + desc = ext4_get_group_desc(sb, g, NULL);
  444 + if (desc) {
  445 + stats->free_inodes = ext4_free_inodes_count(sb, desc);
  446 + stats->free_blocks = ext4_free_blks_count(sb, desc);
  447 + stats->used_dirs = ext4_used_dirs_count(sb, desc);
  448 + } else {
  449 + stats->free_inodes = 0;
  450 + stats->free_blocks = 0;
  451 + stats->used_dirs = 0;
446 452 }
447 453 }
448 454  
... ... @@ -765,6 +771,11 @@
765 771 if (S_ISDIR(mode)) {
766 772 count = ext4_used_dirs_count(sb, gdp) + 1;
767 773 ext4_used_dirs_set(sb, gdp, count);
  774 + if (sbi->s_log_groups_per_flex) {
  775 + ext4_group_t f = ext4_flex_group(sbi, group);
  776 +
  777 + atomic_inc(&sbi->s_flex_groups[f].free_inodes);
  778 + }
768 779 }
769 780 gdp->bg_checksum = ext4_group_desc_csum(sbi, group, gdp);
770 781 err_ret:
... ... @@ -1634,6 +1634,8 @@
1634 1634 ext4_free_inodes_count(sb, gdp));
1635 1635 atomic_set(&sbi->s_flex_groups[flex_group].free_blocks,
1636 1636 ext4_free_blks_count(sb, gdp));
  1637 + atomic_set(&sbi->s_flex_groups[flex_group].used_dirs,
  1638 + ext4_used_dirs_count(sb, gdp));
1637 1639 }
1638 1640  
1639 1641 return 1;