4

アセンブリの構造宣言が win32 API ドキュメントの構造宣言と異なるのはなぜですか (私は c++ から来て、アセンブリ言語を試しています)

たとえば、icezelion のチュートリアル (tutorial3) からこの関数プロトタイプを取得しました。

WNDCLASSEX STRUCT DWORD
  cbSize            DWORD      ?
  style             DWORD      ?
  lpfnWndProc       DWORD      ?
  cbClsExtra        DWORD      ?
  cbWndExtra        DWORD      ?
  hInstance         DWORD      ?
  hIcon             DWORD      ?
  hCursor           DWORD      ?
  hbrBackground     DWORD      ?
  lpszMenuName      DWORD      ?
  lpszClassName     DWORD      ?
  hIconSm           DWORD      ?
WNDCLASSEX ENDS   

ちょっと待って... win32 api ドキュメントのオフライン バージョンで、"WNDCLASSEX" 構造が次のように宣言されていることを知っています....

typedef struct _WNDCLASSEX {    // wc  
    UINT    cbSize; 
    UINT    style; 
    WNDPROC lpfnWndProc; 
    int     cbClsExtra; 
    int     cbWndExtra; 
    HANDLE  hInstance; 
    HICON   hIcon; 
    HCURSOR hCursor; 
    HBRUSH  hbrBackground; 
    LPCTSTR lpszMenuName; 
    LPCTSTR lpszClassName; 
    HICON   hIconSm; 
} WNDCLASSEX; 

asm バージョンが win32 api ドキュメントにあるものとは反対に DWORD のみを使用するのはなぜですか?
間違ったドキュメントを使用していますか? もし私がそうなら、誰かがasmプログラマー向けのWIN32 APIドキュメントのダウンロードリンクを私に投稿できますか?
助けてください、混乱しています。

編集済み:これは私が参照していたチュートリアルへのリンクです:

iczelion の win32 asm チュートリアル 3

4

7 に答える 7

7

DWORDS は、構造体の C バージョンのすべての型と同様に、32 ビット ウィンドウでは 32 ビット型です。したがって、この 2 つは互換性があります。

于 2010-01-29T20:43:35.773 に答える
5

アセンブリ言語には型がありません。DWORD やその他のキーワードは、特定のエンティティ用に予約する必要のあるバイト数を示すだけです。実際、DWORD とそのいとこはオペコード/ニーモニックを表していないため、実際にはマクロ プリプロセッサの機能です。

C/C++ の型は、他の言語の型と同様に、エンディアン、符号ビットの場所、可能なキャスト、変換、代入などの規則によって制約されます。提供した構造の C バージョンは、より具体的です。アセンブリ言語バージョンですが、互換性があります。

于 2010-01-29T20:48:11.610 に答える
4

これらすべての異なる C 型のサイズは DWORD です。アセンブリは厳密に型指定されていません。各変数について知っているのはバイト数だけです。

于 2010-01-29T20:42:58.113 に答える
2

かつて (16 ビット Windows)、これらの型のサイズは異なっていました。Win32 への移行中に、それらはすべて 32 ビット データ型になりました。そのため、 aDWORDは、少なくともある程度、それらすべてと互換性があります。

ただし、一般に信じられていることとは反対に、アセンブリ言語には型があり (または少なくとも可能であり)、かなり公正な型安全性さえあります。たとえば、次のようなことをするとどうなるかを考えてみてください。

mov lpszMenuName[ecx], 0

lpszMenuNamea として定義するDWORDと、アセンブラーはこれを受け入れません。これは、'0' が a byte、 a word、 adwordまたは (64 ビットの世界では) aになる可能性があるためqwordです。それを機能させるには、(本質的に) 型キャストを追加する必要があります。

mov byte ptr lpszMenuName[ecx], 0

したがって、アセンブラは、1 バイトを書き込もうとしていることがわかります。または、次のように定義できますlpszMenuName

lpszMenuName ptr byte

その場合、アセンブラは、毎回明示的に宣言しなくても、バイトを指しているものとして扱う必要があることを認識します。

于 2010-01-29T20:59:34.373 に答える
1

実際、MASM 6+はタイピングの形式をサポートしているため、MASMの構造をCの構造と同じにすることができます。ただし、最初に型階層を再作成する必要があり、すぐに次の利点に気付くでしょう。 MASMでの入力は、どういうわけか制限されています(そこで、それを実行します)。GoogleのMASM6プログラマーズリファレンスPDFファイルをお勧めします。これは、タイピングを含むMASMの「HLL」機能をかなり明確に説明しており、いくつかの例が含まれています。以下のリンクから1部入手できるようですが、他にも浮かんでいます。

http://www.microlab.teipat.gr/upload/arxeshy/Microsoft_MASM_Programmers_Guide_v6.zip

于 2010-01-31T11:56:45.737 に答える
1

WNDPROC、UINT などは C ヘッダーで定義されているため、ASM に直接相当するものはありません。これらはすべて、32 ビット システムでは DWORD サイズの量であるため、このチュートリアルで動作するコードが生成されます。

于 2010-01-29T20:42:33.540 に答える
1

アセンブリでは、高レベルの構造にポインターまたは int があるかどうかに関係なく、実際には、関連する高レベルのデータ型は BYTE、WORD、および DWORD です。この場合、構造はすべて 32 ビットであるため、DWORD (WORD は 16 ビットです) 、DWORDは32ビットです)。アセンブリの構造は C の構造とは異なり、ほとんど同じであると誤解しないでください。アセンブラーには、ポインター、構造体などに関係なく、基本的なデータ型があります。それらを区別するのは、レジスターへのロード方法です (構文によって異なります)。

mov eax, dword ptr [bx]

このアセンブラ サンプルは、eaxレジスタが指す値をレジスタにロードするデモbxです。

int bx = 5;
int *eax;
ptr = &bx;

これがお役に立てば幸いです。よろしくお願いします、トム。

于 2010-01-29T21:22:47.893 に答える