예제 #1
0
void PushTokList (TokList* List, const char* Desc)
/* Push a token list to be used as input for InputFromStack. This includes
 * several initializations needed in the token list structure, so don't use
 * PushInput directly.
 */
{
    /* If the list is empty, just delete it and bail out */
    if (List->Count == 0) {
	FreeTokList (List);
	return;
    }

    /* Reset the last pointer to the first element */
    List->Last = List->Root;

    /* Insert the list specifying our input function */
    PushInput (ReplayTokList, List, Desc);
}
예제 #2
0
static void StartExpDefine (MacExp* E)
/* Start expanding a DEFINE style macro */
{
    /* A define style macro must be called with as many actual parameters
     * as there are formal ones. Get the parameter count.
     */
    unsigned Count = E->M->ParamCount;

    /* Skip the current token */
    NextTok ();

    /* Read the actual parameters */
    while (Count--) {

        TokNode*   Last;

        /* The macro may optionally be enclosed in curly braces */
        token_t Term = GetTokListTerm (TOK_COMMA);

        /* Check if there is really a parameter */
        if (TokIsSep (CurTok.Tok) || CurTok.Tok == Term) {
            ErrorSkip ("Macro parameter #%u is empty", E->ParamCount+1);
            FreeMacExp (E);
            return;
        }

        /* Read tokens for one parameter */
        Last = 0;
        do {

            TokNode* T;

            /* Get the next token in a node */
            T = NewTokNode ();

            /* Insert it into the list */
            if (Last == 0) {
                E->Params [E->ParamCount] = T;
            } else {
                Last->Next = T;
            }
            Last = T;

            /* And skip it... */
            NextTok ();

        } while (CurTok.Tok != Term && !TokIsSep (CurTok.Tok));

        /* One parameter more */
        ++E->ParamCount;

        /* If the macro argument was enclosed in curly braces, end-of-line
         * is an error. Skip the closing curly brace.
         */
        if (Term == TOK_RCURLY) {
            if (TokIsSep (CurTok.Tok)) {
                Error ("End of line encountered within macro argument");
                break;
            }
            NextTok ();
        }

        /* Check for a comma */
        if (Count > 0) {
            if (CurTok.Tok == TOK_COMMA) {
                NextTok ();
            } else {
                Error ("`,' expected");
            }
        }
    }

    /* Macro expansion will overwrite the current token. This is a problem
     * for define style macros since these are called from the scanner level.
     * To avoid it, remember the current token and re-insert it, once macro
     * expansion is done.
     */
    E->Final = NewTokNode ();

    /* Insert a new token input function */
    PushInput (MacExpand, E, ".DEFINE");
}
예제 #3
0
static void StartExpClassic (MacExp* E)
/* Start expanding a classic macro */
{
    token_t     Term;

    /* Skip the macro name */
    NextTok ();

    /* Read the actual parameters */
    while (!TokIsSep (CurTok.Tok)) {

        TokNode* Last;

        /* Check for maximum parameter count */
        if (E->ParamCount >= E->M->ParamCount) {
            ErrorSkip ("Too many macro parameters");
            break;
        }

        /* The macro may optionally be enclosed in curly braces */
        Term = GetTokListTerm (TOK_COMMA);

        /* Read tokens for one parameter, accept empty params */
        Last = 0;
        while (CurTok.Tok != Term && CurTok.Tok != TOK_SEP) {

            TokNode* T;

            /* Check for end of file */
            if (CurTok.Tok == TOK_EOF) {
                Error ("Unexpected end of file");
                FreeMacExp (E);
                return;
            }

            /* Get the next token in a node */
            T = NewTokNode ();

            /* Insert it into the list */
            if (Last == 0) {
                E->Params [E->ParamCount] = T;
            } else {
                Last->Next = T;
            }
            Last = T;

            /* And skip it... */
            NextTok ();
        }

        /* One parameter more */
        ++E->ParamCount;

        /* If the macro argument was enclosed in curly braces, end-of-line
         * is an error. Skip the closing curly brace.
         */
        if (Term == TOK_RCURLY) {
            if (CurTok.Tok == TOK_SEP) {
                Error ("End of line encountered within macro argument");
                break;
            }
            NextTok ();
        }

        /* Check for a comma */
        if (CurTok.Tok == TOK_COMMA) {
            NextTok ();
        } else {
            break;
        }
    }

    /* We must be at end of line now, otherwise something is wrong */
    ExpectSep ();

    /* Insert a new token input function */
    PushInput (MacExpand, E, ".MACRO");
}