Merge pull request #1844 from jrw972/monterey
[ACE_TAO.git] / TAO / TAO_IDL / ast / ast_visitor_reifying.cpp
blobbfece5f5e12bbdcb5f7766542a3a9175b711deaf
1 /**
2 * @file ast_visitor_reifying.cpp
4 * @author Jeff Parsons
5 */
6 //=============================================================================
8 #include "ast_visitor_reifying.h"
9 #include "ast_visitor_context.h"
10 #include "ast_generator.h"
12 #include "ast_interface.h"
13 #include "ast_valuetype.h"
14 #include "ast_valuebox.h"
15 #include "ast_eventtype.h"
16 #include "ast_connector.h"
17 #include "ast_home.h"
18 #include "ast_exception.h"
19 #include "ast_typedef.h"
20 #include "ast_array.h"
21 #include "ast_sequence.h"
22 #include "ast_union.h"
23 #include "ast_enum.h"
24 #include "ast_predefined_type.h"
25 #include "ast_string.h"
26 #include "ast_constant.h"
27 #include "ast_native.h"
28 #include "ast_param_holder.h"
29 #include "ast_template_module.h"
31 #include "utl_identifier.h"
32 #include "utl_exprlist.h"
33 #include "utl_strlist.h"
34 #include "utl_string.h"
35 #include "nr_extern.h"
37 ast_visitor_reifying::ast_visitor_reifying (
38 ast_visitor_context *ctx)
39 : ast_visitor (),
40 ctx_ (ctx),
41 reified_node_ (0)
45 ast_visitor_reifying::~ast_visitor_reifying (void)
49 AST_Decl *
50 ast_visitor_reifying::reified_node (void) const
52 return this->reified_node_;
55 int ast_visitor_reifying::visit_decl (AST_Decl *)
57 return 0;
60 int
61 ast_visitor_reifying::visit_scope (UTL_Scope *)
63 return 0;
66 int
67 ast_visitor_reifying::visit_type (AST_Type *)
69 return 0;
72 int
73 ast_visitor_reifying::visit_module (AST_Module *)
75 return 0;
78 int
79 ast_visitor_reifying::visit_interface_fwd (AST_InterfaceFwd *)
81 return 0;
84 int
85 ast_visitor_reifying::visit_valuebox (AST_ValueBox *node)
87 this->check_and_store (node);
88 return 0;
91 int
92 ast_visitor_reifying::visit_valuetype_fwd (AST_ValueTypeFwd *)
94 return 0;
97 int
98 ast_visitor_reifying::visit_eventtype_fwd (AST_EventTypeFwd *)
100 return 0;
104 ast_visitor_reifying::visit_component_fwd (AST_ComponentFwd *)
106 return 0;
110 ast_visitor_reifying::visit_template_module (AST_Template_Module *)
112 return 0;
116 ast_visitor_reifying::visit_template_module_inst (AST_Template_Module_Inst *)
118 return 0;
122 ast_visitor_reifying::visit_template_module_ref (AST_Template_Module_Ref *)
124 return 0;
128 ast_visitor_reifying::visit_porttype (AST_PortType *node)
130 this->check_and_store (node);
131 return 0;
135 ast_visitor_reifying::visit_provides (AST_Provides *)
137 return 0;
141 ast_visitor_reifying::visit_uses (AST_Uses *)
143 return 0;
147 ast_visitor_reifying::visit_publishes (AST_Publishes *)
149 return 0;
153 ast_visitor_reifying::visit_emits (AST_Emits *)
155 return 0;
159 ast_visitor_reifying::visit_consumes (AST_Consumes *)
161 return 0;
165 ast_visitor_reifying::visit_extended_port (AST_Extended_Port *)
167 return 0;
171 ast_visitor_reifying::visit_mirror_port (AST_Mirror_Port *)
173 return 0;
177 ast_visitor_reifying::visit_connector (AST_Connector *node)
179 this->check_and_store (node);
180 return 0;
184 ast_visitor_reifying::visit_home (AST_Home *node)
186 this->check_and_store (node);
187 return 0;
191 ast_visitor_reifying::visit_factory (AST_Factory *)
193 return 0;
197 ast_visitor_reifying::visit_finder (AST_Finder *)
199 return 0;
203 ast_visitor_reifying::visit_structure (AST_Structure *node)
205 this->check_and_store (node);
206 return 0;
210 ast_visitor_reifying::visit_structure_fwd (AST_StructureFwd *)
212 return 0;
216 ast_visitor_reifying::visit_expression (AST_Expression *)
218 return 0;
222 ast_visitor_reifying::visit_enum (AST_Enum *node)
224 this->check_and_store (node);
225 return 0;
229 ast_visitor_reifying::visit_operation (AST_Operation *)
231 return 0;
235 ast_visitor_reifying::visit_field (AST_Field *)
237 return 0;
241 ast_visitor_reifying::visit_argument (AST_Argument *)
243 return 0;
247 ast_visitor_reifying::visit_attribute (AST_Attribute *)
249 return 0;
253 ast_visitor_reifying::visit_union (AST_Union *node)
255 this->check_and_store (node);
256 return 0;
260 ast_visitor_reifying::visit_union_fwd (AST_UnionFwd *)
262 return 0;
266 ast_visitor_reifying::visit_union_branch (AST_UnionBranch *)
268 return 0;
272 ast_visitor_reifying::visit_union_label (AST_UnionLabel *)
274 return 0;
278 ast_visitor_reifying::visit_enum_val (AST_EnumVal *)
280 return 0;
284 ast_visitor_reifying::visit_root (AST_Root *)
286 return 0;
290 ast_visitor_reifying::visit_native (AST_Native *node)
292 this->check_and_store (node);
293 return 0;
297 ast_visitor_reifying::visit_interface (AST_Interface *node)
299 this->check_and_store (node);
300 return 0;
304 ast_visitor_reifying::visit_valuetype (AST_ValueType *node)
306 this->check_and_store (node);
307 return 0;
311 ast_visitor_reifying::visit_eventtype (AST_EventType *node)
313 this->check_and_store (node);
314 return 0;
318 ast_visitor_reifying::visit_component (AST_Component *node)
320 this->check_and_store (node);
321 return 0;
325 ast_visitor_reifying::visit_exception (AST_Exception *node)
327 this->check_and_store (node);
328 return 0;
332 ast_visitor_reifying::visit_typedef (AST_Typedef *node)
334 this->check_and_store (node);
335 return 0;
339 ast_visitor_reifying::visit_array (AST_Array *node)
341 AST_Type *bt = node->base_type ();
343 if (bt->ast_accept (this) != 0)
345 ACE_ERROR_RETURN ((LM_ERROR,
346 ACE_TEXT ("ast_visitor_reifying::")
347 ACE_TEXT ("visit_array - ")
348 ACE_TEXT ("visit of base type failed\n")),
349 -1);
352 bt = dynamic_cast<AST_Type*> (this->reified_node_);
354 AST_Expression **dims = node->dims ();
355 AST_Expression *v = 0;
356 UTL_ExprList *v_list = 0;
358 for (ACE_CDR::ULong i = 0; i < node->n_dims (); ++i)
360 AST_Param_Holder *ph = dims[i]->param_holder ();
362 if (ph != 0)
364 if (this->visit_param_holder (ph) != 0)
366 if (v_list != 0)
368 v_list->destroy ();
369 delete v_list;
370 v_list = 0;
373 ACE_ERROR_RETURN ((LM_ERROR,
374 ACE_TEXT ("ast_visitor_reifying::")
375 ACE_TEXT ("visit_array - ")
376 ACE_TEXT ("visit_param_holder() ")
377 ACE_TEXT ("failed\n")),
378 -1);
381 AST_Constant *c = dynamic_cast<AST_Constant*> (this->reified_node_);
383 ACE_NEW_RETURN (v,
384 AST_Expression (c->constant_value (),
385 AST_Expression::EV_ulong),
386 -1);
388 else
390 ACE_NEW_RETURN (v,
391 AST_Expression (dims[i],
392 AST_Expression::EV_ulong),
393 -1);
396 UTL_ExprList *el = 0;
397 ACE_NEW_RETURN (el,
398 UTL_ExprList (v, 0),
399 -1);
401 if (v_list == 0)
403 v_list = el;
405 else
407 v_list->nconc (el);
411 UTL_ScopedName sn (node->local_name (), 0);
413 AST_Array *arr =
414 idl_global->gen ()->create_array (&sn,
415 node->n_dims (),
416 v_list,
417 false,
418 false);
420 // No need to add this new node to any scope - it's anonymous
421 // and owned by the node that references it.
423 if (v_list != 0)
425 v_list->destroy ();
426 delete v_list;
427 v_list = 0;
430 arr->set_base_type (bt);
431 this->reified_node_ = arr;
433 return 0;
437 ast_visitor_reifying::visit_sequence (AST_Sequence *node)
439 AST_Type *bt = node->base_type ();
441 if (bt->ast_accept (this) != 0)
443 ACE_ERROR_RETURN ((LM_ERROR,
444 ACE_TEXT ("ast_visitor_reifying::")
445 ACE_TEXT ("visit_sequence - ")
446 ACE_TEXT ("visit of base type failed\n")),
447 -1);
450 bt = dynamic_cast<AST_Type*> (this->reified_node_);
452 AST_Expression *v = node->max_size ();
453 AST_Param_Holder *ph = v->param_holder ();
455 if (ph != 0)
457 if (this->visit_param_holder (ph) != 0)
459 ACE_ERROR_RETURN ((LM_ERROR,
460 ACE_TEXT ("ast_visitor_reifying::")
461 ACE_TEXT ("visit_sequence - ")
462 ACE_TEXT ("visit_param_holder() ")
463 ACE_TEXT ("failed\n")),
464 -1);
467 AST_Constant *c = dynamic_cast<AST_Constant*> (this->reified_node_);
469 v = c->constant_value ();
472 AST_Expression *bound =
473 idl_global->gen ()->create_expr (v,
474 AST_Expression::EV_ulong);
475 Identifier id ("sequence");
476 UTL_ScopedName sn (&id, 0);
478 this->reified_node_ =
479 idl_global->gen ()->create_sequence (bound,
481 &sn,
482 false,
483 false);
485 // No need to add this new node to any scope - it's anonymous
486 // and owned by the node that references it.
488 return 0;
492 ast_visitor_reifying::visit_predefined_type (AST_PredefinedType *node)
494 this->reified_node_ = node;
495 return 0;
499 ast_visitor_reifying::visit_string (AST_String *node)
501 AST_Expression *b = node->max_size ();
502 AST_Param_Holder *ph = b->param_holder ();
504 if (ph != 0)
506 if (this->visit_param_holder (ph) != 0)
508 ACE_ERROR_RETURN ((LM_ERROR,
509 ACE_TEXT ("ast_visitor_reifying::")
510 ACE_TEXT ("visit_string - ")
511 ACE_TEXT ("visit_param_holder() ")
512 ACE_TEXT ("failed\n")),
513 -1);
516 AST_Constant *c = dynamic_cast<AST_Constant*> (this->reified_node_);
518 b = c->constant_value ();
520 else if (b->ev ()->u.ulval == 0)
522 this->reified_node_ = node;
523 return 0;
526 AST_Expression *bound = 0;
527 ACE_NEW_RETURN (bound,
528 AST_Expression (b,
529 AST_Expression::EV_ulong),
530 -1);
532 Identifier id ("string");
533 UTL_ScopedName sn (&id, 0);
535 ACE_NEW_RETURN (this->reified_node_,
536 AST_String (AST_Decl::NT_string,
537 &sn,
538 bound,
539 node->width ()),
540 -1);
542 return 0;
546 ast_visitor_reifying::visit_constant (AST_Constant *node)
548 // AFAICT, this is called only on the member constant of a param
549 // holder, in which case nothing further is needed.
550 this->reified_node_ = node;
551 return 0;
555 ast_visitor_reifying::visit_param_holder (AST_Param_Holder *node)
557 size_t i = 0;
558 FE_Utils::T_ARGLIST const *t_args =
559 this->ctx_->template_args ();
561 for (FE_Utils::T_PARAMLIST_INFO::ITERATOR iter (
562 *this->ctx_->template_params ());
563 !iter.done ();
564 iter.advance (), ++i)
566 FE_Utils::T_Param_Info *item = 0;
567 iter.next (item);
569 ACE_CString name (item->name_);
571 /// The param holder's info->name_ may be the same as the
572 /// node's local name, but if the node comes from an
573 /// alias, info->name_ will be the name of the alias's
574 /// referenced template module parameter, while the local
575 /// name will be that of the corresponding alias param
576 /// name, which is what we want.
577 if (name == node->local_name ()->get_string ())
579 AST_Decl **ret_ptr = 0;
581 if (t_args->get (ret_ptr, i) == 0)
583 AST_Decl *candidate = *ret_ptr;
585 return candidate->ast_accept (this);
587 else
589 ACE_ERROR_RETURN ((LM_ERROR,
590 ACE_TEXT ("ast_visitor_reifying::")
591 ACE_TEXT ("visit_param_holder() - access of ")
592 ACE_TEXT ("current template arglist failed - ")
593 ACE_TEXT ("param=%C scope=%C index=%d\n"),
594 item->name_.c_str (),
595 ScopeAsDecl (idl_global->scopes ().top ())->full_name (),
597 -1);
602 ACE_ERROR_RETURN ((LM_ERROR,
603 ACE_TEXT ("ast_visitor_reifying::")
604 ACE_TEXT ("visit_param_holder() - no match for ")
605 ACE_TEXT ("template param %C in %C\n"),
606 node->local_name ()->get_string (),
607 ScopeAsDecl (idl_global->scopes ().top ())->full_name ()),
608 -1);
611 void
612 ast_visitor_reifying::check_and_store (AST_Decl *node)
614 UTL_ScopedName *tmpl_tail =
615 this->template_module_rel_name (node);
617 if (tmpl_tail != 0)
619 AST_Decl *d =
620 idl_global->scopes ().top ()->lookup_by_name (
621 tmpl_tail,
622 true,
623 false);
625 this->reified_node_ = d;
627 tmpl_tail->destroy ();
628 delete tmpl_tail;
629 tmpl_tail = 0;
631 else
633 this->reified_node_ = node;
637 UTL_ScopedName *
638 ast_visitor_reifying::template_module_rel_name (AST_Decl *d)
640 AST_Decl *tmp = d;
641 ACE_CString name (d->full_name ());
643 while (tmp != 0)
645 if (dynamic_cast<AST_Template_Module*> (tmp) != 0)
647 ACE_CString head (tmp->local_name ()->get_string ());
649 ACE_CString::size_type start = name.find (head) + 2;
651 ACE_CString tail (name.substr (start + head.length ()));
653 return FE_Utils::string_to_scoped_name (tail.c_str ());
656 tmp = ScopeAsDecl (tmp->defined_in ());
659 return 0;