wl12xx: Check buffer bound when processing nvs data
authorPontus Fuchs <pontus.fuchs@gmail.com>
Tue, 18 Oct 2011 07:23:42 +0000 (09:23 +0200)
committerLuciano Coelho <coelho@ti.com>
Thu, 1 Dec 2011 13:55:42 +0000 (15:55 +0200)
An nvs with malformed contents could cause the processing of the
calibration data to read beyond the end of the buffer. Prevent this
from happening by adding bound checking.

Signed-off-by: Pontus Fuchs <pontus.fuchs@gmail.com>
Cc: stable@kernel.org
Reviewed-by: Luciano Coelho <coelho@ti.com>
Signed-off-by: Luciano Coelho <coelho@ti.com>
drivers/net/wireless/wl12xx/boot.c

index 6e140bf..8f9cf5a 100644 (file)
@@ -348,6 +348,9 @@ static int wl1271_boot_upload_nvs(struct wl1271 *wl)
                nvs_ptr += 3;
 
                for (i = 0; i < burst_len; i++) {
+                       if (nvs_ptr + 3 >= (u8 *) wl->nvs + nvs_len)
+                               goto out_badnvs;
+
                        val = (nvs_ptr[0] | (nvs_ptr[1] << 8)
                               | (nvs_ptr[2] << 16) | (nvs_ptr[3] << 24));
 
@@ -359,6 +362,9 @@ static int wl1271_boot_upload_nvs(struct wl1271 *wl)
                        nvs_ptr += 4;
                        dest_addr += 4;
                }
+
+               if (nvs_ptr >= (u8 *) wl->nvs + nvs_len)
+                       goto out_badnvs;
        }
 
        /*
@@ -370,6 +376,10 @@ static int wl1271_boot_upload_nvs(struct wl1271 *wl)
         */
        nvs_ptr = (u8 *)wl->nvs +
                        ALIGN(nvs_ptr - (u8 *)wl->nvs + 7, 4);
+
+       if (nvs_ptr >= (u8 *) wl->nvs + nvs_len)
+               goto out_badnvs;
+
        nvs_len -= nvs_ptr - (u8 *)wl->nvs;
 
        /* Now we must set the partition correctly */
@@ -385,6 +395,10 @@ static int wl1271_boot_upload_nvs(struct wl1271 *wl)
 
        kfree(nvs_aligned);
        return 0;
+
+out_badnvs:
+       wl1271_error("nvs data is malformed");
+       return -EILSEQ;
 }
 
 static void wl1271_boot_enable_interrupts(struct wl1271 *wl)