Registry.cpp

Go to the documentation of this file.
00001 // Registry.cpp,v 4.34 2006/04/19 19:13:09 jwillemsen Exp
00002 
00003 #include "ace/Registry.h"
00004 
00005 ACE_RCSID (ace,
00006            Registry,
00007            "Registry.cpp,v 4.34 2006/04/19 19:13:09 jwillemsen Exp")
00008 
00009 #if defined (ACE_WIN32)
00010 
00011 #  include "ace/os_include/os_netdb.h"
00012 #  include "ace/OS_NS_unistd.h"
00013 
00014 // Funky macro to deal with strange error passing semantics
00015 // of Win32 Reg*() functions
00016 #define ACE_REGISTRY_CALL_RETURN(X) \
00017   do { \
00018     if (X != ERROR_SUCCESS) \
00019     { \
00020       errno = X; \
00021       return -1; \
00022     } \
00023     else \
00024       return 0; \
00025     } while (0)
00026 
00027 
00028 ACE_BEGIN_VERSIONED_NAMESPACE_DECL
00029 
00030 ACE_TCHAR const ACE_Registry::STRING_SEPARATOR[] = ACE_LIB_TEXT ("\\");
00031 
00032 bool
00033 ACE_Registry::Name_Component::operator== (const Name_Component &rhs) const
00034 {
00035   return
00036     rhs.id_ == this->id_ &&
00037     rhs.kind_ == this->kind_;
00038 }
00039 
00040 bool
00041 ACE_Registry::Name_Component::operator!= (const Name_Component &rhs) const
00042 {
00043   return !this->operator== (rhs);
00044 }
00045 
00046 // Simple binding constructor
00047 ACE_Registry::Binding::Binding ()
00048   : name_ (),
00049     type_ (INVALID)
00050 {
00051 }
00052 
00053 
00054 // Binding constructor
00055 // (Name version)
00056 ACE_Registry::Binding::Binding (const Name &name,
00057                                 Binding_Type type)
00058   : name_ (ACE_Registry::make_string (name)),
00059     type_ (type)
00060 {
00061 }
00062 
00063 
00064 // Binding constructor
00065 // (String version)
00066 ACE_Registry::Binding::Binding (const ACE_TString &name,
00067                                 Binding_Type type)
00068   : name_ (name),
00069     type_ (type)
00070 {
00071 }
00072 
00073 
00074 bool
00075 ACE_Registry::Binding::operator== (const Binding &rhs) const
00076 {
00077   return
00078     rhs.name_ == this->name_ &&
00079     rhs.type_ == this->type_;
00080 }
00081 
00082 bool
00083 ACE_Registry::Binding::operator!= (const Binding &rhs) const
00084 {
00085   return !this->operator== (rhs);
00086 }
00087 
00088 // Name accessor
00089 // (Name version)
00090 void
00091 ACE_Registry::Binding::name (Name &name)
00092 {
00093   name = ACE_Registry::make_name (this->name_);
00094 }
00095 
00096 
00097 // Name accessors
00098 // (String version)
00099 void
00100 ACE_Registry::Binding::name (ACE_TString &name)
00101 {
00102   name = this->name_;
00103 }
00104 
00105 
00106 // Name accessors
00107 // (String version)
00108 ACE_TString
00109 ACE_Registry::Binding::name (void)
00110 {
00111   return this->name_;
00112 }
00113 
00114 
00115 // Type accessor
00116 ACE_Registry::Binding_Type
00117 ACE_Registry::Binding::type (void)
00118 {
00119   return this->type_;
00120 }
00121 
00122 
00123 // Simple object constructor
00124 ACE_Registry::Object::Object (void *data,
00125                               u_long size,
00126                               u_long type)
00127   : data_ (data),
00128     size_ (size),
00129     type_ (type)
00130 {
00131 }
00132 
00133 // Object accessors and set methods
00134 void
00135 ACE_Registry::Object::data (void *data)
00136 {
00137   this->data_ = data;
00138 }
00139 
00140 
00141 void *
00142 ACE_Registry::Object::data (void) const
00143 {
00144   return this->data_;
00145 }
00146 
00147 
00148 void
00149 ACE_Registry::Object::size (u_long size)
00150 {
00151   this->size_ = size;
00152 }
00153 
00154 
00155 u_long
00156 ACE_Registry::Object::size (void) const
00157 {
00158   return this->size_;
00159 }
00160 
00161 
00162 void
00163 ACE_Registry::Object::type (u_long type)
00164 {
00165   this->type_ = type;
00166 }
00167 
00168 
00169 u_long
00170 ACE_Registry::Object::type (void) const
00171 {
00172   return this->type_;
00173 }
00174 
00175 
00176 // Simple context constructor
00177 ACE_Registry::Naming_Context::Naming_Context (void)
00178   : key_ ((HKEY) 0),
00179     parent_key_ ((HKEY) 0),
00180     name_ ()
00181 {
00182 }
00183 
00184 
00185 // Context constructor
00186 ACE_Registry::Naming_Context::Naming_Context (const HKEY &key)
00187   : key_ (key),
00188     parent_key_ ((HKEY) 0),
00189     name_ ()
00190 {
00191 }
00192 
00193 
00194 ACE_Registry::Naming_Context::Naming_Context (const Naming_Context &rhs)
00195   : key_ (rhs.key_),
00196     parent_key_ (rhs.parent_key_),
00197     name_ (rhs.name_)
00198 {
00199   // This is incorrect.
00200   // Rather than copying key, we should call ::DuplicateHandle()
00201   // But since this is private (and not used), I don't care much
00202 }
00203 
00204 
00205 const ACE_Registry::Naming_Context &
00206 ACE_Registry::Naming_Context::operator= (const Naming_Context &rhs)
00207 {
00208         ACE_UNUSED_ARG(rhs);
00209 
00210         // Not implemented
00211         return *this;
00212 }
00213 
00214 
00215 // Destructor
00216 ACE_Registry::Naming_Context::~Naming_Context ()
00217 {
00218   this->close ();
00219 }
00220 
00221 
00222 // Insert <object> with <name> into <this> context
00223 // (Name version)
00224 int
00225 ACE_Registry::Naming_Context::bind_new (const Name &name,
00226                                         const Object &object)
00227 {
00228   return this->bind_new (ACE_Registry::make_string (name), object);
00229 }
00230 
00231 
00232 // Insert <object> with <name> into <this> context
00233 // (String version)
00234 int
00235 ACE_Registry::Naming_Context::bind_new (const ACE_TString &name,
00236                                         const Object &object)
00237 {
00238   // temporary object
00239   Object temp;
00240   long result = this->resolve (name, temp);
00241   if (result == 0)
00242     // resolve succeeded
00243     result = -1;
00244   else
00245     // resolve failed
00246     result = this->bind (name, object);
00247   return result;
00248 }
00249 
00250 
00251 // Insert or update <object> with <name> into <this> context
00252 // (Name version)
00253 int
00254 ACE_Registry::Naming_Context::bind (const Name &name,
00255                                     const Object &object)
00256 {
00257   return this->bind (ACE_Registry::make_string (name), object);
00258 }
00259 
00260 
00261 // Insert or update <object> with <name> into <this> context
00262 // (String version)
00263 int
00264 ACE_Registry::Naming_Context::bind (const ACE_TString &name,
00265                                     const Object &object)
00266 {
00267   long result = ACE_TEXT_RegSetValueEx (this->key_,
00268                                         name.c_str (),
00269                                         0,
00270                                         object.type (),
00271                                         (const BYTE *) object.data (),
00272                                         object.size ());
00273   ACE_REGISTRY_CALL_RETURN (result);
00274 }
00275 
00276 
00277 // Update <object> with <name> in <this> context
00278 // (Name version)
00279 int
00280 ACE_Registry::Naming_Context::rebind (const Name &name,
00281                                       const Object &new_object)
00282 {
00283   return this->rebind (ACE_Registry::make_string (name), new_object);
00284 }
00285 
00286 
00287 // Update <object> with <name> in <this> context
00288 // (String version)
00289 int
00290 ACE_Registry::Naming_Context::rebind (const ACE_TString &name,
00291                                       const Object &new_object)
00292 {
00293   Object old_object;
00294   // find the old one first
00295   long result = this->resolve (name, old_object);
00296   if (result == 0)
00297     // no need to delete first
00298     result = this->bind (name, new_object);
00299   return result;
00300 }
00301 
00302 
00303 // Find <object> with <name> in <this> context
00304 // (Name version)
00305 int
00306 ACE_Registry::Naming_Context::resolve (const Name &name,
00307                                        Object &object)
00308 {
00309   return this->resolve (ACE_Registry::make_string (name), object);
00310 }
00311 
00312 
00313 // Find <object> with <name> in <this> context
00314 // (String version)
00315 int
00316 ACE_Registry::Naming_Context::resolve (const ACE_TString &name,
00317                                        Object &object)
00318 {
00319   // Get object state
00320   u_long type;
00321   void *data = object.data ();
00322   u_long size = object.size ();
00323 
00324   long result = ACE_TEXT_RegQueryValueEx (this->key_,
00325                                           name.c_str (),
00326                                           0,
00327                                           &type,
00328                                           (BYTE *)data,
00329                                           &size);
00330   if (result == ERROR_SUCCESS)
00331     {
00332       // Reset object state
00333       // No need to set object.data()
00334       object.type (type);
00335       object.size (size);
00336     }
00337 
00338   ACE_REGISTRY_CALL_RETURN (result);
00339 }
00340 
00341 
00342 // Remove object with <name> in <this> context
00343 // (Name version)
00344 int
00345 ACE_Registry::Naming_Context::unbind (const Name &name)
00346 {
00347   return this->unbind (ACE_Registry::make_string (name));
00348 }
00349 
00350 
00351 // Remove object with <name> in <this> context
00352 // (String version)
00353 int
00354 ACE_Registry::Naming_Context::unbind (const ACE_TString &name)
00355 {
00356   long result = ACE_TEXT_RegDeleteValue (this->key_,
00357                                          name.c_str ());
00358 
00359   ACE_REGISTRY_CALL_RETURN (result);
00360 }
00361 
00362 
00363 // Create new <naming_context> relative to <this> context
00364 // This method may not mean a lot in this implementation
00365 int
00366 ACE_Registry::Naming_Context::new_context (Naming_Context &naming_context)
00367 {
00368   // Make sure that we reset the state and close keys
00369   return naming_context.close ();
00370 }
00371 
00372 
00373 // Insert <naming_context> with <name> relative to <this> context
00374 // (Name version)
00375 int
00376 ACE_Registry::Naming_Context::bind_new_context (const Name &name,
00377                                                 Naming_Context &naming_context,
00378                                                 u_long persistence,
00379                                                 u_long security_access,
00380                                                 LPSECURITY_ATTRIBUTES security_attributes)
00381 {
00382   return this->bind_new_context (ACE_Registry::make_string (name),
00383                                  naming_context,
00384                                  persistence,
00385                                  security_access,
00386                                  security_attributes);
00387 }
00388 
00389 
00390 // Insert <naming_context> with <name> relative to <this> context
00391 // (String version)
00392 int
00393 ACE_Registry::Naming_Context::bind_new_context (const ACE_TString &name,
00394                                                 Naming_Context &naming_context,
00395                                                 u_long persistence,
00396                                                 u_long security_access,
00397                                                 LPSECURITY_ATTRIBUTES security_attributes)
00398 {
00399   u_long reason;
00400 
00401   long result = ACE_TEXT_RegCreateKeyEx (this->key_,
00402                                          name.c_str (),
00403                                          0,
00404                                          0,
00405                                          persistence,
00406                                          security_access,
00407                                          security_attributes,
00408                                          &naming_context.key_,
00409                                          &reason);
00410   if (result == ERROR_SUCCESS)
00411     // If create succeeds
00412     {
00413       if (reason == REG_CREATED_NEW_KEY)
00414         // If new key: success
00415         {
00416           // Set the correct parent
00417           naming_context.parent (this->key_);
00418           // Set the correct name
00419           naming_context.name (name);
00420         }
00421       else
00422         // reason == REG_OPENED_EXISTING_KEY
00423         // Failed to make new key
00424         {
00425           // reset result to failure
00426           result = -1;
00427           // Close the key first
00428           ::RegCloseKey (naming_context.key_);
00429           // Reset key
00430           naming_context.key_ = (HKEY) 0;
00431         }
00432     }
00433 
00434   ACE_REGISTRY_CALL_RETURN (result);
00435 }
00436 
00437 
00438 // Insert or update <naming_context> with <name> relative to <this> context
00439 // (Name version)
00440 int
00441 ACE_Registry::Naming_Context::bind_context (const Name &name,
00442                                             /* const */ Naming_Context &naming_context,
00443                                             u_long persistence,
00444                                             u_long security_access,
00445                                             LPSECURITY_ATTRIBUTES security_attributes)
00446 {
00447   return this->bind_context (ACE_Registry::make_string (name),
00448                              naming_context,
00449                              persistence,
00450                              security_access,
00451                              security_attributes);
00452 }
00453 
00454 
00455 // Insert or update <naming_context> with <name> relative to <this> context
00456 // (String version)
00457 int
00458 ACE_Registry::Naming_Context::bind_context (const ACE_TString &name,
00459                                             /* const */ Naming_Context &naming_context,
00460                                             u_long persistence,
00461                                             u_long security_access,
00462                                             LPSECURITY_ATTRIBUTES security_attributes)
00463 {
00464   u_long reason;
00465 
00466   long result = ACE_TEXT_RegCreateKeyEx (this->key_,
00467                                          name.c_str (),
00468                                          0,
00469                                          0,
00470                                          persistence,
00471                                          security_access,
00472                                          security_attributes,
00473                                          &naming_context.key_,
00474                                          &reason);
00475   if (result == ERROR_SUCCESS)
00476     {
00477       // Set the correct parent
00478       naming_context.parent (this->key_);
00479       // Set the correct name
00480       naming_context.name (name);
00481     }
00482 
00483   ACE_REGISTRY_CALL_RETURN (result);
00484 }
00485 
00486 
00487 // Rename <naming_context> to <name>
00488 // (Name version)
00489 int
00490 ACE_Registry::Naming_Context::rebind_context (const Name &name,
00491                                               /* const */ Naming_Context &new_naming_context)
00492 {
00493   return this->rebind_context (ACE_Registry::make_string (name),
00494                                new_naming_context);
00495 }
00496 
00497 
00498 // Rename <naming_context> to <name>
00499 // (String version)
00500 int
00501 ACE_Registry::Naming_Context::rebind_context (const ACE_TString &name,
00502                                               /* const */ Naming_Context &new_naming_context)
00503 {
00504   Naming_Context old_naming_context;
00505   // find the old one first
00506   long result = this->resolve_context (name,
00507                                        old_naming_context);
00508   if (result == 0)
00509     {
00510       // naming_context is found: delete entry
00511       result = this->unbind_context (name);
00512       if (result == 0)
00513         {
00514           // successful deletion; rebind
00515           // beware of race conditions here
00516           // (lets resolve this later)
00517           result = this->bind_new_context (name, new_naming_context);
00518         }
00519     }
00520   return result;
00521 }
00522 
00523 
00524 // Remove naming_context with <name> from <this> context
00525 // (Name version)
00526 int
00527 ACE_Registry::Naming_Context::unbind_context (const Name &name)
00528 {
00529   return this->unbind_context (ACE_Registry::make_string (name));
00530 }
00531 
00532 
00533 // Remove naming_context with <name> from <this> context
00534 // (String version)
00535 int
00536 ACE_Registry::Naming_Context::unbind_context (const ACE_TString &name)
00537 {
00538   long result = ACE_TEXT_RegDeleteKey (this->key_,
00539                                                        name.c_str ());
00540 
00541   ACE_REGISTRY_CALL_RETURN (result);
00542 }
00543 
00544 
00545 // Find <naming_context> with <name> in <this> context
00546 // (Name version)
00547 int
00548 ACE_Registry::Naming_Context::resolve_context (const Name &name,
00549                                                Naming_Context &naming_context,
00550                                                u_long security_access)
00551 {
00552   return this->resolve_context (ACE_Registry::make_string (name),
00553                                 naming_context,
00554                                 security_access);
00555 }
00556 
00557 
00558 // Find <naming_context> with <name> in <this> context
00559 // (String version)
00560 int
00561 ACE_Registry::Naming_Context::resolve_context (const ACE_TString &name,
00562                                                Naming_Context &naming_context,
00563                                                u_long security_access)
00564 {
00565   long result = ACE_TEXT_RegOpenKeyEx (this->key_,
00566                                        name.c_str (),
00567                                        0,
00568                                        security_access,
00569                                        &naming_context.key_);
00570   if (result == ERROR_SUCCESS)
00571     {
00572       // set the correct parent
00573       naming_context.parent (this->key_);
00574       // set the correct name
00575       naming_context.name (name);
00576     }
00577 
00578   ACE_REGISTRY_CALL_RETURN (result);
00579 }
00580 
00581 
00582 // Same as unbind_context() with <this> as naming_context
00583 int
00584 ACE_Registry::Naming_Context::destroy (void)
00585 {
00586   // hopefully the parent_key_ is still open
00587   long result = ACE_TEXT_RegDeleteKey (this->parent_key_,
00588                                                        this->name_.c_str ());
00589 
00590   ACE_REGISTRY_CALL_RETURN (result);
00591 }
00592 
00593 
00594 // Sync content of context to disk
00595 int
00596 ACE_Registry::Naming_Context::flush (void)
00597 {
00598   long result = ::RegFlushKey (this->key_);
00599   ACE_REGISTRY_CALL_RETURN (result);
00600 }
00601 
00602 
00603 // Close the handle of the context
00604 int
00605 ACE_Registry::Naming_Context::close (void)
00606 {
00607   long result = this->key_ ? ::RegCloseKey (this->key_) : ERROR_SUCCESS;
00608   ACE_REGISTRY_CALL_RETURN (result);
00609 }
00610 
00611 
00612 // Convert a <name> to a <string>
00613 ACE_TString
00614 ACE_Registry::make_string (const Name &const_name)
00615 {
00616   ACE_TString string;
00617   Name &name = const_cast<Name &> (const_name);
00618 
00619   // Iterator through the components of name
00620   for (Name::iterator iterator = name.begin ();
00621        iterator != name.end ();
00622        iterator++)
00623     {
00624       if (iterator != name.begin ())
00625         // If this is not the first component, we will add separators
00626         string += STRING_SEPARATOR;
00627       const Name_Component &component = *iterator;
00628       // Add to string
00629       string += component.id_;
00630     }
00631 
00632   return string;
00633 }
00634 
00635 
00636 // Convert a <string> to a <name>
00637 ACE_Registry::Name
00638 ACE_Registry::make_name (const ACE_TString &string)
00639 {
00640   ssize_t new_position = 0;
00641   ssize_t last_position = 0;
00642   Name name;
00643 
00644   // Rememeber: NPOS is -1
00645   while (new_position != ACE_TString::npos)
00646     {
00647       Name_Component component;
00648       // Find the separator
00649       new_position = string.find (STRING_SEPARATOR, new_position);
00650       if (new_position != ACE_TString::npos)
00651         // If we have not gone past the end
00652         {
00653           // Get the substring
00654           component.id_ = string.substr (last_position,
00655                                          new_position - last_position);
00656           // Skip past the seperator
00657           new_position +=
00658             ACE_OS::strlen (STRING_SEPARATOR);
00659         }
00660       else
00661         {
00662           // Get the last substring
00663           component.id_ = string.substr (last_position);
00664         }
00665       // Update positions
00666       last_position = new_position;
00667       // Insert component into name
00668       name.insert (component);
00669     }
00670 
00671   return name;
00672 }
00673 
00674 
00675 // Set key
00676 void
00677 ACE_Registry::Naming_Context::key (HKEY key)
00678 {
00679   this->key_ = key;
00680 }
00681 
00682 
00683 // Get key
00684 HKEY
00685 ACE_Registry::Naming_Context::key (void)
00686 {
00687   return this->key_;
00688 }
00689 
00690 
00691 // Set parent
00692 void
00693 ACE_Registry::Naming_Context::parent (HKEY parent)
00694 {
00695   this->parent_key_ = parent;
00696 }
00697 
00698 
00699 // Get parent
00700 HKEY
00701 ACE_Registry::Naming_Context::parent (void)
00702 {
00703   return this->parent_key_;
00704 }
00705 
00706 
00707 // Set name
00708 // (Name version)
00709 void
00710 ACE_Registry::Naming_Context::name (const Name &name)
00711 {
00712   this->name_ = ACE_Registry::make_string (name);
00713 }
00714 
00715 
00716 // Get name
00717 // (Name version)
00718 void
00719 ACE_Registry::Naming_Context::name (Name &name)
00720 {
00721   name = ACE_Registry::make_name (this->name_);
00722 }
00723 
00724 
00725 // Set name
00726 // (String version)
00727 void
00728 ACE_Registry::Naming_Context::name (const ACE_TString &name)
00729 {
00730   this->name_ = name;
00731 }
00732 
00733 
00734 // Get name
00735 // (String version)
00736 ACE_TString
00737 ACE_Registry::Naming_Context::name (void)
00738 {
00739   return this->name_;
00740 }
00741 
00742 
00743 // Get name
00744 // (String version)
00745 void
00746 ACE_Registry::Naming_Context::name (ACE_TString &name)
00747 {
00748   name = this->name_;
00749 }
00750 
00751 
00752 // listing function: iterator creator
00753 // This is useful when there are many objects and contexts
00754 // in <this> context and you only want to look at a few entries
00755 // at a time
00756 int
00757 ACE_Registry::Naming_Context::list (u_long how_many,
00758                                     Binding_List &list,
00759                                     Binding_Iterator &iter)
00760 {
00761   // Empty list
00762   static const ACE_Registry::Binding_List empty_list;
00763   // Make sure that the list is empty
00764   list = empty_list;
00765 
00766   // Correctly initalize the iterator
00767   iter.reset ();
00768 
00769   // Make sure that the iterator uses <this> naming context
00770   iter.naming_context (*this);
00771 
00772   // Start iterations from the objects
00773   iter.current_enumeration (iter.object_iteration_);
00774 
00775   // Get the next <how_many> values
00776   long result = iter.next_n (how_many,
00777                                  list);
00778   return result;
00779 }
00780 
00781 
00782 // listing function: iterator creator
00783 // This gives back a listing of all entries in <this> context.
00784 int
00785 ACE_Registry::Naming_Context::list (Binding_List &list)
00786 {
00787   // Empty list
00788   static const ACE_Registry::Binding_List empty_list;
00789   // Make sure that the list is empty
00790   list = empty_list;
00791 
00792   // Create an iterator
00793   ACE_Registry::Binding_Iterator iterator;
00794 
00795   // Make sure that the iterator uses <this> naming context
00796   iterator.naming_context (*this);
00797 
00798   // Start iterations from the objects
00799   iterator.current_enumeration (iterator.object_iteration_);
00800 
00801   long result = 0;
00802   while (1)
00803     {
00804       ACE_Registry::Binding binding;
00805       result = iterator.next_one (binding);
00806       if (result == 0)
00807         list.insert (binding);
00808       else
00809         break;
00810     }
00811   return 0;
00812 }
00813 
00814 
00815 // Default constructor
00816 ACE_Registry::Binding_Iterator::Binding_Iterator ()
00817   : object_iteration_ (*this),
00818     context_iteration_ (*this),
00819     iteration_complete_ (*this)
00820 {
00821   this->reset ();
00822 }
00823 
00824 
00825 void
00826 ACE_Registry::Binding_Iterator::reset ()
00827 {
00828   this->current_enumeration_ = &this->iteration_complete_;
00829   this->iteration_complete_.reset ();
00830   this->object_iteration_.reset ();
00831   this->context_iteration_.reset ();
00832 }
00833 
00834 
00835 void
00836 ACE_Registry::Binding_Iterator::Iteration_State::reset ()
00837 {
00838   this->index_ = 0;
00839 }
00840 
00841 
00842 ACE_Registry::Binding_Iterator::Iteration_State::Iteration_State (Binding_Iterator &iter)
00843   : parent_ (&iter),
00844     index_ (0)
00845 {
00846 }
00847 
00848 
00849 ACE_Registry::Binding_Iterator::Object_Iteration::Object_Iteration (Binding_Iterator &iter)
00850   : Iteration_State (iter)
00851 {
00852 }
00853 
00854 
00855 ACE_Registry::Binding_Iterator::Context_Iteration::Context_Iteration (Binding_Iterator &iter)
00856   : Iteration_State (iter)
00857 {
00858 }
00859 
00860 
00861 ACE_Registry::Binding_Iterator::Iteration_Complete::Iteration_Complete (Binding_Iterator &iter)
00862   : Iteration_State (iter)
00863 {
00864 }
00865 
00866 
00867 // Next entry
00868 int
00869 ACE_Registry::Binding_Iterator::next_one (Binding &binding)
00870 {
00871   u_long how_many = 1;
00872   Binding_List list;
00873 
00874   // Get next n (where n is one)
00875   long result = this->next_n (how_many, list);
00876 
00877   if (result == 0)
00878     // Success
00879     binding = (*list.begin ());
00880 
00881   return result;
00882 }
00883 
00884 
00885 // Next <how_many> entries
00886 int
00887 ACE_Registry::Binding_Iterator::next_n (u_long how_many,
00888                                         Binding_List &list)
00889 {
00890   // Empty list
00891   static const ACE_Registry::Binding_List empty_list;
00892   // Make sure that the list is empty
00893   list = empty_list;
00894 
00895   return this->current_enumeration_->next_n (how_many, list);
00896 }
00897 
00898 
00899 // Destroy iterator
00900 int
00901 ACE_Registry::Binding_Iterator::destroy (void)
00902 {
00903   this->reset ();
00904   return 0;
00905 }
00906 
00907 
00908 // Set/Get naming_context
00909 void
00910 ACE_Registry::Binding_Iterator::naming_context (Naming_Context &naming_context)
00911 {
00912   this->naming_context_ = &naming_context;
00913 }
00914 
00915 
00916 ACE_Registry::Naming_Context &
00917 ACE_Registry::Binding_Iterator::naming_context (void)
00918 {
00919   return *this->naming_context_;
00920 }
00921 
00922 
00923 // Set/Get current enumeration
00924 void
00925 ACE_Registry::Binding_Iterator::current_enumeration (Iteration_State &current_enumeration)
00926 {
00927   this->current_enumeration_ = &current_enumeration;
00928 }
00929 
00930 
00931 ACE_Registry::Binding_Iterator::Iteration_State &
00932 ACE_Registry::Binding_Iterator::current_enumeration (void)
00933 {
00934   return *this->current_enumeration_;
00935 }
00936 
00937 
00938 int
00939 ACE_Registry::Binding_Iterator::Object_Iteration::next_n (u_long how_many,
00940                                                           Binding_List &list)
00941 {
00942   // Make a copy
00943   u_long requested = how_many;
00944 
00945   // While there are more entries to be added to the list
00946   while (how_many > 0)
00947     {
00948       ACE_TCHAR string [ACE_Registry::Naming_Context::MAX_OBJECT_NAME_SIZE];
00949       u_long size = sizeof string / sizeof (ACE_TCHAR);
00950       long result = ACE_TEXT_RegEnumValue (this->parent_->naming_context ().key (),
00951                                            this->index_,
00952                                            string,
00953                                            &size,
00954                                            0,
00955                                            0,
00956                                            0,
00957                                            0);
00958       switch (result)
00959         {
00960         case ERROR_SUCCESS:
00961           // Object found
00962           {
00963             // Readjust counters
00964             this->index_++;
00965             how_many--;
00966 
00967             // Add to list
00968             // Create binding
00969             Binding binding (string, OBJECT);
00970             // Add to binding list
00971             list.insert (binding);
00972           }
00973         // Continue to add to list
00974         break;
00975 
00976         case ERROR_NO_MORE_ITEMS:
00977           // Enumeration of objects complete
00978           // Reset index
00979           this->index_ = 0;
00980 
00981           // Current enumeration will become CONTEXTS
00982           this->parent_->current_enumeration (this->parent_->context_iteration_);
00983           result = this->parent_->current_enumeration ().next_n (how_many,
00984                                                                  list);
00985           // If we were able to add objects
00986           if (requested != how_many)
00987             return 0;
00988           else
00989             return result;
00990 
00991         default:
00992           // Strange error
00993           // Reset index
00994           this->index_ = 0;
00995           // Current enumeration will become COMPLETE
00996           this->parent_->current_enumeration (this->parent_->iteration_complete_);
00997           // strange error
00998           return -1;
00999         }
01000     }
01001   // If we reach here, all of <how_many> pairs were added to the list
01002   // Since more entries may be available
01003   // current enumeration will remain OBJECTS
01004   return 0;
01005 }
01006 
01007 
01008 int
01009 ACE_Registry::Binding_Iterator::Context_Iteration::next_n (u_long how_many,
01010                                                            Binding_List &list)
01011 {
01012   // Make a copy
01013   u_long requested = how_many;
01014 
01015   // While there are more entries to be added to the list
01016   while (how_many > 0)
01017     {
01018       ACE_TCHAR string [ACE_Registry::Naming_Context::MAX_CONTEXT_NAME_SIZE];
01019       u_long size = sizeof string / sizeof (ACE_TCHAR);
01020       long result = ACE_TEXT_RegEnumKeyEx (this->parent_->naming_context (). key (),
01021                                            this->index_,
01022                                            string,
01023                                            &size,
01024                                            0,
01025                                            0,
01026                                            0,
01027                                            0);
01028       switch (result)
01029         {
01030         case ERROR_SUCCESS:
01031           // Object found
01032           {
01033             // Readjust counters
01034             this->index_++;
01035             how_many--;
01036 
01037             // Add to list
01038             // Create binding
01039             Binding binding (string, CONTEXT);
01040             // Add to binding list
01041             list.insert (binding);
01042           }
01043         // Continue to add to list
01044         break;
01045 
01046         case ERROR_NO_MORE_ITEMS:
01047           // Enumeration of objects complete
01048 
01049           /* FALL THROUGH */
01050 
01051         default:
01052           // Strange error
01053 
01054           // Reset index
01055           this->index_ = 0;
01056           // Current enumeration will become CONTEXTS
01057           this->parent_->current_enumeration (this->parent_->iteration_complete_);
01058 
01059           // If we were able to add contexts
01060           if (requested != how_many)
01061             return 0;
01062           else
01063             return -1;
01064         }
01065     }
01066   // If we reach here, all of <how_many> pairs were added to the list
01067   // Since more entries may be available
01068   // current enumeration will remain CONTEXTS
01069   return 0;
01070 }
01071 
01072 
01073 int
01074 ACE_Registry::Binding_Iterator::Iteration_Complete::next_n (u_long how_many,
01075                                                             Binding_List &list)
01076 {
01077         ACE_UNUSED_ARG(list);
01078         ACE_UNUSED_ARG(how_many);
01079 
01080         // No more values
01081         return -1;
01082 }
01083 
01084 
01085 // Factory method to connect to predefined registries
01086 // This method works for both remote and local machines
01087 // However, for remote machines CLASSES_ROOT and CURRENT_USER
01088 // types are not allowed
01089 /* static */
01090 int
01091 ACE_Predefined_Naming_Contexts::connect (ACE_Registry::Naming_Context &naming_context,
01092                                          HKEY predefined,
01093                                          const ACE_TCHAR *machine_name)
01094 {
01095 #if defined (ACE_HAS_WINCE)
01096   return -1;
01097 #else
01098   long result = -1;
01099 
01100   if (machine_name != 0 && ACE_OS::strcmp (ACE_LIB_TEXT ("localhost"), machine_name) == 0)
01101     machine_name = 0;
01102 
01103   if (predefined == HKEY_LOCAL_MACHINE || predefined == HKEY_USERS)
01104     result =
01105       ACE_TEXT_RegConnectRegistry (const_cast<ACE_TCHAR *> (machine_name),
01106                                    predefined,
01107                                    &naming_context.key_);
01108   if (predefined == HKEY_CURRENT_USER || predefined == HKEY_CLASSES_ROOT)
01109     // Make sure that for these types, the machine is local
01110     if (machine_name == 0 ||
01111         ACE_Predefined_Naming_Contexts::is_local_host (machine_name))
01112       {
01113         naming_context.key_ = predefined;
01114         result = 0;
01115       }
01116     else
01117       result = -1;
01118 
01119   ACE_REGISTRY_CALL_RETURN (result);
01120 #endif  // ACE_HAS_WINCE
01121 }
01122 
01123 // Check if <machine_name> is the local host
01124 /* static */
01125 int
01126 ACE_Predefined_Naming_Contexts::is_local_host (const ACE_TCHAR *machine_name)
01127 {
01128   ACE_TCHAR local_host[MAXHOSTNAMELEN];
01129   int result = ACE_OS::hostname (local_host, sizeof local_host / sizeof (ACE_TCHAR));
01130   if (result == 0)
01131     result = !ACE_OS::strcmp (local_host, machine_name);
01132   else
01133     result = 0;
01134   return result;
01135 }
01136 
01137 ACE_END_VERSIONED_NAMESPACE_DECL
01138 
01139 #endif /* ACE_WIN32 */

Generated on Thu Nov 9 09:42:01 2006 for ACE by doxygen 1.3.6