note 64150 deleted from function.flock by danbrown

From: Date: Mon, 18 May 2009 00:38:34 +0000
Subject: note 64150 deleted from function.flock by danbrown
References: 1  Groups: php.notes 
Request: Send a blank email to php-notes+get-155399@lists.php.net to get a copy of this message
Note Submitter: wildcat at brightNOSPAMpages dot net ---- I wrote the following function to make a script wait in a queue of instances accessing the same shared resource and then lock it, as a part of a lock-access-release advisory mechanism based on locking directories. It works on my web site (also passes the loop test proposed by dranger below). Might show unpredicted behaviors on other systems, under conditions I didn't think at or produce, expecially when mkdir atomicity is not guaranteed. The whole script is too long for posting, but everyone interested in looking for eventual bugs, testing, torturing and using it, can download code and documentation from http://brightpages.net/doc > QLCK. Hope it is useful. <?php function qLock($lockSuffix, $tmpDir, $maxWait, $padLength) { if ($tmpDir == '' or !is_dir($tmpDir)) $tmpDir = '.'; $maxWait = (int) $maxWait; if ($maxWait <= 0) $maxWait = 60; $padLength = (int) $padLength; if ($padLength <= 0) $padLength = 6; if ($lockSuffix == '') { return false; } else { $currentdir = getcwd(); chdir($tmpDir); // relative to the current directory $n = 0; $lockdirs = glob('*-*.'.$lockSuffix, GLOB_ONLYDIR) or array(); foreach($lockdirs as $lockdir) { list($m, ) = explode('-', $lockdir); $m = intval($m); if ($m > $n) $n = $m + 1; } $npad = str_pad((string) $n, $padLength, '0', STR_PAD_LEFT); while (glob($npad.'-*.'.$lockSuffix, GLOB_ONLYDIR)) { $n++; $npad = str_pad((string) $n, $padLength, '0', STR_PAD_LEFT); } $lockname = $npad.'-'.md5(uniqid(rand(), true)).'.'.$lockSuffix; if (@mkdir($lockname)) { $nlockdirs = glob($npad.'-*.'.$lockSuffix, GLOB_ONLYDIR) or array(); if (count($nlockdirs) != 1) { @rmdir($lockname); return false; } else { $prelockdirs = array(); $lockdirs = glob('*-*.'.$lockSuffix, GLOB_ONLYDIR) or array(); foreach($lockdirs as $lockdir) { list($m, ) = explode('-', $lockdir); $m = intval($m); if ($m < $n) $prelockdirs[] = $lockdir; } $t0 = time(); $t = 0; while (count($prelockdirs) != 0 and $t < $maxWait) { $prelockdirs = array(); $lockdirs = glob('*-*.'.$lockSuffix, GLOB_ONLYDIR) or array(); foreach($lockdirs as $lockdir) { list($m, ) = explode('-', $lockdir); $m = intval($m); if ($m < $n) $prelockdirs[] = $lockdir; } $t = time() - $t0; } if (count($prelockdirs) != 0) { @rmdir($lockname); return false; } else { return $lockname; } } } else { @rmdir($lockname); return false; } chdir($currentdir); } } ?>

« previous php.notes (#155399) next »