0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014 #include "hfs_fs.h"
0015
0016
0017
0018
0019
0020
0021
0022
0023
0024
0025
0026
0027
0028
0029 static u32 hfs_find_set_zero_bits(__be32 *bitmap, u32 size, u32 offset, u32 *max)
0030 {
0031 __be32 *curr, *end;
0032 u32 mask, start, len, n;
0033 __be32 val;
0034 int i;
0035
0036 len = *max;
0037 if (!len)
0038 return size;
0039
0040 curr = bitmap + (offset / 32);
0041 end = bitmap + ((size + 31) / 32);
0042
0043
0044 val = *curr;
0045 if (~val) {
0046 n = be32_to_cpu(val);
0047 i = offset % 32;
0048 mask = (1U << 31) >> i;
0049 for (; i < 32; mask >>= 1, i++) {
0050 if (!(n & mask))
0051 goto found;
0052 }
0053 }
0054
0055
0056 while (++curr < end) {
0057 val = *curr;
0058 if (~val) {
0059 n = be32_to_cpu(val);
0060 mask = 1 << 31;
0061 for (i = 0; i < 32; mask >>= 1, i++) {
0062 if (!(n & mask))
0063 goto found;
0064 }
0065 }
0066 }
0067 return size;
0068
0069 found:
0070 start = (curr - bitmap) * 32 + i;
0071 if (start >= size)
0072 return start;
0073
0074 len = min(size - start, len);
0075 while (1) {
0076 n |= mask;
0077 if (++i >= 32)
0078 break;
0079 mask >>= 1;
0080 if (!--len || n & mask)
0081 goto done;
0082 }
0083 if (!--len)
0084 goto done;
0085 *curr++ = cpu_to_be32(n);
0086
0087 while (1) {
0088 n = be32_to_cpu(*curr);
0089 if (len < 32)
0090 break;
0091 if (n) {
0092 len = 32;
0093 break;
0094 }
0095 *curr++ = cpu_to_be32(0xffffffff);
0096 len -= 32;
0097 }
0098
0099 mask = 1U << 31;
0100 for (i = 0; i < len; i++) {
0101 if (n & mask)
0102 break;
0103 n |= mask;
0104 mask >>= 1;
0105 }
0106 done:
0107 *curr = cpu_to_be32(n);
0108 *max = (curr - bitmap) * 32 + i - start;
0109 return start;
0110 }
0111
0112
0113
0114
0115
0116
0117
0118
0119
0120
0121
0122
0123
0124
0125
0126
0127
0128
0129
0130
0131
0132
0133
0134
0135
0136
0137
0138
0139 u32 hfs_vbm_search_free(struct super_block *sb, u32 goal, u32 *num_bits)
0140 {
0141 void *bitmap;
0142 u32 pos;
0143
0144
0145 if (!*num_bits)
0146 return 0;
0147
0148 mutex_lock(&HFS_SB(sb)->bitmap_lock);
0149 bitmap = HFS_SB(sb)->bitmap;
0150
0151 pos = hfs_find_set_zero_bits(bitmap, HFS_SB(sb)->fs_ablocks, goal, num_bits);
0152 if (pos >= HFS_SB(sb)->fs_ablocks) {
0153 if (goal)
0154 pos = hfs_find_set_zero_bits(bitmap, goal, 0, num_bits);
0155 if (pos >= HFS_SB(sb)->fs_ablocks) {
0156 *num_bits = pos = 0;
0157 goto out;
0158 }
0159 }
0160
0161 hfs_dbg(BITMAP, "alloc_bits: %u,%u\n", pos, *num_bits);
0162 HFS_SB(sb)->free_ablocks -= *num_bits;
0163 hfs_bitmap_dirty(sb);
0164 out:
0165 mutex_unlock(&HFS_SB(sb)->bitmap_lock);
0166 return pos;
0167 }
0168
0169
0170
0171
0172
0173
0174
0175
0176
0177
0178
0179
0180
0181
0182
0183
0184
0185
0186
0187
0188
0189
0190
0191
0192
0193 int hfs_clear_vbm_bits(struct super_block *sb, u16 start, u16 count)
0194 {
0195 __be32 *curr;
0196 u32 mask;
0197 int i, len;
0198
0199
0200 if (!count)
0201 return 0;
0202
0203 hfs_dbg(BITMAP, "clear_bits: %u,%u\n", start, count);
0204
0205 if ((start + count) > HFS_SB(sb)->fs_ablocks)
0206 return -2;
0207
0208 mutex_lock(&HFS_SB(sb)->bitmap_lock);
0209
0210 curr = HFS_SB(sb)->bitmap + (start / 32);
0211 len = count;
0212
0213
0214 i = start % 32;
0215 if (i) {
0216 int j = 32 - i;
0217 mask = 0xffffffffU << j;
0218 if (j > count) {
0219 mask |= 0xffffffffU >> (i + count);
0220 *curr &= cpu_to_be32(mask);
0221 goto out;
0222 }
0223 *curr++ &= cpu_to_be32(mask);
0224 count -= j;
0225 }
0226
0227
0228 while (count >= 32) {
0229 *curr++ = 0;
0230 count -= 32;
0231 }
0232
0233 if (count) {
0234 mask = 0xffffffffU >> count;
0235 *curr &= cpu_to_be32(mask);
0236 }
0237 out:
0238 HFS_SB(sb)->free_ablocks += len;
0239 mutex_unlock(&HFS_SB(sb)->bitmap_lock);
0240 hfs_bitmap_dirty(sb);
0241
0242 return 0;
0243 }