Whamcloud - gitweb
LU-7980 ldiskfs: always pre-allocate max depth for path 49/19349/7
authorBruno Faccini <bruno.faccini@intel.com>
Wed, 6 Apr 2016 14:38:05 +0000 (16:38 +0200)
committerOleg Drokin <oleg.drokin@intel.com>
Thu, 28 Apr 2016 04:23:24 +0000 (04:23 +0000)
Upon very specific meta-data and I/O pattern a situation can be
encountered where ext_depth() will concurrently (due to i_data_sem
release) grow outside of currently used ext4_ext_path[] array
boundary.
This can lead to potential Slab overrun if current ext_depth()
is used to index previously sized+allocated ext4_ext_path[] array.
This patch fixes this by already pre-allocating _ext_path[]
array of the max possible depth.

This is an alternate way to avoid racy cases, that can lead to
slab overrun, with current and unsafe implementation that causes
ext4_ext_path[] array re-[sizing,allocation] based on current depth.

Now unnecessay free an realloc upon depth change detection prior to
reuse already allocated path space have also been removed.

Signed-off-by: Bruno Faccini <bruno.faccini@intel.com>
Change-Id: I0ae955c5eccf032cb02ef55c6381964a5eaf82c2
Reviewed-on: http://review.whamcloud.com/19349
Tested-by: Jenkins
Reviewed-by: Andreas Dilger <andreas.dilger@intel.com>
Tested-by: Maloo <hpdd-maloo@intel.com>
Reviewed-by: Alex Zhuravlev <alexey.zhuravlev@intel.com>
ldiskfs/kernel_patches/patches/rhel6.6/ext4_s_max_ext_tree_depth.patch [new file with mode: 0644]
ldiskfs/kernel_patches/patches/rhel7/ext4_s_max_ext_tree_depth.patch [new file with mode: 0644]
ldiskfs/kernel_patches/patches/sles11sp3/ext4_s_max_ext_tree_depth.patch [new file with mode: 0644]
ldiskfs/kernel_patches/series/ldiskfs-2.6-rhel6.6.series
ldiskfs/kernel_patches/series/ldiskfs-2.6-rhel6.7.series
ldiskfs/kernel_patches/series/ldiskfs-3.0-sles11.series
ldiskfs/kernel_patches/series/ldiskfs-3.0-sles11sp3.series
ldiskfs/kernel_patches/series/ldiskfs-3.10-rhel7.2.series
ldiskfs/kernel_patches/series/ldiskfs-3.10-rhel7.series

diff --git a/ldiskfs/kernel_patches/patches/rhel6.6/ext4_s_max_ext_tree_depth.patch b/ldiskfs/kernel_patches/patches/rhel6.6/ext4_s_max_ext_tree_depth.patch
new file mode 100644 (file)
index 0000000..96c9b89
--- /dev/null
@@ -0,0 +1,156 @@
+Fix ext4_ext_find_extent() to already pre-allocate ext4_ext_path[]
+array of the max depth instead of current depth.
+This will avoid racy cases of concurrent ext_depth() growth in
+current and unsafe implementation with ext4_ext_path[] array
+re-[sizing,allocation], even with more recent and related patches
+that will be integrated in more recent Kernels.
+
+Index: linux-2.6.32-504.el6.x86_64/fs/ext4/ext4.h
+===================================================================
+--- linux-2.6.32-504.el6.x86_64.orig/fs/ext4/ext4.h
++++ linux-2.6.32-504.el6.x86_64/fs/ext4/ext4.h
+@@ -1147,6 +1147,9 @@
+       unsigned long s_ext_extents;
+ #endif
++      /* maximum possible extents tree depth, to be computed at mount time */
++      unsigned int s_max_ext_tree_depth;
++
+       /* for buddy allocator */
+       struct ext4_group_info ***s_group_info;
+       struct inode *s_buddy_cache;
+Index: linux-2.6.32-504.el6.x86_64/fs/ext4/super.c
+===================================================================
+--- linux-2.6.32-504.el6.x86_64.orig/fs/ext4/super.c
++++ linux-2.6.32-504.el6.x86_64/fs/ext4/super.c
+@@ -3529,6 +3529,8 @@
+               if (ext4_multi_mount_protect(sb, le64_to_cpu(es->s_mmp_block)))
+                       goto failed_mount3;
++      ext4_ext_init(sb); /* needed before using extent-mapped journal */
++
+       /*
+        * The first inode we look at is the journal inode.  Don't try
+        * root first: it may be modified in the journal!
+@@ -3722,7 +3724,6 @@
+               goto failed_mount4a;
+       }
+-      ext4_ext_init(sb);
+       err = ext4_mb_init(sb, needs_recovery);
+       if (err) {
+               ext4_msg(sb, KERN_ERR, "failed to initalize mballoc (%d)",
+Index: linux-2.6.32-504.el6.x86_64/fs/ext4/extents.c
+===================================================================
+--- linux-2.6.32-504.el6.x86_64.orig/fs/ext4/extents.c
++++ linux-2.6.32-504.el6.x86_64/fs/ext4/extents.c
+@@ -699,8 +699,9 @@
+       /* account possible depth increase */
+       if (!path) {
+-              path = kzalloc(sizeof(struct ext4_ext_path) * (depth + 2),
+-                              GFP_NOFS);
++              path = kzalloc(sizeof(struct ext4_ext_path) *
++                             EXT4_SB(inode->i_sb)->s_max_ext_tree_depth,
++                             GFP_NOFS);
+               if (!path)
+                       return ERR_PTR(-ENOMEM);
+               alloc = 1;
+@@ -1915,11 +1916,8 @@
+               /* find extent for this block */
+               down_read(&EXT4_I(inode)->i_data_sem);
+-              if (path && ext_depth(inode) != depth) {
+-                      /* depth was changed. we have to realloc path */
+-                      kfree(path);
+-                      path = NULL;
+-              }
++              /* path of max possible depth will be allocated during
++               * first pass, so its space can be re-used for each loop */
+               path = ext4_ext_find_extent(inode, block, path);
+               if (IS_ERR(path)) {
+@@ -2664,8 +2662,9 @@
+                       path[k].p_block =
+                               le16_to_cpu(path[k].p_hdr->eh_entries)+1;
+       } else {
+-              path = kzalloc(sizeof(struct ext4_ext_path) * (depth + 1),
+-                             GFP_NOFS);
++              path = kzalloc(sizeof(struct ext4_ext_path) *
++                             EXT4_SB(inode->i_sb)->s_max_ext_tree_depth,
++                             GFP_NOFS);
+               if (path == NULL) {
+                       ext4_journal_stop(handle);
+                       return -ENOMEM;
+@@ -2790,13 +2789,15 @@
+  */
+ void ext4_ext_init(struct super_block *sb)
+ {
++      ext4_fsblk_t maxblocks;
++
+       /*
+        * possible initialization would be here
+        */
+       if (EXT4_HAS_INCOMPAT_FEATURE(sb, EXT4_FEATURE_INCOMPAT_EXTENTS)) {
+-#if defined(AGGRESSIVE_TEST) || defined(CHECK_BINSEARCH) || defined(EXTENTS_STATS)
+-              printk(KERN_INFO "EXT4-fs: file extents enabled");
++              printk(KERN_INFO "EXT4-fs (%s): file extents enabled",
++                     sb->s_id);
+ #ifdef AGGRESSIVE_TEST
+               printk(", aggressive tests");
+ #endif
+@@ -2805,14 +2806,35 @@
+ #endif
+ #ifdef EXTENTS_STATS
+               printk(", stats");
+-#endif
+-              printk("\n");
+-#endif
+-#ifdef EXTENTS_STATS
+               spin_lock_init(&EXT4_SB(sb)->s_ext_stats_lock);
+               EXT4_SB(sb)->s_ext_min = 1 << 30;
+               EXT4_SB(sb)->s_ext_max = 0;
+ #endif
++              EXT4_SB(sb)->s_max_ext_tree_depth = 1;
++
++              maxblocks = sb->s_maxbytes / sb->s_blocksize;
++
++              /* 1st/root level/node of extents tree stands in i_data and
++               * entries stored in tree nodes can be of type ext4_extent
++               * (leaf node) or ext4_extent_idx (internal node) */
++              maxblocks /= (sizeof(((struct ext4_inode_info *)0x0)->i_data) -
++                            sizeof(struct ext4_extent_header)) /
++                           max(sizeof(struct ext4_extent),
++                               sizeof(struct ext4_extent_idx));
++
++              /* compute maximum extents tree depth for a fully populated
++               * file of max size made of only minimal/1-block extents */
++              while (maxblocks > 0) {
++                      maxblocks /= (sb->s_blocksize -
++                                    sizeof(struct ext4_extent_header)) /
++                                   max(sizeof(struct ext4_extent),
++                                       sizeof(struct ext4_extent_idx));
++                      EXT4_SB(sb)->s_max_ext_tree_depth++;
++              }
++
++              printk(", maximum tree depth=%u",
++                     EXT4_SB(sb)->s_max_ext_tree_depth);
++              printk("\n");
+       }
+ }
+@@ -4614,11 +4636,8 @@
+                       break;
+               }
+-              if (ext_depth(inode) != depth) {
+-                      /* depth was changed. we have to realloc path */
+-                      kfree(path);
+-                      path = NULL;
+-              }
++              /* path of max possible depth will be allocated during
++               * first pass, so its space can be re-used for each loop */
+               block = cbex.ec_block + cbex.ec_len;
+       }
diff --git a/ldiskfs/kernel_patches/patches/rhel7/ext4_s_max_ext_tree_depth.patch b/ldiskfs/kernel_patches/patches/rhel7/ext4_s_max_ext_tree_depth.patch
new file mode 100644 (file)
index 0000000..0efc834
--- /dev/null
@@ -0,0 +1,135 @@
+Fix ext4_ext_find_extent() to already pre-allocate ext4_ext_path[]
+array of the max depth instead of current depth.
+This will avoid racy cases of concurrent ext_depth() growth in
+current and unsafe implementation with ext4_ext_path[] array
+re-[sizing,allocation], even with more recent and related patches
+that will be integrated in more recent Kernels.
+
+Index: linux-2.6.32-504.el6.x86_64/fs/ext4/ext4.h
+===================================================================
+--- linux-2.6.32-504.el6.x86_64.orig/fs/ext4/ext4.h
++++ linux-2.6.32-504.el6.x86_64/fs/ext4/ext4.h
+@@ -1147,6 +1147,9 @@
+       unsigned long s_ext_extents;
+ #endif
++      /* maximum possible extents tree depth, to be computed at mount time */
++      unsigned int s_max_ext_tree_depth;
++
+       /* for buddy allocator */
+       struct ext4_group_info ***s_group_info;
+       struct inode *s_buddy_cache;
+Index: linux-2.6.32-504.el6.x86_64/fs/ext4/super.c
+===================================================================
+--- linux-2.6.32-504.el6.x86_64.orig/fs/ext4/super.c
++++ linux-2.6.32-504.el6.x86_64/fs/ext4/super.c
+@@ -4038,6 +4038,8 @@
+               if (ext4_multi_mount_protect(sb, le64_to_cpu(es->s_mmp_block)))
+                       goto failed_mount3;
++      ext4_ext_init(sb); /* needed before using extent-mapped journal */
++
+       /*
+        * The first inode we look at is the journal inode.  Don't try
+        * root first: it may be modified in the journal!
+@@ -4200,7 +4202,6 @@
+               goto failed_mount4a;
+       }
+-      ext4_ext_init(sb);
+       err = ext4_mb_init(sb);
+       if (err) {
+               ext4_msg(sb, KERN_ERR, "failed to initialize mballoc (%d)",
+Index: linux-2.6.32-504.el6.x86_64/fs/ext4/extents.c
+===================================================================
+--- linux-2.6.32-504.el6.x86_64.orig/fs/ext4/extents.c
++++ linux-2.6.32-504.el6.x86_64/fs/ext4/extents.c
+@@ -699,8 +699,9 @@
+       /* account possible depth increase */
+       if (!path) {
+-              path = kzalloc(sizeof(struct ext4_ext_path) * (depth + 2),
+-                              GFP_NOFS);
++              path = kzalloc(sizeof(struct ext4_ext_path) *
++                             EXT4_SB(inode->i_sb)->s_max_ext_tree_depth,
++                             GFP_NOFS);
+               if (!path)
+                       return ERR_PTR(-ENOMEM);
+               alloc = 1;
+@@ -1915,11 +1916,8 @@
+               /* find extent for this block */
+               down_read(&EXT4_I(inode)->i_data_sem);
+-              if (path && ext_depth(inode) != depth) {
+-                      /* depth was changed. we have to realloc path */
+-                      kfree(path);
+-                      path = NULL;
+-              }
++              /* path of max possible depth will be allocated during
++               * first pass, so its space can be re-used for each loop */
+               path = ext4_ext_find_extent(inode, block, path);
+               if (IS_ERR(path)) {
+@@ -2664,8 +2662,9 @@
+                       path[k].p_block =
+                               le16_to_cpu(path[k].p_hdr->eh_entries)+1;
+       } else {
+-              path = kzalloc(sizeof(struct ext4_ext_path) * (depth + 1),
+-                             GFP_NOFS);
++              path = kzalloc(sizeof(struct ext4_ext_path) *
++                             EXT4_SB(inode->i_sb)->s_max_ext_tree_depth,
++                             GFP_NOFS);
+               if (path == NULL) {
+                       ext4_journal_stop(handle);
+                       return -ENOMEM;
+@@ -3048,13 +3034,14 @@
+  */
+ void ext4_ext_init(struct super_block *sb)
+ {
++      ext4_fsblk_t maxblocks;
++
+       /*
+        * possible initialization would be here
+        */
+       if (EXT4_HAS_INCOMPAT_FEATURE(sb, EXT4_FEATURE_INCOMPAT_EXTENTS)) {
+-#if defined(AGGRESSIVE_TEST) || defined(CHECK_BINSEARCH) || defined(EXTENTS_STATS)
+-              printk(KERN_INFO "EXT4-fs: file extents enabled"
++              printk(KERN_INFO "EXT4-fs (%s): file extents enabled"
+ #ifdef AGGRESSIVE_TEST
+                      ", aggressive tests"
+ #endif
+@@ -3064,8 +3051,31 @@
+ #ifdef EXTENTS_STATS
+                      ", stats"
+ #endif
+-                     "\n");
+-#endif
++                     , sb->s_id);
++              EXT4_SB(sb)->s_max_ext_tree_depth = 1;
++
++              maxblocks = sb->s_maxbytes / sb->s_blocksize;
++
++              /* 1st/root level/node of extents tree stands in i_data and
++               * entries stored in tree nodes can be of type ext4_extent
++               * (leaf node) or ext4_extent_idx (internal node) */
++              maxblocks /= (sizeof(((struct ext4_inode_info *)0x0)->i_data) -
++                            sizeof(struct ext4_extent_header)) /
++                           max(sizeof(struct ext4_extent),
++                               sizeof(struct ext4_extent_idx));
++
++              /* compute maximum extents tree depth for a fully populated
++               * file of max size made of only minimal/1-block extents */
++              while (maxblocks > 0) {
++                      maxblocks /= (sb->s_blocksize -
++                                    sizeof(struct ext4_extent_header)) /
++                                   max(sizeof(struct ext4_extent),
++                                       sizeof(struct ext4_extent_idx));
++                      EXT4_SB(sb)->s_max_ext_tree_depth++;
++              }
++
++              printk(", maximum tree depth=%u\n",
++                     EXT4_SB(sb)->s_max_ext_tree_depth);
+ #ifdef EXTENTS_STATS
+               spin_lock_init(&EXT4_SB(sb)->s_ext_stats_lock);
+               EXT4_SB(sb)->s_ext_min = 1 << 30;
diff --git a/ldiskfs/kernel_patches/patches/sles11sp3/ext4_s_max_ext_tree_depth.patch b/ldiskfs/kernel_patches/patches/sles11sp3/ext4_s_max_ext_tree_depth.patch
new file mode 100644 (file)
index 0000000..bcbf8e6
--- /dev/null
@@ -0,0 +1,157 @@
+Fix ext4_ext_find_extent() to already pre-allocate ext4_ext_path[]
+array of the max depth instead of current depth.
+This will avoid racy cases of concurrent ext_depth() growth in
+current and unsafe implementation with ext4_ext_path[] array
+re-[sizing,allocation], even with more recent and related patches
+that will be integrated in more recent Kernels.
+
+Index: linux-2.6.32-504.el6.x86_64/fs/ext4/ext4.h
+===================================================================
+--- linux-2.6.32-504.el6.x86_64.orig/fs/ext4/ext4.h
++++ linux-2.6.32-504.el6.x86_64/fs/ext4/ext4.h
+@@ -1147,6 +1147,9 @@
+       unsigned long s_ext_extents;
+ #endif
++      /* maximum possible extents tree depth, to be computed at mount time */
++      unsigned int s_max_ext_tree_depth;
++
+       /* for buddy allocator */
+       struct ext4_group_info ***s_group_info;
+       struct inode *s_buddy_cache;
+Index: linux-2.6.32-504.el6.x86_64/fs/ext4/super.c
+===================================================================
+--- linux-2.6.32-504.el6.x86_64.orig/fs/ext4/super.c
++++ linux-2.6.32-504.el6.x86_64/fs/ext4/super.c
+@@ -3529,6 +3529,8 @@
+               if (ext4_multi_mount_protect(sb, le64_to_cpu(es->s_mmp_block)))
+                       goto failed_mount3;
++      ext4_ext_init(sb); /* needed before using extent-mapped journal */
++
+       /*
+        * The first inode we look at is the journal inode.  Don't try
+        * root first: it may be modified in the journal!
+@@ -3722,7 +3724,6 @@
+               goto failed_mount4a;
+       }
+-      ext4_ext_init(sb);
+       err = ext4_mb_init(sb, needs_recovery);
+       if (err) {
+               ext4_msg(sb, KERN_ERR, "failed to initalize mballoc (%d)",
+Index: linux-2.6.32-504.el6.x86_64/fs/ext4/extents.c
+===================================================================
+--- linux-2.6.32-504.el6.x86_64.orig/fs/ext4/extents.c
++++ linux-2.6.32-504.el6.x86_64/fs/ext4/extents.c
+@@ -687,8 +687,9 @@
+       /* account possible depth increase */
+       if (!path) {
+-              path = kzalloc(sizeof(struct ext4_ext_path) * (depth + 2),
+-                              GFP_NOFS);
++              path = kzalloc(sizeof(struct ext4_ext_path) *
++                             EXT4_SB(inode->i_sb)->s_max_ext_tree_depth,
++                             GFP_NOFS);
+               if (!path)
+                       return ERR_PTR(-ENOMEM);
+               alloc = 1;
+@@ -1985,12 +1986,6 @@
+                       break;
+               }
+-              if (ext_depth(inode) != depth) {
+-                      /* depth was changed. we have to realloc path */
+-                      kfree(path);
+-                      path = NULL;
+-              }
+-
+               block = cbex.ec_block + cbex.ec_len;
+       }
+@@ -2636,7 +2631,8 @@
+        * after i_size and walking into the tree depth-wise.
+        */
+       depth = ext_depth(inode);
+-      path = kzalloc(sizeof(struct ext4_ext_path) * (depth + 1), GFP_NOFS);
++      path = kzalloc(sizeof(struct ext4_ext_path) *
++                     EXT4_SB(inode->i_sb)->s_max_ext_tree_depth, GFP_NOFS);
+       if (path == NULL) {
+               ext4_journal_stop(handle);
+               return -ENOMEM;
+@@ -2755,13 +2751,15 @@
+  */
+ void ext4_ext_init(struct super_block *sb)
+ {
++      ext4_fsblk_t maxblocks;
++
+       /*
+        * possible initialization would be here
+        */
+       if (EXT4_HAS_INCOMPAT_FEATURE(sb, EXT4_FEATURE_INCOMPAT_EXTENTS)) {
+-#if defined(AGGRESSIVE_TEST) || defined(CHECK_BINSEARCH) || defined(EXTENTS_STATS)
+-              printk(KERN_INFO "EXT4-fs: file extents enabled");
++              printk(KERN_INFO "EXT4-fs (%s): file extents enabled",
++                     sb->s_id);
+ #ifdef AGGRESSIVE_TEST
+               printk(", aggressive tests");
+ #endif
+@@ -2770,14 +2768,35 @@
+ #endif
+ #ifdef EXTENTS_STATS
+               printk(", stats");
+-#endif
+-              printk("\n");
+-#endif
+-#ifdef EXTENTS_STATS
+               spin_lock_init(&EXT4_SB(sb)->s_ext_stats_lock);
+               EXT4_SB(sb)->s_ext_min = 1 << 30;
+               EXT4_SB(sb)->s_ext_max = 0;
+ #endif
++              EXT4_SB(sb)->s_max_ext_tree_depth = 1;
++
++              maxblocks = sb->s_maxbytes / sb->s_blocksize;
++
++              /* 1st/root level/node of extents tree stands in i_data and
++               * entries stored in tree nodes can be of type ext4_extent
++               * (leaf node) or ext4_extent_idx (internal node) */
++              maxblocks /= (sizeof(((struct ext4_inode_info *)0x0)->i_data) -
++                            sizeof(struct ext4_extent_header)) /
++                           max(sizeof(struct ext4_extent),
++                               sizeof(struct ext4_extent_idx));
++
++              /* compute maximum extents tree depth for a fully populated
++               * file of max size made of only minimal/1-block extents */
++              while (maxblocks > 0) {
++                      maxblocks /= (sb->s_blocksize -
++                                    sizeof(struct ext4_extent_header)) /
++                                   max(sizeof(struct ext4_extent),
++                                       sizeof(struct ext4_extent_idx));
++                      EXT4_SB(sb)->s_max_ext_tree_depth++;
++              }
++
++              printk(", maximum tree depth=%u",
++                     EXT4_SB(sb)->s_max_ext_tree_depth);
++              printk("\n");
+       }
+ }
+@@ -3592,15 +3611,10 @@
+                                * the start of the hole
+                                */
+                               ext4_ext_drop_refs(path);
+-                              kfree(path);
++                              /* keep/reuse path */
+                               path = ext4_ext_find_extent(inode,
+-                              map->m_lblk, NULL);
+-                              if (IS_ERR(path)) {
+-                                      err = PTR_ERR(path);
+-                                      path = NULL;
+-                                      goto out2;
+-                              }
++                                                          map->m_lblk, path);
+                               depth = ext_depth(inode);
+                               ex = path[depth].p_ext;
index e3df418..9405d7e 100644 (file)
@@ -47,3 +47,4 @@ rhel6.6/ext4-remove-truncate-warning.patch
 rhel6.6/ext4-corrupted-inode-block-bitmaps-handling-patches.patch
 rhel6.3/ext4-notalloc_under_idatasem.patch
 rhel6.5/ext4-give-warning-with-dir-htree-growing.patch
+rhel6.6/ext4_s_max_ext_tree_depth.patch
index e3fd3fd..bea14bc 100644 (file)
@@ -46,3 +46,4 @@ rhel6.6/ext4-remove-truncate-warning.patch
 rhel6.6/ext4-corrupted-inode-block-bitmaps-handling-patches.patch
 rhel6.3/ext4-notalloc_under_idatasem.patch
 rhel6.5/ext4-give-warning-with-dir-htree-growing.patch
+rhel6.6/ext4_s_max_ext_tree_depth.patch
index 4728457..f8405dd 100644 (file)
@@ -38,3 +38,4 @@ sles11sp2/ext4-max-dir-size-options.patch
 rhel6.3/ext4-not-discard-preallocation-umount.patch
 rhel6.3/ext4-journal-path-opt.patch
 rhel6.3/ext4-notalloc_under_idatasem.patch
+sles11sp3/ext4_s_max_ext_tree_depth.patch
index 9cb4ecd..72124a1 100644 (file)
@@ -40,3 +40,4 @@ sles11sp2/ext4-corrupted-inode-block-bitmaps-handling-patches.patch
 rhel6.3/ext4-notalloc_under_idatasem.patch
 rhel6.5/ext4-give-warning-with-dir-htree-growing.patch
 sles11sp3/ext4-mmp-brelse.patch
+sles11sp3/ext4_s_max_ext_tree_depth.patch
index db32551..c4ea562 100644 (file)
@@ -20,3 +20,4 @@ rhel7/ext4-corrupted-inode-block-bitmaps-handling-patches.patch
 rhel7/ext4-give-warning-with-dir-htree-growing.patch
 rhel7/ext4-mmp-brelse.patch
 rhel7/ext4-jcb-optimization.patch
+rhel7/ext4_s_max_ext_tree_depth.patch
index 69906c5..926f63a 100644 (file)
@@ -20,3 +20,4 @@ rhel7/ext4-corrupted-inode-block-bitmaps-handling-patches.patch
 rhel7/ext4-give-warning-with-dir-htree-growing.patch
 rhel7/ext4-mmp-brelse.patch
 rhel7/ext4-jcb-optimization.patch
+rhel7/ext4_s_max_ext_tree_depth.patch