[net.lang] m4 macro processor experience

bob (01/26/83)

Regarding m4 and generated labels:

Since assemblers require labels and m4 is one way to make assemblers more
humane, the problem is to get m4 to generate labels within macro expansions
that do not conflict with each other, or with otherwise defined names.

The simplest approach is the following:

define(`lab_count',1)
define(`lab_gen',``L_'lab_count`'define(`lab_count',incr(lab_count)))

	a) `L_' is used to generate the prefix, which is conventional (mine),
	   and to separate it from the expansion of the macro lab_count.
	b) `' separates the word lab_count from the subsequent redefinition
	   of lab_count.
	c) the body of the interior define (incr(lab_count)) is not quoted
	   so that lab_count is incremented on each invocation of lab_gen.
Usage:
define(`MACRO',`define(`label1',lab_gen)define(`label2',lab_gen)
	body of macro
	jmp	label1
	body of macro
label1:
	jmp	label2
	body of macro
label2:
	end of macro')

Thus label1 and label2 are defined on entry to the macro as, for example,
L_1 and L_2.  On subsequent invocations, they will be given two other
successive names.

Caveats:
	No nested calls of MACRO can occur, since this would redefine
label1 and label2, causing mass confusion.
	Other macro definitions that use labels should have different names
so that they can be invoked from each other.
	Be very careful about quoting since m4 is not as consistent in
its quote-stripping conventions as gpm -- in fact, it more resembles [nt]roff.

The way to deal with the first problem is to create a two level macro
where the first level defines the labels and then passes them to the
second level as parameters, thus binding them until the second level
macro exits.

	Enjoy,
	Bob Dalgleish
	...!utah-cs!sask!dvlcn!bob