~bzr-pqm/bzr/bzr.dev

« back to all changes in this revision

Viewing changes to bzrlib/lockable_files.py

  • Committer: Michael Hudson
  • Date: 2009-03-11 21:44:21 UTC
  • mto: This revision was merged to the branch mainline in revision 4121.
  • Revision ID: michael.hudson@canonical.com-20090311214421-t0n9w8akm4k50ar6
review comments

Show diffs side-by-side

added added

removed removed

Lines of Context:
43
43
# somewhat redundant with what's done in LockDir; the main difference is that
44
44
# LockableFiles permits reentrancy.
45
45
 
46
 
class _LockCounter(object):
47
 
    """Hold a counter for a lock and warn if it's GCed while >= 1.
 
46
class _LockWarner(object):
 
47
    """Hold a counter for a lock and warn if GCed while the count is >= 1.
48
48
 
49
49
    This is separate from LockableFiles because putting a __del__ on
50
50
    LockableFiles can result in uncollectable cycles.
56
56
 
57
57
    def __del__(self):
58
58
        if self.lock_count >= 1:
59
 
            # do not automatically unlock; there should have been a
60
 
            # try/finally to unlock this.
 
59
            # There should have been a try/finally to unlock this.
61
60
            warnings.warn("%r was gc'd while locked" % self.repr)
62
61
 
63
62
 
106
105
        self.lock_name = lock_name
107
106
        self._transaction = None
108
107
        self._lock_mode = None
109
 
        self._lock_counter = _LockCounter(repr(self))
 
108
        self._lock_warner = _LockWarner(repr(self))
110
109
        self._find_modes()
111
110
        esc_name = self._escape(lock_name)
112
111
        self._lock = lock_class(transport, esc_name,
265
264
            if self._lock_mode != 'w' or not self.get_transaction().writeable():
266
265
                raise errors.ReadOnlyError(self)
267
266
            self._lock.validate_token(token)
268
 
            self._lock_counter.lock_count += 1
 
267
            self._lock_warner.lock_count += 1
269
268
            return self._token_from_lock
270
269
        else:
271
270
            token_from_lock = self._lock.lock_write(token=token)
272
271
            #traceback.print_stack()
273
272
            self._lock_mode = 'w'
274
 
            self._lock_counter.lock_count = 1
 
273
            self._lock_warner.lock_count = 1
275
274
            self._set_transaction(transactions.WriteTransaction())
276
275
            self._token_from_lock = token_from_lock
277
276
            return token_from_lock
280
279
        if self._lock_mode:
281
280
            if self._lock_mode not in ('r', 'w'):
282
281
                raise ValueError("invalid lock mode %r" % (self._lock_mode,))
283
 
            self._lock_counter.lock_count += 1
 
282
            self._lock_warner.lock_count += 1
284
283
        else:
285
284
            self._lock.lock_read()
286
285
            #traceback.print_stack()
287
286
            self._lock_mode = 'r'
288
 
            self._lock_counter.lock_count = 1
 
287
            self._lock_warner.lock_count = 1
289
288
            self._set_transaction(transactions.ReadOnlyTransaction())
290
289
            # 5K may be excessive, but hey, its a knob.
291
290
            self.get_transaction().set_cache_size(5000)
293
292
    def unlock(self):
294
293
        if not self._lock_mode:
295
294
            raise errors.LockNotHeld(self)
296
 
        if self._lock_counter.lock_count > 1:
297
 
            self._lock_counter.lock_count -= 1
 
295
        if self._lock_warner.lock_count > 1:
 
296
            self._lock_warner.lock_count -= 1
298
297
        else:
299
298
            #traceback.print_stack()
300
299
            self._finish_transaction()
301
300
            try:
302
301
                self._lock.unlock()
303
302
            finally:
304
 
                self._lock_mode = self._lock_counter.lock_count = None
 
303
                self._lock_mode = self._lock_warner.lock_count = None
305
304
 
306
305
    @property
307
306
    def _lock_count(self):
308
 
        return self._lock_counter.lock_count
 
307
        return self._lock_warner.lock_count
309
308
 
310
309
    def is_locked(self):
311
310
        """Return true if this LockableFiles group is locked"""
312
 
        return self._lock_counter.lock_count >= 1
 
311
        return self._lock_warner.lock_count >= 1
313
312
 
314
313
    def get_physical_lock_status(self):
315
314
        """Return physical lock status.