Boost logo

Boost-Commit :

Subject: [Boost-commit] svn:boost r53362 - in trunk/boost/interprocess: . allocators/detail containers/container detail
From: igaztanaga_at_[hidden]
Date: 2009-05-28 16:44:13


Author: igaztanaga
Date: 2009-05-28 16:44:12 EDT (Thu, 28 May 2009)
New Revision: 53362
URL: http://svn.boost.org/trac/boost/changeset/53362

Log:
Bugs #3090, #3101, #2992, #2973, #2967
Text files modified:
   trunk/boost/interprocess/allocators/detail/node_pool.hpp | 4
   trunk/boost/interprocess/containers/container/stable_vector.hpp | 11 +
   trunk/boost/interprocess/containers/container/vector.hpp | 8
   trunk/boost/interprocess/detail/atomic.hpp | 92 ++++++++++++++
   trunk/boost/interprocess/detail/os_file_functions.hpp | 8
   trunk/boost/interprocess/detail/os_thread_functions.hpp | 4
   trunk/boost/interprocess/detail/tmp_dir_helpers.hpp | 34 +++--
   trunk/boost/interprocess/detail/win32_api.hpp | 250 ++++++++++++++++++++++++---------------
   trunk/boost/interprocess/errors.hpp | 6
   9 files changed, 292 insertions(+), 125 deletions(-)

Modified: trunk/boost/interprocess/allocators/detail/node_pool.hpp
==============================================================================
--- trunk/boost/interprocess/allocators/detail/node_pool.hpp (original)
+++ trunk/boost/interprocess/allocators/detail/node_pool.hpp 2009-05-28 16:44:12 EDT (Thu, 28 May 2009)
@@ -315,13 +315,13 @@
 
    private:
    //!Returns a reference to the block hook placed in the end of the block
- static inline node_t & get_block_hook (void *block, std::size_t blocksize)
+ static node_t & get_block_hook (void *block, std::size_t blocksize)
    {
       return *reinterpret_cast<node_t*>(reinterpret_cast<char*>(block) + blocksize);
    }
 
    //!Returns the starting address of the block reference to the block hook placed in the end of the block
- inline void *get_block_from_hook (node_t *hook, std::size_t blocksize)
+ void *get_block_from_hook (node_t *hook, std::size_t blocksize)
    {
       return (reinterpret_cast<char*>(hook) - blocksize);
    }

Modified: trunk/boost/interprocess/containers/container/stable_vector.hpp
==============================================================================
--- trunk/boost/interprocess/containers/container/stable_vector.hpp (original)
+++ trunk/boost/interprocess/containers/container/stable_vector.hpp 2009-05-28 16:44:12 EDT (Thu, 28 May 2009)
@@ -90,6 +90,8 @@
    }
 
    private:
+ clear_on_destroy(const clear_on_destroy &);
+ clear_on_destroy &operator=(const clear_on_destroy &);
    C &c_;
    bool do_clear_;
 };
@@ -530,6 +532,15 @@
       STABLE_VECTOR_CHECK_INVARIANT;
    }
 
+ explicit stable_vector(size_type n)
+ : internal_data(Allocator()),impl(Allocator())
+ {
+ stable_vector_detail::clear_on_destroy<stable_vector> cod(*this);
+ this->resize(n);
+ STABLE_VECTOR_CHECK_INVARIANT;
+ cod.release();
+ }
+
    stable_vector(size_type n,const T& t=T(),const Allocator& al=Allocator())
    : internal_data(al),impl(al)
    {

Modified: trunk/boost/interprocess/containers/container/vector.hpp
==============================================================================
--- trunk/boost/interprocess/containers/container/vector.hpp (original)
+++ trunk/boost/interprocess/containers/container/vector.hpp 2009-05-28 16:44:12 EDT (Thu, 28 May 2009)
@@ -477,7 +477,7 @@
    //! throws or T's default or copy constructor throws.
    //!
    //! <b>Complexity</b>: Linear to n.
- vector(size_type n)
+ explicit vector(size_type n)
       : base_t(allocator_type())
    { this->resize(n); }
 
@@ -1723,6 +1723,10 @@
    void priv_assign_aux(FwdIt first, FwdIt last, std::forward_iterator_tag)
    {
       size_type n = std::distance(first, last);
+ if(!n){
+ this->prot_destroy_all();
+ return;
+ }
       //Check if we have enough memory or try to expand current memory
       size_type remaining = this->members_.m_capacity - this->members_.m_size;
       bool same_buffer_start;
@@ -1749,7 +1753,7 @@
          if (this->size() >= n){
             //There is memory, but there are more old elements than new ones
             //Overwrite old elements with new ones
- // iG std::copy(first, last, start);
+ assert(start);
             std::copy(first, last, start);
             //Destroy remaining old elements
             this->destroy_n(start + n, this->members_.m_size - n);

Modified: trunk/boost/interprocess/detail/atomic.hpp
==============================================================================
--- trunk/boost/interprocess/detail/atomic.hpp (original)
+++ trunk/boost/interprocess/detail/atomic.hpp 2009-05-28 16:44:12 EDT (Thu, 28 May 2009)
@@ -461,6 +461,98 @@
 } //namespace interprocess{
 } //namespace boost{
 
+#elif defined(__IBMCPP__) && (__IBMCPP__ >= 800) && defined(_AIX)
+
+#include <builtins.h>
+
+namespace boost {
+namespace interprocess {
+namespace detail{
+
+//first define boost::uint32_t versions of __lwarx and __stwcx to avoid poluting
+//all the functions with casts
+
+//! From XLC documenation :
+//! This function can be used with a subsequent stwcxu call to implement a
+//! read-modify-write on a specified memory location. The two functions work
+//! together to ensure that if the store is successfully performed, no other
+//! processor or mechanism can modify the target doubleword between the time
+//! lwarxu function is executed and the time the stwcxu functio ncompletes.
+//! "mem" : pointer to the object
+//! Returns the value at pointed to by mem
+inline boost::uint32_t lwarxu(volatile boost::uint32_t *mem)
+{
+ return static_cast<boost::uint32_t>(__lwarx(reinterpret_cast<volatile int*>(mem)));
+}
+
+//! "mem" : pointer to the object
+//! "val" : the value to store
+//! Returns true if the update of mem is successful and false if it is
+//!unsuccessful
+inline bool stwcxu(volatile boost::uint32_t* mem, boost::uint32_t val)
+{
+ return (__stwcx(reinterpret_cast<volatile int*>(mem), static_cast<int>(val)) != 0);
+}
+
+//! "mem": pointer to the object
+//! "val": amount to add
+//! Returns the old value pointed to by mem
+inline boost::uint32_t atomic_add32
+ (volatile boost::uint32_t *mem, boost::uint32_t val)
+{
+ boost::uint32_t oldValue;
+ do
+ {
+ oldValue = lwarxu(mem);
+ }while (!stwcxu(mem, oldValue+val));
+ return oldValue;
+}
+
+//! Atomically increment an apr_uint32_t by 1
+//! "mem": pointer to the object
+//! Returns the old value pointed to by mem
+inline boost::uint32_t atomic_inc32(volatile boost::uint32_t *mem)
+{ return atomic_add32(mem, 1); }
+
+//! Atomically decrement an boost::uint32_t by 1
+//! "mem": pointer to the atomic value
+//! Returns the old value pointed to by mem
+inline boost::uint32_t atomic_dec32(volatile boost::uint32_t *mem)
+{ return atomic_add32(mem, (boost::uint32_t)-1); }
+
+//! Atomically read an boost::uint32_t from memory
+inline boost::uint32_t atomic_read32(volatile boost::uint32_t *mem)
+{ return *mem; }
+
+//! Compare an boost::uint32_t's value with "cmp".
+//! If they are the same swap the value with "with"
+//! "mem": pointer to the value
+//! "with" what to swap it with
+//! "cmp": the value to compare it to
+//! Returns the old value of *mem
+inline boost::uint32_t atomic_cas32
+ (volatile boost::uint32_t *mem, boost::uint32_t with, boost::uint32_t cmp)
+{
+ boost::uint32_t oldValue;
+ boost::uint32_t valueToStore;
+ do
+ {
+ oldValue = lwarxu(mem);
+ } while (!stwcxu(mem, (oldValue == with) ? cmp : oldValue));
+
+ return oldValue;
+}
+
+//! Atomically set an boost::uint32_t in memory
+//! "mem": pointer to the object
+//! "param": val value that the object will assume
+inline void atomic_write32(volatile boost::uint32_t *mem, boost::uint32_t val)
+{ *mem = val; }
+
+} //namespace detail
+} //namespace interprocess
+} //namespace boost
+
 #else
 
 #error No atomic operations implemented for this platform, sorry!

Modified: trunk/boost/interprocess/detail/os_file_functions.hpp
==============================================================================
--- trunk/boost/interprocess/detail/os_file_functions.hpp (original)
+++ trunk/boost/interprocess/detail/os_file_functions.hpp 2009-05-28 16:44:12 EDT (Thu, 28 May 2009)
@@ -84,6 +84,7 @@
 inline const char *get_temporary_path()
 { return std::getenv("TMP"); }
 
+
 inline file_handle_t create_new_file
    (const char *name, mode_t mode = read_write, bool temporary = false)
 {
@@ -311,12 +312,13 @@
 
 inline const char *get_temporary_path()
 {
+ struct stat data;
    const char *dir = std::getenv("TMPDIR");
- if(!dir){
+ if(!dir || ::stat(dir, &data) != 0){
       dir = std::getenv("TMP");
- if(!dir){
+ if(!dir || ::stat(dir, &data) != 0){
          dir = std::getenv("TEMP");
- if(!dir){
+ if(!dir || ::stat(dir, &data) != 0){
             dir = "/tmp";
          }
       }

Modified: trunk/boost/interprocess/detail/os_thread_functions.hpp
==============================================================================
--- trunk/boost/interprocess/detail/os_thread_functions.hpp (original)
+++ trunk/boost/interprocess/detail/os_thread_functions.hpp 2009-05-28 16:44:12 EDT (Thu, 28 May 2009)
@@ -139,7 +139,7 @@
 }
 
 inline bool equal_thread_id(OS_thread_id_t id1, OS_thread_id_t id2)
-{ return 0 != ::pthread_equal(id1, id2); }
+{ return 0 != pthread_equal(id1, id2); }
 
 inline void thread_yield()
 { ::sched_yield(); }
@@ -152,7 +152,7 @@
 
 inline bool equal_systemwide_thread_id(const OS_systemwide_thread_id_t &id1, const OS_systemwide_thread_id_t &id2)
 {
- return (0 != ::pthread_equal(id1.tid, id2.tid)) && (id1.pid == id2.pid);
+ return (0 != pthread_equal(id1.tid, id2.tid)) && (id1.pid == id2.pid);
 }
 
 inline OS_systemwide_thread_id_t get_invalid_systemwide_thread_id()

Modified: trunk/boost/interprocess/detail/tmp_dir_helpers.hpp
==============================================================================
--- trunk/boost/interprocess/detail/tmp_dir_helpers.hpp (original)
+++ trunk/boost/interprocess/detail/tmp_dir_helpers.hpp 2009-05-28 16:44:12 EDT (Thu, 28 May 2009)
@@ -84,18 +84,30 @@
 }
 #endif
 
-
-inline void tmp_filename(const char *filename, std::string &tmp_name)
+inline void get_tmp_base_dir(std::string &tmp_name)
 {
- const char *tmp_dir = get_temporary_path();
- if(!tmp_dir){
+ #if defined (BOOST_INTERPROCESS_WINDOWS)
+ winapi::get_shared_documents_folder(tmp_name);
+ if(tmp_name.empty()){
+ tmp_name = get_temporary_path();
+ }
+ #else
+ tmp_name = get_temporary_path();
+ #endif
+ if(tmp_name.empty()){
       error_info err = system_error_code();
       throw interprocess_exception(err);
    }
- tmp_name = tmp_dir;
+ //Remove final null.
+ tmp_name += "/boost_interprocess";
+}
+
 
+inline void tmp_filename(const char *filename, std::string &tmp_name)
+{
+ get_tmp_base_dir(tmp_name);
    //Remove final null.
- tmp_name += "/boost_interprocess/";
+ tmp_name += "/";
    #ifdef BOOST_INTERPROCESS_HAS_KERNEL_BOOTTIME
    get_bootstamp(tmp_name, true);
    tmp_name += '/';
@@ -106,15 +118,7 @@
 inline void create_tmp_dir_and_get_filename(const char *filename, std::string &tmp_name)
 {
    //First get the temp directory
- const char *tmp_path = get_temporary_path();
- if(!tmp_path){
- error_info err = system_error_code();
- throw interprocess_exception(err);
- }
-
- //Create Boost.Interprocess dir
- tmp_name = tmp_path;
- tmp_name += "/boost_interprocess";
+ get_tmp_base_dir(tmp_name);
 
    //If fails, check that it's because already exists
    if(!create_directory(tmp_name.c_str())){

Modified: trunk/boost/interprocess/detail/win32_api.hpp
==============================================================================
--- trunk/boost/interprocess/detail/win32_api.hpp (original)
+++ trunk/boost/interprocess/detail/win32_api.hpp 2009-05-28 16:44:12 EDT (Thu, 28 May 2009)
@@ -15,6 +15,7 @@
 #include <boost/interprocess/detail/workaround.hpp>
 #include <cstddef>
 #include <cstring>
+#include <string>
 #include <memory>
 
 #if (defined _MSC_VER) && (_MSC_VER >= 1200)
@@ -145,6 +146,9 @@
 static const long BootstampLength = 8;
 static const unsigned long MaxPath = 260;
 
+//Keys
+static void * const hkey_local_machine = (void*)(unsigned long*)(long)(0x80000002);
+static unsigned long key_query_value = 0x0001;
 
 } //namespace winapi {
 } //namespace interprocess {
@@ -440,6 +444,12 @@
 typedef long (__stdcall * NtQuerySystemInformation_t)(int, void*, unsigned long, unsigned long *);
 typedef long (__stdcall * NtQueryObject_t)(void*, object_information_class, void *, unsigned long, unsigned long *);
 typedef unsigned long (__stdcall * GetMappedFileName_t)(void *, void *, wchar_t *, unsigned long);
+typedef unsigned long (__stdcall * GetMappedFileName_t)(void *, void *, wchar_t *, unsigned long);
+typedef long (__stdcall * RegOpenKey_t)(void *, const char *, void **);
+typedef long (__stdcall * RegOpenKeyEx_t)(void *, const char *, unsigned long, unsigned long, void **);
+typedef long (__stdcall * RegQueryValue_t)(void *, const char *, char *, long*);
+typedef long (__stdcall * RegQueryValueEx_t)(void *, const char *, unsigned long*, unsigned long*, unsigned char *, unsigned long*);
+typedef long (__stdcall * RegCloseKey_t)(void *);
 
 } //namespace winapi {
 } //namespace interprocess {
@@ -453,7 +463,7 @@
 namespace interprocess {
 namespace winapi {
 
-static inline unsigned long format_message
+inline unsigned long format_message
    (unsigned long dwFlags, const void *lpSource,
     unsigned long dwMessageId, unsigned long dwLanguageId,
     char *lpBuffer, unsigned long nSize, std::va_list *Arguments)
@@ -463,34 +473,34 @@
 }
 
 //And now, wrapper functions
-static inline void * local_free(void *hmem)
+inline void * local_free(void *hmem)
 { return LocalFree(hmem); }
 
-static inline unsigned long make_lang_id(unsigned long p, unsigned long s)
+inline unsigned long make_lang_id(unsigned long p, unsigned long s)
 { return ((((unsigned short)(s)) << 10) | (unsigned short)(p)); }
 
-static inline void sched_yield()
+inline void sched_yield()
 { Sleep(1); }
 
-static inline unsigned long get_current_thread_id()
+inline unsigned long get_current_thread_id()
 { return GetCurrentThreadId(); }
 
-static inline unsigned long get_current_process_id()
+inline unsigned long get_current_process_id()
 { return GetCurrentProcessId(); }
 
-static inline unsigned int close_handle(void* handle)
+inline unsigned int close_handle(void* handle)
 { return CloseHandle(handle); }
 
-static inline void * find_first_file(const char *lpFileName, win32_find_data_t *lpFindFileData)
+inline void * find_first_file(const char *lpFileName, win32_find_data_t *lpFindFileData)
 { return FindFirstFileA(lpFileName, lpFindFileData); }
 
-static inline bool find_next_file(void *hFindFile, win32_find_data_t *lpFindFileData)
+inline bool find_next_file(void *hFindFile, win32_find_data_t *lpFindFileData)
 { return FindNextFileA(hFindFile, lpFindFileData) != 0; }
 
-static inline bool find_close(void *handle)
+inline bool find_close(void *handle)
 { return FindClose(handle) != 0; }
 
-static inline bool duplicate_current_process_handle
+inline bool duplicate_current_process_handle
    (void *hSourceHandle, void **lpTargetHandle)
 {
    return 0 != DuplicateHandle
@@ -499,41 +509,41 @@
       , duplicate_same_access);
 }
 
-static inline unsigned long get_last_error()
+inline unsigned long get_last_error()
 { return GetLastError(); }
 
-static inline void get_system_time_as_file_time(interprocess_filetime *filetime)
+inline void get_system_time_as_file_time(interprocess_filetime *filetime)
 { GetSystemTimeAsFileTime(filetime); }
 
-static inline bool file_time_to_local_file_time
+inline bool file_time_to_local_file_time
    (const interprocess_filetime *in, const interprocess_filetime *out)
 { return 0 != FileTimeToLocalFileTime(in, out); }
 
-static inline void *create_mutex(const char *name)
+inline void *create_mutex(const char *name)
 { return CreateMutexA(0, 0, name); }
 
-static inline void *open_mutex(const char *name)
+inline void *open_mutex(const char *name)
 { return OpenMutexA(mutex_all_access, 0, name); }
 
-static inline unsigned long wait_for_single_object(void *handle, unsigned long time)
+inline unsigned long wait_for_single_object(void *handle, unsigned long time)
 { return WaitForSingleObject(handle, time); }
 
-static inline int release_mutex(void *handle)
+inline int release_mutex(void *handle)
 { return ReleaseMutex(handle); }
 
-static inline int unmap_view_of_file(void *address)
+inline int unmap_view_of_file(void *address)
 { return UnmapViewOfFile(address); }
 
-static inline void *create_semaphore(long initialCount, const char *name)
+inline void *create_semaphore(long initialCount, const char *name)
 { return CreateSemaphoreA(0, initialCount, (long)(((unsigned long)(-1))>>1), name); }
 
-static inline int release_semaphore(void *handle, long release_count, long *prev_count)
+inline int release_semaphore(void *handle, long release_count, long *prev_count)
 { return ReleaseSemaphore(handle, release_count, prev_count); }
 
-static inline void *open_semaphore(const char *name)
+inline void *open_semaphore(const char *name)
 { return OpenSemaphoreA(semaphore_all_access, 1, name); }
 
-static inline void * create_file_mapping (void * handle, unsigned long access, unsigned long high_size, unsigned long low_size, const char * name)
+inline void * create_file_mapping (void * handle, unsigned long access, unsigned long high_size, unsigned long low_size, const char * name)
 {
    interprocess_security_attributes sa;
    interprocess_security_descriptor sd;
@@ -549,86 +559,86 @@
   //return CreateFileMappingA (handle, 0, access, high_size, low_size, name);
 }
 
-static inline void * open_file_mapping (unsigned long access, const char *name)
+inline void * open_file_mapping (unsigned long access, const char *name)
 { return OpenFileMappingA (access, 0, name); }
 
-static inline void *map_view_of_file_ex(void *handle, unsigned long file_access, unsigned long highoffset, unsigned long lowoffset, std::size_t numbytes, void *base_addr)
+inline void *map_view_of_file_ex(void *handle, unsigned long file_access, unsigned long highoffset, unsigned long lowoffset, std::size_t numbytes, void *base_addr)
 { return MapViewOfFileEx(handle, file_access, highoffset, lowoffset, numbytes, base_addr); }
 
-static inline void *create_file(const char *name, unsigned long access, unsigned long creation_flags, unsigned long attributes = 0)
+inline void *create_file(const char *name, unsigned long access, unsigned long creation_flags, unsigned long attributes = 0)
 { return CreateFileA(name, access, file_share_read | file_share_write | file_share_delete, 0, creation_flags, attributes, 0); }
 
-static inline bool delete_file(const char *name)
+inline bool delete_file(const char *name)
 { return 0 != DeleteFileA(name); }
 
-static inline bool move_file_ex(const char *source_filename, const char *destination_filename, unsigned long flags)
+inline bool move_file_ex(const char *source_filename, const char *destination_filename, unsigned long flags)
 { return 0 != MoveFileExA(source_filename, destination_filename, flags); }
 
-static inline void get_system_info(system_info *info)
+inline void get_system_info(system_info *info)
 { GetSystemInfo(info); }
 
-static inline int flush_view_of_file(void *base_addr, std::size_t numbytes)
+inline int flush_view_of_file(void *base_addr, std::size_t numbytes)
 { return FlushViewOfFile(base_addr, numbytes); }
 
-static inline bool get_file_size(void *handle, __int64 &size)
+inline bool get_file_size(void *handle, __int64 &size)
 { return 0 != GetFileSizeEx(handle, &size); }
 
-static inline bool create_directory(const char *name, interprocess_security_attributes* security)
+inline bool create_directory(const char *name, interprocess_security_attributes* security)
 { return 0 != CreateDirectoryA(name, security); }
 
-static inline bool remove_directory(const char *lpPathName)
+inline bool remove_directory(const char *lpPathName)
 { return 0 != RemoveDirectoryA(lpPathName); }
 
-static inline unsigned long get_temp_path(unsigned long length, char *buffer)
+inline unsigned long get_temp_path(unsigned long length, char *buffer)
 { return GetTempPathA(length, buffer); }
 
-static inline int set_end_of_file(void *handle)
+inline int set_end_of_file(void *handle)
 { return 0 != SetEndOfFile(handle); }
 
-static inline bool set_file_pointer_ex(void *handle, __int64 distance, __int64 *new_file_pointer, unsigned long move_method)
+inline bool set_file_pointer_ex(void *handle, __int64 distance, __int64 *new_file_pointer, unsigned long move_method)
 { return 0 != SetFilePointerEx(handle, distance, new_file_pointer, move_method); }
 
-static inline bool lock_file_ex(void *hnd, unsigned long flags, unsigned long reserved, unsigned long size_low, unsigned long size_high, interprocess_overlapped *overlapped)
+inline bool lock_file_ex(void *hnd, unsigned long flags, unsigned long reserved, unsigned long size_low, unsigned long size_high, interprocess_overlapped *overlapped)
 { return 0 != LockFileEx(hnd, flags, reserved, size_low, size_high, overlapped); }
 
-static inline bool unlock_file_ex(void *hnd, unsigned long reserved, unsigned long size_low, unsigned long size_high, interprocess_overlapped *overlapped)
+inline bool unlock_file_ex(void *hnd, unsigned long reserved, unsigned long size_low, unsigned long size_high, interprocess_overlapped *overlapped)
 { return 0 != UnlockFileEx(hnd, reserved, size_low, size_high, overlapped); }
 
-static inline bool write_file(void *hnd, const void *buffer, unsigned long bytes_to_write, unsigned long *bytes_written, interprocess_overlapped* overlapped)
+inline bool write_file(void *hnd, const void *buffer, unsigned long bytes_to_write, unsigned long *bytes_written, interprocess_overlapped* overlapped)
 { return 0 != WriteFile(hnd, buffer, bytes_to_write, bytes_written, overlapped); }
 
-static inline long interlocked_increment(long volatile *addr)
+inline long interlocked_increment(long volatile *addr)
 { return BOOST_INTERLOCKED_INCREMENT(addr); }
 
-static inline long interlocked_decrement(long volatile *addr)
+inline long interlocked_decrement(long volatile *addr)
 { return BOOST_INTERLOCKED_DECREMENT(addr); }
 
-static inline long interlocked_compare_exchange(long volatile *addr, long val1, long val2)
+inline long interlocked_compare_exchange(long volatile *addr, long val1, long val2)
 { return BOOST_INTERLOCKED_COMPARE_EXCHANGE(addr, val1, val2); }
 
-static inline long interlocked_exchange_add(long volatile* addend, long value)
+inline long interlocked_exchange_add(long volatile* addend, long value)
 { return BOOST_INTERLOCKED_EXCHANGE_ADD(const_cast<long*>(addend), value); }
 
-static inline long interlocked_exchange(long volatile* addend, long value)
+inline long interlocked_exchange(long volatile* addend, long value)
 { return BOOST_INTERLOCKED_EXCHANGE(const_cast<long*>(addend), value); }
 
 //Forward functions
-static inline void *load_library(const char *name)
+inline void *load_library(const char *name)
 { return LoadLibraryA(name); }
 
-static inline bool free_library(void *module)
+inline bool free_library(void *module)
 { return 0 != FreeLibrary(module); }
 
-static inline void *get_proc_address(void *module, const char *name)
+inline void *get_proc_address(void *module, const char *name)
 { return GetProcAddress(module, name); }
 
-static inline void *get_current_process()
+inline void *get_current_process()
 { return GetCurrentProcess(); }
 
-static inline void *get_module_handle(const char *name)
+inline void *get_module_handle(const char *name)
 { return GetModuleHandleA(name); }
 
-static inline void initialize_object_attributes
+inline void initialize_object_attributes
 ( object_attributes_t *pobject_attr, unicode_string_t *name
  , unsigned long attr, void *rootdir, void *security_descr)
 
@@ -641,7 +651,7 @@
    pobject_attr->SecurityQualityOfService = 0;
 }
 
-static inline void rtl_init_empty_unicode_string(unicode_string_t *ucStr, wchar_t *buf, unsigned short bufSize)
+inline void rtl_init_empty_unicode_string(unicode_string_t *ucStr, wchar_t *buf, unsigned short bufSize)
 {
    ucStr->Buffer = buf;
    ucStr->Length = 0;
@@ -649,9 +659,15 @@
 }
 
 //Complex winapi based functions...
+struct library_unloader
+{
+ void *lib_;
+ library_unloader(void *module) : lib_(module){}
+ ~library_unloader(){ free_library(lib_); }
+};
 
 //pszFilename must have room for at least MaxPath+1 characters
-static inline bool get_file_name_from_handle_function
+inline bool get_file_name_from_handle_function
    (void * hFile, wchar_t *pszFilename, std::size_t length, std::size_t &out_length)
 {
    if(length <= MaxPath){
@@ -662,14 +678,7 @@
    if (0 == hiPSAPI)
       return 0;
 
- class library_unloader
- {
- void *lib_;
-
- public:
- library_unloader(void *module) : lib_(module){}
- ~library_unloader(){ free_library(lib_); }
- } unloader(hiPSAPI);
+ library_unloader unloader(hiPSAPI);
 
    // Pointer to function getMappedFileName() in PSAPI.DLL
    GetMappedFileName_t pfGMFN =
@@ -700,7 +709,7 @@
    return(bSuccess);
 }
 
-static inline bool get_system_time_of_day_information(system_timeofday_information &info)
+inline bool get_system_time_of_day_information(system_timeofday_information &info)
 {
    NtQuerySystemInformation_t pNtQuerySystemInformation = (NtQuerySystemInformation_t)
       get_proc_address(get_module_handle("ntdll.dll"), "NtQuerySystemInformation");
@@ -712,7 +721,7 @@
    return true;
 }
 
-static inline bool get_boot_time(unsigned char (&bootstamp) [BootstampLength])
+inline bool get_boot_time(unsigned char (&bootstamp) [BootstampLength])
 {
    system_timeofday_information info;
    bool ret = get_system_time_of_day_information(info);
@@ -723,7 +732,7 @@
    return true;
 }
 
-static inline bool get_boot_and_system_time(unsigned char (&bootsystemstamp) [BootAndSystemstampLength])
+inline bool get_boot_and_system_time(unsigned char (&bootsystemstamp) [BootAndSystemstampLength])
 {
    system_timeofday_information info;
    bool ret = get_system_time_of_day_information(info);
@@ -734,7 +743,7 @@
    return true;
 }
 
-static inline bool get_boot_time_str(char *bootstamp_str, std::size_t &s) //will write BootstampLength chars
+inline bool get_boot_time_str(char *bootstamp_str, std::size_t &s) //will write BootstampLength chars
 {
    if(s < (BootstampLength*2))
       return false;
@@ -755,7 +764,7 @@
    return true;
 }
 
-static inline bool get_boot_and_system_time_wstr(wchar_t *bootsystemstamp, std::size_t &s) //will write BootAndSystemstampLength chars
+inline bool get_boot_and_system_time_wstr(wchar_t *bootsystemstamp, std::size_t &s) //will write BootAndSystemstampLength chars
 {
    if(s < (BootAndSystemstampLength*2))
       return false;
@@ -776,7 +785,25 @@
    return true;
 }
 
-static inline bool unlink_file(const char *filename)
+class handle_closer
+{
+ void *handle_;
+ public:
+ handle_closer(void *handle) : handle_(handle){}
+ ~handle_closer(){ close_handle(handle_); }
+};
+
+union ntquery_mem_t
+{
+ object_name_information_t name;
+ struct ren_t
+ {
+ file_rename_information_t info;
+ wchar_t buf[32767];
+ } ren;
+};
+
+inline bool unlink_file(const char *filename)
 {
    try{
       NtSetInformationFile_t pNtSetInformationFile =
@@ -795,44 +822,16 @@
          return false;
       }
 
- class handle_closer
- {
- void *handle_;
- public:
- handle_closer(void *handle) : handle_(handle){}
- ~handle_closer(){ close_handle(handle_); }
- } handle_closer(fh);
-
- const std::size_t CharArraySize = 32767; //Max name length
-
- union mem_t
- {
- object_name_information_t name;
- struct ren_t
- {
- file_rename_information_t info;
- wchar_t buf[CharArraySize];
- } ren;
- };
-
- class auto_ptr
- {
- public:
- explicit auto_ptr(mem_t *ptr) : ptr_(ptr){}
- ~auto_ptr(){ delete ptr_; }
- mem_t *get() const{ return (ptr_); }
- mem_t *operator->() const{ return this->get(); }
- private:
- mem_t *ptr_;
- } pmem(new mem_t);
+ handle_closer h_closer(fh);
 
+ std::auto_ptr<ntquery_mem_t> pmem(new ntquery_mem_t);
       file_rename_information_t *pfri = (file_rename_information_t*)&pmem->ren.info;
       const std::size_t RenMaxNumChars =
          ((char*)pmem.get() - (char*)&pmem->ren.info.FileName[0])/sizeof(wchar_t);
 
       //Obtain file name
       unsigned long size;
- if(pNtQueryObject(fh, object_name_information, pmem.get(), sizeof(mem_t), &size)){
+ if(pNtQueryObject(fh, object_name_information, pmem.get(), sizeof(ntquery_mem_t), &size)){
          return false;
       }
 
@@ -870,7 +869,7 @@
 
       //Final step: change the name of the in-use file:
       io_status_block_t io;
- if(0 != pNtSetInformationFile(fh, &io, pfri, sizeof(mem_t::ren_t), file_rename_information)){
+ if(0 != pNtSetInformationFile(fh, &io, pfri, sizeof(ntquery_mem_t::ren_t), file_rename_information)){
          return false;
       }
       return true;
@@ -880,6 +879,61 @@
    }
 }
 
+struct reg_closer
+{
+ RegCloseKey_t func_;
+ void *key_;
+ reg_closer(RegCloseKey_t func, void *key) : func_(func), key_(key){}
+ ~reg_closer(){ (*func_)(key_); }
+};
+
+inline void get_shared_documents_folder(std::string &s)
+{
+ s.clear();
+ void *hAdvapi = load_library("Advapi32.dll");
+ if (hAdvapi){
+ library_unloader unloader(hAdvapi);
+ // Pointer to function RegOpenKeyA
+ RegOpenKeyEx_t pRegOpenKey =
+ (RegOpenKeyEx_t)get_proc_address(hAdvapi, "RegOpenKeyExA");
+ if (pRegOpenKey){
+ // Pointer to function RegCloseKey
+ RegCloseKey_t pRegCloseKey =
+ (RegCloseKey_t)get_proc_address(hAdvapi, "RegCloseKey");
+ if (pRegCloseKey){
+ // Pointer to function RegQueryValueA
+ RegQueryValueEx_t pRegQueryValue =
+ (RegQueryValueEx_t)get_proc_address(hAdvapi, "RegQueryValueExA");
+ if (pRegQueryValue){
+ //Open the key
+ void *key;
+ if ((*pRegOpenKey)( hkey_local_machine
+ , "SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Explorer\\Shell Folders"
+ , 0
+ , key_query_value
+ , &key) == 0){
+ reg_closer key_closer(pRegCloseKey, key);
+
+ //Obtain the value
+ unsigned long size;
+ unsigned long type;
+ const char *const reg_value = "Common AppData";
+ long err = (*pRegQueryValue)( key, reg_value, 0, &type, 0, &size);
+ if(!err){
+ //Size includes terminating NULL
+ s.resize(size);
+ err = (*pRegQueryValue)( key, reg_value, 0, &type, (unsigned char*)(&s[0]), &size);
+ if(!err)
+ s.erase(s.end()-1);
+ (void)err;
+ }
+ }
+ }
+ }
+ }
+ }
+}
+
 } //namespace winapi
 } //namespace interprocess
 } //namespace boost

Modified: trunk/boost/interprocess/errors.hpp
==============================================================================
--- trunk/boost/interprocess/errors.hpp (original)
+++ trunk/boost/interprocess/errors.hpp 2009-05-28 16:44:12 EDT (Thu, 28 May 2009)
@@ -50,7 +50,7 @@
 namespace boost {
 namespace interprocess {
 /// @cond
-static inline int system_error_code() // artifact of POSIX and WINDOWS error reporting
+inline int system_error_code() // artifact of POSIX and WINDOWS error reporting
 {
    #if (defined BOOST_INTERPROCESS_WINDOWS)
    return winapi::get_last_error();
@@ -82,7 +82,7 @@
       str.erase( str.size()-1 );
 }
 # else
-static inline void fill_system_message( int system_error, std::string &str)
+inline void fill_system_message( int system_error, std::string &str)
 { str = std::strerror(system_error); }
 # endif
 /// @endcond
@@ -179,7 +179,7 @@
    #endif //#if (defined BOOST_INTERPROCESS_WINDOWS)
 };
 
-static inline error_code_t lookup_error(native_error_t err)
+inline error_code_t lookup_error(native_error_t err)
 {
    const ec_xlate *cur = &ec_table[0],
                   *end = cur + sizeof(ec_table)/sizeof(ec_xlate);


Boost-Commit list run by bdawes at acm.org, david.abrahams at rcn.com, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk