diff options
-rw-r--r-- | TAO/orbsvcs/orbsvcs/SSLIOP/SSLIOP_Connector.cpp | 2 | ||||
-rw-r--r-- | TAO/orbsvcs/orbsvcs/SSLIOP/SSLIOP_Invocation_Interceptor.cpp | 123 | ||||
-rw-r--r-- | TAO/orbsvcs/orbsvcs/SSLIOP/SSLIOP_Invocation_Interceptor.h | 22 | ||||
-rw-r--r-- | TAO/orbsvcs/orbsvcs/SSLIOP/SSLIOP_ORBInitializer.cpp | 31 | ||||
-rw-r--r-- | TAO/orbsvcs/orbsvcs/Security/SL2_SecurityManager.cpp | 279 | ||||
-rw-r--r-- | TAO/orbsvcs/orbsvcs/Security/SL2_SecurityManager.h | 206 | ||||
-rw-r--r-- | TAO/orbsvcs/orbsvcs/Security/Security_ORBInitializer.cpp | 74 | ||||
-rw-r--r-- | TAO/orbsvcs/orbsvcs/SecurityLevel2.idl | 19 |
8 files changed, 696 insertions, 60 deletions
diff --git a/TAO/orbsvcs/orbsvcs/SSLIOP/SSLIOP_Connector.cpp b/TAO/orbsvcs/orbsvcs/SSLIOP/SSLIOP_Connector.cpp index a1bd7d9b1ec..c192d1b8066 100644 --- a/TAO/orbsvcs/orbsvcs/SSLIOP/SSLIOP_Connector.cpp +++ b/TAO/orbsvcs/orbsvcs/SSLIOP/SSLIOP_Connector.cpp @@ -348,6 +348,7 @@ TAO::SSLIOP::Connector::iiop_connect ( TAO::Profile_Transport_Resolver *resolver, ACE_Time_Value *timeout) { +#if 0 const ::SSLIOP::SSL &ssl_component = ssl_endpoint->ssl_component (); // Only allow connection to the insecure IIOP port if the endpoint @@ -368,6 +369,7 @@ TAO::SSLIOP::Connector::iiop_connect ( TAO::VMCID, EPERM), CORBA::COMPLETED_NO); +#endif TAO_IIOP_Endpoint *iiop_endpoint = ssl_endpoint->iiop_endpoint (); diff --git a/TAO/orbsvcs/orbsvcs/SSLIOP/SSLIOP_Invocation_Interceptor.cpp b/TAO/orbsvcs/orbsvcs/SSLIOP/SSLIOP_Invocation_Interceptor.cpp index f1542176fa3..1b8e35a91bb 100644 --- a/TAO/orbsvcs/orbsvcs/SSLIOP/SSLIOP_Invocation_Interceptor.cpp +++ b/TAO/orbsvcs/orbsvcs/SSLIOP/SSLIOP_Invocation_Interceptor.cpp @@ -1,9 +1,11 @@ #include "orbsvcs/SSLIOP/SSLIOP_Invocation_Interceptor.h" +#include "orbsvcs/SSLIOP/SSLIOP_Current.h" #include "orbsvcs/SecurityLevel2C.h" #include "tao/ORB_Constants.h" #include "tao/PortableServer/PS_CurrentC.h" +#include "tao/PortableServer/POAC.h" #include "tao/debug.h" #if defined (SSLIOP_DEBUG_PEER_CERTIFICATE) @@ -17,12 +19,49 @@ ACE_RCSID (SSLIOP, TAO_BEGIN_VERSIONED_NAMESPACE_DECL -TAO::SSLIOP::Server_Invocation_Interceptor::Server_Invocation_Interceptor ( - ::SSLIOP::Current_ptr current, - ::Security::QOP qop) - : ssliop_current_ (::SSLIOP::Current::_duplicate (current)), - qop_ (qop) +TAO::SSLIOP::Server_Invocation_Interceptor::Server_Invocation_Interceptor +( + PortableInterceptor::ORBInitInfo_ptr info, + ::Security::QOP default_qop, + size_t tss_slot +) +: qop_ (default_qop) { + /* + * Cache references to the "Current" objects that we'll need during + * during invocations. + */ + + CORBA::Object_var obj = + info->resolve_initial_references ("SSLIOPCurrent"); + + this->ssliop_current_ = ::SSLIOP::Current::_narrow (obj.in ()); + + if (!CORBA::is_nil (this->ssliop_current_.in ())) + { + TAO::SSLIOP::Current *tao_current = + dynamic_cast<TAO::SSLIOP::Current *> (this->ssliop_current_.in ()); + + if (tao_current != 0) + { + if (TAO_debug_level > 3) + ACE_DEBUG ((LM_DEBUG, "TAO (%P|%t) SSLIOP_Invocation_Interceptor::CTOR--setting up SSLIOP Current with slot %d\n", tss_slot)); + tao_current->tss_slot (tss_slot); + } + else + throw CORBA::INTERNAL (); + } + + obj = info->resolve_initial_references ("SecurityLevel2:SecurityManager"); + this->sec2manager_ = SecurityLevel2::SecurityManager::_narrow (obj.in ()); + + if (! CORBA::is_nil (this->sec2manager_.in ())) + { + // set the slot id? + } + + obj = info->resolve_initial_references ("POACurrent"); + this->poa_current_ = PortableServer::Current::_narrow (obj.in ()); } TAO::SSLIOP::Server_Invocation_Interceptor::~Server_Invocation_Interceptor ( @@ -54,6 +93,7 @@ TAO::SSLIOP::Server_Invocation_Interceptor::receive_request_service_contexts ( // SecTargetSecureInvocationPolicy so that we can // accept or reject requests on a per-object basis // instead on a per-endpoint basis. +#if 0 CORBA::Boolean const no_ssl = this->ssliop_current_->no_context (); if (TAO_debug_level >= 3) @@ -61,7 +101,7 @@ TAO::SSLIOP::Server_Invocation_Interceptor::receive_request_service_contexts ( if (no_ssl && this->qop_ != ::Security::SecQOPNoProtection) throw CORBA::NO_PERMISSION (); - +#endif #if defined(SSLIOP_DEBUG_PEER_CERTIFICATE) try { @@ -130,8 +170,77 @@ TAO::SSLIOP::Server_Invocation_Interceptor::receive_request_service_contexts ( void TAO::SSLIOP::Server_Invocation_Interceptor::receive_request ( - PortableInterceptor::ServerRequestInfo_ptr /* ri */) + PortableInterceptor::ServerRequestInfo_ptr ri ) { + SecurityLevel2::AccessDecision_var ad = + this->sec2manager_->access_decision (); + + + CORBA::Boolean const no_ssl = + this->ssliop_current_->no_context (); + + if (TAO_debug_level >= 3) + ACE_DEBUG ((LM_DEBUG, "SSLIOP (%P|%t) Interceptor (context), ssl=%d\n", !(no_ssl))); + + // if + // (1) no SSL session state is available (which means that the + // invocation is received across a non-SSL transport) + // AND + // (2) the required Quality of Protection is something other + // than SecQOPNoProtection (set via -SSLNoProtection) + if (no_ssl && this->qop_ != ::Security::SecQOPNoProtection) + { + /* + * Set up all the arguments needed by the call + * to AccessDecision::access_allowed() + */ + + /* Get the credentials from SSLIOP */ + SecurityLevel2::CredentialsList cred_list; // initial empty? +#if 0 + try { + SecurityLevel2::ReceivedCredentials_var rcvd_creds = + this->sec2_current_->received_credentials (); + // this gets the credentials received from the other side. We + // should be able to put this into a CredentialsList with no + // problem. + // + // Do I really need to implement a sec2_current, or can I hack + // the conversion at this level? I probably ought to do it as + // a real sec2_current with the conversion from sec3->sec2 + // happening at a lower level. + + cred_list.length(1); + cred_list[0] = rcvd_creds.in (); + /* + So, in looking for how we can do this, I find that the + SL3_SecurityCurrent::client_credentials() delegates to SL3_SecurityCurrent_Impl::client_credentials(), which is pure virtual. + */ + } + catch (...) { + } +#endif + + /* Get the target object */ + CORBA::Object_var target = CORBA::Object::_nil (); + + target = this->poa_current_->get_reference (); + + CORBA::String_var operation_name = ri->operation (); + CORBA::String_var target_interface_name = ri->target_most_derived_interface(); // is this the repository ID? + + CORBA::Boolean it_should_happen = false; + it_should_happen = ad->access_allowed (cred_list, + target.in(), + operation_name.in(), + target_interface_name.in()); + if (TAO_debug_level >= 3) + ACE_DEBUG ((LM_DEBUG, "TAO (%P|%t) SL2::access_allowed returned %s\n", + it_should_happen ? "true" : "false")); + + if (! it_should_happen) + throw CORBA::NO_PERMISSION (); + } } void diff --git a/TAO/orbsvcs/orbsvcs/SSLIOP/SSLIOP_Invocation_Interceptor.h b/TAO/orbsvcs/orbsvcs/SSLIOP/SSLIOP_Invocation_Interceptor.h index af09c09b702..9375c18ac2d 100644 --- a/TAO/orbsvcs/orbsvcs/SSLIOP/SSLIOP_Invocation_Interceptor.h +++ b/TAO/orbsvcs/orbsvcs/SSLIOP/SSLIOP_Invocation_Interceptor.h @@ -22,8 +22,11 @@ #endif /* ACE_LACKS_PRAGMA_ONCE */ #include "orbsvcs/SSLIOPC.h" +#include "orbsvcs/SecurityLevel2C.h" #include "tao/PortableInterceptorC.h" +#include "tao/PI/ORBInitInfo.h" #include "tao/PI_Server/PI_Server.h" +#include "tao/PortableServer/PS_CurrentC.h" #include "tao/LocalObject.h" // This is to remove "inherits via dominance" warnings from MSVC. @@ -55,9 +58,16 @@ namespace TAO { public: - /// Constructor. - Server_Invocation_Interceptor (::SSLIOP::Current_ptr current, - ::Security::QOP qop); + /*! + \brief Constructor. + \param info reference to the ORBInitInfo object so that + the interceptor can get access to initial references, etc. + \param default_qop the default Quality of Protection + \param tss_slot the TSS slot used by the various security features. + */ + Server_Invocation_Interceptor (PortableInterceptor::ORBInitInfo_ptr info, + ::Security::QOP default_qop, + size_t tss_slot); /** * @name PortableInterceptor::ServerRequestInterceptor Methods @@ -113,9 +123,15 @@ namespace TAO /// Reference to the current SSLIOP execution context. ::SSLIOP::Current_var ssliop_current_; + /// Reference to the POA current + PortableServer::Current_var poa_current_; + /// The default quality-of-protection settings in use. ::Security::QOP qop_; + /// SecurityLevel2 security manager reference + SecurityLevel2::SecurityManager_var sec2manager_; + SecurityLevel2::Current_var sec2_current_; }; } // End SSLIOP namespace. diff --git a/TAO/orbsvcs/orbsvcs/SSLIOP/SSLIOP_ORBInitializer.cpp b/TAO/orbsvcs/orbsvcs/SSLIOP/SSLIOP_ORBInitializer.cpp index c5d7846cb29..d0e0e91d04e 100644 --- a/TAO/orbsvcs/orbsvcs/SSLIOP/SSLIOP_ORBInitializer.cpp +++ b/TAO/orbsvcs/orbsvcs/SSLIOP/SSLIOP_ORBInitializer.cpp @@ -84,34 +84,14 @@ TAO::SSLIOP::ORBInitializer::post_init ( // object is registered for each ORB in this ORBInitializer's // pre_init() method. - CORBA::Object_var obj = - info->resolve_initial_references ("SSLIOPCurrent"); - - SSLIOP::Current_var ssliop_current = - SSLIOP::Current::_narrow (obj.in ()); - - if (!CORBA::is_nil (ssliop_current.in ())) - { - TAO::SSLIOP::Current *tao_current = - dynamic_cast<TAO::SSLIOP::Current *> (ssliop_current.in ()); - - if (tao_current != 0) - { - size_t const slot = this->get_tss_slot_id (info); - - tao_current->tss_slot (slot); - } - else - throw CORBA::INTERNAL (); - } - // Create the SSLIOP secure invocation server request interceptor. PortableInterceptor::ServerRequestInterceptor_ptr si = PortableInterceptor::ServerRequestInterceptor::_nil (); ACE_NEW_THROW_EX (si, - TAO::SSLIOP::Server_Invocation_Interceptor ( - ssliop_current.in (), - this->qop_), + TAO::SSLIOP::Server_Invocation_Interceptor + (info, + this->qop_, + this->get_tss_slot_id (info)), CORBA::NO_MEMORY ( CORBA::SystemException::_tao_minor_code ( TAO::VMCID, @@ -156,7 +136,8 @@ TAO::SSLIOP::ORBInitializer::post_init ( // Register the SSLIOP-specific vault with the // PrincipalAuthenticator. - obj = info->resolve_initial_references ("SecurityLevel3:SecurityManager"); + CORBA::Object_var obj = + info->resolve_initial_references ("SecurityLevel3:SecurityManager"); SecurityLevel3::SecurityManager_var manager = SecurityLevel3::SecurityManager::_narrow (obj.in ()); diff --git a/TAO/orbsvcs/orbsvcs/Security/SL2_SecurityManager.cpp b/TAO/orbsvcs/orbsvcs/Security/SL2_SecurityManager.cpp new file mode 100644 index 00000000000..c7a67144fa3 --- /dev/null +++ b/TAO/orbsvcs/orbsvcs/Security/SL2_SecurityManager.cpp @@ -0,0 +1,279 @@ +// $Id$ + +#include "orbsvcs/Security/SL2_SecurityManager.h" + +#include "tao/ORB_Constants.h" + +ACE_RCSID (Security, + SL2_SecurityManager, + "$Id$") + + +TAO_BEGIN_VERSIONED_NAMESPACE_DECL + +TAO::Security::SecurityManager::SecurityManager (/* unknown */) + : principal_authenticator_ (SecurityLevel2::PrincipalAuthenticator::_nil ()) +{ + // this needs to change to access decision + SecurityLevel2::AccessDecision_ptr ad; + ACE_NEW_THROW_EX (ad, + TAO::Security::AccessDecision, + CORBA::NO_MEMORY ( + CORBA::SystemException::_tao_minor_code ( + TAO::VMCID, + ENOMEM), + CORBA::COMPLETED_NO)); + + this->access_decision_ = ad; +} + +TAO::Security::SecurityManager::~SecurityManager (void) +{ +} + +Security::MechandOptionsList* +TAO::Security::SecurityManager::supported_mechanisms () + ACE_THROW_SPEC ((CORBA::SystemException)) +{ + throw CORBA::NO_IMPLEMENT (); +} + +SecurityLevel2::CredentialsList* +TAO::Security::SecurityManager::own_credentials () + ACE_THROW_SPEC ((CORBA::SystemException)) +{ + throw CORBA::NO_IMPLEMENT (); +} + +SecurityLevel2::RequiredRights_ptr +TAO::Security::SecurityManager::required_rights_object () + ACE_THROW_SPEC ((CORBA::SystemException)) +{ + throw CORBA::NO_IMPLEMENT (); +} + +SecurityLevel2::PrincipalAuthenticator_ptr +TAO::Security::SecurityManager::principal_authenticator () + ACE_THROW_SPEC ((CORBA::SystemException)) +{ + return SecurityLevel2::PrincipalAuthenticator::_duplicate + (this->principal_authenticator_.in () ); +} + +SecurityLevel2::AccessDecision_ptr +TAO::Security::SecurityManager::access_decision () + ACE_THROW_SPEC ((CORBA::SystemException)) +{ + return SecurityLevel2::AccessDecision::_duplicate (this->access_decision_.in () ); +} + +SecurityLevel2::AuditDecision_ptr +TAO::Security::SecurityManager::audit_decision () + ACE_THROW_SPEC ((CORBA::SystemException)) +{ + throw CORBA::NO_IMPLEMENT (); +} + +SecurityLevel2::TargetCredentials_ptr +TAO::Security::SecurityManager::get_target_credentials (CORBA::Object_ptr /*o*/) + ACE_THROW_SPEC ((CORBA::SystemException)) +{ + throw CORBA::NO_IMPLEMENT (); +} + +void +TAO::Security::SecurityManager::remove_own_credentials ( + SecurityLevel2::Credentials_ptr creds) + ACE_THROW_SPEC ((CORBA::SystemException)) +{ + throw CORBA::NO_IMPLEMENT (); +} + +CORBA::Policy_ptr +TAO::Security::SecurityManager::get_security_policy (CORBA::PolicyType policy_type) + ACE_THROW_SPEC ((CORBA::SystemException)) +{ + throw CORBA::NO_IMPLEMENT (); +} + +/* + * AccessDecision stuff below here + */ + +TAO::Security::AccessDecision::AccessDecision () + : default_allowance_decision_ (false) +{ +} + +TAO::Security::AccessDecision::~AccessDecision () +{ +} + +TAO::Security::AccessDecision::OBJECT_KEY +TAO::Security::AccessDecision::map_key_from_objref (CORBA::Object_ptr obj) +{ + // Originally this lived in access_allowed, but it was needed + // in add_object and remove_object, too, so it's been factored out. + // + // We need an ORB reference here. Where do we get it? + // + // The primary place we need this facility is in access_allowed. + // Unfortunately, the interface for access_allowed is cast in + // dormant OMG spec stone, so that can't change. We could pass in a + // reference as an argument to the constructor and store it, but + // what do we do, then, if the same interceptor is registered with + // multiple ORBs (is that possible?!?!)? Then we could end up using + // a different ORB to stringify, which could end up giving us a + // different string, which means they won't compare propertly. + // + // As a hack, we could realize that TAO's CORBA::Object implementation + // has a reference to its associated ORB, and just dip in there + // to get access to it. Ugly, but at least it should probably work. + CORBA::ORB_var orb = obj->_get_orb (); + CORBA::String_var ior = orb->object_to_string (obj); + return ior; +} + +CORBA::Boolean +TAO::Security::AccessDecision::access_allowed ( + const ::SecurityLevel2::CredentialsList & cred_list, + ::CORBA::Object_ptr target, + const char * operation_name, + const char * target_interface_name + ) + ACE_THROW_SPEC ((CORBA::SystemException)) +{ + // @@ I still don't know what we do with the cred_list in here... + // Do we inspect it? + + // Turn the target into what we'll use as a key into the map. + OBJECT_KEY key = this->map_key_from_objref (target); + + // LOCK THE MAP! + ACE_GUARD_RETURN (TAO_SYNCH_MUTEX, guard, this->map_lock_, + this->default_allowance_decision_); + + // Look up the target in access_map_; if there, return the value, + // otherwise return the default value. + CORBA::Boolean access_decision; + if (this->access_map_.find (key, access_decision) == -1) + { + // Couldn't find the IOR in the map, so we use the default + access_decision = this->default_allowance_decision_; + if (TAO_debug_level >= 3) + ACE_DEBUG ((LM_DEBUG, + "TAO (%P|%t) SL2_AccessDecision::access_decision(%s,%s)" + " NOT FOUND using default %d\n", + (const char*)key, operation_name, access_decision)); + } + else if (TAO_debug_level >= 3) + { + ACE_DEBUG ((LM_DEBUG, + "TAO (%P|%t) SL2_AccessDecision::access_decision(%s,%s)" + " found with decision %d\n", + (const char*)key, operation_name, access_decision)); + } + + // For now we just return the default. + return access_decision; +} + +void +TAO::Security::AccessDecision::add_object (CORBA::Object_ptr obj, + CORBA::Boolean allow_insecure_access) + ACE_THROW_SPEC ((CORBA::SystemException)) +{ + // make a key from 'obj' + OBJECT_KEY key = this->map_key_from_objref (obj); + + // bind it into the access_map_, replacing anything that's there. + // LOCK THE MAP! + ACE_GUARD (TAO_SYNCH_MUTEX, guard, this->map_lock_); + + // Since we want to replace any existing entry in the map, we just + // use rebind. + errno = 0; // Not sure if this gets set if rebind fails...it only + // appears to fail when an allocation thru the allocator's + // malloc() fails. Depending on the malloc() implementation, + // errno could get set OR an exception thrown. + int ret = this->access_map_.rebind (key, allow_insecure_access); + if (ret == -1) + { + // rebind shouldn't fail under normal circumstances + if (TAO_debug_level > 1) + ACE_DEBUG ((LM_DEBUG, + "TAO (%P|%t): SL2_AccessDecision::add_object(%s,%d) " + "unexpectedly failed (errno=%d)\n", + (const char*)key, + allow_insecure_access, + errno)); + throw + CORBA::NO_MEMORY(CORBA::SystemException::_tao_minor_code (TAO::VMCID, + errno), + CORBA::COMPLETED_NO); + } + else + { + if (TAO_debug_level >= 3) + ACE_DEBUG ((LM_DEBUG, + "TAO (%P|%t): SL2_AccessDecision::add_object(%s,%d) okay\n", + (const char*)key, + allow_insecure_access)); + } +} + +void +TAO::Security::AccessDecision::remove_object (CORBA::Object_ptr obj) + ACE_THROW_SPEC ((CORBA::SystemException)) +{ + // make a key from 'obj' + OBJECT_KEY key = this->map_key_from_objref (obj); + + // unbind it from access_map_, no matter if it's not in there... + // LOCK THE MAP! + ACE_GUARD (TAO_SYNCH_MUTEX, guard, this->map_lock_); + + errno = 0; + int ret = this->access_map_.unbind (key); + if (ret == -1) + { + if (errno == ENOENT) + { + // ignore b/c we don't care...maybe log a debug message for info + if (TAO_debug_level >= 3) + ACE_DEBUG ((LM_DEBUG, + "TAO (%P|%t): SL2_AccessDecision::remove_object(%s) " + "object not found in access map\n", + (const char*)key)); + } + else + { + if (TAO_debug_level > 0) + ACE_DEBUG ((LM_DEBUG, + "TAO (%P|%t): SL2_AccessDecision::remove_object(%s) " + " unexpected error during unbind from map (errno=%d\n)", + (const char*)key, + errno)); + throw + CORBA::UNKNOWN (CORBA::SystemException::_tao_minor_code (TAO::VMCID, + errno), + CORBA::COMPLETED_NO); + } + } +} + +CORBA::Boolean +TAO::Security::AccessDecision::default_decision (void) + ACE_THROW_SPEC ((::CORBA::SystemException)) +{ + return this->default_allowance_decision_; +} + +void +TAO::Security::AccessDecision::default_decision (CORBA::Boolean d) + ACE_THROW_SPEC ((::CORBA::SystemException)) +{ + this->default_allowance_decision_ = d; +} + +TAO_END_VERSIONED_NAMESPACE_DECL diff --git a/TAO/orbsvcs/orbsvcs/Security/SL2_SecurityManager.h b/TAO/orbsvcs/orbsvcs/Security/SL2_SecurityManager.h new file mode 100644 index 00000000000..66af6656715 --- /dev/null +++ b/TAO/orbsvcs/orbsvcs/Security/SL2_SecurityManager.h @@ -0,0 +1,206 @@ +// -*- C++ -*- + +//============================================================================= +/** + * @file SL2_SecurityManager.h + * + * $Id$ + * + * @author Chris Cleeland <cleeland@ociweb.com> + */ +//============================================================================= + + +#ifndef TAO_SL2_SECURITY_MANAGER_H +#define TAO_SL2_SECURITY_MANAGER_H + +#include /**/ "ace/pre.h" +#include "orbsvcs/Security/security_export.h" + +#if !defined (ACE_LACKS_PRAGMA_ONCE) +# pragma once +#endif /* ACE_LACKS_PRAGMA_ONCE */ + +#include "orbsvcs/SecurityC.h" +#include "orbsvcs/SecurityLevel2C.h" + +#include "tao/LocalObject.h" + +#include "ace/Hash_Map_Manager_T.h" +#include "ace/Null_Mutex.h" + +#if defined(_MSC_VER) +#pragma warning(push) +#pragma warning(disable:4250) +#endif /* _MSC_VER */ + + +TAO_BEGIN_VERSIONED_NAMESPACE_DECL + +namespace TAO +{ + // would prefer SL2, but all the other SL2 stuff is in the Security namespace + namespace Security + { + // This should move out of here probably, but it's easier to stick it + // here for the moment...(CJC) + /** + * @class AccessDecision + * + * @brief + */ + class AccessDecision + : public virtual TAO::SL2::AccessDecision, + public virtual TAO_Local_RefCounted_Object + { + public: + /*! Constructor */ + AccessDecision (/* not yet known */); + ~AccessDecision (void); + + virtual ::CORBA::Boolean access_allowed ( + const ::SecurityLevel2::CredentialsList & cred_list, + ::CORBA::Object_ptr target, + const char * operation_name, + const char * target_interface_name + ) + ACE_THROW_SPEC ((::CORBA::SystemException)); + + virtual ::CORBA::Boolean default_decision (void) + ACE_THROW_SPEC ((::CORBA::SystemException)); + virtual void default_decision (::CORBA::Boolean d) + ACE_THROW_SPEC ((::CORBA::SystemException)); + + virtual void add_object (::CORBA::Object_ptr obj, + ::CORBA::Boolean allow_insecure_access) + ACE_THROW_SPEC ((::CORBA::SystemException)); + virtual void remove_object (::CORBA::Object_ptr obj) + ACE_THROW_SPEC ((::CORBA::SystemException)); + + private: + /*! + * This is the default value that's returned from access_allowed() + * when the access table doesn't contain an entry for the reference. + */ + ::CORBA::Boolean default_allowance_decision_; + + /*! + * Map containing references and their designated insecure access. + */ + // What sorts of maps are available in ACE? We'll be mapping + // an object reference to a boolean, basically. Looks like for + // now we'll map a stringified IOR to the boolean, and provide some + // (for now) simple keys and functions for comparing them. + // + // Locking on this needs to be exclusive to add_object, + // remove_object, and access_allowed. I think that the lock on the + // map itself will be sufficient, but we'll model this after the + // Active Object map in the POA...so whatever way that goes, so, too, + // will this. + typedef CORBA::String_var OBJECT_KEY; + // This is typedef'd because we might try to do something fancier + // where, rather than having just a string as the key, we have a + // structure and the structure precomputes some of the information + // for the actual key. Thus, we could then customize the hash and + // comparison functors so that they use the precomputed information + // rather than computing it each time. For now, though, I want to + // make this easy to get things working. + typedef ACE_Hash_Map_Manager_Ex<OBJECT_KEY, // stringified IOR + CORBA::Boolean, // access_allowed? + ACE_Hash<const char*>, + ACE_Equal_To<const char*>, + ACE_Null_Mutex> // not sure this is right + ACCESS_MAP_TYPE; + + ACCESS_MAP_TYPE access_map_; + + // Lock for accessing the map. It may be possible to get away with + // just using a lock directly in the map, but I'm not sure, so I'll err + // conservatively. + TAO_SYNCH_MUTEX map_lock_; + + private: + /*! + * @brief Encapsulates a TAO-specific way to do object_to_string() without having an ORB reference handy. + * + * @note If OBJECT_KEY changes as described above, this should change + * so that it generates an OBJECT_KEY. + */ + OBJECT_KEY map_key_from_objref (CORBA::Object_ptr obj); + }; + + /** + * @class SecurityManager + * + * @brief + * + */ + class SecurityManager + : public virtual SecurityLevel2::SecurityManager, + public virtual TAO_Local_RefCounted_Object + { + public: + + /// Constructor + SecurityManager (/* not sure what's needed yet */); + + /** + * @name SecurityLevel2::SecurityManager Methods + * + * Methods required by the SecurityLevel2::SecurityManager + * interface. + */ + //@{ + virtual ::Security::MechandOptionsList* supported_mechanisms () + ACE_THROW_SPEC ((CORBA::SystemException)); + virtual SecurityLevel2::CredentialsList* own_credentials () + ACE_THROW_SPEC ((CORBA::SystemException)); + virtual SecurityLevel2::RequiredRights_ptr required_rights_object () + ACE_THROW_SPEC ((CORBA::SystemException)); + virtual SecurityLevel2::PrincipalAuthenticator_ptr principal_authenticator () + ACE_THROW_SPEC ((CORBA::SystemException)); + virtual SecurityLevel2::AccessDecision_ptr access_decision () + ACE_THROW_SPEC ((CORBA::SystemException)); + virtual SecurityLevel2::AuditDecision_ptr audit_decision () + ACE_THROW_SPEC ((CORBA::SystemException)); + virtual SecurityLevel2::TargetCredentials_ptr get_target_credentials (CORBA::Object_ptr o) + ACE_THROW_SPEC ((CORBA::SystemException)); + virtual void remove_own_credentials (SecurityLevel2::Credentials_ptr creds) + ACE_THROW_SPEC ((CORBA::SystemException)); + virtual CORBA::Policy_ptr get_security_policy (CORBA::PolicyType policy_type) + ACE_THROW_SPEC ((CORBA::SystemException)); + //@} + + protected: + + /// Destructor + /** + * Protected destructor to enforce proper memory management + * through the reference counting mechanism. + */ + virtual ~SecurityManager (void); + + private: + + /// The ORB-specific SecurityLevel2::PrincipalAuthenticator + /// reference. + // Except we're not going to have one of these right now + SecurityLevel2::PrincipalAuthenticator_var principal_authenticator_; + + // AccessDecision instance + SecurityLevel2::AccessDecision_var access_decision_; + }; + + } // End SL3 namespace +} // End TAO namespace + +TAO_END_VERSIONED_NAMESPACE_DECL + + +#if defined(_MSC_VER) +#pragma warning(pop) +#endif /* _MSC_VER */ + +#include /**/ "ace/post.h" + +#endif /* TAO_SL2_SECURITY_MANAGER_H */ diff --git a/TAO/orbsvcs/orbsvcs/Security/Security_ORBInitializer.cpp b/TAO/orbsvcs/orbsvcs/Security/Security_ORBInitializer.cpp index 970aff6e1dd..d6a665341a5 100644 --- a/TAO/orbsvcs/orbsvcs/Security/Security_ORBInitializer.cpp +++ b/TAO/orbsvcs/orbsvcs/Security/Security_ORBInitializer.cpp @@ -7,7 +7,10 @@ ACE_RCSID (Security, "$Id$") -// #include "Security_Current.h" +#if 1 +#include "orbsvcs/Security/Security_Current.h" +#include "orbsvcs/Security/SL2_SecurityManager.h" +#endif #include "orbsvcs/Security/SL3_SecurityCurrent.h" #include "orbsvcs/Security/SL3_CredentialsCurator.h" #include "orbsvcs/Security/SL3_SecurityManager.h" @@ -41,36 +44,57 @@ TAO::Security::ORBInitializer::pre_init ( throw CORBA::INTERNAL (); } -// // Reserve a TSS slot in the ORB core internal TSS resources for the -// // thread-specific portion of Security::Current. -// size_t old_tss_slot = tao_info->allocate_tss_slot_id (0 -//); + // Reserve a TSS slot in the ORB core internal TSS resources for the + // thread-specific portion of Security::Current. + size_t tss_slot = tao_info->allocate_tss_slot_id (0 /* no cleanup function */); -// CORBA::String_var orb_id = info->orb_id (); +#if 1 -// // Create the SecurityLevel2::Current object. -// SecurityLevel2::Current_ptr current = SecurityLevel2::Current::_nil (); -// ACE_NEW_THROW_EX (current, -// TAO_Security_Current (old_tss_slot, orb_id.in ()), -// CORBA::NO_MEMORY ( -// CORBA::SystemException::_tao_minor_code ( -// TAO::VMCID, -// ENOMEM), -// CORBA::COMPLETED_NO)); +#if 0 // why am I getting a BAD_OPERATION from no SSL context?! + CORBA::String_var orb_id = info->orb_id (); -// SecurityLevel2::Current_var security_current = current; + // Create the SecurityLevel2::Current object. + SecurityLevel2::Current_ptr current = SecurityLevel2::Current::_nil (); + ACE_NEW_THROW_EX (current, + TAO_Security_Current (tss_slot, orb_id.in ()), + CORBA::NO_MEMORY ( + CORBA::SystemException::_tao_minor_code ( + TAO::VMCID, + ENOMEM), + CORBA::COMPLETED_NO)); -// // Register the SecurityLevel2::Current object reference with the -// // ORB. -// info->register_initial_reference ("SecurityCurrent", -// security_current.in () -//); + SecurityLevel2::Current_var security_current = current; - // Reserve a TSS slot in the ORB core internal TSS resources for the - // thread-specific portion of SecurityLevel3::SecurityCurrent - // object. - size_t tss_slot = tao_info->allocate_tss_slot_id (0); + // Register the SecurityLevel2::Current object reference with the + // ORB. + info->register_initial_reference ("SecurityCurrent", + security_current.in ()); +#endif + /* + * Instantiate and register the SecurityLevel2::SecurityManager + */ + SecurityLevel2::SecurityManager_ptr manager2; + ACE_NEW_THROW_EX (manager2, + TAO::Security::SecurityManager (/*need args*/), + CORBA::NO_MEMORY ( + CORBA::SystemException::_tao_minor_code ( + TAO::VMCID, + ENOMEM), + CORBA::COMPLETED_NO)); + + SecurityLevel2::SecurityManager_var security_manager2 = manager2; + + // Register the SecurityLevel2::SecurityManager object reference + // with the ORB. + info->register_initial_reference ("SecurityLevel2:SecurityManager", + security_manager2.in ()); + +#endif + // Rather than reserve another TSS slot in the ORB core internal TSS + // resources for the thread-specific portion of + // SecurityLevel3::SecurityCurrent object, we will re-use the slot + // allocated earlier. // Create the SecurityLevel3::Current object. SecurityLevel3::SecurityCurrent_ptr current3; diff --git a/TAO/orbsvcs/orbsvcs/SecurityLevel2.idl b/TAO/orbsvcs/orbsvcs/SecurityLevel2.idl index 4826c449ed4..6a13faa6877 100644 --- a/TAO/orbsvcs/orbsvcs/SecurityLevel2.idl +++ b/TAO/orbsvcs/orbsvcs/SecurityLevel2.idl @@ -271,4 +271,23 @@ module SecurityLevel2 { #pragma prefix "" +module TAO { + module SL2 { + local interface AccessDecision : SecurityLevel2::AccessDecision + { + /*! Default value returned when a reference is not in the list. */ + // Can't come up with a good name for this. + attribute boolean default_decision; + + /*! Establish whether a particular object can be accessed via insecure + means. */ + void add_object (in Object obj, + in boolean allow_insecure_access); + void remove_object (in Object obj); + + // Should there be some kind of "find" interface? + }; + }; +}; + #endif /* _SECURITY_LEVEL_2_IDL_ */ |