diff --git a/ase/awk/awk.h b/ase/awk/awk.h index e627e5e4..1f4fd39b 100644 --- a/ase/awk/awk.h +++ b/ase/awk/awk.h @@ -1,5 +1,5 @@ /* - * $Id: awk.h,v 1.57 2006-04-24 11:36:12 bacon Exp $ + * $Id: awk.h,v 1.58 2006-04-26 15:49:33 bacon Exp $ */ #ifndef _XP_AWK_AWK_H_ @@ -74,6 +74,8 @@ enum XP_AWK_ECOMMA, /* comma expected */ XP_AWK_ESEMICOLON, /* semicolon expected */ XP_AWK_ECOLON, /* colon expected */ + XP_AWK_EIN, /* keyword 'in' is expected */ + XP_AWK_ENOTVAR, /* not a variable name after 'in' */ XP_AWK_EEXPRESSION, /* expression expected */ XP_AWK_EWHILE, /* keyword 'while' is expected */ diff --git a/ase/awk/err.c b/ase/awk/err.c index 4f16dd30..ee40ee77 100644 --- a/ase/awk/err.c +++ b/ase/awk/err.c @@ -1,5 +1,5 @@ /* - * $Id: err.c,v 1.15 2006-04-24 11:25:59 bacon Exp $ + * $Id: err.c,v 1.16 2006-04-26 15:49:33 bacon Exp $ */ #include @@ -39,6 +39,8 @@ const xp_char_t* xp_awk_geterrstr (xp_awk_t* awk) XP_TEXT("comma expected"), XP_TEXT("semicolon expected"), XP_TEXT("colon expected"), + XP_TEXT("keyword 'in' expected"), + XP_TEXT("not a variable after 'in'"), XP_TEXT("expression expected"), XP_TEXT("keyword 'while' expected"), diff --git a/ase/awk/misc.c b/ase/awk/misc.c index 014c3581..0e9ff0b8 100644 --- a/ase/awk/misc.c +++ b/ase/awk/misc.c @@ -1,5 +1,5 @@ /* - * $Id: misc.c,v 1.5 2006-04-16 04:31:38 bacon Exp $ + * $Id: misc.c,v 1.6 2006-04-26 15:49:33 bacon Exp $ */ #include @@ -122,11 +122,11 @@ xp_real_t xp_awk_strtoreal (const xp_char_t* str) * circumstatnces, it is the negative of the number of digits in F. * However, if I is very long, the last digits of I get dropped * (otherwise a long I with a large negative exponent could cause an - * unnecessary overflow on I alone). In this case, fracExp is + * unnecessary overflow on I alone). In this case, frac_exp is * incremented one for each dropped digit. */ - int fracExp = 0; + int frac_exp; int mantSize; /* Number of digits in mantissa. */ int decPt; /* Number of mantissa digits BEFORE decimal point */ const xp_char_t *pExp; /* Temporarily holds location of exponent in string */ @@ -176,20 +176,21 @@ xp_real_t xp_awk_strtoreal (const xp_char_t* str) { mantSize -= 1; /* One of the digits was the point */ } + if (mantSize > 18) { - fracExp = decPt - 18; + frac_exp = decPt - 18; mantSize = 18; } else { - fracExp = decPt - mantSize; + frac_exp = decPt - mantSize; } if (mantSize == 0) { fraction = 0.0; - p = str; + /*p = str;*/ goto done; } else @@ -248,8 +249,8 @@ xp_real_t xp_awk_strtoreal (const xp_char_t* str) } } - if (expSign) exp = fracExp - exp; - else exp = fracExp + exp; + if (expSign) exp = frac_exp - exp; + else exp = frac_exp + exp; /* * Generate a floating-point number that represents the exponent. diff --git a/ase/awk/parse.c b/ase/awk/parse.c index cd16d7fb..7fffec24 100644 --- a/ase/awk/parse.c +++ b/ase/awk/parse.c @@ -1,5 +1,5 @@ /* - * $Id: parse.c,v 1.92 2006-04-25 15:20:09 bacon Exp $ + * $Id: parse.c,v 1.93 2006-04-26 15:49:33 bacon Exp $ */ #include @@ -1332,13 +1332,68 @@ static xp_awk_nde_t* __parse_logical_and (xp_awk_t* awk) static xp_awk_nde_t* __parse_in (xp_awk_t* awk) { + /* __binmap_t map[] = { { TOKEN_IN, XP_AWK_BINOP_IN }, - { TOKEN_EOF, 0 } + { TOKEN_EOF, 0 } }; return __parse_binary_expr (awk, map, __parse_regex_match); + */ + + xp_awk_nde_exp_t* nde; + xp_awk_nde_t* left, * right; + + left = __parse_regex_match (awk); + if (left == XP_NULL) return XP_NULL; + + while (1) + { + if (!MATCH(awk,TOKEN_IN)) break; + + if (__get_token(awk) == -1) + { + xp_awk_clrpt (left); + return XP_NULL; + } + + right = __parse_regex_match (awk); + if (right == XP_NULL) + { + xp_awk_clrpt (left); + return XP_NULL; + } + + if (right->type != XP_AWK_NDE_NAMED && + right->type != XP_AWK_NDE_GLOBAL && + right->type != XP_AWK_NDE_LOCAL && + right->type != XP_AWK_NDE_ARG) + { + xp_awk_clrpt (right); + xp_awk_clrpt (left); + PANIC (awk, XP_AWK_ENOTVAR); + } + + nde = (xp_awk_nde_exp_t*) + xp_malloc (xp_sizeof(xp_awk_nde_exp_t)); + if (nde == XP_NULL) + { + xp_awk_clrpt (right); + xp_awk_clrpt (left); + PANIC (awk, XP_AWK_ENOMEM); + } + + nde->type = XP_AWK_NDE_EXP_BIN; + nde->next = XP_NULL; + nde->opcode = XP_AWK_BINOP_IN; + nde->left = left; + nde->right = right; + + left = (xp_awk_nde_t*)nde; + } + + return left; } static xp_awk_nde_t* __parse_regex_match (xp_awk_t* awk) @@ -1778,6 +1833,7 @@ static xp_awk_nde_t* __parse_primary (xp_awk_t* awk) else if (MATCH(awk,TOKEN_LPAREN)) { xp_awk_nde_t* nde; + xp_awk_nde_t* last; /* eat up the left parenthesis */ if (__get_token(awk) == -1) return XP_NULL; @@ -1786,6 +1842,33 @@ static xp_awk_nde_t* __parse_primary (xp_awk_t* awk) nde = __parse_expression (awk); if (nde == XP_NULL) return XP_NULL; +/* ---------------- */ + last = nde; + xp_assert (last->next == XP_NULL); + + while (MATCH(awk,TOKEN_COMMA)) + { + xp_awk_nde_t* tmp; + + if (__get_token(awk) == -1) + { + xp_awk_clrpt (nde); + return XP_NULL; + } + + tmp = __parse_expression (awk); + if (tmp == XP_NULL) + { + xp_awk_clrpt (nde); + return XP_NULL; + } + + xp_assert (tmp->next == XP_NULL); + last->next = tmp; + last = tmp; + } +/* ----------------- */ + /* check for the closing parenthesis */ if (!MATCH(awk,TOKEN_RPAREN)) { @@ -1799,6 +1882,32 @@ static xp_awk_nde_t* __parse_primary (xp_awk_t* awk) return XP_NULL; } +/* ----------------- */ + if (nde->next != XP_NULL) + { + xp_awk_nde_grp_t* tmp; + + if (!MATCH(awk,TOKEN_IN)) + { + xp_awk_clrpt (nde); + PANIC (awk, XP_AWK_EIN); + } + + tmp = (xp_awk_nde_grp_t*) xp_malloc (xp_sizeof(xp_awk_nde_grp_t)); + if (tmp == XP_NULL) + { + xp_awk_clrpt (nde); + PANIC (awk, XP_AWK_ENOMEM); + } + + tmp->type = XP_AWK_NDE_GRP; + tmp->next = XP_NULL; + tmp->body = nde; + + nde = tmp; + } +/* ----------------- */ + return nde; } @@ -2735,6 +2844,7 @@ static int __get_token (xp_awk_t* awk) return -1; } +xp_printf (XP_TEXT("token -> [%s]\n"), XP_STR_BUF(&awk->token.name)); return 0; } diff --git a/ase/awk/run.c b/ase/awk/run.c index d5b1dc68..38096ec2 100644 --- a/ase/awk/run.c +++ b/ase/awk/run.c @@ -1,5 +1,5 @@ /* - * $Id: run.c,v 1.75 2006-04-25 15:20:09 bacon Exp $ + * $Id: run.c,v 1.76 2006-04-26 15:49:33 bacon Exp $ */ #include @@ -865,8 +865,8 @@ static xp_awk_val_t* __eval_expression (xp_awk_run_t* run, xp_awk_nde_t* nde) static xp_awk_val_t* __eval_group (xp_awk_run_t* run, xp_awk_nde_t* nde) { - /* NOT INIMPELMETED YET */ -xp_printf (XP_TEXT("***** eval_group not implemented\n")); + /* in fact, this eval group would only be triggered by the operator in */ +xp_printf (XP_TEXT("***** eval_group NOT IMPLEMENTED\n")); PANIC (run, XP_AWK_EINTERNAL); return XP_NULL; } @@ -1134,7 +1134,6 @@ static xp_awk_val_t* __eval_binary (xp_awk_run_t* run, xp_awk_nde_t* nde) { __eval_binop_lor, __eval_binop_land, - __eval_binop_in, __eval_binop_bor, __eval_binop_bxor, __eval_binop_band, @@ -1156,6 +1155,7 @@ static xp_awk_val_t* __eval_binary (xp_awk_run_t* run, xp_awk_nde_t* nde) __eval_binop_mod, __eval_binop_exp, + __eval_binop_in, __eval_binop_ma, __eval_binop_nm }; @@ -1213,16 +1213,6 @@ static xp_awk_val_t* __eval_binop_land ( return res; } -static xp_awk_val_t* __eval_binop_in ( - xp_awk_run_t* run, xp_awk_val_t* left, xp_awk_val_t* right) -{ - /* TODO: */ - -xp_printf (XP_TEXT("***** __eval_binop_in not implemented yet\n")); - PANIC (run, XP_AWK_EINTERNAL); - return XP_NULL; -} - static xp_awk_val_t* __eval_binop_bor ( xp_awk_run_t* run, xp_awk_val_t* left, xp_awk_val_t* right) { @@ -1827,6 +1817,16 @@ static xp_awk_val_t* __eval_binop_exp ( return res; } +static xp_awk_val_t* __eval_binop_in ( + xp_awk_run_t* run, xp_awk_val_t* left, xp_awk_val_t* right) +{ + /* TODO: */ + +xp_printf (XP_TEXT("***** __eval_binop_in not implemented yet\n")); + PANIC (run, XP_AWK_EINTERNAL); + return XP_NULL; +} + static xp_awk_val_t* __eval_binop_ma ( xp_awk_run_t* run, xp_awk_val_t* left, xp_awk_val_t* right) { diff --git a/ase/awk/run.h b/ase/awk/run.h index 7f227848..71c79c21 100644 --- a/ase/awk/run.h +++ b/ase/awk/run.h @@ -1,5 +1,5 @@ /* - * $Id: run.h,v 1.11 2006-04-25 15:20:09 bacon Exp $ + * $Id: run.h,v 1.12 2006-04-26 15:49:33 bacon Exp $ */ #ifndef _XP_AWK_RUN_H_ @@ -27,7 +27,6 @@ enum * __binop_str in tree.c and __binop_func in run.c accordingly. */ XP_AWK_BINOP_LOR, XP_AWK_BINOP_LAND, - XP_AWK_BINOP_IN, XP_AWK_BINOP_BOR, XP_AWK_BINOP_BXOR, XP_AWK_BINOP_BAND, @@ -49,6 +48,7 @@ enum XP_AWK_BINOP_MOD, XP_AWK_BINOP_EXP, + XP_AWK_BINOP_IN, XP_AWK_BINOP_MA, XP_AWK_BINOP_NM }; diff --git a/ase/awk/tree.c b/ase/awk/tree.c index d9d558a8..db0c820e 100644 --- a/ase/awk/tree.c +++ b/ase/awk/tree.c @@ -1,5 +1,5 @@ /* - * $Id: tree.c,v 1.41 2006-04-24 14:38:46 bacon Exp $ + * $Id: tree.c,v 1.42 2006-04-26 15:49:33 bacon Exp $ */ #include @@ -46,6 +46,7 @@ static const xp_char_t* __binop_str[] = XP_TEXT("%"), XP_TEXT("**"), + XP_TEXT("in"), XP_TEXT("~"), XP_TEXT("!~") }; @@ -81,6 +82,20 @@ static int __print_expression (xp_awk_nde_t* nde) { switch (nde->type) { + case XP_AWK_NDE_GRP: + { + xp_awk_nde_t* p = ((xp_awk_nde_grp_t*)nde)->body; + + xp_printf (XP_TEXT("(")); + while (p != XP_NULL) { + __print_expression (p); + if (p->next != XP_NULL) xp_printf (XP_TEXT(",")); + p = p->next; + } + xp_printf (XP_TEXT(")")); + } + break; + case XP_AWK_NDE_ASS: if (__print_expression (((xp_awk_nde_ass_t*)nde)->left) == -1) return -1; xp_printf (XP_TEXT(" %s "), @@ -570,6 +585,11 @@ void xp_awk_clrpt (xp_awk_nde_t* tree) xp_free (p); break; + case XP_AWK_NDE_GRP: + xp_awk_clrpt (((xp_awk_nde_grp_t*)p)->body); + xp_free (p); + break; + case XP_AWK_NDE_ASS: xp_awk_clrpt (((xp_awk_nde_ass_t*)p)->left); xp_awk_clrpt (((xp_awk_nde_ass_t*)p)->right); diff --git a/ase/awk/tree.h b/ase/awk/tree.h index 4a121374..63dab1a3 100644 --- a/ase/awk/tree.h +++ b/ase/awk/tree.h @@ -1,5 +1,5 @@ /* - * $Id: tree.h,v 1.38 2006-04-24 15:34:52 bacon Exp $ + * $Id: tree.h,v 1.39 2006-04-26 15:49:33 bacon Exp $ */ #ifndef _XP_AWK_TREE_H_ @@ -109,7 +109,7 @@ struct xp_awk_nde_blk_t struct xp_awk_nde_grp_t { XP_AWK_NDE_HDR; - xp_awk_nde_t* head; + xp_awk_nde_t* body; }; /* XP_AWK_NDE_ASS - assignment */ diff --git a/ase/awk/val.h b/ase/awk/val.h index 550b71c1..18d70628 100644 --- a/ase/awk/val.h +++ b/ase/awk/val.h @@ -1,5 +1,5 @@ /* - * $Id: val.h,v 1.20 2006-04-24 11:22:42 bacon Exp $ + * $Id: val.h,v 1.21 2006-04-26 15:53:17 bacon Exp $ */ #ifndef _XP_AWK_VAL_H_ @@ -81,6 +81,10 @@ struct xp_awk_val_rex_t struct xp_awk_val_map_t { XP_AWK_VAL_HDR; + + /* TODO: make val_map to array if the indices used are all integers + * switch to map dynamically once the non-integral index is seen + */ xp_awk_map_t* map; };