:::::: :::::: Manual check reason: "low confidence bisect report" :::::: Manual check reason: "low confidence static check warning: fs/verity/open.c:131:42: warning: use of uninitialized value 'blocks_in_level[level]' [CWE-457] [-Wanalyzer-use-of-uninitialized-value]" :::::: BCC: lkp@intel.com CC: oe-kbuild-all@lists.linux.dev TO: Eric Biggers tree: https://git.kernel.org/pub/scm/linux/kernel/git/ebiggers/linux.git fsverity-pending head: eb588328e1157356bae5a6494fae6b5cc8c42b25 commit: 4fd9af03daac2d1ee12a9afd0dc28512030f9295 [2/7] fsverity: support verification with tree block size < PAGE_SIZE :::::: branch date: 6 days ago :::::: commit date: 6 days ago config: arm-randconfig-c002-20221031 compiler: arm-linux-gnueabi-gcc (GCC) 12.1.0 reproduce (this is a W=1 build): wget https://raw.githubusercontent.com/intel/lkp-tests/master/sbin/make.cross -O ~/bin/make.cross chmod +x ~/bin/make.cross # https://git.kernel.org/pub/scm/linux/kernel/git/ebiggers/linux.git/commit/?id=4fd9af03daac2d1ee12a9afd0dc28512030f9295 git remote add ebiggers https://git.kernel.org/pub/scm/linux/kernel/git/ebiggers/linux.git git fetch --no-tags ebiggers fsverity-pending git checkout 4fd9af03daac2d1ee12a9afd0dc28512030f9295 # save the config file COMPILER_INSTALL_PATH=$HOME/0day COMPILER=gcc-12.1.0 make.cross ARCH=arm KBUILD_USERCFLAGS='-fanalyzer -Wno-error' If you fix the issue, kindly add following tag where applicable | Reported-by: kernel test robot gcc_analyzer warnings: (new ones prefixed by >>) fs/verity/open.c: In function 'fsverity_init_merkle_tree_params': >> fs/verity/open.c:131:42: warning: use of uninitialized value 'blocks_in_level[level]' [CWE-457] [-Wanalyzer-use-of-uninitialized-value] 131 | offset += blocks_in_level[level]; | ~~~~~~~~~~~~~~~^~~~~~~ 'fsverity_init_merkle_tree_params': events 1-4 | | 38 | u64 blocks_in_level[FS_VERITY_MAX_LEVELS]; | | ^~~~~~~~~~~~~~~ | | | | | (1) region created on stack here |...... | 45 | if (IS_ERR(hash_alg)) | | ~ | | | | | (2) following 'false' branch... | 46 | return PTR_ERR(hash_alg); | 47 | params->hash_alg = hash_alg; | | ~~~~~~~~~~~~~~~~~~~~~~~~~~~ | | | | | (3) ...to here |...... | 52 | if (IS_ERR(params->hashstate)) { | | ~ | | | | | (4) following 'false' branch... | 'fsverity_init_merkle_tree_params': events 5-9 | | 74 | if (log_blocksize < 10 || log_blocksize > PAGE_SHIFT || | | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | | | | | | (6) following 'false' branch... (8) following 'false' branch... | 75 | log_blocksize > inode->i_blkbits) { | | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | | | | | (7) ...to here |...... | 81 | params->log_blocksize = log_blocksize; | | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | | | | | (9) ...to here | 'fsverity_init_merkle_tree_params': events 10-11 | |include/linux/log2.h:47:24: | 47 | return (n != 0 && ((n & (n - 1)) == 0)); | | ~~~~~~~~^~~~~~~~~~~~~~~~~~~~~~~~ | | | | | (10) following 'true' branch... | | (11) ...to here | 'fsverity_init_merkle_tree_params': event 12 | |include/asm-generic/bug.h:123:12: | 123 | if (unlikely(__ret_warn_on)) \ | | ^ | | | | | (12) following 'false' branch... fs/verity/open.c:86:13: note: in expansion of macro 'WARN_ON' | 86 | if (WARN_ON(!is_power_of_2(params->digest_size))) { | | ^~~~~~~ | 'fsverity_init_merkle_tree_params': events 13-15 | | 90 | if (params->block_size < 2 * params->digest_size) { | | ~~~~~~~^~~~~~~~~~~~ | | | | | | | (13) ...to here | | (14) following 'false' branch... |...... | 97 | params->log_arity = params->log_blocksize - ilog2(params->digest_size); | | ~~~~~~~~~~~~~~~~~~~~~ | | | | | (15) ...to here | 'fsverity_init_merkle_tree_params': event 16 | |include/linux/log2.h:160:35: | 157 | ( \ | | ~~~ | 158 | __builtin_constant_p(n) ? \ | | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | 159 | ((n) < 2 ? 0 : \ | | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | 160 | 63 - __builtin_clzll(n)) : \ | | ~~~~~~~~~~~~~~~~~~~~~~~~~^~~~~~~ | | | | | (16) following 'true' branch... | 161 | (sizeof(n) <= 4) ? \ | | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | 162 | __ilog2_u32(n) : \ | | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | 163 | __ilog2_u64(n) \ | | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | 164 | ) | | ~ fs/verity/open.c:97:53: note: in expansion of macro 'ilog2' | 97 | params->log_arity = params->log_blocksize - ilog2(params->digest_size); | | ^~~~~ | 'fsverity_init_merkle_tree_params': event 17 | vim +131 fs/verity/open.c fd2d1acfcadfe2 Eric Biggers 2019-07-22 14 fd2d1acfcadfe2 Eric Biggers 2019-07-22 15 /** fd2d1acfcadfe2 Eric Biggers 2019-07-22 16 * fsverity_init_merkle_tree_params() - initialize Merkle tree parameters fd2d1acfcadfe2 Eric Biggers 2019-07-22 17 * @params: the parameters struct to initialize fd2d1acfcadfe2 Eric Biggers 2019-07-22 18 * @inode: the inode for which the Merkle tree is being built fd2d1acfcadfe2 Eric Biggers 2019-07-22 19 * @hash_algorithm: number of hash algorithm to use fd2d1acfcadfe2 Eric Biggers 2019-07-22 20 * @log_blocksize: log base 2 of block size to use fd2d1acfcadfe2 Eric Biggers 2019-07-22 21 * @salt: pointer to salt (optional) fd2d1acfcadfe2 Eric Biggers 2019-07-22 22 * @salt_size: size of salt, possibly 0 fd2d1acfcadfe2 Eric Biggers 2019-07-22 23 * fd2d1acfcadfe2 Eric Biggers 2019-07-22 24 * Validate the hash algorithm and block size, then compute the tree topology fd2d1acfcadfe2 Eric Biggers 2019-07-22 25 * (num levels, num blocks in each level, etc.) and initialize @params. fd2d1acfcadfe2 Eric Biggers 2019-07-22 26 * fd2d1acfcadfe2 Eric Biggers 2019-07-22 27 * Return: 0 on success, -errno on failure fd2d1acfcadfe2 Eric Biggers 2019-07-22 28 */ fd2d1acfcadfe2 Eric Biggers 2019-07-22 29 int fsverity_init_merkle_tree_params(struct merkle_tree_params *params, fd2d1acfcadfe2 Eric Biggers 2019-07-22 30 const struct inode *inode, fd2d1acfcadfe2 Eric Biggers 2019-07-22 31 unsigned int hash_algorithm, fd2d1acfcadfe2 Eric Biggers 2019-07-22 32 unsigned int log_blocksize, fd2d1acfcadfe2 Eric Biggers 2019-07-22 33 const u8 *salt, size_t salt_size) fd2d1acfcadfe2 Eric Biggers 2019-07-22 34 { 439bea104c3d21 Eric Biggers 2019-12-31 35 struct fsverity_hash_alg *hash_alg; fd2d1acfcadfe2 Eric Biggers 2019-07-22 36 int err; fd2d1acfcadfe2 Eric Biggers 2019-07-22 37 u64 blocks; 4fd9af03daac2d Eric Biggers 2022-10-28 38 u64 blocks_in_level[FS_VERITY_MAX_LEVELS]; fd2d1acfcadfe2 Eric Biggers 2019-07-22 39 u64 offset; fd2d1acfcadfe2 Eric Biggers 2019-07-22 40 int level; fd2d1acfcadfe2 Eric Biggers 2019-07-22 41 fd2d1acfcadfe2 Eric Biggers 2019-07-22 42 memset(params, 0, sizeof(*params)); fd2d1acfcadfe2 Eric Biggers 2019-07-22 43 fd2d1acfcadfe2 Eric Biggers 2019-07-22 44 hash_alg = fsverity_get_hash_alg(inode, hash_algorithm); fd2d1acfcadfe2 Eric Biggers 2019-07-22 45 if (IS_ERR(hash_alg)) fd2d1acfcadfe2 Eric Biggers 2019-07-22 46 return PTR_ERR(hash_alg); fd2d1acfcadfe2 Eric Biggers 2019-07-22 47 params->hash_alg = hash_alg; fd2d1acfcadfe2 Eric Biggers 2019-07-22 48 params->digest_size = hash_alg->digest_size; fd2d1acfcadfe2 Eric Biggers 2019-07-22 49 fd2d1acfcadfe2 Eric Biggers 2019-07-22 50 params->hashstate = fsverity_prepare_hash_state(hash_alg, salt, fd2d1acfcadfe2 Eric Biggers 2019-07-22 51 salt_size); fd2d1acfcadfe2 Eric Biggers 2019-07-22 52 if (IS_ERR(params->hashstate)) { fd2d1acfcadfe2 Eric Biggers 2019-07-22 53 err = PTR_ERR(params->hashstate); fd2d1acfcadfe2 Eric Biggers 2019-07-22 54 params->hashstate = NULL; fd2d1acfcadfe2 Eric Biggers 2019-07-22 55 fsverity_err(inode, "Error %d preparing hash state", err); fd2d1acfcadfe2 Eric Biggers 2019-07-22 56 goto out_err; fd2d1acfcadfe2 Eric Biggers 2019-07-22 57 } fd2d1acfcadfe2 Eric Biggers 2019-07-22 58 4fd9af03daac2d Eric Biggers 2022-10-28 59 /* 4fd9af03daac2d Eric Biggers 2022-10-28 60 * fs/verity/ directly assumes that the Merkle tree block size is a 4fd9af03daac2d Eric Biggers 2022-10-28 61 * power of 2 less than or equal to PAGE_SIZE. Another restriction 4fd9af03daac2d Eric Biggers 2022-10-28 62 * arises from the interaction between fs/verity/ and the filesystems 4fd9af03daac2d Eric Biggers 2022-10-28 63 * themselves: filesystems expect to be able to verify a single 4fd9af03daac2d Eric Biggers 2022-10-28 64 * filesystem block of data at a time. Therefore, the Merkle tree block 4fd9af03daac2d Eric Biggers 2022-10-28 65 * size must also be less than or equal to the filesystem block size. 4fd9af03daac2d Eric Biggers 2022-10-28 66 * 4fd9af03daac2d Eric Biggers 2022-10-28 67 * The above are the only hard limitations, so in theory the Merkle tree 4fd9af03daac2d Eric Biggers 2022-10-28 68 * block size could be as small as twice the digest size. However, 4fd9af03daac2d Eric Biggers 2022-10-28 69 * that's not useful, and it would result in some unusually deep and 4fd9af03daac2d Eric Biggers 2022-10-28 70 * large Merkle trees. So we currently require that the Merkle tree 4fd9af03daac2d Eric Biggers 2022-10-28 71 * block size be at least 1024 bytes. That's small enough to test the 4fd9af03daac2d Eric Biggers 2022-10-28 72 * sub-page block case on systems with 4K pages, but not too small. 4fd9af03daac2d Eric Biggers 2022-10-28 73 */ 4fd9af03daac2d Eric Biggers 2022-10-28 74 if (log_blocksize < 10 || log_blocksize > PAGE_SHIFT || 4fd9af03daac2d Eric Biggers 2022-10-28 75 log_blocksize > inode->i_blkbits) { fd2d1acfcadfe2 Eric Biggers 2019-07-22 76 fsverity_warn(inode, "Unsupported log_blocksize: %u", fd2d1acfcadfe2 Eric Biggers 2019-07-22 77 log_blocksize); fd2d1acfcadfe2 Eric Biggers 2019-07-22 78 err = -EINVAL; fd2d1acfcadfe2 Eric Biggers 2019-07-22 79 goto out_err; fd2d1acfcadfe2 Eric Biggers 2019-07-22 80 } fd2d1acfcadfe2 Eric Biggers 2019-07-22 81 params->log_blocksize = log_blocksize; fd2d1acfcadfe2 Eric Biggers 2019-07-22 82 params->block_size = 1 << log_blocksize; 4fd9af03daac2d Eric Biggers 2022-10-28 83 params->log_blocks_per_page = PAGE_SHIFT - log_blocksize; 4fd9af03daac2d Eric Biggers 2022-10-28 84 params->blocks_per_page = 1 << params->log_blocks_per_page; fd2d1acfcadfe2 Eric Biggers 2019-07-22 85 fd2d1acfcadfe2 Eric Biggers 2019-07-22 86 if (WARN_ON(!is_power_of_2(params->digest_size))) { fd2d1acfcadfe2 Eric Biggers 2019-07-22 87 err = -EINVAL; fd2d1acfcadfe2 Eric Biggers 2019-07-22 88 goto out_err; fd2d1acfcadfe2 Eric Biggers 2019-07-22 89 } fd2d1acfcadfe2 Eric Biggers 2019-07-22 90 if (params->block_size < 2 * params->digest_size) { fd2d1acfcadfe2 Eric Biggers 2019-07-22 91 fsverity_warn(inode, fd2d1acfcadfe2 Eric Biggers 2019-07-22 92 "Merkle tree block size (%u) too small for hash algorithm \"%s\"", fd2d1acfcadfe2 Eric Biggers 2019-07-22 93 params->block_size, hash_alg->name); fd2d1acfcadfe2 Eric Biggers 2019-07-22 94 err = -EINVAL; fd2d1acfcadfe2 Eric Biggers 2019-07-22 95 goto out_err; fd2d1acfcadfe2 Eric Biggers 2019-07-22 96 } fd2d1acfcadfe2 Eric Biggers 2019-07-22 97 params->log_arity = params->log_blocksize - ilog2(params->digest_size); fd2d1acfcadfe2 Eric Biggers 2019-07-22 98 params->hashes_per_block = 1 << params->log_arity; fd2d1acfcadfe2 Eric Biggers 2019-07-22 99 4fd9af03daac2d Eric Biggers 2022-10-28 100 pr_debug("Merkle tree uses %s with %u-byte blocks (%u hashes/block, %u blocks/page), salt=%*phN\n", fd2d1acfcadfe2 Eric Biggers 2019-07-22 101 hash_alg->name, params->block_size, params->hashes_per_block, 4fd9af03daac2d Eric Biggers 2022-10-28 102 params->blocks_per_page, (int)salt_size, salt); fd2d1acfcadfe2 Eric Biggers 2019-07-22 103 fd2d1acfcadfe2 Eric Biggers 2019-07-22 104 /* fd2d1acfcadfe2 Eric Biggers 2019-07-22 105 * Compute the number of levels in the Merkle tree and create a map from fd2d1acfcadfe2 Eric Biggers 2019-07-22 106 * level to the starting block of that level. Level 'num_levels - 1' is fd2d1acfcadfe2 Eric Biggers 2019-07-22 107 * the root and is stored first. Level 0 is the level directly "above" fd2d1acfcadfe2 Eric Biggers 2019-07-22 108 * the data blocks and is stored last. fd2d1acfcadfe2 Eric Biggers 2019-07-22 109 */ fd2d1acfcadfe2 Eric Biggers 2019-07-22 110 fd2d1acfcadfe2 Eric Biggers 2019-07-22 111 /* Compute number of levels and the number of blocks in each level */ 80f6e3080bfcf8 Eric Biggers 2021-09-16 112 blocks = ((u64)inode->i_size + params->block_size - 1) >> log_blocksize; fd2d1acfcadfe2 Eric Biggers 2019-07-22 113 pr_debug("Data is %lld bytes (%llu blocks)\n", inode->i_size, blocks); fd2d1acfcadfe2 Eric Biggers 2019-07-22 114 while (blocks > 1) { fd2d1acfcadfe2 Eric Biggers 2019-07-22 115 if (params->num_levels >= FS_VERITY_MAX_LEVELS) { fd2d1acfcadfe2 Eric Biggers 2019-07-22 116 fsverity_err(inode, "Too many levels in Merkle tree"); 4fd9af03daac2d Eric Biggers 2022-10-28 117 err = -EFBIG; fd2d1acfcadfe2 Eric Biggers 2019-07-22 118 goto out_err; fd2d1acfcadfe2 Eric Biggers 2019-07-22 119 } fd2d1acfcadfe2 Eric Biggers 2019-07-22 120 blocks = (blocks + params->hashes_per_block - 1) >> fd2d1acfcadfe2 Eric Biggers 2019-07-22 121 params->log_arity; 4fd9af03daac2d Eric Biggers 2022-10-28 122 blocks_in_level[params->num_levels++] = blocks; fd2d1acfcadfe2 Eric Biggers 2019-07-22 123 } fd2d1acfcadfe2 Eric Biggers 2019-07-22 124 fd2d1acfcadfe2 Eric Biggers 2019-07-22 125 /* Compute the starting block of each level */ fd2d1acfcadfe2 Eric Biggers 2019-07-22 126 offset = 0; fd2d1acfcadfe2 Eric Biggers 2019-07-22 127 for (level = (int)params->num_levels - 1; level >= 0; level--) { fd2d1acfcadfe2 Eric Biggers 2019-07-22 128 params->level_start[level] = offset; fd2d1acfcadfe2 Eric Biggers 2019-07-22 129 pr_debug("Level %d is %llu blocks starting at index %llu\n", 4fd9af03daac2d Eric Biggers 2022-10-28 130 level, blocks_in_level[level], offset); 4fd9af03daac2d Eric Biggers 2022-10-28 @131 offset += blocks_in_level[level]; 4fd9af03daac2d Eric Biggers 2022-10-28 132 } 4fd9af03daac2d Eric Biggers 2022-10-28 133 4fd9af03daac2d Eric Biggers 2022-10-28 134 /* 4fd9af03daac2d Eric Biggers 2022-10-28 135 * With block_size != PAGE_SIZE, an in-memory bitmap will need to be 4fd9af03daac2d Eric Biggers 2022-10-28 136 * allocated to track the "verified" status of hash blocks. Don't allow 4fd9af03daac2d Eric Biggers 2022-10-28 137 * this bitmap to get too large. For now, limit it to 1 MiB, which 4fd9af03daac2d Eric Biggers 2022-10-28 138 * limits the file size to about 4.4 TB with SHA-256 and 4K blocks. 4fd9af03daac2d Eric Biggers 2022-10-28 139 * 4fd9af03daac2d Eric Biggers 2022-10-28 140 * Together with the fact that the data, and thus also the Merkle tree, 4fd9af03daac2d Eric Biggers 2022-10-28 141 * cannot have more than ULONG_MAX pages, this implies that hash block 4fd9af03daac2d Eric Biggers 2022-10-28 142 * indices can always fit in an 'unsigned long'. But to be safe, we 4fd9af03daac2d Eric Biggers 2022-10-28 143 * explicitly check for that too. Note, this is only for hash block 4fd9af03daac2d Eric Biggers 2022-10-28 144 * indices; data block indices might not fit in an 'unsigned long'. 4fd9af03daac2d Eric Biggers 2022-10-28 145 */ 4fd9af03daac2d Eric Biggers 2022-10-28 146 if ((params->block_size != PAGE_SIZE && offset > 1 << 23) || 4fd9af03daac2d Eric Biggers 2022-10-28 147 offset > ULONG_MAX) { 4fd9af03daac2d Eric Biggers 2022-10-28 148 fsverity_err(inode, "Too many blocks in Merkle tree"); 4fd9af03daac2d Eric Biggers 2022-10-28 149 err = -EFBIG; 4fd9af03daac2d Eric Biggers 2022-10-28 150 goto out_err; fd2d1acfcadfe2 Eric Biggers 2019-07-22 151 } fd2d1acfcadfe2 Eric Biggers 2019-07-22 152 fd2d1acfcadfe2 Eric Biggers 2019-07-22 153 params->tree_size = offset << log_blocksize; 4fd9af03daac2d Eric Biggers 2022-10-28 154 params->tree_pages = PAGE_ALIGN(params->tree_size) >> PAGE_SHIFT; fd2d1acfcadfe2 Eric Biggers 2019-07-22 155 return 0; fd2d1acfcadfe2 Eric Biggers 2019-07-22 156 fd2d1acfcadfe2 Eric Biggers 2019-07-22 157 out_err: fd2d1acfcadfe2 Eric Biggers 2019-07-22 158 kfree(params->hashstate); fd2d1acfcadfe2 Eric Biggers 2019-07-22 159 memset(params, 0, sizeof(*params)); fd2d1acfcadfe2 Eric Biggers 2019-07-22 160 return err; fd2d1acfcadfe2 Eric Biggers 2019-07-22 161 } fd2d1acfcadfe2 Eric Biggers 2019-07-22 162 -- 0-DAY CI Kernel Test Service https://01.org/lkp