UIPMC_Profile.cpp

Go to the documentation of this file.
00001 // UIPMC_Profile.cpp,v 1.28 2006/05/23 16:09:34 mitza Exp
00002 
00003 #include "orbsvcs/PortableGroup/UIPMC_Profile.h"
00004 #include "orbsvcs/PortableGroup/miopconf.h"
00005 #include "tao/CDR.h"
00006 #include "tao/Environment.h"
00007 #include "tao/ORB.h"
00008 #include "tao/ORB_Core.h"
00009 #include "tao/debug.h"
00010 #include "tao/target_specification.h"
00011 #include "ace/os_include/os_ctype.h"
00012 
00013 #include "orbsvcs/miopC.h"
00014 #include "orbsvcs/PortableGroupC.h"
00015 
00016 ACE_RCSID (PortableGroup,
00017            UIPMC_Profile,
00018            "UIPMC_Profile.cpp,v 1.28 2006/05/23 16:09:34 mitza Exp")
00019 
00020 static const char the_prefix[] = "uipmc";
00021 
00022 // UIPMC doesn't support object keys, so send profiles by default in the GIOP 1.2 target
00023 // specification.
00024 static const CORBA::Short default_addressing_mode_ = TAO_Target_Specification::Profile_Addr;
00025 
00026 TAO_BEGIN_VERSIONED_NAMESPACE_DECL
00027 
00028 const char TAO_UIPMC_Profile::object_key_delimiter_ = '/';
00029 
00030 char
00031 TAO_UIPMC_Profile::object_key_delimiter (void) const
00032 {
00033   return TAO_UIPMC_Profile::object_key_delimiter_;
00034 }
00035 
00036 
00037 TAO_UIPMC_Profile::TAO_UIPMC_Profile (TAO_ORB_Core *orb_core)
00038   : TAO_Profile (IOP::TAG_UIPMC,
00039                  orb_core,
00040                  TAO_GIOP_Message_Version (TAO_DEF_GIOP_MAJOR, TAO_DEF_GIOP_MINOR)),
00041     endpoint_ (),
00042     count_ (1),
00043     tagged_profile_ ()
00044 {
00045     addressing_mode_ = default_addressing_mode_;
00046 }
00047 
00048 TAO_UIPMC_Profile::TAO_UIPMC_Profile (const ACE_INET_Addr &addr,
00049                                       TAO_ORB_Core *orb_core)
00050   : TAO_Profile (IOP::TAG_UIPMC,
00051                  orb_core,
00052                  TAO_GIOP_Message_Version (TAO_DEF_GIOP_MAJOR, TAO_DEF_GIOP_MINOR)),
00053     endpoint_ (addr),
00054     count_ (1),
00055     tagged_profile_ ()
00056 {
00057     addressing_mode_ = default_addressing_mode_;
00058 }
00059 
00060 TAO_UIPMC_Profile::TAO_UIPMC_Profile (const CORBA::Octet class_d_address[4],
00061                                       CORBA::UShort port,
00062                                       TAO_ORB_Core *orb_core)
00063   : TAO_Profile (IOP::TAG_UIPMC,
00064                  orb_core,
00065                  TAO_GIOP_Message_Version (TAO_DEF_GIOP_MAJOR, TAO_DEF_GIOP_MINOR)),
00066     endpoint_ (class_d_address, port),
00067     count_ (1),
00068     tagged_profile_ ()
00069 {
00070     addressing_mode_ = default_addressing_mode_;
00071 }
00072 
00073 /*
00074 
00075 TAO_UIPMC_Profile::TAO_UIPMC_Profile (const char *string,
00076                                       TAO_ORB_Core *orb_core
00077                                       ACE_ENV_ARG_DECL)
00078   : TAO_Profile (TAO_TAG_UIPMC_PROFILE,
00079                  orb_core,
00080                  TAO_GIOP_Message_Version (TAO_DEF_GIOP_MAJOR, TAO_DEF_GIOP_MINOR)),
00081     endpoint_ (),
00082     count_ (1),
00083     tagged_profile_ ()
00084 {
00085   this->add_group_component ();
00086   this->parse_string (string ACE_ENV_ARG_PARAMETER);
00087   ACE_CHECK;
00088   addressing_mode_ = default_addressing_mode_;
00089 }
00090 
00091 TAO_UIPMC_Profile::TAO_UIPMC_Profile (TAO_ORB_Core *orb_core)
00092   : TAO_Profile (TAO_TAG_UIPMC_PROFILE,
00093                  orb_core,
00094                  TAO_GIOP_Message_Version (TAO_DEF_GIOP_MAJOR, TAO_DEF_GIOP_MINOR)),
00095     endpoint_ (),
00096     count_ (1),
00097     tagged_profile_ ()
00098 {
00099   addressing_mode_ = default_addressing_mode_;
00100 }
00101 */
00102 
00103 TAO_UIPMC_Profile::~TAO_UIPMC_Profile (void)
00104 {
00105 }
00106 
00107 int
00108 TAO_UIPMC_Profile::decode (TAO_InputCDR& cdr)
00109 {
00110   // The following is a selective reproduction of TAO_Profile::decode
00111 
00112   CORBA::ULong encap_len = cdr.length ();
00113 
00114   // Read and verify major, minor versions, ignoring profiles
00115   // whose versions we don't understand.
00116   if (!(cdr.read_octet (this->version_.major)
00117         && this->version_.major == TAO_DEF_GIOP_MAJOR
00118         && cdr.read_octet (this->version_.minor)
00119         && this->version_.minor <= TAO_DEF_GIOP_MINOR))
00120     {
00121       if (TAO_debug_level > 0)
00122         {
00123           ACE_DEBUG ((LM_DEBUG,
00124                       ACE_TEXT ("TAO (%P|%t) - Profile::decode - v%d.%d\n"),
00125                       this->version_.major,
00126                       this->version_.minor));
00127         }
00128 
00129       return -1;
00130     }
00131 
00132   // Transport specific details
00133   if (this->decode_profile (cdr) < 0)
00134     {
00135       return -1;
00136     }
00137 
00138   // UIPMC profiles must have tagged components.
00139   if (this->tagged_components_.decode (cdr) == 0)
00140     {
00141       return -1;
00142     }
00143 
00144   if (cdr.length () != 0 && TAO_debug_level)
00145     {
00146       // If there is extra data in the profile we are supposed to
00147       // ignore it, but print a warning just in case...
00148       ACE_DEBUG ((LM_DEBUG,
00149                   ACE_TEXT ("%d bytes out of %d left after profile data\n"),
00150                   cdr.length (),
00151                   encap_len));
00152     }
00153 
00154   // We don't call ::decode_endpoints because it is implemented
00155   // as ACE_NOTSUP_RETURN (-1) for this profile
00156 
00157   return 1;
00158 }
00159 
00160 int
00161 TAO_UIPMC_Profile::decode_endpoints (void)
00162 {
00163   ACE_NOTSUP_RETURN (-1);
00164 }
00165 
00166 int
00167 TAO_UIPMC_Profile::decode_profile (TAO_InputCDR& cdr)
00168 {
00169   CORBA::UShort port = 0;
00170   ACE_CString address;
00171   if (!(cdr.read_string (address)
00172         && cdr.read_ushort (port)))
00173     {
00174       if (TAO_debug_level > 0)
00175         ACE_DEBUG ((LM_DEBUG,
00176                     ACE_TEXT ("TAO (%P|%t) UIPMC_Profile::decode - ")
00177                     ACE_TEXT ("Couldn't unmarshal address and port!\n")));
00178       return -1;
00179     }
00180 
00181   if (cdr.good_bit ())
00182     {
00183       // If everything was successful, update the endpoint's address
00184       // and port with the new data.
00185       ACE_INET_Addr addr (port, address.c_str ());
00186       this->endpoint_.object_addr (addr);
00187       return 1;
00188     }
00189 
00190   return -1;
00191 }
00192 
00193 void
00194 TAO_UIPMC_Profile::parse_string (const char *string
00195                                  ACE_ENV_ARG_DECL)
00196 {
00197   this->parse_string_i (string
00198                         ACE_ENV_ARG_PARAMETER);
00199 }
00200 
00201 void
00202 TAO_UIPMC_Profile::parse_string_i (const char *string
00203                                    ACE_ENV_ARG_DECL)
00204 {
00205   // Remove the "N.n@" version prefix, if it exists, and verify the
00206   // version is one that we accept.
00207 
00208   // Check for MIOP version
00209   if (isdigit (string [0]) &&
00210       string[1] == '.' &&
00211       isdigit (string [2]) &&
00212       string[3] == '@')
00213     {
00214       if (string[0] != '1' ||
00215           string[2] != '0')
00216         {
00217           ACE_THROW (CORBA::INV_OBJREF (
00218                           CORBA::SystemException::_tao_minor_code (
00219                             TAO::VMCID,
00220                             EINVAL),
00221                           CORBA::COMPLETED_NO));
00222         }
00223 
00224       string += 4;
00225       // Skip over the "N.n@"
00226     }
00227 
00228   // UIPMC profiles always use GIOP 1.2
00229   this->version_.set_version (1, 2);
00230 
00231   //
00232   // Parse the group_id.
00233   //
00234 
00235   // Parse the group component version.
00236   if (isdigit (string [0]) &&
00237       string[1] == '.' &&
00238       isdigit (string [2]) &&
00239       string[3] == '-')
00240     {
00241       CORBA::Char major;
00242       CORBA::Char minor;
00243 
00244       major = (char) (string [0] - '0');
00245       minor = (char) (string [2] - '0');
00246 
00247       // Verify that a supported version of MIOP is specified.
00248       if (major != TAO_DEF_MIOP_MAJOR ||
00249           minor >  TAO_DEF_MIOP_MINOR)
00250         {
00251           ACE_THROW (CORBA::INV_OBJREF (
00252                           CORBA::SystemException::_tao_minor_code (
00253                             TAO::VMCID,
00254                             EINVAL),
00255                           CORBA::COMPLETED_NO));
00256         }
00257 
00258       // Skip over "N.n-"
00259       string += 4;
00260     }
00261   else
00262     {
00263       // The group component version is mandatory.
00264       ACE_THROW (CORBA::INV_OBJREF (
00265                       CORBA::SystemException::_tao_minor_code (
00266                         TAO::VMCID,
00267                         EINVAL),
00268                       CORBA::COMPLETED_NO));
00269     }
00270 
00271   // Parse the group_domain_id.
00272   // The Domain ID is terminated with a '-'.
00273 
00274   // Wrap the string in a ACE_CString
00275   ACE_CString ace_str (string, 0, 0);
00276 
00277   // Look for the group domain delimitor.
00278   ssize_t pos = ace_str.find ('-');
00279 
00280   if (pos == ACE_CString::npos)
00281     {
00282       // The group_domain_id is mandatory, so throw an
00283       // exception if it isn't found.
00284       ACE_THROW (CORBA::INV_OBJREF (
00285                       CORBA::SystemException::_tao_minor_code (
00286                         TAO::VMCID,
00287                         EINVAL),
00288                       CORBA::COMPLETED_NO));
00289     }
00290 
00291   // Save the group_domain_id.
00292   ACE_CString group_domain_id = ace_str.substring (0, pos);
00293 
00294   // Parse the group_id.
00295   // The group_id is terminated with a '-' or a '/'.
00296 
00297   // Skip past the last '-'.
00298   pos++;
00299   ssize_t end_pos = ace_str.find ('-',pos);
00300 
00301   CORBA::Boolean parse_group_ref_version_flag = 0;
00302 
00303   if (end_pos != ACE_CString::npos)
00304     {
00305       // String was terminated by a '-', so there's a group
00306       // reference version to be parsed.
00307       parse_group_ref_version_flag = 1;
00308     }
00309   else
00310     {
00311       // Look for a slash as the separator.
00312       end_pos = ace_str.find ('/', pos);
00313 
00314       if (end_pos == ACE_CString::npos)
00315         {
00316           // The Group ID is mandatory, so throw an exception.
00317           ACE_THROW (CORBA::INV_OBJREF (
00318                           CORBA::SystemException::_tao_minor_code (
00319                             TAO::VMCID,
00320                             EINVAL),
00321                           CORBA::COMPLETED_NO));
00322         }
00323     }
00324 
00325   // Get the domain_id.
00326   ACE_CString str_domain_id = ace_str.substring (pos, end_pos - pos);
00327 
00328   // Convert the domain_id into numerical form.
00329   // @@ group_id is actually 64 bits, but strtoul only can parse 32 bits.
00330   // @@ Need a 64 bit strtoul...
00331   PortableGroup::ObjectGroupId group_id =
00332     ACE_OS::strtoul (str_domain_id.c_str (), 0, 10);
00333 
00334   PortableGroup::ObjectGroupRefVersion ref_version = 0;
00335   if (parse_group_ref_version_flag)
00336     {
00337       // Try to find the group version.  It is terminated by a '/'.
00338       pos = end_pos + 1;
00339       end_pos = ace_str.find ('/', pos);
00340       if (end_pos == ACE_CString::npos)
00341         {
00342           // The group version was expected but not found,
00343           // so throw an exception.
00344           ACE_THROW (CORBA::INV_OBJREF (
00345                           CORBA::SystemException::_tao_minor_code (
00346                             TAO::VMCID,
00347                             EINVAL),
00348                           CORBA::COMPLETED_NO));
00349         }
00350 
00351       ACE_CString str_group_ref_ver = ace_str.substring (pos, end_pos - pos);
00352 
00353       ref_version =
00354         ACE_OS::strtoul (str_group_ref_ver.c_str (), 0, 10);
00355     }
00356 
00357   // Parse the group multicast address.
00358   // The multicast address is terminated by a ':'.
00359   pos = end_pos + 1;
00360   end_pos = ace_str.find (':', pos);
00361 
00362   if (end_pos == ACE_CString::npos)
00363     {
00364       // The multicast address is mandatory, so throw an exception,
00365       // since it wasn't found.
00366       ACE_THROW (CORBA::INV_OBJREF (
00367                       CORBA::SystemException::_tao_minor_code (
00368                         TAO::VMCID,
00369                         EINVAL),
00370                       CORBA::COMPLETED_NO));
00371     }
00372 
00373   ACE_CString mcast_addr = ace_str.substring (pos, end_pos - pos);
00374 
00375   // Parse the multicast port number.
00376 
00377   // First check that there's something left in the string.
00378   pos = end_pos + 1;
00379   if (ace_str[pos] == '\0')
00380     {
00381       // The multicast port is mandatory, so throw an exception,
00382       // since it wasn't found.
00383       ACE_THROW (CORBA::INV_OBJREF (
00384                       CORBA::SystemException::_tao_minor_code (
00385                         TAO::VMCID,
00386                         EINVAL),
00387                       CORBA::COMPLETED_NO));
00388     }
00389 
00390   CORBA::UShort mcast_port =
00391       static_cast<CORBA::UShort> (ACE_OS::strtoul (ace_str.c_str () + pos, 0, 10));
00392 
00393   //
00394   // Finally, set all of the fields of the profile.
00395   //
00396 
00397   ACE_INET_Addr addr (mcast_port, mcast_addr.c_str ());
00398   this->endpoint_.object_addr (addr);
00399 
00400   this->set_group_info (group_domain_id.c_str (),
00401                         group_id,
00402                         ref_version);
00403 
00404 }
00405 
00406 CORBA::Boolean
00407 TAO_UIPMC_Profile::do_is_equivalent (const TAO_Profile *other_profile)
00408 {
00409   const TAO_UIPMC_Profile *op =
00410     dynamic_cast<const TAO_UIPMC_Profile *> (other_profile);
00411 
00412   if (op == 0)
00413     return 0;
00414 
00415   return this->endpoint_.is_equivalent (&op->endpoint_);
00416 }
00417 
00418 CORBA::ULong
00419 TAO_UIPMC_Profile::hash (CORBA::ULong max
00420                          ACE_ENV_ARG_DECL_NOT_USED)
00421 {
00422   // Get the hashvalue for all endpoints.
00423   CORBA::ULong hashval = this->endpoint_.hash ();
00424 
00425   hashval += this->version_.minor;
00426   hashval += this->tag ();
00427 
00428   return hashval % max;
00429 }
00430 
00431 TAO_Endpoint*
00432 TAO_UIPMC_Profile::endpoint (void)
00433 {
00434   return &this->endpoint_;
00435 }
00436 
00437 int
00438 TAO_UIPMC_Profile::encode_endpoints (void)
00439 {
00440   return 1;
00441 }
00442 
00443 CORBA::ULong
00444 TAO_UIPMC_Profile::endpoint_count (void) const
00445 {
00446   return 1;
00447 }
00448 
00449 char *
00450 TAO_UIPMC_Profile::to_string (ACE_ENV_SINGLE_ARG_DECL_NOT_USED)
00451 {
00452   // @@ Frank: Update to pull out GroupID information...
00453 
00454   size_t buflen = (ACE_OS::strlen (::the_prefix) +
00455                    3 /* "loc" */ +
00456                    1 /* colon separator */ +
00457                    2 /* double-slash separator */ +
00458                    1 /* major version */ +
00459                    1 /* decimal point */ +
00460                    1 /* minor version */ +
00461                    1 /* `@' character */ +
00462                    15 /* dotted decimal IPv4 address */ +
00463                    1 /* colon separator */ +
00464                    5 /* port number */);
00465 
00466   char * buf = CORBA::string_alloc (static_cast<CORBA::ULong> (buflen));
00467 
00468   ACE_OS::sprintf (buf,
00469                    "corbaloc:%s://1.0@%s:%d",
00470                    ::the_prefix,
00471                    this->endpoint_.get_host_addr (),
00472                    this->endpoint_.port ());
00473   return buf;
00474 }
00475 
00476 const char *
00477 TAO_UIPMC_Profile::prefix (void)
00478 {
00479   return ::the_prefix;
00480 }
00481 
00482 IOP::TaggedProfile &
00483 TAO_UIPMC_Profile::create_tagged_profile (void)
00484 {
00485   // Check whether we have already created the TaggedProfile
00486   if (this->tagged_profile_.profile_data.length () == 0)
00487     {
00488       // As we have not created we will now create the TaggedProfile
00489       this->tagged_profile_.tag = IOP::TAG_UIPMC;
00490 
00491       // Create the encapsulation....
00492       TAO_OutputCDR encap;
00493 
00494       // Create the profile body
00495       this->create_profile_body (encap);
00496 
00497       CORBA::ULong length =
00498         static_cast<CORBA::ULong> (encap.total_length ());
00499 
00500 #if (TAO_NO_COPY_OCTET_SEQUENCES == 1)
00501       // Place the message block in to the Sequence of Octets that we
00502       // have
00503       this->tagged_profile_.profile_data.replace (length,
00504                                                   encap.begin ());
00505 #else
00506       this->tagged_profile_.profile_data.length (length);
00507       CORBA::Octet *buffer =
00508         this->tagged_profile_.profile_data.get_buffer ();
00509       for (const ACE_Message_Block *i = encap.begin ();
00510            i != encap.end ();
00511            i = i->next ())
00512         {
00513           ACE_OS::memcpy (buffer, i->rd_ptr (), i->length ());
00514           buffer += i->length ();
00515         }
00516 #endif /* TAO_NO_COPY_OCTET_SEQUENCES == 1 */
00517     }
00518 
00519   return this->tagged_profile_;
00520 }
00521 
00522 void
00523 TAO_UIPMC_Profile::create_profile_body (TAO_OutputCDR &encap) const
00524 {
00525   encap.write_octet (TAO_ENCAP_BYTE_ORDER);
00526 
00527   // The GIOP version
00528   // Note: Only GIOP 1.2 and above are supported currently for MIOP.
00529   encap.write_octet (this->version_.major);
00530   encap.write_octet (this->version_.minor);
00531 
00532   // Address.
00533   encap.write_string (this->endpoint_.get_host_addr ());
00534 
00535   // Port number.
00536   encap.write_ushort (this->endpoint_.port ());
00537 
00538   // UIPMC is only supported by versions of GIOP that have tagged components,
00539   // so unconditionally encode the components.
00540   this->tagged_components ().encode (encap);
00541 }
00542 
00543 /*
00544 int
00545 TAO_UIPMC_Profile::decode_endpoints (void)
00546 {
00547   IOP::TaggedComponent tagged_component;
00548   tagged_component.tag = TAO_TAG_ENDPOINTS;
00549 
00550   if (this->tagged_components_.get_component (tagged_component))
00551     {
00552       const CORBA::Octet *buf =
00553         tagged_component.component_data.get_buffer ();
00554 
00555       TAO_InputCDR in_cdr (reinterpret_cast<const char*> (buf),
00556                            tagged_component.component_data.length ());
00557 
00558       // Extract the Byte Order.
00559       CORBA::Boolean byte_order;
00560       if ((in_cdr >> ACE_InputCDR::to_boolean (byte_order)) == 0)
00561         return -1;
00562       in_cdr.reset_byte_order (static_cast<int> (byte_order));
00563 
00564       // Extract endpoints sequence.
00565       TAO_UIPMCEndpointSequence endpoints;
00566 
00567       if ((in_cdr >> endpoints) == 0)
00568         return -1;
00569 
00570       // Get the priority of the first endpoint (head of the list.
00571       // It's other data is extracted as part of the standard profile
00572       // decoding.
00573       this->endpoint_.priority (endpoints[0].priority);
00574 
00575       // Use information extracted from the tagged component to
00576       // populate the profile.  Skip the first endpoint, since it is
00577       // always extracted through standard profile body.  Also, begin
00578       // from the end of the sequence to preserve endpoint order,
00579       // since <add_endpoint> method reverses the order of endpoints
00580       // in the list.
00581       for (CORBA::ULong i = endpoints.length () - 1;
00582            i > 0;
00583            --i)
00584         {
00585           TAO_UIPMC_Endpoint *endpoint = 0;
00586           ACE_NEW_RETURN (endpoint,
00587                           TAO_UIPMC_Endpoint (endpoints[i].host,
00588                                              endpoints[i].port,
00589                                              endpoints[i].priority),
00590                           -1);
00591 
00592           this->add_endpoint (endpoint);
00593         }
00594     }
00595 
00596   return 0;
00597 }
00598 */
00599 
00600 void
00601 TAO_UIPMC_Profile::set_group_info (const char *domain_id,
00602                                    PortableGroup::ObjectGroupId group_id,
00603                                    PortableGroup::ObjectGroupRefVersion ref_version)
00604 {
00605   // First, record the group information.
00606   this->group_domain_id_.set (domain_id);
00607   this->group_id_ = group_id;
00608   this->ref_version_ = ref_version;
00609 
00610   // Update the cached version of the group component.
00611   this->update_cached_group_component ();
00612 }
00613 
00614 void
00615 TAO_UIPMC_Profile::update_cached_group_component (void)
00616 {
00617   PortableGroup::TagGroupTaggedComponent group;
00618 
00619   // Encode the data structure.
00620   group.component_version.major = TAO_DEF_MIOP_MAJOR;
00621   group.component_version.minor = TAO_DEF_MIOP_MINOR;
00622 
00623   group.group_domain_id = CORBA::string_dup (this->group_domain_id_.c_str ());
00624   group.object_group_id = this->group_id_;
00625   group.object_group_ref_version = this->ref_version_;
00626 
00627   TAO_OutputCDR out_cdr;
00628 
00629   // Write the byte order.
00630   out_cdr << ACE_OutputCDR::from_boolean (ACE_CDR_BYTE_ORDER);
00631 
00632   // Write the group information.
00633   if ((out_cdr << group) == 0)
00634     {
00635       ACE_DEBUG ((LM_DEBUG,
00636                   "Error marshaling group component!"));
00637       return;
00638     }
00639 
00640   size_t length = out_cdr.total_length ();
00641 
00642   IOP::TaggedComponent tagged_component;
00643   tagged_component.tag = IOP::TAG_GROUP;
00644   tagged_component.component_data.length (static_cast<CORBA::ULong> (length));
00645   CORBA::Octet *buf =
00646     tagged_component.component_data.get_buffer ();
00647 
00648   for (const ACE_Message_Block *iterator = out_cdr.begin ();
00649        iterator != 0;
00650        iterator = iterator->cont ())
00651     {
00652       size_t i_length = iterator->length ();
00653       ACE_OS::memcpy (buf, iterator->rd_ptr (), i_length);
00654 
00655       buf += i_length;
00656     }
00657 
00658   // Add component with encoded endpoint data to this profile's
00659   // TaggedComponents.
00660   this->tagged_components_.set_component (tagged_component);
00661 }
00662 
00663 void
00664 TAO_UIPMC_Profile::request_target_specifier (
00665                       TAO_Target_Specification &target_spec,
00666                       TAO_Target_Specification::TAO_Target_Address required_type
00667                       ACE_ENV_ARG_DECL)
00668 {
00669   // Fill out the target specifier based on the required type.
00670   switch (required_type)
00671     {
00672     case TAO_Target_Specification::Profile_Addr:
00673 
00674       // Only using a profile as the target specifier is supported
00675       // at this time.  Object keys are strictly not supported since
00676       // UIPMC profiles do not have object keys.
00677       target_spec.target_specifier (
00678             this->create_tagged_profile ());
00679       break;
00680 
00681     case TAO_Target_Specification::Key_Addr:
00682     case TAO_Target_Specification::Reference_Addr:
00683     default:
00684       // Unsupported or unknown required type.  Throw an exception.
00685       ACE_THROW (CORBA::MARSHAL ());
00686     }
00687 }
00688 
00689 int
00690 TAO_UIPMC_Profile::supports_multicast (void) const
00691 {
00692   // Yes!  We support multicast!
00693   return 1;
00694 }
00695 
00696 void
00697 TAO_UIPMC_Profile::addressing_mode (CORBA::Short addr_mode
00698                                     ACE_ENV_ARG_DECL)
00699 {
00700   // ** See race condition note about addressing mode in Profile.h **
00701   switch (addr_mode)
00702     {
00703     case TAO_Target_Specification::Profile_Addr:
00704     case TAO_Target_Specification::Reference_Addr:
00705       this->addressing_mode_ = addr_mode;
00706       break;
00707 
00708     case TAO_Target_Specification::Key_Addr:
00709       // There is no object key, so it is not supported.
00710 
00711     default:
00712       ACE_THROW (CORBA::BAD_PARAM (
00713              CORBA::SystemException::_tao_minor_code (
00714                TAO::VMCID,
00715                EINVAL),
00716              CORBA::COMPLETED_NO));
00717     }
00718 }
00719 
00720 int
00721 TAO_UIPMC_Profile::extract_group_component (const IOP::TaggedProfile &profile,
00722                                             PortableGroup::TagGroupTaggedComponent &group)
00723 {
00724   // Create the decoding stream from the encapsulation in the buffer,
00725 //#if (TAO_NO_COPY_OCTET_SEQUENCES == 1)
00726 //  TAO_InputCDR cdr (profile.profile_data.mb ());
00727 //#else
00728   TAO_InputCDR cdr (reinterpret_cast<const char*> (profile.profile_data.get_buffer ()),
00729                     profile.profile_data.length ());
00730 //#endif /* TAO_NO_COPY_OCTET_SEQUENCES == 1 */
00731 
00732   // Extract the Byte Order.
00733   CORBA::Boolean byte_order;
00734   if ((cdr >> ACE_InputCDR::to_boolean (byte_order)) == 0)
00735     return -1;
00736   cdr.reset_byte_order (static_cast<int> (byte_order));
00737 
00738   // Read and verify major, minor versions, ignoring UIPMC profiles
00739   // whose versions we don't understand.
00740   CORBA::Octet major;
00741   CORBA::Octet minor = CORBA::Octet();
00742 
00743   // Read the version. We just read it here. We don't*do any*
00744   // processing.
00745   if (!(cdr.read_octet (major)
00746         && cdr.read_octet (minor)))
00747   {
00748     if (TAO_debug_level > 0)
00749       {
00750         ACE_DEBUG ((LM_DEBUG,
00751                     ACE_TEXT ("TAO (%P|%t) UIPMC_Profile::extract_group_component - v%d.%d\n"),
00752                     major,
00753                     minor));
00754       }
00755     return -1;
00756   }
00757 
00758   // Decode the endpoint.
00759   ACE_CString address;
00760   CORBA::UShort port;
00761 
00762   if (!(cdr.read_string (address)
00763         && cdr.read_ushort (port)))
00764     {
00765       if (TAO_debug_level > 0)
00766         ACE_DEBUG ((LM_DEBUG,
00767                     ACE_TEXT ("TAO (%P|%t) UIPMC_Profile::extract_group_component - Couldn't unmarshal address and port!\n")));
00768       return -1;
00769     }
00770 
00771   TAO_Tagged_Components tagged_components;
00772   if (tagged_components.decode (cdr) == 0)
00773     return -1;
00774 
00775   IOP::TaggedComponent tagged_component;
00776   tagged_component.tag = IOP::TAG_GROUP;
00777 
00778   // Try to find it.
00779   if (tagged_components.get_component (tagged_component) == 0)
00780     return -1;
00781 
00782   // Found it.
00783   const CORBA::Octet *buf =
00784     tagged_component.component_data.get_buffer ();
00785 
00786   TAO_InputCDR in_cdr (reinterpret_cast<const char*> (buf),
00787                        tagged_component.component_data.length ());
00788 
00789   // Extract the Byte Order.
00790   if ((in_cdr >> ACE_InputCDR::to_boolean (byte_order)) == 0)
00791     return -1;
00792   in_cdr.reset_byte_order (static_cast<int> (byte_order));
00793 
00794   if ((in_cdr >> group) == 0)
00795     return -1;
00796 
00797   return 0;
00798 }
00799 
00800 TAO_END_VERSIONED_NAMESPACE_DECL

Generated on Thu Nov 9 14:03:35 2006 for TAO_PortableGroup by doxygen 1.3.6