diff options
Diffstat (limited to 'indra/llplugin/llpluginsharedmemory.cpp')
-rw-r--r-- | indra/llplugin/llpluginsharedmemory.cpp | 1004 |
1 files changed, 502 insertions, 502 deletions
diff --git a/indra/llplugin/llpluginsharedmemory.cpp b/indra/llplugin/llpluginsharedmemory.cpp index 3fc9cbd973..e6c43f5fcc 100644 --- a/indra/llplugin/llpluginsharedmemory.cpp +++ b/indra/llplugin/llpluginsharedmemory.cpp @@ -1,502 +1,502 @@ -/** - * @file llpluginsharedmemory.cpp - * LLPluginSharedMemory manages a shared memory segment for use by the LLPlugin API. - * - * @cond - * $LicenseInfo:firstyear=2008&license=viewerlgpl$ - * Second Life Viewer Source Code - * Copyright (C) 2010, Linden Research, Inc. - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation; - * version 2.1 of the License only. - * - * This library is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public - * License along with this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - * - * Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA - * $/LicenseInfo$ - * @endcond - */ - -#include "linden_common.h" - -#include "llpluginsharedmemory.h" - -// on Mac and Linux, we use the native shm_open/mmap interface by using -// #define USE_SHM_OPEN_SHARED_MEMORY 1 -// in the appropriate sections below. - -// For Windows, use: -// #define USE_WIN32_SHARED_MEMORY 1 - -// If we ever want to fall back to the apr implementation for a platform, use: -// #define USE_APR_SHARED_MEMORY 1 - -#if LL_WINDOWS -// #define USE_APR_SHARED_MEMORY 1 - #define USE_WIN32_SHARED_MEMORY 1 -#elif LL_DARWIN - #define USE_SHM_OPEN_SHARED_MEMORY 1 -#elif LL_LINUX - #define USE_SHM_OPEN_SHARED_MEMORY 1 -#endif - - -// FIXME: This path thing is evil and unacceptable. -#if LL_WINDOWS - #define APR_SHARED_MEMORY_PREFIX_STRING "C:\\LLPlugin_" - // Apparnently using the "Global\\" prefix here only works from administrative accounts under Vista. - // Other options I've seen referenced are "Local\\" and "Session\\". - #define WIN32_SHARED_MEMORY_PREFIX_STRING "Local\\LL_" -#else - // mac and linux - #define APR_SHARED_MEMORY_PREFIX_STRING "/tmp/LLPlugin_" - #define SHM_OPEN_SHARED_MEMORY_PREFIX_STRING "/LL" -#endif - -#if USE_APR_SHARED_MEMORY - #include "llapr.h" - #include "apr_shm.h" -#elif USE_SHM_OPEN_SHARED_MEMORY - #include <sys/fcntl.h> - #include <sys/mman.h> - #include <errno.h> -#elif USE_WIN32_SHARED_MEMORY -#include <windows.h> -#endif // USE_APR_SHARED_MEMORY - - -int LLPluginSharedMemory::sSegmentNumber = 0; - -std::string LLPluginSharedMemory::createName(void) -{ - std::stringstream newname; - -#if LL_WINDOWS - newname << GetCurrentProcessId(); -#else // LL_WINDOWS - newname << getpid(); -#endif // LL_WINDOWS - - newname << "_" << sSegmentNumber++; - - return newname.str(); -} - -/** - * @brief LLPluginSharedMemoryImpl is the platform-dependent implementation of LLPluginSharedMemory. TODO:DOC is this necessary/sufficient? kinda obvious. - * - */ -class LLPluginSharedMemoryPlatformImpl -{ -public: - LLPluginSharedMemoryPlatformImpl(); - ~LLPluginSharedMemoryPlatformImpl(); - -#if USE_APR_SHARED_MEMORY - apr_shm_t* mAprSharedMemory; -#elif USE_SHM_OPEN_SHARED_MEMORY - int mSharedMemoryFD; -#elif USE_WIN32_SHARED_MEMORY - HANDLE mMapFile; -#endif - -}; - -/** - * Constructor. Creates a shared memory segment. - */ -LLPluginSharedMemory::LLPluginSharedMemory() -{ - mSize = 0; - mMappedAddress = NULL; - mNeedsDestroy = false; - - mImpl = new LLPluginSharedMemoryPlatformImpl; -} - -/** - * Destructor. Uses destroy() and detach() to ensure shared memory segment is cleaned up. - */ -LLPluginSharedMemory::~LLPluginSharedMemory() -{ - if(mNeedsDestroy) - destroy(); - else - detach(); - - unlink(); - - delete mImpl; -} - -#if USE_APR_SHARED_MEMORY -// MARK: apr implementation - -LLPluginSharedMemoryPlatformImpl::LLPluginSharedMemoryPlatformImpl() -{ - mAprSharedMemory = NULL; -} - -LLPluginSharedMemoryPlatformImpl::~LLPluginSharedMemoryPlatformImpl() -{ - -} - -bool LLPluginSharedMemory::map(void) -{ - mMappedAddress = apr_shm_baseaddr_get(mImpl->mAprSharedMemory); - if(mMappedAddress == NULL) - { - return false; - } - - return true; -} - -bool LLPluginSharedMemory::unmap(void) -{ - // This is a no-op under apr. - return true; -} - -bool LLPluginSharedMemory::close(void) -{ - // This is a no-op under apr. - return true; -} - -bool LLPluginSharedMemory::unlink(void) -{ - // This is a no-op under apr. - return true; -} - - -bool LLPluginSharedMemory::create(size_t size) -{ - mName = APR_SHARED_MEMORY_PREFIX_STRING; - mName += createName(); - mSize = size; - - apr_status_t status = apr_shm_create( &(mImpl->mAprSharedMemory), mSize, mName.c_str(), gAPRPoolp ); - - if(ll_apr_warn_status(status)) - { - return false; - } - - mNeedsDestroy = true; - - return map(); -} - -bool LLPluginSharedMemory::destroy(void) -{ - if(mImpl->mAprSharedMemory) - { - apr_status_t status = apr_shm_destroy(mImpl->mAprSharedMemory); - if(ll_apr_warn_status(status)) - { - // TODO: Is this a fatal error? I think not... - } - mImpl->mAprSharedMemory = NULL; - } - - return true; -} - -bool LLPluginSharedMemory::attach(const std::string &name, size_t size) -{ - mName = name; - mSize = size; - - apr_status_t status = apr_shm_attach( &(mImpl->mAprSharedMemory), mName.c_str(), gAPRPoolp ); - - if(ll_apr_warn_status(status)) - { - return false; - } - - return map(); -} - - -bool LLPluginSharedMemory::detach(void) -{ - if(mImpl->mAprSharedMemory) - { - apr_status_t status = apr_shm_detach(mImpl->mAprSharedMemory); - if(ll_apr_warn_status(status)) - { - // TODO: Is this a fatal error? I think not... - } - mImpl->mAprSharedMemory = NULL; - } - - return true; -} - - -#elif USE_SHM_OPEN_SHARED_MEMORY -// MARK: shm_open/mmap implementation - -LLPluginSharedMemoryPlatformImpl::LLPluginSharedMemoryPlatformImpl() -{ - mSharedMemoryFD = -1; -} - -LLPluginSharedMemoryPlatformImpl::~LLPluginSharedMemoryPlatformImpl() -{ -} - -bool LLPluginSharedMemory::map(void) -{ - mMappedAddress = ::mmap(NULL, mSize, PROT_READ | PROT_WRITE, MAP_SHARED, mImpl->mSharedMemoryFD, 0); - if(mMappedAddress == NULL) - { - return false; - } - - LL_DEBUGS("Plugin") << "memory mapped at " << mMappedAddress << LL_ENDL; - - return true; -} - -bool LLPluginSharedMemory::unmap(void) -{ - if(mMappedAddress != NULL) - { - LL_DEBUGS("Plugin") << "calling munmap(" << mMappedAddress << ", " << mSize << ")" << LL_ENDL; - if(::munmap(mMappedAddress, mSize) == -1) - { - // TODO: Is this a fatal error? I think not... - } - - mMappedAddress = NULL; - } - - return true; -} - -bool LLPluginSharedMemory::close(void) -{ - if(mImpl->mSharedMemoryFD != -1) - { - LL_DEBUGS("Plugin") << "calling close(" << mImpl->mSharedMemoryFD << ")" << LL_ENDL; - if(::close(mImpl->mSharedMemoryFD) == -1) - { - // TODO: Is this a fatal error? I think not... - } - - mImpl->mSharedMemoryFD = -1; - } - return true; -} - -bool LLPluginSharedMemory::unlink(void) -{ - if(!mName.empty()) - { - if(::shm_unlink(mName.c_str()) == -1) - { - return false; - } - } - - return true; -} - - -bool LLPluginSharedMemory::create(size_t size) -{ - mName = SHM_OPEN_SHARED_MEMORY_PREFIX_STRING; - mName += createName(); - mSize = size; - - // Preemptive unlink, just in case something didn't get cleaned up. - unlink(); - - mImpl->mSharedMemoryFD = ::shm_open(mName.c_str(), O_CREAT | O_RDWR, S_IRUSR | S_IWUSR); - if(mImpl->mSharedMemoryFD == -1) - { - return false; - } - - mNeedsDestroy = true; - - if(::ftruncate(mImpl->mSharedMemoryFD, mSize) == -1) - { - return false; - } - - - return map(); -} - -bool LLPluginSharedMemory::destroy(void) -{ - unmap(); - close(); - - return true; -} - - -bool LLPluginSharedMemory::attach(const std::string &name, size_t size) -{ - mName = name; - mSize = size; - - mImpl->mSharedMemoryFD = ::shm_open(mName.c_str(), O_RDWR, S_IRUSR | S_IWUSR); - if(mImpl->mSharedMemoryFD == -1) - { - return false; - } - - // unlink here so the segment will be cleaned up automatically after the last close. - unlink(); - - return map(); -} - -bool LLPluginSharedMemory::detach(void) -{ - unmap(); - close(); - return true; -} - -#elif USE_WIN32_SHARED_MEMORY -// MARK: Win32 CreateFileMapping-based implementation - -// Reference: http://msdn.microsoft.com/en-us/library/aa366551(VS.85).aspx - -LLPluginSharedMemoryPlatformImpl::LLPluginSharedMemoryPlatformImpl() -{ - mMapFile = NULL; -} - -LLPluginSharedMemoryPlatformImpl::~LLPluginSharedMemoryPlatformImpl() -{ - -} - -bool LLPluginSharedMemory::map(void) -{ - mMappedAddress = MapViewOfFile( - mImpl->mMapFile, // handle to map object - FILE_MAP_ALL_ACCESS, // read/write permission - 0, - 0, - mSize); - - if(mMappedAddress == NULL) - { - LL_WARNS("Plugin") << "MapViewOfFile failed: " << GetLastError() << LL_ENDL; - return false; - } - - LL_DEBUGS("Plugin") << "memory mapped at " << mMappedAddress << LL_ENDL; - - return true; -} - -bool LLPluginSharedMemory::unmap(void) -{ - if(mMappedAddress != NULL) - { - UnmapViewOfFile(mMappedAddress); - mMappedAddress = NULL; - } - - return true; -} - -bool LLPluginSharedMemory::close(void) -{ - if(mImpl->mMapFile != NULL) - { - CloseHandle(mImpl->mMapFile); - mImpl->mMapFile = NULL; - } - - return true; -} - -bool LLPluginSharedMemory::unlink(void) -{ - // This is a no-op on Windows. - return true; -} - - -bool LLPluginSharedMemory::create(size_t size) -{ - mName = WIN32_SHARED_MEMORY_PREFIX_STRING; - mName += createName(); - mSize = size; - - mImpl->mMapFile = CreateFileMappingA( - INVALID_HANDLE_VALUE, // use paging file - NULL, // default security - PAGE_READWRITE, // read/write access - 0, // max. object size - mSize, // buffer size - mName.c_str()); // name of mapping object - - if(mImpl->mMapFile == NULL) - { - LL_WARNS("Plugin") << "CreateFileMapping failed: " << GetLastError() << LL_ENDL; - return false; - } - - mNeedsDestroy = true; - - return map(); -} - -bool LLPluginSharedMemory::destroy(void) -{ - unmap(); - close(); - return true; -} - -bool LLPluginSharedMemory::attach(const std::string &name, size_t size) -{ - mName = name; - mSize = size; - - mImpl->mMapFile = OpenFileMappingA( - FILE_MAP_ALL_ACCESS, // read/write access - false, // do not inherit the name - mName.c_str()); // name of mapping object - - if(mImpl->mMapFile == NULL) - { - LL_WARNS("Plugin") << "OpenFileMapping failed: " << GetLastError() << LL_ENDL; - return false; - } - - return map(); -} - -bool LLPluginSharedMemory::detach(void) -{ - unmap(); - close(); - return true; -} - - - -#endif +/**
+ * @file llpluginsharedmemory.cpp
+ * LLPluginSharedMemory manages a shared memory segment for use by the LLPlugin API.
+ *
+ * @cond
+ * $LicenseInfo:firstyear=2008&license=viewerlgpl$
+ * Second Life Viewer Source Code
+ * Copyright (C) 2010, Linden Research, Inc.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation;
+ * version 2.1 of the License only.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
+ *
+ * Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA
+ * $/LicenseInfo$
+ * @endcond
+ */
+
+#include "linden_common.h"
+
+#include "llpluginsharedmemory.h"
+
+// on Mac and Linux, we use the native shm_open/mmap interface by using
+// #define USE_SHM_OPEN_SHARED_MEMORY 1
+// in the appropriate sections below.
+
+// For Windows, use:
+// #define USE_WIN32_SHARED_MEMORY 1
+
+// If we ever want to fall back to the apr implementation for a platform, use:
+// #define USE_APR_SHARED_MEMORY 1
+
+#if LL_WINDOWS
+// #define USE_APR_SHARED_MEMORY 1
+ #define USE_WIN32_SHARED_MEMORY 1
+#elif LL_DARWIN
+ #define USE_SHM_OPEN_SHARED_MEMORY 1
+#elif LL_LINUX
+ #define USE_SHM_OPEN_SHARED_MEMORY 1
+#endif
+
+
+// FIXME: This path thing is evil and unacceptable.
+#if LL_WINDOWS
+ #define APR_SHARED_MEMORY_PREFIX_STRING "C:\\LLPlugin_"
+ // Apparnently using the "Global\\" prefix here only works from administrative accounts under Vista.
+ // Other options I've seen referenced are "Local\\" and "Session\\".
+ #define WIN32_SHARED_MEMORY_PREFIX_STRING "Local\\LL_"
+#else
+ // mac and linux
+ #define APR_SHARED_MEMORY_PREFIX_STRING "/tmp/LLPlugin_"
+ #define SHM_OPEN_SHARED_MEMORY_PREFIX_STRING "/LL"
+#endif
+
+#if USE_APR_SHARED_MEMORY
+ #include "llapr.h"
+ #include "apr_shm.h"
+#elif USE_SHM_OPEN_SHARED_MEMORY
+ #include <sys/fcntl.h>
+ #include <sys/mman.h>
+ #include <errno.h>
+#elif USE_WIN32_SHARED_MEMORY
+#include <windows.h>
+#endif // USE_APR_SHARED_MEMORY
+
+
+int LLPluginSharedMemory::sSegmentNumber = 0;
+
+std::string LLPluginSharedMemory::createName(void)
+{
+ std::stringstream newname;
+
+#if LL_WINDOWS
+ newname << GetCurrentProcessId();
+#else // LL_WINDOWS
+ newname << getpid();
+#endif // LL_WINDOWS
+
+ newname << "_" << sSegmentNumber++;
+
+ return newname.str();
+}
+
+/**
+ * @brief LLPluginSharedMemoryImpl is the platform-dependent implementation of LLPluginSharedMemory. TODO:DOC is this necessary/sufficient? kinda obvious.
+ *
+ */
+class LLPluginSharedMemoryPlatformImpl
+{
+public:
+ LLPluginSharedMemoryPlatformImpl();
+ ~LLPluginSharedMemoryPlatformImpl();
+
+#if USE_APR_SHARED_MEMORY
+ apr_shm_t* mAprSharedMemory;
+#elif USE_SHM_OPEN_SHARED_MEMORY
+ int mSharedMemoryFD;
+#elif USE_WIN32_SHARED_MEMORY
+ HANDLE mMapFile;
+#endif
+
+};
+
+/**
+ * Constructor. Creates a shared memory segment.
+ */
+LLPluginSharedMemory::LLPluginSharedMemory()
+{
+ mSize = 0;
+ mMappedAddress = NULL;
+ mNeedsDestroy = false;
+
+ mImpl = new LLPluginSharedMemoryPlatformImpl;
+}
+
+/**
+ * Destructor. Uses destroy() and detach() to ensure shared memory segment is cleaned up.
+ */
+LLPluginSharedMemory::~LLPluginSharedMemory()
+{
+ if(mNeedsDestroy)
+ destroy();
+ else
+ detach();
+
+ unlink();
+
+ delete mImpl;
+}
+
+#if USE_APR_SHARED_MEMORY
+// MARK: apr implementation
+
+LLPluginSharedMemoryPlatformImpl::LLPluginSharedMemoryPlatformImpl()
+{
+ mAprSharedMemory = NULL;
+}
+
+LLPluginSharedMemoryPlatformImpl::~LLPluginSharedMemoryPlatformImpl()
+{
+
+}
+
+bool LLPluginSharedMemory::map(void)
+{
+ mMappedAddress = apr_shm_baseaddr_get(mImpl->mAprSharedMemory);
+ if(mMappedAddress == NULL)
+ {
+ return false;
+ }
+
+ return true;
+}
+
+bool LLPluginSharedMemory::unmap(void)
+{
+ // This is a no-op under apr.
+ return true;
+}
+
+bool LLPluginSharedMemory::close(void)
+{
+ // This is a no-op under apr.
+ return true;
+}
+
+bool LLPluginSharedMemory::unlink(void)
+{
+ // This is a no-op under apr.
+ return true;
+}
+
+
+bool LLPluginSharedMemory::create(size_t size)
+{
+ mName = APR_SHARED_MEMORY_PREFIX_STRING;
+ mName += createName();
+ mSize = size;
+
+ apr_status_t status = apr_shm_create( &(mImpl->mAprSharedMemory), mSize, mName.c_str(), gAPRPoolp );
+
+ if(ll_apr_warn_status(status))
+ {
+ return false;
+ }
+
+ mNeedsDestroy = true;
+
+ return map();
+}
+
+bool LLPluginSharedMemory::destroy(void)
+{
+ if(mImpl->mAprSharedMemory)
+ {
+ apr_status_t status = apr_shm_destroy(mImpl->mAprSharedMemory);
+ if(ll_apr_warn_status(status))
+ {
+ // TODO: Is this a fatal error? I think not...
+ }
+ mImpl->mAprSharedMemory = NULL;
+ }
+
+ return true;
+}
+
+bool LLPluginSharedMemory::attach(const std::string &name, size_t size)
+{
+ mName = name;
+ mSize = size;
+
+ apr_status_t status = apr_shm_attach( &(mImpl->mAprSharedMemory), mName.c_str(), gAPRPoolp );
+
+ if(ll_apr_warn_status(status))
+ {
+ return false;
+ }
+
+ return map();
+}
+
+
+bool LLPluginSharedMemory::detach(void)
+{
+ if(mImpl->mAprSharedMemory)
+ {
+ apr_status_t status = apr_shm_detach(mImpl->mAprSharedMemory);
+ if(ll_apr_warn_status(status))
+ {
+ // TODO: Is this a fatal error? I think not...
+ }
+ mImpl->mAprSharedMemory = NULL;
+ }
+
+ return true;
+}
+
+
+#elif USE_SHM_OPEN_SHARED_MEMORY
+// MARK: shm_open/mmap implementation
+
+LLPluginSharedMemoryPlatformImpl::LLPluginSharedMemoryPlatformImpl()
+{
+ mSharedMemoryFD = -1;
+}
+
+LLPluginSharedMemoryPlatformImpl::~LLPluginSharedMemoryPlatformImpl()
+{
+}
+
+bool LLPluginSharedMemory::map(void)
+{
+ mMappedAddress = ::mmap(NULL, mSize, PROT_READ | PROT_WRITE, MAP_SHARED, mImpl->mSharedMemoryFD, 0);
+ if(mMappedAddress == NULL)
+ {
+ return false;
+ }
+
+ LL_DEBUGS("Plugin") << "memory mapped at " << mMappedAddress << LL_ENDL;
+
+ return true;
+}
+
+bool LLPluginSharedMemory::unmap(void)
+{
+ if(mMappedAddress != NULL)
+ {
+ LL_DEBUGS("Plugin") << "calling munmap(" << mMappedAddress << ", " << mSize << ")" << LL_ENDL;
+ if(::munmap(mMappedAddress, mSize) == -1)
+ {
+ // TODO: Is this a fatal error? I think not...
+ }
+
+ mMappedAddress = NULL;
+ }
+
+ return true;
+}
+
+bool LLPluginSharedMemory::close(void)
+{
+ if(mImpl->mSharedMemoryFD != -1)
+ {
+ LL_DEBUGS("Plugin") << "calling close(" << mImpl->mSharedMemoryFD << ")" << LL_ENDL;
+ if(::close(mImpl->mSharedMemoryFD) == -1)
+ {
+ // TODO: Is this a fatal error? I think not...
+ }
+
+ mImpl->mSharedMemoryFD = -1;
+ }
+ return true;
+}
+
+bool LLPluginSharedMemory::unlink(void)
+{
+ if(!mName.empty())
+ {
+ if(::shm_unlink(mName.c_str()) == -1)
+ {
+ return false;
+ }
+ }
+
+ return true;
+}
+
+
+bool LLPluginSharedMemory::create(size_t size)
+{
+ mName = SHM_OPEN_SHARED_MEMORY_PREFIX_STRING;
+ mName += createName();
+ mSize = size;
+
+ // Preemptive unlink, just in case something didn't get cleaned up.
+ unlink();
+
+ mImpl->mSharedMemoryFD = ::shm_open(mName.c_str(), O_CREAT | O_RDWR, S_IRUSR | S_IWUSR);
+ if(mImpl->mSharedMemoryFD == -1)
+ {
+ return false;
+ }
+
+ mNeedsDestroy = true;
+
+ if(::ftruncate(mImpl->mSharedMemoryFD, mSize) == -1)
+ {
+ return false;
+ }
+
+
+ return map();
+}
+
+bool LLPluginSharedMemory::destroy(void)
+{
+ unmap();
+ close();
+
+ return true;
+}
+
+
+bool LLPluginSharedMemory::attach(const std::string &name, size_t size)
+{
+ mName = name;
+ mSize = size;
+
+ mImpl->mSharedMemoryFD = ::shm_open(mName.c_str(), O_RDWR, S_IRUSR | S_IWUSR);
+ if(mImpl->mSharedMemoryFD == -1)
+ {
+ return false;
+ }
+
+ // unlink here so the segment will be cleaned up automatically after the last close.
+ unlink();
+
+ return map();
+}
+
+bool LLPluginSharedMemory::detach(void)
+{
+ unmap();
+ close();
+ return true;
+}
+
+#elif USE_WIN32_SHARED_MEMORY
+// MARK: Win32 CreateFileMapping-based implementation
+
+// Reference: http://msdn.microsoft.com/en-us/library/aa366551(VS.85).aspx
+
+LLPluginSharedMemoryPlatformImpl::LLPluginSharedMemoryPlatformImpl()
+{
+ mMapFile = NULL;
+}
+
+LLPluginSharedMemoryPlatformImpl::~LLPluginSharedMemoryPlatformImpl()
+{
+
+}
+
+bool LLPluginSharedMemory::map(void)
+{
+ mMappedAddress = MapViewOfFile(
+ mImpl->mMapFile, // handle to map object
+ FILE_MAP_ALL_ACCESS, // read/write permission
+ 0,
+ 0,
+ mSize);
+
+ if(mMappedAddress == NULL)
+ {
+ LL_WARNS("Plugin") << "MapViewOfFile failed: " << GetLastError() << LL_ENDL;
+ return false;
+ }
+
+ LL_DEBUGS("Plugin") << "memory mapped at " << mMappedAddress << LL_ENDL;
+
+ return true;
+}
+
+bool LLPluginSharedMemory::unmap(void)
+{
+ if(mMappedAddress != NULL)
+ {
+ UnmapViewOfFile(mMappedAddress);
+ mMappedAddress = NULL;
+ }
+
+ return true;
+}
+
+bool LLPluginSharedMemory::close(void)
+{
+ if(mImpl->mMapFile != NULL)
+ {
+ CloseHandle(mImpl->mMapFile);
+ mImpl->mMapFile = NULL;
+ }
+
+ return true;
+}
+
+bool LLPluginSharedMemory::unlink(void)
+{
+ // This is a no-op on Windows.
+ return true;
+}
+
+
+bool LLPluginSharedMemory::create(size_t size)
+{
+ mName = WIN32_SHARED_MEMORY_PREFIX_STRING;
+ mName += createName();
+ mSize = size;
+
+ mImpl->mMapFile = CreateFileMappingA(
+ INVALID_HANDLE_VALUE, // use paging file
+ NULL, // default security
+ PAGE_READWRITE, // read/write access
+ 0, // max. object size
+ mSize, // buffer size
+ mName.c_str()); // name of mapping object
+
+ if(mImpl->mMapFile == NULL)
+ {
+ LL_WARNS("Plugin") << "CreateFileMapping failed: " << GetLastError() << LL_ENDL;
+ return false;
+ }
+
+ mNeedsDestroy = true;
+
+ return map();
+}
+
+bool LLPluginSharedMemory::destroy(void)
+{
+ unmap();
+ close();
+ return true;
+}
+
+bool LLPluginSharedMemory::attach(const std::string &name, size_t size)
+{
+ mName = name;
+ mSize = size;
+
+ mImpl->mMapFile = OpenFileMappingA(
+ FILE_MAP_ALL_ACCESS, // read/write access
+ false, // do not inherit the name
+ mName.c_str()); // name of mapping object
+
+ if(mImpl->mMapFile == NULL)
+ {
+ LL_WARNS("Plugin") << "OpenFileMapping failed: " << GetLastError() << LL_ENDL;
+ return false;
+ }
+
+ return map();
+}
+
+bool LLPluginSharedMemory::detach(void)
+{
+ unmap();
+ close();
+ return true;
+}
+
+
+
+#endif
|