From 59514868fde1190f719e78d4c4b91bd14a321541 Mon Sep 17 00:00:00 2001 From: "Arnold D. Robbins" Date: Fri, 20 Mar 2015 10:31:49 +0200 Subject: Start on testing/fixing indirect calls of builtins. --- builtin.c | 23 +++++++++++++++++++++++ 1 file changed, 23 insertions(+) (limited to 'builtin.c') diff --git a/builtin.c b/builtin.c index 1383572a..4dd08eb1 100644 --- a/builtin.c +++ b/builtin.c @@ -2994,6 +2994,29 @@ done: return make_number((AWKNUM) matches); } +/* call_sub_func --- call do_sub indirectly */ + +NODE * +call_sub_func(const char *name, int nargs) +{ + unsigned int flags = 0; + NODE *tmp; + + if (name[0] == 'g') { + if (name[1] == 'e') + flags = GENSUB; + else + flags = GSUB; + } + + tmp = PEEK(1); + if (tmp->type == Node_val) { + flags |= LITERAL; + } + + return do_sub(nargs, flags); +} + /* make_integer - Convert an integer to a number node. */ -- cgit v1.2.3 From 080694ae82635e76992158591b39a06af7363da0 Mon Sep 17 00:00:00 2001 From: "Arnold D. Robbins" Date: Tue, 24 Mar 2015 22:15:31 +0200 Subject: Further progress on indirect calls of builtins. --- builtin.c | 15 ++++++++++----- 1 file changed, 10 insertions(+), 5 deletions(-) (limited to 'builtin.c') diff --git a/builtin.c b/builtin.c index 4dd08eb1..7926a320 100644 --- a/builtin.c +++ b/builtin.c @@ -3000,7 +3000,7 @@ NODE * call_sub_func(const char *name, int nargs) { unsigned int flags = 0; - NODE *tmp; + NODE *regex, *replace; if (name[0] == 'g') { if (name[1] == 'e') @@ -3009,10 +3009,15 @@ call_sub_func(const char *name, int nargs) flags = GSUB; } - tmp = PEEK(1); - if (tmp->type == Node_val) { - flags |= LITERAL; - } + if ((flags == 0 || flags == GSUB) && nargs != 2) + fatal(_("%s: can be called indirectly only with two arguments"), name); + + replace = POP(); + + regex = POP(); /* the regex */ + regex = make_regnode(Node_regex, regex); + PUSH(regex); + PUSH(replace); return do_sub(nargs, flags); } -- cgit v1.2.3 From 2ee1a928483f4fe4f594aebc5c1f8da1253c28b9 Mon Sep 17 00:00:00 2001 From: "Arnold D. Robbins" Date: Tue, 31 Mar 2015 06:23:04 +0300 Subject: Further improvements. sub/gsub working. --- builtin.c | 66 ++++++++++++++++++++++++++++++++++++++++++++++++++++++--------- 1 file changed, 57 insertions(+), 9 deletions(-) (limited to 'builtin.c') diff --git a/builtin.c b/builtin.c index 7926a320..c222ce78 100644 --- a/builtin.c +++ b/builtin.c @@ -3000,7 +3000,10 @@ NODE * call_sub_func(const char *name, int nargs) { unsigned int flags = 0; - NODE *regex, *replace; + NODE *regex, *replace, *glob_flag; + NODE **lhs, *rhs; + NODE *zero = make_number(0.0); + NODE *result; if (name[0] == 'g') { if (name[1] == 'e') @@ -3009,17 +3012,62 @@ call_sub_func(const char *name, int nargs) flags = GSUB; } - if ((flags == 0 || flags == GSUB) && nargs != 2) - fatal(_("%s: can be called indirectly only with two arguments"), name); + if (flags == 0 || flags == GSUB) { + /* sub or gsub */ + if (nargs != 2) + fatal(_("%s: can be called indirectly only with two arguments"), name); - replace = POP(); + replace = POP_STRING(); + regex = POP(); /* the regex */ + /* + * push regex + * push replace + * push $0 + */ + regex = make_regnode(Node_regex, regex); + PUSH(regex); + PUSH(replace); + lhs = r_get_field(zero, (Func_ptr *) 0, true); + nargs++; + PUSH_ADDRESS(lhs); + } else { + /* gensub */ + if (nargs == 4) + rhs = POP(); + else + rhs = NULL; + glob_flag = POP_STRING(); + replace = POP_STRING(); + regex = POP(); /* the regex */ + /* + * push regex + * push replace + * push glob_flag + * if (nargs = 3) { + * push $0 + * nargs++ + * } + */ + regex = make_regnode(Node_regex, regex); + PUSH(regex); + PUSH(replace); + PUSH(glob_flag); + if (rhs == NULL) { + lhs = r_get_field(zero, (Func_ptr *) 0, true); + rhs = *lhs; + UPREF(rhs); + PUSH(rhs); + nargs++; + } + PUSH(rhs); + } - regex = POP(); /* the regex */ - regex = make_regnode(Node_regex, regex); - PUSH(regex); - PUSH(replace); - return do_sub(nargs, flags); + unref(zero); + result = do_sub(nargs, flags); + if (flags != GENSUB) + reset_record(); + return result; } -- cgit v1.2.3 From a47af3141cf4a6b43e20db872e2b45ff9abb071f Mon Sep 17 00:00:00 2001 From: "Arnold D. Robbins" Date: Tue, 31 Mar 2015 22:07:53 +0300 Subject: Get indirect calls working! --- builtin.c | 68 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++-- 1 file changed, 66 insertions(+), 2 deletions(-) (limited to 'builtin.c') diff --git a/builtin.c b/builtin.c index c222ce78..dde3121c 100644 --- a/builtin.c +++ b/builtin.c @@ -2994,10 +2994,10 @@ done: return make_number((AWKNUM) matches); } -/* call_sub_func --- call do_sub indirectly */ +/* call_sub --- call do_sub indirectly */ NODE * -call_sub_func(const char *name, int nargs) +call_sub(const char *name, int nargs) { unsigned int flags = 0; NODE *regex, *replace, *glob_flag; @@ -3070,6 +3070,70 @@ call_sub_func(const char *name, int nargs) return result; } +/* call_match --- call do_match indirectly */ + +NODE * +call_match(int nargs) +{ + NODE *regex, *text, *array; + NODE *result; + + regex = text = array = NULL; + if (nargs == 3) + array = POP(); + regex = POP(); + + /* Don't need to pop the string just to push it back ... */ + + regex = make_regnode(Node_regex, regex); + PUSH(regex); + + if (array) + PUSH(array); + + result = do_match(nargs); + return result; +} + +/* call_split_func --- call do_split or do_pat_split indirectly */ + +NODE * +call_split_func(const char *name, int nargs) +{ + NODE *regex, *seps; + NODE *result; + + regex = seps = NULL; + if (nargs < 2) + fatal(_("indirect call to %s requires at least two arguments"), + name); + + if (nargs == 4) + seps = POP(); + + if (nargs >= 3) { + regex = POP_STRING(); + regex = make_regnode(Node_regex, regex); + } else { + if (name[0] == 's') { + regex = make_regnode(Node_regex, FS_node->var_value); + regex->re_flags |= FS_DFLT; + } else + regex = make_regnode(Node_regex, FPAT_node->var_value); + nargs++; + } + + /* Don't need to pop the string or the data array */ + + PUSH(regex); + + if (seps) + PUSH(seps); + + result = (name[0] == 's') ? do_split(nargs) : do_patsplit(nargs); + + return result; +} /* make_integer - Convert an integer to a number node. */ -- cgit v1.2.3 From ddc290584b39bab2c1edcec935a31ea12d343246 Mon Sep 17 00:00:00 2001 From: "Arnold D. Robbins" Date: Fri, 3 Apr 2015 09:08:54 +0300 Subject: Rename "div()" to "intdiv()". --- builtin.c | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) (limited to 'builtin.c') diff --git a/builtin.c b/builtin.c index 99293b9a..b70176dc 100644 --- a/builtin.c +++ b/builtin.c @@ -3752,7 +3752,7 @@ do_bindtextdomain(int nargs) return make_string(the_result, strlen(the_result)); } -/* do_div --- do integer division, return quotient and remainder in dest array */ +/* do_intdiv --- do integer division, return quotient and remainder in dest array */ /* * We define the semantics as: @@ -3763,7 +3763,7 @@ do_bindtextdomain(int nargs) */ NODE * -do_div(int nargs) +do_intdiv(int nargs) { NODE *numerator, *denominator, *result; double num, denom, quotient, remainder; @@ -3771,7 +3771,7 @@ do_div(int nargs) result = POP_PARAM(); if (result->type != Node_var_array) - fatal(_("div: third argument is not an array")); + fatal(_("intdiv: third argument is not an array")); assoc_clear(result); denominator = POP_SCALAR(); @@ -3779,9 +3779,9 @@ do_div(int nargs) if (do_lint) { if ((numerator->flags & (NUMCUR|NUMBER)) == 0) - lintwarn(_("div: received non-numeric first argument")); + lintwarn(_("intdiv: received non-numeric first argument")); if ((denominator->flags & (NUMCUR|NUMBER)) == 0) - lintwarn(_("div: received non-numeric second argument")); + lintwarn(_("intdiv: received non-numeric second argument")); } (void) force_number(numerator); @@ -3790,7 +3790,7 @@ do_div(int nargs) denom = double_to_int(get_number_d(denominator)); if (denom == 0.0) - fatal(_("div: division by zero attempted")); + fatal(_("intdiv: division by zero attempted")); quotient = double_to_int(num / denom); /* -- cgit v1.2.3