ACE_DLL_Manager Class Reference

This class is a singleton and serves as a factory and repository for instances of ACE_DLL_Handle. More...

#include <DLL_Manager.h>

Collaboration diagram for ACE_DLL_Manager:

Collaboration graph
[legend]
List of all members.

Public Types

 DEFAULT_SIZE = ACE_DEFAULT_DLL_MANAGER_SIZE
enum  { DEFAULT_SIZE = ACE_DEFAULT_DLL_MANAGER_SIZE }

Public Member Functions

ACE_DLL_Handleopen_dll (const ACE_TCHAR *dll_name, int openmode, ACE_SHLIB_HANDLE handle)
int close_dll (const ACE_TCHAR *dll_name)
 Close the underlying dll. Decrements the refcount.
u_long unload_policy (void) const
 Returns the current per-process UNLOAD_POLICY.
void unload_policy (u_long unload_policy)

Static Public Member Functions

static ACE_DLL_Managerinstance (int size=ACE_DLL_Manager::DEFAULT_SIZE)
 Return a unique instance.

Protected Member Functions

 ACE_DLL_Manager (int size=ACE_DLL_Manager::DEFAULT_SIZE)
 Default constructor.
 ~ACE_DLL_Manager (void)
 Destructor.
int open (int size)
int close (void)
ACE_DLL_Handlefind_dll (const ACE_TCHAR *dll_name) const
int unload_dll (ACE_DLL_Handle *dll_handle, int force_unload=0)

Private Member Functions

 ACE_DLL_Manager (const ACE_DLL_Manager &)
void operator= (const ACE_DLL_Manager &)

Static Private Member Functions

static void close_singleton (void)
 Close the singleton instance.

Private Attributes

ACE_DLL_Handle ** handle_vector_
 Vector containing all loaded handle objects.
int current_size_
 Current number of handles.
int total_size_
 Maximum number of handles.
u_long unload_policy_
 Unload strategy.

Static Private Attributes

static ACE_DLL_Managerinstance_ = 0
 Pointer to a process-wide ACE_DLL_Manager.

Friends

class ACE_Framework_Repository
class ACE_Object_Manager

Detailed Description

This class is a singleton and serves as a factory and repository for instances of ACE_DLL_Handle.

This class is a singleton whose lifetime is managed by the ACE_Framework_Repository. Although it is normally meant to be used directly only by ACE_DLL, applications can call the unload_policy() methods in order get/set the the dll unload policy. Unload policies include per_process/per-dll and eager/lazy. Dlls can export set their own policy by using the ACE_DLL_UNLOAD_POLICY macro found in config-all.h. If a dll choses to set an unload policy, it will be used when the per-dll policy (the default) is in effect. If the per-dll policy is in effect and a dll has not chosen to set a policy, the current per-process policy will be used.

The following policy macros are provided in config-all.h:

ACE_DLL_UNLOAD_POLICY_PER_PROCESS - Per-process policy that unloads dlls eagerly.

ACE_DLL_UNLOAD_POLICY_PER_DLL - Apply policy on a per-dll basis. If the dll doesn't use one of the macros below, the current per-process policy will be used.

ACE_DLL_UNLOAD_POLICY_LAZY - Don't unload dll when refcount reaches zero, i.e., wait for either an explicit unload request or program exit.

ACE_DLL_UNLOAD_POLICY_DEFAULT - Default policy allows dlls to control their own destinies, but will unload those that don't make a choice eagerly.

Definition at line 182 of file DLL_Manager.h.


Member Enumeration Documentation

anonymous enum

Enumerator:
DEFAULT_SIZE 

Definition at line 188 of file DLL_Manager.h.

00189   {
00190     DEFAULT_SIZE = ACE_DEFAULT_DLL_MANAGER_SIZE
00191   };


Constructor & Destructor Documentation

ACE_DLL_Manager::ACE_DLL_Manager ( int  size = ACE_DLL_Manager::DEFAULT_SIZE  )  [protected]

Default constructor.

Definition at line 530 of file DLL_Manager.cpp.

References ACE_ERROR, ACE_TEXT, ACE_TRACE, ACE::debug(), and LM_ERROR.

00531   : handle_vector_ (0),
00532     current_size_ (0),
00533     total_size_ (0),
00534     unload_policy_ (ACE_DLL_UNLOAD_POLICY_PER_DLL)
00535 {
00536   ACE_TRACE ("ACE_DLL_Manager::ACE_DLL_Manager");
00537 
00538   if (this->open (size) != 0 && ACE::debug ())
00539     ACE_ERROR ((LM_ERROR,
00540                 ACE_TEXT ("ACE_DLL_Manager ctor failed to allocate ")
00541                 ACE_TEXT ("handle_vector_.\n")));
00542 }

ACE_DLL_Manager::~ACE_DLL_Manager ( void   )  [protected]

Destructor.

Definition at line 544 of file DLL_Manager.cpp.

References ACE_ERROR, ACE_TEXT, ACE_TRACE, ACE::debug(), and LM_ERROR.

00545 {
00546   ACE_TRACE ("ACE_DLL_Manager::~ACE_DLL_Manager");
00547 
00548   if (this->close () != 0 && ACE::debug ())
00549     ACE_ERROR ((LM_ERROR,
00550                 ACE_TEXT ("ACE_DLL_Manager dtor failed to close ")
00551                 ACE_TEXT ("properly.\n")));
00552 }

ACE_DLL_Manager::ACE_DLL_Manager ( const ACE_DLL_Manager  )  [private]


Member Function Documentation

int ACE_DLL_Manager::close ( void   )  [protected]

Definition at line 678 of file DLL_Manager.cpp.

References ACE_TRACE, current_size_, handle_vector_, and unload_dll().

00679 {
00680   ACE_TRACE ("ACE_DLL_Manager::close");
00681 
00682   int force_close = 1;
00683 
00684   if (this->handle_vector_ != 0)
00685     {
00686       // Delete components in reverse order.
00687       for (int i = this->current_size_ - 1; i >= 0; i--)
00688         {
00689           if (this->handle_vector_[i])
00690             {
00691               ACE_DLL_Handle *s =
00692                 const_cast<ACE_DLL_Handle *> (this->handle_vector_[i]);
00693               this->handle_vector_[i] = 0;
00694               this->unload_dll (s, force_close);
00695               delete s;
00696             }
00697         }
00698 
00699       delete [] this->handle_vector_;
00700       this->handle_vector_ = 0;
00701       this->current_size_ = 0;
00702     }
00703   return 0;
00704 }

int ACE_DLL_Manager::close_dll ( const ACE_TCHAR dll_name  ) 

Close the underlying dll. Decrements the refcount.

Definition at line 608 of file DLL_Manager.cpp.

References ACE_GUARD_RETURN, ACE_TRACE, find_dll(), and unload_dll().

Referenced by ACE_DLL::close().

00609 {
00610   ACE_TRACE ("ACE_DLL_Manager::close_dll");
00611   ACE_DLL_Handle *handle = 0;
00612 
00613   {
00614     ACE_MT (ACE_GUARD_RETURN (ACE_Thread_Mutex, ace_mon, this->lock_, 0));
00615     handle = this->find_dll (dll_name);
00616   }
00617 
00618   if (handle)
00619     {
00620       return this->unload_dll (handle, 0);
00621     }
00622 
00623   return -1;
00624 }

void ACE_DLL_Manager::close_singleton ( void   )  [static, private]

Close the singleton instance.

Definition at line 519 of file DLL_Manager.cpp.

References ACE_GUARD, ACE_TRACE, and instance_.

Referenced by ACE_Framework_Repository::close(), and ACE_Object_Manager::fini().

00520 {
00521   ACE_TRACE ("ACE_DLL_Manager::close_singleton");
00522 
00523   ACE_MT (ACE_GUARD (ACE_Recursive_Thread_Mutex, ace_mon,
00524                      *ACE_Static_Object_Lock::instance ()));
00525 
00526   delete ACE_DLL_Manager::instance_;
00527   ACE_DLL_Manager::instance_ = 0;
00528 }

ACE_DLL_Handle * ACE_DLL_Manager::find_dll ( const ACE_TCHAR dll_name  )  const [protected]

Definition at line 707 of file DLL_Manager.cpp.

References ACE_TRACE, current_size_, handle_vector_, and ACE_OS::strcmp().

Referenced by close_dll(), and open_dll().

00708 {
00709   ACE_TRACE ("ACE_DLL_Manager::find_dll");
00710 
00711   for (int i = 0; i < this->current_size_; i++)
00712     if (this->handle_vector_[i] &&
00713         ACE_OS::strcmp (this->handle_vector_[i]->dll_name (), dll_name) == 0)
00714       {
00715         return this->handle_vector_[i];
00716       }
00717 
00718   return 0;
00719 }

ACE_DLL_Manager * ACE_DLL_Manager::instance ( int  size = ACE_DLL_Manager::DEFAULT_SIZE  )  [static]

Return a unique instance.

Definition at line 498 of file DLL_Manager.cpp.

References ACE_GUARD_RETURN, ACE_NEW_RETURN, ACE_TRACE, and instance_.

Referenced by ACE_DLL::close(), and ACE_DLL::open_i().

00499 {
00500   ACE_TRACE ("ACE_DLL_Manager::instance");
00501 
00502   if (ACE_DLL_Manager::instance_ == 0)
00503     {
00504       // Perform Double-Checked Locking Optimization.
00505       ACE_MT (ACE_GUARD_RETURN (ACE_Recursive_Thread_Mutex, ace_mon,
00506                                 *ACE_Static_Object_Lock::instance (), 0));
00507       if (ACE_DLL_Manager::instance_ == 0)
00508         {
00509           ACE_NEW_RETURN (ACE_DLL_Manager::instance_,
00510                           ACE_DLL_Manager (size),
00511                           0);
00512         }
00513     }
00514 
00515   return ACE_DLL_Manager::instance_;
00516 }

int ACE_DLL_Manager::open ( int  size  )  [protected]

Definition at line 662 of file DLL_Manager.cpp.

References ACE_NEW_RETURN, ACE_TRACE, handle_vector_, and total_size_.

00663 {
00664   ACE_TRACE ("ACE_DLL_Manager::open");
00665 
00666   ACE_DLL_Handle **temp = 0;
00667 
00668   ACE_NEW_RETURN (temp,
00669                   ACE_DLL_Handle *[size],
00670                   -1);
00671 
00672   this->handle_vector_ = temp;
00673   this->total_size_ = size;
00674   return 0;
00675 }

ACE_DLL_Handle * ACE_DLL_Manager::open_dll ( const ACE_TCHAR dll_name,
int  openmode,
ACE_SHLIB_HANDLE  handle 
)

Factory for ACE_DLL_Handle objects. If one already exits, its refcount is incremented.

Definition at line 555 of file DLL_Manager.cpp.

References ACE_ERROR, ACE_GUARD_RETURN, ACE_NEW_RETURN, ACE_TEXT, ACE_TRACE, current_size_, ACE::debug(), find_dll(), handle_vector_, LM_ERROR, and ACE_DLL_Handle::open().

Referenced by ACE_DLL::open_i().

00558 {
00559   ACE_TRACE ("ACE_DLL_Manager::open_dll");
00560 
00561   ACE_DLL_Handle *temp_handle = 0;
00562   ACE_DLL_Handle *dll_handle = 0;
00563   {
00564     ACE_MT (ACE_GUARD_RETURN (ACE_Thread_Mutex, ace_mon, this->lock_, 0));
00565     dll_handle = this->find_dll (dll_name);
00566     if (!dll_handle)
00567       {
00568         if (this->current_size_ < this->total_size_)
00569           {
00570             ACE_NEW_RETURN (temp_handle,
00571                             ACE_DLL_Handle,
00572                             0);
00573 
00574             dll_handle = temp_handle;
00575           }
00576       }
00577   }
00578 
00579   if (dll_handle)
00580     {
00581       if (dll_handle->open (dll_name, open_mode, handle) != 0)
00582         {
00583           // Error while opening dll. Free temp handle
00584           if (ACE::debug ())
00585             ACE_ERROR ((LM_ERROR,
00586                         ACE_TEXT ("ACE_DLL_Manager::open_dll: Could not ")
00587                         ACE_TEXT ("open dll %s.\n"),
00588                         dll_name));
00589 
00590           delete temp_handle;
00591           return 0;
00592         }
00593 
00594       // Add the handle to the vector only if the dll is successfully
00595       // opened.
00596       if (temp_handle != 0)
00597         {
00598           ACE_MT (ACE_GUARD_RETURN (ACE_Thread_Mutex, ace_mon, this->lock_, 0));
00599           this->handle_vector_[this->current_size_] = dll_handle;
00600           ++this->current_size_;
00601         }
00602     }
00603 
00604   return dll_handle;
00605 }

void ACE_DLL_Manager::operator= ( const ACE_DLL_Manager  )  [private]

int ACE_DLL_Manager::unload_dll ( ACE_DLL_Handle dll_handle,
int  force_unload = 0 
) [protected]

Definition at line 722 of file DLL_Manager.cpp.

References ACE_BIT_DISABLED, ACE_ERROR, ACE_TEXT, ACE_TRACE, ACE_DLL_Handle::close(), ACE::debug(), LM_ERROR, and ACE_DLL_Handle::symbol().

Referenced by close(), and close_dll().

00723 {
00724   ACE_TRACE ("ACE_DLL_Manager::unload_dll");
00725 
00726   if (dll_handle)
00727     {
00728       int unload = force_unload;
00729       if (unload == 0)
00730         {
00731           // apply strategy
00732           if (ACE_BIT_DISABLED (this->unload_policy_,
00733                                 ACE_DLL_UNLOAD_POLICY_PER_DLL))
00734             {
00735               unload = ACE_BIT_DISABLED (this->unload_policy_,
00736                                          ACE_DLL_UNLOAD_POLICY_LAZY);
00737             }
00738           else
00739             {
00740               // Declare the type of the symbol:
00741               typedef int (*dll_unload_policy)(void);
00742 
00743               void * const unload_policy_ptr =
00744                 dll_handle->symbol (ACE_TEXT ("_get_dll_unload_policy"), 1);
00745 #if defined (ACE_OPENVMS) && (!defined (__INITIAL_POINTER_SIZE) || (__INITIAL_POINTER_SIZE < 64))
00746               int const temp_p =
00747                 reinterpret_cast<int> (unload_policy_ptr);
00748 #else
00749               intptr_t const temp_p =
00750                 reinterpret_cast<intptr_t> (unload_policy_ptr);
00751 #endif
00752 
00753               dll_unload_policy const the_policy =
00754                 reinterpret_cast<dll_unload_policy> (temp_p);
00755 
00756               if (the_policy != 0)
00757                 unload = ACE_BIT_DISABLED (the_policy (),
00758                                            ACE_DLL_UNLOAD_POLICY_LAZY);
00759               else
00760                 unload = ACE_BIT_DISABLED (this->unload_policy_,
00761                                            ACE_DLL_UNLOAD_POLICY_LAZY);
00762             }
00763         }
00764 
00765       if (dll_handle->close (unload) != 0)
00766         {
00767           if (ACE::debug ())
00768             ACE_ERROR ((LM_ERROR,
00769                         ACE_TEXT ("ACE_DLL_Manager::unload error.\n")));
00770 
00771           return -1;
00772         }
00773     }
00774   else
00775     {
00776       if (ACE::debug ())
00777         ACE_ERROR ((LM_ERROR,
00778                     ACE_TEXT ("ACE_DLL_Manager::unload_dll called with ")
00779                     ACE_TEXT ("null pointer.\n")));
00780 
00781       return -1;
00782     }
00783 
00784   return 0;
00785 }

void ACE_DLL_Manager::unload_policy ( u_long  unload_policy  ) 

Set the per-process UNLOAD_POLICY. If the policy is changed from LAZY to EAGER, then it will also unload any dlls with zero refcounts.

Definition at line 634 of file DLL_Manager.cpp.

References ACE_BIT_DISABLED, ACE_BIT_ENABLED, ACE_GUARD, ACE_TRACE, and unload_policy_.

00635 {
00636   ACE_TRACE ("ACE_DLL_Manager::unload_policy");
00637   ACE_MT (ACE_GUARD (ACE_Thread_Mutex, ace_mon, this->lock_));
00638 
00639   u_long old_policy = this->unload_policy_;
00640   this->unload_policy_ = unload_policy;
00641 
00642   // If going from LAZY to EAGER or from PER_DLL to PER_PROCESS|EAGER,
00643   // call close(1) on all the ACE_DLL_Handle objects with refcount == 0
00644   // which will force those that are still loaded to be unloaded.
00645   if (this->handle_vector_)
00646     if (( ACE_BIT_ENABLED (old_policy, ACE_DLL_UNLOAD_POLICY_LAZY) &&
00647           ACE_BIT_DISABLED (this->unload_policy_, ACE_DLL_UNLOAD_POLICY_LAZY) ) ||
00648         ( ACE_BIT_DISABLED (this->unload_policy_, ACE_DLL_UNLOAD_POLICY_LAZY) &&
00649           ACE_BIT_ENABLED (old_policy, ACE_DLL_UNLOAD_POLICY_PER_DLL) &&
00650           ACE_BIT_DISABLED (this->unload_policy_, ACE_DLL_UNLOAD_POLICY_PER_DLL) ))
00651       {
00652         for (int i = this->current_size_ - 1; i >= 0; i--)
00653           {
00654             if (this->handle_vector_[i] &&
00655                 this->handle_vector_[i]->refcount () == 0)
00656               this->handle_vector_[i]->close (1);
00657           }
00658       }
00659 }

u_long ACE_DLL_Manager::unload_policy ( void   )  const

Returns the current per-process UNLOAD_POLICY.

Definition at line 627 of file DLL_Manager.cpp.

References ACE_TRACE, and unload_policy_.

00628 {
00629   ACE_TRACE ("ACE_DLL_Manager::unload_policy");
00630   return this->unload_policy_;
00631 }


Friends And Related Function Documentation

friend class ACE_Framework_Repository [friend]

Definition at line 185 of file DLL_Manager.h.

friend class ACE_Object_Manager [friend]

Definition at line 186 of file DLL_Manager.h.


Member Data Documentation

int ACE_DLL_Manager::current_size_ [private]

Current number of handles.

Definition at line 248 of file DLL_Manager.h.

Referenced by close(), find_dll(), and open_dll().

ACE_DLL_Handle** ACE_DLL_Manager::handle_vector_ [private]

Vector containing all loaded handle objects.

Definition at line 245 of file DLL_Manager.h.

Referenced by close(), find_dll(), open(), and open_dll().

ACE_DLL_Manager * ACE_DLL_Manager::instance_ = 0 [static, private]

Pointer to a process-wide ACE_DLL_Manager.

Definition at line 257 of file DLL_Manager.h.

Referenced by close_singleton(), and instance().

int ACE_DLL_Manager::total_size_ [private]

Maximum number of handles.

Definition at line 251 of file DLL_Manager.h.

Referenced by open().

u_long ACE_DLL_Manager::unload_policy_ [private]

Unload strategy.

Definition at line 254 of file DLL_Manager.h.

Referenced by unload_policy().


The documentation for this class was generated from the following files:
Generated on Tue Feb 2 17:35:04 2010 for ACE by  doxygen 1.4.7