flat assembler
Message board for the users of flat assembler.

Index > Main > Using macro 2+3/2-3*2 replace 2,3/2,3*2

Author
Thread Post new topic Reply to topic
Roman



Joined: 21 Apr 2012
Posts: 1763
Roman 14 Jul 2013, 15:03
Mn EQU 2+3/2-3*2

I need replace all + and - on comma. Using match and macros.


Mn EQU 2+3/2-3*2
after macro Mn = 2,3/2,3*2

And Mn may be of different lengths.
I mean Mn EQU 2+3/2-3*2 or Mn EQU 2+3/2-3*2-4+3/2-1

I encountered a problem. EQU work but work otherwise. If we write EQU in section IF. I mean in macro.
Quote:

macro La arg { Re EQU '123'
If `arg = `+
Re EQU '456'
end if
}


We all ways get Re EQU '456' ! How fixed this?


Last edited by Roman on 15 Jul 2013, 10:35; edited 2 times in total
Post 14 Jul 2013, 15:03
View user's profile Send private message Reply with quote
Roman



Joined: 21 Apr 2012
Posts: 1763
Roman 15 Jul 2013, 10:29
That no one knows how to do it?
Wow !
Shocked
Post 15 Jul 2013, 10:29
View user's profile Send private message Reply with quote
bitRAKE



Joined: 21 Jul 2003
Posts: 4016
Location: vpcmpistri
bitRAKE 15 Jul 2013, 11:20
l_inc posted something that is very close to your desired goal. Instead of displaying the values, they would need to be compared against your list of symbols, and alternate action taken in that case.
Code:
struc asComputationDestination {
  macro . [\.] \{ common match ==\\.,\. \\{ irps \\\.,\\. \\\{
        __out equ \\\.
        match +,\\\. \\\\{ restore __out
                           __out equ , \\\\}
        match -,\\\. \\\\{ restore __out
                           __out equ , \\\\}
        match \\\\.,__out \\\\{ display \\\\`\\\\. \\\\}
        restore __out
\\\} \\} \} }

x asComputationDestination
x = 20*10/20+1
display 13,10
x = 2+3/2-3*2
display 13,10
x = 2+3/2-3*2-4+3/2-1    
Twisted Evil

Despite this code looking gnarly, __out is the only part I've added. It either remains the current symbol, or is replaced by a comma.

_________________
¯\(°_o)/¯ “languages are not safe - uses can be” Bjarne Stroustrup
Post 15 Jul 2013, 11:20
View user's profile Send private message Visit poster's website Reply with quote
Roman



Joined: 21 Apr 2012
Posts: 1763
Roman 15 Jul 2013, 11:47
bitRAKE
Fantastic !
Thanks.

How you write this macro? How then can you understand that macro?
Post 15 Jul 2013, 11:47
View user's profile Send private message Reply with quote
Roman



Joined: 21 Apr 2012
Posts: 1763
Roman 15 Jul 2013, 11:59
bitRAKE
You macro cool !
But you macro display.
I need get (for example NewResult) NewResult EQU 2,3/2,3*2 and then i use NewResult in next steps of code.
I mean thats.
Post 15 Jul 2013, 11:59
View user's profile Send private message Reply with quote
bitRAKE



Joined: 21 Jul 2003
Posts: 4016
Location: vpcmpistri
bitRAKE 15 Jul 2013, 13:03
Code:
struc Parse0 [A] { common
  . equ
  irps B,A \{
    __out equ B
    match +,B \\{ restore __out
                  __out equ , \\}
    match -,B \\{ restore __out
                  __out equ , \\}
    match C,__out \\{
      match D,. \\\{
        restore .
        . equ D\\\#C
      \\\}
      match ,. \\\{
        restore .
        . equ C
      \\\}
    \\}
    restore __out
\} }

y Parse0 2+3/2-3*2-4+3/2-1
;  y EQU 2,3/2,3*2,4,3/2,1
; can even verify with previous macro
x = y Wink    
You help me understand because I try to help wherever I can. Read, read, read... Often I fail, and I try again. Then one day I see something I didn't see before.

The FASM manual is pretty good - read it a couple times; keep it open as a reference. Use the \FASM\TOOLS\* to see what happens behind the scenes. Little by little it will become clear.


Last edited by bitRAKE on 15 Jul 2013, 13:45; edited 2 times in total
Post 15 Jul 2013, 13:03
View user's profile Send private message Visit poster's website Reply with quote
Roman



Joined: 21 Apr 2012
Posts: 1763
Roman 15 Jul 2013, 13:13
bitRAKE Thanks !

Sorry. What is FASM\TOOLS ?
I never used FASM\TOOLS
Post 15 Jul 2013, 13:13
View user's profile Send private message Reply with quote
bitRAKE



Joined: 21 Jul 2003
Posts: 4016
Location: vpcmpistri
bitRAKE 15 Jul 2013, 13:36
I believe it's in the download.

LISTING
PREPSRC
SYMBOLS

Read here: http://board.flatassembler.net/topic.php?t=9792
Post 15 Jul 2013, 13:36
View user's profile Send private message Visit poster's website Reply with quote
l_inc



Joined: 23 Oct 2009
Posts: 881
l_inc 15 Jul 2013, 14:34
bitRAKE
Quote:
You help me understand because I try to help wherever I can. Read, read, read... Often I fail, and I try again. Then one day I see something I didn't see before.

Consider two things regarding your macro:
1) You're using the match directive extensively, even though it's not needed. Remember, that match and equ perform symbol expansion. Thus in the following case I would expect y to have the value var1*2, not var5*2 .
Code:
define var5 50
define var4 var5
define var3 var4
define var2 var3
define var1 var2
define exp1 var1*2

match x,exp1 { y Parse0 x }    

2) The concatenation operator is incorrectly used. No symbol concatenation is needed. This way the following code should give y the value "2 x" and not the value "2x":
Code:
define exp 2 x
match x,exp { y Parse0 x }    

_________________
Faith is a superposition of knowledge and fallacy
Post 15 Jul 2013, 14:34
View user's profile Send private message Reply with quote
bitRAKE



Joined: 21 Jul 2003
Posts: 4016
Location: vpcmpistri
bitRAKE 15 Jul 2013, 15:06
Feel free to provide a more general solution.
Post 15 Jul 2013, 15:06
View user's profile Send private message Visit poster's website Reply with quote
l_inc



Joined: 23 Oct 2009
Posts: 881
l_inc 15 Jul 2013, 15:22
bitRAKE
This one seems to be quite general:
Code:
;Allows to substitute one symbol in a list with another symbol
;usage: expression equsubs var2,var1,sqrt(var1)/var1*2+3
struc equsubs symnew, symold*, [arg]
{
        common
                restore .
                . equ
                res2 equ
                irps sym,arg
                \{
                        \forward
                                define res1 sym
                                match =symold, res1
                                \\{
                                        restore res1
                                        define res1 symnew
                                \\}
                        \forward
                                res2 equ res1 res2
                                restore res1
                        \common
                                restore .
                                . equ res2
                        \forward restore res2
                \}
                restore res2
}    

_________________
Faith is a superposition of knowledge and fallacy
Post 15 Jul 2013, 15:22
View user's profile Send private message Reply with quote
bitRAKE



Joined: 21 Jul 2003
Posts: 4016
Location: vpcmpistri
bitRAKE 15 Jul 2013, 16:00
Nice execution. Don't understand why the prior value of (.) should be lost though, but that's just me.
Post 15 Jul 2013, 16:00
View user's profile Send private message Visit poster's website Reply with quote
l_inc



Joined: 23 Oct 2009
Posts: 881
l_inc 15 Jul 2013, 17:22
bitRAKE
Quote:
Don't understand why the prior value of (.) should be lost though

That's for convenience. I don't like macro or constant stacks to arbitrarily accumulate. Kinda principle of least side effect. Thus every time a logical scope of a constant (or a macro) is closed it should be restored (or purged). For that reason it's easier to include restore into the constant transformation routines than to explicitly invoke restore each time a constant needs to be transformed:

Code:
;Allows to assign new value to a symbol without congesting it's stack
;usage: mysym equ 1
;               mysym reequ mysym,2
struc reequ [val]
{
        common
                tmp equ val
                        restore .
                        . equ tmp
                restore tmp
}

;Allows calculations with preprocessor
;usage: result equcalc 15/2 mod result
struc equcalc expr
{
        rept 1 res:expr
        \{
                restore .
                . equ res
        \}
}

;Finds the maximum value
;usage: max equmax 10,-15
struc equmax val1*, val2*
{
        rept 1 diff: ((val1)-(val2))
        \{
                restore .
                . equ val1
                match - any,diff
                \\{
                        restore .
                        . equ val2                      
                \\}
        \}
}

;Finds the minimum value
;usage: max equmin 10,-15
struc equmin val1*, val2*
{
        rept 1 diff: ((val1)-(val2))
        \{
                restore .
                . equ val2
                match - any,diff
                \\{
                        restore .
                        . equ val1
                \\}
        \}
}

;Allows to replicate the specified symbol a number of times
;with an optional delimiter
;usage: replication equdup 'hello',10,<#',',>
;               display replication
struc equdup val*, count*, delim
{
        tmp equ
        tmp equmax 1,count
        
        restore .
        . equ
        rept tmp-1 \{ . reequ . val delim \}
        rept 1 i:count \{ match =i,tmp \\{ . reequ . val \\} \}
        
        restore tmp
}

;Allows to concatenate values of the arguments
;usage: concatenation equcat x,y,z
;               concatenation:
struc equcat [arg]
{
        common
                tmp equ
        forward
                match val1,arg
                \{
                        match val0,tmp
                        \\{
                                restore tmp
                                define tmp val0\\#val1
                        \\}
                        match ,tmp
                        \\{
                                restore tmp
                                define tmp val1
                        \\}
                \}
        common
                        restore .
                        . equ tmp
                restore tmp
}

;and so on ...    


This approach also corresponds to the generally accepted requirement to define variable before using:
Code:
myvar1 equ 3                      ;define myvar1
myvar2 equ 2                      ;define myvar2
myvar1 equcalc myvar1*4
myvar2 equcalc myvar2*5

tmpvar equ myvar1                 ;define tmpvar
myvar1 equmin myvar1,myvar2
myvar2 equmax tmpvar,myvar2

lbl equ                           ;define lbl with dummy value
lbl equdup x,myvar1,<,_,>

        match x,lbl {
lbl equcat x,_,myvar2
        }

lbl:

restore myvar1,myvar2,tmpvar,lbl  ;destroy all constants

if defined x_x_x_x_x_x_x_x_x_x_12
        display 'We''ve just defined something completely useless',13,10
end if    

_________________
Faith is a superposition of knowledge and fallacy
Post 15 Jul 2013, 17:22
View user's profile Send private message Reply with quote
Roman



Joined: 21 Apr 2012
Posts: 1763
Roman 17 Jul 2013, 03:44
How to make a counter?
Example. We have V1 fix 2+1/2*3 and after using macro x Parse V1 we have x = 2,1/2*3
And need have count = 6. Number 6 is pointer to * befor 3.
If we do restore count we get count= 4 (Number 4 is pointer to / befor 2)
My code not work.
Quote:


rept 80 i:0 { Count equ i }
struc Parse [A] { common

. equ
irps B,A \{ restore Count
__out equ B
match +,B \\{ restore __out
restore Count
__out equ , \\}
match -,B \\{ restore __out
restore Count
__out equ , \\}
match C,__out \\{
match D,. \\\{ restore Count
restore .
. equ D\\\#C
\\\}
match ,. \\\{
restore .
. equ C
\\\}
\\}
restore __out
\} }
Post 17 Jul 2013, 03:44
View user's profile Send private message 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.