win32彙編 屏幕截圖保存BMP 學習筆記之odbg調試

我們來回顧下raiky code
根據帖子裏的討論錯誤的疑點在於
1. 對每個像素所佔字節的估算可能有誤
wBitCount;位圖中每個像素所佔字節數 簡單的賦值4
2. 涉及到後面的調色板的處理 我本人不喜歡調色板
3. 位圖內存分配大小的錯誤
接下來對每一行試着運行一番看看效果吧
你問我有沒有玩過debug?
買過書沒看算麼? 書到用時方恨少
哦 想起來了以前玩VBA 調試過代碼 這和exe程序完全不能比啊
趕鴨子上架 用obdg v110.. 110 ..110…

開始之前我們先準備下全局變量的改造
因爲帖子裏的變量本來都是局部在給函數內部使用
被我把代碼拉到了start內
因爲我調試的時候不希望step into(F7)
我目前只會用F8(Step over) 這樣能有效避免被跳暈
請看下面 變量聲明被我改成這樣了

    .data
hBmp dd 0

;
.data? ;這些本來是local型的局部變量 我將它們挪到了全局變量裏來 連struct BITMAPINFO也放來了 
hDc dd ?
MemDc dd ?
Data dd ?  ;普通變量?
bi BITMAPINFO <> ;結構體採用<>

BITMAPINFO 是個window.ini定義的結構體
別看簡單的改動 我走了不少彎路
raiky簡單的 一行LOCAL @bi:BITMAPINFO 就在函數內聲明瞭
我當時想換到全局變量的時候網上搜了半天
沒有紮實的基礎每一步都好艱辛 以後得抽時間多看書

Debug環境的準備
對電腦整個屏幕的截圖 最好是用個簡單的solid color來分析
於是我隱藏了taskbar,隱藏了桌面圖標
設置了電腦桌面爲solid color
桌面背景圖
查看下這張圖的B-G-R值對應16進製爲 B1-63-00
對 你沒有看錯,順序就是B-G-R後面會證實這點
Specifically in the order (blue, green and red, 8-bits per each sample). 聽說這是微軟說的

OllyDbg
先來一張入門的界面介紹
這裏寫圖片描述
MASM32編譯程序
然後 用OllyDbg打開生成的exe
剛打開exe是這樣的 請注意下圖黃色標註的地址
這裏寫圖片描述
上面是77開頭下面是0040開頭 不在一個地址段
先按F8 幾次 讓他走幾步….

等到程序運行到0040開頭的地址後開始往下翻
這裏寫圖片描述
找到CreateDIBSection函數處
CreateDIBSection
還記得我們前面說過CreateDIBSection的參數Data嗎
00403078就是Data, 也可以理解爲電腦不知道Data這個名字,就是分配了這個地址00403078用來存變量 這個變量就是我們程序裏的Data
你問我 我是怎麼找到他的?
你看他前後的參數
一個叫DIB_RGB_COLORS
一個是NULL 那麼夾在中間的肯定是Data

invoke CreateDIBSection,MemDc,addr bi,DIB_RGB_COLORS,addr Data,NULL,0 

還記得Data是幹嘛的嗎 ?
Data就是存BMP信息的地址
這個Data是CreateDIBSection函數的參數ppBits=pointer to pointer variable
也就是說地址00403078存放着的另外一塊內存的地址
現在內存地址00403078的內容還是空的0
繼續F8
一旦函數CreateDIBSection執行完畢00403078的值就有了 如下圖
00403078
02 15 00 00 (x86小數在前 所以要顛倒下

打開view-memory
找到02-15-00-00 size是00-5e-f0-00
雙擊進去查看,目前還沒有bitblt 從頭至尾全是0
這裏寫圖片描述
繼續F8
執行完bitblt 馬上Data所指向的這塊memory就有內容了–我的天吶 我剛纔抓屏的時候dbg界面最大化了 很多藍色抓不到
我現在再run一次 這次getDC之前我將debug軟件窗口縮小 儘量讓四周都是藍色桌面壁紙(這次我將前面的DbgDump註釋掉了 可以少按很多F8)

這次地址變了 (因爲我註釋掉了一些函數?好像每次Data指向的RAM地址也都不固定)
bitblt之前data的內容依然是0
這裏寫圖片描述

bitblt運行之後data的內容馬上出來了
這裏寫圖片描述
看到了嗎 B1 63 00-B1 63 00-……
多麼熟悉的數字
每個像素3個字節!!!

我自己用截圖PrtSc快捷鍵截屏 粘貼到小畫家保存壁紙爲24bit BMP
用OllyDbg view file 打開這個文件
這裏寫圖片描述
這個文件裏除了開頭一些字節 其餘全是B1-63-00 這應該是沒有調色板的 我就喜歡這種單純的文件 懶得研究調色板了

我們的彙編裏該怎麼實現呢
好吧搜到了
bmiHeader初始化的時候bmiHeader.biCompression賦值爲BI_RGB 這樣就不會有調色板了
具體如下

     mov bi.bmiHeader.biPlanes,1
     mov bi.bmiHeader.biBitCount,24 ;ok
     mov bi.bmiHeader.biCompression,BI_RGB ;當biCompression成員的值是BI_RGB(0)時,它沒有調色板

前面已經用RtlZeroMemory將整個bi填充過一次0了
而BI_RGB本身就是0 所以這個biCompression可以忽略 不賦值0也一樣的效果

這樣bitblt出來的全是B1-63-00了 當然後面沒有用完的地址默認還是00
<未完待續, 第四篇將會介紹文件的生成>

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章