Unverified Commit 376dd57d authored by Mark Brown's avatar Mark Brown
Browse files

Merge series "ASoC: SOF: fix kcontrol size checks" from Kai Vehmanen...

Merge series "ASoC: SOF: fix kcontrol size checks" from Kai Vehmanen <kai.vehmanen@linux.intel.com>:

Series that fixes checks for 'size' in kcontrol get/put ext_bytes methods
for SOF. The gaps in these checks were discovered via cppcheck warnings
on unused variable values.

Pierre-Louis Bossart (5):
  ASoC: SOF: control: fix size checks for ext_bytes control .get()
  ASoC: SOF: control: fix size checks for volatile ext_bytes control
    .get()
  ASoC: SOF: control: add size checks for ext_bytes control .put()
  ASoC: SOF: control: remove const in sizeof()
  ASoC: SOF: topology: remove const in sizeof()

 sound/soc/sof/control.c  | 53 +++++++++++++++++++++++++++++++---------
 sound/soc/sof/topology.c |  2 +-
 2 files changed, 43 insertions(+), 12 deletions(-)

--
2.27.0
parents 163cd105 2ca21011
Loading
Loading
Loading
Loading
+32 −1
Original line number Diff line number Diff line
@@ -300,6 +300,10 @@ int snd_sof_bytes_ext_put(struct snd_kcontrol *kcontrol,
	const struct snd_ctl_tlv __user *tlvd =
		(const struct snd_ctl_tlv __user *)binary_data;

	/* make sure we have at least a header */
	if (size < sizeof(struct snd_ctl_tlv))
		return -EINVAL;

	/*
	 * The beginning of bytes data contains a header from where
	 * the length (as bytes) is needed to know the correct copy
@@ -308,6 +312,13 @@ int snd_sof_bytes_ext_put(struct snd_kcontrol *kcontrol,
	if (copy_from_user(&header, tlvd, sizeof(const struct snd_ctl_tlv)))
		return -EFAULT;

	/* make sure TLV info is consistent */
	if (header.length + sizeof(struct snd_ctl_tlv) > size) {
		dev_err_ratelimited(scomp->dev, "error: inconsistent TLV, data %d + header %zu > %d\n",
				    header.length, sizeof(struct snd_ctl_tlv), size);
		return -EINVAL;
	}

	/* be->max is coming from topology */
	if (header.length > be->max) {
		dev_err_ratelimited(scomp->dev, "error: Bytes data size %d exceeds max %d.\n",
@@ -369,6 +380,14 @@ int snd_sof_bytes_ext_volatile_get(struct snd_kcontrol *kcontrol, unsigned int _
	int ret;
	int err;

	/*
	 * Decrement the limit by ext bytes header size to
	 * ensure the user space buffer is not exceeded.
	 */
	if (size < sizeof(struct snd_ctl_tlv))
		return -ENOSPC;
	size -= sizeof(struct snd_ctl_tlv);

	ret = pm_runtime_get_sync(scomp->dev);
	if (ret < 0 && ret != -EACCES) {
		dev_err_ratelimited(scomp->dev, "error: bytes_ext get failed to resume %d\n", ret);
@@ -396,6 +415,12 @@ int snd_sof_bytes_ext_volatile_get(struct snd_kcontrol *kcontrol, unsigned int _

	data_size = cdata->data->size + sizeof(const struct sof_abi_hdr);

	/* make sure we don't exceed size provided by user space for data */
	if (data_size > size) {
		ret = -ENOSPC;
		goto out;
	}

	header.numid = scontrol->cmd;
	header.length = data_size;
	if (copy_to_user(tlvd, &header, sizeof(const struct snd_ctl_tlv))) {
@@ -432,7 +457,9 @@ int snd_sof_bytes_ext_get(struct snd_kcontrol *kcontrol,
	 * Decrement the limit by ext bytes header size to
	 * ensure the user space buffer is not exceeded.
	 */
	size -= sizeof(const struct snd_ctl_tlv);
	if (size < sizeof(struct snd_ctl_tlv))
		return -ENOSPC;
	size -= sizeof(struct snd_ctl_tlv);

	/* set the ABI header values */
	cdata->data->magic = SOF_ABI_MAGIC;
@@ -448,6 +475,10 @@ int snd_sof_bytes_ext_get(struct snd_kcontrol *kcontrol,

	data_size = cdata->data->size + sizeof(const struct sof_abi_hdr);

	/* make sure we don't exceed size provided by user space for data */
	if (data_size > size)
		return -ENOSPC;

	header.numid = scontrol->cmd;
	header.length = data_size;
	if (copy_to_user(tlvd, &header, sizeof(const struct snd_ctl_tlv)))