1
|
1
|
<?php
|
|
2
|
+/***************************************************************************
|
|
3
|
+ * This gives a method of mutual exclusion for critical Sections within
|
|
4
|
+ * your script. A lock-file will be created for every critical section that
|
|
5
|
+ * must be secured. The file hold information about the lock and is a
|
|
6
|
+ * handle (name) for the lock, so that every script uses the same lock.
|
|
7
|
+ * The lock will be achieved by one of two ways.
|
|
8
|
+ *
|
|
9
|
+ * 1. by using semaphores if they are available within the current php
|
|
10
|
+ * installation.
|
|
11
|
+ * 2. else by using flock, which exists within every php installation.
|
|
12
|
+ *
|
|
13
|
+ * Semaphores are used in favour because flock did not work reliably in
|
|
14
|
+ * threaded environments. That means, if we have no semaphores and are
|
|
15
|
+ * in a threaded environment these functions are also not reliable.
|
|
16
|
+ * In doubt ask your administrator or provider.
|
|
17
|
+ *
|
|
18
|
+ * Author: Georg Steffers <georg@steffers.org
|
|
19
|
+ * Date: 14th Oct. 2007
|
|
20
|
+ ***************************************************************************/
|
2
|
21
|
|
3
|
22
|
require_once dirname(__FILE__) . '/../config.php';
|
4
|
23
|
require_once LIBDIR . 'errException.php';
|
5
|
24
|
|
6
|
|
-
|
7
|
|
-function acquireLock ($lockFile, $csId)
|
|
25
|
+/**
|
|
26
|
+ * Try to acquire a lock to enter a critical section. If the lock is already
|
|
27
|
+ * acquired the function blocks until the lock id freed again. If more than
|
|
28
|
+ * one process waits for the lock, than it is undefined which process get
|
|
29
|
+ * the lock next. This depends on which process gets CPU time first. All other
|
|
30
|
+ * processes continue waiting.
|
|
31
|
+ *
|
|
32
|
+ * Sideeffects:
|
|
33
|
+ * If this function succeeds ignore_user_abort is set to TRUE so that the
|
|
34
|
+ * critical section might not be interruped by a user abort. This can
|
|
35
|
+ * but shouldn't be changed within the critical section and will be reset
|
|
36
|
+ * in releaseLock.
|
|
37
|
+ *
|
|
38
|
+ * Arguments:
|
|
39
|
+ * $lockFile <string>: Path and basename to the lockfile to use.
|
|
40
|
+ * $csId <string[1]>: Id of the critical section, will be part of filename.
|
|
41
|
+ * $msg <string>: The message to be written to the lockfile.
|
|
42
|
+ *
|
|
43
|
+ * If $msg is NULL, a default message is created from session_id and time
|
|
44
|
+ *
|
|
45
|
+ * Returns:
|
|
46
|
+ * Array of lock information.
|
|
47
|
+ * [0] Filehandle to opened lockfile.
|
|
48
|
+ * [1] Resource id for semaphor
|
|
49
|
+ * [2] the old setting of ignore_user_abort.
|
|
50
|
+ */
|
|
51
|
+function acquireLock ($lockFile, $csId, $msg = NULL)
|
8
|
52
|
{
|
9
|
53
|
$fName = $lockFile . $csId . '.lck';
|
10
|
54
|
$lock = NULL;
|
...
|
...
|
@@ -31,7 +75,9 @@ function acquireLock ($lockFile, $csId) |
31
|
75
|
}
|
32
|
76
|
|
33
|
77
|
// Here one could write informations in the lockfile...time, pid, etc.
|
34
|
|
- fwrite ($lockHandle, session_id () . '::' . time ());
|
|
78
|
+ if ($msg === NULL)
|
|
79
|
+ $msg = session_id () . '::' . time ();
|
|
80
|
+ fwrite ($lockHandle, $msg . "\n");
|
35
|
81
|
fflush ($lockHandle);
|
36
|
82
|
|
37
|
83
|
resetErrExceptionMapping ();
|
...
|
...
|
@@ -40,6 +86,15 @@ function acquireLock ($lockFile, $csId) |
40
|
86
|
return array ($lockHandle, $lock, $userAbort);
|
41
|
87
|
}
|
42
|
88
|
|
|
89
|
+/**
|
|
90
|
+ * Release a lock previously acquired by acquireLock.
|
|
91
|
+ *
|
|
92
|
+ * Sideeffects:
|
|
93
|
+ * Sets ignore_user_abort to the value before acquireLock succeds.
|
|
94
|
+ *
|
|
95
|
+ * Arguments:
|
|
96
|
+ * $lock <array[3]>: The array returned by a successfull acquireLock call.
|
|
97
|
+ */
|
43
|
98
|
function releaseLock ($lock)
|
44
|
99
|
{
|
45
|
100
|
setErrExceptionMapping ();
|
...
|
...
|
|