X-Git-Url: https://git.gag.com/?a=blobdiff_plain;f=as%2Fz80%2Fasexpr.c;h=f9bda739d79d6c9c3b0b41c1235225cbd78db8ae;hb=d292118ff0143ef2ae3848ac5f1353d95636c4a1;hp=2664550db4d31b42763ae8ef2cb8eaabcf85c05b;hpb=096bffb5e2bf6cfd2afe2b235d15120ec337d3b6;p=fw%2Fsdcc diff --git a/as/z80/asexpr.c b/as/z80/asexpr.c index 2664550d..f9bda739 100644 --- a/as/z80/asexpr.c +++ b/as/z80/asexpr.c @@ -1,13 +1,20 @@ -/* asexpr.c */ +/* asexpr.c -/* - * (C) Copyright 1989-1995 - * All Rights Reserved - * - * Alan R. Baldwin - * 721 Berkeley St. - * Kent, Ohio 44240 - */ + Copyright (C) 1989-1995 Alan R. Baldwin + 721 Berkeley St., Kent, Ohio 44240 + +This program is free software; you can redistribute it and/or modify it +under the terms of the GNU General Public License as published by the +Free Software Foundation; either version 3, or (at your option) any +later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program. If not, see . */ #include #include @@ -15,68 +22,68 @@ #include "asm.h" -/*)Module asexpr.c - * - * The module asexpr.c contains the routines to evaluate - * arithmetic/numerical expressions. The functions in - * asexpr.c perform a recursive evaluation of the arithmetic - * expression read from the assembler-source text line. - * The expression may include binary/unary operators, brackets, - * symbols, labels, and constants in hexadecimal, decimal, octal - * and binary. Arithmetic operations are prioritized and - * evaluated by normal arithmetic conventions. - * - * asexpr.c contains the following functions: - * VOID abscheck() - * Addr_T absexpr() - * VOID clrexpr() - * int digit() - * VOID expr() - * int oprio() - * VOID term() - * - * asexpr.c contains no local/static variables +/*)Module asexpr.c + * + * The module asexpr.c contains the routines to evaluate + * arithmetic/numerical expressions. The functions in + * asexpr.c perform a recursive evaluation of the arithmetic + * expression read from the assembler-source text line. + * The expression may include binary/unary operators, brackets, + * symbols, labels, and constants in hexadecimal, decimal, octal + * and binary. Arithmetic operations are prioritized and + * evaluated by normal arithmetic conventions. + * + * asexpr.c contains the following functions: + * VOID abscheck() + * Addr_T absexpr() + * VOID clrexpr() + * int digit() + * VOID expr() + * int oprio() + * VOID term() + * + * asexpr.c contains no local/static variables */ -/*)Function VOID expr(esp, n) - * - * expr * esp pointer to an expr structure - * int n a firewall priority; all top - * level calls (from the user) - * should be made with n set to 0. - * - * The function expr() evaluates an expression and - * stores its value and relocation information into - * the expr structure supplied by the user. - * - * local variables: - * int c current assembler-source - * text character - * int p current operator priority - * area * ap pointer to an area structure - * exp re internal expr structure - * - * global variables: - * char ctype[] array of character types, one per - * ASCII character - * - * functions called: - * VOID abscheck() asexpr.c - * VOID clrexpr() asexpr.c - * VOID expr() asexpr.c - * int getnb() aslex.c - * int oprio() asexpr.c - * VOID qerr() assubr.c - * VOID rerr() assubr.c - * VOID term() asexpr.c - * VOID unget() aslex.c - * - * - * side effects: - * An expression is evaluated modifying the user supplied - * expr structure, a sym structure maybe created for an - * undefined symbol, and the parse of the expression may - * terminate if a 'q' error occurs. +/*)Function VOID expr(esp, n) + * + * expr * esp pointer to an expr structure + * int n a firewall priority; all top + * level calls (from the user) + * should be made with n set to 0. + * + * The function expr() evaluates an expression and + * stores its value and relocation information into + * the expr structure supplied by the user. + * + * local variables: + * int c current assembler-source + * text character + * int p current operator priority + * area * ap pointer to an area structure + * exp re internal expr structure + * + * global variables: + * char ctype[] array of character types, one per + * ASCII character + * + * functions called: + * VOID abscheck() asexpr.c + * VOID clrexpr() asexpr.c + * VOID expr() asexpr.c + * int getnb() aslex.c + * int oprio() asexpr.c + * VOID qerr() assubr.c + * VOID rerr() assubr.c + * VOID term() asexpr.c + * VOID unget() aslex.c + * + * + * side effects: + * An expression is evaluated modifying the user supplied + * expr structure, a sym structure maybe created for an + * undefined symbol, and the parse of the expression may + * terminate if a 'q' error occurs. */ VOID @@ -90,31 +97,31 @@ int n; term(esp); while (ctype[c = getnb()] & BINOP) { - /* - * Handle binary operators + - * / & | % ^ << >> - */ + /* + * Handle binary operators + - * / & | % ^ << >> + */ if ((p = oprio(c)) <= n) break; if ((c == '>' || c == '<') && c != get()) qerr(); - clrexpr(&re); + clrexpr(&re); expr(&re, p); - esp->e_rlcf |= re.e_rlcf; + esp->e_rlcf |= re.e_rlcf; if (c == '+') { - /* - * esp + re, at least one must be absolute - */ + /* + * esp + re, at least one must be absolute + */ if (esp->e_base.e_ap == NULL) { - /* - * esp is absolute (constant), - * use area from re - */ + /* + * esp is absolute (constant), + * use area from re + */ esp->e_base.e_ap = re.e_base.e_ap; } else if (re.e_base.e_ap) { - /* - * re should be absolute (constant) - */ + /* + * re should be absolute (constant) + */ rerr(); } if (esp->e_flag && re.e_flag) @@ -124,9 +131,9 @@ int n; esp->e_addr += re.e_addr; } else if (c == '-') { - /* - * esp - re - */ + /* + * esp - re + */ if ((ap = re.e_base.e_ap) != NULL) { if (esp->e_base.e_ap == ap) { esp->e_base.e_ap = NULL; @@ -138,9 +145,9 @@ int n; rerr(); esp->e_addr -= re.e_addr; } else { - /* - * Both operands (esp and re) must be constants - */ + /* + * Both operands (esp and re) must be constants + */ abscheck(esp); abscheck(&re); switch (c) { @@ -177,35 +184,35 @@ int n; esp->e_addr >>= re.e_addr; break; - default: - qerr(); - break; + default: + qerr(); + break; } } } unget(c); } -/*)Function Addr_T absexpr() +/*)Function Addr_T absexpr() * - * The function absexpr() evaluates an expression, verifies it - * is absolute (i.e. not position dependent or relocatable), and - * returns its value. + * The function absexpr() evaluates an expression, verifies it + * is absolute (i.e. not position dependent or relocatable), and + * returns its value. * - * local variables: - * expr e expr structure + * local variables: + * expr e expr structure * - * global variables: - * none + * global variables: + * none * - * functions called: - * VOID abscheck() asexpr.c - * VOID clrexpr() asexpr.c - * VOID expr() asexpr.c + * functions called: + * VOID abscheck() asexpr.c + * VOID clrexpr() asexpr.c + * VOID expr() asexpr.c * - * side effects: - * If the expression is not absolute then - * a 'r' error is reported. + * side effects: + * If the expression is not absolute then + * a 'r' error is reported. */ Addr_T @@ -213,55 +220,55 @@ absexpr() { struct expr e; - clrexpr(&e); - expr(&e, 0); - abscheck(&e); - return (e.e_addr); + clrexpr(&e); + expr(&e, 0); + abscheck(&e); + return (e.e_addr); } -/*)Function VOID term(esp) - * - * expr * esp pointer to an expr structure - * - * The function term() evaluates a single constant - * or symbol value prefaced by any unary operator - * ( +, -, ~, ', ", >, or < ). This routine is also - * responsible for setting the relocation type to symbol - * based (e.flag != 0) on global references. - * - * local variables: - * int c current character - * char id[] symbol name - * char * jp pointer to assembler-source text - * int n constant evaluation running sum - * int r current evaluation radix - * sym * sp pointer to a sym structure - * tsym * tp pointer to a tsym structure - * int v current digit evaluation - * - * global variables: - * char ctype[] array of character types, one per - * ASCII character - * sym * symp pointer to a symbol structure - * - * functions called: - * VOID abscheck() asexpr.c - * int digit() asexpr.c - * VOID err() assubr.c - * VOID expr() asexpr.c - * int is_abs() asexpr.c - * int get() aslex.c - * VOID getid() aslex.c - * int getmap() aslex.c - * int getnb() aslex.c - * sym * lookup() assym.c - * VOID qerr() assubr.c - * VOID unget() aslex.c - * - * side effects: - * An arithmetic term is evaluated, a symbol structure - * may be created, term evaluation may be terminated - * by a 'q' error. +/*)Function VOID term(esp) + * + * expr * esp pointer to an expr structure + * + * The function term() evaluates a single constant + * or symbol value prefaced by any unary operator + * ( +, -, ~, ', ", >, or < ). This routine is also + * responsible for setting the relocation type to symbol + * based (e.flag != 0) on global references. + * + * local variables: + * int c current character + * char id[] symbol name + * char * jp pointer to assembler-source text + * int n constant evaluation running sum + * int r current evaluation radix + * sym * sp pointer to a sym structure + * tsym * tp pointer to a tsym structure + * int v current digit evaluation + * + * global variables: + * char ctype[] array of character types, one per + * ASCII character + * sym * symp pointer to a symbol structure + * + * functions called: + * VOID abscheck() asexpr.c + * int digit() asexpr.c + * VOID err() assubr.c + * VOID expr() asexpr.c + * int is_abs() asexpr.c + * int get() aslex.c + * VOID getid() aslex.c + * int getmap() aslex.c + * int getnb() aslex.c + * sym * lookup() assym.c + * VOID qerr() assubr.c + * VOID unget() aslex.c + * + * side effects: + * An arithmetic term is evaluated, a symbol structure + * may be created, term evaluation may be terminated + * by a 'q' error. */ VOID @@ -269,23 +276,23 @@ term(esp) register struct expr *esp; { register int c, n; - register char *jp; + register const char *jp; char id[NCPS]; struct sym *sp; struct tsym *tp; int r = 0, v; c = getnb(); - /* - * Discard the unary '+' at this point and - * also any reference to numerical arguments - * associated with the '#' prefix. - */ + /* + * Discard the unary '+' at this point and + * also any reference to numerical arguments + * associated with the '#' prefix. + */ while (c == '+' || c == '#') { c = getnb(); } - /* - * Evaluate all binary operators - * by recursively calling expr(). - */ + /* + * Evaluate all binary operators + * by recursively calling expr(). + */ if (c == LFTERM) { expr(esp, 0); if (getnb() != RTTERM) @@ -322,28 +329,28 @@ register struct expr *esp; } if (c == '>' || c == '<') { expr(esp, 100); - if (is_abs (esp)) { - /* - * evaluate msb/lsb directly - */ - if (c == '>') - esp->e_addr >>= 8; - esp->e_addr &= 0377; - return; - } else { - /* - * let linker perform msb/lsb, lsb is default - */ - esp->e_rlcf |= R_BYT2; - if (c == '>') - esp->e_rlcf |= R_MSB; - return; - } + if (is_abs (esp)) { + /* + * evaluate msb/lsb directly + */ + if (c == '>') + esp->e_addr >>= 8; + esp->e_addr &= 0377; + return; + } else { + /* + * let linker perform msb/lsb, lsb is default + */ + esp->e_rlcf |= R_BYT2; + if (c == '>') + esp->e_rlcf |= R_MSB; + return; + } } - /* - * Evaluate digit sequences as local symbols - * if followed by a '$' or as constants. - */ + /* + * Evaluate digit sequences as local symbols + * if followed by a '$' or as constants. + */ if (ctype[c] & DIGIT) { esp->e_mode = S_USER; jp = ip; @@ -409,57 +416,58 @@ register struct expr *esp; esp->e_addr = n; return; } - /* - * Evaluate '$' sequences as a temporary radix - * if followed by a '%', '&', '#', or '$'. - */ + /* + * Evaluate '$' sequences as a temporary radix + * if followed by a '%', '&', '#', or '$'. + */ if (c == '$') { c = get(); if (c == '%' || c == '&' || c == '#' || c == '$') { - switch (c) { - case '%': - r = 2; - break; - case '&': - r = 8; - break; - case '#': - r = 10; - break; - case '$': - r = 16; - break; - default: - break; - } - c = get(); - n = 0; - while ((v = digit(c, r)) >= 0) { - n = r*n + v; - c = get(); - } - unget(c); - esp->e_mode = S_USER; - esp->e_addr = n; - return; - } - unget(c); - c = '$'; + switch (c) { + case '%': + r = 2; + break; + case '&': + r = 8; + break; + case '#': + r = 10; + break; + case '$': + r = 16; + break; + default: + break; + } + c = get(); + n = 0; + while ((v = digit(c, r)) >= 0) { + n = r*n + v; + c = get(); + } + unget(c); + esp->e_mode = S_USER; + esp->e_addr = n; + return; + } + unget(c); + c = '$'; } - /* - * Evaluate symbols and labels - */ + /* + * Evaluate symbols and labels + */ if (ctype[c] & LETTER) { esp->e_mode = S_USER; getid(id, c); sp = lookup(id); if (sp->s_type == S_NEW) { - if (sp->s_flag&S_GBL) { - esp->e_flag = 1; - esp->e_base.e_sp = sp; - return; - } - err('u'); + esp->e_addr = 0; + if (sp->s_flag&S_GBL) { + esp->e_flag = 1; + esp->e_base.e_sp = sp; + return; + } + err('u'); } else { esp->e_mode = sp->s_type; esp->e_addr = sp->s_addr; @@ -467,33 +475,33 @@ register struct expr *esp; } return; } - /* - * Else not a term. - */ + /* + * Else not a term. + */ qerr(); } -/*)Function int digit(c, r) +/*)Function int digit(c, r) * - * int c digit character - * int r current radix + * int c digit character + * int r current radix * - * The function digit() returns the value of c - * in the current radix r. If the c value is not - * a number of the current radix then a -1 is returned. + * The function digit() returns the value of c + * in the current radix r. If the c value is not + * a number of the current radix then a -1 is returned. * - * local variables: - * none + * local variables: + * none * - * global variables: - * char ctype[] array of character types, one per - * ASCII character + * global variables: + * char ctype[] array of character types, one per + * ASCII character * - * functions called: - * none + * functions called: + * none * - * side effects: - * none + * side effects: + * none */ int @@ -524,31 +532,31 @@ register int c, r; return (-1); } -/*)Function VOID abscheck(esp) +/*)Function VOID abscheck(esp) * - * expr * esp pointer to an expr structure + * expr * esp pointer to an expr structure * - * The function abscheck() tests the evaluation of an - * expression to verify it is absolute. If the evaluation - * is relocatable then an 'r' error is noted and the expression - * made absolute. + * The function abscheck() tests the evaluation of an + * expression to verify it is absolute. If the evaluation + * is relocatable then an 'r' error is noted and the expression + * made absolute. * - * Note: The area type (i.e. ABS) is not checked because - * the linker can be told to explicitly relocate an - * absolute area. + * Note: The area type (i.e. ABS) is not checked because + * the linker can be told to explicitly relocate an + * absolute area. * - * local variables: - * none + * local variables: + * none * - * global variables: - * none + * global variables: + * none * - * functions called: - * VOID rerr() assubr.c + * functions called: + * VOID rerr() assubr.c * - * side effects: - * The expression may be changed to absolute and the - * 'r' error invoked. + * side effects: + * The expression may be changed to absolute and the + * 'r' error invoked. */ VOID @@ -562,29 +570,29 @@ register struct expr *esp; } } -/*)Function int is_abs(esp) +/*)Function int is_abs(esp) * - * expr * esp pointer to an expr structure + * expr * esp pointer to an expr structure * - * The function is_abs() tests the evaluation of an - * expression to verify it is absolute. If the evaluation - * is absolute then 1 is returned, else 0 is returned. + * The function is_abs() tests the evaluation of an + * expression to verify it is absolute. If the evaluation + * is absolute then 1 is returned, else 0 is returned. * - * Note: The area type (i.e. ABS) is not checked because - * the linker can be told to explicitly relocate an - * absolute area. + * Note: The area type (i.e. ABS) is not checked because + * the linker can be told to explicitly relocate an + * absolute area. * - * local variables: - * none + * local variables: + * none * - * global variables: - * none + * global variables: + * none * - * functions called: - * none + * functions called: + * none * - * side effects: - * none + * side effects: + * none */ int @@ -592,31 +600,31 @@ is_abs (esp) register struct expr *esp; { if (esp->e_flag || esp->e_base.e_ap) { - return(0); + return(0); } - return(1); + return(1); } -/*)Function int oprio(c) +/*)Function int oprio(c) * - * int c operator character + * int c operator character * - * The function oprio() returns a relative priority - * for all valid unary and binary operators. + * The function oprio() returns a relative priority + * for all valid unary and binary operators. * - * local variables: - * none + * local variables: + * none * - * global variables: - * none + * global variables: + * none * - * functions called: - * none + * functions called: + * none * - * side effects: - * none + * side effects: + * none */ - + int oprio(c) register int c; @@ -636,32 +644,32 @@ register int c; return (0); } -/*)Function VOID clrexpr(esp) +/*)Function VOID clrexpr(esp) * - * expr * esp pointer to expression structure + * expr * esp pointer to expression structure * - * The function clrexpr() clears the expression structure. + * The function clrexpr() clears the expression structure. * - * local variables: - * none + * local variables: + * none * - * global variables: - * none + * global variables: + * none * - * functions called: - * none + * functions called: + * none * - * side effects: - * expression structure cleared. + * side effects: + * expression structure cleared. */ - + VOID clrexpr(esp) register struct expr *esp; { - esp->e_mode = 0; - esp->e_flag = 0; - esp->e_addr = 0; - esp->e_base.e_ap = NULL; - esp->e_rlcf = 0; + esp->e_mode = 0; + esp->e_flag = 0; + esp->e_addr = 0; + esp->e_base.e_ap = NULL; + esp->e_rlcf = 0; }