From cbf79a67348e48557c0d0bb9bc58391b3f84bc46 Mon Sep 17 00:00:00 2001 From: Katish Paran Date: Tue, 24 Dec 2013 14:11:41 +0530 Subject: diag: dci: Safeguard to prevent integer overflow At certain point in diag driver there can be integer overflow thus can lead to memory leak. Added a safegaurd for it. Change-Id: I9347405d8f1f95ed42fe0abf35cbf4c362281bdf CRs-fixed: 565160 Signed-off-by: Katish Paran --- drivers/char/diag/diag_dci.c | 12 +++++++++--- 1 file changed, 9 insertions(+), 3 deletions(-) diff --git a/drivers/char/diag/diag_dci.c b/drivers/char/diag/diag_dci.c index 2dbb2f5..7772ebe 100644 --- a/drivers/char/diag/diag_dci.c +++ b/drivers/char/diag/diag_dci.c @@ -383,17 +383,23 @@ void extract_dci_events(unsigned char *buf) void extract_dci_log(unsigned char *buf) { - uint16_t log_code, item_num; + uint16_t log_code, item_num, log_length; uint8_t equip_id, *log_mask_ptr, byte_mask; unsigned int i, byte_index, byte_offset = 0; struct diag_dci_client_tbl *entry; + log_length = *(uint16_t *)(buf + 2); log_code = *(uint16_t *)(buf + 6); equip_id = LOG_GET_EQUIP_ID(log_code); item_num = LOG_GET_ITEM_NUM(log_code); byte_index = item_num/8 + 2; byte_mask = 0x01 << (item_num % 8); + if (log_length > USHRT_MAX - 4) { + pr_err("diag: Integer overflow in %s, log_len:%d", + __func__, log_length); + return; + } byte_offset = (equip_id * 514) + byte_index; if (byte_offset >= DCI_LOG_MASK_SIZE) { pr_err("diag: Invalid byte_offset %d in dci log\n", @@ -430,8 +436,8 @@ void extract_dci_log(unsigned char *buf) *(int *)(entry->dci_data+entry->data_len) = DCI_LOG_TYPE; memcpy(entry->dci_data + entry->data_len + 4, - buf + 4, *(uint16_t *)(buf + 2)); - entry->data_len += 4 + *(uint16_t *)(buf + 2); + buf + 4, log_length); + entry->data_len += 4 + log_length; } mutex_unlock(&entry->data_mutex); mutex_unlock(&dci_health_mutex); -- cgit v1.1