
| Title | Microsoft Internet Explorer MSHTML Findtext processing issue |
| Analysis | http://www.abysssec.com |
| Vendor | http://www.microsoft.com |
| Impact | Medium |
| Contact | shahin [at] abysssec.com , info [at] abysssec.com |
| @abysssec | |
| CVE | CVE-2010-2553 |
| Internet explorer 6 |
| Internet explorer 7 |
| Internet explorer 8 |
| Class | 1- Processing Issue |
| Impact | Successfully exploiting this issue allows remote attackers to cause denial-of-service conditions. |
| Remotely Exploitable | Yes |
| Locally Exploitable | Yes |
mshtml.dll is one of the module that is used in processing html tags which exist in sysyem32 directory. Vulnerability exists in Findtext function related to TextRange object.
TextRange object show a text in html element. This object has some functions, one of them is FindText. This function searches a string in an exact range in the document and if the intended string is found returns true.
Here is the definition of the function:
The first necessary argument is the string to search. The second optional argument specify range and direction of search which can be a positive (forward search) and negative( backward search ) number. The third optional argument represent type of search.
Here is a simple example of using this function:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 | <input onclick="Search()" type="button" value="Crachme!" /> <input id="Abysssec" type="text" value="Abysssec" /> <script type="text/javascript">// <![CDATA[ function Search() { var textinput = document.getElementById("abysssec"); var textRange = textinput.createTextRange(); textRange.findText(unescape("%u41"),1); textRange.select(document.getElementById('d')); document.body.appendChild(textinput); } // ]]></script> <p id="p">Abysssec</p> |
CAutoRange::findText function in mshtml.dll module is responsible for processing findtext function of TextRange object. In body of this function, FindTextW of CMarkupPointe interface is called. And in CMarkupPointer__FindTextW function, CTxtPtr__FindTextW is also called.
TxtPtr__FindTextW takes four arguments. The first argument is a value that can be variable based on search range argument. For example, if the search range argument is equal to a negative number, the value of this argument is different in case of a positive search range argument.
The second specify search type flag. Third argument is a pointer to the buffer containing our intended string to search. Fourth argument is size of the string.
In part of the function, fourth argument is compared if less or equal to zero or not:
1 2 3 4 5 6 7 8 9 | .text:77721879 mov eax, [ebp+Size] .text:7772187C mov ecx, edi .text:7772187E lea edi, [ecx+eax*2-2] .text:77721882 .text:77721882 loc_77721882: ; CODE XREF: CTxtPtr::FindTextW(long,ulong,ushort const *,long)+D3j .text:77721882 and [ebp+var_C0], ebx ; ebx = 0 .text:77721888 cmp [ebp+Size], ebx .text:7772188B jle loc_77721935 .text:77721891 loc_77721891: ; CODE XREF: CTxtPtr::FindTextW(long,ulong,ushort const *,long)+18Bj |
If size is greater than zero, two other values are compared. The result of logical ‘and’ of second argument with 0×20000 is compared if zero or not and then checking the first two bytes of intended string if less than 0xff.
1 2 3 4 | .text:77721891 test esi, esi .text:77721893 jnz short loc_777218A0 .text:77721895 cmp word ptr [edi], 0FFh .text:7772189A jnb loc_7772195F |
If the above conditions are not happened CTxtPtr__FindComplexHelper function is called:
1 2 3 4 5 6 7 | .text:7772195F ; CTxtPtr::FindTextW(long,ulong,ushort const *,long)+2CCj .text:7772195F push [ebp+Size] ; Size .text:77721962 mov ecx, [ebp+var_C8] .text:77721968 push [ebp+cchCount1] ; cchCount1 .text:7772196E push [ebp+arg_4] ; int .text:77721971 push [ebp+arg_0] ; int .text:77721974 call ?FindComplexHelper@CTxtPtr@@QAEJJKPBGJ@Z ; CTxtPtr::FindComplexHelper(long,ulong,ushort const *,long) |
CTxtPtr__FindComplexHelper function takes the same arguments of CTxtPtr__FindComplexHelper. In part of the CTxtPtr__FindComplexHelper function, CMarkup::TreePosAtCp function is called.
1 2 3 4 5 6 7 8 9 | .text:777211CA mov eax, [ebx] .text:777211CC mov eax, [eax+10h] .text:777211CF mov ecx, [ebx+10h] .text:777211D2 mov [ebp+var_C], eax .text:777211D5 push 0 .text:777211D7 lea eax, [ebp+var_40] .text:777211DA push eax .text:777211DB push dword ptr [ebx+0Ch] .text:777211DE call ?TreePosAtCp@CMarkup@@QBEPAVCTreePos@@JPAJH@Z ; CMarkup::TreePosAtCp(long,long *,int) |
Output of this function is a structure which based on type of search and negative or positive search have different values. Some of the fields of this function contain some addresses which are used in next functions.
Here is the flaw because in case of calling findtext of TextRange object with special arguments, the output structure of CMarkup::TreePosAtCp function hav invalid (0×00000000) address.
If first argument of findtext argument contains a character of Unicode which is greater than or equal to 0xff and second argument is a negative number, then the returned structure of CMarkup::TreePosAtCp function have invalid(0×00000000) address.
In such case, CTreePos::NextTreePos function is called which extract this 0×0000000 address from the structure and return it. And this returned value is used by CTreePos__GetC function.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 | .text:7772132A cmp esi, eax .text:7772132C jz loc_77721213 .text:77721332 mov ecx, esi .text:77721334 call ?PreviousTreePos@CTreePos@@QAEPAV1@XZ ; CTreePos::PreviousTreePos(void) .text:77721339 mov edi, eax .text:7772133B test edi, edi .text:7772133D jz short loc_77721356 .text:7772133F test byte ptr [esi], 3 .text:77721342 jz short loc_77721350 .text:77721344 push 0 .text:77721346 push esi .text:77721347 call ?ClassifyNodePos@@YG?AW4NODE_CLASS@@PAVCTreePos@@PAH@Z ; ClassifyNodePos(CTreePos *,int *) .text:7772134C test eax, eax .text:7772134E jnz short loc_77721356 .text:77721350 .text:77721350 mov esi, edi .text:77721352 xor eax, eax .text:77721354 jmp short loc_7772132A .text:77721356 ; --------------------------------------------------------------------------- .text:77721356 .text:77721356 mov ecx, esi .text:77721358 call ?NextTreePos@CTreePos@@QAEPAV1@XZ ; CTreePos::NextTreePos(void) .text:7772135D mov ecx, eax .text:7772135F call ?GetCp@CTreePos@@QAEJXZ ; CTreePos::GetCp(void) |
In CTreePos__GetC function some values from the returned address of CTreePos::NextTreePos is called and because it is zero it cause an access violation excepton.
1 2 3 4 5 6 7 8 9 | .text:77538081 mov edi, edi .text:77538083 push ebp .text:77538084 mov ebp, esp .text:77538086 push ecx .text:77538087 push esi .text:77538088 push edi .text:77538089 mov edi, ecx .text:7753808B mov edx, [edi] .text:7753808D mov esi, [edi+4] |
Please note that: this issue was founded in wild before us but still not patched.
Check out the Microsoft Internet Explorer MSHTML Findtext Processing Issue PoC.



