I'm using a simple macro (I simplified a little more here) to declare related variables:
estado macro name:REQ
a&name REAL8 0.0
b&name REAL8 0.0
c&name REAL8 0.0
endm
The appplication:
estado prot
estado fat
The result:
aprot REAL8 0.0
bprot REAL8 0.0
cprot REAL8 0.0
afat REAL8 0.0
bfat REAL8 0.0
cfat REAL8 0.0
The question: It's posible, for a large number of names (60 for example), to obtein:
aprot REAL8 0.0
afat REAL8 0.0
bprot REAL8 0.0
bfat REAL8 0.0
cprot REAL8 0.0
cfat REAL8 0.0
Thanks in advance. HSE
It is, it is...include \masm32\include\masm32rt.inc
makevars MACRO varcount
Local ct, tmp$
.data
ct=0
repeat varcount
tmp$ CATSTR <prot>, %ct, < REAL8 >, %ct, <.0>
% echo tmp$
tmp$
tmp$ CATSTR <fat>, %ct, < REAL8 0.0>
% echo tmp$
tmp$
ct=ct+1
ENDM
.code
ENDM
.code
start:
makevars 60
fld prot40
fld fat59
exit
end start
Thanks JJ!
I don't explain enough, I think.
1. large number of "name" : prot, fat, water, Ac, Fa, Bu, ...
(very large for using VARARG in a nice code)
2. need to be: a+name, b+name, c+name. Not 1+name, name+1, name+a
The CATSTR part shows how to do it, the % echo shows the actual name while assembling. But in any case, this looks more like a candidate for a structure, or an array of structures:
include \masm32\MasmBasic\MasmBasic.inc ; download (http://masm32.com/board/index.php?topic=94.0)
FOOD STRUCT
prot REAL8 ?
fat REAL8 ?
water REAL8 ?
Ac REAL8 ?
Fa REAL8 ?
Bu REAL8 ?
FOOD ENDS
Init
Dim MyFood() As FOOD
fldpi ; get a real number
fstp MyFood(0, water)
Print Str$("Food 0/water=%f", MyFood(0, water))
EndOfCode
Structure seems like a good idea but actually it seems HSE wants this:
abc STRUCT
a REAL8 ?
b REAL8 ?
b REAL8 ?
abc ENDS
Then instantiate prot, fat etc as that struct, and use prot.a, fat.b etc instead of aprot, afat etc.
An array of struct's might be a good idea, matter of style I guess.
As for the original problem: I think that's a bug. Macros can do stuff like that when you push them. In fact, HSE, you found another case like that last year. But note, all your variables are getting defined correctly, just in the wrong order. Instead of all prot's followed by all fat's, it's all a's followed by all b's, and so forth. Code still works.
Finally, the point of jj's first post is to use a CATSTR to make sure the order is the way you want it - if you go with that technique. But note, in that case it might screw up because there's a limit on size of the concatenated string.
estado macro names:VARARG
FOR name,<names>
a&name REAL8 0.0
b&name REAL8 0.0
c&name REAL8 0.0
ENDM
endm
?
Quote from: rrr314159 on June 16, 2016, 06:55:37 PM
As for the original problem: I think that's a bug. Macros can do stuff like that when you push them. In fact, HSE, you found another case like that last year.
What exactly is a bug? What was the other case?
regards
A bug, in this case, is unexpected behavior that arises sometimes when you use too many macros, or push them too far; you might say, "get too clever". HSE, last year, had too many nested macros; no doubt he can reference the thread if you're interested. One unexpected factor was that EXITM constituted a "nested macro".
If you want other examples, I'd have to go through my notes. I remember one happened using HLL statements with two terms "and"-ed together, in a complex series of .if statements. Fixed by putting them in two separate .if statements. Verified by debugging: the emitted code was wrong. I think it amounted to an obviously missing jump. But really don't remember the (maybe half dozen) cases well. One just works around it, and forgets about it.
You (or hutch) might say "it's not a bug, you just don't understand the beast well enough." Probably true in some cases, but not all.
Consider the present OP where HSE's declarations are, apparently, being emitted in the wrong order if called 60 times, as he says. That's an excellent example. Even if there's some reason - "it's not a bug, it's a feature" - it sure feels like a bug when you run into it.
Thanks very much!
The entire example is in http://masm32.com/board/index.php?topic=5244.0 , but with the real code perhaps is dificult to see the subject.
Very clever JJ, that variables are inside an structure, an Object in this case.
In the way I define variables I obtein an array. The access to array demand calculation:
firstinitial textequ iprot
ForLp v1, 0 , topebucle
mov ebx , v1
mov eax , v1
mov ecx , 3
mul ecx
f2f [esi].integrales[ebx*8], [esi].modelo.firstinitial[eax*8]
Next v1
If the variables are sorted is more simple to access this variables.
In a tipical run this type of code is called 1.2e3 times and optimization don't pay, but perhaps I need to run 1.2e9 or more for some problems. For more complicated problems writing by hand perhaps pay, even losing readability, that it's a must here (or should be).
What you mention qWord, for my purpose could be:
estado macro names:VARARG
FOR name,<names>
a&name REAL8 0.0
ENDM
FOR name,<names>
b&name REAL8 0.0
ENDM
FOR name,<names>
c&name REAL8 0.0
ENDM
endm
It's the option. I don't know if there is a limit for VARARG. And I don't have the posibilty of charge values:
estado macro name:REQ, value1
a&name REAL8 &value1
b&name REAL8 0.0
c&name REAL8 0.0
endm
Perhaps you are rigth rrr, and the problem is a bug, that is the question! I think I saw a macro with specific location of variables, but could be a dream (or a very real bad interpretation). I don't know what case you remember, there is so many :biggrin:. Very nice of You remember only one!
I see there is new post at the same time.
It's a good warning rrr!
Allowing most level macros in the compiler solved last year problem and works perfect, of course you lost more time in the case of errors, recurrency, etc. Perhaps need the leyend "Don't use for aeronautic controls, live support systems and... " (is something like that)
I don't remember the ".if" thing, perhaps never work.
In this case the variables are emited in the expected order, just I want a diferent order (with the same code!).
Thanks for your opinion!
Quote from: rrr314159 on June 17, 2016, 01:15:45 AM
A bug, in this case, is unexpected behavior that arises sometimes when you use too many macros, or push them too far; you might say, "get too clever". HSE, last year, had too many nested macros; no doubt he can reference the thread if you're interested. One unexpected factor was that EXITM constituted a "nested macro".
It's not a bug, you just don't understand the beast well enough ;-D
Anyway, you are right: too much macros can overcomplicate the problem.
Quote from: rrr314159 on June 17, 2016, 01:15:45 AMI remember one happened using HLL statements with two terms "and"-ed together, in a complex series of .if statements. Fixed by putting them in two separate .if statements. Verified by debugging: the emitted code was wrong.
Could be possible, however, these are MASM statements and not macros (should be strictly separated IMO).
Quote from: rrr314159 on June 17, 2016, 01:15:45 AM
Consider the present OP where HSE's declarations are, apparently, being emitted in the wrong order if called 60 times, as he says. That's an excellent example. Even if there's some reason - "it's not a bug, it's a feature" - it sure feels like a bug when you run into it.
hard to say, because (at least for me) it not so clear what he want to do.
Quote from: HSE on June 17, 2016, 02:01:22 AM
Allowing most level macros in the compiler solved that problem
You problem can't express iterative? I've doubts on that.
qWord;
Was not clear, my fault. Last year problem, that rrr remember pretty well, was that compilers don't allow the number of macro levels when using SmplMath with ObjAsm32. For that thing, I use HJWasm modified with more macro levels. Very simple, not errors. (and not related with the question)
Quote from: HSE on June 17, 2016, 01:20:28 AM
In the way I define variables I obtein an array. The access to array demand calculation:
Here a plain Masm32 example. Note the imul instruction. With opattr, you could determine if index is a register or memory variable, to produce even more efficient code (this example stolen from the MasmBasic Dim (http://www.webalice.it/jj2006/MasmBasicQuickReference.htm#Mb1126) macro ;))
include \masm32\include\masm32rt.inc
FOOD STRUCT
prot REAL8 ?
fat REAL8 ?
water REAL8 ?
Ac REAL8 ?
Fa REAL8 ?
Bu REAL8 ?
FOOD ENDS
MyFood MACRO index, element
mov eax, index
imul eax, eax, FOOD
exitm <myfood.&element[eax]>
ENDM
.data?
myfood FOOD 20 dup(<>)
.code
start:
fld1 ; get a real number, 1 in this case
fstp MyFood(4, fat) ; store it as element 4, fat
fldpi ; get a real number
fstp MyFood(2, water) ; store it
printf("Food(2, water)=\t%f\n", MyFood(2, water))
printf("Food(4, fat)=\t%f\n", MyFood(4, fat))
exit
end start
Thanks JJ!
That will be usefull in a future step.
Meanwhile your program give me the idea to improve the access:
mov ecx,topebucle
iniloop1:
imul eax , ecx, 3
f2f [esi].integrales[ecx*8],[esi].modelo.firstinitial[eax*8]
dec ecx
jnl iniloop1