full macro

at genex
compile a full macro to CPX area first and set a reference to that address.  

    tkCOLON:			// define macro
        idx = cdr car e		// e = (name ex)
        currentf = idx
        e = item2 e
//	ads = CP
//	CP = CPX
//	setRef idx CP
        setRef idx e

//      if e != NIL
//          ypush MARK
//          genex e
//          cleanm idx
//          if (getType idx) == tyMAC
//              setRef idx e // set to parsetree
//      CPX = CP
//      CP = ads

cleanm is similar to clean

// for macro, may not be correct
to cleanm fn | i ref =
    ref = getRef fn
    patchbreak
    outa icEnd 0
    tailCall2 fn
    setEnd fn CP-1
    setRetv fn (findRet fn)

    // check if any assign local, full macro
    for i ref CP-1
        if XOP[i] == icPut
            setType fn tyFULL
            break

at domacro

// macro expansion
// should have special case for arity 1
// a full macro has been compiled and generated 
// to CPX
to domacro idx el | e a i op n first =
    if (getType idx) == tyMAC	   // simple macro
        e = subst (getRef idx) el  // subst body
        genex e
    else
        genlist el
        // extend current f locals
        first = getLv currentf
        setLv currentf first+(getLv idx)
        // pass param
        a = getArity idx
        for i 1 a
            outa icPut first+(a-i+1)
        // rename body
        i = getRef idx
        op = XOP[i]
        n = XARG[i]
        while op != icEnd
            if (isV op) n = first + n
            outa op n
            i = i + 1
            op = XOP[i]
            n = XARG[i]
// end

26 Aug 2007
