NASM - The Netwide Assembler

NASM Forum => Programming with NASM => Topic started by: paml27 on April 07, 2020, 12:36:52 AM

Title: How to reference the fields of a struc?
Post by: paml27 on April 07, 2020, 12:36:52 AM
In the .data section I defined a struc:

%define O_RDWR 00000002

struc mq_attr
  .mq_flags: resd 1
  .mq_maxmsg: resd 1
  .mq_msgsize: resd 1
  .mq_curmsgs: resd 1
endstruc

mq_attributes:
  istruc mq_attr
    at mq_attr.mq_flags, dd O_RDWR
    at mq_attr.mq_maxmsg, dd 100
    at mq_attr.mq_msgsize, dd 1000 ;656
    at mq_attr.mq_curmsgs, dd 0
  iend

In the text (code) section, I followed the directions in the 2.13.02 manual to examine the structure elements, but only the third element shows correctly:

194     mov rax,[mq_attributes+mq_attr.mq_flags]
rax            0x6400000002     429496729602
195     mov rax,[mq_attributes+mq_attr.mq_maxmsg]
rax            0x3e800000064    4294967296100
196     mov rax,[mq_attributes+mq_attr.mq_msgsize]
rax            0x3e8    1000
197     mov rax,[mq_attributes+mq_attr.mq_curmsgs]
rax            0x6e616c6300000000       7953757589370568704

Did I calculate the offsets correctly (e.g. mq_attributes+mq_attr.mq_flags)?  If so, why do elements 1, 2 and 4 not show correctly? 

Thanks very much. 




Title: Re: How to reference the fields of a struc?
Post by: fredericopissarra on April 07, 2020, 10:51:36 AM
Since the structure fields are DWORDs, you should use, for example:

Code: [Select]
; the upper 32 bits will be zeroed!
mov eax,[mq_attributes+mq_attr.mq_flags]
Title: Re: How to reference the fields of a struc?
Post by: paml27 on April 07, 2020, 02:42:20 PM
Thanks, Frederico.  That turned out to be the right answer.  I'm surprised it didn't zero-extend into rax. 
Title: Re: How to reference the fields of a struc?
Post by: Dr1v3n on December 07, 2020, 09:42:19 PM
Is there some magic going on under the hood which explains this? I'm just curious as to why the number being moved into rax wouldn't just put it into rax proper. This almost looks like some sort of signedness issue to me based on the values that were in there in the example the OP showed, but I'm not sure why this would be the case.
Title: Re: How to reference the fields of a struc?
Post by: fredericopissarra on December 08, 2020, 01:19:00 PM
Is there some magic going on under the hood which explains this? I'm just curious as to why the number being moved into rax wouldn't just put it into rax proper. This almost looks like some sort of signedness issue to me based on the values that were in there in the example the OP showed, but I'm not sure why this would be the case.

The almighty chief engineer at AMD,years ago, conjured some demon and, since then, the x86-64 standard dictates every time you change the lower 32 bits of R?? register, the upper DWORD will be zeroed (read the holy Intel SDM and AMD CPU manuals)..
Title: Re: How to reference the fields of a struc?
Post by: vitsoft on December 17, 2020, 09:08:17 AM
x86-64 standard dictates every time you change the lower 32 bits of R?? register, the upper DWORD will be zeroed
Actually, this is not accurate. Bits 32..63 of GPR will be zeroed only when the operand size is 32.

     MOV RAX,0x123456789ABCDEF0h
   ; RAX is now 0x123456789ABCDEF0h, nothing is zeroed, though the lower 32 bits are changed.
   MOV EAX,0x12345678
   ; RAX is now 0x0000000012345678, upper DWORD is zeroed.


The only reason is performance: removing internal dependencies in CPU microcode, prefectly explained at StackOverflow (https://stackoverflow.com/questions/11177137/why-do-x86-64-instructions-on-32-bit-registers-zero-the-upper-part-of-the-full-6)