pike.git/
src/
language.yacc
Branch:
Tag:
Non-build tags
All tags
No tags
2019-03-28
2019-03-28 10:53:43 by Henrik Grubbström (Grubba) <grubba@grubba.org>
65e0e161280a723f8f53d36f70256323520cac1e (
114
lines) (+
80
/-
34
)
[
Show
|
Annotate
]
Branch:
master
Compiler: Allow more constant expressions in inherit.
159:
#include "pike_embed.h" #include "opcodes.h" #include "operators.h"
+
#include "builtin_functions.h"
#include "bignum.h" #define YYMAXDEPTH 1000
426:
/* NOTE: This rule pushes a string "name" on the stack in addition * to resolving the program reference. */
-
low_program_ref:
string
_
constant
+
low_program_ref:
safe
_
expr0
{
-
+
node *n = $1;
+
STACK_LEVEL_START(0);
-
ref
_
push
_
string
($1->u.sval.u.
string
);
-
if (call_handle_inherit(
$1
-
>u
.
sval.
u.string)) {
+
while (n) {
+
switch (n->token) {
+
case F_EXTERNAL:
+
case F_GET_SET:
+
$$ = n;
+
add_
ref
(n);
+
free
_
node($1);
+
goto got
_
program_ref;
+
case F_APPLY:
+
{
+
if
(
(CAR(n)
->
token == F_CONSTANT) &&
+
(TYPEOF(CAR(n)->
u.sval
) == T_FUNCTION) &&
+
(SUBTYPEOF(CAR(n)->u
.
sval) == FUNCTION_BUILTIN) &&
+
(CAR(n)->
u.
sval.u.efun->function == debug_f_aggregate
)
) {
+
/* Disambiguate multiple inherit ::-reference. */
+
node *arg
;
+
while(1) {
+
while ((arg = CDR(n))) {
+
n = arg;
+
if (
n->token != F_ARG_LIST) goto found_program_ref;
+
}
+
/* Paranoia. */
+
if ((arg = CAR(n))) {
+
n = arg;
+
continue;
+
}
+
/* FIXME: Ought to go up a level and try the car there...
+
* But as this code probably won't be reached, we
+
* just fail.
+
*/
+
yyerror("Failed to get last argument from empty array.");
+
n = NULL;
+
break;
+
}
+
found_program_ref:
+
/* NB: The traditional C grammar requires a statement
+
* after a label.
+
*/
+
continue;
+
}
+
}
+
/* FALLTHRU */
+
default:
+
/* Evaluate the expression. */
+
break;
+
}
+
break;
+
}
+
+
resolv_constant(n);
+
free_node($1);
+
+
if (TYPEOF(Pike_sp[-1]) == T_STRING) {
+
if (
call_handle_inherit(
Pike_sp[
-
1]
.u.string)) {
STACK_LEVEL_CHECK(2);
-
$$=mksvaluenode(Pike_sp-1);
+
$$
=
mksvaluenode(Pike_sp-1);
pop_stack(); } else
-
$$=mknewintnode(0);
+
$$
=
mknewintnode(0);
STACK_LEVEL_CHECK(1); if($$->name) free_string($$->name); #ifdef PIKE_DEBUG
445:
Pike_fatal("Compiler lost track of program name.\n"); } #endif /* PIKE_DEBUG */
-
/* FIXME: Why not use $1->u.sval.u.string here? */
+
add_ref( $$->name=Pike_sp[-1].u.string );
-
free
_
node
(
$1
);
+
} else {
+
$$ = mksvaluenode(Pike
_
sp-1);
+
pop_stack
();
-
STACK
_
LEVEL
_
DONE(1);
-
}
-
|
idents
-
{
-
STACK_LEVEL_
START
(0);
-
-
if(Pike_compiler->last_identifier)
-
{
+
got
_
program
_
ref:
+
STACK_LEVEL_
CHECK
(0);
+
if
(Pike_compiler->last_identifier) {
ref_push_string(Pike_compiler->last_identifier);
-
}else{
+
} else {
push_empty_string(); }
-
$$=$1;
+
}
STACK_LEVEL_DONE(1); }
513:
pop_stack(); yyerror("Missing ';'."); }
-
| modifiers TOK_INHERIT error ';' { yyerrok; }
-
| modifiers TOK_INHERIT error TOK_LEX_EOF
-
{
-
yyerror("Missing ';'.");
-
yyerror("Unexpected end of file.");
-
}
-
| modifiers TOK_INHERIT error '}' { yyerror("Missing ';'."); }
+
; import: TOK_IMPORT constant_expr ';'