1b2441318SGreg Kroah-Hartman // SPDX-License-Identifier: GPL-2.0 2889c92d2SH. Peter Anvin /* 3889c92d2SH. Peter Anvin * decompress.c 4889c92d2SH. Peter Anvin * 5889c92d2SH. Peter Anvin * Detect the decompression method based on magic number 6889c92d2SH. Peter Anvin */ 7889c92d2SH. Peter Anvin 8889c92d2SH. Peter Anvin #include <linux/decompress/generic.h> 9889c92d2SH. Peter Anvin 10889c92d2SH. Peter Anvin #include <linux/decompress/bunzip2.h> 11889c92d2SH. Peter Anvin #include <linux/decompress/unlzma.h> 123ebe1243SLasse Collin #include <linux/decompress/unxz.h> 13889c92d2SH. Peter Anvin #include <linux/decompress/inflate.h> 14cacb246fSAlbin Tonnerre #include <linux/decompress/unlzo.h> 15e76e1fdfSKyungsik Lee #include <linux/decompress/unlz4.h> 16*4963bb2bSNick Terrell #include <linux/decompress/unzstd.h> 17889c92d2SH. Peter Anvin 18889c92d2SH. Peter Anvin #include <linux/types.h> 19889c92d2SH. Peter Anvin #include <linux/string.h> 2033e2a422SHein Tibosch #include <linux/init.h> 216aa7a29aSDaniel M. Weeks #include <linux/printk.h> 22889c92d2SH. Peter Anvin 2323a22d57SH. Peter Anvin #ifndef CONFIG_DECOMPRESS_GZIP 2423a22d57SH. Peter Anvin # define gunzip NULL 2523a22d57SH. Peter Anvin #endif 2623a22d57SH. Peter Anvin #ifndef CONFIG_DECOMPRESS_BZIP2 2723a22d57SH. Peter Anvin # define bunzip2 NULL 2823a22d57SH. Peter Anvin #endif 2923a22d57SH. Peter Anvin #ifndef CONFIG_DECOMPRESS_LZMA 3023a22d57SH. Peter Anvin # define unlzma NULL 3123a22d57SH. Peter Anvin #endif 323ebe1243SLasse Collin #ifndef CONFIG_DECOMPRESS_XZ 333ebe1243SLasse Collin # define unxz NULL 343ebe1243SLasse Collin #endif 35cacb246fSAlbin Tonnerre #ifndef CONFIG_DECOMPRESS_LZO 36cacb246fSAlbin Tonnerre # define unlzo NULL 37cacb246fSAlbin Tonnerre #endif 38e76e1fdfSKyungsik Lee #ifndef CONFIG_DECOMPRESS_LZ4 39e76e1fdfSKyungsik Lee # define unlz4 NULL 40e76e1fdfSKyungsik Lee #endif 41*4963bb2bSNick Terrell #ifndef CONFIG_DECOMPRESS_ZSTD 42*4963bb2bSNick Terrell # define unzstd NULL 43*4963bb2bSNick Terrell #endif 4423a22d57SH. Peter Anvin 4533e2a422SHein Tibosch struct compress_format { 46889c92d2SH. Peter Anvin unsigned char magic[2]; 47889c92d2SH. Peter Anvin const char *name; 48889c92d2SH. Peter Anvin decompress_fn decompressor; 4933e2a422SHein Tibosch }; 5033e2a422SHein Tibosch 516f9982bdSAndi Kleen static const struct compress_format compressed_formats[] __initconst = { 52a060bfe0SHaesung Kim { {0x1f, 0x8b}, "gzip", gunzip }, 53a060bfe0SHaesung Kim { {0x1f, 0x9e}, "gzip", gunzip }, 54889c92d2SH. Peter Anvin { {0x42, 0x5a}, "bzip2", bunzip2 }, 55889c92d2SH. Peter Anvin { {0x5d, 0x00}, "lzma", unlzma }, 563ebe1243SLasse Collin { {0xfd, 0x37}, "xz", unxz }, 57cacb246fSAlbin Tonnerre { {0x89, 0x4c}, "lzo", unlzo }, 58e76e1fdfSKyungsik Lee { {0x02, 0x21}, "lz4", unlz4 }, 59*4963bb2bSNick Terrell { {0x28, 0xb5}, "zstd", unzstd }, 60889c92d2SH. Peter Anvin { {0, 0}, NULL, NULL } 61889c92d2SH. Peter Anvin }; 62889c92d2SH. Peter Anvin 63d97b07c5SYinghai Lu decompress_fn __init decompress_method(const unsigned char *inbuf, long len, 64889c92d2SH. Peter Anvin const char **name) 65889c92d2SH. Peter Anvin { 66889c92d2SH. Peter Anvin const struct compress_format *cf; 67889c92d2SH. Peter Anvin 685a09e6ceSAneesh Kumar K.V if (len < 2) { 695a09e6ceSAneesh Kumar K.V if (name) 705a09e6ceSAneesh Kumar K.V *name = NULL; 71889c92d2SH. Peter Anvin return NULL; /* Need at least this much... */ 725a09e6ceSAneesh Kumar K.V } 73889c92d2SH. Peter Anvin 746aa7a29aSDaniel M. Weeks pr_debug("Compressed data magic: %#.2x %#.2x\n", inbuf[0], inbuf[1]); 756aa7a29aSDaniel M. Weeks 76e4aa7ca5SAlain Knaff for (cf = compressed_formats; cf->name; cf++) { 77889c92d2SH. Peter Anvin if (!memcmp(inbuf, cf->magic, 2)) 78889c92d2SH. Peter Anvin break; 79889c92d2SH. Peter Anvin 80889c92d2SH. Peter Anvin } 81889c92d2SH. Peter Anvin if (name) 82889c92d2SH. Peter Anvin *name = cf->name; 83889c92d2SH. Peter Anvin return cf->decompressor; 84889c92d2SH. Peter Anvin } 85