diff options
32 files changed, 2839 insertions, 292 deletions
diff --git a/TAO/tao/AbstractBase.cpp b/TAO/tao/AbstractBase.cpp new file mode 100644 index 00000000000..da99baf4106 --- /dev/null +++ b/TAO/tao/AbstractBase.cpp @@ -0,0 +1,323 @@ +// $Id$ + +// ============================================================================ +// +// = LIBRARY +// TAO +// +// = FILENAME +// AbstractBase.cpp +// +// = AUTHOR +// Jeff Parsons <parsons@cs.wustl.edu> +// +// ============================================================================ + +#include "tao/AbstractBase.h" +#include "tao/Any.h" +#include "tao/Stub.h" +#include "tao/Profile.h" +#include "tao/ValueFactory.h" + +#if defined (TAO_HAS_VALUETYPE) + +#if !defined (__ACE_INLINE__) +# include "tao/AbstractBase.inl" +#endif /* ! __ACE_INLINE__ */ + +ACE_RCSID (tao, + AbstractBase, + "$Id$") + +int CORBA_AbstractBase::_tao_class_id = 0; + +void * +CORBA_AbstractBase::_tao_QueryInterface (ptr_arith_t type) +{ + void *retv = 0; + + if (type == ACE_reinterpret_cast ( + ptr_arith_t, + &CORBA_AbstractBase::_tao_class_id) + ) + { + retv = ACE_reinterpret_cast (void*, this); + } + + if (retv != 0) + { + this->_add_ref (); + } + + return retv; +} + +void +CORBA_AbstractBase::_add_ref (void) +{ + if (this->refcount_lock_ != 0) + { + ACE_GUARD (TAO_SYNCH_MUTEX, mon, *this->refcount_lock_); + + this->refcount_++; + } +} + +void +CORBA_AbstractBase::_remove_ref (void) +{ + if (this->refcount_lock_ != 0) + { + { + ACE_GUARD (TAO_SYNCH_MUTEX, mon, *this->refcount_lock_); + + this->refcount_--; + + if (this->refcount_ != 0) + { + return; + } + } + + delete this; + } +} + +CORBA::Object_ptr +CORBA_AbstractBase::_to_object (void) +{ + if (this->concrete_stubobj_ == 0) + { + return CORBA::Object::_nil (); + } + + TAO_ORB_Core *orb_core = this->concrete_stubobj_->orb_core (); + this->concrete_stubobj_->_incr_refcnt (); + + return orb_core->create_object (this->concrete_stubobj_); +} + +CORBA::ValueBase * +CORBA_AbstractBase::_to_value (void) +{ + if (this->is_objref_) + { + return 0; + } + + CORBA::ValueBase *retval = this->_tao_to_value (); + + if (retval == 0) + { + return retval; + } + + retval->_add_ref (); + return retval; +} + +CORBA::Boolean +operator<< (TAO_OutputCDR &strm, const CORBA_AbstractBase_ptr abs) +{ + CORBA::Boolean discriminator = 0; + + if (abs->_is_objref ()) + { + discriminator = 1; + + if (strm << ACE_OutputCDR::from_boolean (discriminator)) + { + TAO_Stub *stubobj = abs->_stubobj (); + + if (stubobj == 0) + { + return 0; + } + + // STRING, a type ID hint + if ((strm << stubobj->type_id.in ()) == 0) + { + return 0; + } + + const TAO_MProfile& mprofile = stubobj->base_profiles (); + + CORBA::ULong profile_count = mprofile.profile_count (); + + if ((strm << profile_count) == 0) + { + return 0; + } + + // @@ The MProfile should be locked during this iteration, is there + // anyway to achieve that? + for (CORBA::ULong i = 0; i < profile_count; ++i) + { + const TAO_Profile *p = mprofile.get_profile (i); + + if (p->encode (strm) == 0) + { + return 0; + } + } + + return (CORBA::Boolean) strm.good_bit (); + } + } + else + { + discriminator = 0; + + if (strm << ACE_OutputCDR::from_boolean (discriminator)) + { + CORBA::Boolean retval = 1; + + CORBA::ULong value_tag = TAO_OBV_GIOP_Flags::Value_tag_base + | TAO_OBV_GIOP_Flags::Type_info_single; + + retval = strm.write_ulong (value_tag); + + if (retval == 0) + { + return retval; + } + + retval = strm << abs->_tao_obv_repository_id (); + + if (retval == 0) + { + return retval; + } + + return abs->_tao_marshal_v (strm); + } + } + + return 0; +} + +CORBA::Boolean +operator>> (TAO_InputCDR &strm, CORBA_AbstractBase_ptr &abs) +{ + abs = 0; + CORBA::Boolean discriminator = 0; + ACE_InputCDR::to_boolean tb (discriminator); + TAO_ORB_Core *orb_core = 0; + + if (strm >> tb) + { + if (discriminator == 0) + { + CORBA::ULong value_tag; + + if (!strm.read_ulong (value_tag)) + { + return 0; + } + + if (TAO_OBV_GIOP_Flags::is_null_ref (value_tag)) + { + // Ok, null reference unmarshaled. + return 1; + } + + if (!TAO_OBV_GIOP_Flags::is_value_tag (value_tag)) + { + ACE_DEBUG ((LM_DEBUG, + ACE_TEXT ("operator>> CORBA::AbstractBase ") + ACE_TEXT ("not value_tag\n"))); + return 0; + } + + CORBA::String_var repo_id_stream; + + // It would be more efficient not to copy the string) + if (strm.read_string (repo_id_stream.inout ()) == 0) + { + return 0; + } + + orb_core = strm.orb_core (); + + if (orb_core == 0) + { + orb_core = TAO_ORB_Core_instance (); + + if (TAO_debug_level > 0) + { + ACE_DEBUG ((LM_WARNING, + "TAO (%P|%t) WARNING: extracting valuetype using " + "default ORB_Core\n")); + } + } + + CORBA::ValueFactory_var factory = + orb_core->orb ()->lookup_value_factory (repo_id_stream.in ()); + + // We should throw an exception, if there were an appropriate one. + if (factory == 0) + { + ACE_DEBUG ((LM_ERROR, + ACE_TEXT ("(%N:%l) OBV factory is null !!!\n"))); + return 0; + } + + abs = factory->create_for_unmarshal_abstract (); + + return abs->_tao_unmarshal_v (strm); + } + else + { + CORBA::Object_var generic_objref; + + if (strm >> generic_objref.inout ()) + { + TAO_Stub *concrete_stubobj = generic_objref->_stubobj (); + + CORBA::Boolean stores_orb = + ! CORBA::is_nil (concrete_stubobj->servant_orb_var ().ptr ()); + + if (stores_orb) + { + orb_core = + concrete_stubobj->servant_orb_var ()->orb_core (); + } + + CORBA::Boolean collocated = + orb_core != 0 + && orb_core->optimize_collocation_objects () + && generic_objref->_is_collocated (); + + ACE_NEW_RETURN (abs, + CORBA_AbstractBase (concrete_stubobj, + collocated, + generic_objref->_servant ()), + 0); + return 1; + } + } + } + + return 0; +} + +CORBA::Boolean +CORBA_AbstractBase::_tao_marshal_v (TAO_OutputCDR &) +{ + return 0; +} + +CORBA::Boolean +CORBA_AbstractBase::_tao_unmarshal_v (TAO_InputCDR &) +{ + return 0; +} + +CORBA::ValueBase * +CORBA_AbstractBase::_tao_to_value (void) +{ + return 0; +} + +#endif /* TAO_HAS_VALUETYPE */ + diff --git a/TAO/tao/AbstractBase.h b/TAO/tao/AbstractBase.h new file mode 100644 index 00000000000..aae68288ed3 --- /dev/null +++ b/TAO/tao/AbstractBase.h @@ -0,0 +1,196 @@ +// -*- C++ -*- + +//============================================================================= +/** + * @file AbstractBase.h + * + * $Id$ + * + * @author Jeff Parsons <parsons@cs.wust.edu> + */ +//============================================================================= + + +#ifndef TAO_ABSTRACTBASE_H +#define TAO_ABSTRACTBASE_H + +#include "ace/pre.h" + +#if !defined (ACE_LACKS_PRAGMA_ONCE) +# pragma once +#endif /* ACE_LACKS_PRAGMA_ONCE */ + +#include "tao/corbafwd.h" +#include "tao/Object.h" +#include "tao/ValueBase.h" +#include "tao/ValueFactory.h" + +#if defined (TAO_HAS_VALUETYPE) + +/** + * @class CORBA_AbstractBase + * + * @brief Abstract base class for Interfaces and Valuetypes + * + * Allows the determination of whether an object has been + * passed by reference or by value to be deferred until runtime. + */ +class TAO_Export CORBA_AbstractBase +{ +public: + /// So the extraction operator can call the protectec constructor. + friend TAO_Export CORBA::Boolean + operator<< (TAO_OutputCDR &, const CORBA_AbstractBase_ptr); + + friend TAO_Export CORBA::Boolean + operator>> (TAO_InputCDR &, CORBA_AbstractBase_ptr &); + + typedef CORBA_AbstractBase_ptr _ptr_type; + typedef CORBA_AbstractBase_var _var_type; + + static int _tao_class_id; + + static CORBA::AbstractBase_ptr _narrow (CORBA::AbstractBase_ptr obj + ACE_ENV_ARG_DECL_WITH_DEFAULTS); + static CORBA::AbstractBase_ptr _unchecked_narrow ( + CORBA::AbstractBase_ptr obj + ACE_ENV_ARG_DECL_WITH_DEFAULTS + ); + + static CORBA::AbstractBase_ptr _duplicate (CORBA::AbstractBase_ptr obj); + static CORBA::AbstractBase_ptr _nil (void); + + CORBA::Object_ptr _to_object (void); + CORBA::ValueBase *_to_value (void); + + virtual CORBA::Boolean _is_a (const char *type_id + ACE_ENV_ARG_DECL_WITH_DEFAULTS); + virtual void *_tao_QueryInterface (ptr_arith_t type); + virtual const char* _interface_repository_id (void) const; + virtual const char* _tao_obv_repository_id (void) const; + virtual void *_tao_obv_narrow (ptr_arith_t type_id); + virtual CORBA::Boolean _tao_marshal_v (TAO_OutputCDR &strm); + virtual CORBA::Boolean _tao_unmarshal_v (TAO_InputCDR &strm); + + virtual void _add_ref (void); + virtual void _remove_ref (void); + + CORBA::Boolean _is_objref (void) const; + TAO_Stub *_stubobj (void) const; + CORBA::Boolean _is_collocated (void) const; + TAO_Abstract_ServantBase *_servant (void) const; + CORBA::Boolean _is_local (void) const; + +protected: + CORBA_AbstractBase (void); + CORBA_AbstractBase (const CORBA_AbstractBase &); + CORBA_AbstractBase (TAO_Stub *p, + CORBA::Boolean collocated, + TAO_Abstract_ServantBase *servant); + + virtual ~CORBA_AbstractBase (void); + +protected: + CORBA::Boolean is_objref_; + +private: + CORBA_AbstractBase & operator= (const CORBA_AbstractBase &); + + virtual CORBA::ValueBase *_tao_to_value (void); + +private: + TAO_Stub *concrete_stubobj_; + CORBA::Boolean is_collocated_; + TAO_Abstract_ServantBase *servant_; + CORBA::Boolean is_local_; + + /// Number of outstanding references to this object. + CORBA::ULong refcount_; + + /// Protect reference count manipulation from race conditions. + /** + * This lock is only instantiated for unconstrained objects. The + * reason for this is that locality-constrained objects that do not + * require reference counting (the default) may be instantiated in + * the critical path. + * + * @note This assumes that unconstrained objects will not be + * instantiated in the critical path. + */ + TAO_SYNCH_MUTEX * refcount_lock_; +}; + +/** + * @class CORBA_AbstractBase_var + * + * @brief _var class for AbstractBase + */ +class TAO_Export CORBA_AbstractBase_var +{ +public: + CORBA_AbstractBase_var (void); + CORBA_AbstractBase_var (CORBA::AbstractBase_ptr); + CORBA_AbstractBase_var (const CORBA_AbstractBase_var &); + ~CORBA_AbstractBase_var (void); + + CORBA_AbstractBase_var &operator= (CORBA::AbstractBase_ptr); + CORBA_AbstractBase_var &operator= (const CORBA_AbstractBase_var &); + CORBA::AbstractBase_ptr operator-> (void) const; + + /// in, inout, out, _retn + operator const CORBA::AbstractBase_ptr &() const; + operator CORBA::AbstractBase_ptr &(); + CORBA::AbstractBase_ptr in (void) const; + CORBA::AbstractBase_ptr &inout (void); + CORBA::AbstractBase_ptr &out (void); + CORBA::AbstractBase_ptr _retn (void); + CORBA::AbstractBase_ptr ptr (void) const; + + static CORBA::AbstractBase_ptr tao_duplicate (CORBA::AbstractBase_ptr); + static void tao_release (CORBA::AbstractBase_ptr); + static CORBA::AbstractBase_ptr tao_nil (void); + static CORBA::AbstractBase_ptr tao_narrow (CORBA::AbstractBase * + ACE_ENV_ARG_DECL_NOT_USED); + static CORBA::AbstractBase * tao_upcast (void *); + +private: + CORBA::AbstractBase_ptr ptr_; +}; + +/** + * @class CORBA_AbstractBase_var + * + * @brief _out class for AbstractBase + */ +class TAO_Export CORBA_AbstractBase_out +{ +public: + CORBA_AbstractBase_out (CORBA::AbstractBase_ptr &); + CORBA_AbstractBase_out (CORBA_AbstractBase_var &); + CORBA_AbstractBase_out (const CORBA_AbstractBase_out &); + CORBA_AbstractBase_out &operator= (const CORBA_AbstractBase_out &); + CORBA_AbstractBase_out &operator= (const CORBA_AbstractBase_var &); + CORBA_AbstractBase_out &operator= (CORBA::AbstractBase_ptr); + operator CORBA::AbstractBase_ptr &(); + CORBA::AbstractBase_ptr &ptr (void); + CORBA::AbstractBase_ptr operator-> (void); + +private: + CORBA::AbstractBase_ptr &ptr_; +}; + +TAO_Export CORBA::Boolean +operator<< (TAO_OutputCDR &, const CORBA_AbstractBase_ptr); + +TAO_Export CORBA::Boolean +operator>> (TAO_InputCDR &, CORBA_AbstractBase_ptr &); + +#if defined (__ACE_INLINE__) +# include "tao/AbstractBase.inl" +#endif /* __ACE_INLINE__) */ + +#endif /* TAO_HAS_VALUETYPE */ + +#include "ace/post.h" + +#endif /* TAO_ABSTRACTBASE_H */ diff --git a/TAO/tao/AbstractBase.inl b/TAO/tao/AbstractBase.inl new file mode 100644 index 00000000000..243c258e460 --- /dev/null +++ b/TAO/tao/AbstractBase.inl @@ -0,0 +1,403 @@ +// This may not look like C++, but it's really -*- C++ -*- +// $Id$ + +ACE_INLINE +CORBA_AbstractBase::CORBA_AbstractBase (void) + : is_objref_ (0), + concrete_stubobj_ (0), + is_collocated_ (0), + servant_ (0), + is_local_ (0), + refcount_ (1), + refcount_lock_ (0) +{ + ACE_NEW (this->refcount_lock_, + TAO_SYNCH_MUTEX); +} + +ACE_INLINE +CORBA_AbstractBase::CORBA_AbstractBase (const CORBA_AbstractBase &rhs) + : is_objref_ (rhs.is_objref_), + concrete_stubobj_ (rhs.concrete_stubobj_), + is_collocated_ (rhs.is_collocated_), + servant_ (rhs.servant_), + is_local_ (rhs.is_local_), + refcount_ (1), + refcount_lock_ (0) +{ + if (this->concrete_stubobj_ != 0) + { + (void) this->concrete_stubobj_->_incr_refcnt (); + + // Only instantiate a lock if the object is unconstrained. + // Locality-constrained objects have no-op reference counting by + // default. Furthermore locality-constrained objects may be + // instantiated in the critical path. Instantiating a lock for + // unconstrained objects alone optimizes instantiation of such + // locality-constrained objects. + ACE_NEW (this->refcount_lock_, + TAO_SYNCH_MUTEX); + } +} + +ACE_INLINE +CORBA_AbstractBase::CORBA_AbstractBase (TAO_Stub * protocol_proxy, + CORBA::Boolean collocated, + TAO_Abstract_ServantBase * servant) + : is_objref_ (1), + concrete_stubobj_ (protocol_proxy), + is_collocated_ (collocated), + servant_ (servant), + is_local_ (protocol_proxy == 0 ? 1 : 0), + refcount_ (1), + refcount_lock_ (0) +{ + if (this->concrete_stubobj_ != 0) + { + (void) this->concrete_stubobj_->_incr_refcnt (); + + // Only instantiate a lock if the object is unconstrained. + // Locality-constrained objects have no-op reference counting by + // default. Furthermore locality-constrained objects may be + // instantiated in the critical path. Instantiating a lock for + // unconstrained objects alone optimizes instantiation of such + // locality-constrained objects. + ACE_NEW (this->refcount_lock_, + TAO_SYNCH_MUTEX); + } +} + +ACE_INLINE +CORBA_AbstractBase::~CORBA_AbstractBase (void) +{ + if (this->concrete_stubobj_ != 0) + { + (void) this->concrete_stubobj_->_decr_refcnt (); + } + + delete this->refcount_lock_; +} + +ACE_INLINE +CORBA::AbstractBase_ptr +CORBA_AbstractBase::_nil (void) +{ + return 0; +} + +ACE_INLINE +CORBA_AbstractBase_ptr +CORBA_AbstractBase::_duplicate (CORBA_AbstractBase_ptr obj) +{ + if (obj) + { + obj->_add_ref (); + } + + return obj; +} + +/// Just call _duplicate and let it decide what to do. +ACE_INLINE +CORBA::AbstractBase_ptr +CORBA_AbstractBase::_narrow (CORBA::AbstractBase_ptr obj + ACE_ENV_ARG_DECL_NOT_USED) +{ + return CORBA_AbstractBase::_duplicate (obj); +} + +/// Same for this one. +ACE_INLINE +CORBA::AbstractBase_ptr +CORBA_AbstractBase::_unchecked_narrow (CORBA::AbstractBase_ptr obj + ACE_ENV_ARG_DECL_NOT_USED) +{ + return CORBA_AbstractBase::_duplicate (obj); +} + +ACE_INLINE +CORBA::Boolean +CORBA_AbstractBase::_is_a (const char *type_id + ACE_ENV_ARG_DECL_NOT_USED) +{ + return ! ACE_OS::strcmp (type_id, + "IDL:omg.org/CORBA/AbstractBase:1.0"); +} + +ACE_INLINE +const char * +CORBA_AbstractBase::_interface_repository_id (void) const +{ + return "IDL:omg.org/CORBA/AbstractBase:1.0"; +} + +ACE_INLINE +const char * +CORBA_AbstractBase::_tao_obv_repository_id (void) const +{ + return "IDL:omg.org/CORBA/AbstractBase:1.0"; +} + +ACE_INLINE +void * +CORBA_AbstractBase::_tao_obv_narrow (ptr_arith_t /* type_id */) +{ + return this; +} + +ACE_INLINE +CORBA::Boolean +CORBA_AbstractBase::_is_objref (void) const +{ + return this->is_objref_; +} + +ACE_INLINE +TAO_Stub * +CORBA_AbstractBase::_stubobj (void) const +{ + return this->concrete_stubobj_; +} + +ACE_INLINE +CORBA::Boolean +CORBA_AbstractBase::_is_collocated (void) const +{ + return this->is_collocated_; +} + +ACE_INLINE +TAO_Abstract_ServantBase * +CORBA_AbstractBase::_servant (void) const +{ + return this->servant_; +} + +ACE_INLINE +CORBA::Boolean +CORBA_AbstractBase::_is_local (void) const +{ + return this->is_local_; +} + +// ************************************************************ +// These are in CORBA namespace + +ACE_INLINE +void +CORBA::release (CORBA::AbstractBase_ptr obj) +{ + if (obj) + { + obj->_remove_ref (); + } +} + +ACE_INLINE +CORBA::Boolean +CORBA::is_nil (CORBA::AbstractBase_ptr obj) +{ + return (obj == 0); +} + +// ************************************************************* +// Inline operations for class CORBA_AbstractBase_var +// ************************************************************* + +ACE_INLINE +CORBA_AbstractBase_var::CORBA_AbstractBase_var (void) + : ptr_ (CORBA::AbstractBase::_nil ()) +{ +} + +ACE_INLINE +CORBA_AbstractBase_var::CORBA_AbstractBase_var (CORBA::AbstractBase_ptr p) + : ptr_ (p) +{ +} + +ACE_INLINE +CORBA_AbstractBase_var::~CORBA_AbstractBase_var (void) +{ + CORBA::release (this->ptr_); +} + +ACE_INLINE CORBA::AbstractBase_ptr +CORBA_AbstractBase_var::ptr (void) const +{ + return this->ptr_; +} + +ACE_INLINE +CORBA_AbstractBase_var::CORBA_AbstractBase_var (const CORBA_AbstractBase_var &p) + : ptr_ (CORBA_AbstractBase::_duplicate (p.ptr ())) +{ +} + +ACE_INLINE CORBA_AbstractBase_var & +CORBA_AbstractBase_var::operator= (CORBA::AbstractBase_ptr p) +{ + CORBA::release (this->ptr_); + this->ptr_ = p; + return *this; +} + +ACE_INLINE CORBA_AbstractBase_var & +CORBA_AbstractBase_var::operator= (const CORBA_AbstractBase_var &p) +{ + if (this != &p) + { + CORBA::release (this->ptr_); + this->ptr_ = CORBA_AbstractBase::_duplicate (p.ptr ()); + } + + return *this; +} + +ACE_INLINE +CORBA_AbstractBase_var::operator const CORBA::AbstractBase_ptr &() const // cast +{ + return this->ptr_; +} + +ACE_INLINE +CORBA_AbstractBase_var::operator CORBA::AbstractBase_ptr &() // cast +{ + return this->ptr_; +} + +ACE_INLINE CORBA::AbstractBase_ptr +CORBA_AbstractBase_var::operator-> (void) const +{ + return this->ptr_; +} + +ACE_INLINE CORBA::AbstractBase_ptr +CORBA_AbstractBase_var::in (void) const +{ + return this->ptr_; +} + +ACE_INLINE CORBA::AbstractBase_ptr & +CORBA_AbstractBase_var::inout (void) +{ + return this->ptr_; +} + +ACE_INLINE CORBA::AbstractBase_ptr & +CORBA_AbstractBase_var::out (void) +{ + CORBA::release (this->ptr_); + this->ptr_ = CORBA_AbstractBase::_nil (); + return this->ptr_; +} + +ACE_INLINE CORBA::AbstractBase_ptr +CORBA_AbstractBase_var::_retn (void) +{ + // Yield ownership of valuebase. + CORBA::AbstractBase_ptr val = this->ptr_; + this->ptr_ = CORBA_AbstractBase::_nil (); + return val; +} + +ACE_INLINE CORBA::AbstractBase_ptr +CORBA_AbstractBase_var::tao_duplicate (CORBA::AbstractBase_ptr p) +{ + return CORBA_AbstractBase::_duplicate (p); +} + +ACE_INLINE void +CORBA_AbstractBase_var::tao_release (CORBA::AbstractBase_ptr p) +{ + CORBA::release (p); +} + +ACE_INLINE CORBA::AbstractBase_ptr +CORBA_AbstractBase_var::tao_nil (void) +{ + return CORBA_AbstractBase::_nil (); +} + +ACE_INLINE CORBA::AbstractBase_ptr +CORBA_AbstractBase_var::tao_narrow ( + CORBA::AbstractBase *p + ACE_ENV_ARG_DECL_NOT_USED + ) +{ + return CORBA_AbstractBase::_duplicate (p); +} + +ACE_INLINE CORBA::AbstractBase * +CORBA_AbstractBase_var::tao_upcast (void *src) +{ + CORBA_AbstractBase **tmp = + ACE_static_cast (CORBA_AbstractBase **, src); + return *tmp; +} + +// ************************************************************* +// Inline operations for class CORBA_AbstractBase_out +// ************************************************************* + +ACE_INLINE +CORBA_AbstractBase_out::CORBA_AbstractBase_out (CORBA::AbstractBase_ptr &p) + : ptr_ (p) +{ + this->ptr_ = CORBA_AbstractBase::_nil (); +} + +ACE_INLINE +CORBA_AbstractBase_out::CORBA_AbstractBase_out (CORBA_AbstractBase_var &p) + : ptr_ (p.out ()) +{ + CORBA::release (this->ptr_); + this->ptr_ = CORBA_AbstractBase::_nil (); +} + +ACE_INLINE +CORBA_AbstractBase_out::CORBA_AbstractBase_out (const CORBA_AbstractBase_out &p) + : ptr_ (p.ptr_) +{ +} + +ACE_INLINE CORBA_AbstractBase_out & +CORBA_AbstractBase_out::operator= (const CORBA_AbstractBase_out &p) +{ + this->ptr_ = p.ptr_; + return *this; +} + +ACE_INLINE CORBA_AbstractBase_out & +CORBA_AbstractBase_out::operator= (const CORBA_AbstractBase_var &p) +{ + this->ptr_ = CORBA_AbstractBase::_duplicate (p.ptr ()); + return *this; +} + +ACE_INLINE CORBA_AbstractBase_out & +CORBA_AbstractBase_out::operator= (CORBA::AbstractBase_ptr p) +{ + this->ptr_ = p; + return *this; +} + +ACE_INLINE +CORBA_AbstractBase_out::operator CORBA::AbstractBase_ptr &() // cast +{ + return this->ptr_; +} + +ACE_INLINE CORBA::AbstractBase_ptr & +CORBA_AbstractBase_out::ptr (void) // ptr +{ + return this->ptr_; +} + +ACE_INLINE CORBA::AbstractBase_ptr +CORBA_AbstractBase_out::operator-> (void) +{ + return this->ptr_; +} + + diff --git a/TAO/tao/Any.cpp b/TAO/tao/Any.cpp index a012020adc6..2c98d29d0ba 100644 --- a/TAO/tao/Any.cpp +++ b/TAO/tao/Any.cpp @@ -11,6 +11,7 @@ #include "tao/Marshal.h" #include "tao/ORB_Core.h" #include "tao/Object.h" +#include "tao/AbstractBase.h" #include "tao/debug.h" #if !defined (__ACE_INLINE__) @@ -1611,7 +1612,7 @@ CORBA_Any::operator>>= (to_object obj) const // is only useful to implement the >>=(to_object) operator, // which is very rarely used. // It is better to just demarshal the object everytime, - // specially because the caller is owns the returned object. + // specially because the caller owns the returned object. // // if (this->any_owns_data_ && this->value_) // { @@ -1648,6 +1649,104 @@ CORBA_Any::operator>>= (to_object obj) const return 0; } +CORBA::Boolean +CORBA_Any::operator>>= (to_abstract_base obj) const +{ + ACE_DECLARE_NEW_CORBA_ENV; + + ACE_TRY + { + CORBA::ULong kind = + this->type_->kind (ACE_ENV_SINGLE_ARG_PARAMETER); + ACE_TRY_CHECK; + + CORBA::TypeCode_var tcvar = + CORBA::TypeCode::_duplicate (this->type_.in ()); + + while (kind == CORBA::tk_alias) + { + tcvar = tcvar->content_type (ACE_ENV_SINGLE_ARG_PARAMETER); + ACE_TRY_CHECK; + + kind = tcvar->kind (ACE_ENV_SINGLE_ARG_PARAMETER); + ACE_TRY_CHECK; + } + + if (kind != CORBA::tk_abstract_interface) + { + return 0; + } + + // @@ This uses ORB_Core instance because we need one to + // demarshal objects (to create the right profiles for that + // object), but the Any does not belong to any ORB. + TAO_InputCDR stream (this->cdr_, + this->byte_order_, + TAO_DEF_GIOP_MAJOR, + TAO_DEF_GIOP_MINOR, + TAO_ORB_Core_instance ()); + + if (stream >> obj.ref_) + { + return 1; + } + } + ACE_CATCHANY + { + ACE_DEBUG ((LM_DEBUG, + ACE_TEXT ("Exception in CORBA::AbstractBase extraction\n"))); + } + ACE_ENDTRY; + + return 0; +} + +CORBA::Boolean +CORBA_Any::operator>>= (to_value obj) const +{ + ACE_DECLARE_NEW_CORBA_ENV; + + ACE_TRY + { + CORBA::ULong kind = + this->type_->kind (ACE_ENV_SINGLE_ARG_PARAMETER); + ACE_TRY_CHECK; + + CORBA::TypeCode_var tcvar = + CORBA::TypeCode::_duplicate (this->type_.in ()); + + while (kind == CORBA::tk_alias) + { + tcvar = tcvar->content_type (ACE_ENV_SINGLE_ARG_PARAMETER); + ACE_TRY_CHECK; + + kind = tcvar->kind (ACE_ENV_SINGLE_ARG_PARAMETER); + ACE_TRY_CHECK; + } + + if (kind != CORBA::tk_value) + { + return 0; + } + + TAO_InputCDR stream (this->cdr_, + this->byte_order_); + + if (stream >> obj.ref_) + { + return 1; + } + } + ACE_CATCHANY + { + ACE_DEBUG ((LM_DEBUG, + ACE_TEXT ("Exception in CORBA::ValueBase extraction\n"))); + } + ACE_ENDTRY; + + return 0; +} + // this is a copying version for unbounded strings Not inline, to // avoid use in Any.i before definition in ORB.i. diff --git a/TAO/tao/Any.h b/TAO/tao/Any.h index 4f062dacd5b..34e1516b8f4 100644 --- a/TAO/tao/Any.h +++ b/TAO/tao/Any.h @@ -241,7 +241,8 @@ public: typedef ACE_InputCDR::to_string to_string; typedef ACE_InputCDR::to_wstring to_wstring; - // This one's not in ACE. + // These are not in ACE. + struct TAO_Export to_object { // This signature reflects the change set out in @@ -250,7 +251,19 @@ public: CORBA::Object_ptr &ref_; }; - // extraction of the special types + struct TAO_Export to_abstract_base + { + to_abstract_base (CORBA_AbstractBase_ptr &obj); + CORBA::AbstractBase_ptr &ref_; + }; + + struct TAO_Export to_value + { + to_value (CORBA_ValueBase *&base); + CORBA::ValueBase *&ref_; + }; + + // Extraction of the special types. /// extract a boolean CORBA::Boolean operator>>= (to_boolean) const; @@ -273,6 +286,12 @@ public: /// extract an object reference CORBA::Boolean operator>>= (to_object) const; + /// extract an abstract interface + CORBA::Boolean operator>>= (to_abstract_base) const; + + /// extract a valuetype + CORBA::Boolean operator>>= (to_value) const; + // the following are unsafe operations // ORBOS/90-01-11, pg 672: For C++ mapping using the CORBA_Environment // parameter, two forms of the replace method are provided. diff --git a/TAO/tao/Any.i b/TAO/tao/Any.i index a3656c26813..eb243d46614 100644 --- a/TAO/tao/Any.i +++ b/TAO/tao/Any.i @@ -39,6 +39,18 @@ CORBA_Any::to_object::to_object (CORBA_Object_out obj) { } +ACE_INLINE +CORBA_Any::to_abstract_base::to_abstract_base (CORBA_AbstractBase_ptr &obj) + : ref_ (obj) +{ +} + +ACE_INLINE +CORBA_Any::to_value::to_value (CORBA_ValueBase *&obj) + : ref_ (obj) +{ +} + // ************************************************************* // Inline operations for class CORBA_Any_var // ************************************************************* diff --git a/TAO/tao/ClientRequestInfo_i.cpp b/TAO/tao/ClientRequestInfo_i.cpp index 995b1bd1344..de3a8b3c417 100644 --- a/TAO/tao/ClientRequestInfo_i.cpp +++ b/TAO/tao/ClientRequestInfo_i.cpp @@ -3,6 +3,7 @@ #include "ClientRequestInfo_i.h" #include "Invocation.h" #include "Stub.h" +#include "AbstractBase.h" #include "Profile.h" #include "Tagged_Components.h" #include "debug.h" @@ -21,6 +22,46 @@ TAO_ClientRequestInfo_i::TAO_ClientRequestInfo_i (TAO_GIOP_Invocation *inv, CORBA::Object_ptr target) : invocation_ (inv), target_ (target), // No need to duplicate. + abstract_target_ (CORBA::AbstractBase::_nil ()), + caught_exception_ (0), + response_expected_ (1), + reply_status_ (-1), + rs_pi_current_ () +{ + + // Retrieve the thread scope current (no TSS access incurred yet). + TAO_PICurrent *pi_current = inv->orb_core ()->pi_current (); + + // If the slot count is zero, then there is nothing to copy. + // Prevent any copying (and hence TSS accesses) from occurring. + if (pi_current != 0 && pi_current->slot_count () != 0) + { + // Retrieve the thread scope current. + TAO_PICurrent_Impl *tsc = pi_current->tsc (); + + // Copy the TSC to the RSC. + this->rs_pi_current_.copy (*tsc, 0); // Shallow copy + + // PICurrent will potentially have to call back on the request + // scope current so that it can deep copy the contents of the + // thread scope current if the contents of the thread scope + // current are about to be modified. It is necessary to do this + // deep copy once in order to completely isolate the request + // scope current from the thread scope current. This is only + // necessary, if the thread scope current is modified after its + // contents have been *logically* copied to the request scope + // current. + tsc->pi_peer (&this->rs_pi_current_); + } +} + +TAO_ClientRequestInfo_i::TAO_ClientRequestInfo_i ( + TAO_GIOP_Invocation *inv, + CORBA::AbstractBase_ptr abstract_target + ) + : invocation_ (inv), + target_ (CORBA::Object::_nil ()), + abstract_target_ (abstract_target), // No need to duplicate. caught_exception_ (0), response_expected_ (1), reply_status_ (-1), @@ -61,6 +102,11 @@ CORBA::Object_ptr TAO_ClientRequestInfo_i::target (ACE_ENV_SINGLE_ARG_DECL_NOT_USED) ACE_THROW_SPEC ((CORBA::SystemException)) { + if (CORBA::is_nil (this->target_)) + { + return this->abstract_target_->_to_object (); + } + return CORBA::Object::_duplicate (this->target_); } @@ -76,6 +122,11 @@ TAO_ClientRequestInfo_i::effective_target (ACE_ENV_SINGLE_ARG_DECL_NOT_USED) return this->invocation_->forward_reference (); } + if (CORBA::is_nil (this->target_)) + { + return this->abstract_target_->_to_object (); + } + return CORBA::Object::_duplicate (this->target_); } diff --git a/TAO/tao/ClientRequestInfo_i.h b/TAO/tao/ClientRequestInfo_i.h index 2f9ac946964..49639e6a8ef 100644 --- a/TAO/tao/ClientRequestInfo_i.h +++ b/TAO/tao/ClientRequestInfo_i.h @@ -44,10 +44,14 @@ class TAO_Export TAO_ClientRequestInfo_i { public: - /// Constructor. + /// Constructor from concrete interface. TAO_ClientRequestInfo_i (TAO_GIOP_Invocation *invocation, CORBA::Object_ptr target); + /// Constructor from abstract interface. + TAO_ClientRequestInfo_i (TAO_GIOP_Invocation *invocation, + CORBA::AbstractBase_ptr abstract_target); + /// Destructor. virtual ~TAO_ClientRequestInfo_i (void); @@ -235,6 +239,9 @@ protected: /// Reference to the target object. CORBA::Object_ptr target_; + /// Reference to the abstract interface target. + CORBA::AbstractBase_ptr abstract_target_; + /// Pointer to the caught exception. CORBA::Exception *caught_exception_; diff --git a/TAO/tao/DynamicAny/DynCommon.cpp b/TAO/tao/DynamicAny/DynCommon.cpp index b809c617510..790e329b834 100644 --- a/TAO/tao/DynamicAny/DynCommon.cpp +++ b/TAO/tao/DynamicAny/DynCommon.cpp @@ -756,7 +756,7 @@ TAO_DynCommon::insert_dyn_any (DynamicAny::DynAny_ptr value ACE_CHECK; } -#ifdef TAO_HAS_VALUETYPE +#if defined (TAO_HAS_VALUETYPE) void TAO_DynCommon::insert_val (CORBA::ValueBase_ptr ACE_ENV_ARG_DECL) @@ -1459,7 +1459,7 @@ TAO_DynCommon::get_dyn_any (ACE_ENV_SINGLE_ARG_DECL) ACE_ENV_ARG_PARAMETER); } -#ifdef TAO_HAS_VALUETYPE +#if defined (TAO_HAS_VALUETYPE) CORBA::ValueBase_ptr TAO_DynCommon::get_val (ACE_ENV_SINGLE_ARG_DECL) ACE_THROW_SPEC (( diff --git a/TAO/tao/DynamicAny/DynCommon.h b/TAO/tao/DynamicAny/DynCommon.h index eaa75c8c3e9..6f94aacebb7 100644 --- a/TAO/tao/DynamicAny/DynCommon.h +++ b/TAO/tao/DynamicAny/DynCommon.h @@ -255,7 +255,7 @@ public: DynamicAny::DynAny::InvalidValue )); -#ifdef TAO_HAS_VALUETYPE +#if defined (TAO_HAS_VALUETYPE) virtual void insert_val ( CORBA::ValueBase_ptr value ACE_ENV_ARG_DECL_WITH_DEFAULTS) @@ -438,7 +438,7 @@ public: DynamicAny::DynAny::InvalidValue )); -#ifdef TAO_HAS_VALUETYPE +#if defined (TAO_HAS_VALUETYPE) virtual CORBA::ValueBase_ptr get_val ( ACE_ENV_SINGLE_ARG_DECL_WITH_DEFAULTS) diff --git a/TAO/tao/Messaging/MessagingC.cpp b/TAO/tao/Messaging/MessagingC.cpp index 29105ffd318..9b35fb2b39b 100644 --- a/TAO/tao/Messaging/MessagingC.cpp +++ b/TAO/tao/Messaging/MessagingC.cpp @@ -5457,31 +5457,44 @@ CORBA::Boolean Messaging::ExceptionHolder::_tao_unmarshal_v (TAO_InputCDR & strm return this->_tao_unmarshal__Messaging_ExceptionHolder (strm); } -CORBA::Boolean Messaging::ExceptionHolder::_tao_unmarshal (TAO_InputCDR &strm, ExceptionHolder *&new_object) -{ - CORBA::Boolean retval = 1; - CORBA::ValueBase *base; // %! should be a _var - CORBA::ValueFactory_ptr factory; // %! should be a _var - if (!CORBA::ValueBase::_tao_unmarshal_pre (strm, factory, base, - ExceptionHolder::_tao_obv_static_repository_id ()) ) +CORBA::Boolean Messaging::ExceptionHolder::_tao_unmarshal ( + TAO_InputCDR &strm, + ExceptionHolder *&new_object + ) +{ + CORBA::ValueBase *base; + CORBA::ValueFactory_var factory; + CORBA::Boolean retval = + CORBA::ValueBase::_tao_unmarshal_pre ( + strm, + factory.out (), + base, + ExceptionHolder::_tao_obv_static_repository_id () + ); + + if (retval == 0 || factory.in () == 0) { return 0; } - if (factory != 0) + + base = factory->create_for_unmarshal (); + + if (base == 0) { - base = factory->create_for_unmarshal (); - factory->_remove_ref (); - if (base == 0) return 0; // %! except.? - //%! ACE_DEBUG ((LM_DEBUG, "Messaging::ExceptionHolder::_tao_unmarshal %s\n", base->_tao_obv_repository_id () )); - retval = base->_tao_unmarshal_v (strm); - //%! ACE_DEBUG ((LM_DEBUG, "Messaging::ExceptionHolder::_tao_unmarshal retval unmarshal_v is %d\n", retval)); - if (!retval) return 0; + return 0; // %! except.? } + + retval = base->_tao_unmarshal_v (strm); + + if (!retval) + { + return 0; + } + // Now base must be null or point to the unmarshaled object. // Align the pointer to the right subobject. new_object = ExceptionHolder::_downcast (base); - // %! unmarshal_post - return 1; + return retval; } Messaging::ExceptionHolder_init::ExceptionHolder_init () diff --git a/TAO/tao/ORB.cpp b/TAO/tao/ORB.cpp index 2cc143792ce..76bff005891 100644 --- a/TAO/tao/ORB.cpp +++ b/TAO/tao/ORB.cpp @@ -180,7 +180,7 @@ CORBA_ORB::~CORBA_ORB (void) // This destructor is only invoked when the last ORB reference (not // instance) is being destroyed. -# ifdef TAO_HAS_VALUETYPE +# if defined (TAO_HAS_VALUETYPE) // delete valuetype_factory_map_; // @@ not really, its a singleton # endif /* TAO_HAS_VALUETYPE */ @@ -1990,13 +1990,12 @@ CORBA_ORB::set_timeout (ACE_Time_Value *timeout) // Valuetype factory operations // ************************************************************* -#ifdef TAO_HAS_VALUETYPE +#if defined (TAO_HAS_VALUETYPE) -CORBA::ValueFactory_ptr -CORBA_ORB::register_value_factory ( - const char *repository_id, - CORBA::ValueFactory_ptr factory - ACE_ENV_ARG_DECL) +CORBA::ValueFactory +CORBA_ORB::register_value_factory (const char *repository_id, + CORBA::ValueFactory factory + ACE_ENV_ARG_DECL) { // %! guard, and ACE_Null_Mutex in the map // do _add_ref here not in map->rebind @@ -2031,7 +2030,7 @@ CORBA_ORB::unregister_value_factory (const char * /* repository_id */ // %! TODO } -CORBA::ValueFactory_ptr +CORBA::ValueFactory CORBA_ORB::lookup_value_factory (const char *repository_id ACE_ENV_ARG_DECL_NOT_USED) { @@ -2039,10 +2038,15 @@ CORBA_ORB::lookup_value_factory (const char *repository_id // do _add_ref here not in map->find if (valuetype_factory_map_) { - CORBA::ValueFactory_ptr factory; - int result = valuetype_factory_map_->find (repository_id, factory); + CORBA::ValueFactory factory; + int result = valuetype_factory_map_->find (repository_id, + factory); + if (result == -1) - factory = 0; // %! raise exception ! + { + factory = 0; // %! raise exception ! + } + return factory; } else diff --git a/TAO/tao/ORB.h b/TAO/tao/ORB.h index 109b52ad0aa..8dc4f944a80 100644 --- a/TAO/tao/ORB.h +++ b/TAO/tao/ORB.h @@ -52,7 +52,7 @@ class TAO_Stub; class TAO_Acceptor_Filter; -#ifdef TAO_HAS_VALUETYPE +#if defined (TAO_HAS_VALUETYPE) class TAO_ValueFactory_Map; #endif /* TAO_HAS_VALUETYPE */ @@ -146,15 +146,15 @@ public: ACE_ENV_ARG_DECL_WITH_DEFAULTS); -#ifdef TAO_HAS_VALUETYPE +#if defined (TAO_HAS_VALUETYPE) // Value factory operations (CORBA 2.3 ptc/98-10-05 Ch. 4.2 p.4-7) - CORBA::ValueFactory_ptr register_value_factory ( + CORBA::ValueFactory register_value_factory ( const char *repository_id, - CORBA::ValueFactory_ptr factory + CORBA::ValueFactory factory ACE_ENV_ARG_DECL_WITH_DEFAULTS ); void unregister_value_factory (const char * repository_id ACE_ENV_ARG_DECL_WITH_DEFAULTS ); - CORBA::ValueFactory_ptr lookup_value_factory ( + CORBA::ValueFactory lookup_value_factory ( const char *repository_id ACE_ENV_ARG_DECL_WITH_DEFAULTS ); #endif /* TAO_HAS_VALUETYPE */ diff --git a/TAO/tao/Object.h b/TAO/tao/Object.h index eea6a887f72..19553c26269 100644 --- a/TAO/tao/Object.h +++ b/TAO/tao/Object.h @@ -91,7 +91,7 @@ public: /// Is this a local object? virtual CORBA::Boolean _is_local (void) const; - virtual TAO_Abstract_ServantBase*_servant (void) const; + virtual TAO_Abstract_ServantBase *_servant (void) const; #if (TAO_HAS_MINIMUM_CORBA == 0) @@ -321,7 +321,8 @@ public: static CORBA::Object_ptr tao_duplicate (CORBA::Object_ptr); static void tao_release (CORBA::Object_ptr); static CORBA::Object_ptr tao_nil (void); - static CORBA::Object_ptr tao_narrow (CORBA::Object * ACE_ENV_ARG_DECL_NOT_USED); + static CORBA::Object_ptr tao_narrow (CORBA::Object * + ACE_ENV_ARG_DECL_NOT_USED); static CORBA::Object * tao_upcast (void *); private: diff --git a/TAO/tao/ObjectReferenceTemplateC.cpp b/TAO/tao/ObjectReferenceTemplateC.cpp index a80aab64ccd..c0e66b16033 100644 --- a/TAO/tao/ObjectReferenceTemplateC.cpp +++ b/TAO/tao/ObjectReferenceTemplateC.cpp @@ -461,31 +461,44 @@ PortableInterceptor::ObjectReferenceFactory::_tao_any_destructor (void *_tao_voi delete tmp; } -CORBA::Boolean PortableInterceptor::ObjectReferenceFactory::_tao_unmarshal (TAO_InputCDR &strm, ObjectReferenceFactory *&new_object) +CORBA::Boolean PortableInterceptor::ObjectReferenceFactory::_tao_unmarshal ( + TAO_InputCDR &strm, + ObjectReferenceFactory *&new_object + ) { - CORBA::Boolean retval = 1; - CORBA::ValueBase *base; // %! should be a _var - CORBA::ValueFactory_ptr factory; // %! should be a _var - if (!CORBA::ValueBase::_tao_unmarshal_pre (strm, factory, base, - ObjectReferenceFactory::_tao_obv_static_repository_id ()) ) + CORBA::ValueBase *base; + CORBA::ValueFactory_var factory; + CORBA::Boolean retval = + CORBA::ValueBase::_tao_unmarshal_pre ( + strm, + factory.out (), + base, + ObjectReferenceFactory::_tao_obv_static_repository_id () + ); + + if (retval == 0 || factory == 0) { return 0; } - if (factory != 0) + + base = factory->create_for_unmarshal (); + + if (base == 0) + { + return 0; // %! except.? + } + + retval = base->_tao_unmarshal_v (strm); + + if (retval == 0) { - base = factory->create_for_unmarshal (); - factory->_remove_ref (); - if (base == 0) return 0; // %! except.? - //%! ACE_DEBUG ((LM_DEBUG, "PortableInterceptor::ObjectReferenceFactory::_tao_unmarshal %s\n", base->_tao_obv_repository_id () )); - retval = base->_tao_unmarshal_v (strm); - //%! ACE_DEBUG ((LM_DEBUG, "PortableInterceptor::ObjectReferenceFactory::_tao_unmarshal retval unmarshal_v is %d\n", retval)); - if (!retval) return 0; + return 0; } + // Now base must be null or point to the unmarshaled object. // Align the pointer to the right subobject. new_object = ObjectReferenceFactory::_downcast (base); - // %! unmarshal_post - return 1; + return retval; } static const CORBA::Long _oc_PortableInterceptor_ObjectReferenceTemplate[] = @@ -632,6 +645,22 @@ PortableInterceptor::ObjectReferenceTemplate_var::_retn (void) return tmp; } +void +PortableInterceptor::ObjectReferenceTemplate_var::tao_add_ref ( + ObjectReferenceTemplate *p + ) +{ + CORBA::add_ref (p); +} + +void +PortableInterceptor::ObjectReferenceTemplate_var::tao_remove_ref ( + ObjectReferenceTemplate *p + ) +{ + CORBA::remove_ref (p); +} + // ************************************************************* // Operations for class PortableInterceptor::ObjectReferenceTemplate_out // ************************************************************* @@ -721,31 +750,44 @@ PortableInterceptor::ObjectReferenceTemplate::_tao_any_destructor (void *_tao_vo delete tmp; } -CORBA::Boolean PortableInterceptor::ObjectReferenceTemplate::_tao_unmarshal (TAO_InputCDR &strm, ObjectReferenceTemplate *&new_object) +CORBA::Boolean PortableInterceptor::ObjectReferenceTemplate::_tao_unmarshal ( + TAO_InputCDR &strm, + ObjectReferenceTemplate *&new_object + ) { - CORBA::Boolean retval = 1; - CORBA::ValueBase *base; // %! should be a _var - CORBA::ValueFactory_ptr factory; // %! should be a _var - if (!CORBA::ValueBase::_tao_unmarshal_pre (strm, factory, base, - ObjectReferenceTemplate::_tao_obv_static_repository_id ()) ) + CORBA::ValueBase *base; + CORBA::ValueFactory_var factory; + CORBA::Boolean retval = + CORBA::ValueBase::_tao_unmarshal_pre ( + strm, + factory.out (), + base, + ObjectReferenceTemplate::_tao_obv_static_repository_id () + ); + + if (retval == 0 || factory.in () == 0) { return 0; } - if (factory != 0) + + base = factory->create_for_unmarshal (); + + if (base == 0) + { + return 0; // %! except.? + } + + retval = base->_tao_unmarshal_v (strm); + + if (retval == 0) { - base = factory->create_for_unmarshal (); - factory->_remove_ref (); - if (base == 0) return 0; // %! except.? - //%! ACE_DEBUG ((LM_DEBUG, "PortableInterceptor::ObjectReferenceTemplate::_tao_unmarshal %s\n", base->_tao_obv_repository_id () )); - retval = base->_tao_unmarshal_v (strm); - //%! ACE_DEBUG ((LM_DEBUG, "PortableInterceptor::ObjectReferenceTemplate::_tao_unmarshal retval unmarshal_v is %d\n", retval)); - if (!retval) return 0; + return 0; } + // Now base must be null or point to the unmarshaled object. // Align the pointer to the right subobject. new_object = ObjectReferenceTemplate::_downcast (base); - // %! unmarshal_post - return 1; + return retval; } diff --git a/TAO/tao/ObjectReferenceTemplateC.h b/TAO/tao/ObjectReferenceTemplateC.h index d32217bbbe3..5d44a98a9a4 100644 --- a/TAO/tao/ObjectReferenceTemplateC.h +++ b/TAO/tao/ObjectReferenceTemplateC.h @@ -230,6 +230,11 @@ public: ObjectReferenceTemplate* &out (void); ObjectReferenceTemplate* _retn (void); ObjectReferenceTemplate* ptr (void) const; + + // Hooks used by template sequence and valuetype manager classes + // for non-defined forward declared valuetypes. + static void tao_add_ref (ObjectReferenceTemplate *); + static void tao_remove_ref (ObjectReferenceTemplate *); private: ObjectReferenceTemplate* ptr_; diff --git a/TAO/tao/PortableServer/Default_ORTC.cpp b/TAO/tao/PortableServer/Default_ORTC.cpp index ae7a24a82f0..441b52926aa 100644 --- a/TAO/tao/PortableServer/Default_ORTC.cpp +++ b/TAO/tao/PortableServer/Default_ORTC.cpp @@ -281,31 +281,44 @@ CORBA::Boolean TAO_Default_ORT::ObjectReferenceFactory::_tao_unmarshal_v (TAO_In return this->_tao_unmarshal__TAO_Default_ORT_ObjectReferenceFactory (strm); } -CORBA::Boolean TAO_Default_ORT::ObjectReferenceFactory::_tao_unmarshal (TAO_InputCDR &strm, ObjectReferenceFactory *&new_object) +CORBA::Boolean TAO_Default_ORT::ObjectReferenceFactory::_tao_unmarshal ( + TAO_InputCDR &strm, + ObjectReferenceFactory *&new_object + ) { - CORBA::Boolean retval = 1; - CORBA::ValueBase *base; // %! should be a _var - CORBA::ValueFactory_ptr factory; // %! should be a _var - if (!CORBA::ValueBase::_tao_unmarshal_pre (strm, factory, base, - ObjectReferenceFactory::_tao_obv_static_repository_id ()) ) + CORBA::ValueBase *base; + CORBA::ValueFactory_var factory; + CORBA::Boolean retval = + CORBA::ValueBase::_tao_unmarshal_pre ( + strm, + factory.out (), + base, + ObjectReferenceFactory::_tao_obv_static_repository_id () + ); + + if (retval == 0 || factory.in () == 0) { return 0; } - if (factory != 0) + + base = factory->create_for_unmarshal (); + + if (base == 0) { - base = factory->create_for_unmarshal (); - factory->_remove_ref (); - if (base == 0) return 0; // %! except.? - //%! ACE_DEBUG ((LM_DEBUG, "TAO_Default_ORT::ObjectReferenceFactory::_tao_unmarshal %s\n", base->_tao_obv_repository_id () )); - retval = base->_tao_unmarshal_v (strm); - //%! ACE_DEBUG ((LM_DEBUG, "TAO_Default_ORT::ObjectReferenceFactory::_tao_unmarshal retval unmarshal_v is %d\n", retval)); - if (!retval) return 0; + return 0; // %! except.? } + + retval = base->_tao_unmarshal_v (strm); + + if (retval == 0) + { + return 0; + } + // Now base must be null or point to the unmarshaled object. // Align the pointer to the right subobject. new_object = ObjectReferenceFactory::_downcast (base); - // %! unmarshal_post - return 1; + return retval; } static const CORBA::Long _oc_TAO_Default_ORT_ObjectReferenceTemplate[] = @@ -548,31 +561,44 @@ CORBA::Boolean TAO_Default_ORT::ObjectReferenceTemplate::_tao_unmarshal_v (TAO_I return this->_tao_unmarshal__TAO_Default_ORT_ObjectReferenceTemplate (strm); } -CORBA::Boolean TAO_Default_ORT::ObjectReferenceTemplate::_tao_unmarshal (TAO_InputCDR &strm, ObjectReferenceTemplate *&new_object) +CORBA::Boolean TAO_Default_ORT::ObjectReferenceTemplate::_tao_unmarshal ( + TAO_InputCDR &strm, + ObjectReferenceTemplate *&new_object + ) { - CORBA::Boolean retval = 1; - CORBA::ValueBase *base; // %! should be a _var - CORBA::ValueFactory_ptr factory; // %! should be a _var - if (!CORBA::ValueBase::_tao_unmarshal_pre (strm, factory, base, - ObjectReferenceTemplate::_tao_obv_static_repository_id ()) ) + CORBA::ValueBase *base; + CORBA::ValueFactory_var factory; + CORBA::Boolean retval = + CORBA::ValueBase::_tao_unmarshal_pre ( + strm, + factory.out (), + base, + ObjectReferenceTemplate::_tao_obv_static_repository_id () + ); + + if (retval == 0 || factory.in () == 0) { return 0; } - if (factory != 0) + + base = factory->create_for_unmarshal (); + + if (base == 0) { - base = factory->create_for_unmarshal (); - factory->_remove_ref (); - if (base == 0) return 0; // %! except.? - //%! ACE_DEBUG ((LM_DEBUG, "TAO_Default_ORT::ObjectReferenceTemplate::_tao_unmarshal %s\n", base->_tao_obv_repository_id () )); - retval = base->_tao_unmarshal_v (strm); - //%! ACE_DEBUG ((LM_DEBUG, "TAO_Default_ORT::ObjectReferenceTemplate::_tao_unmarshal retval unmarshal_v is %d\n", retval)); - if (!retval) return 0; + return 0; // %! except.? } + + retval = base->_tao_unmarshal_v (strm); + + if (retval == 0) + { + return 0; + } + // Now base must be null or point to the unmarshaled object. // Align the pointer to the right subobject. new_object = ObjectReferenceTemplate::_downcast (base); - // %! unmarshal_post - return 1; + return retval; } CORBA::Boolean diff --git a/TAO/tao/Sequence_T.cpp b/TAO/tao/Sequence_T.cpp index f22c7350642..dece80234c5 100644 --- a/TAO/tao/Sequence_T.cpp +++ b/TAO/tao/Sequence_T.cpp @@ -403,9 +403,88 @@ TAO_Pseudo_Object_Manager<T,T_var>::operator=(const T_var &p) // class TAO_Valuetype_Manager // ************************************************************* -template <class T, class T_var> TAO_Valuetype_Manager<T,T_var>& -TAO_Valuetype_Manager<T,T_var>:: - operator= (const TAO_Valuetype_Manager<T,T_var> &rhs) +template <class T, class T_var> +TAO_Valuetype_Manager<T,T_var> & +TAO_Valuetype_Manager<T,T_var>::operator= ( + const TAO_Valuetype_Manager<T,T_var> &rhs + ) +{ + if (this == &rhs) + { + return *this; + } + + if (this->release_) + { + T_var::tao_remove_ref (*this->ptr_); + *this->ptr_ = *rhs.ptr_; + T_var::tao_add_ref (*this->ptr_); + } + else + { + *this->ptr_ = *rhs.ptr_; + } + + return *this; +} + +template <class T, class T_var> +TAO_Valuetype_Manager<T,T_var> & +TAO_Valuetype_Manager<T,T_var>::operator= (T *p) +{ + if (this->release_) + { + // The semantics of the elements of a sequence are the same as + // that of a var variable. Therefore we will not duplicate the + // user provided pointer before assigning it to the internal + // variable. + T_var::tao_remove_ref (*this->ptr_); + *this->ptr_ = p; + } + else + { + *this->ptr_ = p; + } + + return *this; +} + +template <class T, class T_var> +TAO_Valuetype_Manager<T,T_var> & +TAO_Valuetype_Manager<T,T_var>::operator= (const T_var &p) +{ + if (this->release_) + { + // The semantics of the elements of a sequence are the same as + // that of a var variable. Therefore we duplicate p's + // pointer before assigning it to the internal + // variable. + if (*this->ptr_ != 0) + { + (*this->ptr_)->_remove_ref (); + } + + T_var::tao_remove_ref (*this->ptr_); + *this->ptr_ = p.in (); + T_var::tao_add_ref (*this->ptr_); + } + else + { + *this->ptr_ = p.in (); + } + + return *this; +} + +// ************************************************************* +// class TAO_Abstract_Manager +// ************************************************************* + +template <class T, class T_var> +TAO_Abstract_Manager<T,T_var> & +TAO_Abstract_Manager<T,T_var>::operator= ( + const TAO_Abstract_Manager<T,T_var> &rhs + ) { if (this == &rhs) { @@ -434,8 +513,9 @@ TAO_Valuetype_Manager<T,T_var>:: return *this; } -template <class T, class T_var>TAO_Valuetype_Manager<T,T_var> & -TAO_Valuetype_Manager<T,T_var>::operator=(T* p) +template <class T, class T_var> +TAO_Abstract_Manager<T,T_var> & +TAO_Abstract_Manager<T,T_var>::operator= (T *p) { if (this->release_) { @@ -458,8 +538,9 @@ TAO_Valuetype_Manager<T,T_var>::operator=(T* p) return *this; } -template <class T, class T_var>TAO_Valuetype_Manager<T,T_var> & -TAO_Valuetype_Manager<T,T_var>::operator=(const T_var &p) +template <class T, class T_var> +TAO_Abstract_Manager<T,T_var> & +TAO_Abstract_Manager<T,T_var>::operator= (const T_var &p) { if (this->release_) { @@ -1278,37 +1359,33 @@ TAO_Bounded_Pseudo_Sequence<T, T_var,MAX>::_shrink_buffer (CORBA::ULong nl, // Constructor for unbounded sequence. template <class T, class T_var> -TAO_Unbounded_Valuetype_Sequence<T,T_var>::TAO_Unbounded_Valuetype_Sequence ( +TAO_Unbounded_Valuetype_Sequence<T, T_var>::TAO_Unbounded_Valuetype_Sequence ( CORBA::ULong maximum ) : TAO_Unbounded_Base_Sequence ( maximum, - TAO_Unbounded_Valuetype_Sequence<T,T_var>::allocbuf (maximum) + TAO_Unbounded_Valuetype_Sequence<T, T_var>::allocbuf (maximum) ) { } template <class T, class T_var> -TAO_Unbounded_Valuetype_Sequence<T,T_var>::TAO_Unbounded_Valuetype_Sequence ( - const TAO_Unbounded_Valuetype_Sequence<T,T_var> &rhs +TAO_Unbounded_Valuetype_Sequence<T, T_var>::TAO_Unbounded_Valuetype_Sequence ( + const TAO_Unbounded_Valuetype_Sequence<T, T_var> &rhs ) : TAO_Unbounded_Base_Sequence (rhs) { if (rhs.buffer_ != 0) { T **tmp1 = - TAO_Unbounded_Valuetype_Sequence<T,T_var>::allocbuf (this->maximum_); + TAO_Unbounded_Valuetype_Sequence<T, T_var>::allocbuf (this->maximum_); T ** const tmp2 = ACE_reinterpret_cast (T ** ACE_CAST_CONST, rhs.buffer_); for (CORBA::ULong i = 0; i < rhs.length_; ++i) { - if (tmp2[i] != 0) - { - tmp2[i]->_add_ref (); - } - + T_var::tao_add_ref (tmp2[i]); tmp1[i] = tmp2[i]; } @@ -1321,15 +1398,18 @@ TAO_Unbounded_Valuetype_Sequence<T,T_var>::TAO_Unbounded_Valuetype_Sequence ( } template<class T, class T_var> -TAO_Unbounded_Valuetype_Sequence<T,T_var>::~TAO_Unbounded_Valuetype_Sequence (void) +TAO_Unbounded_Valuetype_Sequence<T, T_var>::~TAO_Unbounded_Valuetype_Sequence ( + void + ) { this->_deallocate_buffer (); } // assignment operator -template <class T, class T_var>TAO_Unbounded_Valuetype_Sequence<T,T_var>& -TAO_Unbounded_Valuetype_Sequence<T,T_var>::operator= ( - const TAO_Unbounded_Valuetype_Sequence<T,T_var> &rhs +template <class T, class T_var> +TAO_Unbounded_Valuetype_Sequence<T, T_var>& +TAO_Unbounded_Valuetype_Sequence<T, T_var>::operator= ( + const TAO_Unbounded_Valuetype_Sequence<T, T_var> &rhs ) { if (this == &rhs) @@ -1344,19 +1424,15 @@ TAO_Unbounded_Valuetype_Sequence<T,T_var>::operator= ( for (CORBA::ULong i = 0; i < this->length_; ++i) { - if (tmp[i] != 0) - { - tmp[i]->_remove_ref (); - } - + T_var::tao_remove_ref (tmp[i]); tmp[i] = 0; } if (this->maximum_ < rhs.maximum_) { - TAO_Unbounded_Valuetype_Sequence<T,T_var>::freebuf (tmp); + TAO_Unbounded_Valuetype_Sequence<T, T_var>::freebuf (tmp); this->buffer_ = - TAO_Unbounded_Valuetype_Sequence<T,T_var>::allocbuf (rhs.maximum_); + TAO_Unbounded_Valuetype_Sequence<T, T_var>::allocbuf (rhs.maximum_); } } else @@ -1368,7 +1444,9 @@ TAO_Unbounded_Valuetype_Sequence<T,T_var>::operator= ( else { this->buffer_ = - TAO_Unbounded_Valuetype_Sequence<T,T_var>::allocbuf (rhs.maximum_); + TAO_Unbounded_Valuetype_Sequence<T, T_var>::allocbuf ( + rhs.maximum_ + ); } } @@ -1381,19 +1459,16 @@ TAO_Unbounded_Valuetype_Sequence<T,T_var>::operator= ( for (CORBA::ULong i = 0; i < rhs.length_; ++i) { - if (tmp2[i] != 0) - { - tmp2[i]->_add_ref (); - } - + T_var::tao_add_ref (tmp2[i]); tmp1[i] = tmp2[i]; } return *this; } -template <class T, class T_var> T ** -TAO_Unbounded_Valuetype_Sequence<T,T_var>::allocbuf (CORBA::ULong nelems) +template <class T, class T_var> +T ** +TAO_Unbounded_Valuetype_Sequence<T, T_var>::allocbuf (CORBA::ULong nelems) { T **buf = 0; ACE_NEW_RETURN (buf, @@ -1408,8 +1483,9 @@ TAO_Unbounded_Valuetype_Sequence<T,T_var>::allocbuf (CORBA::ULong nelems) return buf; } -template <class T, class T_var> void -TAO_Unbounded_Valuetype_Sequence<T,T_var>::freebuf (T **buffer) +template <class T, class T_var> +void +TAO_Unbounded_Valuetype_Sequence<T, T_var>::freebuf (T **buffer) { if (buffer == 0) { @@ -1431,10 +1507,13 @@ TAO_Unbounded_Valuetype_Sequence<T,T_var>::freebuf (T **buffer) delete [] buffer; } -template<class T, class T_var> void -TAO_Unbounded_Valuetype_Sequence<T,T_var>::_allocate_buffer (CORBA::ULong length) +template<class T, class T_var> +void +TAO_Unbounded_Valuetype_Sequence<T, T_var>::_allocate_buffer ( + CORBA::ULong length + ) { - T **tmp = TAO_Unbounded_Valuetype_Sequence<T,T_var>::allocbuf (length); + T **tmp = TAO_Unbounded_Valuetype_Sequence<T, T_var>::allocbuf (length); if (this->buffer_ != 0) { @@ -1449,11 +1528,7 @@ TAO_Unbounded_Valuetype_Sequence<T,T_var>::_allocate_buffer (CORBA::ULong length // the old instances. if (!this->release_) { - if (old[i] != 0) - { - old[i]->_add_ref (); - } - + T_var::tao_add_ref (tmp[i]); tmp[i] = old[i]; } else @@ -1466,11 +1541,12 @@ TAO_Unbounded_Valuetype_Sequence<T,T_var>::_allocate_buffer (CORBA::ULong length delete [] old; } } + this->buffer_ = tmp; } template<class T, class T_var> void -TAO_Unbounded_Valuetype_Sequence<T,T_var>::_deallocate_buffer (void) +TAO_Unbounded_Valuetype_Sequence<T, T_var>::_deallocate_buffer (void) { if (this->buffer_ == 0 || this->release_ == 0) { @@ -1482,32 +1558,24 @@ TAO_Unbounded_Valuetype_Sequence<T,T_var>::_deallocate_buffer (void) for (CORBA::ULong i = 0; i < this->length_; ++i) { - if (tmp[i] != 0) - { - tmp[i]->_remove_ref (); - } - + T_var::tao_remove_ref (tmp[i]); tmp[i] = 0; } - TAO_Unbounded_Valuetype_Sequence<T,T_var>::freebuf (tmp); + TAO_Unbounded_Valuetype_Sequence<T, T_var>::freebuf (tmp); this->buffer_ = 0; } template<class T, class T_var> void -TAO_Unbounded_Valuetype_Sequence<T,T_var>::_shrink_buffer (CORBA::ULong nl, - CORBA::ULong ol) +TAO_Unbounded_Valuetype_Sequence<T ,T_var>::_shrink_buffer (CORBA::ULong nl, + CORBA::ULong ol) { T **tmp = ACE_static_cast (T**, this->buffer_); for (CORBA::ULong i = nl; i < ol; ++i) { - if (tmp[i] != 0) - { - tmp[i]->_remove_ref (); - } - + T_var::tao_remove_ref (tmp[i]); tmp[i] = 0; } } @@ -1517,37 +1585,33 @@ TAO_Unbounded_Valuetype_Sequence<T,T_var>::_shrink_buffer (CORBA::ULong nl, // ************************************************************* template <class T, class T_var, size_t MAX> -TAO_Bounded_Valuetype_Sequence<T, T_var,MAX>::TAO_Bounded_Valuetype_Sequence ( +TAO_Bounded_Valuetype_Sequence<T, T_var, MAX>::TAO_Bounded_Valuetype_Sequence ( void ) : TAO_Bounded_Base_Sequence ( MAX, - TAO_Bounded_Valuetype_Sequence<T, T_var,MAX>::allocbuf (MAX) + TAO_Bounded_Valuetype_Sequence<T, T_var, MAX>::allocbuf (MAX) ) { } template <class T, class T_var, size_t MAX> -TAO_Bounded_Valuetype_Sequence<T, T_var,MAX>::TAO_Bounded_Valuetype_Sequence ( - const TAO_Bounded_Valuetype_Sequence<T, T_var,MAX> &rhs +TAO_Bounded_Valuetype_Sequence<T, T_var, MAX>::TAO_Bounded_Valuetype_Sequence ( + const TAO_Bounded_Valuetype_Sequence<T, T_var, MAX> &rhs ) : TAO_Bounded_Base_Sequence (rhs) { if (rhs.buffer_ != 0) { T **tmp1 = - TAO_Bounded_Valuetype_Sequence<T, T_var,MAX>::allocbuf (MAX); + TAO_Bounded_Valuetype_Sequence<T, T_var, MAX>::allocbuf (MAX); T ** const tmp2 = ACE_reinterpret_cast (T** ACE_CAST_CONST, rhs.buffer_); for (CORBA::ULong i = 0; i < rhs.length_; i++) { - if (tmp2[i] != 0) - { - tmp2[i]->_add_ref (); - } - + T_var::tao_add_ref (tmp2[i]); tmp1[i] = tmp2[i]; } @@ -1559,9 +1623,10 @@ TAO_Bounded_Valuetype_Sequence<T, T_var,MAX>::TAO_Bounded_Valuetype_Sequence ( } } -template <class T, class T_var, size_t MAX> TAO_Bounded_Valuetype_Sequence<T, T_var,MAX>& -TAO_Bounded_Valuetype_Sequence<T, T_var,MAX>::operator= ( - const TAO_Bounded_Valuetype_Sequence<T,T_var, MAX> &rhs +template <class T, class T_var, size_t MAX> +TAO_Bounded_Valuetype_Sequence<T, T_var, MAX>& +TAO_Bounded_Valuetype_Sequence<T, T_var, MAX>::operator= ( + const TAO_Bounded_Valuetype_Sequence<T, T_var, MAX> &rhs ) { if (this == &rhs) @@ -1576,11 +1641,7 @@ TAO_Bounded_Valuetype_Sequence<T, T_var,MAX>::operator= ( for (CORBA::ULong i = 0; i < this->length_; ++i) { - if (tmp[i] != 0) - { - tmp[i]->_remove_ref (); - } - + T_var::tao_remove_ref (tmp[i]); tmp[i] = 0; } // No need to reallocate the buffer since it is always of size @@ -1595,7 +1656,9 @@ TAO_Bounded_Valuetype_Sequence<T, T_var,MAX>::operator= ( else { this->buffer_ = - TAO_Bounded_Valuetype_Sequence<T,T_var,MAX>::allocbuf (rhs.maximum_); + TAO_Bounded_Valuetype_Sequence<T, T_var, MAX>::allocbuf ( + rhs.maximum_ + ); } } @@ -1608,19 +1671,16 @@ TAO_Bounded_Valuetype_Sequence<T, T_var,MAX>::operator= ( for (CORBA::ULong i=0; i < rhs.length_; ++i) { - if (tmp2[i] != 0) - { - tmp2[i]->_add_ref (); - } - + T_var::tao_add_ref (tmp2[i]); tmp1[i] = tmp2[i]; } return *this; } -template <class T, class T_var, size_t MAX> T ** -TAO_Bounded_Valuetype_Sequence<T, T_var,MAX>::allocbuf (CORBA::ULong) +template <class T, class T_var, size_t MAX> +T ** +TAO_Bounded_Valuetype_Sequence<T, T_var, MAX>::allocbuf (CORBA::ULong) { T **buf = 0; ACE_NEW_RETURN (buf, @@ -1635,8 +1695,9 @@ TAO_Bounded_Valuetype_Sequence<T, T_var,MAX>::allocbuf (CORBA::ULong) return buf; } -template <class T, class T_var, size_t MAX> void -TAO_Bounded_Valuetype_Sequence<T, T_var,MAX>::freebuf (T **buffer) +template <class T, class T_var, size_t MAX> +void +TAO_Bounded_Valuetype_Sequence<T, T_var, MAX>::freebuf (T **buffer) { // How much do we deallocate? Easy! allocbuf() always creates MAX // elements and initialize them to T::_nil(). So we can be @@ -1645,11 +1706,7 @@ TAO_Bounded_Valuetype_Sequence<T, T_var,MAX>::freebuf (T **buffer) { if (buffer[i] != 0) { - if (buffer[i] != 0) - { - buffer[i]->_remove_ref (); - } - + T_var::tao_remove_ref (buffer[i]); buffer[i] = 0; } } @@ -1657,19 +1714,21 @@ TAO_Bounded_Valuetype_Sequence<T, T_var,MAX>::freebuf (T **buffer) delete [] buffer; } -template<class T, class T_var, size_t MAX> void -TAO_Bounded_Valuetype_Sequence<T, T_var,MAX>::_allocate_buffer ( +template<class T, class T_var, size_t MAX> +void +TAO_Bounded_Valuetype_Sequence<T, T_var, MAX>::_allocate_buffer ( CORBA::ULong length ) { // For this class memory is never reallocated so the implementation // is *really* simple. this->buffer_ = - TAO_Bounded_Valuetype_Sequence<T, T_var,MAX>::allocbuf (length); + TAO_Bounded_Valuetype_Sequence<T, T_var, MAX>::allocbuf (length); } -template<class T, class T_var, size_t MAX> void -TAO_Bounded_Valuetype_Sequence<T,T_var,MAX>::_deallocate_buffer (void) +template<class T, class T_var, size_t MAX> +void +TAO_Bounded_Valuetype_Sequence<T, T_var, MAX>::_deallocate_buffer (void) { if (this->release_ == 0) { @@ -1678,11 +1737,12 @@ TAO_Bounded_Valuetype_Sequence<T,T_var,MAX>::_deallocate_buffer (void) T **tmp = ACE_reinterpret_cast (T **, this->buffer_); - TAO_Bounded_Valuetype_Sequence<T,T_var,MAX>::freebuf (tmp); + TAO_Bounded_Valuetype_Sequence<T, T_var, MAX>::freebuf (tmp); this->buffer_ = 0; } -template<class T, class T_var, size_t MAX> void +template<class T, class T_var, size_t MAX> +void TAO_Bounded_Valuetype_Sequence<T,T_var, MAX>::_shrink_buffer (CORBA::ULong nl, CORBA::ULong ol) { @@ -1691,12 +1751,406 @@ TAO_Bounded_Valuetype_Sequence<T,T_var, MAX>::_shrink_buffer (CORBA::ULong nl, for (CORBA::ULong i = nl; i < ol; ++i) { - if (tmp[i] != 0) + T_var::tao_remove_ref (tmp[i]); + tmp[i] = 0; + } +} + +// ************************************************************* +// Operations for class TAO_Unbounded_Abstract_Sequence +// ************************************************************* + +// Constructor for unbounded sequence. +template <class T, class T_var> +TAO_Unbounded_Abstract_Sequence<T, T_var>::TAO_Unbounded_Abstract_Sequence ( + CORBA::ULong maximum + ) + : TAO_Unbounded_Base_Sequence ( + maximum, + TAO_Unbounded_Abstract_Sequence<T, T_var>::allocbuf (maximum) + ) +{ +} + +template <class T, class T_var> +TAO_Unbounded_Abstract_Sequence<T, T_var>::TAO_Unbounded_Abstract_Sequence ( + const TAO_Unbounded_Abstract_Sequence<T, T_var> &rhs + ) + : TAO_Unbounded_Base_Sequence (rhs) +{ + if (rhs.buffer_ != 0) + { + T **tmp1 = + TAO_Unbounded_Abstract_Sequence<T, T_var>::allocbuf (this->maximum_); + T ** const tmp2 = + ACE_reinterpret_cast (T ** ACE_CAST_CONST, + rhs.buffer_); + + for (CORBA::ULong i = 0; i < rhs.length_; ++i) { - tmp[i]->_remove_ref (); + tmp1[i] = T_var::tao_duplicate (tmp2[i]); } - tmp[i] = 0; + this->buffer_ = tmp1; + } + else + { + this->buffer_ = 0; + } +} + +template<class T, class T_var> +TAO_Unbounded_Abstract_Sequence<T, T_var>::~TAO_Unbounded_Abstract_Sequence ( + void + ) +{ + this->_deallocate_buffer (); +} + +// assignment operator +template <class T, class T_var> +TAO_Unbounded_Abstract_Sequence<T, T_var>& +TAO_Unbounded_Abstract_Sequence<T, T_var>::operator= ( + const TAO_Unbounded_Abstract_Sequence<T, T_var> &rhs + ) +{ + if (this == &rhs) + { + return *this; + } + + if (this->release_) + { + T **tmp = ACE_reinterpret_cast (T **, + this->buffer_); + + for (CORBA::ULong i = 0; i < this->length_; ++i) + { + T_var::tao_release (tmp[i]); + tmp[i] = T_var::tao_nil (); + } + + if (this->maximum_ < rhs.maximum_) + { + TAO_Unbounded_Abstract_Sequence<T, T_var>::freebuf (tmp); + this->buffer_ = + TAO_Unbounded_Abstract_Sequence<T, T_var>::allocbuf (rhs.maximum_); + } + } + else + { + if (rhs.maximum_ == 0) + { + this->buffer_ = 0; + } + else + { + this->buffer_ = + TAO_Unbounded_Abstract_Sequence<T, T_var>::allocbuf ( + rhs.maximum_ + ); + } + } + + TAO_Unbounded_Base_Sequence::operator= (rhs); + + T **tmp1 = ACE_reinterpret_cast (T **, + this->buffer_); + T ** const tmp2 = ACE_reinterpret_cast (T ** ACE_CAST_CONST, + rhs.buffer_); + + for (CORBA::ULong i = 0; i < rhs.length_; ++i) + { + tmp1[i] = T_var::tao_duplicate (tmp2[i]); + } + + return *this; +} + +template <class T, class T_var> +T ** +TAO_Unbounded_Abstract_Sequence<T, T_var>::allocbuf (CORBA::ULong nelems) +{ + T **buf = 0; + ACE_NEW_RETURN (buf, + T*[nelems], + 0); + + for (CORBA::ULong i = 0; i < nelems; i++) + { + buf[i] = T_var::tao_nil (); + } + + return buf; +} + +template <class T, class T_var> +void +TAO_Unbounded_Abstract_Sequence<T, T_var>::freebuf (T **buffer) +{ + if (buffer == 0) + { + return; + } + + // {orbos/97-05-15:16.11} The freebuf function ensures that the + // destructor for each element is called before the buffer is + // destroyed, except for string elements, which are freed using + // string_free(), and object reference elements, which are freed + // using release(). The freebuf function will ignore null pointers + // passed to it. + + // @@ How are we supposed to implement that! We don't know the + // length of the buffer here. + // Mark the length in the first four bytes? For the moment we let + // that be. + + delete [] buffer; +} + +template<class T, class T_var> +void +TAO_Unbounded_Abstract_Sequence<T, T_var>::_allocate_buffer ( + CORBA::ULong length + ) +{ + T **tmp = TAO_Unbounded_Abstract_Sequence<T, T_var>::allocbuf (length); + + if (this->buffer_ != 0) + { + T **old = ACE_reinterpret_cast (T**, + this->buffer_); + + for (CORBA::ULong i = 0; i < this->length_; ++i) + // Only call duplicate when we did not own the previous + // buffer, since after this method we own it we must also own + // the objects. If we already own the objects there is no + // need to copy them, if we did we would also have to remove + // the old instances. + if (!this->release_) + { + tmp[i] = T_var::tao_duplicate (old[i]); + } + else + { + tmp[i] = old[i]; + } + + if (this->release_) + { + delete [] old; + } + } + + this->buffer_ = tmp; +} + +template<class T, class T_var> void +TAO_Unbounded_Abstract_Sequence<T, T_var>::_deallocate_buffer (void) +{ + if (this->buffer_ == 0 || this->release_ == 0) + { + return; + } + + T **tmp = ACE_reinterpret_cast (T**, + this->buffer_); + + for (CORBA::ULong i = 0; i < this->length_; ++i) + { + T_var::tao_release (tmp[i]); + tmp[i] = T_var::tao_nil (); + } + + TAO_Unbounded_Abstract_Sequence<T, T_var>::freebuf (tmp); + this->buffer_ = 0; +} + +template<class T, class T_var> void +TAO_Unbounded_Abstract_Sequence<T ,T_var>::_shrink_buffer (CORBA::ULong nl, + CORBA::ULong ol) +{ + T **tmp = ACE_static_cast (T**, + this->buffer_); + + for (CORBA::ULong i = nl; i < ol; ++i) + { + T_var::tao_release (tmp[i]); + tmp[i] = T_var::tao_nil (); + } +} + +// ************************************************************* +// Operations for class TAO_Bounded_Abstract_Sequence +// ************************************************************* + +template <class T, class T_var, size_t MAX> +TAO_Bounded_Abstract_Sequence<T, T_var, MAX>::TAO_Bounded_Abstract_Sequence ( + void + ) + : TAO_Bounded_Base_Sequence ( + MAX, + TAO_Bounded_Abstract_Sequence<T, T_var, MAX>::allocbuf (MAX) + ) +{ +} + +template <class T, class T_var, size_t MAX> +TAO_Bounded_Abstract_Sequence<T, T_var, MAX>::TAO_Bounded_Abstract_Sequence ( + const TAO_Bounded_Abstract_Sequence<T, T_var, MAX> &rhs + ) + : TAO_Bounded_Base_Sequence (rhs) +{ + if (rhs.buffer_ != 0) + { + T **tmp1 = + TAO_Bounded_Abstract_Sequence<T, T_var, MAX>::allocbuf (MAX); + + T ** const tmp2 = + ACE_reinterpret_cast (T** ACE_CAST_CONST, rhs.buffer_); + + for (CORBA::ULong i = 0; i < rhs.length_; i++) + { + tmp1[i] = T_var::tao_duplicate (tmp2[i]); + } + + this->buffer_ = tmp1; + } + else + { + this->buffer_ = 0; + } +} + +template <class T, class T_var, size_t MAX> +TAO_Bounded_Abstract_Sequence<T, T_var, MAX>& +TAO_Bounded_Abstract_Sequence<T, T_var, MAX>::operator= ( + const TAO_Bounded_Abstract_Sequence<T, T_var, MAX> &rhs + ) +{ + if (this == &rhs) + { + return *this; + } + + if (this->release_) + { + T **tmp = ACE_reinterpret_cast (T **, + this->buffer_); + + for (CORBA::ULong i = 0; i < this->length_; ++i) + { + T_var::tao_release (tmp[i]); + tmp[i] = T_var::tao_nil (); + } + // No need to reallocate the buffer since it is always of size + // MAX + } + else + { + if (rhs.maximum_ == 0) + { + this->buffer_ = 0; + } + else + { + this->buffer_ = + TAO_Bounded_Abstract_Sequence<T, T_var, MAX>::allocbuf ( + rhs.maximum_ + ); + } + } + + TAO_Bounded_Base_Sequence::operator= (rhs); + + T **tmp1 = ACE_reinterpret_cast (T **, + this->buffer_); + T ** const tmp2 = ACE_reinterpret_cast (T ** ACE_CAST_CONST, + rhs.buffer_); + + for (CORBA::ULong i=0; i < rhs.length_; ++i) + { + tmp1[i] = T_var::tao_duplicate (tmp2[i]); + } + + return *this; +} + +template <class T, class T_var, size_t MAX> +T ** +TAO_Bounded_Abstract_Sequence<T, T_var, MAX>::allocbuf (CORBA::ULong) +{ + T **buf = 0; + ACE_NEW_RETURN (buf, + T*[MAX], + 0); + + for (CORBA::ULong i = 0; i < MAX; ++i) + { + buf[i] = T_var::tao_nil (); + } + + return buf; +} + +template <class T, class T_var, size_t MAX> +void +TAO_Bounded_Abstract_Sequence<T, T_var, MAX>::freebuf (T **buffer) +{ + // How much do we deallocate? Easy! allocbuf() always creates MAX + // elements and initialize them to T::_nil(). So we can be + // complaint and call CORBA::release() on each one. + for (CORBA::ULong i = 0; i < MAX; ++i) + { + if (buffer[i] != T_var::tao_nil ()) + { + T_var::tao_release (buffer[i]); + buffer[i] = T_var::tao_nil (); + } + } + + delete [] buffer; +} + +template<class T, class T_var, size_t MAX> +void +TAO_Bounded_Abstract_Sequence<T, T_var, MAX>::_allocate_buffer ( + CORBA::ULong length + ) +{ + // For this class memory is never reallocated so the implementation + // is *really* simple. + this->buffer_ = + TAO_Bounded_Abstract_Sequence<T, T_var, MAX>::allocbuf (length); +} + +template<class T, class T_var, size_t MAX> +void +TAO_Bounded_Abstract_Sequence<T, T_var, MAX>::_deallocate_buffer (void) +{ + if (this->release_ == 0) + { + return; + } + + T **tmp = ACE_reinterpret_cast (T **, + this->buffer_); + TAO_Bounded_Abstract_Sequence<T, T_var, MAX>::freebuf (tmp); + this->buffer_ = 0; +} + +template<class T, class T_var, size_t MAX> +void +TAO_Bounded_Abstract_Sequence<T,T_var, MAX>::_shrink_buffer (CORBA::ULong nl, + CORBA::ULong ol) +{ + T **tmp = ACE_reinterpret_cast (T **, + this->buffer_); + + for (CORBA::ULong i = nl; i < ol; ++i) + { + T_var::tao_release (tmp[i]); + tmp[i] = T_var::tao_nil (); } } diff --git a/TAO/tao/Sequence_T.h b/TAO/tao/Sequence_T.h index 4b930afd63e..466db7d48c3 100644 --- a/TAO/tao/Sequence_T.h +++ b/TAO/tao/Sequence_T.h @@ -468,7 +468,8 @@ public: * only TAO_*_Object_Sequence would use it, but we have some * problems with friendship and templates. */ - TAO_Valuetype_Manager (T **, CORBA::Boolean release); + TAO_Valuetype_Manager (T **, + CORBA::Boolean release); /// Destructor, only releases the object if <release_> is true. ~TAO_Valuetype_Manager (void); @@ -523,6 +524,91 @@ private: // ************************************************************* + /** + * @class TAO_Abstract_Manager + * + * @brief Manager for abstract intefaces. + * + * An abstract interface can be either a valuetype or an object + * references, so a manager class is needed. + * + * @see TAO_Object_Manager + */ +template<class T, class T_var> +class TAO_Abstract_Manager +{ +// friend class TAO_Unbounded_Abstract_Sequence<T,T_var>; +public: + // = Initialization and termination methods. + /** + * Copy constructor, the semantics are non-trivial: + * + The referenced element is duplicated or not according to the + * release value on the <rhs>. + * + In any case a new reference to the same object is created. + */ + TAO_Abstract_Manager (const TAO_Abstract_Manager<T,T_var> &rhs); + + /** + * Constructor from address of an element, it should be private and + * only TAO_*_Object_Sequence would use it, but we have some + * problems with friendship and templates. + */ + TAO_Abstract_Manager (T **, + CORBA::Boolean release); + + /// Destructor, only releases the object if <release_> is true. + ~TAO_Abstract_Manager (void); + + /** + * Assignment from another managed type, only release if + * <this->release_> is true. + * @@ TODO what happens if rhs.release_ is true an this->relase_ is + * false? + */ + TAO_Abstract_Manager<T,T_var> &operator= (const TAO_Abstract_Manager<T,T_var> &rhs); + + /// Assignment from T *. + TAO_Abstract_Manager<T,T_var> &operator= (T *); + + /// Assignment from T_var. + TAO_Abstract_Manager<T,T_var> &operator= (const T_var &); + + /// Return pointer. + T *operator-> (void) const; + + /// Cast (read-only). + operator const T *() const; + + /// Cast. + operator T *&(); + + /// Cast (read-only) so that assignment from a structured + /// type to a T_var will make a copy. + operator const T_var () const; + + /// for in parameter. + T *in (void) const; + + /// for inout parameter. + T *& inout (void); + + /// for out parameter. + T *& out (void); + + /// for return type + T *_retn (void); + +private: + /// data member, notice that it is a pointer, to implement the + /// reference behavior for assignment. + T **ptr_; + + /// release flag based on parent's flag + CORBA::Boolean release_; +}; + +// ************************************************************* + /** * @class TAO_Unbounded_Object_Sequence * @@ -862,7 +948,9 @@ public: CORBA::Boolean release=0); /// Copy ctor, deep copies. - TAO_Unbounded_Valuetype_Sequence(const TAO_Unbounded_Valuetype_Sequence<T,T_var> &); + TAO_Unbounded_Valuetype_Sequence ( + const TAO_Unbounded_Valuetype_Sequence<T,T_var> & + ); /// The destructor releases all object reference memebrs and frees /// all string members. @@ -873,7 +961,9 @@ public: * members and frees all string members, and then performs a * deepcopy to create a new structure. */ - TAO_Unbounded_Valuetype_Sequence<T,T_var> &operator= (const TAO_Unbounded_Valuetype_Sequence <T,T_var> &); + TAO_Unbounded_Valuetype_Sequence<T,T_var> &operator= ( + const TAO_Unbounded_Valuetype_Sequence <T,T_var> & + ); /// read-write accessor TAO_Valuetype_Manager<T,T_var> operator[] (CORBA::ULong slot) const; @@ -918,13 +1008,17 @@ public: CORBA::Boolean release=0); /// Copy constructor. - TAO_Bounded_Valuetype_Sequence (const TAO_Bounded_Valuetype_Sequence<T,T_var,MAX> &); + TAO_Bounded_Valuetype_Sequence ( + const TAO_Bounded_Valuetype_Sequence<T,T_var,MAX> & + ); /// destructor ~TAO_Bounded_Valuetype_Sequence (void); /// Assignment from another Bounded sequence. - TAO_Bounded_Valuetype_Sequence &operator= (const TAO_Bounded_Valuetype_Sequence<T,T_var,MAX> &); + TAO_Bounded_Valuetype_Sequence &operator= ( + const TAO_Bounded_Valuetype_Sequence<T,T_var,MAX> & + ); /// Read-write accessor. TAO_Valuetype_Manager<T,T_var> operator[] (CORBA::ULong slot) const; @@ -948,6 +1042,125 @@ public: // ************************************************************* /** + * @class TAO_Unbounded_Abstract_Sequence + * + * @brief Parametric sequence for abstract interfaces + * + * @see TAO_Unbounded_Object_Sequence + */ +template<class T,class T_var> +class TAO_Unbounded_Abstract_Sequence : public TAO_Unbounded_Base_Sequence +{ +public: + // = Initialization and termination methods. + + // Default ctor. + TAO_Unbounded_Abstract_Sequence (void); + + /// Constructor with a "hint" for the maximum capacity. + TAO_Unbounded_Abstract_Sequence (CORBA::ULong max); + + /// Constructor with a given buffer. + TAO_Unbounded_Abstract_Sequence (CORBA::ULong maximum, + CORBA::ULong length, + T* *data, + CORBA::Boolean release=0); + + /// Copy ctor, deep copies. + TAO_Unbounded_Abstract_Sequence ( + const TAO_Unbounded_Abstract_Sequence<T,T_var> & + ); + + /// The destructor releases all object reference memebrs and frees + /// all string members. + ~TAO_Unbounded_Abstract_Sequence (void); + + /** + * The assignment operator first releases all object reference + * members and frees all string members, and then performs a + * deepcopy to create a new structure. + */ + TAO_Unbounded_Abstract_Sequence<T,T_var> &operator= ( + const TAO_Unbounded_Abstract_Sequence <T,T_var> & + ); + + /// read-write accessor + TAO_Abstract_Manager<T,T_var> operator[] (CORBA::ULong slot) const; + + /// The allocbuf function allocates a vector of T elements that can + /// be passed to the T *data constructor. + static T **allocbuf (CORBA::ULong); + + /// Release all the elements. + static void freebuf (T **); + + // The Base_Sequence functions, please see "tao/Sequence.h" + /// No default to workaround egcs problem with templates and + /// namespaces + virtual void _allocate_buffer (CORBA::ULong length); + virtual void _deallocate_buffer (void); + virtual void _shrink_buffer (CORBA::ULong new_length, + CORBA::ULong old_length); +}; + +// ************************************************************* + +/** + * @class TAO_Bounded_Abstract_Sequence + * + * @brief Parametric sequence for types that require managers. + * + * Please see the documentation for the unbounded case. + */ +template<class T, class T_var, size_t MAX> +class TAO_Bounded_Abstract_Sequence : public TAO_Bounded_Base_Sequence +{ +public: + // = Initialization and termination methods. + + // Default ctor. + TAO_Bounded_Abstract_Sequence (void); + + /// Constructor from data. + TAO_Bounded_Abstract_Sequence (CORBA::ULong length, + T* *value, + CORBA::Boolean release=0); + + /// Copy constructor. + TAO_Bounded_Abstract_Sequence ( + const TAO_Bounded_Abstract_Sequence<T,T_var,MAX> & + ); + + /// destructor + ~TAO_Bounded_Abstract_Sequence (void); + + /// Assignment from another Bounded sequence. + TAO_Bounded_Abstract_Sequence &operator= ( + const TAO_Bounded_Abstract_Sequence<T,T_var,MAX> & + ); + + /// Read-write accessor. + TAO_Abstract_Manager<T,T_var> operator[] (CORBA::ULong slot) const; + + /// Allocate storage for a sequence.. + static T **allocbuf (CORBA::ULong length); + + /// Free a buffer allocated by allocbuf() and release each element on + /// it. + static void freebuf (T **buffer); + + // The Base_Sequence functions, please see "tao/sequence.h" + /// No default to workaround egcs problem with templates and + /// namespaces + virtual void _allocate_buffer (CORBA::ULong length); + virtual void _deallocate_buffer (void); + virtual void _shrink_buffer (CORBA::ULong new_length, + CORBA::ULong old_length); +}; + +// ************************************************************* + +/** * @class TAO_Unbounded_Array_Sequence * * @brief Parametric sequence for arrays. diff --git a/TAO/tao/Sequence_T.i b/TAO/tao/Sequence_T.i index 7ecf78b9478..18e213d2323 100644 --- a/TAO/tao/Sequence_T.i +++ b/TAO/tao/Sequence_T.i @@ -348,14 +348,18 @@ TAO_Valuetype_Manager<T,T_var>::~TAO_Valuetype_Manager (void) } template <class T, class T_var> ACE_INLINE -TAO_Valuetype_Manager<T,T_var>::TAO_Valuetype_Manager (const TAO_Valuetype_Manager<T,T_var> &rhs) +TAO_Valuetype_Manager<T,T_var>::TAO_Valuetype_Manager ( + const TAO_Valuetype_Manager<T,T_var> &rhs + ) : ptr_ (rhs.ptr_), release_ (rhs.release_) { } template <class T, class T_var> ACE_INLINE -TAO_Valuetype_Manager<T,T_var>::TAO_Valuetype_Manager(T** buffer, CORBA::Boolean release) +TAO_Valuetype_Manager<T,T_var>::TAO_Valuetype_Manager( + T** buffer, CORBA::Boolean release + ) : ptr_ (buffer), release_ (release) { @@ -370,8 +374,7 @@ TAO_Valuetype_Manager<T,T_var>::operator-> (void) const template <class T, class T_var> ACE_INLINE TAO_Valuetype_Manager<T,T_var>::operator const T_var () const { - if (*this->ptr_ != 0) - (*this->ptr_)->_add_ref (); + T_var::tao_add_ref (*this->ptr_); return *this->ptr_; } @@ -402,8 +405,7 @@ TAO_Valuetype_Manager<T,T_var>::inout (void) template <class T, class T_var> ACE_INLINE T *& TAO_Valuetype_Manager<T,T_var>::out (void) { - if (*this->ptr_ != 0) - (*this->ptr_)->_remove_ref (); + T_var::tao_remove_ref (*this->ptr_); *this->ptr_ = 0; return *this->ptr_; } @@ -417,6 +419,94 @@ TAO_Valuetype_Manager<T,T_var>::_retn (void) } // ************************************************************* +// Inline operations for class TAO_Abstract_Manager +// ************************************************************* + +template <class T, class T_var> ACE_INLINE +TAO_Abstract_Manager<T,T_var>::~TAO_Abstract_Manager (void) +{ +} + +template <class T, class T_var> ACE_INLINE +TAO_Abstract_Manager<T,T_var>::TAO_Abstract_Manager ( + const TAO_Abstract_Manager<T,T_var> &rhs + ) + : ptr_ (rhs.ptr_), + release_ (rhs.release_) +{ +} + +template <class T, class T_var> ACE_INLINE +TAO_Abstract_Manager<T,T_var>::TAO_Abstract_Manager( + T** buffer, CORBA::Boolean release + ) + : ptr_ (buffer), + release_ (release) +{ +} + +template <class T, class T_var> ACE_INLINE T * +TAO_Abstract_Manager<T,T_var>::operator-> (void) const +{ + return *this->ptr_; +} + +template <class T, class T_var> ACE_INLINE +TAO_Abstract_Manager<T,T_var>::operator const T_var () const +{ + if (*this->ptr_ != 0) + { + (*this->ptr_)->_add_ref (); + } + + return *this->ptr_; +} + +template <class T, class T_var> ACE_INLINE +TAO_Abstract_Manager<T,T_var>::operator const T* () const // cast +{ + return *this->ptr_; +} + +template <class T, class T_var> ACE_INLINE +TAO_Abstract_Manager<T,T_var>::operator T* &() // cast +{ + return *this->ptr_; +} + +template <class T, class T_var> ACE_INLINE T * +TAO_Abstract_Manager<T,T_var>::in (void) const +{ + return *this->ptr_; +} + +template <class T, class T_var> ACE_INLINE T *& +TAO_Abstract_Manager<T,T_var>::inout (void) +{ + return *this->ptr_; +} + +template <class T, class T_var> ACE_INLINE T *& +TAO_Abstract_Manager<T,T_var>::out (void) +{ + if (*this->ptr_ != 0) + { + (*this->ptr_)->_remove_ref (); + } + + *this->ptr_ = 0; + return *this->ptr_; +} + +template <class T, class T_var> ACE_INLINE T * +TAO_Abstract_Manager<T,T_var>::_retn (void) +{ + T *temp = *this->ptr_; + *this->ptr_ = 0; + return temp; +} + +// ************************************************************* // class TAO_Unbounded_Object_Sequence // ************************************************************* @@ -533,54 +623,142 @@ TAO_Bounded_Pseudo_Sequence<T, T_var,MAX>::operator[] (CORBA::ULong slot) const // ************************************************************* //default constructor -template <class T, class T_var> ACE_INLINE -TAO_Unbounded_Valuetype_Sequence<T,T_var>::TAO_Unbounded_Valuetype_Sequence (void) +template <class T, class T_var> +ACE_INLINE +TAO_Unbounded_Valuetype_Sequence<T,T_var>::TAO_Unbounded_Valuetype_Sequence ( + void + ) +{ +} + +template <class T, class T_var> +ACE_INLINE +TAO_Unbounded_Valuetype_Sequence<T,T_var>::TAO_Unbounded_Valuetype_Sequence ( + CORBA::ULong maximum, + CORBA::ULong length, + T* *value, + CORBA::Boolean release + ) + : TAO_Unbounded_Base_Sequence (maximum, length, value, release) { } -template <class T, class T_var> ACE_INLINE -TAO_Unbounded_Valuetype_Sequence<T,T_var>:: -TAO_Unbounded_Valuetype_Sequence (CORBA::ULong maximum, - CORBA::ULong length, - T* *value, - CORBA::Boolean release) +template <class T, class T_var> +ACE_INLINE +TAO_Valuetype_Manager<T,T_var> +TAO_Unbounded_Valuetype_Sequence<T,T_var>::operator[] ( + CORBA::ULong slot + ) const +{ + ACE_ASSERT (slot < this->maximum_); + T ** const tmp = ACE_reinterpret_cast (T ** ACE_CAST_CONST, this->buffer_); + return TAO_Valuetype_Manager<T,T_var> (tmp + slot, this->release_); +} + +// ************************************************************* +// class TAO_Bounded_Valuetype_Sequence +// ************************************************************* + +template<class T, class T_var, size_t MAX> +ACE_INLINE +TAO_Bounded_Valuetype_Sequence<T,T_var,MAX>::~TAO_Bounded_Valuetype_Sequence ( + void + ) +{ + this->_deallocate_buffer (); +} + +template <class T, class T_var, size_t MAX> +ACE_INLINE +TAO_Bounded_Valuetype_Sequence<T,T_var,MAX>::TAO_Bounded_Valuetype_Sequence ( + CORBA::ULong length, + T **value, + CORBA::Boolean release + ) + : TAO_Bounded_Base_Sequence (MAX, length, value, release) +{ +} + +template <class T, class T_var, size_t MAX> +ACE_INLINE +TAO_Valuetype_Manager<T,T_var> +TAO_Bounded_Valuetype_Sequence<T, T_var, MAX>::operator[] ( + CORBA::ULong slot + ) const +{ + ACE_ASSERT (slot < this->maximum_); + T **const tmp = ACE_reinterpret_cast (T ** ACE_CAST_CONST, this->buffer_); + return TAO_Valuetype_Manager<T,T_var> (tmp + slot, this->release_); +} + +// ************************************************************* +// class TAO_Unbounded_Abstract_Sequence +// ************************************************************* + +//default constructor +template <class T, class T_var> +ACE_INLINE +TAO_Unbounded_Abstract_Sequence<T,T_var>::TAO_Unbounded_Abstract_Sequence ( + void + ) +{ +} + +template <class T, class T_var> +ACE_INLINE +TAO_Unbounded_Abstract_Sequence<T,T_var>::TAO_Unbounded_Abstract_Sequence ( + CORBA::ULong maximum, + CORBA::ULong length, + T* *value, + CORBA::Boolean release + ) : TAO_Unbounded_Base_Sequence (maximum, length, value, release) { } -template <class T, class T_var> ACE_INLINE TAO_Valuetype_Manager<T,T_var> -TAO_Unbounded_Valuetype_Sequence<T,T_var>::operator[] (CORBA::ULong slot) const +template <class T, class T_var> +ACE_INLINE +TAO_Abstract_Manager<T,T_var> +TAO_Unbounded_Abstract_Sequence<T,T_var>::operator[] (CORBA::ULong slot) const { ACE_ASSERT (slot < this->maximum_); T ** const tmp = ACE_reinterpret_cast (T ** ACE_CAST_CONST, this->buffer_); - return TAO_Valuetype_Manager<T,T_var> (tmp + slot, this->release_); + return TAO_Abstract_Manager<T,T_var> (tmp + slot, this->release_); } // ************************************************************* -// class TAO_Bounded_Valuetype_Sequence +// class TAO_Bounded_Abstract_Sequence // ************************************************************* -template<class T, class T_var, size_t MAX> ACE_INLINE -TAO_Bounded_Valuetype_Sequence<T,T_var,MAX>::~TAO_Bounded_Valuetype_Sequence (void) +template<class T, class T_var, size_t MAX> +ACE_INLINE +TAO_Bounded_Abstract_Sequence<T,T_var,MAX>::~TAO_Bounded_Abstract_Sequence ( + void + ) { this->_deallocate_buffer (); } template <class T, class T_var, size_t MAX> ACE_INLINE -TAO_Bounded_Valuetype_Sequence<T,T_var,MAX>:: -TAO_Bounded_Valuetype_Sequence (CORBA::ULong length, - T **value, - CORBA::Boolean release) +TAO_Bounded_Abstract_Sequence<T,T_var,MAX>::TAO_Bounded_Abstract_Sequence ( + CORBA::ULong length, + T **value, + CORBA::Boolean release + ) : TAO_Bounded_Base_Sequence (MAX, length, value, release) { } -template <class T, class T_var, size_t MAX> ACE_INLINE TAO_Valuetype_Manager<T,T_var> -TAO_Bounded_Valuetype_Sequence<T, T_var,MAX>::operator[] (CORBA::ULong slot) const +template <class T, class T_var, size_t MAX> +ACE_INLINE +TAO_Abstract_Manager<T,T_var> +TAO_Bounded_Abstract_Sequence<T, T_var, MAX>::operator[] ( + CORBA::ULong slot + ) const { ACE_ASSERT (slot < this->maximum_); T **const tmp = ACE_reinterpret_cast (T ** ACE_CAST_CONST, this->buffer_); - return TAO_Valuetype_Manager<T,T_var> (tmp + slot, this->release_); + return TAO_Abstract_Manager<T,T_var> (tmp + slot, this->release_); } // ************************************************************* diff --git a/TAO/tao/TAO.dsp b/TAO/tao/TAO.dsp index c30063ea89a..792283b838e 100644 --- a/TAO/tao/TAO.dsp +++ b/TAO/tao/TAO.dsp @@ -163,6 +163,10 @@ SOURCE=.\Abstract_Servant_Base.cpp # End Source File
# Begin Source File
+SOURCE=.\AbstractBase.cpp
+# End Source File
+# Begin Source File
+
SOURCE=.\Acceptor_Filter.cpp
# End Source File
# Begin Source File
@@ -947,6 +951,10 @@ SOURCE=.\Abstract_Servant_Base.h # End Source File
# Begin Source File
+SOURCE=.\AbstractBase.h
+# End Source File
+# Begin Source File
+
SOURCE=.\Acceptor_Filter.h
# End Source File
# Begin Source File
@@ -1775,6 +1783,10 @@ SOURCE=.\WrongTransactionC.h # PROP Default_Filter "i;inl"
# Begin Source File
+SOURCE=.\AbstractBase.inl
+# End Source File
+# Begin Source File
+
SOURCE=.\Acceptor_Filter.i
# End Source File
# Begin Source File
diff --git a/TAO/tao/TAO_Static.dsp b/TAO/tao/TAO_Static.dsp index fecdd967d98..c62b118f0a7 100644 --- a/TAO/tao/TAO_Static.dsp +++ b/TAO/tao/TAO_Static.dsp @@ -40,8 +40,8 @@ RSC=rc.exe # PROP Output_Dir ""
# PROP Intermediate_Dir "LIB\Release"
# PROP Target_Dir ""
-MTL=midl.exe
LINK32=link.exe -lib
+MTL=midl.exe
# ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /YX /FD /c
# ADD CPP /nologo /MD /W3 /GX /Zi /O2 /I "../../" /I "../" /D "_WINDOWS" /D "_CONSOLE" /D "NDEBUG" /D "WIN32" /D "TAO_AS_STATIC_LIBS" /D "ACE_AS_STATIC_LIBS" /FD /c
# SUBTRACT CPP /YX
@@ -66,8 +66,8 @@ LIB32=link.exe -lib # PROP Output_Dir ""
# PROP Intermediate_Dir "LIB\Debug"
# PROP Target_Dir ""
-MTL=midl.exe
LINK32=link.exe -lib
+MTL=midl.exe
# ADD BASE CPP /nologo /W3 /GX /Z7 /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /YX /FD /c
# ADD CPP /nologo /MDd /W3 /GX /Zi /Od /I "../../" /I "../" /D "_WINDOWS" /D "_CONSOLE" /D "_DEBUG" /D "WIN32" /D "ACE_AS_STATIC_LIBS" /D "TAO_AS_STATIC_LIBS" /FD /c
# SUBTRACT CPP /YX
@@ -95,6 +95,10 @@ SOURCE=.\Abstract_Servant_Base.cpp # End Source File
# Begin Source File
+SOURCE=.\AbstractBase.cpp
+# End Source File
+# Begin Source File
+
SOURCE=.\Acceptor_Filter.cpp
# End Source File
# Begin Source File
@@ -879,6 +883,10 @@ SOURCE=.\Abstract_Servant_Base.h # End Source File
# Begin Source File
+SOURCE=.\AbstractBase.h
+# End Source File
+# Begin Source File
+
SOURCE=.\Acceptor_Filter.h
# End Source File
# Begin Source File
@@ -1763,6 +1771,10 @@ SOURCE=.\WrongTransactionC.h # PROP Default_Filter "i;inl"
# Begin Source File
+SOURCE=.\AbstractBase.inl
+# End Source File
+# Begin Source File
+
SOURCE=.\Acceptor_Filter.i
# End Source File
# Begin Source File
diff --git a/TAO/tao/ValueBase.cpp b/TAO/tao/ValueBase.cpp index 1af07433583..e7d1cf2134f 100644 --- a/TAO/tao/ValueBase.cpp +++ b/TAO/tao/ValueBase.cpp @@ -18,15 +18,18 @@ #include "tao/ORB.h" #include "tao/ORB_Core.h" #include "tao/ValueBase.h" +#include "tao/ValueFactory.h" #include "tao/debug.h" -#ifdef TAO_HAS_VALUETYPE +#if defined (TAO_HAS_VALUETYPE) #if !defined (__ACE_INLINE__) # include "tao/ValueBase.i" #endif /* ! __ACE_INLINE__ */ -ACE_RCSID(tao, ValueBase, "$Id$") +ACE_RCSID (tao, + ValueBase, + "$Id$") // destructor CORBA_ValueBase::~CORBA_ValueBase (void) @@ -34,7 +37,7 @@ CORBA_ValueBase::~CORBA_ValueBase (void) } CORBA_ValueBase* -CORBA_ValueBase::_downcast (CORBA_ValueBase* vt) +CORBA_ValueBase::_downcast (CORBA_ValueBase *vt) { return vt; // every vt is a CORBA::ValueBase :-) } @@ -88,18 +91,24 @@ CORBA_ValueBase::_tao_marshal (TAO_OutputCDR &strm, // is provided. The latter is necessary if the formal_type_id // is unequal the 'true derived' type of this object. +++ - CORBA::ULong value_tag = TAO_OBV_GIOP_Flags::Value_tag_base + CORBA::ULong value_tag = TAO_OBV_GIOP_Flags::Value_tag_base | TAO_OBV_GIOP_Flags::Type_info_single; retval = strm.write_ulong (value_tag); - if (!retval) - return retval; + + if (! retval) + { + return retval; + } // 4. Marshal type information. retval = strm.write_string (this_->_tao_obv_repository_id ()); - if (!retval) - return retval; + + if (! retval) + { + return retval; + } // 5. if (chunking) let room for a blocksize-tag. (i.e. write ULong) @@ -119,8 +128,8 @@ CORBA_ValueBase::_tao_marshal (TAO_OutputCDR &strm, CORBA::Boolean -CORBA_ValueBase::_tao_unmarshal (TAO_InputCDR &, - CORBA_ValueBase *&) +CORBA_ValueBase::_tao_unmarshal (TAO_InputCDR &strm, + CORBA_ValueBase *&new_object) { // This is for the special case only that one unmarshals in order // to assign the newly created object directly to a ValueBase pointer. @@ -135,14 +144,46 @@ CORBA_ValueBase::_tao_unmarshal (TAO_InputCDR &, // new_object->_tao_unmarshal_v () // new_object->_tao_unmarshal_post () - ACE_DEBUG ((LM_DEBUG, ACE_TEXT ("unimpl. CORBA::ValueBase::_tao_unmarshal\n"))); - return 0; // %! +// CORBA::ValueBase *base = 0; + CORBA::ValueFactory_var factory; + CORBA::Boolean retval = + CORBA::ValueBase::_tao_unmarshal_pre (strm, + factory.out (), + new_object, + 0); + + if (retval == 0) + { + return 0; + } + + if (factory.in () != 0) + { + new_object = factory->create_for_unmarshal (); + + if (new_object == 0) + { + return 0; // %! except.? + } + + retval = new_object->_tao_unmarshal_v (strm); + + if (retval == 0) + { + return 0; + } + } + + // Now base must be null or point to the unmarshaled object. + // Align the pointer to the right subobject. +// new_object = CORBA_ValueBase::_downcast (base); + return retval; } CORBA::Boolean CORBA_ValueBase::_tao_unmarshal_pre (TAO_InputCDR &strm, - CORBA_ValueFactory_ptr &factory, + CORBA_ValueFactory &factory, CORBA_ValueBase *&valuetype, const char * const /* repo_id */) { // %! dont leak on error case ! @@ -160,6 +201,7 @@ CORBA_ValueBase::_tao_unmarshal_pre (TAO_InputCDR &strm, // So the type should be checked ... +++ CORBA::ULong value_tag; + if (!strm.read_ulong (value_tag)) { return 0; @@ -178,7 +220,9 @@ CORBA_ValueBase::_tao_unmarshal_pre (TAO_InputCDR &strm, if (!TAO_OBV_GIOP_Flags::is_value_tag (value_tag)) { - ACE_DEBUG ((LM_DEBUG, ACE_TEXT ("!CORBA::ValueBase::_tao_unmarshal_pre not value_tag\n"))); + ACE_DEBUG ((LM_DEBUG, + ACE_TEXT ("!CORBA::ValueBase::_tao_unmarshal_pre ") + ACE_TEXT ("not value_tag\n"))); return 0; } @@ -198,9 +242,11 @@ CORBA_ValueBase::_tao_unmarshal_pre (TAO_InputCDR &strm, } TAO_ORB_Core *orb_core = strm.orb_core (); + if (orb_core == 0) { orb_core = TAO_ORB_Core_instance (); + if (TAO_debug_level > 0) { ACE_DEBUG ((LM_WARNING, @@ -209,10 +255,12 @@ CORBA_ValueBase::_tao_unmarshal_pre (TAO_InputCDR &strm, } } - factory = orb_core->orb ()->lookup_value_factory (repo_id_stream.in()); + factory = orb_core->orb ()->lookup_value_factory (repo_id_stream.in ()); + if (factory == 0) // %! except.! { - ACE_DEBUG ((LM_ERROR, ACE_TEXT ("(%N:%l) OBV factory is null !!!\n"))); + ACE_DEBUG ((LM_ERROR, + ACE_TEXT ("(%N:%l) OBV factory is null !!!\n"))); return 0; } @@ -266,7 +314,6 @@ CORBA_DefaultValueRefCountBase::_refcount_value (void) return this->_tao_refcount_value (); } - // some constants const CORBA::ULong TAO_OBV_GIOP_Flags::Value_tag_base = 0x7fffff00L; diff --git a/TAO/tao/ValueBase.h b/TAO/tao/ValueBase.h index 6c9f323cb88..b48a614f110 100644 --- a/TAO/tao/ValueBase.h +++ b/TAO/tao/ValueBase.h @@ -22,7 +22,7 @@ # pragma once #endif /* ACE_LACKS_PRAGMA_ONCE */ -#ifdef TAO_HAS_VALUETYPE +#if defined (TAO_HAS_VALUETYPE) #include "ace/OS.h" /* for ptr_arith_t */ #include "ace/Synch_T.h" @@ -36,7 +36,6 @@ */ class TAO_Export CORBA_ValueBase { - public: // reference counting /// %! virtual CORBA::ValueBase* _copy_value (void) = 0; @@ -48,7 +47,7 @@ public: static CORBA::ValueBase* _downcast (CORBA::ValueBase*); /// TAO extension - virtual const char* _tao_obv_repository_id () const = 0; + virtual const char* _tao_obv_repository_id (void) const = 0; // TAO internal -------------------------- @@ -56,11 +55,11 @@ public: /// how it is called) static CORBA::Boolean _tao_marshal (TAO_OutputCDR &strm, CORBA_ValueBase *_this, - ptr_arith_t formal_type_id = 0); + ptr_arith_t formal_type_id = 0); /// Unmarshal a valuetype, if formal type is a pointer to ValueBase static CORBA::Boolean _tao_unmarshal (TAO_InputCDR &strm, - CORBA_ValueBase *&_this); + CORBA_ValueBase *&new_object); // static CORBA::Boolean // T::_tao_unmarshal (TAO_InputCDR &, CORBA_ValueBase *&_this) @@ -69,12 +68,11 @@ public: /// Both used internally and are called from T::_tao_unmarshal () static CORBA::Boolean _tao_unmarshal_pre (TAO_InputCDR &strm, - CORBA_ValueFactory_ptr &, + CORBA_ValueFactory &, CORBA_ValueBase *&, const char * const repo_id); CORBA::Boolean _tao_unmarshal_post (TAO_InputCDR &strm); - public: // otherwise these cannot be called from a static function virtual void *_tao_obv_narrow (ptr_arith_t) = 0; @@ -87,10 +85,10 @@ public: // otherwise these cannot be called from a static function protected: CORBA_ValueBase (void); CORBA_ValueBase (const CORBA_ValueBase&); - virtual ~CORBA_ValueBase (); + virtual ~CORBA_ValueBase (void); private: - void operator= (const CORBA_ValueBase &); + CORBA_ValueBase & operator= (const CORBA_ValueBase &); #ifdef SUN_CC_HAS_PVFC_BUG // Need ugly fix for sun cc "pure virtual function called" bug. @@ -101,8 +99,57 @@ private: }; // CORBA_ValueBase +/** + * @class CORBA_ValueBase_var + * + * @brief _var class for ValueBase + */ +class TAO_Export CORBA_ValueBase_var +{ +public: + CORBA_ValueBase_var (void); + CORBA_ValueBase_var (CORBA::ValueBase *); + CORBA_ValueBase_var (const CORBA_ValueBase_var &); + ~CORBA_ValueBase_var (void); + + CORBA_ValueBase_var &operator= (CORBA::ValueBase *); + CORBA_ValueBase_var &operator= (const CORBA_ValueBase_var &); + CORBA::ValueBase *operator-> (void) const; + + /// in, inout, out, _retn + operator const CORBA::ValueBase *&() const; + operator CORBA::ValueBase *&(); + CORBA::ValueBase *in (void) const; + CORBA::ValueBase *&inout (void); + CORBA::ValueBase *&out (void); + CORBA::ValueBase *_retn (void); + CORBA::ValueBase *ptr (void) const; +private: + CORBA::ValueBase *ptr_; +}; +/** + * @class CORBA_ValueBase_var + * + * @brief _out class for ValueBase + */ +class TAO_Export CORBA_ValueBase_out +{ +public: + CORBA_ValueBase_out (CORBA::ValueBase *&); + CORBA_ValueBase_out (CORBA_ValueBase_var &); + CORBA_ValueBase_out (const CORBA_ValueBase_out &); + CORBA_ValueBase_out &operator= (const CORBA_ValueBase_out &); + CORBA_ValueBase_out &operator= (const CORBA_ValueBase_var &); + CORBA_ValueBase_out &operator= (CORBA::ValueBase *); + operator CORBA::ValueBase *&(); + CORBA::ValueBase *&ptr (void); + CORBA::ValueBase *operator-> (void); + +private: + CORBA::ValueBase *&ptr_; +}; /** * @class CORBA_DefaultValueRefCountBase @@ -169,6 +216,12 @@ public: static CORBA::Boolean is_end_tag (CORBA::ULong); }; +TAO_Export CORBA::Boolean +operator<< (TAO_OutputCDR&, const CORBA_ValueBase *); + +TAO_Export CORBA::Boolean +operator>> (TAO_InputCDR&, CORBA_ValueBase *&); + #if defined (__ACE_INLINE__) # include "tao/ValueBase.i" #endif /* __ACE_INLINE__) */ diff --git a/TAO/tao/ValueBase.i b/TAO/tao/ValueBase.i index 38ce044122b..42886889f23 100644 --- a/TAO/tao/ValueBase.i +++ b/TAO/tao/ValueBase.i @@ -25,6 +25,174 @@ CORBA_ValueBase::CORBA_ValueBase (void) { } +// ************************************************************* +// Inline operations for class CORBA_ValueBase_var +// ************************************************************* + +ACE_INLINE +CORBA_ValueBase_var::CORBA_ValueBase_var (void) + : ptr_ (0) +{ +} + +ACE_INLINE +CORBA_ValueBase_var::CORBA_ValueBase_var (CORBA::ValueBase *p) + : ptr_ (p) +{ +} + +ACE_INLINE +CORBA_ValueBase_var::~CORBA_ValueBase_var (void) +{ + CORBA::remove_ref (this->ptr_); +} + +ACE_INLINE CORBA::ValueBase * +CORBA_ValueBase_var::ptr (void) const +{ + return this->ptr_; +} + +ACE_INLINE +CORBA_ValueBase_var::CORBA_ValueBase_var (const CORBA_ValueBase_var &p) + : ptr_ (p.ptr_) +{ + p.ptr_->_add_ref (); +} + +ACE_INLINE CORBA_ValueBase_var & +CORBA_ValueBase_var::operator= (CORBA::ValueBase *p) +{ + CORBA::remove_ref (this->ptr_); + this->ptr_ = p; + return *this; +} + +ACE_INLINE CORBA_ValueBase_var & +CORBA_ValueBase_var::operator= (const CORBA_ValueBase_var &p) +{ + if (this != &p) + { + CORBA::remove_ref (this->ptr_); + p.ptr_->_add_ref (); + this->ptr_ = p.ptr_; + } + + return *this; +} + +ACE_INLINE +CORBA_ValueBase_var::operator const CORBA::ValueBase *&() const // cast +{ + return ACE_const_cast (const CORBA::ValueBase *&, + this->ptr_); +} + +ACE_INLINE +CORBA_ValueBase_var::operator CORBA::ValueBase *&() // cast +{ + return this->ptr_; +} + +ACE_INLINE CORBA::ValueBase * +CORBA_ValueBase_var::operator-> (void) const +{ + return this->ptr_; +} + +ACE_INLINE CORBA::ValueBase * +CORBA_ValueBase_var::in (void) const +{ + return this->ptr_; +} + +ACE_INLINE CORBA::ValueBase *& +CORBA_ValueBase_var::inout (void) +{ + return this->ptr_; +} + +ACE_INLINE CORBA::ValueBase *& +CORBA_ValueBase_var::out (void) +{ + CORBA::remove_ref (this->ptr_); + this->ptr_ = 0; + return this->ptr_; +} + +ACE_INLINE CORBA::ValueBase * +CORBA_ValueBase_var::_retn (void) +{ + // Yield ownership of valuebase. + CORBA::ValueBase *val = this->ptr_; + this->ptr_ = 0; + return val; +} + +// ************************************************************* +// Inline operations for class CORBA_ValueBase_out +// ************************************************************* + +ACE_INLINE +CORBA_ValueBase_out::CORBA_ValueBase_out (CORBA::ValueBase *&p) + : ptr_ (p) +{ + this->ptr_ = 0; +} + +ACE_INLINE +CORBA_ValueBase_out::CORBA_ValueBase_out (CORBA_ValueBase_var &p) + : ptr_ (p.out ()) +{ + this->ptr_->_remove_ref (); + this->ptr_ = 0; +} + +ACE_INLINE +CORBA_ValueBase_out::CORBA_ValueBase_out (const CORBA_ValueBase_out &p) + : ptr_ (p.ptr_) +{ +} + +ACE_INLINE CORBA_ValueBase_out & +CORBA_ValueBase_out::operator= (const CORBA_ValueBase_out &p) +{ + this->ptr_ = p.ptr_; + return *this; +} + +ACE_INLINE CORBA_ValueBase_out & +CORBA_ValueBase_out::operator= (const CORBA_ValueBase_var &p) +{ + p.ptr ()->_add_ref (); + this->ptr_ = p.ptr (); + return *this; +} + +ACE_INLINE CORBA_ValueBase_out & +CORBA_ValueBase_out::operator= (CORBA::ValueBase *p) +{ + this->ptr_ = p; + return *this; +} + +ACE_INLINE +CORBA_ValueBase_out::operator CORBA::ValueBase *&() // cast +{ + return this->ptr_; +} + +ACE_INLINE CORBA::ValueBase *& +CORBA_ValueBase_out::ptr (void) // ptr +{ + return this->ptr_; +} + +ACE_INLINE CORBA::ValueBase * +CORBA_ValueBase_out::operator-> (void) +{ + return this->ptr_; +} // =========================================================== @@ -134,3 +302,26 @@ TAO_OBV_GIOP_Flags::is_end_tag (CORBA::ULong tag) { return (0x80000000L < tag && tag <= 0xFFFFFFFFL); } + +// =========================================================== + +ACE_INLINE CORBA::Boolean +operator<< (TAO_OutputCDR &strm, + const CORBA_ValueBase *_tao_valuetype) +{ + return CORBA_ValueBase::_tao_marshal ( + strm, + ACE_const_cast (CORBA_ValueBase *, + _tao_valuetype), + (ptr_arith_t) &CORBA_ValueBase::_downcast + ); +} + +ACE_INLINE CORBA::Boolean +operator>> (TAO_InputCDR &strm, + CORBA_ValueBase *&_tao_valuetype) +{ + return CORBA_ValueBase::_tao_unmarshal (strm, + _tao_valuetype); +} + diff --git a/TAO/tao/ValueFactory.cpp b/TAO/tao/ValueFactory.cpp index 6b8f049ca11..def77db55bd 100644 --- a/TAO/tao/ValueFactory.cpp +++ b/TAO/tao/ValueFactory.cpp @@ -16,16 +16,24 @@ #include "tao/ValueFactory.h" -#ifdef TAO_HAS_VALUETYPE +#if defined (TAO_HAS_VALUETYPE) #if !defined (__ACE_INLINE__) # include "tao/ValueFactory.i" #endif /* ! __ACE_INLINE__ */ -ACE_RCSID(tao, ValueFactory, "$Id$") +ACE_RCSID (tao, + ValueFactory, "$Id$") -CORBA_ValueFactoryBase::~CORBA_ValueFactoryBase () +CORBA_ValueFactoryBase::~CORBA_ValueFactoryBase (void) { } +// No-op. This should never be called, but it can't be pure virtual. +CORBA::AbstractBase * +CORBA_ValueFactoryBase::create_for_unmarshal_abstract (void) +{ + return 0; +} + #endif /* TAO_HAS_VALUETYPE */ diff --git a/TAO/tao/ValueFactory.h b/TAO/tao/ValueFactory.h index 014db27bfc0..5948e95c797 100644 --- a/TAO/tao/ValueFactory.h +++ b/TAO/tao/ValueFactory.h @@ -21,7 +21,7 @@ # pragma once #endif /* ACE_LACKS_PRAGMA_ONCE */ -#ifdef TAO_HAS_VALUETYPE +#if defined (TAO_HAS_VALUETYPE) #include "ace/Synch_T.h" @@ -43,14 +43,46 @@ public: // private: %! /// In a derived class T use return type TAO_OBV_CREATE_RETURN_TYPE (T) /// (see at definition below) - virtual CORBA_ValueBase* create_for_unmarshal (void) = 0; + virtual CORBA_ValueBase * create_for_unmarshal (void) = 0; + + // Not pure virtual because this will be overridden only by valuetypes + // that support an abstract interface. + virtual CORBA_AbstractBase * create_for_unmarshal_abstract (void); private: CORBA::ULong _tao_reference_count_; TAO_SYNCH_MUTEX _tao_reference_count_lock_; }; // CORBA_ValueFactoryBase +/** + * @class CORBA_ValueFactoryBase_var + * + * @brief _var class for ValueFactoryBase + */ +class TAO_Export CORBA_ValueFactoryBase_var +{ +public: + CORBA_ValueFactoryBase_var (void); + CORBA_ValueFactoryBase_var (CORBA::ValueFactoryBase *); + CORBA_ValueFactoryBase_var (const CORBA_ValueFactoryBase_var &); + ~CORBA_ValueFactoryBase_var (void); + + CORBA_ValueFactoryBase_var &operator= (CORBA::ValueFactoryBase *); + CORBA_ValueFactoryBase_var &operator= (const CORBA_ValueFactoryBase_var &); + CORBA::ValueFactoryBase *operator-> (void) const; + + /// in, inout, out, _retn + operator const CORBA::ValueFactoryBase *&() const; + operator CORBA::ValueFactoryBase *&(); + CORBA::ValueFactoryBase *in (void) const; + CORBA::ValueFactoryBase *&inout (void); + CORBA::ValueFactoryBase *&out (void); + CORBA::ValueFactoryBase *_retn (void); + CORBA::ValueFactoryBase *ptr (void) const; +private: + CORBA::ValueFactoryBase *ptr_; +}; // Use this macro for writing code that is independend from // the compiler support of covariant return types of pointers to @@ -65,8 +97,6 @@ private: # define TAO_OBV_CREATE_RETURN_TYPE(TYPE) CORBA::ValueBase * #endif /* TAO_HAS_OBV_COVARIANT_RETURN */ - - // (The obtaining of the repository id is currently not yet like the OMG way. %!) // // Macro for on the fly registration of a factory (with type Factory). @@ -85,7 +115,6 @@ private: if (prev_factory) prev_factory->_remove_ref (); \ factory->_remove_ref (); } - #if defined (__ACE_INLINE__) # include "tao/ValueFactory.i" #endif /* __ACE_INLINE__) */ diff --git a/TAO/tao/ValueFactory.i b/TAO/tao/ValueFactory.i index 805374eadfb..a632b0ddbe6 100644 --- a/TAO/tao/ValueFactory.i +++ b/TAO/tao/ValueFactory.i @@ -24,3 +24,129 @@ CORBA_ValueFactoryBase::_remove_ref (void) } delete this; } + +// ************************************************************* +// Inline operations for class CORBA_ValueFactoryBase_var +// ************************************************************* + +ACE_INLINE +CORBA_ValueFactoryBase_var::CORBA_ValueFactoryBase_var (void) + : ptr_ (0) +{ +} + +ACE_INLINE +CORBA_ValueFactoryBase_var::CORBA_ValueFactoryBase_var ( + CORBA::ValueFactoryBase *p + ) + : ptr_ (p) +{ +} + +ACE_INLINE +CORBA_ValueFactoryBase_var::~CORBA_ValueFactoryBase_var (void) +{ + if (this->ptr_ != 0) + { + this->ptr_->_remove_ref (); + } +} + +ACE_INLINE CORBA::ValueFactoryBase * +CORBA_ValueFactoryBase_var::ptr (void) const +{ + return this->ptr_; +} + +ACE_INLINE +CORBA_ValueFactoryBase_var::CORBA_ValueFactoryBase_var ( + const CORBA_ValueFactoryBase_var &p + ) + : ptr_ (p.ptr_) +{ + p.ptr_->_add_ref (); +} + +ACE_INLINE CORBA_ValueFactoryBase_var & +CORBA_ValueFactoryBase_var::operator= (CORBA::ValueFactoryBase *p) +{ + if (this->ptr_ != 0) + { + this->ptr_->_remove_ref (); + } + + this->ptr_ = p; + return *this; +} + +ACE_INLINE CORBA_ValueFactoryBase_var & +CORBA_ValueFactoryBase_var::operator= (const CORBA_ValueFactoryBase_var &p) +{ + if (this != &p) + { + if (this->ptr_ != 0) + { + this->ptr_->_remove_ref (); + } + + p.ptr_->_add_ref (); + this->ptr_ = p.ptr_; + } + + return *this; +} + +// cast +ACE_INLINE +CORBA_ValueFactoryBase_var::operator const CORBA::ValueFactoryBase *&() const +{ + return ACE_const_cast (const CORBA::ValueFactoryBase *&, + this->ptr_); +} + +// cast +ACE_INLINE +CORBA_ValueFactoryBase_var::operator CORBA::ValueFactoryBase *&() +{ + return this->ptr_; +} + +ACE_INLINE CORBA::ValueFactoryBase * +CORBA_ValueFactoryBase_var::operator-> (void) const +{ + return this->ptr_; +} + +ACE_INLINE CORBA::ValueFactoryBase * +CORBA_ValueFactoryBase_var::in (void) const +{ + return this->ptr_; +} + +ACE_INLINE CORBA::ValueFactoryBase *& +CORBA_ValueFactoryBase_var::inout (void) +{ + return this->ptr_; +} + +ACE_INLINE CORBA::ValueFactoryBase *& +CORBA_ValueFactoryBase_var::out (void) +{ + if (this->ptr_ != 0) + { + this->ptr_->_remove_ref (); + } + + this->ptr_ = 0; + return this->ptr_; +} + +ACE_INLINE CORBA::ValueFactoryBase * +CORBA_ValueFactoryBase_var::_retn (void) +{ + // Yield ownership of valuebase. + CORBA::ValueFactoryBase *val = this->ptr_; + this->ptr_ = 0; + return val; +} + diff --git a/TAO/tao/ValueFactory_Map.cpp b/TAO/tao/ValueFactory_Map.cpp index 13eea5d0967..2fb06895ae3 100644 --- a/TAO/tao/ValueFactory_Map.cpp +++ b/TAO/tao/ValueFactory_Map.cpp @@ -17,7 +17,7 @@ #include "tao/ValueFactory.h" #include "tao/ORB.h" -#ifdef TAO_HAS_VALUETYPE +#if defined (TAO_HAS_VALUETYPE) #if !defined (__ACE_INLINE__) # include "tao/ValueFactory_Map.i" @@ -55,32 +55,35 @@ TAO_ValueFactory_Map::~TAO_ValueFactory_Map () int TAO_ValueFactory_Map::rebind (const char *repo_id, - CORBA_ValueFactory_ptr &factory) + CORBA_ValueFactory &factory) { // ACE_READ_GUARD_RETURN (TAO_SYNCH_RW_MUTEX, guard, map_->mutex(),-1); // --- but must be recursive const char *prev_repo_id; - CORBA_ValueFactory_ptr prev_factory; + CORBA_ValueFactory prev_factory; int ret = 0; ret = this->map_.rebind (CORBA::string_dup (repo_id), factory, prev_repo_id, prev_factory); + if (ret > -1) // ok, no error { factory->_add_ref (); // The map owns one reference. + if (ret == 1) // there was a previous factory { factory = prev_factory; CORBA::string_free (ACE_const_cast(char*,prev_repo_id)); } } + return ret; } int TAO_ValueFactory_Map::unbind (const char *repo_id, - CORBA_ValueFactory_ptr &factory) + CORBA_ValueFactory &factory) { // ACE_Hash_Map_Entry<const char *, CORBA_ValueFactory_ptr> *prev_entry; FACTORY_MAP_MANAGER::ENTRY *prev_entry; @@ -104,7 +107,7 @@ TAO_ValueFactory_Map::unbind (const char *repo_id, // %! perhaps inline int TAO_ValueFactory_Map::find (const char *repo_id, - CORBA_ValueFactory_ptr &factory) + CORBA_ValueFactory &factory) { int ret = 0; ret = this->map_.find (repo_id, diff --git a/TAO/tao/ValueFactory_Map.h b/TAO/tao/ValueFactory_Map.h index b1ec129edc3..e0889f849ed 100644 --- a/TAO/tao/ValueFactory_Map.h +++ b/TAO/tao/ValueFactory_Map.h @@ -25,7 +25,7 @@ #include "ace/Synch.h" #include "tao/corbafwd.h" -#ifdef TAO_HAS_VALUETYPE +#if defined (TAO_HAS_VALUETYPE) class TAO_ValueFactory_Map { @@ -42,25 +42,25 @@ public: * Returns -1 on failure, 0 on success and 1 if a previous factory * is found (and returned in factory). */ - int rebind (const char *repo_id, CORBA_ValueFactory_ptr &factory); + int rebind (const char *repo_id, CORBA_ValueFactory &factory); /// Removes entry for repo_id from the map and sets factory to /// the tied one. - int unbind (const char *repo_id, CORBA_ValueFactory_ptr &factory); + int unbind (const char *repo_id, CORBA_ValueFactory &factory); /** * Lookup a matching factory for repo_id. * Invokes _add_ref () on the factory if found. * Returns -1 on failure and 0 on success. */ - int find (const char *repo_id, CORBA_ValueFactory_ptr &factory); + int find (const char *repo_id, CORBA_ValueFactory &factory); void dump (void); private: /// The hash table data structure. typedef ACE_Hash_Map_Manager_Ex<const char *, - CORBA_ValueFactory_ptr, + CORBA_ValueFactory, ACE_Hash<const char *>, ACE_Equal_To<const char *>, TAO_SYNCH_RW_MUTEX> diff --git a/TAO/tao/corba.h b/TAO/tao/corba.h index 1eb4e39b4a6..3d337243719 100644 --- a/TAO/tao/corba.h +++ b/TAO/tao/corba.h @@ -52,6 +52,7 @@ #include "tao/BoundsC.h" #include "tao/ValueBase.h" #include "tao/ValueFactory.h" +#include "tao/AbstractBase.h" #include "tao/PolicyC.h" #include "tao/Services.h" #include "tao/DomainC.h" diff --git a/TAO/tao/corbafwd.h b/TAO/tao/corbafwd.h index 23fe1e07692..93b8a0632a3 100644 --- a/TAO/tao/corbafwd.h +++ b/TAO/tao/corbafwd.h @@ -229,13 +229,22 @@ typedef class CORBA_Principal *CORBA_Principal_ptr; typedef class CORBA_ImplementationDef *CORBA_ImplementationDef_ptr; -#ifdef TAO_HAS_VALUETYPE +#if defined (TAO_HAS_VALUETYPE) class CORBA_ValueBase; +class CORBA_ValueBase_var; +class CORBA_ValueBase_out; class CORBA_ValueFactoryBase; -typedef CORBA_ValueFactoryBase *CORBA_ValueFactory_ptr; +class CORBA_ValueFactoryBase_var; +typedef CORBA_ValueFactoryBase *CORBA_ValueFactory; +typedef CORBA_ValueFactoryBase_var CORBA_ValueFactory_var; class CORBA_DefaultValueRefCountBase; #endif /* TAO_HAS_VALUETYPE */ +class CORBA_AbstractBase; +typedef CORBA_AbstractBase *CORBA_AbstractBase_ptr; +class CORBA_AbstractBase_var; +class CORBA_AbstractBase_out; + class CORBA_String_var; class CORBA_String_out; class CORBA_WString_var; @@ -746,17 +755,25 @@ TAO_NAMESPACE CORBA typedef CORBA_TypeCodeFactory_var TypeCodeFactory_var; TAO_NAMESPACE_STORAGE_CLASS CORBA::TypeCode_ptr _tc_TypeCodeFactory; -#ifdef TAO_HAS_VALUETYPE +#if defined (TAO_HAS_VALUETYPE) typedef CORBA_ValueBase ValueBase; typedef CORBA_ValueBase *ValueBase_ptr; + typedef CORBA_ValueBase_var ValueBase_var; + typedef CORBA_ValueBase_out ValueBase_out; typedef CORBA_ValueFactoryBase ValueFactoryBase; typedef CORBA_ValueFactoryBase *ValueFactory; // as CORBA 2.3a C++ map. 20.17.10 says - typedef CORBA_ValueFactoryBase *ValueFactory_ptr; + typedef CORBA_ValueFactoryBase *ValueFactory; + typedef CORBA_ValueFactory_var ValueFactory_var; // own invention, more readable typedef CORBA_DefaultValueRefCountBase DefaultValueRefCountBase; TAO_NAMESPACE_INLINE_FUNCTION void add_ref (ValueBase *); TAO_NAMESPACE_INLINE_FUNCTION void remove_ref (ValueBase *); + + typedef CORBA_AbstractBase AbstractBase; + typedef CORBA_AbstractBase *AbstractBase_ptr; + typedef CORBA_AbstractBase_var AbstractBase_var; + typedef CORBA_AbstractBase_out AbstractBase_out; #endif /* TAO_HAS_VALUETYPE */ // enum values defined in nvlist.hh, bitwise ORed. @@ -792,6 +809,7 @@ TAO_NAMESPACE CORBA // = all the CORBA::is_nil methods. TAO_NAMESPACE_INLINE_FUNCTION Boolean is_nil (Object_ptr); + TAO_NAMESPACE_INLINE_FUNCTION Boolean is_nil (AbstractBase_ptr); TAO_NAMESPACE_INLINE_FUNCTION Boolean is_nil (Environment_ptr); TAO_NAMESPACE_INLINE_FUNCTION Boolean is_nil (TypeCode_ptr); TAO_NAMESPACE_INLINE_FUNCTION Boolean is_nil (ORB_ptr); @@ -804,6 +822,7 @@ TAO_NAMESPACE CORBA // = all the CORBA release methods. TAO_NAMESPACE_INLINE_FUNCTION void release (Object_ptr); + TAO_NAMESPACE_INLINE_FUNCTION void release (AbstractBase_ptr); TAO_NAMESPACE_INLINE_FUNCTION void release (Environment_ptr); TAO_NAMESPACE_INLINE_FUNCTION void release (Principal_ptr); TAO_NAMESPACE_INLINE_FUNCTION void release (TypeCode_ptr); |