gnupic: Re: [gnupic] More than one #v(expression) in a single line of a macro
Subject:
Re: [gnupic] More than one #v(expression) in a single line of a
macro
From:
Ben Dugan ####@####.####
Date:
8 Sep 2005 15:25:07 +0100
Message-Id: <432049B0.6080905@curdes.com>
Scott,
Thanks very much for your email. It provides some very helpful
explanation. I will give this some thought and I may get into trying to
make some changes, but I have to re-emphasize that this type of work is
really at the edge of my ability as a programmer. Recursion, in
particular, almost always confuses me, and it sounds like it would be
part of the solution in this case.
As I said in a post earlier today, I think I've found a work-around in
the assembly program I'm working on.
Ben
Scott Dattalo wrote:
> On Wed, 2005-09-07 at 09:35 -0400, Ben Dugan wrote:
>
> <snip> info about gpasm macro limitations.
>
>
>>Does anyone have a clever suggestion for a workaround, or do the
>>developers have any pointers about how I might, for example, tweak
>>scan.l to do this? (I was thinking a brute force approach might be to
>>add a #w(expression) "operator", but that's not very good.)
>
>
> Ben,
>
> I'm not an expert with Bison/Flex, but the real solution to gpasm macro
> problems lies there. The (or maybe 'a') proper way to tackle this problem
> is by introduce recursive parsing. This can be done by adding a new lexer
> state that is entered during the #v() processing. The idea here is that
> the #v() really needs to be evaluated when it is encountered, turned into
> a string (actually that's the result of the evaluation), and then fed back
> into yybuffer. The recursive aspect is that it's possible for an
> expression to be evaluated and recycled in the input stream multiple times
> until something stable eventually pops out. Your particular example,
> didn't involve recursion so it may be much simpler then what I am about to
> describe... but
>
> I recently solved a somewhat similar problem in gpsim's parser. Let me
> describe the problem and the solution and then maybe this can inspire you
> to tackle gpasm.
>
> gpsim supports parameterized macros. These are defined with the macro
> command. When a macro is defined, it's pretty much stored verbatim in a
> structure. The only parsing done is that the text names for the parameters
> are stored in a list separate from the text for the body. The only
> difficult part is that you have to differentiate text that is for a macro
> definition from text that is for a command that needs to be executed now.
> This is accomplished with a lexer state. A lexer state or mode defines how
> an incoming stream is to be lexed. In other words, it controls how the
> lexer should turn the input strings into tokens. A simple example could be
> something like a numeric string. In one mode it could be interpreted as a
> number where as in another it could be interpreted as an identifier. (This
> example is trivial and there are better ways of deciphering how a numeric
> string should be interpreted.) gpsim has a MACRO_BODY lexer mode to handle
> macro definitions.
>
> Expanding macros in gpsim is also a fairly straightforward process. When
> an identifier is encountered and recognized to be macro, then the macro
> arguments are stored in a list and the macro body along with its
> parameters are accessed for the macro expansion. During an expansion,
> unidentifiable identifiers (i.e. strings of text that are neither commands
> or symbols) are compared against the macro parameter list. If a match is
> found then the unidentified text is substituted with the invocation
> argument. The expansion process involves creating text and feeding it back
> into the lexer. One challenge here is that the normal input stream (i.e.
> the command line) has to be interrupted while the macro is being expanded.
> But the idea is that a single command line consisting of a macro
> invocation can turn into many gpsim commands that ultimately are fed back
> into the lexer.
>
> Macro definitions and expansions are relatively simple until you consider
> nested macro invocations. A nested macro invocation consists of a macro
> that references another macro. For example, you may create a "step and
> examine" macro to execute the step instruction N times and to examine the
> contents of a variable. The number of steps and the variable to examine
> are both parameters. Now you may also create the "run and examine macro"
> where this macro will set a break 1000 cycles into the future, call the
> "step and examine" macro, start running, and examine a variable when the
> simulation stops. The variable to be examined is a parameter to both
> macros. There are several challenges with nested macro invocations. First,
> while expanding a nested macro, the expansion state of the previous macro
> has to be saved. gpsim handles this with a macro invocation stack. Second,
> parameters for an outer invocation may be passed down as arguments to
> nested invocations. Again, the argument and parameter lists are saved in
> stacks.
>
> I'd say there are many challenges involved here: one is to identify if a
> new lexer state is even needed. Then if so, how are the input and output
> streams to be handled. Another related issue is how to manage input
> streams in the context of the current design. Fortunately Craig has
> created a regression test suite so you'll know when something breaks!
>
> I hope this helps.
>
> Scott
>
>
> ---------------------------------------------------------------------
> To unsubscribe, e-mail: ####@####.####
> For additional commands, e-mail: ####@####.####
>
>
>