]> sourceware.org Git - systemtap.git/commitdiff
2005-08-09 Graydon Hoare <graydon@redhat.com>
authorgraydon <graydon>
Tue, 9 Aug 2005 18:17:24 +0000 (18:17 +0000)
committergraydon <graydon>
Tue, 9 Aug 2005 18:17:24 +0000 (18:17 +0000)
* 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.

ChangeLog
elaborate.cxx
elaborate.h
staptree.cxx
testsuite/buildok/eight.stp [new file with mode: 0755]
translate.cxx

index 0dd8e82f334a6b04effb8d3350e9cecb1a508906..ef39160d58f69edb8cbfb9bd736726e33c2cd9fe 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,20 @@
+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.
+
 2005-08-08  Roland McGrath  <roland@redhat.com>
 
        * loc2c-test.c: New file.
index 8adcc2a7811f786a19d15aac6cd7baa87a276132..c9f1fcd15acaaabcd402fa8448547895377623bb 100644 (file)
@@ -730,6 +730,45 @@ symresolution_info::visit_foreach_loop (foreach_loop* e)
   e->block->visit (this);
 }
 
+struct 
+delete_statement_symresolution_info:
+  public traversing_visitor
+{
+  symresolution_info *parent;
+
+  delete_statement_symresolution_info (symresolution_info *p):
+    parent(p)
+  {}
+
+  void visit_arrayindex (arrayindex* e)
+  {
+    parent->visit_arrayindex (e);
+  }
+  void visit_functioncall (functioncall* e)
+  {
+    parent->visit_functioncall (e);
+  }
+
+  void visit_symbol (symbol* e)
+  {
+    if (e->referent)
+      return;
+    
+    vardecl* d = parent->find_var (e->name, -1);
+    if (d)
+      e->referent = d;
+    else
+      throw semantic_error ("unresolved array in delete statement", e->tok);
+  }
+};
+
+void 
+symresolution_info::visit_delete_statement (delete_statement* s)
+{
+  delete_statement_symresolution_info di (this);
+  s->value->visit (&di);
+}
+
 
 void
 symresolution_info::visit_symbol (symbol* e)
@@ -807,7 +846,7 @@ symresolution_info::visit_functioncall (functioncall* e)
 
 
 vardecl* 
-symresolution_info::find_var (const string& name, unsigned arity)
+symresolution_info::find_var (const string& name, int arity)
 {
 
   // search locals
@@ -837,12 +876,12 @@ symresolution_info::find_var (const string& name, unsigned arity)
   // search processed globals
   for (unsigned i=0; i<session.globals.size(); i++)
     if (session.globals[i]->name == name
-       && session.globals[i]->compatible_arity(arity))
+       && session.globals[i]->compatible_arity(arity))  
       {
        session.globals[i]->set_arity (arity);
        return session.globals[i];
       }
-
+  
   // search library globals
   for (unsigned i=0; i<session.library_files.size(); i++)
     {
@@ -852,7 +891,7 @@ symresolution_info::find_var (const string& name, unsigned arity)
           vardecl* g = f->globals[j];
           if (g->name == name && g->compatible_arity (arity))
             {
-              g->set_arity (arity);
+             g->set_arity (arity);
               
               // put library into the queue if not already there           
               if (find (session.files.begin(), session.files.end(), f) 
@@ -1510,11 +1549,35 @@ typeresolution_info::visit_expr_statement (expr_statement* e)
 }
 
 
+struct delete_statement_typeresolution_info: 
+  public throwing_visitor
+{
+  typeresolution_info *parent;
+  delete_statement_typeresolution_info (typeresolution_info *p):
+    throwing_visitor ("invalid operand of delete expression"),
+    parent (p)
+  {}
+
+  void visit_arrayindex (arrayindex* e)
+  {
+    parent->visit_arrayindex (e);
+  }
+  
+  void visit_symbol (symbol* e)
+  {
+    exp_type ignored = pe_unknown;
+    assert (e->referent != 0);    
+    resolve_2types (e, e->referent, parent, ignored);
+  }
+};
+
+
 void
 typeresolution_info::visit_delete_statement (delete_statement* e)
 {
-  // XXX: not yet supported
-  unresolved (e->tok);
+  delete_statement_typeresolution_info di (this);
+  t = pe_unknown;
+  e->value->visit (&di);
 }
 
 
index 4b42e0bef113e558af09846736ccd1e4cbe5fc91..86da8b5158daba090e806e9009b3e0854a26f71c 100644 (file)
@@ -35,10 +35,8 @@ public:
 
   // XXX: instead in systemtap_session?
   void derive_probes (match_node * root, probe *p, std::vector<derived_probe*>& dps);
-
-protected:
   
-  vardecl* find_var (const std::string& name, unsigned arity);
+  vardecl* find_var (const std::string& name, int arity);
   functiondecl* find_function (const std::string& name, unsigned arity);
 
   void visit_block (block *s);
@@ -46,6 +44,7 @@ protected:
   void visit_foreach_loop (foreach_loop* e);
   void visit_arrayindex (arrayindex* e);
   void visit_functioncall (functioncall* e);
+  void visit_delete_statement (delete_statement* s);
 };
 
 
index b5a7ae49c73382c5ff9177ff348f6e6891c4d44e..31330017a025c775ffb5deeeb940900af1a73026 100644 (file)
@@ -106,7 +106,8 @@ vardecl::vardecl ():
 void
 vardecl::set_arity (int a)
 {
-  assert (a >= 0);
+  if (a < 0)
+    return;
 
   if (arity != a && arity >= 0)
     throw semantic_error ("inconsistent arity", tok);
@@ -123,7 +124,7 @@ vardecl::set_arity (int a)
 bool 
 vardecl::compatible_arity (int a)
 {
-  if (arity == -1)
+  if (arity == -1 || a == -1)
     return true;
   return arity == a;
 }
diff --git a/testsuite/buildok/eight.stp b/testsuite/buildok/eight.stp
new file mode 100755 (executable)
index 0000000..8439027
--- /dev/null
@@ -0,0 +1,10 @@
+#! stap -p4
+
+global foo
+
+probe begin {
+       foo[1] = 1
+       delete foo[1]
+       delete foo[foo[foo[foo[1]]]]
+       delete foo
+}
index 0bb56815448422911f470731f0c2079fb1f98c06..b013fc29158a677bb3fdd5fc6fb3d85cd732fe33 100644 (file)
@@ -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);
 }
 
 
This page took 0.054083 seconds and 5 git commands to generate.