線上訂房服務-台灣趴趴狗聯合訂房中心
發文 回覆 瀏覽次數:4338
推到 Plurk!
推到 Facebook!

每次由gamemaster or ce 抓的「資料記憶體位址為何都不同」的問題

缺席
smartboss
初階會員


發表:19
回覆:93
積分:42
註冊:2004-12-29

發送簡訊給我
#1 引用回覆 回覆 發表時間:2009-02-20 09:46:11 IP:115.82.xxx.xxx 訂閱
本文是延伸至該篇文章而來
http://delphi.ktop.com.tw/board.php?cid=168&fid=914&tid=96753

我透過這個軟體CHEAT Engine(CE) 協助抓取記憶體中的資料與資料位址
http://www.cheatengine.org/
我following 以下這個範例,並剪下部份程式碼,將我覺得奇怪的部份拿出來請教前輩,
這讓我想到之前看到的踩地雷外掛的文章
http://delphi.ktop.com.tw/board.php?cid=31&fid=79&tid=90336

我將這個 sample 裡 hook 部份的code 截取了 hack 那部份的function 出來應用,去取得我想 trace 的那個grid cell 的資料位址,再如以下這段程式碼,置入資料位址並將記憶體資料讀出。

[code cpp]
GetWindowThreadProcessId(hWnd,&ProcessId);
hProcess=OpenProcess(PROCESS_ALL_ACCESS,FALSE,ProcessId);
dwBaseAddress = 0x01005330;
ReadProcessMemory(hProcess,(void*)dwBaseAddress ,&dwBombCount,sizeof(DWORD),NULL);

[/code]
但是問出來了,我發現當我關掉再重新啟動我的來源資料程式時,我發現上次ce 所抓到的 dwBaseAddress 值己經失效,也就是說,上一次來源程式關畢前的 dwBaseAddress 位址,與我這次重新開啟來源程式之後的 dwBaseAddress 位址是不一樣的,為了證明這事,我重新再使用 ce 再將我要的grid cell 資料再抓取一次,也確實證明他的資料位址與前次開啟時是不同的,請問像這樣的問題是怎產生的,而又有辦法克服嗎?
而我大略知道每當一個 program 從新啟動時記憶體都會重新配置,而造成該種結果,但是我能透過 offset 的計算或其他方法算出每次重啟後該資料位址正確的記憶體位址值嗎?
編輯記錄
smartboss 重新編輯於 2009-02-20 13:16:56, 註解 無‧
ikk
尊榮會員


發表:4
回覆:413
積分:768
註冊:2003-06-30

發送簡訊給我
#2 引用回覆 回覆 發表時間:2009-02-20 11:39:25 IP:163.28.xxx.xxx 訂閱
那你應該是要知道, dwBaseAddress = 0x01005330;
那個數值是怎麼產生的吧...
再動態取得新的位址.
------
FPGA驗證, FPGA開發平台, http://smims.com
smartboss
初階會員


發表:19
回覆:93
積分:42
註冊:2004-12-29

發送簡訊給我
#3 引用回覆 回覆 發表時間:2009-02-20 13:09:36 IP:115.82.xxx.xxx 訂閱
就範例中的code他的標地程式是以windowns裡附的踩地雷game為標地,而dwBaseAddress = 0x01005330; 這個位址是這個game 中陣列起始的位址,而我認為其怪的是,像這個game 他的陣列起始位址這個0x01005330;的值卻始終都不會變,即始我重啟了踩地雷數十次後,這個位址都是固定的,而我想問怎麼才能取得新的位址而他的義意為何呢?再則目前我的標地程式(不是踩地雷喔)是由ce or gamemaster 去抓記憶體資料位址,而每次標地程式重啟後之前抓到的資料記憶體位址就都不一樣了,那我該如何去取得新的位址呢?


===================引 用 ikk 文 章===================
那你應該是要知道, dwBaseAddress = 0x01005330;
那個數值是怎麼產生的吧...
再動態取得新的位址.
ikk
尊榮會員


發表:4
回覆:413
積分:768
註冊:2003-06-30

發送簡訊給我
#4 引用回覆 回覆 發表時間:2009-02-20 13:34:07 IP:163.28.xxx.xxx 訂閱
那個位址可能是透過人工去檢查出來的吧.
------
FPGA驗證, FPGA開發平台, http://smims.com
hotswin
中階會員


發表:72
回覆:92
積分:52
註冊:2003-11-06

發送簡訊給我
#5 引用回覆 回覆 發表時間:2009-02-20 17:10:50 IP:220.134.xxx.xxx 訂閱
  基本上在記憶体眾多資料中,必定有2種資料:值 與址
當你查到某一固定的位址,你要去反相查那些位址使用了這個固定址。
別的位址可能是把這固 定位址當作是一個值或址來計算。
所以你要計算它的位移差,也就是每一次程式啟動時,別的位址也跟著變,而位移差是固定的。

這個要多練習,才能快速直覺得的找到你要的數據,加油嘍。



===================引 用 ikk 文 章===================
那個位址可能是透過人工去檢查出來的吧.
------
http://xinjier.0424617287.com/gift/
禮贈品
ChungLin.Net
中階會員


發表:2
回覆:33
積分:52
註冊:2006-07-26

發送簡訊給我
#6 引用回覆 回覆 發表時間:2009-02-21 01:21:58 IP:123.204.xxx.xxx 訂閱
這個問題很可能是因為您所抓取的資料是動態記憶體所產生而造成每次存取的記憶體位址會有所不同~

踩地雷程式他的記憶體位址是在編譯時已經建立固定的空間用來存取資料,所以位址上大多不會有所不
同,但也難說不會有意外情況,我曾在自己電腦上寫過一支讀取某支程式資訊的資料,在我電腦上位址
一直固定不變,除非主程式有所更新才會變動,但丟到他人的電腦執行時,所設的固定位址卻無法正常
讀取資料,關於這個問題後來我也無解,最後只有採取搜尋的方式來處理~

如果在程式中使用固定大小的資料,通常位址就會較固定。相對編譯出來的程式大小就會較大,因為程
式在編譯時就會預留資料空間~如:

char a[512]="11111111112222222222222233333333333333.....";

在編譯出來的程式中 就能找到 a[512] 所存放的資料空間,所以存放的資料就會較固定在某個位址。

如果在程式中使用動態大小的資斗,通常位址就會有所變動了,所編譯出來的程式大小也會較小,因為
程式會需要使用空間時,從記憶體中建立資料空間出來,如:

char *a;
a=(char*)malloc(512 1);
memset(a,'\0',513);

在編譯出來的程式中,不會有513bytes 的預留空間,所以每次抓取位址時,就會有所變動。

通常未使用動態記憶體的程式,他的程式內容記憶體是不太會有所變動,這個應該有牽扯到計算機概論
原理,關於這部份我也沒很了解。就我知的概念來說,比如我宣告三個變數

int a=1;
int b=2;
int c=3;

在程式執行後,扣除其他本身程式的處理,只看這部份的話~ 那麼他的程式碼記憶體位址啟始段就是(假
設性,實際資料未必如此)

--------------- 00 01 02 03 04 05 06 07 08 09 0A 0B 0C 0D 0E
0000:0000 01 00 00 00 02 00 00 00 03 00 00 00 ........

不論程式本身的記憶體啟始位址為何
0000:0000 所抓到的 4bytes 就是 a 變數的值 ,
0000:0004 所抓到的 4bytes 就是 b 變數的值 ,
0000:0008 所抓到的 4bytes 就是 c 變數的值。
當然以上只是定義固定的資料,而未有程式上的處理才會有這種情況

如果換成是動態記憶體的話

int *a;
int *b;
int *c;

.... 動態記憶體建立 .....

a=1;
b=2;
c=3;

在程式執行後,記憶體位址啟始段就是(假設性,實際資料未必如此)

--------------- 00 01 02 03 04 05 06 07 08 09 0A 0B 0C 0D 0E
0000:0000 01 E0 F0 00 02 0F F0 E0 05 0E 0F 10 ........

0000:0000 - 0000:0003 所存的就是 a 的資料記憶體位址,而不是 a 的值。

而所尋找的 a=1 的 記憶體位址就不會是在 0000:0000 而是在 0000:0000 所存的資料記憶體位址中。

以上是小弟對記憶體位址淺薄的認知,如有錯誤,煩請不吝指教。


------
無限的想像,無盡的延伸。
smartboss
初階會員


發表:19
回覆:93
積分:42
註冊:2004-12-29

發送簡訊給我
#7 引用回覆 回覆 發表時間:2009-02-23 13:46:35 IP:115.83.xxx.xxx 訂閱
ikk
基本上這個 dwBaseAddress 我想一定是人去「找」或是「查」出來的所以,他所在的位置本值上對我來說應該是不具義意,因為今天如果我要抓一個gril cell 值,而這一個 gril cell 的 Base Address always different 我就無法去查到我所要抓取的那個 cell 的 value 值,而該例中的 dwBaseAddress 應該如你所述是查出來的,但我的重點在於我如何透過計算的方式而得到這個位址,而依據點或許是從一個 process 抓到的 hwnd 值去計算而來。

===================引 用 ikk 文 章===================
那個位址可能是透過人工去檢查出來的吧.
編輯記錄
smartboss 重新編輯於 2009-03-06 16:12:54, 註解 無‧
smartboss
初階會員


發表:19
回覆:93
積分:42
註冊:2004-12-29

發送簡訊給我
#8 引用回覆 回覆 發表時間:2009-02-23 13:50:23 IP:115.83.xxx.xxx 訂閱
您講的東西應該是指 segment : offset ,我當然知道每次重啟位址值都會變,所以我才問「怎麼計算出來」,「怎麼計算出來」這是我的問題重點。

===================引 用 hotswin 文 章===================
基本上在記憶体眾多資料中,必定有2種資料:值 與址
當你查到某一固定的位址,你要去反相查那些位址使用了這個固定址。
別的位址可能是把這固 定位址當作是一個值或址來計算。
所以你要計算它的位移差,也就是每一次程式啟動時,別的位址也跟著變,而位移差是固定的。

這個要多練習,才能快速直覺得的找到你要的數據,加油嘍。



===================引 用 ikk 文 章===================
那個位址可能是透過人工去檢查出來的吧.
smartboss
初階會員


發表:19
回覆:93
積分:42
註冊:2004-12-29

發送簡訊給我
#9 引用回覆 回覆 發表時間:2009-02-23 14:03:28 IP:115.83.xxx.xxx 訂閱
ChungLin.Net
>>踩地雷程式他的記憶體位址是在編譯時已經建立固定的空間用來存取資料,所以位址上大多不會有所不
同,

我想您分析的應該沒錯,所以這個 array 是固定的,而這個程式的 dwBaseAddress 應該是如 ikk 兄所述是人去查出來的。

>>如果換成是動態記憶體的話
int *a;
int *b;
int *c;
.... 動態記憶體建立 .....
a=1;
b=2;
c=3;
在程式執行後,記憶體位址啟始段就是(假設性,實際資料未必如此)
--------------- 00 01 02 03 04 05 06 07 08 09 0A 0B 0C 0D 0E
0000:0000 01 E0 F0 00 02 0F F0 E0 05 0E 0F 10 ........
0000:0000 - 0000:0003 所存的就是 a 的資料記憶體位址,而不是 a 的值。
而所尋找的 a=1 的 記憶體位址就不會是在 0000:0000 而是在 0000:0000 所存的資料記憶體位址中。

坦白說其實我也一直認為是這樣沒錯,只是我一直想更追根究底些,是否可以由我想像中的流程而找到真正的資料位址,比如我們都可以透過finwindows抓到 hwnd 值,而再經由這個值,我們是否可以透過某些api 再去抓取到您該範例中所舉例的 int *a; 的資料宣告記憶體位址,進而當該指標位址有指向某個實體位置時,我們便可再進一步抓取得到實際資料 a=1; 所在的記憶體位置。
編輯記錄
smartboss 重新編輯於 2009-03-06 16:12:21, 註解 無‧
hotswin
中階會員


發表:72
回覆:92
積分:52
註冊:2003-11-06

發送簡訊給我
#10 引用回覆 回覆 發表時間:2009-02-24 13:28:09 IP:220.134.xxx.xxx 訂閱
http://mp5idv.myweb.hinet.net/ce/tut7-8.htm

這篇動畫教學應該可以滿足你的需求
CE已經裏面的教學範例已經講的很清楚了。

===================引 用 smartboss 文 章===================
您講的東西應該是指 segment : offset ,我當然知道每次重啟位址值都會變,所以我才問「怎麼計算出來」,「怎麼計算出來」這是我的問題重點。

===================引 用 hotswin 文 章===================
基本上在記憶体眾多資料中,必定有2種資料:值 與址
當你查到某一固定的位址,你要去反相查那些位址使用了這個固定址。
別的位址可能是把這固 定位址當作是一個值或址來計算。
所以你要計算它的位移差,也就是每一次程式啟動時,別的位址也跟著變,而位移差是固定的。

這個要多練習,才能快速直覺得的找到你要的數據,加油嘍。



===================引 用 ikk 文 章===================
那個位址可能是透過人工去檢查出來的吧.
------
http://xinjier.0424617287.com/gift/
禮贈品
smartboss
初階會員


發表:19
回覆:93
積分:42
註冊:2004-12-29

發送簡訊給我
#11 引用回覆 回覆 發表時間:2009-03-06 15:58:14 IP:59.124.xxx.xxx 訂閱
您的動畫教學確實是有抓取到偏移位址的功能,但是與我所提情況並不相同,我的情況是「每次重啟後的 handle 值會不同」而不是每次重啟後去借由ce 來計算出不同的偏移位址。

===================引 用 hotswin 文 章===================
http://mp5idv.myweb.hinet.net/ce/tut7-8.htm

這篇動畫教學應該可以滿足你的需求
CE已經裏面的教學範例已經講的很清楚了。
吧.
lu
高階會員


發表:11
回覆:189
積分:195
註冊:2003-11-19

發送簡訊給我
#12 引用回覆 回覆 發表時間:2009-03-06 16:21:57 IP:203.73.xxx.xxx 訂閱
hotswin 兄我想樓主的用意是,如何讓程式自動判斷抓取的 Address ,而不是每次都要使用者介入操作,你所提供的工具,有一部份是建立在有使用者輸入已知的數據或資料,再用比對的方式去算出來,若要把這部分自動化,有一定的難度......如何讓程式『自行』輸入數值,這牽扯到一點所謂的人工智慧了

這個問題,我個人直覺,可透過畫面上所顯示文字來做判斷,只不過此一方式,效率差誤差大...

===================引 用 hotswin 文 章===================
http://mp5idv.myweb.hinet.net/ce/tut7-8.htm

這篇動畫教學應該可以滿足你的需求
CE已經裏面的教學範例已經講的很清楚了。

hotswin
中階會員


發表:72
回覆:92
積分:52
註冊:2003-11-06

發送簡訊給我
#13 引用回覆 回覆 發表時間:2009-03-06 19:30:14 IP:220.134.xxx.xxx 訂閱
 LU 兄說的太好了,所謂的人工智慧,簡單的來說是取代你手工的動作
,現在你只要寫一支代替你人工去查記憶体的資料。
這不叫人工智慧嗎?(隨便說說,勿 打我)

我copy的教學網址,只是提供參考,用的人要舉一反三. 我是覺得先把馬步打好,再談後面的吧。

===================引 用 lu 文 章===================
hotswin 兄我想樓主的用意是,如何讓程式自動判斷抓取的 Address ,而不是每次都要使用者介入操作,你所提供的工具,有一部份是建立在有使用者輸入已知的數據或資料,再用比對的方式去算出來,若要把這部分自動化,有一定的難度......如何讓程式『自行』輸入數值,這牽扯到一點所謂的人工智慧了

這個問題,我個人直覺,可透過畫面上所顯示文字來做判斷,只不過此一方式,效率差誤差大...

===================引 用 hotswin 文 章===================
http://mp5idv.myweb.hinet.net/ce/tut7-8.htm

這篇動畫教學應該可以滿足你的需求
CE已經裏面的教學範例已經講的很清楚了。

------
http://xinjier.0424617287.com/gift/
禮贈品
smartboss
初階會員


發表:19
回覆:93
積分:42
註冊:2004-12-29

發送簡訊給我
#14 引用回覆 回覆 發表時間:2009-03-06 20:35:15 IP:115.81.xxx.xxx 訂閱
     我看不少關於系統資料截取與處理的案子,我去查過一些文章,於事我想這樣處理,目前只差一步,但不知是否有相關經驗去取得一個物件(hwnd)的真正 name 或其它屬於它獨有特徵的資料,那我就得以判定並取得該物件的hwnd 值。
我看過幾篇文章,他為了要把某些button or menu裡的item停掉,於是他首先去取得這物件的caption 跟 classname,之後開始對該程式進行所有物件列舉的動作,當他一一列舉的過程中,他去比對被列舉到的物件的 caption 跟 classname 如果相同於他要控製的物件時,他即將該物件的 hwnd 值抓取起來,以進入下一步應用。
因此,我擔心的事是,會不會在一個大個程式中,他可能會有兩個以上的 button caption 名稱與 classname都相同的,那就可能造成誤判並控製錯誤的情形,因此想問是否有方法透過hwnd查找到該物件他在建立時真正的name或期它屬於它獨有特徵的資料,我就可以確定那就是我要控製的物件。
編輯記錄
smartboss 重新編輯於 2009-03-09 09:58:49, 註解 無‧
smartboss 重新編輯於 2009-03-09 13:07:03, 註解 無‧
系統時間:2017-12-15 4:46:51
聯絡我們 | Delphi K.Top討論版
本站聲明
1. 本論壇為無營利行為之開放平台,所有文章都是由網友自行張貼,如牽涉到法律糾紛一切與本站無關。
2. 假如網友發表之內容涉及侵權,而損及您的利益,請立即通知版主刪除。
3. 請勿批評中華民國元首及政府或批評各政黨,是藍是綠本站無權干涉,但這裡不是政治性論壇!