-----BEGIN PGP SIGNED MESSAGE----- Hash: SHA1 Advisory: avast! 4.8 and 5.0 aavmker4.sys Kernel Memory Corruption Advisory ID: TKADV2010-003 Revision: 1.0 Release Date: 2010/02/22 Last Modified: 2010/02/22 Date Reported: 2010/02/01 Author: Tobias Klein (tk at trapkit.de) Affected Software: avast! 4.8 <= 4.8.1368.0 avast! 5.0 < 5.0.418.0 Remotely Exploitable: No Locally Exploitable: Yes Vendor URL: http://www.avast.com Vendor Status: Vendor has released an updated version Patch development time: 10 days ====================== Vulnerability Details: ====================== The kernel driver aavmker4.sys shipped with avast! 4.8 and 5.0 contains a vulnerability in the code that handles IOCTL requests. Exploitation of this vulnerability can result in: 1) local denial of service attacks (system crash due to a kernel panic), or 2) local execution of arbitrary code at the kernel level (complete system compromise) The issue can be triggered by sending a specially crafted IOCTL request. No special user rights are required to exploit the vulnerability. ================== Technical Details: ================== The IOCTL call 0xb2d60030 of the aavmker4.sys kernel driver shipped with avast! 4.8 and 5.0 accepts user supplied input that doesn't get validated enough. In consequence it is possible to overwrite arbitrary kernel space and user space memory addresses with arbitrary values. This can be exploited to control the kernel execution flow and to execute arbitrary code at the kernel level. Disassembly of aavmker4.sys (avast! 4.8, file version 4.8.1356.0): [..] .text:00010E46 [1] cmp eax, 0B2D60030h ; vulnerable IOCTL .text:00010E4B jz loc_10EEF [..] .text:00010EEF loc_10EEF: .text:00010EEF cmp byte_1262C, 0 .text:00010EF6 jz short loc_10F0C [..] .text:00010F0C loc_10F0C: .text:00010F0C [2] mov edi, [ebx+0Ch] .text:00010F0F [3] cmp esi, 878h ; InputBufferSize == 0x878? .text:00010F15 jz short loc_10F21 [..] [1] Vulnerable IOCTL [2] EDI now points to user controlled IOCTL input data [3] The size of the IOCTL input data must be equal to 0x878 [..] .text:00010F21 loc_10F21: .text:00010F21 and [ebp+var_4], 0 .text:00010F25 cmp dword ptr [edi], 0 .text:00010F28 jz loc_10FC5 .text:00010F2E [4] mov esi, [edi+870h] .text:00010F34 mov [ebp+v34_uc], esi .text:00010F37 mov eax, ds:MmUserProbeAddress .text:00010F3C [5] cmp esi, [eax] ; user space or kernel space? .text:00010F3E jnb short loc_10F46 [..] [4] If the input size equals 0x878 a pointer value gets extracted from the user supplied IOCTL input data and saved in ESI [5] It is checked if ESI points into user space or kernel space [..] .text:00010F46 loc_10F46: .text:00010F46 push esi ; VirtualAddress .text:00010F47 [6] call ds:MmIsAddressValid .text:00010F4D test al, al .text:00010F4F jz short loc_10F5F .text:00010F51 lea eax, [esi+8] .text:00010F54 push eax ; VirtualAddress .text:00010F55 [7] call ds:MmIsAddressValid .text:00010F5B test al, al .text:00010F5D jnz short loc_10F65 [..] [6] + [7] If ESI points to an address in kernel space it is checked if ESI and ESI+8 are pointing to valid memory addresses [..] .text:00010F65 loc_10F65: .text:00010F65 [8] mov eax, [esi] .text:00010F67 mov [ebp+v32_uc], eax .text:00010F6A [9] mov esi, [esi+4] .text:00010F6D mov [ebp+var_4C], esi .text:00010F70 [10] xor [ebp+v32_uc], 55667788h .text:00010F77 [11] xor esi, 11223344h .text:00010F7D mov [ebp+var_4C], esi .text:00010F80 mov eax, dword_125E8 .text:00010F85 [12] cmp eax, [ebp+v32_uc] ; check pattern1 .text:00010F88 jnz short loc_10F93 .text:00010F8A mov eax, dword_125EC .text:00010F8F [13] cmp eax, esi ; check pattern2 .text:00010F91 jz short loc_10F99 [..] [8] + [9] If the addresses are valid, EAX and ESI are filled with data from the user defined kernel space address (pointed to by ESI) The first value (EAX) is xor'ed with 0x55667788 (see [10]) and then compared with the value 0x85B8DA8F found at dword_125E8 (see [12]). .data:000125E8 dword_125E8 dd 85B8DA8Fh The second value (ESI) is xor'ed with 0x11223344 (see [11]) and then compared with the value 0x198E3FE found at dword_125EC (see [13]). .data:000125EC dword_125EC dd 198E3FEh If both patterns match, the following code gets executed: [..] .text:00010F99 loc_10F99: .text:00010F99 xor edx, edx .text:00010F9B mov eax, [ebp+v34_uc] .text:00010F9E mov [eax], edx .text:00010FA0 mov [eax+4], edx .text:00010FA3 lea esi, [edi+4] ; src .text:00010FA6 mov ecx, 21Ah ; len .text:00010FAB mov edi, [eax+18h] ; dst .text:00010FAE [14] rep movsd ; memcpy [..] The memcpy function at [14] gets called with the following parameters: memcpy (EDI, ESI, ECX); EDI (dst): this value is extracted from a user defined kernel space address ESI (src): points to user controlled IOCTL input data ECX (len): 0x21A Vulnerability: If an attacker were able to (temporarily) store user controlled data at a user defined address in kernel space, the check at [5] could be passed and the memcpy() call would lead to an exploitable memory corruption condition. Unfortunately, the aavmker4.sys driver supports at least one IOCTL that allows an unprivileged user to temporarily store arbitrary data at a known kernel space address. Exploitation: STEP 1: Use one of the IOCTLs supported by aavmker4.sys to temporarily store arbitrary data at a known kernel space address (e.g. the IOCTL 0xb2d6001c). This data has to start with the two patterns that are checked at [12] and [13]. STEP 2: Send a request to the vulnerable IOCTL. Store a pointer at offset 0x870 of the IOCTL data that points to the kernel space address of STEP 1. ========= Solution: ========= Update to avast! 5.0 >= 5.0.418. ==================== Disclosure Timeline: ==================== Format: year/month/day 2010/01/24 - Vendor notified using info@avast.com 2010/01/29 - Vendor response with PGP key 2010/02/01 - Detailed vulnerability information sent to the vendor 2010/02/01 - Vendor confirms the vulnerability 2010/02/09 - Status update by ALWIL Software 2010/02/11 - Vendor releases updated version 2010/02/22 - Release date of this security advisory ======== Credits: ======== Vulnerability found and advisory written by Tobias Klein. =========== References: =========== [REF1] http://forum.avast.com/index.php?topic=55484.0 [REF2] http://www.trapkit.de/advisories/TKADV2010-003.txt ======== Changes: ======== Revision 0.1 - Initial draft release to the vendor Revision 1.0 - Public release =========== Disclaimer: =========== The information within this advisory may change without notice. Use of this information constitutes acceptance for use in an AS IS condition. There are no warranties, implied or express, with regard to this information. In no event shall the author be liable for any direct or indirect damages whatsoever arising out of or in connection with the use or spread of this information. Any use of this information is at the user's own risk. ================== PGP Signature Key: ================== http://www.trapkit.de/advisories/tk-advisories-signature-key.asc Copyright 2010 Tobias Klein. All rights reserved. -----BEGIN PGP SIGNATURE----- Version: PGP Charset: utf-8 wj8DBQFLgn5okXxgcAIbhEERAj8GAJ9pYDOH4TrvUzvyeOALoWLENLM7xwCg0W1g WaQ8IbevEtzmE2njc/RRcWI= =Egms -----END PGP SIGNATURE-----