I'm interested in creating a macro, that will 'store' and return a number (used for EQU's) that increments.
A bit difficult to explain, but used primarily on window controls, where you assign the 'messageID' a value, usually greater than WM_USER eg.


WM_TEXT_NOTES EQU WM_USER + 1
WM_TEXT_HELLO EQU WM_USER + 2
WM_BUTTON_CONTINUE EQU WM_USER + 3
WM_BUTTON_CANCEL EQU WM_USER + 4

I want a macro that takes no input but returns a 'unique', incremented number in the form "WM_USER + n".

eg. Pseudo-code


EquInc MACRO
IFNDEF EquIncVariable
EquIncVariable :DWORD
EquIncVariable = WM_USER
ENDIF
EquIncVariable = EquIncVariable + 1
EXITM <EQU EquIncVariable>
ENDM

WM_TEXT_NOTES EquInc
WM_TEXT_HELLO EquInc
WM_BUTTON_CONTINUE EquInc
WM_BUTTON_CANCEL EquInc

Thanx
Posted on 2004-04-22 04:01:34 by SubEvil
(Untested)


EquInc MACRO
IFNDEF EquIncVariable
EquIncVariable = WM_USER
ENDIF
EquIncVariable = EquIncVariable + 1
EXITM <EQU EquIncVariable>
ENDM

Perhaps what would be a lot more interesting (and harder) is an "enum" macro, more or less imitating the C++ syntax.
enum {WM_TEXT_NOTES=WM_USER,\

WM_TEXT_HELLO,\
WM_BUTTON_CONTINUE,\
WM_BUTTON_CANCEL}

It would treat the passed arguments as a single string. :)
Posted on 2004-04-22 11:33:40 by QvasiModo
QvasiModo, the line length limit in MASM prevents many cool macros. Furthermore, passing parameters to macros that return values cannot be on multiple lines. :(
Posted on 2004-04-22 12:17:49 by bitRAKE

QvasiModo, the line length limit in MASM prevents many cool macros.

Hadn't thought of that. :(
Furthermore, passing parameters to macros that return values cannot be on multiple lines. :(

No, my idea was to directly generate code, not return any parameters.
Posted on 2004-04-23 15:17:42 by QvasiModo
While I agree with bitRAKE that the line length issue is annoying to work with sometimes, i dont think its all that critical. Just design some recourse for this case. Below is my version of the problem, with the ability to define on the fly the next value in the enum. This alows you to break it up over many lines.
ENUM    MACRO   args:VARARG

LOCAL a1, x1, sz1, sz2, sz3
x1 = 0
for arg, <args>
a1 equ @InStr(1,arg,<:=>)
if a1 ne 0
x1 = @SubStr(arg,a1+2)
sz1 EQU @SubStr(arg,1,a1-1)
else
sz1 EQU arg
endif
sz3 TEXTEQU %x1
sz2 EQU @CatStr(sz1,< EQU >, sz3)
x1 = x1 + 1
[color=red] %echo sz2[/color]
sz2
endm
endm

ENUM_MSG MACRO args:VARARG
LOCAL a1, x1, sz1, sz2, sz3
x1 = 0
for arg, <args>
a1 equ @InStr(1,arg,<:=>)
if a1 ne 0
x1 = @SubStr(arg,a1+2)
sz1 EQU @SubStr(arg,1,a1-1)
else
sz1 EQU arg
endif
sz3 TEXTEQU %x1
sz2 EQU @CatStr(sz1,< EQU WM_USER + >, sz3)
x1 = x1 + 1
[color=red] %echo sz2[/color]
sz2
endm
endm


You would use it like so:
ENUM  Data1, Data2, Data3, Data4

Will produce:


Data1 EQU 0
Data2 EQU 1
Data3 EQU 2
Data4 EQU 3

To adjust the starting number, do the following:


ENUM Data5:=10, Data6, Data7:=20, Data8

Which would then produce:


Data5 EQU 10
Data6 EQU 11
Data7 EQU 20
Data8 EQU 21


Additionally, i made a copy of this routine specifically to WM_USER messages. The same 'features' apply. Only the generated equates would look like:
[Label]  EQU WM_USER + [autoValue]


PS: If your convinced of the macros and like them, comment out or remove the lines above noted in RED. These are compile outputs I left in to show you what is generated when compiled.

Hope you like this. Thanks for the idea SubEvil and QvasiModo!
Regards,
:NaN:
Posted on 2004-04-23 21:59:02 by NaN
SubEvil,

Trivial. Ratch





= 00000400 USE$R = WM_USER
USERINC MACRO
USE$R = USE$R + 1
EXITM <EQU USE$R>
ENDM

= 00000401 WM_TEXT_NOTES USERINC()
= 00000402 WM_TEXT_HELLO USERINC()
= 00000403 WM_BUTTON_CONTINUE USERINC()
= 00000404 WM_BUTTON_CANCEL USERINC()


00000000 .DATA?
00000000 .DATA
00000000 .CODE
00000000 MAIN:
00000000 B8 00000402 MOV EAX,WM_TEXT_HELLO
END MAIN
Posted on 2004-04-24 07:07:50 by Ratch
QvasiModo,

Trivial. Ratch



= 000003FF USE$R = WM_USER-1
ENUM MACRO P1:VARARG
FOR ARG,<P1>
USE$R = USE$R + 1
ARG EQU USE$R
ENDM
ENDM

ENUM WM_TEXT_NOTES,\
WM_TEXT_HELLO,\
WM_BUTTON_CONTINUE,\
WM_BUTTON_CANCEL
= 00000400 2 WM_TEXT_NOTES EQU USE$R
= 00000401 2 WM_TEXT_HELLO EQU USE$R
= 00000402 2 WM_BUTTON_CONTINUE EQU USE$R
= 00000403 2 WM_BUTTON_CANCEL EQU USE$R

ENUM WM_A,\
WM_B,\
WM_C,\
WM_D
= 00000404 2 WM_A EQU USE$R
= 00000405 2 WM_B EQU USE$R
= 00000406 2 WM_C EQU USE$R
= 00000407 2 WM_D EQU USE$R
Posted on 2004-04-24 07:40:29 by Ratch
No one said this wasn't trivial. Ratch essentially repeated my above source without any 'features' (not like this stuff is rocket science to begin with). If your interested in macro size then go with Ratches suggested solution, it definitely is the lean & mean version. However, I designed the extra's into it such that (1) you dont need to externally define a working equate to use the macro's ~ Im refering to USE$R in Ratch's source; (2) You can define the starting point of each enumeration, or default to zero, in the same line; (3) you can control the linearity of the enumeration as I had shown in my above example (10,11,20,21).

Regards,
:alright:
NaN
Posted on 2004-04-24 09:07:41 by NaN