Testbench: Check num_elems in tokens parsing

This patch adds check for sane num_elems value. If the calculated
array size exceeds the value size an error is returned and topology
parsing is aborted.

Signed-off-by: Seppo Ingalsuo <seppo.ingalsuo@linux.intel.com>
This commit is contained in:
Seppo Ingalsuo 2020-07-28 18:23:49 +03:00 committed by Liam Girdwood
parent d9fea08a24
commit fa4a7bda4e
2 changed files with 57 additions and 32 deletions

View File

@ -200,18 +200,18 @@ int sof_parse_tokens(void *object,
const struct sof_topology_token *tokens,
int count, struct snd_soc_tplg_vendor_array *array,
int priv_size);
void sof_parse_string_tokens(void *object,
const struct sof_topology_token *tokens,
int count,
struct snd_soc_tplg_vendor_array *array);
void sof_parse_uuid_tokens(void *object,
const struct sof_topology_token *tokens,
int count,
struct snd_soc_tplg_vendor_array *array);
void sof_parse_word_tokens(void *object,
const struct sof_topology_token *tokens,
int count,
struct snd_soc_tplg_vendor_array *array);
int sof_parse_string_tokens(void *object,
const struct sof_topology_token *tokens,
int count,
struct snd_soc_tplg_vendor_array *array);
int sof_parse_uuid_tokens(void *object,
const struct sof_topology_token *tokens,
int count,
struct snd_soc_tplg_vendor_array *array);
int sof_parse_word_tokens(void *object,
const struct sof_topology_token *tokens,
int count,
struct snd_soc_tplg_vendor_array *array);
int get_token_dai_type(void *elem, void *object, uint32_t offset,
uint32_t size);
enum sof_ipc_dai_type find_dai(const char *name);

View File

@ -1264,8 +1264,9 @@ int sof_parse_tokens(void *object, const struct sof_topology_token *tokens,
int priv_size)
{
int asize;
int ret = 0;
while (priv_size > 0) {
while (priv_size > 0 && ret == 0) {
asize = array->size;
/* validate asize */
@ -1287,19 +1288,16 @@ int sof_parse_tokens(void *object, const struct sof_topology_token *tokens,
/* call correct parser depending on type */
switch (array->type) {
case SND_SOC_TPLG_TUPLE_TYPE_UUID:
sof_parse_uuid_tokens(object, tokens, count,
array);
ret = sof_parse_uuid_tokens(object, tokens, count, array);
break;
case SND_SOC_TPLG_TUPLE_TYPE_STRING:
sof_parse_string_tokens(object, tokens, count,
array);
ret = sof_parse_string_tokens(object, tokens, count, array);
break;
case SND_SOC_TPLG_TUPLE_TYPE_BOOL:
case SND_SOC_TPLG_TUPLE_TYPE_BYTE:
case SND_SOC_TPLG_TUPLE_TYPE_WORD:
case SND_SOC_TPLG_TUPLE_TYPE_SHORT:
sof_parse_word_tokens(object, tokens, count,
array);
ret = sof_parse_word_tokens(object, tokens, count, array);
break;
default:
fprintf(stderr, "error: unknown token type %d\n",
@ -1307,18 +1305,25 @@ int sof_parse_tokens(void *object, const struct sof_topology_token *tokens,
return -EINVAL;
}
}
return 0;
return ret;
}
/* parse word tokens */
void sof_parse_word_tokens(void *object,
const struct sof_topology_token *tokens,
int count,
struct snd_soc_tplg_vendor_array *array)
int sof_parse_word_tokens(void *object,
const struct sof_topology_token *tokens,
int count,
struct snd_soc_tplg_vendor_array *array)
{
struct snd_soc_tplg_vendor_value_elem *elem;
int i, j;
if (sizeof(struct snd_soc_tplg_vendor_value_elem) * array->num_elems +
sizeof(struct snd_soc_tplg_vendor_array) > array->size) {
fprintf(stderr, "error: illegal array number of elements %d\n",
array->num_elems);
return -EINVAL;
}
/* parse element by element */
for (i = 0; i < array->num_elems; i++) {
elem = &array->value[i];
@ -1338,17 +1343,26 @@ void sof_parse_word_tokens(void *object,
tokens[j].size);
}
}
return 0;
}
/* parse uuid tokens */
void sof_parse_uuid_tokens(void *object,
const struct sof_topology_token *tokens,
int count,
struct snd_soc_tplg_vendor_array *array)
int sof_parse_uuid_tokens(void *object,
const struct sof_topology_token *tokens,
int count,
struct snd_soc_tplg_vendor_array *array)
{
struct snd_soc_tplg_vendor_uuid_elem *elem;
int i, j;
if (sizeof(struct snd_soc_tplg_vendor_uuid_elem) * array->num_elems +
sizeof(struct snd_soc_tplg_vendor_array) > array->size) {
fprintf(stderr, "error: illegal array number of elements %d\n",
array->num_elems);
return -EINVAL;
}
/* parse element by element */
for (i = 0; i < array->num_elems; i++) {
elem = &array->uuid[i];
@ -1368,17 +1382,26 @@ void sof_parse_uuid_tokens(void *object,
tokens[j].size);
}
}
return 0;
}
/* parse string tokens */
void sof_parse_string_tokens(void *object,
const struct sof_topology_token *tokens,
int count,
struct snd_soc_tplg_vendor_array *array)
int sof_parse_string_tokens(void *object,
const struct sof_topology_token *tokens,
int count,
struct snd_soc_tplg_vendor_array *array)
{
struct snd_soc_tplg_vendor_string_elem *elem;
int i, j;
if (sizeof(struct snd_soc_tplg_vendor_string_elem) * array->num_elems +
sizeof(struct snd_soc_tplg_vendor_array) > array->size) {
fprintf(stderr, "error: illegal array number of elements %d\n",
array->num_elems);
return -EINVAL;
}
/* parse element by element */
for (i = 0; i < array->num_elems; i++) {
elem = &array->string[i];
@ -1398,6 +1421,8 @@ void sof_parse_string_tokens(void *object,
tokens[j].size);
}
}
return 0;
}
enum sof_ipc_frame find_format(const char *name)