]> git.ipfire.org Git - thirdparty/kernel/stable-queue.git/blob - releases/4.4.73/romfs-use-different-way-to-generate-fsid-for-block-or-mtd.patch
5.1-stable patches
[thirdparty/kernel/stable-queue.git] / releases / 4.4.73 / romfs-use-different-way-to-generate-fsid-for-block-or-mtd.patch
1 From foo@baz Thu Jun 15 16:23:46 CEST 2017
2 From: Coly Li <colyli@suse.de>
3 Date: Tue, 24 Jan 2017 15:18:46 -0800
4 Subject: romfs: use different way to generate fsid for BLOCK or MTD
5
6 From: Coly Li <colyli@suse.de>
7
8
9 [ Upstream commit f598f82e204ec0b17797caaf1b0311c52d43fb9a ]
10
11 Commit 8a59f5d25265 ("fs/romfs: return f_fsid for statfs(2)") generates
12 a 64bit id from sb->s_bdev->bd_dev. This is only correct when romfs is
13 defined with CONFIG_ROMFS_ON_BLOCK. If romfs is only defined with
14 CONFIG_ROMFS_ON_MTD, sb->s_bdev is NULL, referencing sb->s_bdev->bd_dev
15 will triger an oops.
16
17 Richard Weinberger points out that when CONFIG_ROMFS_BACKED_BY_BOTH=y,
18 both CONFIG_ROMFS_ON_BLOCK and CONFIG_ROMFS_ON_MTD are defined.
19 Therefore when calling huge_encode_dev() to generate a 64bit id, I use
20 the follow order to choose parameter,
21
22 - CONFIG_ROMFS_ON_BLOCK defined
23 use sb->s_bdev->bd_dev
24 - CONFIG_ROMFS_ON_BLOCK undefined and CONFIG_ROMFS_ON_MTD defined
25 use sb->s_dev when,
26 - both CONFIG_ROMFS_ON_BLOCK and CONFIG_ROMFS_ON_MTD undefined
27 leave id as 0
28
29 When CONFIG_ROMFS_ON_MTD is defined and sb->s_mtd is not NULL, sb->s_dev
30 is set to a device ID generated by MTD_BLOCK_MAJOR and mtd index,
31 otherwise sb->s_dev is 0.
32
33 This is a try-best effort to generate a uniq file system ID, if all the
34 above conditions are not meet, f_fsid of this romfs instance will be 0.
35 Generally only one romfs can be built on single MTD block device, this
36 method is enough to identify multiple romfs instances in a computer.
37
38 Link: http://lkml.kernel.org/r/1482928596-115155-1-git-send-email-colyli@suse.de
39 Signed-off-by: Coly Li <colyli@suse.de>
40 Reported-by: Nong Li <nongli1031@gmail.com>
41 Tested-by: Nong Li <nongli1031@gmail.com>
42 Cc: Richard Weinberger <richard.weinberger@gmail.com>
43 Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
44 Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
45 Signed-off-by: Sasha Levin <alexander.levin@verizon.com>
46 Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
47 ---
48 fs/romfs/super.c | 23 ++++++++++++++++++++++-
49 1 file changed, 22 insertions(+), 1 deletion(-)
50
51 --- a/fs/romfs/super.c
52 +++ b/fs/romfs/super.c
53 @@ -74,6 +74,7 @@
54 #include <linux/highmem.h>
55 #include <linux/pagemap.h>
56 #include <linux/uaccess.h>
57 +#include <linux/major.h>
58 #include "internal.h"
59
60 static struct kmem_cache *romfs_inode_cachep;
61 @@ -415,7 +416,22 @@ static void romfs_destroy_inode(struct i
62 static int romfs_statfs(struct dentry *dentry, struct kstatfs *buf)
63 {
64 struct super_block *sb = dentry->d_sb;
65 - u64 id = huge_encode_dev(sb->s_bdev->bd_dev);
66 + u64 id = 0;
67 +
68 + /* When calling huge_encode_dev(),
69 + * use sb->s_bdev->bd_dev when,
70 + * - CONFIG_ROMFS_ON_BLOCK defined
71 + * use sb->s_dev when,
72 + * - CONFIG_ROMFS_ON_BLOCK undefined and
73 + * - CONFIG_ROMFS_ON_MTD defined
74 + * leave id as 0 when,
75 + * - CONFIG_ROMFS_ON_BLOCK undefined and
76 + * - CONFIG_ROMFS_ON_MTD undefined
77 + */
78 + if (sb->s_bdev)
79 + id = huge_encode_dev(sb->s_bdev->bd_dev);
80 + else if (sb->s_dev)
81 + id = huge_encode_dev(sb->s_dev);
82
83 buf->f_type = ROMFS_MAGIC;
84 buf->f_namelen = ROMFS_MAXFN;
85 @@ -488,6 +504,11 @@ static int romfs_fill_super(struct super
86 sb->s_flags |= MS_RDONLY | MS_NOATIME;
87 sb->s_op = &romfs_super_ops;
88
89 +#ifdef CONFIG_ROMFS_ON_MTD
90 + /* Use same dev ID from the underlying mtdblock device */
91 + if (sb->s_mtd)
92 + sb->s_dev = MKDEV(MTD_BLOCK_MAJOR, sb->s_mtd->index);
93 +#endif
94 /* read the image superblock and check it */
95 rsb = kmalloc(512, GFP_KERNEL);
96 if (!rsb)