Greetings,
I'm creating a common header for masm 32bit and 64bit, and i have the following macro:
IFDEF RAX
REG_AX textequ <rax>
ELSE
REG_AX textequ <eax>
ENDIF
; Copy the value from requested member in the BOOK structs array
; to the general purpose register.
GET_BOOK_MEMBER MACRO Member, BookIndex
mov REG_AX, gBooks
add REG_AX, SIZEOF BOOK * BookIndex
assume REG_AX:PTR BOOK
mov REG_AX, [REG_AX].Member
ENDM
I'm compling using visual studio, and the compliation FAILS!!! with ml64.exe with the following errors:
A2008: syntax error: rax
A2008: syntax error: rax
If i remove the "assume REG_AX:PTR BOOK" it works.... the assume statement works in 32bit. What did i do wrong? i want to
use rax as a pointer to a struct.
It is safer to use a global switch (credits to rrr (http://masm32.com/board/index.php?topic=5491.msg58912#msg58912)):
if @AssembleAs64bit
SIZE_P equ <QWORD> ; int and long are 32-bit, pointer is 64-bit
else
SIZE_P equ <DWORD> ; int, long, and pointer are 32-bit
rax equ eax
rcx equ ecx
rdx equ edx
rsi equ esi
rdi equ edi
rbx equ ebx
rbp equ ebp
rsp equ esp
endif
This works like a charm with ML/ML64, UAsm, AsmC and JWasm (-> 64-bit assembly with RichMasm (http://masm32.com/board/index.php?topic=5314.msg59884#msg59884)).
The principle is simple: You write all code using rax for pointers and pointer-sized variables; when assembled as 32-bit code, rax is not a keyword, so the preprocessor translates it to eax.
Thank you for the reply!
I'm still getting the same errors...
Here's the full code:
HARRY_POTTER = 0
IFDEF RAX
EXTERN gBooks:NEAR
SIZE_P equ <QWORD> ; int and long are 32-bit, pointer is 64-bit
_gBooks textequ <gBooks>
ELSE
EXTERN _gBooks:NEAR
SIZE_P equ <DWORD> ; int, long, and pointer are 32-bit
rax equ eax
ENDIF
BOOK struc
Name SIZE_P ?
Length SIZE_P ?
BOOK endS
; Copy the value from requested member in the BOOK struct
; to the general purpose register rax.
GET_HOOK_MEMBER MACRO Member, BookIndex
mov rax, _gBooks
add rax, SIZEOF BOOK * BookIndex
assume rax:PTR BOOK
mov rax, [rax].Member
assume rax:nothing
ENDM
;Get the name in rax
BOOK_NAME MACRO BookIndex
GET_BOOK_MEMBER Name, BookIndex
ENDM
;Get the length in rax
BOOK_LENGTH MACRO BookIndex
GET_BOOK_MEMBER Length, BookIndex
ENDM
I'm still getting
"syntax error: rax"
"undefined symbol: Length"
"undefined symbol: Name"
When using these macros in my assembly code.
If i remove the "ASSUME rax: ptr BOOK", it compiles... but i need that statement.
It is probably the case that ML64 treats registers as key words and won't let you equate them to anything else.
Well... this is literally my code now:
.CODE
Foo PROC
ASSUME rax:NOTHING
Foo ENDP
END
And i'm getting the same errors.. still:
Severity Code Description Project File Line Suppression State
Error A2008 syntax error : rax foo_project foo.asm 3
Severity Code Description Project File Line Suppression State
Error MSB3721 The command "ml64.exe /c /nologo /Zi /Fo"C:\foo\x64\Release\foo.obj"" /W3 /errorReport:prompt /foo.asm" exited with code 1. foo_project C:\Program Files\MSBuild\Microsoft.Cpp\v4.0\V140\BuildCustomizations\masm.targets 50
This is indeed... weird.. i'm not sure what to do now.. it doesn't like the "ASSUME" directive. Is it obsolete?
ML64 is indeed weird. Your code assembles fine with UAsm. Give it a try...
Otherwise, use an equate instead of assume:
book equ [rax.BOOK]
Mov rdx, book.xName
Mov rcx, book.xLength
I added the x because Name and Length are reserved words. Change your struct.
Maybe this?
assume rax:ptr StructureName
mov rsi, [rax].whatever
assume rax:nothing
Late to the party, nothing new. Story of my life.
ml64
MODEL STRUCT
m_MyValue0 dq ?
m_MyValue1 dq ?
m_MyValue2 dq ?
m_MyValue3 dq ?
MODEL ENDS
Some64bit_Croc proc
local TheModel:MODEL ; and she's looking good.
; assume rcx:ptr TheModel <- syntax error : rcx (A2008)
lea rcx, TheModel
mov qword ptr[rcx][MODEL.m_MyValue0], 080000000h ; Note "qword ptr" not needed, essential aesthetics IMAO.
mov qword ptr[rcx][MODEL.m_MyValue1], 07FFFFFFFh
mov qword ptr[rcx][MODEL.m_MyValue2], 0FEEDABBEh
mov rax, 0FEEDABBEh
mov qword ptr[rcx][MODEL.m_MyValue3], rax
mov qword ptr[rcx].MODEL.m_MyValue3, rax ; <- alternative syntax
mov qword ptr[rcx+MODEL.m_MyValue3], rax ; <- alternative syntax
; assume rcx:nothing <- syntax error : rcx (A2008)
; Also look carefully at the values held
; by m_MyValue0,1,2,3 after operations.
; Compare 0 with 1.
; Note dissimilarity between 2 and 3.
...
ret
Some64bit_Croc endp
Try
mov TheModel.m_MyValue0, 080000000h
instead of
mov qword ptr[rcx][MODEL.m_MyValue0], 080000000h
Thank you very much jj.
I need this syntax for OOP.
CModel_Initialize proc
mov [rax].CModel.m_ModelCaller, rdi
mov rdi, rax
mov [rdi].CModel.m_TextureCount, rcx
mov [rdi].CModel.m_TextureFile[0], rdx
mov [rdi].CModel.m_TextureFile[8], r8
mov [rdi].CModel.m_TextureFile[16], r9
call (CModel ptr[rdi]).LoadModelMesh
cmp [edi].m_ModelType, BumpType
jne TypeBump
call (CModel ptr[rdi]).CalculateBumpVectors
TypeBump:
call (CModel ptr[rdi]).InitializeBuffers
call (CModel ptr[rdi]).LoadTexture
mov rdi, [rdi].CModel.m_ModelCaller
ret
CModel_Initialize endp
Quote from: Caché GB on November 06, 2019, 03:41:51 PMI need this syntax for OOP
More choices ;-)
MyModel equ [rax.MODEL]
lea rax, TheModel
mov MyModel.m_MyValue0, 080000000h
mov TheModel.m_MyValue0, 080000000h
mov qword ptr[rax][MODEL.m_MyValue0], 080000000h