From fd1475e8aed72afee1e9544127c140f1edfa8f38 Mon Sep 17 00:00:00 2001 From: sbw1 Date: Fri, 10 Jul 1998 22:02:32 +0000 Subject: Fixed some memory leaks --- TAO/orbsvcs/orbsvcs/Trader/Constraint_Nodes.cpp | 4 +- TAO/orbsvcs/orbsvcs/Trader/Constraint_Visitors.h | 8 +- TAO/orbsvcs/orbsvcs/Trader/Offer_Database.cpp | 4 +- TAO/orbsvcs/orbsvcs/Trader/Offer_Iterators.cpp | 1 + .../orbsvcs/Trader/Service_Type_Repository.cpp | 91 ++++++++++++++-------- TAO/orbsvcs/orbsvcs/Trader/Trader.cpp | 4 + TAO/orbsvcs/orbsvcs/Trader/Trader.h | 2 + TAO/orbsvcs/orbsvcs/Trader/Trader_Interfaces.cpp | 55 ++++++++----- TAO/orbsvcs/orbsvcs/Trader/Trader_T.h | 2 +- TAO/orbsvcs/orbsvcs/Trader/Trader_Utils.cpp | 56 ++++++++++--- TAO/orbsvcs/orbsvcs/Trader/Trader_Utils.h | 14 +++- 11 files changed, 167 insertions(+), 74 deletions(-) diff --git a/TAO/orbsvcs/orbsvcs/Trader/Constraint_Nodes.cpp b/TAO/orbsvcs/orbsvcs/Trader/Constraint_Nodes.cpp index a1b1dc04285..9802fde9086 100644 --- a/TAO/orbsvcs/orbsvcs/Trader/Constraint_Nodes.cpp +++ b/TAO/orbsvcs/orbsvcs/Trader/Constraint_Nodes.cpp @@ -350,9 +350,9 @@ TAO_Literal_Constraint (CORBA::Any* any) break; case TAO_STRING: { - char * s; + char* s; any_ref >>= s; - this->op_.str_ = CORBA::string_dup (s); + this->op_.str_ = s; } break; case TAO_SEQUENCE: diff --git a/TAO/orbsvcs/orbsvcs/Trader/Constraint_Visitors.h b/TAO/orbsvcs/orbsvcs/Trader/Constraint_Visitors.h index 9195da6426b..f82e88f5534 100644 --- a/TAO/orbsvcs/orbsvcs/Trader/Constraint_Visitors.h +++ b/TAO/orbsvcs/orbsvcs/Trader/Constraint_Visitors.h @@ -217,13 +217,13 @@ private: void do_the_op (int operation); int visit_bin_op (TAO_Binary_Constraint* op, int operation); - CORBA::Boolean sequence_does_contain(CORBA::Any* sequence, - TAO_Literal_Constraint& element); + CORBA::Boolean sequence_does_contain (CORBA::Any* sequence, + TAO_Literal_Constraint& element); // Determine if sequence contains , a literal of the same // simple type as . Return 1 in this eventuality. - TAO_Literal_Constraint& left_operand(void); - TAO_Literal_Constraint& right_operand(void); + TAO_Literal_Constraint& left_operand (void); + TAO_Literal_Constraint& right_operand (void); TAO_Constraint_Evaluator (const TAO_Constraint_Evaluator&); TAO_Constraint_Evaluator& operator= (const TAO_Constraint_Evaluator&); diff --git a/TAO/orbsvcs/orbsvcs/Trader/Offer_Database.cpp b/TAO/orbsvcs/orbsvcs/Trader/Offer_Database.cpp index b88ab5709c1..0b7f2826eca 100644 --- a/TAO/orbsvcs/orbsvcs/Trader/Offer_Database.cpp +++ b/TAO/orbsvcs/orbsvcs/Trader/Offer_Database.cpp @@ -14,7 +14,7 @@ template TAO_Offer_Database::~TAO_Offer_Database (void) { ACE_WRITE_GUARD (LOCK_TYPE, ace_mon, this->db_lock_); - + for (Offer_Database::iterator type_iter (this->offer_db_); ! type_iter.done (); type_iter++) @@ -39,7 +39,7 @@ TAO_Offer_Database::~TAO_Offer_Database (void) } delete offer_map_entry; - } + } } template CosTrading::OfferId diff --git a/TAO/orbsvcs/orbsvcs/Trader/Offer_Iterators.cpp b/TAO/orbsvcs/orbsvcs/Trader/Offer_Iterators.cpp index e426d968613..cc75d343c0c 100644 --- a/TAO/orbsvcs/orbsvcs/Trader/Offer_Iterators.cpp +++ b/TAO/orbsvcs/orbsvcs/Trader/Offer_Iterators.cpp @@ -44,6 +44,7 @@ TAO_Offer_Iterator::destroy (CORBA::Environment& env) { PortableServer::POA_var poa = this->_default_POA (TAO_TRY_ENV); TAO_CHECK_ENV; + PortableServer::ObjectId_var id = poa->servant_to_id (this, TAO_TRY_ENV); TAO_CHECK_ENV; diff --git a/TAO/orbsvcs/orbsvcs/Trader/Service_Type_Repository.cpp b/TAO/orbsvcs/orbsvcs/Trader/Service_Type_Repository.cpp index 4b2c12b45a8..fa06f4a848f 100644 --- a/TAO/orbsvcs/orbsvcs/Trader/Service_Type_Repository.cpp +++ b/TAO/orbsvcs/orbsvcs/Trader/Service_Type_Repository.cpp @@ -32,8 +32,7 @@ TAO_Service_Type_Repository (ACE_Lock* lock) } -TAO_Service_Type_Repository:: -~TAO_Service_Type_Repository (void) +TAO_Service_Type_Repository::~TAO_Service_Type_Repository (void) { { ACE_WRITE_GUARD (ACE_Lock, ace_mon, *this->lock_); @@ -46,7 +45,7 @@ TAO_Service_Type_Repository:: delete type_info; } } - + delete this->lock_; } @@ -241,12 +240,20 @@ describe_type (const char * name, (CosTradingRepos::ServiceTypeRepository::TypeStruct*) 0); // return appropriate information about the type. - CosTradingRepos::ServiceTypeRepository::TypeStruct* descr = - new CosTradingRepos::ServiceTypeRepository::TypeStruct; + CosTradingRepos::ServiceTypeRepository::TypeStruct* descr = 0; + ACE_NEW_RETURN (descr, CosTradingRepos::ServiceTypeRepository::TypeStruct, 0); CosTradingRepos::ServiceTypeRepository::TypeStruct & s = type_entry->int_id_->type_struct_; - - (*descr) = s; + + descr->if_name = s.if_name; + descr->masked = s.masked; + descr->incarnation = s.incarnation; + descr->super_types = s.super_types; + + CORBA::ULong length = s.props.length (); + CosTradingRepos::ServiceTypeRepository::PropStruct* pstructs = + s.props.get_buffer (CORBA::B_FALSE); + descr->props.replace (length, length, pstructs, CORBA::B_FALSE); return descr; } @@ -383,32 +390,38 @@ fully_describe_type_i (const CosTradingRepos::ServiceTypeRepository::TypeStruct& } num_props += type_struct.props.length (); - props.length (num_props); + CosTradingRepos::ServiceTypeRepository::PropStruct* pstructs = + CosTradingRepos::ServiceTypeRepository::PropStructSeq::allocbuf (num_props); super_types.length (num_types); - - // Copy in all properties. - int i = 0; - CORBA::ULong prop_index = 0; - CORBA::ULong type_index = 0; - for (i = type_struct.props.length () - 1; i >= 0; i--) - props[prop_index++] = type_struct.props[i]; - - iterator.first (); - for (; ! iterator.done (); iterator.advance ()) - { - const char** next_type_name = 0; - Service_Type_Map::ENTRY* type_entry = 0; - iterator.next (next_type_name); - TAO_String_Hash_Key hash_key (*next_type_name); - this->type_map_.find (*next_type_name, type_entry); - - CosTradingRepos::ServiceTypeRepository::TypeStruct& tstruct = - type_entry->int_id_->type_struct_; - for (i = tstruct.props.length () - 1; i >= 0; i--) - props[prop_index++] = tstruct.props[i]; - - super_types[type_index++] = CORBA::string_dup (*next_type_name); + if (pstructs != 0) + { + // Copy in all properties. + int i = 0; + CORBA::ULong prop_index = 0, + type_index = 0; + for (i = type_struct.props.length () - 1; i >= 0; i--) + pstructs[prop_index++] = type_struct.props[i]; + + iterator.first (); + for (; ! iterator.done (); iterator.advance ()) + { + const char** next_type_name = 0; + Service_Type_Map::ENTRY* type_entry = 0; + + iterator.next (next_type_name); + TAO_String_Hash_Key hash_key (*next_type_name); + this->type_map_.find (*next_type_name, type_entry); + + CosTradingRepos::ServiceTypeRepository::TypeStruct& tstruct = + type_entry->int_id_->type_struct_; + for (i = tstruct.props.length () - 1; i >= 0; i--) + pstructs[prop_index++] = tstruct.props[i]; + + super_types[type_index++] = *next_type_name; + } + + props.replace (num_props, num_props, pstructs, CORBA::B_TRUE); } } @@ -560,11 +573,23 @@ update_type_map (const char* name, // all parameters are valid, create an entry for this service type // in the this->type_map_. type->type_struct_.if_name = if_name; - type->type_struct_.props = props; - type->type_struct_.super_types = super_types; type->type_struct_.masked = CORBA::B_FALSE; type->type_struct_.incarnation = this->incarnation_; type->has_subtypes_ = CORBA::B_FALSE; + type->type_struct_.super_types = super_types; + + // Move the prop struct sequences and super type names from the in + // params to the internal storage. + CORBA::ULong pslength = props.length (); + CosTradingRepos::ServiceTypeRepository::PropStructSeq* pstructs = + ACE_const_cast (CosTradingRepos::ServiceTypeRepository::PropStructSeq*, + &props); + CosTradingRepos::ServiceTypeRepository::PropStruct* psbuf = + pstructs->get_buffer (CORBA::B_TRUE); + type->type_struct_.props.replace (pslength, + pslength, + psbuf, + CORBA::B_TRUE);; this->type_map_.bind (type_name, type); } diff --git a/TAO/orbsvcs/orbsvcs/Trader/Trader.cpp b/TAO/orbsvcs/orbsvcs/Trader/Trader.cpp index 1ede183ccda..24158ffe55d 100644 --- a/TAO/orbsvcs/orbsvcs/Trader/Trader.cpp +++ b/TAO/orbsvcs/orbsvcs/Trader/Trader.cpp @@ -29,6 +29,10 @@ TAO_Trader_Base::TAO_Trader_Base (void) { } +TAO_Trader_Base::~TAO_Trader_Base (void) +{ +} + TAO_Import_Attributes_Impl & TAO_Trader_Base::import_attributes (void) { diff --git a/TAO/orbsvcs/orbsvcs/Trader/Trader.h b/TAO/orbsvcs/orbsvcs/Trader/Trader.h index a60a93b8d0d..eab6d273118 100644 --- a/TAO/orbsvcs/orbsvcs/Trader/Trader.h +++ b/TAO/orbsvcs/orbsvcs/Trader/Trader.h @@ -387,6 +387,8 @@ public: ADMIN = 0x010 }; + virtual ~TAO_Trader_Base (void); + // = Accessors for objects that manage trader's configuration. TAO_Trading_Components_Impl &trading_components (void); diff --git a/TAO/orbsvcs/orbsvcs/Trader/Trader_Interfaces.cpp b/TAO/orbsvcs/orbsvcs/Trader/Trader_Interfaces.cpp index 4612cfd0a6f..bc475691b6b 100644 --- a/TAO/orbsvcs/orbsvcs/Trader/Trader_Interfaces.cpp +++ b/TAO/orbsvcs/orbsvcs/Trader/Trader_Interfaces.cpp @@ -69,7 +69,7 @@ query (const char *type, // If a federated query returns to us, ignore it to prevent // redundant results and infinite loops. CosTrading::Admin::OctetSeq_ptr request_id = policies.request_id (env); - TAO_CHECK_ENV_RETURN_VOID (env); + TAO_CHECK_ENV_RETURN_VOID (env); { ACE_GUARD (TRADER_LOCK_TYPE, trader_mon, this->lock_); @@ -199,16 +199,23 @@ query (const char *type, if (should_follow && links->length () != 0) { // Perform the sequence of federated queries. + CosTrading::Admin::OctetSeq_var rid; if (request_id == 0) { CosTrading::Admin_ptr admin_if = this->trader_.trading_components ().admin_if (); request_id = admin_if->request_id_stem (env); TAO_CHECK_ENV_RETURN_VOID (env); - - ACE_GUARD (TRADER_LOCK_TYPE, trader_mon, this->lock_); - this->request_ids_.insert (*request_id); - TAO_CHECK_ENV_RETURN_VOID (env); + + if (request_id != 0) + { + rid = request_id; + ACE_GUARD (TRADER_LOCK_TYPE, trader_mon, this->lock_); + this->request_ids_.insert (*request_id); + TAO_CHECK_ENV_RETURN_VOID (env); + } + else + return; } this->federated_query (links.in (), @@ -852,7 +859,7 @@ TAO_Register::export (CORBA::Object_ptr reference, // Yank our friend, the type struct, and confirm that the given // properties match the type definition. - CosTradingRepos::ServiceTypeRepository::TypeStruct* type_struct = + CosTradingRepos::ServiceTypeRepository::TypeStruct_var type_struct = rep->fully_describe_type (type, _env); TAO_CHECK_ENV_RETURN (_env, 0); @@ -869,12 +876,18 @@ TAO_Register::export (CORBA::Object_ptr reference, // Validate that the properties defined for this offer are correct // to their types and strength. - this->validate_properties (type, type_struct, properties, _env); + this->validate_properties (type, type_struct.ptr (), properties, _env); TAO_CHECK_ENV_RETURN (_env, 0); + CORBA::ULong plength = properties.length (); ACE_NEW_RETURN (offer, CosTrading::Offer, 0); + + // No copying, no memory leaks. + CosTrading::PropertySeq* hack_seq = + ACE_const_cast (CosTrading::PropertySeq*, &properties); + CosTrading::Property* pbuf = hack_seq->get_buffer (CORBA::B_TRUE); + offer->properties.replace (plength, plength, pbuf, CORBA::B_TRUE); offer->reference = reference->_duplicate (reference); - offer->properties = properties; // Insert the offer into the underlying type map. CosTrading::OfferId id = offer_database.insert_offer (type, offer); @@ -917,7 +930,11 @@ TAO_Register::describe (const char *id, offer_info->reference = offer->reference->_duplicate (offer->reference); offer_info->type = CORBA::string_dup (type); - offer_info->properties = offer->properties; + + // Let the offer_info prop_seq "borrow" the sequence of properties. + CORBA::ULong length = offer->properties.length (); + CosTrading::Property* prop_buf = offer->properties.get_buffer (); + offer_info->properties.replace (length, length, prop_buf, CORBA::B_FALSE); return offer_info; } @@ -1440,25 +1457,21 @@ list_offers (CORBA::ULong how_many, TAO_THROW (CosTrading::NotImplemented()); TRADER::Offer_Database& type_map = this->trader_.offer_database (); - - CosTrading::OfferIdIterator_ptr oi = - type_map.retrieve_all_offer_ids ()->_this (_env); - TAO_CHECK_ENV_RETURN_VOID (_env); + TAO_Offer_Id_Iterator* offer_id_iter = type_map.retrieve_all_offer_ids (); id_itr = CosTrading::OfferIdIterator::_nil (); if (how_many > 0) { - if (oi->next_n (how_many, ids, _env) == CORBA::B_FALSE) - { - // No more items left in the iterator. - oi->destroy (_env); - oi = CosTrading::OfferIdIterator::_nil (); - } + if (offer_id_iter->next_n (how_many, ids, _env) == CORBA::B_TRUE) + { + id_itr = offer_id_iter->_this (_env); + TAO_CHECK_ENV_RETURN_VOID (_env); + } else - id_itr = oi; + delete offer_id_iter; } else - ids = new CosTrading::OfferIdSeq(0); + ids = new CosTrading::OfferIdSeq (0); } template void diff --git a/TAO/orbsvcs/orbsvcs/Trader/Trader_T.h b/TAO/orbsvcs/orbsvcs/Trader/Trader_T.h index d41d25b70e6..b8f95dfc222 100644 --- a/TAO/orbsvcs/orbsvcs/Trader/Trader_T.h +++ b/TAO/orbsvcs/orbsvcs/Trader/Trader_T.h @@ -60,7 +60,7 @@ public: // The argument is a bitwise OR of desired Trader_Components as listed // in enumerated type above. - ~TAO_Trader (void); + virtual ~TAO_Trader (void); // destructor. Offer_Database& offer_database (void); diff --git a/TAO/orbsvcs/orbsvcs/Trader/Trader_Utils.cpp b/TAO/orbsvcs/orbsvcs/Trader/Trader_Utils.cpp index d6283b4fe9e..234e1c96c7a 100644 --- a/TAO/orbsvcs/orbsvcs/Trader/Trader_Utils.cpp +++ b/TAO/orbsvcs/orbsvcs/Trader/Trader_Utils.cpp @@ -189,8 +189,14 @@ TAO_Property_Evaluator:: TAO_Property_Evaluator(const CosTrading::PropertySeq& props, CORBA::Boolean supports_dp) : props_ (props), - supports_dp_ (supports_dp) + supports_dp_ (supports_dp), + dp_cache_ (new CORBA::Any*[props.length ()]) { + if (this->dp_cache_ != 0) + { + for (int i = 0; i < this->props_.length (); i++) + this->dp_cache_[i] = 0; + } } @@ -198,8 +204,26 @@ TAO_Property_Evaluator:: TAO_Property_Evaluator(CosTrading::Offer& offer, CORBA::Boolean supports_dp) : props_ (offer.properties), - supports_dp_ (supports_dp) + supports_dp_ (supports_dp), + dp_cache_ (new CORBA::Any*[offer.properties.length ()]) { + if (this->dp_cache_ != 0) + { + for (int i = 0; i < this->props_.length (); i++) + this->dp_cache_[i] = 0; + } +} + +TAO_Property_Evaluator::~TAO_Property_Evaluator (void) +{ + // Clean up the results of any dynamic properties. + for (int i = 0; i < this->props_.length (); i++) + { + if (this->dp_cache_[i] != 0) + delete this->dp_cache_[i]; + } + + delete [] this->dp_cache_; } int @@ -230,9 +254,13 @@ TAO_Property_Evaluator::property_value (int index, TAO_THROW_SPEC ((CosTradingDynamic::DPEvalFailure)) { CORBA::Any* prop_val = 0; + CORBA::Boolean in_cache = + this->dp_cache_ != 0 && this->dp_cache_[index] != 0; - if (! this->is_dynamic_property(index)) + if (! this->is_dynamic_property (index)) prop_val = (CORBA::Any *) &(this->props_[index].value); + else if (this->supports_dp_ && in_cache) + prop_val = this->dp_cache_[index]; else if (this->supports_dp_) { // Property is defined at this point. @@ -273,6 +301,9 @@ TAO_Property_Evaluator::property_value (int index, // Retrieve the value of the dynamic property. prop_val = dp_eval->evalDP(name, type, info, TAO_TRY_ENV); TAO_CHECK_ENV; + + if (this->dp_cache_ != 0) + this->dp_cache_[index] = prop_val; } TAO_CATCH (CORBA::SystemException, excp) { @@ -895,7 +926,6 @@ TAO_Policies::copy_to_forward (CosTrading::PolicySeq& policy_seq, // Allocating here avoids copying in the policy // any. CORBA::ULong length = trader_name.length (); - CosTrading::TraderName* new_name = 0; CosTrading::LinkName* buf = CosTrading::TraderName::allocbuf (length - 1); @@ -905,10 +935,11 @@ TAO_Policies::copy_to_forward (CosTrading::PolicySeq& policy_seq, buf[j - 1] = CORBA::string_dup (trader_name[j]); new_policy.name = this->policies_[i]->name; - ACE_NEW (new_name, CosTrading::TraderName (length - 1, - length -1, - buf, - CORBA::B_TRUE)); + CosTrading::TraderName new_name (length - 1, + length - 1, + buf, + CORBA::B_TRUE); + new_policy.value <<= new_name; counter++; } @@ -1289,10 +1320,10 @@ TAO_Property_Filter::filter_offer (CosTrading::Offer& source, Prop_Queue prop_queue; CosTrading::PropertySeq& s_props = source.properties; CosTrading::PropertySeq& d_props = destination.properties; - int length = s_props.length (), elem = 0; + CORBA::ULong length = s_props.length (), elem = 0; destination.reference = source.reference->_duplicate (source.reference); - if (this->policy_ != CosTrading::Lookup::none) + if (this->policy_ == CosTrading::Lookup::some) { for (int i = 0; i < length; i++) { @@ -1322,6 +1353,11 @@ TAO_Property_Filter::filter_offer (CosTrading::Offer& source, d_props[elem] = **prop_ptr; } } + else if (this->policy_ == CosTrading::Lookup::all) + { + CosTrading::Property* props = s_props.get_buffer (CORBA::B_FALSE); + d_props.replace (length, length, props, CORBA::B_FALSE); + } } #if defined (ACE_HAS_EXPLICIT_TEMPLATE_INSTANTIATION) diff --git a/TAO/orbsvcs/orbsvcs/Trader/Trader_Utils.h b/TAO/orbsvcs/orbsvcs/Trader/Trader_Utils.h index 983376f2162..3019fa48e96 100644 --- a/TAO/orbsvcs/orbsvcs/Trader/Trader_Utils.h +++ b/TAO/orbsvcs/orbsvcs/Trader/Trader_Utils.h @@ -61,6 +61,9 @@ public: // Construct an instance of TAO_Property_Evaluator that operates on // an where the support for dynamic properties is dictated // by . + + virtual ~TAO_Property_Evaluator (void); + // Clean up dynamic properties. int is_dynamic_property(int index); // Returns 1 if the property at index is dynamic. Returns a @@ -77,7 +80,7 @@ public: // CosTradingDynamic::DPEvalFailure exception on failure. If the // property index is undefined, the method returns a null pointer. - CORBA::TypeCode* property_type(int index); + CORBA::TypeCode* property_type (int index); // Returns the type of the property whose index is . If the // property is dynamic and the trader supports dynamic properties, // then the method returns the field of the @@ -89,6 +92,7 @@ public: typedef CosTradingDynamic::DynamicProp DP_Struct; typedef CosTradingDynamic::DynamicPropEval DP_Eval; + const CosTrading::PropertySeq& props_; // The offer from which the TAO_Property_Evaluator extracts property @@ -96,6 +100,14 @@ public: int supports_dp_; + CORBA::Any** dp_cache_; + // In order to the result of property_value uniformly, we need to + // collect the dynamically allocated anys retrieved from dynamic + // properties in order to free them upon deletion. If we didn't do + // this, then the property_value method would leak or cause seg + // faults, since the client wouldn't be able to tell whether or not + // the return value should be freed. + private: TAO_Property_Evaluator (const TAO_Property_Evaluator&); -- cgit v1.2.1