use strict; use warnings 'all'; do 'generate.pl'; our (@order, %ops); sub generate_output { for my $opname (@order) { my ($op) = $ops{$opname}; if (!$op->{OPTIMIZABLE} || $op->{UNIMPLEMENTED}) { print "case $opname:\n"; print " NOT_REACHED ();\n\n"; next; } my (@decls); my ($arg_idx) = 0; for my $arg (@{$op->{ARGS}}) { my ($decl); my ($name) = $arg->{NAME}; my ($type) = $arg->{TYPE}; my ($ctype) = c_type ($type); my ($idx) = $arg->{IDX}; if (!defined ($idx)) { my ($func) = "get_$type->{ATOM}_arg"; push (@decls, "${ctype}arg_$name = $func (node, $arg_idx)"); } else { my ($decl) = "size_t arg_$idx = node->arg_cnt"; $decl .= " - $arg_idx" if $arg_idx; push (@decls, $decl); push (@decls, "${ctype}*arg_$name = " . "get_$type->{ATOM}_args " . " (node, $arg_idx, arg_$idx, e)"); } $arg_idx++; } my ($sysmis_cond) = make_sysmis_decl ($op, "node->min_valid"); push (@decls, $sysmis_cond) if defined $sysmis_cond; my (@args); for my $arg (@{$op->{ARGS}}) { push (@args, "arg_$arg->{NAME}"); if (defined $arg->{IDX}) { my ($idx) = "arg_$arg->{IDX}"; $idx .= " / $arg->{TIMES}" if $arg->{TIMES} != 1; push (@args, $idx); } } for my $aux (@{$op->{AUX}}) { my ($type) = $aux->{TYPE}; if ($type->{ROLE} eq 'leaf') { my ($func) = "get_$type->{ATOM}_arg"; push (@args, "$func (node, $arg_idx)"); $arg_idx++; } elsif ($type->{ROLE} eq 'fixed') { push (@args, $type->{FIXED_VALUE}); } else { die; } } my ($result) = "eval_$op->{OPNAME} (" . join (', ', @args) . ")"; if (@decls && defined ($sysmis_cond)) { my ($miss_ret) = $op->{RETURNS}{MISSING_VALUE}; push (@decls, c_type ($op->{RETURNS}) . "result = " . "force_sysmis ? $miss_ret : $result"); $result = "result"; } print "case $opname:\n"; my ($alloc_func) = "expr_allocate_$op->{RETURNS}{NAME}"; if (@decls) { print " {\n"; print " $_;\n" foreach @decls; print " return $alloc_func (e, $result);\n"; print " }\n"; } else { print " return $alloc_func (e, $result);\n"; } print "\n"; } }