Go to the documentation of this file.00001
00010
00011
00012
00013
00014 #ifndef ECL_IPC_SHARED_MEMORY_RT_HPP_
00015 #define ECL_IPC_SHARED_MEMORY_RT_HPP_
00016
00017
00018
00019
00020
00021 #include <ecl/config.hpp>
00022 #if defined(ECL_IS_POSIX)
00023 #include <unistd.h>
00024 #include <bits/posix_opt.h>
00025 #ifdef _POSIX_SHARED_MEMORY_OBJECTS
00026 #if _POSIX_SHARED_MEMORY_OBJECTS > 0
00027
00028
00029
00030
00031
00032 #ifndef ECL_HAS_POSIX_SHARED_MEMORY
00033 #define ECL_HAS_POSIX_SHARED_MEMORY
00034 #endif
00035 #ifndef ECL_HAS_SHARED_MEMORY
00036 #define ECL_HAS_SHARED_MEMORY
00037 #endif
00038
00039
00040
00041
00042
00043 #include <sstream>
00044 #include <string>
00045 #include <sys/mman.h>
00046 #include <fcntl.h>
00047 #include <ecl/exceptions/macros.hpp>
00048 #include <ecl/exceptions/standard_exception.hpp>
00049 #include <ecl/config/macros.hpp>
00050
00051
00052
00053
00054
00055 namespace ecl {
00056
00057
00058
00059
00060
00061 namespace ipc {
00062
00063 #ifdef ECL_HAS_EXCEPTIONS
00064
00073
00074 ECL_PUBLIC ecl::StandardException openSharedSectionException(const char* loc);
00083 ECL_PUBLIC ecl::StandardException memoryMapException(const char* loc);
00084
00085
00086 #endif
00087
00095 class ECL_PUBLIC SharedMemoryBase {
00096 public:
00102 void unlink();
00103
00104 protected:
00105 SharedMemoryBase(const std::string &name_id) :
00106 name(name_id),
00107 shared_memory_manager(false)
00108 {};
00116 int open();
00117
00118 std::string name;
00119 bool shared_memory_manager;
00120 };
00121
00122 }
00123
00124
00125
00126
00138 template <typename Storage>
00139 class ECL_PUBLIC SharedMemory : public ipc::SharedMemoryBase
00140 {
00141 public:
00142
00143
00144
00145 SharedMemory(const std::string& string_id) ecl_throw_decl(StandardException);
00146 virtual ~SharedMemory();
00147
00148 Storage* data() { return storage; }
00150 private:
00151 SharedMemory() {}
00152 const int shared_memory_size;
00153 Storage *storage;
00154 };
00155
00156
00157
00158
00159
00171 template <typename Storage>
00172 SharedMemory<Storage>::SharedMemory(const std::string& string_id ) ecl_throw_decl(StandardException) :
00173 ipc::SharedMemoryBase(std::string("/")+string_id),
00174 shared_memory_size(sizeof(Storage)),
00175 storage(NULL)
00176 {
00177 int shm_descriptor = open();
00178 if ( shm_descriptor == -1) {
00179 ecl_throw( ipc::openSharedSectionException(LOC) );
00180 }
00181
00182
00183
00184
00185
00186
00187
00188
00189
00190
00191
00192
00193
00194
00195
00196 void * shm_address;
00197 if ( (shm_address = mmap(0,shared_memory_size,PROT_READ|PROT_WRITE,MAP_SHARED,shm_descriptor,(long) 0)) == MAP_FAILED )
00198 {
00199 shared_memory_manager = false;
00200 close(shm_descriptor);
00201 unlink();
00202 ecl_throw( ipc::memoryMapException(LOC) );
00203 }
00204
00205
00206
00207
00208 if ( ftruncate(shm_descriptor,shared_memory_size) < 0 )
00209 {
00210 shared_memory_manager = false;
00211 close(shm_descriptor);
00212 unlink();
00213 ecl_throw(StandardException(LOC,OpenError,"Shared memory created, but inflation to the desired size failed."));
00214 }
00215
00216
00217
00218
00219
00220
00221
00222
00223 close(shm_descriptor);
00224
00225 storage = (Storage*) shm_address;
00226
00227
00228 if ( shared_memory_manager ) {
00229 *storage = Storage();
00230 }
00231 }
00237 template <typename Storage>
00238 SharedMemory<Storage>::~SharedMemory()
00239 {
00240
00241 munmap( (void*) storage,shared_memory_size);
00242
00243
00244 if ( shared_memory_manager ) {
00245 unlink();
00246 }
00247 }
00248
00249 };
00250
00251
00252 #endif
00253 #endif
00254 #endif
00255
00256 #endif