5

これをより適切に尋ねる方法がわかりませんが、なぜこれを行うのですか:

call ExitProcess

これと同じことをしますか?:

mov eax, ExitProcess
mov eax, [eax]
call eax

これらは同等だと思います:

call ExitProcess


mov eax, ExitProcess
call eax
4

1 に答える 1

11

DLL からコードをインポートする場合、シンボルExitProcessは実際にはプロセスを終了するコードのアドレスではありません (これはaddress のアドレスです)。したがって、その場合、実際のコード アドレスを取得するには、逆参照する必要があります。

つまり、次を使用する必要があります。

call [ExitProcess]

それを呼び出すために。

たとえば、この場所には次を含むコードがあります。

;; Note how we use 'AllocConsole' as if it was a variable. 'AllocConsole', to 
;; NASM, means the address of the AllocConsole "variable" ; but since the 
;; pointer to the AllocConsole() Win32 API function is stored in that 
;; variable, we need to call the address from that variable. 
;; So it's "call the code at the address: whatever's at the address
;; AllocConsole" . 
call [AllocConsole] 

ただし、DLL をユーザー コードに直接インポートすることが、関数を取得する唯一の方法ではありません。両方の方法が表示される理由を以下で説明します。

DLL 関数を呼び出す「通常の」手段は、それをマークしexternimportから DLL から呼び出すことです。

extern ExitProcess
import ExitProcess kernel32.dll
:
call [ExitProcess]

これにより、シンボルがコードへの間接参照になるように設定されるため、間接的に呼び出す必要があります。

いくつかの検索の後、ネイキッド フォームを使用するコードが実際に存在するようです

call ExitProcess

私が知る限り、これはすべて、ライブラリ ファイルalinkとリンクするリンカを使用しているようです。win32.libこのライブラリは、次のような実際のDLL コードを呼び出すためのスタブを提供する可能性があります。

import ExitProcessActual kernel32.dll ExitProcess
global ExitProcess

ExitProcess:
    jmp [ExitProcessActual]

では、これは のアドレスをDLL からnasmインポートしてを呼び出しますが、このアドレスはコード自体のアドレスではなく、コードへの間接的な参照であることに注意してください。ExitProcessExitProcessActual

ExitProcess次に、エントリ ポイント (DLL 内のエントリ ポイントではなく、この LIB ファイル内のエントリ ポイント) をエクスポートして、他のユーザーが使用できるようにします。

次に、誰かが簡単に書くことができます:

extern ExitProcess
:
call ExitProcess

プロセスを終了するには、ライブラリが実際の DLL コードにジャンプします。


実際、もう少し調査すると、これがまさに起こっていることです。alink.txtダウンロードに付属のファイルからalink

Win32 用のサンプル インポート ライブラリが として含まれていwin32.libます。、、、、、、、、、Kernel32およびのすべてUser32の名前付きエクスポートが含まれます。GDI32Shell32ADVAPI32versionwinmmlz32commdlgcommctl

使用する:

alink -oPE file[.obj] win32.lib

それを含めるか指定する

INCLUDELIB "win32"

ソースファイルで。

これは、インポート リダイレクション - の一連のエントリで構成され、インポート テーブルにあるcall MessageBoxAにジャンプします。[__imp_MessageBoxA]

したがって、call [__imp_importName]の代わりに を使用すると、インポートの呼び出しが高速になりcall importNameます。

test.asm双方向のメッセージ ボックスを呼び出すサンプル プログラムを参照してください。

includelib "win32.lib"
extrn MessageBoxA:near
extrn __imp_MessageBoxA:dword

codeseg

start:
push 0 ; OK button
push offset title1
push offset string1
push 0
call MessageBoxA

push 0 ; OK button
push offset title1
push offset string2
push 0
call large [large __imp_MessageBoxA]

(__imp_MessageBoxAは DLL からインポートされたシンボルで、ExitProcessActual上記の my と同等です)。

于 2012-07-31T01:20:14.830 に答える