WinFlash AwdFlash分析
在windows下,刷新BIOS需要讀寫物理內存或IO端口。
在NT平臺下,讀寫物理內存或IO端口需要驅動來支持(也可以使用/dev/PhysicalMemory來完成,但是2003sp1...)
winflash使用驅動來實現物理內存/IO端口的讀寫,這一點很明顯。
winflash/awdflash都是使用SMI Flash來進行BIOS刷新的。對winflash/awdflash反匯編,
都可以發現
mov???? dx, ds:SMI_PORT
mov???? al, 28h
out???? dx, al????????? ; manufacture's diagnostic checkpoint
之類的字樣.
(開始還以為這是調試用的端口.../感謝網友 的文章。)
廢話就不說了,先看一下WinFlash的FlowChart吧:
直接將winflash拖到IDA中也可以,如果你能看得下去...
winflash是經過加殼的,用PE Scan檢測一下,aspack 2.12
可直接脫殼,沒有什么特殊的障礙...
在NT下,Winflash需要動態加載驅動,直接在代碼中查找CreateService(),
然后在逐級找到calller,hehe,最后來到如下位置
snyped:004029A0 084???????????????? mov???? ecx, esi
snyped:004029A2 084???????????????? call??? check_OS_Version
snyped:004029A2
snyped:004029A7 084???????????????? mov???? ecx, esi
snyped:004029A9 084???????????????? call??? Start_SYS_Driver
snyped:004029A9
snyped:004029AE 084???????????????? test??? al, al
snyped:004029B0 084???????????????? jnz???? short Check_Award_BIOS
snyped:004029B0
snyped:004029B2 084???????????????? lea???? ecx, [ebp+var_74]
snyped:004029B5 084???????????????? mov???? [ebp+var_4], 0FFFFFFFFh
snyped:004029BC 084???????????????? call??? CCommandLineInfo::~CCommandLineInfo(void)
有關MFC的東西不用管了,接著看下面
主要是調用驅動的功能來讀取物理內存的F000:0000段的內容,
即SystemBIOS模塊的內容(初始化后),從中獲取BIOS/FlashROM的相關信息。
snyped:004029D4???? Check_Award_BIOS:?????????????????????? ; CODE XREF: CMainFrame_InitInstance+120j
snyped:004029D4 084???????????????? mov???? ecx, offset flash_info_struct
snyped:004029D9 084???????????????? call??? PhysicalMemoryRead????? ;這里使用DeviceIoCtrl的222000h功能
??????????????????????????????????????????????????????????????????? ;讀取0xF0000-0xFFFFF的內存到用戶態緩沖區
snyped:004029D9
snyped:004029DE 084???????????????? mov???? ecx, offset flash_info_struct
snyped:004029E3 084???????????????? call??? Get_Award_Modular_Sig?? ;此函數從讀取的0xF000段數據中獲取BIOS信息
??????????????????????????????????????????????????????????????????? ;
snyped:004029E3
snyped:004029E8 084???????????????? test??? al, al
snyped:004029EA 084???????????????? jnz???? short BIOS_is_Award
snyped:004029EA
snyped:004029EC 084???????????????? push??? offset s_XBiosAwardGb ; " 本機主板 BIOS 不是 Award 的!"
snyped:004029F1 088???????????????? push??? 1?????????????? ; int
snyped:004029F3 08C???????????????? push??? 0?????????????? ; int
snyped:004029F5 090???????????????? mov???? ecx, esi
snyped:004029F7 090???????????????? call??? ErrorDialog__1
snyped:004029F7
snyped:004029FC 084???????????????? lea???? ecx, [ebp+var_74]
snyped:004029FF 084???????????????? mov???? [ebp+var_4], 0FFFFFFFFh
snyped:00402A06 084???????????????? call??? CCommandLineInfo::~CCommandLineInfo(void)
在上面的代碼中,最重要的函數就是0x004029E3 位置調用的函數
snyped:004011D0???? Get_Award_Modular_Sig proc near???????? ; CODE XREF: CMainFrame_InitInstance+153p
snyped:004011D0???????????????????????????????????????????? ; sub_4033A0+8p
snyped:004011D0 000???????????????? push??? esi
snyped:004011D1 004???????????????? mov???? esi, ecx
snyped:004011D3 004???????????????? mov???? ds:byte_44FB08, 0
snyped:004011DA 004???????????????? mov???? eax, [esi+4]
snyped:004011DD 004???????????????? push??? eax
snyped:004011DE 008???????????????? call??? check_Award_Modular_BIOS_Sig??? ;當找到"Award Modular BIOS"字符串時,此函數返回1
snyped:004011DE
snyped:004011E3 004???????????????? test??? al, al
snyped:004011E5 004???????????????? jnz???? short loc_4011E9??? ;AwdBIOS,在這里跳轉
snyped:004011E5
snyped:004011E7 004???????????????? pop???? esi
snyped:004011E8 000???????????????? retn
snyped:004011E8
snyped:004011E9???? ; ---------------------------------------------------------------------------
snyped:004011E9
snyped:004011E9???? loc_4011E9:???????????????????????????? ; CODE XREF: Get_Award_Modular_Sig+15j
snyped:004011E9 004???????????????? mov???? ecx, esi
snyped:004011EB 004???????????????? call??? GetSMI_Port???? ;在Offset_"$@AWDFLASH"+0x2A位置獲取SMI_PORT
snyped:004011EB
snyped:004011F0 004???????????????? mov???? ecx, esi等
snyped:004011F2 004???????????????? call??? GetFlashInfo??? ;由"KAFLASH" 獲取BIOS FlashROM信息,包括FlashROM 大小,Base Addr
snyped:004011F2
snyped:004011F7 004???????????????? mov???? ecx, esi
snyped:004011F9 004???????????????? call??? GetDecompressInfo?? ;暫時這樣認為,獲取DecompressBlock的起始位置...(????)
snyped:004011F9
snyped:004011FE 004???????????????? mov???? al, 1
snyped:00401200 004???????????????? pop???? esi
snyped:00401201 000???????????????? retn
snyped:00401201
snyped:00401201???? Get_Award_Modular_Sig endp
獲取了BIOS和FlashROM的相關信息后,
下面是設置驅動的全局變量,SMI_PORT
其中IoCtlCode:
222004h-->設置驅動的全局變量,(in/out Buffer見下面)
222008h-->調用SMI_0x2E功能
snyped:00402A1E???? BIOS_is_Award:????????????????????????? ; CODE XREF: CMainFrame_InitInstance+15Aj
snyped:00402A1E 084???????????????? cmp???? ds:Window_Version, 2000h
snyped:00402A28 084???????????????? jnz???? short SMI_0x2E_Func_0
snyped:00402A28
snyped:00402A2A 084???????????????? mov???? ax, ds:SMI_PORT
snyped:00402A30 084???????????????? lea???? ecx, [ebp+BytesReturned]
snyped:00402A33 084???????????????? mov???? edi, ds:DeviceIoControl
snyped:00402A39 084???????????????? push??? 0?????????????? ; lpOverlapped
snyped:00402A3B 088???????????????? push??? ecx???????????? ; lpBytesReturned
snyped:00402A3C 08C???????????????? push??? 0?????????????? ; nOutBufferSize
snyped:00402A3E 090???????????????? push??? 0?????????????? ; lpOutBuffer
snyped:00402A40 094???????????????? lea???? edx, [ebp+SMI_Port]
snyped:00402A43 094???????????????? mov???? word ptr [ebp+SMI_Port], ax
snyped:00402A47 094???????????????? mov???? eax, ds:hDevice
snyped:00402A4C 094???????????????? push??? 2?????????????? ; nInBufferSize
snyped:00402A4E 098???????????????? push??? edx???????????? ; lpInBuffer
snyped:00402A4F 09C???????????????? push??? 222004h ; <suspicious> ; dwIoControlCode
snyped:00402A54 0A0???????????????? push??? eax???????????? ; hDevice
snyped:00402A55 0A4???????????????? call??? edi ; DeviceIoControl ; Set SMI Port!!!
snyped:00402A57 084???????????????? lea???? ecx, [ebp+BytesReturned]
snyped:00402A5A 084???????????????? push??? 0?????????????? ; lpOverlapped
snyped:00402A5C 088???????????????? push??? ecx???????????? ; lpBytesReturned
snyped:00402A5D 08C???????????????? mov???? ecx, ds:hDevice
snyped:00402A63 08C???????????????? lea???? edx, [ebp+OutBuffer]
snyped:00402A66 08C???????????????? push??? 10h???????????? ; nOutBufferSize
snyped:00402A68 090???????????????? push??? edx???????????? ; lpOutBuffer
snyped:00402A69 094???????????????? lea???? eax, [ebp+OutBuffer]
snyped:00402A6C 094???????????????? push??? 2?????????????? ; nInBufferSize
snyped:00402A6E 098???????????????? push??? eax???????????? ; lpInBuffer
snyped:00402A6F 09C???????????????? push??? 222008h ; <suspicious> ; dwIoControlCode
snyped:00402A74 0A0???????????????? push??? ecx???????????? ; hDevice
snyped:00402A75 0A4???????????????? mov???? [ebp+OutBuffer], 0
snyped:00402A7C 0A4???????????????? call??? edi ; DeviceIoControl ; SMI_0x2E Func 00h
snyped:00402A7C???????????????????????????????????????????? ; GetBiosInfo
snyped:00402A7E 084???????????????? cmp???? ds:Window_Version, 2000h
snyped:00402A88 084???????????????? jz????? short loc_402AA5 ; jmp here!!!
///MFC Init here...
基本上,WinFlash的基本init_FlowChart就出來了
下面轉到到正題:
至于WinFlash怎樣Program FlashROM,只需調試一下winflash.exe即可
說的太麻煩
大家有各自的調試手段
我使用的是IDA5來進行Ring3調試的(hehe),直接用ida5啟動(unpacked)winflash.exe,然后
在刷新BIOS時將進程中斷,即可由中斷的代碼位置來判斷caller(call tree/path?)
基本上,刷新的代碼部分如下,注視自己隨便填寫了,看得懂即可
//
//winflash代碼里針對win98和NT做了不同的處理,這里只關心NT
//
snyped:0040209F???? os_is_win2000:????????????????????????? ; CODE XREF: SST_SectorProg+19j
snyped:0040209F 018???????????????? mov???? eax, [esp+18h+BytesReturned]
snyped:004020A3 018???????????????? lea???? ecx, [esp+18h+BytesReturned]
snyped:004020A7 018???????????????? mov???? ebx, ds:DeviceIoControl
snyped:004020AD 018???????????????? push??? 0?????????????? ; lpOverlapped
snyped:004020AF 01C???????????????? push??? ecx???????????? ; lpBytesReturned
snyped:004020B0 020???????????????? push??? 0?????????????? ; nOutBufferSize
snyped:004020B2 024???????????????? push??? 0?????????????? ; lpOutBuffer
snyped:004020B4 028???????????????? lea???? edx, [esp+28h+LocalBuffer] ; input buffer dd FFFC0000h
snyped:004020B4???????????????????????????????????????????? ;
snyped:004020B8 028???????????????? mov???? [esp+28h+LocalBuffer], eax
snyped:004020BC 028???????????????? mov???? eax, ds:hDevice
snyped:004020C1 028???????????????? push??? 4?????????????? ; nInBufferSize
snyped:004020C3 02C???????????????? push??? edx???????????? ; lpInBuffer
snyped:004020C4 030???????????????? push??? 222010h ; <suspicious> ; dwIoControlCode
snyped:004020C9 034???????????????? push??? eax???????????? ; hDevice
snyped:004020CA 038???????????????? call??? ebx ; DeviceIoControl ; SetGlobal_Var
snyped:004020CC 018???????????????? mov???? edi, [esp+18h+Size_0x1000] ; edi==0x1000
snyped:004020D0 018???????????????? test??? edi, edi??????? ; EDI=FFFC0000h //很多注釋都是調試的時候加上去的,應該很明顯的....
snyped:004020D2 018???????????????? jbe???? short loc_4020FE
snyped:004020D2
snyped:004020D4 018???????????????? add???? edi, 0Fh??????? ; edi=0x100F
snyped:004020D7 018???????????????? shr???? edi, 4????????? ; edi=0x100
snyped:004020D7
snyped:004020DA
snyped:004020DA???? loop_Byte_program:????????????????????? ; CODE XREF: SST_SectorProg+ACj
snyped:004020DA 018???????????????? mov???? eax, ds:hDevice
snyped:004020DF 018???????????????? lea???? ecx, [esp+18h+BytesReturned]
snyped:004020E3 018???????????????? push??? 0?????????????? ; lpOverlapped
snyped:004020E5 01C???????????????? push??? ecx???????????? ; lpBytesReturned
snyped:004020E6 020???????????????? lea???? edx, [esp+20h+OutBuffer]
snyped:004020EA 020???????????????? push??? 4?????????????? ; nOutBufferSize
snyped:004020EC 024???????????????? push??? edx???????????? ; lpOutBuffer
snyped:004020ED 028???????????????? push??? 10h???????????? ; nInBufferSize
snyped:004020EF 02C???????????????? push??? esi???????????? ; lpInBuffer
snyped:004020F0 030???????????????? push??? 22201Ch ; <suspicious> ; dwIoControlCode
snyped:004020F5 034???????????????? push??? eax???????????? ; hDevice
snyped:004020F6 038???????????????? call??? ebx ; DeviceIoControl ; 處理16個字節,flash 16Bytes
snyped:004020F8 018???????????????? add???? esi, 10h??????? ; 移動到下16個字節
snyped:004020FB 018???????????????? dec???? edi???????????? ; 總數減去16字節
snyped:004020FC 018???????????????? jnz???? short loop_Byte_program ; 循環處理
snyped:004020FC
snyped:004020FE
snyped:004020FE???? loc_4020FE:???????????????????????????? ; CODE XREF: SST_SectorProg+23j
snyped:004020FE???????????????????????????????????????????? ; SST_SectorProg+82j
snyped:004020FE 018???????????????? pop???? edi
snyped:004020FF 014???????????????? pop???? esi
snyped:00402100 010???????????????? pop???? ebp
snyped:00402101 00C???????????????? mov???? al, 1
snyped:00402103 00C???????????????? pop???? ebx
snyped:00402104 008???????????????? add???? esp, 8
snyped:00402107 000???????????????? retn??? 0Ch
snyped:00402107
snyped:00402107???? SST_SectorProg? endp
//SST是自己之前隨便寫的,還以為針對每種Flash有不同的flash方法函數...
在Flash之前,先使用SMI_0x29按4KB擦除ROM...
麻煩
看到這里你可能還是很糊涂,到底怎樣Flash?
winflash.exe是請求winflash.sys來完成Flash的,直接靜態反匯編winflash.sys即可(文件很簡單,是個普通的driver/文件很小...)
至于各個寄存器的設置,反匯編的代碼里看得很清楚了。
如果有疑問,可以使用softice調試一下:
做法是在winflash刷新的時候,ctrl+d,然后
addr winflash
mod winflash.sys找到winflash的加載基址
然后根據IDA反匯編的代碼偏移計算出需要中斷的代碼位置,然后bpx即可.
(也可以直接單步跟蹤,如果你很有耐心的話...)
這樣,winfash的FlowChart基本上出來了
你也可以自己寫一個Flash BIOS的程序(前提是awd/SMI Flash...)
不想說廢話了
這里加一個自己部分注釋的winflash.* 的IDB(適用于IDA5)地址.
link:?? winflash_unpack.idb???? http://xxx
link:?? winflash_sys.idb??????? http://xxx?//后面提供一個集中下載的位置...
總結
以上是生活随笔為你收集整理的WinFlash AwdFlash分析的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 多媒体计算机涉及的关键技术有什么,多媒体
- 下一篇: Linux 字符设备驱动及一些简单的Li