Struct_TypeCode.cpp

Go to the documentation of this file.
00001 // $Id: Struct_TypeCode.cpp 80140 2007-11-30 00:40:17Z jtc $
00002 
00003 #ifndef TAO_STRUCT_TYPECODE_CPP
00004 #define TAO_STRUCT_TYPECODE_CPP
00005 
00006 #include "tao/AnyTypeCode/Struct_TypeCode.h"
00007 #include "tao/AnyTypeCode/TypeCode_Struct_Field.h"
00008 #include "tao/AnyTypeCode/TypeCode_Traits.h"
00009 #include "tao/ORB_Core.h"
00010 #include "tao/TypeCodeFactory_Adapter.h"
00011 #include "tao/CDR.h"
00012 #include "tao/SystemException.h"
00013 
00014 
00015 #ifndef __ACE_INLINE__
00016 # include "tao/AnyTypeCode/Struct_TypeCode.inl"
00017 #endif  /* !__ACE_INLINE__ */
00018 
00019 #include "ace/Dynamic_Service.h"
00020 
00021 TAO_BEGIN_VERSIONED_NAMESPACE_DECL
00022 
00023 template <typename StringType,
00024           typename TypeCodeType,
00025           class FieldArrayType,
00026           class RefCountPolicy>
00027 bool
00028 TAO::TypeCode::Struct<StringType,
00029                       TypeCodeType,
00030                       FieldArrayType,
00031                       RefCountPolicy>::tao_marshal (TAO_OutputCDR & cdr,
00032                                                     CORBA::ULong offset) const
00033 {
00034   // A tk_struct TypeCode has a "complex" parameter list type (see
00035   // Table 15-2 in Section 15.3.5.1 "TypeCode" in the CDR section of
00036   // the CORBA specification), meaning that it must be marshaled into
00037   // a CDR encapsulation.
00038 
00039   // Create a CDR encapsulation.
00040   TAO_OutputCDR enc;
00041 
00042   // Account for the encoded CDR encapsulation length and byte order.
00043   //
00044   // Aligning on an octet since the next value after the CDR
00045   // encapsulation length will always be the byte order octet/boolean
00046   // in this case.
00047   offset = ACE_align_binary (offset + 4,
00048                              ACE_CDR::OCTET_ALIGN);
00049 
00050   bool const success =
00051     (enc << TAO_OutputCDR::from_boolean (TAO_ENCAP_BYTE_ORDER))
00052     && (enc << TAO_OutputCDR::from_string (this->base_attributes_.id (), 0))
00053     && (enc << TAO_OutputCDR::from_string (this->base_attributes_.name (), 0))
00054     && (enc << this->nfields_);
00055 
00056   if (!success)
00057     return false;
00058 
00059   Struct_Field<StringType, TypeCodeType> const * const begin =
00060     &this->fields_[0];
00061   Struct_Field<StringType, TypeCodeType> const * const end =
00062     begin + this->nfields_;
00063 
00064   for (Struct_Field<StringType, TypeCodeType> const * i = begin; i != end; ++i)
00065     {
00066       Struct_Field<StringType, TypeCodeType> const & field = *i;
00067 
00068       if (!(enc << TAO_OutputCDR::from_string (
00069                        Traits<StringType>::get_string (field.name), 0))
00070           || !marshal (enc,
00071                        Traits<StringType>::get_typecode (field.type),
00072                        offset + enc.total_length ()))
00073         return false;
00074     }
00075 
00076   return
00077     cdr << static_cast<CORBA::ULong> (enc.total_length ())
00078     && cdr.write_octet_array_mb (enc.begin ());
00079 }
00080 
00081 template <typename StringType,
00082           typename TypeCodeType,
00083           class FieldArrayType,
00084           class RefCountPolicy>
00085 void
00086 TAO::TypeCode::Struct<StringType,
00087                       TypeCodeType,
00088                       FieldArrayType,
00089                       RefCountPolicy>::tao_duplicate (void)
00090 {
00091   this->RefCountPolicy::add_ref ();
00092 }
00093 
00094 template <typename StringType,
00095           typename TypeCodeType,
00096           class FieldArrayType,
00097           class RefCountPolicy>
00098 void
00099 TAO::TypeCode::Struct<StringType,
00100                       TypeCodeType,
00101                       FieldArrayType,
00102                       RefCountPolicy>::tao_release (void)
00103 {
00104   this->RefCountPolicy::remove_ref ();
00105 }
00106 
00107 template <typename StringType,
00108           typename TypeCodeType,
00109           class FieldArrayType,
00110           class RefCountPolicy>
00111 CORBA::Boolean
00112 TAO::TypeCode::Struct<StringType,
00113                       TypeCodeType,
00114                       FieldArrayType,
00115                       RefCountPolicy>::equal_i (CORBA::TypeCode_ptr tc) const
00116 {
00117   // This call shouldn't throw since CORBA::TypeCode::equal() verified
00118   // that the TCKind is the same as our's prior to invoking this
00119   // method, meaning that member_count() is supported.
00120 
00121   CORBA::ULong const tc_nfields =
00122     tc->member_count ();
00123 
00124   if (tc_nfields != this->nfields_)
00125     return false;
00126 
00127   for (CORBA::ULong i = 0; i < this->nfields_; ++i)
00128     {
00129       Struct_Field<StringType, TypeCodeType> const & lhs_field =
00130         this->fields_[i];
00131 
00132       char const * const lhs_name =
00133         Traits<StringType>::get_string (lhs_field.name);
00134       char const * const rhs_name = tc->member_name (i);
00135 
00136       if (ACE_OS::strcmp (lhs_name, rhs_name) != 0)
00137         return false;
00138 
00139       CORBA::TypeCode_ptr const lhs_tc =
00140         Traits<StringType>::get_typecode (lhs_field.type);
00141       CORBA::TypeCode_var const rhs_tc =
00142         tc->member_type (i);
00143 
00144       CORBA::Boolean const equal_members =
00145         lhs_tc->equal (rhs_tc.in ());
00146 
00147       if (!equal_members)
00148         return false;
00149     }
00150 
00151   return true;
00152 }
00153 
00154 template <typename StringType,
00155           typename TypeCodeType,
00156           class FieldArrayType,
00157           class RefCountPolicy>
00158 CORBA::Boolean
00159 TAO::TypeCode::Struct<StringType,
00160                       TypeCodeType,
00161                       FieldArrayType,
00162                       RefCountPolicy>::equivalent_i (
00163   CORBA::TypeCode_ptr tc) const
00164 {
00165   // Perform a structural comparison, excluding the name() and
00166   // member_name() operations.
00167 
00168   CORBA::ULong const tc_nfields =
00169     tc->member_count ();
00170 
00171   if (tc_nfields != this->nfields_)
00172     return false;
00173 
00174   for (CORBA::ULong i = 0; i < this->nfields_; ++i)
00175     {
00176       CORBA::TypeCode_ptr const lhs =
00177         Traits<StringType>::get_typecode (this->fields_[i].type);
00178       CORBA::TypeCode_var const rhs =
00179         tc->member_type (i);
00180 
00181       CORBA::Boolean const equiv_members =
00182         lhs->equivalent (rhs.in ());
00183 
00184       if (!equiv_members)
00185         return false;
00186     }
00187 
00188   return true;
00189 }
00190 
00191 template <typename StringType,
00192           typename TypeCodeType,
00193           class FieldArrayType,
00194           class RefCountPolicy>
00195 CORBA::TypeCode_ptr
00196 TAO::TypeCode::Struct<StringType,
00197                       TypeCodeType,
00198                       FieldArrayType,
00199                       RefCountPolicy>::get_compact_typecode_i (void) const
00200 {
00201   ACE_Array_Base<Struct_Field<CORBA::String_var,
00202                               CORBA::TypeCode_var> >
00203     tc_fields (this->nfields_);
00204 
00205   if (this->nfields_ > 0)
00206     {
00207       // Dynamically construct a new array of fields stripped of
00208       // member names.
00209 
00210       static char const empty_name[] = "";
00211 
00212       for (CORBA::ULong i = 0; i < this->nfields_; ++i)
00213         {
00214           // Member names will be stripped, i.e. not embedded within
00215           // the compact TypeCode.
00216 
00217           tc_fields[i].name = empty_name;
00218           tc_fields[i].type =
00219             Traits<StringType>::get_typecode (
00220               this->fields_[i].type)->get_compact_typecode ();
00221         }
00222     }
00223 
00224   TAO_TypeCodeFactory_Adapter * const adapter =
00225     ACE_Dynamic_Service<TAO_TypeCodeFactory_Adapter>::instance (
00226       TAO_ORB_Core::typecodefactory_adapter_name ());
00227 
00228   if (adapter == 0)
00229     {
00230       throw ::CORBA::INTERNAL ();
00231     }
00232 
00233   return
00234     adapter->create_struct_except_tc (this->kind_,
00235                                       this->base_attributes_.id (),
00236                                       ""  /* empty name */,
00237                                       tc_fields,
00238                                       this->nfields_);
00239 }
00240 
00241 template <typename StringType,
00242           typename TypeCodeType,
00243           class FieldArrayType,
00244           class RefCountPolicy>
00245 char const *
00246 TAO::TypeCode::Struct<StringType,
00247                       TypeCodeType,
00248                       FieldArrayType,
00249                       RefCountPolicy>::id_i (void) const
00250 {
00251   // Ownership is retained by the TypeCode, as required by the C++
00252   // mapping.
00253   return this->base_attributes_.id ();
00254 }
00255 
00256 template <typename StringType,
00257           typename TypeCodeType,
00258           class FieldArrayType,
00259           class RefCountPolicy>
00260 char const *
00261 TAO::TypeCode::Struct<StringType,
00262                       TypeCodeType,
00263                       FieldArrayType,
00264                       RefCountPolicy>::name_i (void) const
00265 {
00266   // Ownership is retained by the TypeCode, as required by the C++
00267   // mapping.
00268   return this->base_attributes_.name ();
00269 }
00270 
00271 template <typename StringType,
00272           typename TypeCodeType,
00273           class FieldArrayType,
00274           class RefCountPolicy>
00275 CORBA::ULong
00276 TAO::TypeCode::Struct<StringType,
00277                       TypeCodeType,
00278                       FieldArrayType,
00279                       RefCountPolicy>::member_count_i (void) const
00280 {
00281   return this->nfields_;
00282 }
00283 
00284 template <typename StringType,
00285           typename TypeCodeType,
00286           class FieldArrayType,
00287           class RefCountPolicy>
00288 char const *
00289 TAO::TypeCode::Struct<StringType,
00290                       TypeCodeType,
00291                       FieldArrayType,
00292                       RefCountPolicy>::member_name_i (
00293   CORBA::ULong index) const
00294 {
00295   // Ownership is retained by the TypeCode, as required by the C++
00296   // mapping.
00297   if (index >= this->nfields_)
00298     throw ::CORBA::TypeCode::Bounds ();
00299 
00300   return Traits<StringType>::get_string (this->fields_[index].name);
00301 }
00302 
00303 template <typename StringType,
00304           typename TypeCodeType,
00305           class FieldArrayType,
00306           class RefCountPolicy>
00307 CORBA::TypeCode_ptr
00308 TAO::TypeCode::Struct<StringType,
00309                       TypeCodeType,
00310                       FieldArrayType,
00311                       RefCountPolicy>::member_type_i (
00312   CORBA::ULong index) const
00313 {
00314   if (index >= this->nfields_)
00315     throw ::CORBA::TypeCode::Bounds ();
00316 
00317   return
00318     CORBA::TypeCode::_duplicate (
00319       Traits<StringType>::get_typecode (this->fields_[index].type));
00320 }
00321 
00322 TAO_END_VERSIONED_NAMESPACE_DECL
00323 
00324 #endif  /* TAO_STRUCT_TYPECODE_CPP */

Generated on Tue Feb 2 17:40:11 2010 for TAO_AnyTypeCode by  doxygen 1.4.7