diff options
author | graydon <graydon> | 2005-08-09 18:17:24 +0000 |
---|---|---|
committer | graydon <graydon> | 2005-08-09 18:17:24 +0000 |
commit | d98d459c440fb476869b34a84bb8a75d28fbb188 (patch) | |
tree | 592d6ab998b1bab7c3d67ea23272884f78fc8860 /translate.cxx | |
parent | debd8982950caa54b27944775910dd282b82b338 (diff) | |
download | systemtap-steved-d98d459c440fb476869b34a84bb8a75d28fbb188.tar.gz systemtap-steved-d98d459c440fb476869b34a84bb8a75d28fbb188.tar.xz systemtap-steved-d98d459c440fb476869b34a84bb8a75d28fbb188.zip |
2005-08-09 Graydon Hoare <graydon@redhat.com>
* elaborate.cxx:
(delete_statement_symresolution_info): New struct.
(symresolution_info::visit_delete_statement): Use it.
(delete_statement_typeresolution_info): New struct.
(typeresolution_info::visit_delete_statement): Use it.
(symresolution_info::find_var): Accept -1 as 'unknown' arity.
* elaborate.h: Update to reflect changes in .cxx.
* translate.cxx (mapvar::del): New method.
(c_unparser::getmap): Check arity >= 1;
(delete_statement_operand_visitor): New struct.
(c_unparser::visit_delete_statement): Use it.
* staptree.cxx (vardecl::set_arity): Accept and ignore -1.
(vardecl::compatible_arity): Likewise.
* testsuite/buildok/eight.stp: New test for 'delete' operator.
Diffstat (limited to 'translate.cxx')
-rw-r--r-- | translate.cxx | 48 |
1 files changed, 46 insertions, 2 deletions
diff --git a/translate.cxx b/translate.cxx index 0bb56815..b013fc29 100644 --- a/translate.cxx +++ b/translate.cxx @@ -327,6 +327,11 @@ struct mapvar static string key_typename(exp_type e); static string value_typename(exp_type e); + string del () const + { + return "_stp_map_key_del (" + qname() + ")"; + } + string seek (vector<tmpvar> const & indices) const { string result = "_stp_map_key" + mangled_indices() + " ("; @@ -1203,7 +1208,9 @@ c_unparser::getvar(vardecl *v, token const *tok) mapvar c_unparser::getmap(vardecl *v, token const *tok) -{ +{ + if (v->arity < 1) + throw new semantic_error("attempt to use scalar where map expected", tok); return mapvar (is_local (v, tok), v->type, v->name, v->index_types); } @@ -1380,10 +1387,47 @@ c_unparser::visit_next_statement (next_statement* s) } +struct delete_statement_operand_visitor: + public throwing_visitor +{ + c_unparser *parent; + delete_statement_operand_visitor (c_unparser *p): + throwing_visitor ("invalid operand of delete expression"), + parent (p) + {} + void visit_symbol (symbol* e); + void visit_arrayindex (arrayindex* e); +}; + +void +delete_statement_operand_visitor::visit_symbol (symbol* e) +{ + mapvar mvar = parent->getmap(e->referent, e->tok); + varlock guard (*parent, mvar); + parent->o->newline() << mvar.fini (); + parent->o->newline() << mvar.init (); +} + +void +delete_statement_operand_visitor::visit_arrayindex (arrayindex* e) +{ + vector<tmpvar> idx; + parent->load_map_indices (e, idx); + parent->o->newline() << "if (unlikely (c->errorcount)) goto out;"; + { + mapvar mvar = parent->getmap (e->referent, e->tok); + varlock guard (*parent, mvar); + parent->o->newline() << mvar.seek (idx) << ";"; + parent->o->newline() << mvar.del () << ";"; + } +} + + void c_unparser::visit_delete_statement (delete_statement* s) { - throw semantic_error ("delete statement not yet implemented", s->tok); + delete_statement_operand_visitor dv (this); + s->value->visit (&dv); } |