Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

erofs: enable error reporting for z_erofs_fixup_insize()

Enable propagation of detailed errors to callers.

Signed-off-by: Gao Xiang <hsiangkao@linux.alibaba.com>

Gao Xiang 30e13e41 3a991f78

+38 -38
+2 -2
fs/erofs/compress.h
··· 72 72 73 73 const char *z_erofs_stream_switch_bufs(struct z_erofs_stream_dctx *dctx, 74 74 void **dst, void **src, struct page **pgpl); 75 - int z_erofs_fixup_insize(struct z_erofs_decompress_req *rq, const char *padbuf, 76 - unsigned int padbufsize); 75 + const char *z_erofs_fixup_insize(struct z_erofs_decompress_req *rq, 76 + const char *padbuf, unsigned int padbufsize); 77 77 int __init z_erofs_init_decompressor(void); 78 78 void z_erofs_exit_decompressor(void); 79 79 int z_erofs_crypto_decompress(struct z_erofs_decompress_req *rq,
+11 -10
fs/erofs/decompressor.c
··· 178 178 } 179 179 180 180 /* 181 - * Get the exact inputsize with zero_padding feature. 182 - * - For LZ4, it should work if zero_padding feature is on (5.3+); 183 - * - For MicroLZMA, it'd be enabled all the time. 181 + * Get the exact on-disk size of the compressed data: 182 + * - For LZ4, it should apply if the zero_padding feature is on (5.3+); 183 + * - For others, zero_padding is enabled all the time. 184 184 */ 185 - int z_erofs_fixup_insize(struct z_erofs_decompress_req *rq, const char *padbuf, 186 - unsigned int padbufsize) 185 + const char *z_erofs_fixup_insize(struct z_erofs_decompress_req *rq, 186 + const char *padbuf, unsigned int padbufsize) 187 187 { 188 188 const char *padend; 189 189 190 190 padend = memchr_inv(padbuf, 0, padbufsize); 191 191 if (!padend) 192 - return -EFSCORRUPTED; 192 + return "compressed data start not found"; 193 193 rq->inputsize -= padend - padbuf; 194 194 rq->pageofs_in += padend - padbuf; 195 - return 0; 195 + return NULL; 196 196 } 197 197 198 198 static int z_erofs_lz4_decompress_mem(struct z_erofs_decompress_req *rq, u8 *dst) ··· 200 200 bool support_0padding = false, may_inplace = false; 201 201 unsigned int inputmargin; 202 202 u8 *out, *headpage, *src; 203 + const char *reason; 203 204 int ret, maptype; 204 205 205 206 DBG_BUGON(*rq->in == NULL); ··· 209 208 /* LZ4 decompression inplace is only safe if zero_padding is enabled */ 210 209 if (erofs_sb_has_zero_padding(EROFS_SB(rq->sb))) { 211 210 support_0padding = true; 212 - ret = z_erofs_fixup_insize(rq, headpage + rq->pageofs_in, 211 + reason = z_erofs_fixup_insize(rq, headpage + rq->pageofs_in, 213 212 min_t(unsigned int, rq->inputsize, 214 213 rq->sb->s_blocksize - rq->pageofs_in)); 215 - if (ret) { 214 + if (reason) { 216 215 kunmap_local(headpage); 217 - return ret; 216 + return IS_ERR(reason) ? PTR_ERR(reason) : -EFSCORRUPTED; 218 217 } 219 218 may_inplace = !((rq->pageofs_in + rq->inputsize) & 220 219 (rq->sb->s_blocksize - 1));
+4 -3
fs/erofs/decompressor_crypto.c
··· 9 9 struct sg_table st_src, st_dst; 10 10 struct acomp_req *req; 11 11 struct crypto_wait wait; 12 + const char *reason; 12 13 u8 *headpage; 13 14 int ret; 14 15 15 16 headpage = kmap_local_page(*rq->in); 16 - ret = z_erofs_fixup_insize(rq, headpage + rq->pageofs_in, 17 + reason = z_erofs_fixup_insize(rq, headpage + rq->pageofs_in, 17 18 min_t(unsigned int, rq->inputsize, 18 19 rq->sb->s_blocksize - rq->pageofs_in)); 19 20 kunmap_local(headpage); 20 - if (ret) 21 - return ret; 21 + if (reason) 22 + return IS_ERR(reason) ? PTR_ERR(reason) : -EFSCORRUPTED; 22 23 23 24 req = acomp_request_alloc(tfm); 24 25 if (!req)
+9 -10
fs/erofs/decompressor_deflate.c
··· 103 103 struct super_block *sb = rq->sb; 104 104 struct z_erofs_stream_dctx dctx = { .rq = rq, .no = -1, .ni = 0 }; 105 105 struct z_erofs_deflate *strm; 106 - const char *reason = NULL; 107 - int zerr, err; 106 + const char *reason; 107 + int zerr; 108 108 109 109 /* 1. get the exact DEFLATE compressed size */ 110 110 dctx.kin = kmap_local_page(*rq->in); 111 - err = z_erofs_fixup_insize(rq, dctx.kin + rq->pageofs_in, 111 + reason = z_erofs_fixup_insize(rq, dctx.kin + rq->pageofs_in, 112 112 min(rq->inputsize, sb->s_blocksize - rq->pageofs_in)); 113 - if (err) { 113 + if (reason) { 114 114 kunmap_local(dctx.kin); 115 - return ERR_PTR(err); 115 + return reason; 116 116 } 117 117 118 118 /* 2. get an available DEFLATE context */ ··· 130 130 /* 3. multi-call decompress */ 131 131 zerr = zlib_inflateInit2(&strm->z, -MAX_WBITS); 132 132 if (zerr != Z_OK) { 133 - err = -EINVAL; 133 + reason = ERR_PTR(-EINVAL); 134 134 goto failed_zinit; 135 135 } 136 136 ··· 161 161 reason = (zerr == Z_DATA_ERROR ? 162 162 "corrupted compressed data" : 163 163 "unexpected end of stream"); 164 - err = -EFSCORRUPTED; 165 164 break; 166 165 } 167 166 } 168 - if (zlib_inflateEnd(&strm->z) != Z_OK && !err) 169 - err = -EIO; 167 + if (zlib_inflateEnd(&strm->z) != Z_OK && !reason) 168 + reason = ERR_PTR(-EIO); 170 169 if (dctx.kout) 171 170 kunmap_local(dctx.kout); 172 171 failed_zinit: ··· 176 177 z_erofs_deflate_head = strm; 177 178 spin_unlock(&z_erofs_deflate_lock); 178 179 wake_up(&z_erofs_deflate_wq); 179 - return reason ?: ERR_PTR(err); 180 + return reason; 180 181 } 181 182 182 183 static const char *z_erofs_deflate_decompress(struct z_erofs_decompress_req *rq,
+5 -6
fs/erofs/decompressor_lzma.c
··· 154 154 struct xz_buf buf = {}; 155 155 struct z_erofs_lzma *strm; 156 156 enum xz_ret xz_err; 157 - const char *reason = NULL; 158 - int err; 157 + const char *reason; 159 158 160 159 /* 1. get the exact LZMA compressed size */ 161 160 dctx.kin = kmap_local_page(*rq->in); 162 - err = z_erofs_fixup_insize(rq, dctx.kin + rq->pageofs_in, 161 + reason = z_erofs_fixup_insize(rq, dctx.kin + rq->pageofs_in, 163 162 min(rq->inputsize, sb->s_blocksize - rq->pageofs_in)); 164 - if (err) { 163 + if (reason) { 165 164 kunmap_local(dctx.kin); 166 - return ERR_PTR(err); 165 + return reason; 167 166 } 168 167 169 168 /* 2. get an available lzma context */ ··· 223 224 z_erofs_lzma_head = strm; 224 225 spin_unlock(&z_erofs_lzma_lock); 225 226 wake_up(&z_erofs_lzma_wq); 226 - return reason ?: ERR_PTR(err); 227 + return reason; 227 228 } 228 229 229 230 const struct z_erofs_decompressor z_erofs_lzma_decomp = {
+7 -7
fs/erofs/decompressor_zstd.c
··· 143 143 zstd_in_buffer in_buf = { NULL, 0, 0 }; 144 144 zstd_out_buffer out_buf = { NULL, 0, 0 }; 145 145 struct z_erofs_zstd *strm; 146 - const char *reason = NULL; 147 146 zstd_dstream *stream; 148 - int zerr, err; 147 + const char *reason; 148 + int zerr; 149 149 150 150 /* 1. get the exact compressed size */ 151 151 dctx.kin = kmap_local_page(*rq->in); 152 - err = z_erofs_fixup_insize(rq, dctx.kin + rq->pageofs_in, 152 + reason = z_erofs_fixup_insize(rq, dctx.kin + rq->pageofs_in, 153 153 min(rq->inputsize, sb->s_blocksize - rq->pageofs_in)); 154 - if (err) { 154 + if (reason) { 155 155 kunmap_local(dctx.kin); 156 - return ERR_PTR(err); 156 + return reason; 157 157 } 158 158 159 159 /* 2. get an available ZSTD context */ ··· 162 162 /* 3. multi-call decompress */ 163 163 stream = zstd_init_dstream(z_erofs_zstd_max_dictsize, strm->wksp, strm->wkspsz); 164 164 if (!stream) { 165 - err = -ENOMEM; 165 + reason = ERR_PTR(-ENOMEM); 166 166 goto failed_zinit; 167 167 } 168 168 ··· 208 208 z_erofs_zstd_head = strm; 209 209 spin_unlock(&z_erofs_zstd_lock); 210 210 wake_up(&z_erofs_zstd_wq); 211 - return reason ?: ERR_PTR(err); 211 + return reason; 212 212 } 213 213 214 214 const struct z_erofs_decompressor z_erofs_zstd_decomp = {