load_balancer_i.cpp
来自「这是广泛使用的通信开源项目,对于大容量,高并发的通讯要求完全能够胜任,他广泛可用」· C++ 代码 · 共 1,042 行 · 第 1/3 页
CPP
1,042 行
// Load_Balancer_i.cpp,v 1.16 2003/02/21 01:32:34 ossama Exp
#include "Load_Balancer_i.h"
#include "ace/Auto_Ptr.h"
#include "ace/Hash_Map_Manager_T.h"
const char *rr_name_bind = "RR_Group";
// Name binding for the location of the Round Robin info in the mem pool
const char *random_name_bind = "Random_Group";
// Name binding for the location of the Random info in the mem pool
const char *flags_name_bind = "FLAGS";
// Name binding for the location of the flags info in the mem pool
const char *dll_name_bind = "DLL_LIST";
// Name binding for the DLL_LIst in the me_pool;
const char *server_id_name_bind = "server_id";
// Some cookie that is used for appending names
Object_Group_Factory_i::Object_Group_Factory_i (CORBA::ORB_ptr orb,
PortableServer::POA_ptr poa)
:orb_ (orb),
poa_ (PortableServer::POA::_duplicate (poa)),
random_groups_ (0),
rr_groups_ (0),
flags_ (0)
{
ACE_MMAP_Memory_Pool::OPTIONS options (ACE_DEFAULT_BASE_ADDR);
ACE_NEW (this->mem_pool_,
ALLOCATOR ("Mem_Pool",
"Mem_Pool",
&options));
}
Object_Group_Factory_i::~Object_Group_Factory_i (void)
{
delete this->mem_pool_;
}
PortableServer::POA_ptr
Object_Group_Factory_i::_default_POA (ACE_ENV_SINGLE_ARG_DECL_NOT_USED)
ACE_THROW_SPEC ((CORBA::SystemException))
{
return PortableServer::POA::_duplicate (this->poa_.in ());
}
Load_Balancer::Object_Group_ptr
Object_Group_Factory_i::make_round_robin (const char * id
ACE_ENV_ARG_DECL)
ACE_THROW_SPEC ((CORBA::SystemException,
Load_Balancer::duplicate_group))
{
if (this->mem_pool_->find (rr_name_bind,
(void *&)this->rr_groups_) == -1)
{
void *hash_map = this->mem_pool_->malloc (sizeof (HASH_MAP));
ACE_NEW_THROW_EX (this->rr_groups_,
(hash_map) HASH_MAP (this->mem_pool_),
CORBA::NO_MEMORY ());
ACE_CHECK_RETURN (Load_Balancer::Object_Group::_nil ());
// Bind it in the mem pool with a name
if (this->mem_pool_->bind (rr_name_bind,
(void *)this->rr_groups_) != 0)
{
ACE_ERROR_RETURN ((LM_ERROR,
"Unable to bind \n"),
0);
}
}
return this->make_group (0,
id
ACE_ENV_ARG_PARAMETER);
}
void
Object_Group_Factory_i::unbind_round_robin (const char * id
ACE_ENV_ARG_DECL)
ACE_THROW_SPEC ((CORBA::SystemException,
Load_Balancer::no_such_group))
{
if (this->rr_groups_ == 0)
{
if (this->mem_pool_->find (rr_name_bind,
(void *&)this->rr_groups_) == -1)
ACE_THROW (Load_Balancer::no_such_group ());
}
char *int_id = 0;
// Throw an exception if not found in the HASH MAP
if (this->rr_groups_->find (ACE_const_cast (char *, id),
this->mem_pool_) < 0)
ACE_THROW (Load_Balancer::no_such_group ());
// Unbind the entry
this->rr_groups_->unbind (ACE_const_cast (char *, id),
int_id,
this->mem_pool_);
// Free the memory from the pool
this->mem_pool_->free (int_id - (ACE_OS::strlen (id) + 1));
// Change the FLAGS variable
if (this->flags_ == 0)
{
if (this->mem_pool_->find (flags_name_bind,
(void *&)this->flags_) == -1)
return;
}
// Bump down the flags value
--this->flags_;
}
Load_Balancer::Object_Group_ptr
Object_Group_Factory_i::make_random (const char * id
ACE_ENV_ARG_DECL)
ACE_THROW_SPEC ((CORBA::SystemException,
Load_Balancer::duplicate_group))
{
if (this->mem_pool_->find (random_name_bind, (void * &)this->random_groups_) == -1)
{
void *hash_map = this->mem_pool_->malloc (sizeof (HASH_MAP));
ACE_NEW_THROW_EX (this->random_groups_,
(hash_map) HASH_MAP (this->mem_pool_),
CORBA::NO_MEMORY ());
ACE_CHECK_RETURN (Load_Balancer::Object_Group::_nil ());
// Bind it in the mem pool with a name
if (this->mem_pool_->bind (random_name_bind,
(void *)this->random_groups_) != 0)
{
ACE_ERROR_RETURN ((LM_ERROR,
"Unable to bind \n"),
0);
}
}
return this->make_group (1,
id
ACE_ENV_ARG_PARAMETER);
}
void
Object_Group_Factory_i::unbind_random (const char * id
ACE_ENV_ARG_DECL)
ACE_THROW_SPEC ((CORBA::SystemException,
Load_Balancer::no_such_group))
{
if (this->random_groups_ == 0)
{
if (this->mem_pool_->find (random_name_bind,
(void *&)this->random_groups_) == -1)
ACE_THROW (Load_Balancer::no_such_group ());
}
char *int_id = 0;
// Throw an exception if not found in the HASH MAP
if (this->random_groups_->find (ACE_const_cast (char *, id),
this->mem_pool_) < 0)
ACE_THROW (Load_Balancer::no_such_group ());
// Unbind the entry
this->random_groups_->unbind (ACE_const_cast (char *, id),
int_id,
this->mem_pool_);
// Free the memory from the pool
this->mem_pool_->free (int_id - (ACE_OS::strlen (id) + 1));
// Change the FLAGS variable
if (this->flags_ == 0)
{
if (this->mem_pool_->find (flags_name_bind,
(void *&)this->flags_) == -1)
return;
}
// Bump down the flags value
this->flags_ -= 2;
}
Load_Balancer::Object_Group_ptr
Object_Group_Factory_i::make_group (int random,
const char * id
ACE_ENV_ARG_DECL)
ACE_THROW_SPEC ((CORBA::SystemException,
Load_Balancer::duplicate_group))
{
// Store our result here for return.
Load_Balancer::Object_Group_var group;
// Create an appropriate servant.
Object_Group_i *group_servant = 0;
// Check to make sure we don't already have a group with the same
// <id>.
if (random)
{
if (this->random_groups_->find (ACE_const_cast (char *,id),
this->mem_pool_) == 0)
ACE_THROW_RETURN (Load_Balancer::duplicate_group (),
Load_Balancer::Object_Group::_nil ());
}
else
{
if (this->rr_groups_->find (ACE_const_cast (char *,id),
this->mem_pool_) == 0)
ACE_THROW_RETURN (Load_Balancer::duplicate_group (),
Load_Balancer::Object_Group::_nil ());
}
// As we are sure that it is not in the list go ahead and insert it
if (random)
ACE_NEW_THROW_EX (group_servant,
Random_Object_Group (id,
this->poa_.in ()),
CORBA::NO_MEMORY ());
else
ACE_NEW_THROW_EX (group_servant,
RR_Object_Group (id,
this->poa_.in ()),
CORBA::NO_MEMORY ());
ACE_CHECK_RETURN (group._retn ());
// Register with the poa, begin using ref. counting.
group = group_servant->_this (ACE_ENV_SINGLE_ARG_PARAMETER);
ACE_CHECK_RETURN (group._retn ());
group_servant->_remove_ref (ACE_ENV_SINGLE_ARG_PARAMETER);
ACE_CHECK_RETURN (Load_Balancer::Object_Group::_nil ());
CORBA::String_var ior =
this->orb_->object_to_string (group.in ()
ACE_ENV_ARG_PARAMETER);
ACE_CHECK_RETURN (Load_Balancer::Object_Group::_nil ());
// Calculate and allocate the memory we need to store this name to
// object binding.
size_t id_len = ACE_OS::strlen (id) + 1;
size_t kind_len = ACE_OS::strlen (ior.in ()) + 1;
char *ptr = (char *) this->mem_pool_->malloc (id_len + kind_len);
if (ptr == 0)
ACE_THROW_RETURN (CORBA::NO_MEMORY (),
Load_Balancer::Object_Group::_nil ());
char * id_ptr = ptr;
char * ior_ptr = ptr + id_len;
ACE_OS::strcpy (id_ptr, id);
ACE_OS::strcpy (ior_ptr, ior.in ());
// Store the results here
CORBA::Long result = 0;
// Make an entry in appropriate map of groups.
if (random)
{
result = this->random_groups_->bind (id_ptr,
ior_ptr,
this->mem_pool_);
}
else
{
result = this->rr_groups_->bind (id_ptr,
ior_ptr,
this->mem_pool_);
}
// Update the value of flags_
this->update_flags (random
ACE_ENV_ARG_PARAMETER);
ACE_CHECK_RETURN (Load_Balancer::Object_Group::_nil ());
if (result == -1)
{
// For some reason the bind failed. Free our
// dynamically allocated memory.
this->mem_pool_->free ((void *) ptr);
ACE_THROW_RETURN (Load_Balancer::duplicate_group (),
Load_Balancer::Object_Group::_nil ());
}
// Return.
ACE_DEBUG ((LM_DEBUG, "Successfully created new group: %s\n", id));
return group._retn ();
}
Load_Balancer::Object_Group_ptr
Object_Group_Factory_i::resolve (const char * id
ACE_ENV_ARG_DECL)
ACE_THROW_SPEC ((CORBA::SystemException,
Load_Balancer::no_such_group))
{
#if defined (DOORS_MEASURE_STATS)
// Time the calls
// Record the entry time.
ACE_hrtime_t latency_base = ACE_OS::gethrtime ();
#endif /*DOORS_MEASURE_STATS*/
// It could be that the Load balancing service could have failed
// before the Client tries to invoke this call.. In such a case the
// Service should look in to the MMAP file and read in the info
// before it can resolve the ID sent by the client.. So we check
// whether the class holds the pointer.. If not we look in to the
// MMAP file for the relevant info..
if (!this->rr_groups_)
{
if (this->mem_pool_->find (rr_name_bind,
(void *&)this->rr_groups_) == -1)
{
ACE_ERROR_RETURN ((LM_ERROR,
ACE_TEXT ("(%N|%l) The factory does not have any references "),
ACE_TEXT ("to the group that you have sought \n\n")),
0);
}
}
if (!this->random_groups_)
{
if (this->mem_pool_->find (random_name_bind,
(void *&)this->random_groups_) == -1)
{
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?