diff options
| author | Siena Richard <sienar@codeaurora.org> | 2017-02-28 12:52:30 -0800 |
|---|---|---|
| committer | Gerrit - the friendly Code Review server <code-review@localhost> | 2017-03-03 10:29:35 -0800 |
| commit | 5b2f6e011ba92f28e8d7dbeb11c4ee7344c33186 (patch) | |
| tree | cfc292f4641218c32b9cbbb3d9a131de0639e09b /drivers/soc/qcom/qdsp6v2/voice_svc.c | |
| parent | 2a7bbea49bd05426d54b3392ac780a93490c6542 (diff) | |
drivers: soc: add size check
Add size check to ensure the payload fits inside the declared payload
size to prevent loss of data when copying.
CRs-Fixed: 2009224
Signed-off-by: Siena Richard <sienar@codeaurora.org>
Change-Id: I4275c626605272941143b54a7b8861b25f8e750a
Diffstat (limited to 'drivers/soc/qcom/qdsp6v2/voice_svc.c')
| -rw-r--r-- | drivers/soc/qcom/qdsp6v2/voice_svc.c | 57 |
1 files changed, 44 insertions, 13 deletions
diff --git a/drivers/soc/qcom/qdsp6v2/voice_svc.c b/drivers/soc/qcom/qdsp6v2/voice_svc.c index 10f71b85a15b..fe5458974406 100644 --- a/drivers/soc/qcom/qdsp6v2/voice_svc.c +++ b/drivers/soc/qcom/qdsp6v2/voice_svc.c @@ -368,6 +368,9 @@ static ssize_t voice_svc_write(struct file *file, const char __user *buf, struct voice_svc_prvt *prtd; struct voice_svc_write_msg *data = NULL; uint32_t cmd; + struct voice_svc_register *register_data = NULL; + struct voice_svc_cmd_request *request_data = NULL; + uint32_t request_payload_size; pr_debug("%s\n", __func__); @@ -416,12 +419,19 @@ static ssize_t voice_svc_write(struct file *file, const char __user *buf, */ if (count == (sizeof(struct voice_svc_write_msg) + sizeof(struct voice_svc_register))) { - ret = process_reg_cmd( - (struct voice_svc_register *)data->payload, prtd); + register_data = + (struct voice_svc_register *)data->payload; + if (register_data == NULL) { + pr_err("%s: register data is NULL", __func__); + ret = -EINVAL; + goto done; + } + ret = process_reg_cmd(register_data, prtd); if (!ret) ret = count; } else { - pr_err("%s: invalid payload size\n", __func__); + pr_err("%s: invalid data payload size for register command\n", + __func__); ret = -EINVAL; goto done; } @@ -430,19 +440,40 @@ static ssize_t voice_svc_write(struct file *file, const char __user *buf, /* * Check that count reflects the expected size to ensure * sufficient memory was allocated. Since voice_svc_cmd_request - * has a variable size, check the minimum value count must be. + * has a variable size, check the minimum value count must be to + * parse the message request then check the minimum size to hold + * the payload of the message request. */ if (count >= (sizeof(struct voice_svc_write_msg) + sizeof(struct voice_svc_cmd_request))) { - ret = voice_svc_send_req( - (struct voice_svc_cmd_request *)data->payload, prtd); - if (!ret) - ret = count; - } else { - pr_err("%s: invalid payload size\n", __func__); - ret = -EINVAL; - goto done; - } + request_data = + (struct voice_svc_cmd_request *)data->payload; + if (request_data == NULL) { + pr_err("%s: request data is NULL", __func__); + ret = -EINVAL; + goto done; + } + + request_payload_size = request_data->payload_size; + + if (count >= (sizeof(struct voice_svc_write_msg) + + sizeof(struct voice_svc_cmd_request) + + request_payload_size)) { + ret = voice_svc_send_req(request_data, prtd); + if (!ret) + ret = count; + } else { + pr_err("%s: invalid request payload size\n", + __func__); + ret = -EINVAL; + goto done; + } + } else { + pr_err("%s: invalid data payload size for request command\n", + __func__); + ret = -EINVAL; + goto done; + } break; default: pr_debug("%s: Invalid command: %u\n", __func__, cmd); |
