00001 #include "orbsvcs/SSLIOP/SSLIOP_Acceptor.h"
00002 #include "orbsvcs/SSLIOP/SSLIOP_Profile.h"
00003
00004 #include "tao/MProfile.h"
00005 #include "tao/ORB_Core.h"
00006 #include "tao/Server_Strategy_Factory.h"
00007 #include "tao/Codeset_Manager.h"
00008 #include "tao/CDR.h"
00009 #include "tao/debug.h"
00010
00011 #if !defined(__ACE_INLINE__)
00012 #include "orbsvcs/SSLIOP/SSLIOP_Acceptor.inl"
00013 #endif
00014
00015
00016 ACE_RCSID (SSLIOP,
00017 SSLIOP_Acceptor,
00018 "$Id: SSLIOP_Acceptor.cpp 81470 2008-04-28 12:40:23Z elliott_c $")
00019
00020 TAO_BEGIN_VERSIONED_NAMESPACE_DECL
00021
00022 TAO::SSLIOP::Acceptor::Acceptor (::Security::QOP qop,
00023 const ACE_Time_Value & timeout)
00024 : TAO::IIOP_SSL_Acceptor (),
00025 ssl_acceptor_ (this),
00026 creation_strategy_ (0),
00027 concurrency_strategy_ (0),
00028 accept_strategy_ (0),
00029 timeout_ (timeout)
00030 {
00031
00032
00033
00034 this->ssl_component_.target_supports = 0;
00035 this->ssl_component_.target_requires = 0;
00036
00037
00038 ACE_SET_BITS (this->ssl_component_.target_requires,
00039 ::Security::Integrity
00040 | ::Security::Confidentiality
00041 | ::Security::NoDelegation);
00042
00043
00044 ACE_SET_BITS (this->ssl_component_.target_supports,
00045 ::Security::Integrity
00046 | ::Security::Confidentiality
00047 | ::Security::EstablishTrustInTarget
00048 | ::Security::NoDelegation);
00049
00050
00051 this->ssl_component_.port = 0;
00052
00053
00054
00055 if (qop == ::Security::SecQOPNoProtection)
00056 ACE_SET_BITS (this->ssl_component_.target_supports,
00057 ::Security::NoProtection);
00058
00059
00060
00061
00062
00063
00064 this->csiv2_component_.target_supports = 0;
00065 this->csiv2_component_.target_requires = 0;
00066
00067
00068 ACE_SET_BITS (this->csiv2_component_.target_requires,
00069 CSIIOP::Integrity
00070 | CSIIOP::Confidentiality
00071 | CSIIOP::NoDelegation);
00072
00073
00074 ACE_SET_BITS (this->csiv2_component_.target_supports,
00075 CSIIOP::Integrity
00076 | CSIIOP::Confidentiality
00077 | CSIIOP::EstablishTrustInTarget
00078 | CSIIOP::NoDelegation);
00079
00080
00081
00082 if (qop == CSIIOP::NoProtection)
00083 ACE_SET_BITS (this->csiv2_component_.target_supports,
00084 CSIIOP::NoProtection);
00085 }
00086
00087 TAO::SSLIOP::Acceptor::~Acceptor (void)
00088 {
00089
00090
00091 this->close ();
00092
00093 delete this->creation_strategy_;
00094 delete this->concurrency_strategy_;
00095 delete this->accept_strategy_;
00096 }
00097
00098 int
00099 TAO::SSLIOP::Acceptor::create_profile (const TAO::ObjectKey &object_key,
00100 TAO_MProfile &mprofile,
00101 CORBA::Short priority)
00102 {
00103
00104 if (this->endpoint_count_ == 0)
00105 return -1;
00106
00107
00108
00109 if (priority == TAO_INVALID_PRIORITY)
00110 return this->create_new_profile (object_key,
00111 mprofile,
00112 priority);
00113 else
00114 return this->create_shared_profile (object_key,
00115 mprofile,
00116 priority);
00117 }
00118
00119 int
00120 TAO::SSLIOP::Acceptor::create_new_profile (const TAO::ObjectKey &object_key,
00121 TAO_MProfile &mprofile,
00122 CORBA::Short priority)
00123 {
00124
00125 const int count = mprofile.profile_count ();
00126 if ((mprofile.size () - count) < this->endpoint_count_
00127 && mprofile.grow (count + this->endpoint_count_) == -1)
00128 return -1;
00129
00130
00131 for (size_t i = 0; i < this->endpoint_count_; ++i)
00132 {
00133 TAO_SSLIOP_Profile *pfile = 0;
00134
00135
00136
00137
00138
00139
00140
00141
00142 ACE_NEW_RETURN (pfile,
00143 TAO_SSLIOP_Profile (this->hosts_[i],
00144 this->addrs_[i].get_port_number (),
00145 object_key,
00146 this->addrs_[i],
00147 this->version_,
00148 this->orb_core_,
00149 &(this->ssl_component_)),
00150 -1);
00151 pfile->endpoint ()->priority (priority);
00152
00153 if (mprofile.give_profile (pfile) == -1)
00154 {
00155 pfile->_decr_refcnt ();
00156 pfile = 0;
00157 return -1;
00158 }
00159
00160 if (this->orb_core_->orb_params ()->std_profile_components () == 0)
00161 continue;
00162
00163 pfile->tagged_components ().set_orb_type (TAO_ORB_TYPE);
00164
00165 TAO_Codeset_Manager *csm = this->orb_core_->codeset_manager();
00166 if (csm)
00167 csm->set_codeset (pfile->tagged_components());
00168
00169 IOP::TaggedComponent component;
00170 component.tag = ::SSLIOP::TAG_SSL_SEC_TRANS;
00171
00172
00173 TAO_OutputCDR cdr;
00174 cdr << TAO_OutputCDR::from_boolean (TAO_ENCAP_BYTE_ORDER);
00175
00176
00177
00178
00179
00180
00181
00182
00183 cdr << this->ssl_component_;
00184
00185
00186
00187 const CORBA::ULong length = cdr.total_length ();
00188 component.component_data.length (length);
00189 CORBA::Octet *buf = component.component_data.get_buffer ();
00190 for (const ACE_Message_Block *i = cdr.begin ();
00191 i != 0;
00192 i = i->cont ())
00193 {
00194 ACE_OS::memcpy (buf, i->rd_ptr (), i->length ());
00195 buf += i->length ();
00196 }
00197
00198 pfile->tagged_components ().set_component (component);
00199 }
00200
00201 return 0;
00202 }
00203
00204
00205 int
00206 TAO::SSLIOP::Acceptor::create_shared_profile (const TAO::ObjectKey &object_key,
00207 TAO_MProfile &mprofile,
00208 CORBA::Short priority)
00209 {
00210 size_t index = 0;
00211 TAO_Profile *pfile = 0;
00212 TAO_SSLIOP_Profile *ssliop_profile = 0;
00213
00214
00215 for (TAO_PHandle i = 0; i != mprofile.profile_count (); ++i)
00216 {
00217 pfile = mprofile.get_profile (i);
00218 if (pfile->tag () == IOP::TAG_INTERNET_IOP)
00219 {
00220 ssliop_profile = dynamic_cast<TAO_SSLIOP_Profile *> (pfile);
00221 if (ssliop_profile == 0)
00222 return -1;
00223 break;
00224 }
00225 }
00226
00227
00228
00229 if (ssliop_profile == 0)
00230 {
00231
00232
00233
00234
00235
00236
00237
00238 ACE_NEW_RETURN (ssliop_profile,
00239 TAO_SSLIOP_Profile (this->hosts_[0],
00240 this->addrs_[0].get_port_number (),
00241 object_key,
00242 this->addrs_[0],
00243 this->version_,
00244 this->orb_core_,
00245 &(this->ssl_component_)),
00246 -1);
00247
00248 TAO_SSLIOP_Endpoint * const ssliop_endp =
00249 dynamic_cast<TAO_SSLIOP_Endpoint *> (ssliop_profile->endpoint ());
00250
00251 if (!ssliop_endp)
00252 return -1;
00253
00254 ssliop_endp->priority (priority);
00255 ssliop_endp->iiop_endpoint ()->priority (priority);
00256
00257 if (mprofile.give_profile (ssliop_profile) == -1)
00258 {
00259 ssliop_profile->_decr_refcnt ();
00260 ssliop_profile = 0;
00261 return -1;
00262 }
00263
00264 if (this->orb_core_->orb_params ()->std_profile_components () != 0)
00265 {
00266 ssliop_profile->tagged_components ().set_orb_type (TAO_ORB_TYPE);
00267
00268 TAO_Codeset_Manager *csm = this->orb_core_->codeset_manager();
00269 if (csm)
00270 csm->set_codeset(ssliop_profile->tagged_components());
00271
00272 IOP::TaggedComponent component;
00273 component.tag = ::SSLIOP::TAG_SSL_SEC_TRANS;
00274
00275 TAO_OutputCDR cdr;
00276 cdr << TAO_OutputCDR::from_boolean (TAO_ENCAP_BYTE_ORDER);
00277
00278
00279
00280
00281
00282
00283
00284
00285
00286 cdr << this->ssl_component_;
00287
00288
00289
00290 CORBA::ULong length = cdr.total_length ();
00291 component.component_data.length (length);
00292 CORBA::Octet *buf = component.component_data.get_buffer ();
00293 for (const ACE_Message_Block *i = cdr.begin ();
00294 i != 0;
00295 i = i->cont ())
00296 {
00297 ACE_OS::memcpy (buf, i->rd_ptr (), i->length ());
00298 buf += i->length ();
00299 }
00300
00301 ssliop_profile->tagged_components ().set_component (component);
00302 }
00303
00304 index = 1;
00305 }
00306
00307
00308 for (;
00309 index < this->endpoint_count_;
00310 ++index)
00311 {
00312 TAO_SSLIOP_Endpoint *ssl_endp = 0;
00313 TAO_IIOP_Endpoint *iiop_endp = 0;
00314 ACE_NEW_RETURN (iiop_endp,
00315 TAO_IIOP_Endpoint (this->hosts_[index],
00316 this->addrs_[index].get_port_number (),
00317 this->addrs_[index]),
00318 -1);
00319 iiop_endp->priority (priority);
00320
00321 ACE_NEW_RETURN (ssl_endp,
00322 TAO_SSLIOP_Endpoint (&(this->ssl_component_),
00323 iiop_endp),
00324 -1);
00325
00326 ssl_endp->priority (priority);
00327 ssliop_profile->add_endpoint (ssl_endp);
00328 }
00329
00330 return 0;
00331 }
00332
00333 int
00334 TAO::SSLIOP::Acceptor::is_collocated (const TAO_Endpoint *endpoint)
00335 {
00336 const TAO_SSLIOP_Endpoint *endp =
00337 dynamic_cast<const TAO_SSLIOP_Endpoint *> (endpoint);
00338
00339
00340 if (endp == 0)
00341 return 0;
00342
00343 for (size_t i = 0; i < this->endpoint_count_; ++i)
00344 {
00345
00346
00347
00348
00349
00350
00351 if (endp->iiop_endpoint ()->object_addr () == this->addrs_[i])
00352 return 1;
00353 }
00354
00355 return 0;
00356 }
00357
00358 int
00359 TAO::SSLIOP::Acceptor::close (void)
00360 {
00361 int r = this->ssl_acceptor_.close ();
00362 if (this->IIOP_SSL_Acceptor::close () != 0)
00363 r = -1;
00364
00365 return r;
00366 }
00367
00368 int
00369 TAO::SSLIOP::Acceptor::open (TAO_ORB_Core *orb_core,
00370 ACE_Reactor *reactor,
00371 int major,
00372 int minor,
00373 const char *address,
00374 const char *options)
00375 {
00376
00377
00378 if (this->verify_secure_configuration (orb_core,
00379 major,
00380 minor) != 0)
00381 return -1;
00382
00383 ACE_INET_Addr addr;
00384 ACE_CString specified_hostname;
00385 if (this->parse_address (address, addr, specified_hostname) == -1)
00386 return -1;
00387
00388
00389
00390 if (this->IIOP_SSL_Acceptor::open (orb_core,
00391 reactor,
00392 major,
00393 minor,
00394 address,
00395 options) != 0)
00396 return -1;
00397
00398
00399
00400 addr.set_port_number (this->ssl_component_.port);
00401
00402 return this->ssliop_open_i (orb_core,
00403 addr,
00404 reactor);
00405 }
00406
00407 int
00408 TAO::SSLIOP::Acceptor::open_default (TAO_ORB_Core *orb_core,
00409 ACE_Reactor *reactor,
00410 int major,
00411 int minor,
00412 const char *options)
00413 {
00414
00415
00416 if (this->verify_secure_configuration (orb_core,
00417 major,
00418 minor) != 0)
00419 return -1;
00420
00421
00422
00423 if (this->IIOP_SSL_Acceptor::open_default (orb_core,
00424 reactor,
00425 major,
00426 minor,
00427 options) == -1)
00428 return -1;
00429
00430
00431
00432
00433 ACE_INET_Addr addr;
00434
00435
00436
00437 if (addr.set (this->ssl_component_.port,
00438 static_cast<ACE_UINT32> (INADDR_ANY),
00439 1) != 0)
00440 return -1;
00441
00442 return this->ssliop_open_i (orb_core,
00443 addr,
00444 reactor);
00445 }
00446
00447 int
00448 TAO::SSLIOP::Acceptor::ssliop_open_i (TAO_ORB_Core *orb_core,
00449 const ACE_INET_Addr& addr,
00450 ACE_Reactor *reactor)
00451 {
00452 this->orb_core_ = orb_core;
00453
00454 ACE_NEW_RETURN (this->creation_strategy_,
00455 CREATION_STRATEGY (this->orb_core_),
00456 -1);
00457
00458 ACE_NEW_RETURN (this->concurrency_strategy_,
00459 CONCURRENCY_STRATEGY (this->orb_core_),
00460 -1);
00461
00462 ACE_NEW_RETURN (this->accept_strategy_,
00463 ACCEPT_STRATEGY (this->orb_core_,
00464 this->timeout_),
00465 -1);
00466
00467 u_short requested_port = addr.get_port_number ();
00468 if (requested_port == 0)
00469 {
00470
00471 if (this->ssl_acceptor_.open (addr,
00472 reactor,
00473 this->creation_strategy_,
00474 this->accept_strategy_,
00475 this->concurrency_strategy_,
00476 0, 0, 0, 1,
00477 this->reuse_addr_) == -1)
00478 {
00479 if (TAO_debug_level > 0)
00480 ACE_DEBUG ((LM_DEBUG,
00481 ACE_TEXT ("\n\nTAO (%P|%t) ")
00482 ACE_TEXT ("SSLIOP_Acceptor::open_i - %p\n\n"),
00483 ACE_TEXT ("cannot open acceptor")));
00484 return -1;
00485 }
00486 }
00487 else
00488 {
00489 ACE_INET_Addr a(addr);
00490
00491 int found_a_port = 0;
00492 ACE_UINT32 last_port = requested_port + this->port_span_ - 1;
00493 if (last_port > ACE_MAX_DEFAULT_PORT)
00494 {
00495 last_port = ACE_MAX_DEFAULT_PORT;
00496 }
00497
00498 for (ACE_UINT32 p = requested_port; p <= last_port; p++)
00499 {
00500 if (TAO_debug_level > 5)
00501 ACE_DEBUG ((LM_DEBUG,
00502 ACE_TEXT ("TAO (%P|%t) IIOP_Acceptor::open_i() ")
00503 ACE_TEXT ("trying to listen on port %d\n"), p));
00504
00505
00506 a.set_port_number ((u_short)p);
00507 if (this->ssl_acceptor_.open (a,
00508 reactor,
00509 this->creation_strategy_,
00510 this->accept_strategy_,
00511 this->concurrency_strategy_,
00512 0, 0, 0, 1,
00513 this->reuse_addr_) != -1)
00514 {
00515 found_a_port = 1;
00516 break;
00517 }
00518 }
00519
00520
00521 if (! found_a_port)
00522 {
00523 if (TAO_debug_level > 0)
00524 ACE_DEBUG ((LM_DEBUG,
00525 ACE_TEXT ("\n\nTAO (%P|%t) ")
00526 ACE_TEXT ("SSLIOP_Acceptor::open_i - %p\n\n"),
00527 ACE_TEXT ("cannot open acceptor")));
00528 return -1;
00529 }
00530 }
00531
00532 ACE_INET_Addr ssl_address;
00533
00534
00535
00536 if (this->ssl_acceptor_.acceptor ().get_local_addr (ssl_address) != 0)
00537 {
00538
00539 if (TAO_debug_level > 0)
00540 ACE_DEBUG ((LM_DEBUG,
00541 ACE_TEXT ("\n\nTAO (%P|%t) ")
00542 ACE_TEXT ("SSLIOP_Acceptor::open_i - %p\n\n"),
00543 ACE_TEXT ("cannot get local addr")));
00544 return -1;
00545 }
00546
00547
00548
00549 this->ssl_component_.port = ssl_address.get_port_number ();
00550
00551 (void) this->ssl_acceptor_.acceptor().enable (ACE_CLOEXEC);
00552
00553
00554
00555
00556
00557 if (TAO_debug_level > 5)
00558 {
00559 for (size_t i = 0; i < this->endpoint_count_; ++i)
00560 {
00561 ACE_DEBUG ((LM_DEBUG,
00562 ACE_TEXT ("TAO (%P|%t) ")
00563 ACE_TEXT ("SSLIOP_Acceptor::open_i - ")
00564 ACE_TEXT ("listening on: <%s:%u>\n"),
00565 this->hosts_[i],
00566 this->ssl_component_.port));
00567 }
00568 }
00569
00570
00571
00572
00573
00574 this->set_error_retry_delay (
00575 this->orb_core_->orb_params ()->accept_error_delay());
00576
00577 return 0;
00578 }
00579
00580 int
00581 TAO::SSLIOP::Acceptor::parse_options_i (int &argc, ACE_CString ** argv)
00582 {
00583
00584 int result = this->IIOP_SSL_Acceptor::parse_options_i(argc,argv);
00585 if (result == -1)
00586 return result;
00587
00588
00589 int i = 0;
00590 while (i < argc)
00591 {
00592
00593
00594
00595 int slot = argv[i]->find ("=");
00596 ACE_CString name = argv[i]->substring (0, slot);
00597 ACE_CString value = argv[i]->substring (slot + 1);
00598
00599 if (name == "priority")
00600 {
00601 ACE_ERROR_RETURN ((LM_ERROR,
00602 ACE_TEXT ("TAO (%P|%t) Invalid SSLIOP endpoint format: ")
00603 ACE_TEXT ("endpoint priorities no longer supported. \n"),
00604 value.c_str ()),
00605 -1);
00606 }
00607 else if (ACE_OS::strcmp (name.c_str (), "ssl_port") == 0)
00608 {
00609 int ssl_port = ACE_OS::atoi (value.c_str ());
00610
00611 if (ssl_port >= 0 && ssl_port < 65536)
00612 this->ssl_component_.port = ssl_port;
00613 else
00614 ACE_ERROR_RETURN ((LM_ERROR,
00615 ACE_TEXT ("TAO (%P|%t) Invalid ")
00616 ACE_TEXT ("IIOP/SSL endpoint ")
00617 ACE_TEXT ("port: <%s>\n"),
00618 value.c_str ()),
00619 -1);
00620 }
00621 else
00622 {
00623
00624 i++;
00625 continue;
00626 }
00627
00628
00629
00630
00631 argc--;
00632 ACE_CString *temp = argv[i];
00633 for (int j = i; j <= argc-1; j++)
00634 argv[j] = argv[j+1];
00635 argv[argc] = temp;
00636
00637 }
00638 return 0;
00639 }
00640
00641 int
00642 TAO::SSLIOP::Acceptor::verify_secure_configuration (TAO_ORB_Core *orb_core,
00643 int major,
00644 int minor)
00645 {
00646
00647 if (major < 1)
00648 {
00649
00650 errno = EINVAL;
00651 return -1;
00652 }
00653
00654
00655
00656
00657
00658
00659
00660
00661
00662
00663
00664
00665
00666
00667
00668 if ((orb_core->orb_params ()->std_profile_components () == 0
00669 || (major == 1 && minor == 0))
00670 && ACE_BIT_DISABLED (this->ssl_component_.target_requires,
00671 ::Security::NoProtection))
00672 {
00673 if (TAO_debug_level > 0)
00674 ACE_ERROR ((LM_ERROR,
00675 ACE_TEXT ("(%P|%t) Cannot support secure ")
00676 ACE_TEXT ("IIOP over SSL connection if\n")
00677 ACE_TEXT ("(%P|%t) standard profile ")
00678 ACE_TEXT ("components are disabled\n")
00679 ACE_TEXT ("(%P|%t) or IIOP 1.0 endpoint is ")
00680 ACE_TEXT ("used.\n")));
00681
00682 errno = EINVAL;
00683 return -1;
00684 }
00685
00686 return 0;
00687 }
00688
00689 TAO_END_VERSIONED_NAMESPACE_DECL