2 //=============================================================================
6 * Extension of class AST_Array that provides additional means for C++
9 * @author Copyright 1994-1995 by Sun Microsystems
10 * @author Inc. and Aniruddha Gokhale
12 //=============================================================================
15 #include "be_codegen.h"
17 #include "be_helper.h"
18 #include "be_visitor.h"
19 #include "utl_identifier.h"
20 #include "idl_defines.h"
21 #include "global_extern.h"
23 #include "ace/Log_Msg.h"
25 be_array::be_array (UTL_ScopedName
*n
,
32 AST_Decl (AST_Decl::NT_array
,
35 AST_Type (AST_Decl::NT_array
,
37 AST_ConcreteType (AST_Decl::NT_array
,
44 be_decl (AST_Decl::NT_array
,
46 be_type (AST_Decl::NT_array
,
49 if (!this->imported ())
51 idl_global
->array_seen_
= true;
56 be_array::create_name ()
58 char namebuf
[NAMEBUFSIZE
];
60 UTL_ScopedName
*n
= nullptr;
61 be_decl
*scope
= nullptr;
63 ACE_OS::memset (namebuf
,
66 // Retrieve the base type.
67 // The name always starts this way.
68 be_type
*bt
= dynamic_cast<be_type
*> (this->base_type ());
72 ACE_ERROR_RETURN ((LM_ERROR
,
79 ACE_OS::sprintf (namebuf
,
81 bt
->local_name ()->get_string ());
83 // Now append dimensions.
84 for (i
= 0; i
< this->n_dims (); ++i
)
86 AST_Expression
*expr
= this->dims ()[i
];
89 if ((expr
== nullptr) || ((expr
!= nullptr) && (expr
->ev () == nullptr)))
91 ACE_ERROR_RETURN ((LM_ERROR
,
94 "bad array dimension\n"),
97 if (expr
->ev ()->et
== AST_Expression::EV_ulong
)
99 ACE_OS::sprintf (namebuf
,
102 ((int)expr
->ev ()->u
.ulval
));
106 ACE_ERROR_RETURN ((LM_ERROR
,
109 "bad dimension value\n"),
114 // Now see if we have a fully scoped name and if so, generate one.
115 scope
= dynamic_cast<be_scope
*> (this->defined_in ())->decl ();
119 // Make a copy of the enclosing scope's name.
120 n
= (UTL_ScopedName
*)scope
->name ()->copy ();
122 Identifier
*id
= nullptr;
124 Identifier (ACE_OS::strdup (namebuf
)),
127 UTL_ScopedName
*sn
= nullptr;
133 // Add our local name as the last component.
135 // Set the fully scoped name.
140 // We better be not here because we must be inside some scope,
141 // at least the ROOT scope.
150 be_array::compute_tc_name ()
152 // Array TypeCodes can only be accessed through an alias
153 // TypeCode. Generate a TypeCode name that is meant for internal
156 Identifier
* tao_id
= nullptr;
160 ACE_NEW (this->tc_name_
,
161 UTL_ScopedName (tao_id
,
164 ACE_CString local_tc_name
=
166 + ACE_CString (this->flat_name ());
168 Identifier
* typecode_scope
= nullptr;
169 ACE_NEW (typecode_scope
,
170 Identifier ("TypeCode"));
172 UTL_ScopedName
* tc_scope_conc_name
= nullptr;
173 ACE_NEW (tc_scope_conc_name
,
174 UTL_ScopedName (typecode_scope
,
177 this->tc_name_
->nconc (tc_scope_conc_name
);
179 Identifier
* id
= nullptr;
181 Identifier (local_tc_name
.c_str ()));
183 UTL_ScopedName
* conc_name
= nullptr;
188 this->tc_name_
->nconc (conc_name
);
194 be_array::gen_dimensions (TAO_OutStream
*os
,
195 unsigned short slice
)
200 // Print our dimensions.
201 for (i
= (slice
? 1 : 0); i
< this->n_dims (); ++i
)
204 AST_Expression
*expr
= this->dims ()[i
];
207 if ((expr
== nullptr) || ((expr
!= nullptr) && (expr
->ev () == nullptr)))
209 ACE_ERROR_RETURN ((LM_ERROR
,
212 "bad array dimension\n"),
216 if (expr
->ev ()->et
== AST_Expression::EV_ulong
)
218 *os
<< "[" << ((int)expr
->ev ()->u
.ulval
) << "]";
222 ACE_ERROR_RETURN ((LM_ERROR
,
225 "bad dimension value\n"),
235 be_array::gen_ostream_operator (TAO_OutStream
*os
,
238 be_scope
* scope
= dynamic_cast<be_scope
*> (this->defined_in ());
239 be_decl
* parent
= scope
->decl ();
240 ACE_CString
arg_name (ACE_CString (parent
->full_name ())
242 + (use_underscore
? "_" : "")
243 + this->local_name ()->get_string ()
244 + "_forany &_tao_array");
246 // Using 'const' with xxx_forany here prevents the compiler from
247 // automatically converting back to xxx_slice *.
249 << "std::ostream& operator<< (" << be_idt
<< be_idt_nl
250 << "std::ostream &strm," << be_nl
251 << "const " << arg_name
.c_str () << be_uidt_nl
254 << "strm << \"" << this->name () << "\";" << be_nl_2
;
256 ACE_CDR::ULong ndims
= this->n_dims ();
257 ACE_CDR::ULong i
= 0;
259 for (i
= 0; i
< ndims
; ++i
)
261 *os
<< "strm << \"[\";" << be_nl_2
;
263 AST_Expression
*expr
= this->dims ()[i
];
265 // Generate a loop for each dimension.
266 *os
<< "for (::CORBA::ULong i" << i
<< " = 0; i" << i
<< " < "
267 << expr
->ev ()->u
.ulval
<< "; ++i" << i
<< ")" << be_idt_nl
269 << "if (i" << i
<< " != 0)" << be_idt_nl
271 << "strm << \", \";" << be_uidt_nl
272 << "}" << be_uidt_nl
<< be_nl
;
277 ACE_CString
instance_name ("_tao_array.in ()");
279 for (i
= 0; i
< ndims
; ++i
)
281 char *working
= instance_name
.rep ();
282 instance_name
+= "[i";
283 instance_name
+= ACE_OS::itoa (i
, working
, 10);
284 instance_name
+= "]";
287 be_type
*bt
= dynamic_cast<be_type
*> (this->base_type ());
288 bt
->gen_member_ostream_operator (os
,
289 instance_name
.c_str (),
295 for (i
= 0; i
< ndims
; ++i
)
298 << "}" << be_uidt_nl
<< be_nl
303 << "return strm;" << be_uidt_nl
308 be_array::gen_member_ostream_operator (TAO_OutStream
*os
,
309 const char *instance_name
,
313 be_scope
* scope
= dynamic_cast<be_scope
*> (this->defined_in ());
314 be_decl
* parent
= scope
->decl ();
315 ACE_CString
decl_name (ACE_CString (parent
->full_name ())
317 + (use_underscore
? "_" : "")
318 + this->local_name ()->get_string ());
320 // The container is always const, so the member is const as well,
321 // but we have to cast it away for the forany constructor.
322 *os
<< decl_name
.c_str () << "_forany ("
323 << "const_cast< " << decl_name
.c_str () << "_slice *> (";
325 this->be_type::gen_member_ostream_operator (os
,
334 be_array::accept (be_visitor
*visitor
)
336 return visitor
->visit_array (this);
342 this->be_type::destroy ();
343 this->AST_Array::destroy ();