def _checkForOrphans(filename): if logger.isEnabledFor(logging.DEBUG): logger.debug('Checking for orphan locks on ' + filename) readLockDir = filename + readLockAppend writeLockDir = filename + writeLockAppend orphanRemoved = False nowTime = time.time() # check for read lock orphans if os.path.exists(readLockDir): for f in os.listdir(readLockDir): fullpath = readLockDir + '/' + f try: statinfo = os.stat(fullpath) if nowTime - ORPHAN_TIMEOUT > statinfo.st_mtime: logger.warn("Orphan lock " + fullpath + " found and will be removed.") os.remove(fullpath) orphanRemoved = True except OSError, e: if e.errno != 2: # 2 indicates file was removed by other process looking for orphans logger.error("Error removing orphaned lock: " + str(e)) try: if len(os.listdir(readLockDir)) == 0: logger.warn("Orphan lock " + readLockDir + " found and will be removed.") os.rmdir(readLockDir) except OSError, e: if e.errno != 2 and e.errno != 39: # error 2 is no directory exists, implying a different read release # raced and removed it first # error 39 is directory is not empty, implying a different read # added a pid file after we checked the dir's number of files logger.error('Unable to remove orphaned read lock ' + readLockDir + ': ' + str(e))
def getLock(filename, mode): t0 = time.time() dirCheck(filename) gotLock, fpath = _getLockInternal(filename, mode) if gotLock: if logger.isEnabledFor(logging.DEBUG): logger.debug('Got lock on ' + str(filename)) else: if logger.isEnabledFor(logging.DEBUG): logger.debug(str(os.getpid()) + " failed to get lock") t1=time.time() if timeMap.has_key('getLock'): timeMap['getLock']+=t1-t0 else: timeMap['getLock']=t1-t0 return gotLock, fpath
def getLock(filename, mode): t0 = time.time() dirCheck(filename) gotLock = False startTime = time.time() nowTime = time.time() if mode == 'w' or mode == 'a': lockOp = fcntl.LOCK_EX fmode = os.O_RDWR else: lockOp = fcntl.LOCK_SH fmode = os.O_RDONLY fd = os.open(filename, fmode) lockOp = lockOp | fcntl.LOCK_NB if logger.isEnabledFor(logging.DEBUG): logger.debug( str(os.getpid()) + " Attempting to get lock on " + str(fd) + " mode " + mode + " " + filename) while not gotLock and (nowTime - startTime) < MAX_TIME_TO_WAIT: try: fcntl.lockf(fd, lockOp) gotLock = True except: time.sleep(.1) nowTime = time.time() if gotLock: if logger.isEnabledFor(logging.DEBUG): logger.debug('Got lock on ' + str(fd)) else: if logger.isEnabledFor(logging.DEBUG): logger.debug(str(os.getpid()) + " failed to get lock") os.close(fd) t1 = time.time() if timeMap.has_key('getLock'): timeMap['getLock'] += t1 - t0 else: timeMap['getLock'] = t1 - t0 return gotLock, fd
def releaseLock(fd): t0 = time.time() fcntl.lockf(fd, fcntl.LOCK_UN) os.close(fd) if logger.isEnabledFor(logging.DEBUG): logger.debug('Released lock on ' + str(fd)) t1 = time.time() if timeMap.has_key('releaseLock'): timeMap['releaseLock'] += t1 - t0 else: timeMap['releaseLock'] = t1 - t0
def _getLockInternal(filename, mode): gotLock = False lockPath = None startTime = time.time() if logger.isEnabledFor(logging.DEBUG): logger.debug(str(os.getpid()) +" Attempting to get lock on mode " + mode + " " + filename) readLockDir = filename + readLockAppend writeLockDir = filename + writeLockAppend count = 0 timeElapsed = time.time() - startTime while not gotLock and timeElapsed < MAX_TIME_TO_WAIT: count += 1 if count % 100 == 0: # check for orphans every 100 tries _checkForOrphans(filename) if mode == 'r': if os.path.exists(writeLockDir): time.sleep(_getSleepTime(timeElapsed)) timeElapsed = time.time() - startTime else: try: os.mkdir(readLockDir) except OSError, e: # error 17 is dir already exists, which we can ignore if e.errno != 17: raise e try: # Need to check to make sure write lock wasn't created # between last check and our dir creation if os.path.exists(writeLockDir): os.rmdir(readLockDir) continue except OSError, e: continue #Ignore error try: f = open(readLockDir + '/' + str(os.getpid()) + '.pid', 'w') gotLock = True lockPath = f.name except IOError, e: if e.errno != 2: # 2 indicates directory is gone, could have had another # process remove the read dir before the file was created raise e
try: if len(os.listdir(dirpath)) == 0: os.rmdir(dirpath) except OSError, e: if e.errno != 2 and e.errno != 39: # error 2 is no directory exists, implying a different read release # raced and removed it first # error 39 is directory is not empty, implying a different read # added a pid file after we checked the dir's number of files logger.warn('Unable to remove read lock ' + dirpath + ': ' + str(e)) else: # it was a write os.rmdir(lockPath) if logger.isEnabledFor(logging.DEBUG): logger.debug('Released lock on ' + str(lockPath)) t1=time.time() if timeMap.has_key('releaseLock'): timeMap['releaseLock']+=t1-t0 else: timeMap['releaseLock']=t1-t0 def _checkForOrphans(filename): if logger.isEnabledFor(logging.DEBUG): logger.debug('Checking for orphan locks on ' + filename) readLockDir = filename + readLockAppend writeLockDir = filename + writeLockAppend