1 /* 2 * This file is part of gtkD. 3 * 4 * gtkD is free software; you can redistribute it and/or modify 5 * it under the terms of the GNU Lesser General Public License 6 * as published by the Free Software Foundation; either version 3 7 * of the License, or (at your option) any later version, with 8 * some exceptions, please read the COPYING file. 9 * 10 * gtkD is distributed in the hope that it will be useful, 11 * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 * GNU Lesser General Public License for more details. 14 * 15 * You should have received a copy of the GNU Lesser General Public License 16 * along with gtkD; if not, write to the Free Software 17 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110, USA 18 */ 19 20 // generated automatically - do not change 21 // find conversion definition on APILookup.txt 22 // implement new conversion functionalities on the wrap.utils pakage 23 24 /* 25 * Conversion parameters: 26 * inFile = 27 * outPack = gthread 28 * outFile = RWLock 29 * strct = GStaticRWLock 30 * realStrct= 31 * ctorStrct= 32 * clss = RWLock 33 * interf = 34 * class Code: Yes 35 * interface Code: No 36 * template for: 37 * extend = 38 * implements: 39 * prefixes: 40 * - g_static_rw_lock_ 41 * omit structs: 42 * omit prefixes: 43 * omit code: 44 * omit signals: 45 * imports: 46 * structWrap: 47 * module aliases: 48 * local aliases: 49 * overrides: 50 */ 51 52 module gthread.RWLock; 53 54 public import gtkc.gthreadtypes; 55 56 private import gtkc.gthread; 57 private import glib.ConstructionException; 58 59 60 61 62 63 64 /** 65 * Description 66 * Threads act almost like processes, but unlike processes all threads 67 * of one process share the same memory. This is good, as it provides 68 * easy communication between the involved threads via this shared 69 * memory, and it is bad, because strange things (so called 70 * "Heisenbugs") might happen if the program is not carefully designed. 71 * In particular, due to the concurrent nature of threads, no 72 * assumptions on the order of execution of code running in different 73 * threads can be made, unless order is explicitly forced by the 74 * programmer through synchronization primitives. 75 * The aim of the thread related functions in GLib is to provide a 76 * portable means for writing multi-threaded software. There are 77 * primitives for mutexes to protect the access to portions of memory 78 * (GMutex, GStaticMutex, G_LOCK_DEFINE, GStaticRecMutex and 79 * GStaticRWLock). There are primitives for condition variables to 80 * allow synchronization of threads (GCond). There are primitives for 81 * thread-private data - data that every thread has a private instance 82 * of (GPrivate, GStaticPrivate). Last but definitely not least there 83 * are primitives to portably create and manage threads (GThread). 84 * The threading system is initialized with g_thread_init(), which 85 * takes an optional custom thread implementation or NULL for the 86 * default implementation. If you want to call g_thread_init() with a 87 * non-NULL argument this must be done before executing any other GLib 88 * functions (except g_mem_set_vtable()). This is a requirement even if 89 * no threads are in fact ever created by the process. 90 * Calling g_thread_init() with a NULL argument is somewhat more 91 * relaxed. You may call any other glib functions in the main thread 92 * before g_thread_init() as long as g_thread_init() is not called from 93 * a glib callback, or with any locks held. However, many libraries 94 * above glib does not support late initialization of threads, so doing 95 * this should be avoided if possible. 96 * Please note that since version 2.24 the GObject initialization 97 * function g_type_init() initializes threads (with a NULL argument), 98 * so most applications, including those using Gtk+ will run with 99 * threads enabled. If you want a special thread implementation, make 100 * sure you call g_thread_init() before g_type_init() is called. 101 * After calling g_thread_init(), GLib is completely thread safe (all 102 * global data is automatically locked), but individual data structure 103 * instances are not automatically locked for performance reasons. So, 104 * for example you must coordinate accesses to the same GHashTable 105 * from multiple threads. The two notable exceptions from this rule 106 * are GMainLoop and GAsyncQueue, which are 107 * threadsafe and need no further application-level locking to be 108 * accessed from multiple threads. 109 * To help debugging problems in multithreaded applications, GLib 110 * supports error-checking mutexes that will give you helpful error 111 * messages on common problems. To use error-checking mutexes, define 112 * the symbol G_ERRORCHECK_MUTEXES when compiling the application. 113 */ 114 public class RWLock 115 { 116 117 /** the main Gtk struct */ 118 protected GStaticRWLock* gStaticRWLock; 119 120 121 public GStaticRWLock* getRWLockStruct() 122 { 123 return gStaticRWLock; 124 } 125 126 127 /** the main Gtk struct as a void* */ 128 protected void* getStruct() 129 { 130 return cast(void*)gStaticRWLock; 131 } 132 133 /** 134 * Sets our main struct and passes it to the parent class 135 */ 136 public this (GStaticRWLock* gStaticRWLock) 137 { 138 this.gStaticRWLock = gStaticRWLock; 139 } 140 141 /** 142 * Creates a new initialized RWLock. 143 */ 144 public this () 145 { 146 this(new GStaticRWLock); 147 148 init(); 149 } 150 151 /** 152 */ 153 154 /** 155 * A GStaticRWLock must be initialized with this function before it 156 * can be used. Alternatively you can initialize it with 157 * G_STATIC_RW_LOCK_INIT. 158 */ 159 public void init() 160 { 161 // void g_static_rw_lock_init (GStaticRWLock *lock); 162 g_static_rw_lock_init(gStaticRWLock); 163 } 164 165 /** 166 * Locks lock for reading. There may be unlimited concurrent locks for 167 * reading of a GStaticRWLock at the same time. If lock is already 168 * locked for writing by another thread or if another thread is already 169 * waiting to lock lock for writing, this function will block until 170 * lock is unlocked by the other writing thread and no other writing 171 * threads want to lock lock. This lock has to be unlocked by 172 * g_static_rw_lock_reader_unlock(). 173 * GStaticRWLock is not recursive. It might seem to be possible to 174 * recursively lock for reading, but that can result in a deadlock, due 175 * to writer preference. 176 */ 177 public void readerLock() 178 { 179 // void g_static_rw_lock_reader_lock (GStaticRWLock *lock); 180 g_static_rw_lock_reader_lock(gStaticRWLock); 181 } 182 183 /** 184 * Tries to lock lock for reading. If lock is already locked for 185 * writing by another thread or if another thread is already waiting to 186 * lock lock for writing, immediately returns FALSE. Otherwise locks 187 * lock for reading and returns TRUE. This lock has to be unlocked by 188 * g_static_rw_lock_reader_unlock(). 189 * Params: 190 * lock = a GStaticRWLock to lock for reading. 191 * Returns: TRUE, if lock could be locked for reading. 192 */ 193 public int readerTrylock() 194 { 195 // gboolean g_static_rw_lock_reader_trylock (GStaticRWLock *lock); 196 return g_static_rw_lock_reader_trylock(gStaticRWLock); 197 } 198 199 /** 200 * Unlocks lock. If a thread waits to lock lock for writing and all 201 * locks for reading have been unlocked, the waiting thread is woken up 202 * and can lock lock for writing. 203 * Params: 204 * lock = a GStaticRWLock to unlock after reading. 205 */ 206 public void readerUnlock() 207 { 208 // void g_static_rw_lock_reader_unlock (GStaticRWLock *lock); 209 g_static_rw_lock_reader_unlock(gStaticRWLock); 210 } 211 212 /** 213 * Locks lock for writing. If lock is already locked for writing or 214 * reading by other threads, this function will block until lock is 215 * completely unlocked and then lock lock for writing. While this 216 * functions waits to lock lock, no other thread can lock lock for 217 * reading. When lock is locked for writing, no other thread can lock 218 * lock (neither for reading nor writing). This lock has to be 219 * unlocked by g_static_rw_lock_writer_unlock(). 220 */ 221 public void writerLock() 222 { 223 // void g_static_rw_lock_writer_lock (GStaticRWLock *lock); 224 g_static_rw_lock_writer_lock(gStaticRWLock); 225 } 226 227 /** 228 * Tries to lock lock for writing. If lock is already locked (for 229 * either reading or writing) by another thread, it immediately returns 230 * FALSE. Otherwise it locks lock for writing and returns TRUE. This 231 * lock has to be unlocked by g_static_rw_lock_writer_unlock(). 232 * Params: 233 * lock = a GStaticRWLock to lock for writing. 234 * Returns: TRUE, if lock could be locked for writing. 235 */ 236 public int writerTrylock() 237 { 238 // gboolean g_static_rw_lock_writer_trylock (GStaticRWLock *lock); 239 return g_static_rw_lock_writer_trylock(gStaticRWLock); 240 } 241 242 /** 243 * Unlocks lock. If a thread is waiting to lock lock for writing and 244 * all locks for reading have been unlocked, the waiting thread is 245 * woken up and can lock lock for writing. If no thread is waiting to 246 * lock lock for writing, and some thread or threads are waiting to 247 * lock lock for reading, the waiting threads are woken up and can 248 * lock lock for reading. 249 * Params: 250 * lock = a GStaticRWLock to unlock after writing. 251 */ 252 public void writerUnlock() 253 { 254 // void g_static_rw_lock_writer_unlock (GStaticRWLock *lock); 255 g_static_rw_lock_writer_unlock(gStaticRWLock); 256 } 257 258 /** 259 * Releases all resources allocated to lock. 260 * You don't have to call this functions for a GStaticRWLock with an 261 * unbounded lifetime, i.e. objects declared 'static', but if you have 262 * a GStaticRWLock as a member of a structure, and the structure is 263 * freed, you should also free the GStaticRWLock. 264 */ 265 public void free() 266 { 267 // void g_static_rw_lock_free (GStaticRWLock *lock); 268 g_static_rw_lock_free(gStaticRWLock); 269 } 270 }