aboutsummaryrefslogtreecommitdiffstats
path: root/fs/minix/bitmap.c
diff options
context:
space:
mode:
Diffstat (limited to 'fs/minix/bitmap.c')
-rw-r--r--fs/minix/bitmap.c25
1 files changed, 13 insertions, 12 deletions
diff --git a/fs/minix/bitmap.c b/fs/minix/bitmap.c
index 3aebe322271a..6ac693faae49 100644
--- a/fs/minix/bitmap.c
+++ b/fs/minix/bitmap.c
@@ -12,13 +12,14 @@
12/* bitmap.c contains the code that handles the inode and block bitmaps */ 12/* bitmap.c contains the code that handles the inode and block bitmaps */
13 13
14#include "minix.h" 14#include "minix.h"
15#include <linux/smp_lock.h>
16#include <linux/buffer_head.h> 15#include <linux/buffer_head.h>
17#include <linux/bitops.h> 16#include <linux/bitops.h>
18#include <linux/sched.h> 17#include <linux/sched.h>
19 18
20static const int nibblemap[] = { 4,3,3,2,3,2,2,1,3,2,2,1,2,1,1,0 }; 19static const int nibblemap[] = { 4,3,3,2,3,2,2,1,3,2,2,1,2,1,1,0 };
21 20
21static DEFINE_SPINLOCK(bitmap_lock);
22
22static unsigned long count_free(struct buffer_head *map[], unsigned numblocks, __u32 numbits) 23static unsigned long count_free(struct buffer_head *map[], unsigned numblocks, __u32 numbits)
23{ 24{
24 unsigned i, j, sum = 0; 25 unsigned i, j, sum = 0;
@@ -69,11 +70,11 @@ void minix_free_block(struct inode *inode, unsigned long block)
69 return; 70 return;
70 } 71 }
71 bh = sbi->s_zmap[zone]; 72 bh = sbi->s_zmap[zone];
72 lock_kernel(); 73 spin_lock(&bitmap_lock);
73 if (!minix_test_and_clear_bit(bit, bh->b_data)) 74 if (!minix_test_and_clear_bit(bit, bh->b_data))
74 printk("minix_free_block (%s:%lu): bit already cleared\n", 75 printk("minix_free_block (%s:%lu): bit already cleared\n",
75 sb->s_id, block); 76 sb->s_id, block);
76 unlock_kernel(); 77 spin_unlock(&bitmap_lock);
77 mark_buffer_dirty(bh); 78 mark_buffer_dirty(bh);
78 return; 79 return;
79} 80}
@@ -88,18 +89,18 @@ int minix_new_block(struct inode * inode)
88 struct buffer_head *bh = sbi->s_zmap[i]; 89 struct buffer_head *bh = sbi->s_zmap[i];
89 int j; 90 int j;
90 91
91 lock_kernel(); 92 spin_lock(&bitmap_lock);
92 j = minix_find_first_zero_bit(bh->b_data, bits_per_zone); 93 j = minix_find_first_zero_bit(bh->b_data, bits_per_zone);
93 if (j < bits_per_zone) { 94 if (j < bits_per_zone) {
94 minix_set_bit(j, bh->b_data); 95 minix_set_bit(j, bh->b_data);
95 unlock_kernel(); 96 spin_unlock(&bitmap_lock);
96 mark_buffer_dirty(bh); 97 mark_buffer_dirty(bh);
97 j += i * bits_per_zone + sbi->s_firstdatazone-1; 98 j += i * bits_per_zone + sbi->s_firstdatazone-1;
98 if (j < sbi->s_firstdatazone || j >= sbi->s_nzones) 99 if (j < sbi->s_firstdatazone || j >= sbi->s_nzones)
99 break; 100 break;
100 return j; 101 return j;
101 } 102 }
102 unlock_kernel(); 103 spin_unlock(&bitmap_lock);
103 } 104 }
104 return 0; 105 return 0;
105} 106}
@@ -211,10 +212,10 @@ void minix_free_inode(struct inode * inode)
211 minix_clear_inode(inode); /* clear on-disk copy */ 212 minix_clear_inode(inode); /* clear on-disk copy */
212 213
213 bh = sbi->s_imap[ino]; 214 bh = sbi->s_imap[ino];
214 lock_kernel(); 215 spin_lock(&bitmap_lock);
215 if (!minix_test_and_clear_bit(bit, bh->b_data)) 216 if (!minix_test_and_clear_bit(bit, bh->b_data))
216 printk("minix_free_inode: bit %lu already cleared\n", bit); 217 printk("minix_free_inode: bit %lu already cleared\n", bit);
217 unlock_kernel(); 218 spin_unlock(&bitmap_lock);
218 mark_buffer_dirty(bh); 219 mark_buffer_dirty(bh);
219 out: 220 out:
220 clear_inode(inode); /* clear in-memory copy */ 221 clear_inode(inode); /* clear in-memory copy */
@@ -237,7 +238,7 @@ struct inode * minix_new_inode(const struct inode * dir, int * error)
237 j = bits_per_zone; 238 j = bits_per_zone;
238 bh = NULL; 239 bh = NULL;
239 *error = -ENOSPC; 240 *error = -ENOSPC;
240 lock_kernel(); 241 spin_lock(&bitmap_lock);
241 for (i = 0; i < sbi->s_imap_blocks; i++) { 242 for (i = 0; i < sbi->s_imap_blocks; i++) {
242 bh = sbi->s_imap[i]; 243 bh = sbi->s_imap[i];
243 j = minix_find_first_zero_bit(bh->b_data, bits_per_zone); 244 j = minix_find_first_zero_bit(bh->b_data, bits_per_zone);
@@ -245,17 +246,17 @@ struct inode * minix_new_inode(const struct inode * dir, int * error)
245 break; 246 break;
246 } 247 }
247 if (!bh || j >= bits_per_zone) { 248 if (!bh || j >= bits_per_zone) {
248 unlock_kernel(); 249 spin_unlock(&bitmap_lock);
249 iput(inode); 250 iput(inode);
250 return NULL; 251 return NULL;
251 } 252 }
252 if (minix_test_and_set_bit(j, bh->b_data)) { /* shouldn't happen */ 253 if (minix_test_and_set_bit(j, bh->b_data)) { /* shouldn't happen */
253 unlock_kernel(); 254 spin_unlock(&bitmap_lock);
254 printk("minix_new_inode: bit already set\n"); 255 printk("minix_new_inode: bit already set\n");
255 iput(inode); 256 iput(inode);
256 return NULL; 257 return NULL;
257 } 258 }
258 unlock_kernel(); 259 spin_unlock(&bitmap_lock);
259 mark_buffer_dirty(bh); 260 mark_buffer_dirty(bh);
260 j += i * bits_per_zone; 261 j += i * bits_per_zone;
261 if (!j || j > sbi->s_ninodes) { 262 if (!j || j > sbi->s_ninodes) {