Jack2 1.9.10
|
00001 /* 00002 Copyright (C) 2004-2008 Grame 00003 00004 This program is free software; you can redistribute it and/or modify 00005 it under the terms of the GNU Lesser General Public License as published by 00006 the Free Software Foundation; either version 2.1 of the License, or 00007 (at your option) any later version. 00008 00009 This program is distributed in the hope that it will be useful, 00010 but WITHOUT ANY WARRANTY; without even the implied warranty of 00011 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00012 GNU Lesser General Public License for more details. 00013 00014 You should have received a copy of the GNU Lesser General Public License 00015 along with this program; if not, write to the Free Software 00016 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. 00017 00018 */ 00019 00020 #ifndef __JackShmMem__ 00021 #define __JackShmMem__ 00022 00023 #include "shm.h" 00024 #include "JackError.h" 00025 #include "JackCompilerDeps.h" 00026 00027 #include <new> // GCC 4.0 00028 #include <errno.h> 00029 #include <stdlib.h> 00030 00031 #include "JackShmMem_os.h" 00032 00033 namespace Jack 00034 { 00035 00036 void LockMemoryImp(void* ptr, size_t size); 00037 void InitLockMemoryImp(void* ptr, size_t size); 00038 void UnlockMemoryImp(void* ptr, size_t size); 00039 void LockAllMemory(); 00040 void UnlockAllMemory(); 00041 00042 class JackMem 00043 { 00044 private: 00045 00046 size_t fSize; 00047 static size_t gSize; 00048 00049 protected: 00050 00051 JackMem(): fSize(gSize) 00052 {} 00053 ~JackMem() 00054 {} 00055 00056 public: 00057 00058 void* operator new(size_t size) 00059 { 00060 gSize = size; 00061 return calloc(1, size); 00062 } 00063 00064 void operator delete(void* ptr, size_t size) 00065 { 00066 free(ptr); 00067 } 00068 00069 void LockMemory() 00070 { 00071 LockMemoryImp(this, fSize); 00072 } 00073 00074 void UnlockMemory() 00075 { 00076 UnlockMemoryImp(this, fSize); 00077 } 00078 00079 }; 00080 00087 class JackShmMemAble 00088 { 00089 protected: 00090 00091 jack_shm_info_t fInfo; 00092 00093 public: 00094 00095 void Init(); 00096 00097 int GetShmIndex() 00098 { 00099 return fInfo.index; 00100 } 00101 00102 char* GetShmAddress() 00103 { 00104 return (char*)fInfo.ptr.attached_at; 00105 } 00106 00107 void LockMemory() 00108 { 00109 LockMemoryImp(this, fInfo.size); 00110 } 00111 00112 void UnlockMemory() 00113 { 00114 UnlockMemoryImp(this, fInfo.size); 00115 } 00116 00117 }; 00118 00125 class SERVER_EXPORT JackShmMem : public JackShmMemAble 00126 { 00127 00128 protected: 00129 00130 JackShmMem(); 00131 ~JackShmMem(); 00132 00133 public: 00134 00135 void* operator new(size_t size); 00136 void* operator new(size_t size, void* memory); 00137 00138 void operator delete(void* p, size_t size); 00139 void operator delete(void* p); 00140 00141 }; 00142 00147 template <class T> 00148 class JackShmReadWritePtr 00149 { 00150 00151 private: 00152 00153 jack_shm_info_t fInfo; 00154 00155 void Init(int index, const char* server_name = JACK_DEFAULT_SERVER_NAME) 00156 { 00157 if (fInfo.index < 0 && index >= 0) { 00158 jack_log("JackShmReadWritePtr::Init %ld %ld", index, fInfo.index); 00159 if (jack_initialize_shm(server_name) < 0) { 00160 throw std::bad_alloc(); 00161 } 00162 fInfo.index = index; 00163 if (jack_attach_lib_shm(&fInfo)) { 00164 throw std::bad_alloc(); 00165 } 00166 GetShmAddress()->LockMemory(); 00167 } 00168 } 00169 00170 public: 00171 00172 JackShmReadWritePtr() 00173 { 00174 fInfo.index = -1; 00175 fInfo.ptr.attached_at = (char*)NULL; 00176 } 00177 00178 JackShmReadWritePtr(int index, const char* server_name) 00179 { 00180 Init(index, server_name); 00181 } 00182 00183 ~JackShmReadWritePtr() 00184 { 00185 if (fInfo.index >= 0) { 00186 jack_log("JackShmReadWritePtr::~JackShmReadWritePtr %ld", fInfo.index); 00187 GetShmAddress()->UnlockMemory(); 00188 jack_release_lib_shm(&fInfo); 00189 fInfo.index = -1; 00190 } 00191 } 00192 00193 T* operator->() const 00194 { 00195 return (T*)fInfo.ptr.attached_at; 00196 } 00197 00198 operator T*() const 00199 { 00200 return (T*)fInfo.ptr.attached_at; 00201 } 00202 00203 JackShmReadWritePtr& operator=(int index) 00204 { 00205 Init(index); 00206 return *this; 00207 } 00208 00209 void SetShmIndex(int index, const char* server_name) 00210 { 00211 Init(index, server_name); 00212 } 00213 00214 int GetShmIndex() 00215 { 00216 return fInfo.index; 00217 } 00218 00219 T* GetShmAddress() 00220 { 00221 return (T*)fInfo.ptr.attached_at; 00222 } 00223 }; 00224 00229 template <class T> 00230 class JackShmReadWritePtr1 00231 { 00232 00233 private: 00234 00235 jack_shm_info_t fInfo; 00236 00237 void Init(int index, const char* server_name = JACK_DEFAULT_SERVER_NAME) 00238 { 00239 if (fInfo.index < 0 && index >= 0) { 00240 jack_log("JackShmReadWritePtr1::Init %ld %ld", index, fInfo.index); 00241 if (jack_initialize_shm(server_name) < 0) { 00242 throw std::bad_alloc(); 00243 } 00244 fInfo.index = index; 00245 if (jack_attach_lib_shm(&fInfo)) { 00246 throw std::bad_alloc(); 00247 } 00248 GetShmAddress()->LockMemory(); 00249 /* 00250 nobody else needs to access this shared memory any more, so 00251 destroy it. because we have our own attachment to it, it won't 00252 vanish till we exit (and release it). 00253 */ 00254 jack_destroy_shm(&fInfo); 00255 } 00256 } 00257 00258 public: 00259 00260 JackShmReadWritePtr1() 00261 { 00262 fInfo.index = -1; 00263 fInfo.ptr.attached_at = NULL; 00264 } 00265 00266 JackShmReadWritePtr1(int index, const char* server_name) 00267 { 00268 Init(index, server_name); 00269 } 00270 00271 ~JackShmReadWritePtr1() 00272 { 00273 if (fInfo.index >= 0) { 00274 jack_log("JackShmReadWritePtr1::~JackShmReadWritePtr1 %ld", fInfo.index); 00275 GetShmAddress()->UnlockMemory(); 00276 jack_release_lib_shm(&fInfo); 00277 fInfo.index = -1; 00278 } 00279 } 00280 00281 T* operator->() const 00282 { 00283 return (T*)fInfo.ptr.attached_at; 00284 } 00285 00286 operator T*() const 00287 { 00288 return (T*)fInfo.ptr.attached_at; 00289 } 00290 00291 JackShmReadWritePtr1& operator=(int index) 00292 { 00293 Init(index); 00294 return *this; 00295 } 00296 00297 void SetShmIndex(int index, const char* server_name) 00298 { 00299 Init(index, server_name); 00300 } 00301 00302 int GetShmIndex() 00303 { 00304 return fInfo.index; 00305 } 00306 00307 T* GetShmAddress() 00308 { 00309 return (T*)fInfo.ptr.attached_at; 00310 } 00311 }; 00312 00317 template <class T> 00318 class JackShmReadPtr 00319 { 00320 00321 private: 00322 00323 jack_shm_info_t fInfo; 00324 00325 void Init(int index, const char* server_name = JACK_DEFAULT_SERVER_NAME) 00326 { 00327 if (fInfo.index < 0 && index >= 0) { 00328 jack_log("JackShmPtrRead::Init %ld %ld", index, fInfo.index); 00329 if (jack_initialize_shm(server_name) < 0) { 00330 throw std::bad_alloc(); 00331 } 00332 fInfo.index = index; 00333 if (jack_attach_lib_shm_read(&fInfo)) { 00334 throw std::bad_alloc(); 00335 } 00336 GetShmAddress()->LockMemory(); 00337 } 00338 } 00339 00340 public: 00341 00342 JackShmReadPtr() 00343 { 00344 fInfo.index = -1; 00345 fInfo.ptr.attached_at = NULL; 00346 } 00347 00348 JackShmReadPtr(int index, const char* server_name) 00349 { 00350 Init(index, server_name); 00351 } 00352 00353 ~JackShmReadPtr() 00354 { 00355 if (fInfo.index >= 0) { 00356 jack_log("JackShmPtrRead::~JackShmPtrRead %ld", fInfo.index); 00357 GetShmAddress()->UnlockMemory(); 00358 jack_release_lib_shm(&fInfo); 00359 fInfo.index = -1; 00360 } 00361 } 00362 00363 T* operator->() const 00364 { 00365 return (T*)fInfo.ptr.attached_at; 00366 } 00367 00368 operator T*() const 00369 { 00370 return (T*)fInfo.ptr.attached_at; 00371 } 00372 00373 JackShmReadPtr& operator=(int index) 00374 { 00375 Init(index); 00376 return *this; 00377 } 00378 00379 void SetShmIndex(int index, const char* server_name) 00380 { 00381 Init(index, server_name); 00382 } 00383 00384 int GetShmIndex() 00385 { 00386 return fInfo.index; 00387 } 00388 00389 T* GetShmAddress() 00390 { 00391 return (T*)fInfo.ptr.attached_at; 00392 } 00393 00394 }; 00395 00396 } // end of namespace 00397 00398 #endif