1

I have this block of ASM code with a few variables and 1 instruction:

.data
g BYTE 32h
a DWORD 11111111h
h BYTE 64h
.code
mov ebx, DWORD PTR g

Could anyone explain why the value of ebx is not 11 11 11 32 instead of 00 00 00 32 or at least how does PTR work?

I thought that the PTR directive would represent the operand as a 32-bit operand ?

Thanks in advance.

Wolfat
  • 85
  • 1
  • 9
  • `ebx` after that should be `11111111h` since you have just loaded `a`. `32` , which is part of `g` and is earlier in memory can not be in `ebx`. – Jester Feb 09 '17 at 16:15
  • http://stackoverflow.com/q/41562732/4271923 Take a note of the pun comments, which basically explains how `PTR` works - it does not, it's just 3 letters required due to syntax, when you specify argument width. At least in TASM/MASM assemblers. For example in NASM the "`PTR`" is not used at all, as it doesn't really do anything. (there may be of course some completely other assembler using PTR even for something meaningful, but I guess you are asking about MASM/TASM one) – Ped7g Feb 09 '17 at 18:22

2 Answers2

0

See @Jester's comment if your code really looks like what you've posted.


But judging by your question I'm guessing that your code actually contains this line instead:

mov ebx, DWORD PTR g

I thought that the PTR directive would represent the operand as a 32-bit operand ?

That depends on what you mean by that. DWORD PTR would be used as a size specifier when the size is ambiguous.
For example, the instruction mov [eax], 0 would be ambiguous because the assembler has no idea of knowing if you meant to write a byte, a word, a dword, etc. So in that case you could use DWORD PTR to state that you want to write a DWORD to memory: mov DWORD PTR [eax], 0.

If you want to read a byte from memory and convert it to a DWORD you need to use movzx or movsx:

movzx ebx, BYTE PTR g   ; if g should be treated as unsigned
movsx ebx, BYTE PTR g   ; if g should be treated as signed
Michael
  • 57,169
  • 9
  • 80
  • 125
  • DWORD PTR could also be used to overide the size of a data type, such as `xyz dw 05678h,01234h` ... `mov ebx,dword ptr xyz`, which would load 012345678h into ebx. In this case, the operand size is known, but MASM and other assemblers will generate an error if 'dword ptr' override is not used. – rcgldr Feb 09 '17 at 18:21
  • @rcgldr yeah, but if you follow valid Intel syntax, the `mov ebx,[xyz]` will compile without DWORD PTR even in MASM? I guess. I don't know. I was using TASM in "ideal" mode, where it certainly did work like that, the register width was enough, and braces were used properly. – Ped7g Feb 09 '17 at 18:26
  • One case where ptr may not mean pointer is with a push immediate such as `push dword ptr 012345678h`, since the immediate value could mean something other than a pointer. – rcgldr Feb 09 '17 at 18:48
  • 2
    @Ped7g - Microsoft MASM / ML will complain without the override. A programmer is pretty much forced to use this when loading 128 bit xmm register. `abc dq 00123456789abcdefh,0fedbca9876543210h` ... `movdqa xmm0, xmmword ptr abc` . (movdqa = move double quad word aligned), as MASM doesn't have something like ddq or dx to generate 128 bit data. – rcgldr Feb 09 '17 at 18:49
  • @Michael Thanks for your reply. One more thing, if I want to compare eax (having some value) to a 8-bit operand such as g , must I move g to a 32-bit operand for comparison ? And is there any use of PTR for this? – Wolfat Feb 10 '17 at 10:40
  • If you want to compare `eax` against the byte at `g`, then yes, you'd have to mov that byte into a 32-bit register using `movzx/movsx`. If you just want to compare the least significant byte of `eax` against `g` you can do that directly: `cmp al,[g]`. – Michael Feb 10 '17 at 11:15
0

Unfortunately the assembly language for x86 was too generic, using

mov ebx,a

If you look at the instruction encodings (if you are writing/learning assembly you should have a reference handy and open anyway) you find that that might mean read a byte at address 8, or a 16 bit word at address a or perhaps a 32 bit word at address a. And it may or may not go further and allow for sign extension or not. So in order to get the right instruction that you want you need to add more stuff.

Assembly language is not some standard it is defined by the assembler, the program reading the ASCII file, so one assembly language for the same instruction set does not dictate what another is. x86 in particular starting with intel vs AT&T and then gcc vs masm vs nasm and so on. And naturally with gcc and AT&T and everyone else that intentionally didnt want to go along with what was already out there, how you specify if this is a byte read or word read or dword read varies. Likewise the default instruction if any that is generated if you dont specify what you want.

old_timer
  • 69,149
  • 8
  • 89
  • 168