All of lore.kernel.org
 help / color / mirror / Atom feed
From: Takashi Iwai <tiwai@suse.de>
To: Luis Chamberlain <mcgrof@kernel.org>
Cc: Greg Kroah-Hartman <gregkh@linuxfoundation.org>,
	"Rafael J . Wysocki" <rafael@kernel.org>,
	linux-kernel@vger.kernel.org
Subject: Re: [PATCH RFC 1/4] firmware: Add the support for ZSTD-compressed firmware files
Date: Wed, 17 Feb 2021 14:22:41 +0100	[thread overview]
Message-ID: <s5hczwy4yn2.wl-tiwai@suse.de> (raw)
In-Reply-To: <20210217131644.GM4332@42.do-not-panic.com>

On Wed, 17 Feb 2021 14:16:44 +0100,
Luis Chamberlain wrote:
> 
> On Wed, Jan 27, 2021 at 04:49:36PM +0100, Takashi Iwai wrote:
> > Due to the popular demands on ZSTD, here is a patch to add a support
> > of ZSTD-compressed firmware files via the direct firmware loader.
> > It's just like XZ-compressed file support, providing a decompressor
> > with ZSTD.  Since ZSTD API can give the decompression size beforehand,
> > the code is even simpler than XZ.
> > 
> > Signed-off-by: Takashi Iwai <tiwai@suse.de>
> > ---
> >  drivers/base/firmware_loader/Kconfig | 21 ++++++--
> >  drivers/base/firmware_loader/main.c  | 74 ++++++++++++++++++++++++++--
> >  2 files changed, 87 insertions(+), 8 deletions(-)
> > 
> > diff --git a/drivers/base/firmware_loader/Kconfig b/drivers/base/firmware_loader/Kconfig
> > index 5b24f3959255..f5307978927c 100644
> > --- a/drivers/base/firmware_loader/Kconfig
> > +++ b/drivers/base/firmware_loader/Kconfig
> > @@ -157,17 +157,28 @@ config FW_LOADER_USER_HELPER_FALLBACK
> >  
> >  config FW_LOADER_COMPRESS
> >  	bool "Enable compressed firmware support"
> > -	select FW_LOADER_PAGED_BUF
> > -	select XZ_DEC
> >  	help
> >  	  This option enables the support for loading compressed firmware
> >  	  files. The caller of firmware API receives the decompressed file
> >  	  content. The compressed file is loaded as a fallback, only after
> >  	  loading the raw file failed at first.
> >  
> > -	  Currently only XZ-compressed files are supported, and they have to
> > -	  be compressed with either none or crc32 integrity check type (pass
> > -	  "-C crc32" option to xz command).
> > +if FW_LOADER_COMPRESS
> > +config FW_LOADER_COMPRESS_XZ
> > +	bool "Enable XZ-compressed firmware support"
> > +	select FW_LOADER_PAGED_BUF
> > +	select XZ_DEC
> > +	help
> > +	  This option adds the support for XZ-compressed files.
> > +	  The files have to be compressed with either none or crc32
> > +	  integrity check type (pass "-C crc32" option to xz command).
> > +
> > +config FW_LOADER_COMPRESS_ZSTD
> > +	bool "Enable ZSTD-compressed firmware support"
> > +	select ZSTD_DECOMPRESS
> > +	help
> > +	  This option adds the support for ZSTD-compressed files.
> > +endif # FW_LOADER_COMPRESS
> >  
> >  config FW_CACHE
> >  	bool "Enable firmware caching during suspend"
> > diff --git a/drivers/base/firmware_loader/main.c b/drivers/base/firmware_loader/main.c
> > index 78355095e00d..71332ed4959d 100644
> > --- a/drivers/base/firmware_loader/main.c
> > +++ b/drivers/base/firmware_loader/main.c
> > @@ -34,6 +34,7 @@
> >  #include <linux/syscore_ops.h>
> >  #include <linux/reboot.h>
> >  #include <linux/security.h>
> > +#include <linux/zstd.h>
> >  #include <linux/xz.h>
> >  
> >  #include <generated/utsrelease.h>
> > @@ -362,10 +363,72 @@ int fw_map_paged_buf(struct fw_priv *fw_priv)
> >  }
> >  #endif
> >  
> > +/*
> > + * ZSTD-compressed firmware support
> > + */
> > +#ifdef CONFIG_FW_LOADER_COMPRESS_ZSTD
> > +static int fw_decompress_zstd(struct device *dev, struct fw_priv *fw_priv,
> > +			      size_t in_size, const void *in_buffer)
> > +{
> > +	size_t len, out_size, workspace_size;
> > +	void *workspace, *out_buf;
> > +	ZSTD_DCtx *ctx;
> > +	int err;
> > +
> > +	if (fw_priv->data) {
> > +		out_size = fw_priv->allocated_size;
> > +		out_buf = fw_priv->data;
> > +	} else {
> > +		out_size = ZSTD_findDecompressedSize(in_buffer, in_size);
> > +		if (out_size == ZSTD_CONTENTSIZE_UNKNOWN ||
> > +		    out_size == ZSTD_CONTENTSIZE_ERROR) {
> > +			dev_dbg(dev, "%s: invalid decompression size\n", __func__);
> > +			return -EINVAL;
> > +		}
> > +		out_buf = vzalloc(out_size);
> > +		if (!out_buf)
> > +			return -ENOMEM;
> > +	}
> > +
> > +	workspace_size = ZSTD_DCtxWorkspaceBound();
> > +	workspace = kvzalloc(workspace_size, GFP_KERNEL);
> > +	if (!workspace) {
> > +		err = -ENOMEM;
> > +		goto error;
> > +	}
> > +
> > +	ctx = ZSTD_initDCtx(workspace, workspace_size);
> > +	if (!ctx) {
> > +		dev_dbg(dev, "%s: failed to initialize context\n", __func__);
> > +		err = -EINVAL;
> > +		goto error;
> > +	}
> > +
> > +	len = ZSTD_decompressDCtx(ctx, out_buf, out_size, in_buffer, in_size);
> > +	if (ZSTD_isError(len)) {
> > +		dev_dbg(dev, "%s: failed to decompress: %d\n", __func__,
> > +			ZSTD_getErrorCode(len));
> > +		err = -EINVAL;
> > +		goto error;
> > +	}
> > +
> > +	fw_priv->size = len;
> > +	if (!fw_priv->data)
> > +		fw_priv->data = out_buf;
> > +	err = 0;
> > +
> > + error:
> > +	kvfree(workspace);
> > +	if (!fw_priv->data)
> > +		vfree(out_buf);
> > +	return err;
> > +}
> > +#endif /* CONFIG_FW_LOADER_COMPRESS_ZSTD */
> > +
> >  /*
> >   * XZ-compressed firmware support
> >   */
> > -#ifdef CONFIG_FW_LOADER_COMPRESS
> > +#ifdef CONFIG_FW_LOADER_COMPRESS_XZ
> >  /* show an error and return the standard error code */
> >  static int fw_decompress_xz_error(struct device *dev, enum xz_ret xz_ret)
> >  {
> > @@ -459,7 +522,7 @@ static int fw_decompress_xz(struct device *dev, struct fw_priv *fw_priv,
> >  	else
> >  		return fw_decompress_xz_pages(dev, fw_priv, in_size, in_buffer);
> >  }
> > -#endif /* CONFIG_FW_LOADER_COMPRESS */
> > +#endif /* CONFIG_FW_LOADER_COMPRESS_XZ */
> >  
> >  /* direct firmware loading support */
> >  static char fw_path_para[256];
> > @@ -814,7 +877,12 @@ _request_firmware(const struct firmware **firmware_p, const char *name,
> >  	if (!(opt_flags & FW_OPT_PARTIAL))
> >  		nondirect = true;
> >  
> > -#ifdef CONFIG_FW_LOADER_COMPRESS
> > +#ifdef CONFIG_FW_LOADER_COMPRESS_ZSTD
> > +	if (ret == -ENOENT && nondirect)
> > +		ret = fw_get_filesystem_firmware(device, fw->priv, ".zst",
> > +						 fw_decompress_zstd);
> > +#endif
> > +#ifdef CONFIG_FW_LOADER_COMPRESS_XZ
> >  	if (ret == -ENOENT && nondirect)
> >  		ret = fw_get_filesystem_firmware(device, fw->priv, ".xz",
> >  						 fw_decompress_xz);
> 
> Since this is growing, it would be nicer if we avoid the #ifdef mess and
> simply have code iterate over supported compressions, and this is
> observed here in one line.

If it ever grows further, yeah, but I guess this won't happen so
often :)  As of now, I chose the open-code as there are only two.


thanks,

Takashi

  reply	other threads:[~2021-02-17 13:31 UTC|newest]

Thread overview: 19+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2021-01-27 15:49 [PATCH RFC 0/4] firmware: Add ZSTD-compressed file support Takashi Iwai
2021-01-27 15:49 ` [PATCH RFC 1/4] firmware: Add the support for ZSTD-compressed firmware files Takashi Iwai
2021-02-17 13:16   ` Luis Chamberlain
2021-02-17 13:22     ` Takashi Iwai [this message]
2021-02-17 13:24   ` Luis Chamberlain
2021-02-17 13:34     ` Takashi Iwai
2021-02-17 14:17       ` Greg Kroah-Hartman
2021-02-17 14:21         ` Takashi Iwai
2021-01-27 15:49 ` [PATCH RFC 2/4] selftests: firmware: Simplify test patterns Takashi Iwai
2021-01-27 15:49 ` [PATCH RFC 3/4] selftest: firmware: Fix the request_firmware_into_buf() test for XZ format Takashi Iwai
2021-01-27 15:49 ` [PATCH RFC 4/4] selftest: firmware: Add ZSTD compressed file tests Takashi Iwai
2021-01-27 17:09 ` [PATCH RFC 0/4] firmware: Add ZSTD-compressed file support Greg Kroah-Hartman
2022-01-27 18:22   ` Hideki Yamane
2022-01-27 18:41     ` Greg Kroah-Hartman
2022-01-28  0:33       ` Hideki Yamane
2022-01-28  6:54         ` Greg Kroah-Hartman
2022-01-28  8:13           ` Takashi Iwai
2022-02-01 17:36             ` Hideki Yamane
2022-02-02 10:56               ` Takashi Iwai

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=s5hczwy4yn2.wl-tiwai@suse.de \
    --to=tiwai@suse.de \
    --cc=gregkh@linuxfoundation.org \
    --cc=linux-kernel@vger.kernel.org \
    --cc=mcgrof@kernel.org \
    --cc=rafael@kernel.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.