1
# Copyright (C) 2009 Canonical Ltd
3
# This program is free software; you can redistribute it and/or modify
4
# it under the terms of the GNU General Public License as published by
5
# the Free Software Foundation; either version 2 of the License, or
6
# (at your option) any later version.
8
# This program is distributed in the hope that it will be useful,
9
# but WITHOUT ANY WARRANTY; without even the implied warranty of
10
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11
# GNU General Public License for more details.
13
# You should have received a copy of the GNU General Public License
14
# along with this program; if not, write to the Free Software
15
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
17
"""Tests for OS Locks."""
29
def load_tests(standard_tests, module, loader):
30
"""Parameterize tests for all versions of groupcompress."""
32
for name, write_lock, read_lock in lock._lock_classes:
33
scenarios.append((name, {'write_lock': write_lock,
34
'read_lock': read_lock}))
35
suite = loader.suiteClass()
36
result = tests.multiply_tests(standard_tests, scenarios, suite)
40
class TestOSLock(tests.TestCaseInTempDir):
47
super(TestOSLock, self).setUp()
48
self.build_tree(['a-lock-file'])
50
def test_create_read_lock(self):
51
r_lock = self.read_lock('a-lock-file')
54
def test_create_write_lock(self):
55
w_lock = self.write_lock('a-lock-file')
58
def test_read_locks_share(self):
59
r_lock = self.read_lock('a-lock-file')
61
lock2 = self.read_lock('a-lock-file')
66
def test_write_locks_are_exclusive(self):
67
w_lock = self.write_lock('a-lock-file')
69
self.assertRaises(errors.LockContention,
70
self.write_lock, 'a-lock-file')
74
def test_read_locks_block_write_locks(self):
75
r_lock = self.read_lock('a-lock-file')
77
if lock.have_fcntl and self.write_lock is lock._fcntl_WriteLock:
78
# With -Dlock, fcntl locks are properly exclusive
79
debug.debug_flags.add('strict_locks')
80
self.assertRaises(errors.LockContention,
81
self.write_lock, 'a-lock-file')
83
debug.debug_flags.remove('strict_locks')
85
w_lock = self.write_lock('a-lock-file')
86
except errors.LockContention:
87
self.fail('Unexpected success. fcntl read locks'
88
' do not usually block write locks')
91
self.knownFailure('fcntl read locks don\'t'
92
' block write locks without -Dlock')
94
self.assertRaises(errors.LockContention,
95
self.write_lock, 'a-lock-file')
99
def test_write_locks_block_read_lock(self):
100
w_lock = self.write_lock('a-lock-file')
102
if lock.have_fcntl and self.read_lock is lock._fcntl_ReadLock:
103
# With -Dlock, fcntl locks are properly exclusive
104
debug.debug_flags.add('strict_locks')
105
self.assertRaises(errors.LockContention,
106
self.read_lock, 'a-lock-file')
108
debug.debug_flags.remove('strict_locks')
110
r_lock = self.read_lock('a-lock-file')
111
except errors.LockContention:
112
self.fail('Unexpected success. fcntl write locks'
113
' do not usually block read locks')
116
self.knownFailure('fcntl write locks don\'t'
117
' block read locks without -Dlock')
119
self.assertRaises(errors.LockContention,
120
self.read_lock, 'a-lock-file')
125
def test_temporary_write_lock(self):
126
r_lock = self.read_lock('a-lock-file')
128
status, w_lock = r_lock.temporary_write_lock()
129
self.assertTrue(status)
130
# This should block another write lock
132
self.assertRaises(errors.LockContention,
133
self.write_lock, 'a-lock-file')
135
r_lock = w_lock.restore_read_lock()
136
# We should be able to take a read lock now
137
r_lock2 = self.read_lock('a-lock-file')
142
def test_temporary_write_lock_fails(self):
143
r_lock = self.read_lock('a-lock-file')
145
r_lock2 = self.read_lock('a-lock-file')
147
status, w_lock = r_lock.temporary_write_lock()
148
self.assertFalse(status)
149
# Taking out the lock requires unlocking and locking again, so
150
# we have to replace the original object
154
# We should be able to take a read lock now
155
r_lock2 = self.read_lock('a-lock-file')