flat assembler
Message board for the users of flat assembler.

Index > Macroinstructions > restore: why?

Author
Thread Post new topic Reply to topic
gandalf



Joined: 27 Feb 2009
Posts: 31
gandalf 04 Apr 2009, 22:29
I don't know if this is the right section for this question.
I find the define-restore mechanism quite cumbersome.
I "cleaned" my parsing macros and now the code looks awkward:

a equ b

became

restore a
a equ b

and

a equ a b

became

tmp equ a b
restore a
a equ tmp
restore tmp

Is there a *direct* way to overwrite a symbol definition?
Post 04 Apr 2009, 22:29
View user's profile Send private message Reply with quote
revolution
When all else fails, read the source


Joined: 24 Aug 2004
Posts: 20299
Location: In your JS exploiting you and your system
revolution 05 Apr 2009, 00:50
gandalf wrote:
Is there a *direct* way to overwrite a symbol definition?
You can always overload
Code:
a equ 123
a equ 456
a equ 789    
But the original value of 'a' is now buried 4 deep in the equ 'stack'.
Post 05 Apr 2009, 00:50
View user's profile Send private message Visit poster's website Reply with quote
gandalf



Joined: 27 Feb 2009
Posts: 31
gandalf 05 Apr 2009, 09:39
revolution wrote:
gandalf wrote:
Is there a *direct* way to overwrite a symbol definition?
You can always overload
Code:
a equ 123
a equ 456
a equ 789    
But the original value of 'a' is now buried 4 deep in the equ 'stack'.


And what would I be complaining about, if not that very behavior?

But my question still stands: why?
If equ and define overwrote previous definitions and we could push values with some other directive it would be all much simpler. For compatibility reasons we could add overwriting versions of equ and define. User macros would still hurt performance: overwriting should be natively supported.
Post 05 Apr 2009, 09:39
View user's profile Send private message Reply with quote
revolution
When all else fails, read the source


Joined: 24 Aug 2004
Posts: 20299
Location: In your JS exploiting you and your system
revolution 05 Apr 2009, 10:12
Did you know this?
The define directive followed by the name of constant and then the value, is the alternative way of defining symbolic constant. The only difference between define and equ is that define assigns the value as it is, it does not replace the symbolic constants with their values inside it.
Post 05 Apr 2009, 10:12
View user's profile Send private message Visit poster's website Reply with quote
Tomasz Grysztar



Joined: 16 Jun 2003
Posts: 8351
Location: Kraków, Poland
Tomasz Grysztar 05 Apr 2009, 10:14
You'd hardly get any noticeable performance improvement by making them discard the previous values. It's the growing preprocessed source that eats your memory when you have thousands of those definitions (and this source is generated and kept anyway), the lookup tables contain just merely pointer to the content in the source. Preprocessor was designed with the restorable content in mind (exactly same goes with "purge"), so to gain anything from such idea you'd perhaps have to write another preprocessor.
Post 05 Apr 2009, 10:14
View user's profile Send private message Visit poster's website Reply with quote
Tomasz Grysztar



Joined: 16 Jun 2003
Posts: 8351
Location: Kraków, Poland
Tomasz Grysztar 05 Apr 2009, 10:15
revolution: I'm sure he already known the difference between "equ" and "define" - but the thing he's talking about is common to both of them (well, in fact it's common for all the preprocessor's entities).
Post 05 Apr 2009, 10:15
View user's profile Send private message Visit poster's website Reply with quote
revolution
When all else fails, read the source


Joined: 24 Aug 2004
Posts: 20299
Location: In your JS exploiting you and your system
revolution 05 Apr 2009, 10:18
This example led me to believe that gandalf might not have been aware of the define difference
Code:
a equ a b

became

tmp equ a b
restore a
a equ tmp
restore tmp    
Still, no harm on repeating info here I guess, someone else may not be aware of the difference.
Post 05 Apr 2009, 10:18
View user's profile Send private message Visit poster's website Reply with quote
Tomasz Grysztar



Joined: 16 Jun 2003
Posts: 8351
Location: Kraków, Poland
Tomasz Grysztar 05 Apr 2009, 10:40
The "define" wouldn't help him with this sample, I think. What he's trying to do is to make "a" have no stacked definitions, so he need to restore value of "a" before defining it with new value - and since the new value refers to "a" already, he needs temporary variable.

But, by the way: there is no point in doing "restore" unless you really need to get back the previous value - with fasm's preprocessor architecture you don't even gain any memory back by doing "restore".
Post 05 Apr 2009, 10:40
View user's profile Send private message Visit poster's website Reply with quote
revolution
When all else fails, read the source


Joined: 24 Aug 2004
Posts: 20299
Location: In your JS exploiting you and your system
revolution 05 Apr 2009, 11:01
Tomasz Grysztar wrote:
The "define" wouldn't help him with this sample, I think. What he's trying to do is to make "a" have no stacked definitions, so he need to restore value of "a" before defining it with new value - and since the new value refers to "a" already, he needs temporary variable.
Oh, yeah. I completely missed that on my first parse. Embarassed
Tomasz Grysztar wrote:
But, by the way: there is no point in doing "restore" unless you really need to get back the previous value - with fasm's preprocessor architecture you don't even gain any memory back by doing "restore".
Yeah, I clumsily tried to say the same thing in my first reply above.
Post 05 Apr 2009, 11:01
View user's profile Send private message Visit poster's website Reply with quote
gandalf



Joined: 27 Feb 2009
Posts: 31
gandalf 05 Apr 2009, 12:37
Tomasz Grysztar wrote:
You'd hardly get any noticeable performance improvement by making them discard the previous values. It's the growing preprocessed source that eats your memory when you have thousands of those definitions (and this source is generated and kept anyway), the lookup tables contain just merely pointer to the content in the source. Preprocessor was designed with the restorable content in mind (exactly same goes with "purge"), so to gain anything from such idea you'd perhaps have to write another preprocessor.


I use a few global definitions that are updated many times. Restoring them after many updates is not easy and what would happen if someone else were using them (i.e. symbols with the same names)?
Moreover (due to backtracking) I often need to restore definitions that have been updated many times. Calling restore many times would be cumbersome and not very efficient, I guess, so I save their old values somewhere and then restore them by writing back the old values.
Since these are user variables, I can't make them locals. Now how can the user restore them when he/she doesn't need them anymore?
With the "workaround" shown in the open post of this thread, the user may simply invoke restore once. Of course he can't invoke restore until the symbol is undefined because someone else could use the same symbol. He/she might use a unique name to mark the exact point where she must stop restoring the symbols, but that's awkward, IMHO.
A write-without-pushing directive would make my code much simpler and slightly more efficient because 20% shorter.

EDIT: Maybe I might just use a simple macro... (wequ?) But wouldn't it hurt performance a little too much?
Post 05 Apr 2009, 12:37
View user's profile Send private message Reply with quote
revolution
When all else fails, read the source


Joined: 24 Aug 2004
Posts: 20299
Location: In your JS exploiting you and your system
revolution 05 Apr 2009, 12:48
I think if you can show a really useful practical example of your parsing macros that can't be done in another way then there might be a case to introduce a new directive into fasm. But right now it looks like they are just a curiosity (but still a nice example if some techniques) and there is no need to make new directives just yet.

BTW: What would you suggest the name for such a new directive would be?
Post 05 Apr 2009, 12:48
View user's profile Send private message Visit poster's website Reply with quote
revolution
When all else fails, read the source


Joined: 24 Aug 2004
Posts: 20299
Location: In your JS exploiting you and your system
revolution 05 Apr 2009, 12:50
gandalf wrote:
But wouldn't it hurt performance a little too much?
Is performance really the issue here? How much time is saved/lost?
Post 05 Apr 2009, 12:50
View user's profile Send private message Visit poster's website Reply with quote
Tomasz Grysztar



Joined: 16 Jun 2003
Posts: 8351
Location: Kraków, Poland
Tomasz Grysztar 05 Apr 2009, 13:29
gandalf wrote:
I use a few global definitions that are updated many times. Restoring them after many updates is not easy and what would happen if someone else were using them (i.e. symbols with the same names)?

The same problem applies to all the macros that use some global variables - I usually use the name@package name form, which is very unlikely to be used elsewhere.

As for restoring the definitions that are updated frequently: what do you need to restore them for? If you really need the original value, then store it in some other variable at startup.
Post 05 Apr 2009, 13:29
View user's profile Send private message Visit poster's website Reply with quote
gandalf



Joined: 27 Feb 2009
Posts: 31
gandalf 05 Apr 2009, 14:35
Tomasz Grysztar wrote:

The same problem applies to all the macros that use some global variables - I usually use the name@package name form, which is very unlikely to be used elsewhere.


That's not a very safe solution (it reminds me of TeX and all its problems when it grew up).

Tomasz Grysztar wrote:

As for restoring the definitions that are updated frequently: what do you need to restore them for? If you really need the original value, then store it in some other variable at startup.


That's exactly what I did before. But now my code is much cleaner.
Every macro overwrites/returns "output" variables and any other modifications are transient. That way, if the user wants to preserve a definition, say curExpr, they just write:
curExpr equ ; dummy value
matchExpr ; overwrites curExpr
restore curExpr
This way, if they need to make incremental parsing, they can call the parsing macros as many times as they want:
curExpr equ ; dummy value
matchExpr ; overwrites curExpr
readAnd readSymbol, ..... ; etc...
readOr .......
restore curExpr
and still be able to restore everything with a single restore.
It also makes my code easier to write, if not more elegant.
I just hoped there was another way (of doing the *same* thing).
Post 05 Apr 2009, 14:35
View user's profile Send private message Reply with quote
Madis731



Joined: 25 Sep 2003
Posts: 2139
Location: Estonia
Madis731 05 Apr 2009, 17:36
...maybe FASM 2.0 Razz
Post 05 Apr 2009, 17:36
View user's profile Send private message Visit poster's website Yahoo Messenger MSN Messenger Reply with quote
gandalf



Joined: 27 Feb 2009
Posts: 31
gandalf 05 Apr 2009, 18:26
revolution wrote:
gandalf wrote:
But wouldn't it hurt performance a little too much?
Is performance really the issue here? How much time is saved/lost?


I think a macro expansion for every single equ would hurt performance and waste memory. I don't know how much, though.
Post 05 Apr 2009, 18:26
View user's profile Send private message Reply with quote
Tomasz Grysztar



Joined: 16 Jun 2003
Posts: 8351
Location: Kraków, Poland
Tomasz Grysztar 05 Apr 2009, 20:59
gandalf wrote:
That's not a very safe solution (it reminds me of TeX and all its problems when it grew up).

Well, you have to reserve some names anyway - even the names of your macro get reserved this way (what if someone already had a macro called the same as one of your macros?). I don't see anything unusal here.


gandalf wrote:
That's exactly what I did before. But now my code is much cleaner.
Every macro overwrites/returns "output" variables and any other modifications are transient. That way, if the user wants to preserve a definition, say curExpr, they just write:
curExpr equ ; dummy value
matchExpr ; overwrites curExpr
restore curExpr

So it would be enough to use some other variable internally, and assign value to "curExpr" just once in your macro - so that you have separate internal "working" variable (which you can even define as local to macro, and this way ensure no name conflicts will arise at all), and separate official external interface variable for output.
Post 05 Apr 2009, 20:59
View user's profile Send private message Visit poster's website Reply with quote
gandalf



Joined: 27 Feb 2009
Posts: 31
gandalf 06 Apr 2009, 10:01
Tomasz Grysztar wrote:
gandalf wrote:
That's not a very safe solution (it reminds me of TeX and all its problems when it grew up).

Well, you have to reserve some names anyway - even the names of your macro get reserved this way (what if someone already had a macro called the same as one of your macros?). I don't see anything unusal here.


That's true. The user should be able to use conflicting macros without modifying too much code. Maybe one might just "parametrize" the package name. When not needed, the package name would be blank, otherwise "<package>@".

Tomasz Grysztar wrote:

So it would be enough to use some other variable internally, and assign value to "curExpr" just once in your macro - so that you have separate internal "working" variable (which you can even define as local to macro, and this way ensure no name conflicts will arise at all), and separate official external interface variable for output.


Yes, it would be enough, but I hoped to save memory (it increased instead, as you predicted). What I don't know is whether or not FASM does all the expansions BEFOREHAND. If I invoke the same macro 1000 times does the final code contain 1000 expansions of that macro???
Post 06 Apr 2009, 10:01
View user's profile Send private message Reply with quote
Tomasz Grysztar



Joined: 16 Jun 2003
Posts: 8351
Location: Kraków, Poland
Tomasz Grysztar 06 Apr 2009, 10:03
gandalf wrote:
If I invoke the same macro 1000 times does the final code contain 1000 expansions of that macro???
Yes, exactly. This is the main "memory eater" here.
Post 06 Apr 2009, 10:03
View user's profile Send private message Visit poster's website Reply with quote
Display posts from previous:
Post new topic Reply to topic

Jump to:  


< Last Thread | Next Thread >
Forum Rules:
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum
You cannot attach files in this forum
You can download files in this forum


Copyright © 1999-2024, Tomasz Grysztar. Also on GitHub, YouTube.

Website powered by rwasa.