E.5 Using Labels with Macros

Regular labels throughout an entire program unit submitted to the assembler must be unique, in order that the assembler may refer to data locations or branch targets properly. Remember that regular labels begin with an alphabetic character (Section 3.5.2).

Since much of the utility of macros derives from being able to invoke any macro at multiple points, clearly any hard-coded regular labels defined by multiple expansions of a macro would be considered multiply defined by the assembler.

The temporary labels supported by the GCC assembler offer some ways around this problem of reconciling multiplicity and uniqueness. A given temporary label may occur multiple times in a program, but there is a rule ensuring a unique interpretation of which specific occurrence should be the target of any branch instruction. Remember that temporary labels take the form of small decimal numbers. Branching will seek out the nearest label representing a given number in the forward (e.g., 10f) or backward (e.g., 20b) direction (Section 5.5.4).

These provisions suggest that a macro could be defined with a label for the target of a conditional branch instruction required to construct an alternative:

 .macro  equal   PAR         addl    r14 = @gprel(\PAR),gp   // r14 -> \PAR         ld8     r15 = [r14]             // r15 = mem(\PAR)         cmp.ne  p6,p0 = r15,r0          // if \PAR ne 0         (p6)    br.cond.sptk 10f        //  then skip ahead         < what to do if \PAR = 0 > 10:     < what to do regardless of \PAR > .endm 

Then if the macro equal is invoked twice with different actual parameter for PAR:

 equal   DAT2 < possible intervening code > equal   DAT3 

the expansion will be of the form

         addl    r14 = @gprel(DAT2),gp   // r14 -> DAT2         ld8     r15 = [r14]             // r15 = mem(DAT2)         cmp.ne  p6,p0 = r15,r0          // if DAT2 ne 0         (p6)    br.cond.sptk 10f        //  then skip ahead         < what to do if DAT2 = 0 > 10:     < what to do regardless of DAT2 >         < possible intervening code >         addl    r14 = @gprel(DAT2),gp   // r14 -> DAT3         ld8     r15 = [r14]             // r15 = mem(DAT3)         cmp.ne  p6,p0 = r15,r0          // if DAT3 ne 0         (p6)    br.cond.sptk 10f        //  then skip ahead         < what to do if DAT3 = 0 > 10:     < what to do regardless of DAT3 > 

Since the temporary label 10 has been generated by the macro, the appropriate occurrence of it will be the one "closest" in the forward direction from the branch instruction.



ItaniumR Architecture for Programmers. Understanding 64-Bit Processors and EPIC Principles
ItaniumR Architecture for Programmers. Understanding 64-Bit Processors and EPIC Principles
ISBN: N/A
EAN: N/A
Year: 2003
Pages: 223

flylib.com © 2008-2017.
If you may any questions please contact us: flylib@qtcs.net