blob: bab9cfab34c7329235b65b671c9245e4ff315484 [file] [log] [blame]
David Teiglandb3b94fa2006-01-16 16:50:04 +00001/*
2 * Copyright (C) Sistina Software, Inc. 1997-2003 All rights reserved.
Bob Petersonfe6c9912008-01-28 11:13:02 -06003 * Copyright (C) 2004-2008 Red Hat, Inc. All rights reserved.
David Teiglandb3b94fa2006-01-16 16:50:04 +00004 *
5 * This copyrighted material is made available to anyone wishing to use,
6 * modify, copy, or redistribute it subject to the terms and conditions
Steven Whitehousee9fc2aa2006-09-01 11:05:15 -04007 * of the GNU General Public License version 2.
David Teiglandb3b94fa2006-01-16 16:50:04 +00008 */
9
David Teiglandb3b94fa2006-01-16 16:50:04 +000010#include <linux/slab.h>
11#include <linux/spinlock.h>
12#include <linux/completion.h>
13#include <linux/buffer_head.h>
Steven Whitehousef42faf42006-01-30 18:34:10 +000014#include <linux/fs.h>
Steven Whitehouse5c676f62006-02-27 17:23:27 -050015#include <linux/gfs2_ondisk.h>
Fabio Massimo Di Nitto7d308592006-09-19 07:56:29 +020016#include <linux/lm_interface.h>
Bob Peterson1f466a42008-03-10 18:17:47 -050017#include <linux/prefetch.h>
David Teiglandb3b94fa2006-01-16 16:50:04 +000018
19#include "gfs2.h"
Steven Whitehouse5c676f62006-02-27 17:23:27 -050020#include "incore.h"
David Teiglandb3b94fa2006-01-16 16:50:04 +000021#include "glock.h"
22#include "glops.h"
David Teiglandb3b94fa2006-01-16 16:50:04 +000023#include "lops.h"
24#include "meta_io.h"
25#include "quota.h"
26#include "rgrp.h"
27#include "super.h"
28#include "trans.h"
Steven Whitehouse5c676f62006-02-27 17:23:27 -050029#include "util.h"
Benjamin Marzinski172e0452007-03-23 14:51:56 -060030#include "log.h"
Steven Whitehousec8cdf472007-06-08 10:05:33 +010031#include "inode.h"
Steven Whitehouse51ff87b2007-10-15 14:42:35 +010032#include "ops_address.h"
David Teiglandb3b94fa2006-01-16 16:50:04 +000033
Steven Whitehouse2c1e52a2006-09-05 15:41:57 -040034#define BFITNOENT ((u32)~0)
Bob Peterson6760bdc2007-07-24 14:09:32 -050035#define NO_BLOCK ((u64)~0)
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -040036
Bob Peterson1f466a42008-03-10 18:17:47 -050037#if BITS_PER_LONG == 32
38#define LBITMASK (0x55555555UL)
39#define LBITSKIP55 (0x55555555UL)
40#define LBITSKIP00 (0x00000000UL)
41#else
42#define LBITMASK (0x5555555555555555UL)
43#define LBITSKIP55 (0x5555555555555555UL)
44#define LBITSKIP00 (0x0000000000000000UL)
45#endif
46
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -040047/*
48 * These routines are used by the resource group routines (rgrp.c)
49 * to keep track of block allocation. Each block is represented by two
Steven Whitehousefeaa7bb2006-06-14 15:32:57 -040050 * bits. So, each byte represents GFS2_NBBY (i.e. 4) blocks.
51 *
52 * 0 = Free
53 * 1 = Used (not metadata)
54 * 2 = Unlinked (still in use) inode
55 * 3 = Used (metadata)
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -040056 */
57
58static const char valid_change[16] = {
59 /* current */
Steven Whitehousefeaa7bb2006-06-14 15:32:57 -040060 /* n */ 0, 1, 1, 1,
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -040061 /* e */ 1, 0, 0, 0,
Steven Whitehousefeaa7bb2006-06-14 15:32:57 -040062 /* w */ 0, 0, 0, 1,
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -040063 1, 0, 0, 0
64};
65
Steven Whitehousec8cdf472007-06-08 10:05:33 +010066static u32 rgblk_search(struct gfs2_rgrpd *rgd, u32 goal,
Steven Whitehouseb45e41d2008-02-06 10:11:15 +000067 unsigned char old_state, unsigned char new_state,
68 unsigned int *n);
Steven Whitehousec8cdf472007-06-08 10:05:33 +010069
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -040070/**
71 * gfs2_setbit - Set a bit in the bitmaps
72 * @buffer: the buffer that holds the bitmaps
73 * @buflen: the length (in bytes) of the buffer
74 * @block: the block to set
75 * @new_state: the new state of the block
76 *
77 */
78
Steven Whitehouseb45e41d2008-02-06 10:11:15 +000079static inline void gfs2_setbit(struct gfs2_rgrpd *rgd, unsigned char *buf1,
80 unsigned char *buf2, unsigned int offset,
81 unsigned int buflen, u32 block,
82 unsigned char new_state)
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -040083{
Steven Whitehouseb45e41d2008-02-06 10:11:15 +000084 unsigned char *byte1, *byte2, *end, cur_state;
85 const unsigned int bit = (block % GFS2_NBBY) * GFS2_BIT_SIZE;
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -040086
Steven Whitehouseb45e41d2008-02-06 10:11:15 +000087 byte1 = buf1 + offset + (block / GFS2_NBBY);
88 end = buf1 + offset + buflen;
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -040089
Steven Whitehouseb45e41d2008-02-06 10:11:15 +000090 BUG_ON(byte1 >= end);
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -040091
Steven Whitehouseb45e41d2008-02-06 10:11:15 +000092 cur_state = (*byte1 >> bit) & GFS2_BIT_MASK;
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -040093
Steven Whitehouseb45e41d2008-02-06 10:11:15 +000094 if (unlikely(!valid_change[new_state * 4 + cur_state])) {
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -040095 gfs2_consist_rgrpd(rgd);
Steven Whitehouseb45e41d2008-02-06 10:11:15 +000096 return;
97 }
98 *byte1 ^= (cur_state ^ new_state) << bit;
99
100 if (buf2) {
101 byte2 = buf2 + offset + (block / GFS2_NBBY);
102 cur_state = (*byte2 >> bit) & GFS2_BIT_MASK;
103 *byte2 ^= (cur_state ^ new_state) << bit;
104 }
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -0400105}
106
107/**
108 * gfs2_testbit - test a bit in the bitmaps
109 * @buffer: the buffer that holds the bitmaps
110 * @buflen: the length (in bytes) of the buffer
111 * @block: the block to read
112 *
113 */
114
Steven Whitehouseb45e41d2008-02-06 10:11:15 +0000115static inline unsigned char gfs2_testbit(struct gfs2_rgrpd *rgd,
116 const unsigned char *buffer,
117 unsigned int buflen, u32 block)
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -0400118{
Steven Whitehouseb45e41d2008-02-06 10:11:15 +0000119 const unsigned char *byte, *end;
120 unsigned char cur_state;
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -0400121 unsigned int bit;
122
123 byte = buffer + (block / GFS2_NBBY);
124 bit = (block % GFS2_NBBY) * GFS2_BIT_SIZE;
125 end = buffer + buflen;
126
127 gfs2_assert(rgd->rd_sbd, byte < end);
128
129 cur_state = (*byte >> bit) & GFS2_BIT_MASK;
130
131 return cur_state;
132}
133
134/**
135 * gfs2_bitfit - Search an rgrp's bitmap buffer to find a bit-pair representing
136 * a block in a given allocation state.
137 * @buffer: the buffer that holds the bitmaps
138 * @buflen: the length (in bytes) of the buffer
139 * @goal: start search at this block's bit-pair (within @buffer)
Bob Peterson6760bdc2007-07-24 14:09:32 -0500140 * @old_state: GFS2_BLKST_XXX the state of the block we're looking for.
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -0400141 *
142 * Scope of @goal and returned block number is only within this bitmap buffer,
143 * not entire rgrp or filesystem. @buffer will be offset from the actual
144 * beginning of a bitmap block buffer, skipping any header structures.
145 *
146 * Return: the block number (bitmap buffer scope) that was found
147 */
148
Steven Whitehouse110acf32008-01-29 13:30:20 +0000149static u32 gfs2_bitfit(const u8 *buffer, unsigned int buflen, u32 goal,
150 u8 old_state)
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -0400151{
Bob Peterson1f466a42008-03-10 18:17:47 -0500152 const u8 *byte, *start, *end;
153 int bit, startbit;
154 u32 g1, g2, misaligned;
155 unsigned long *plong;
156 unsigned long lskipval;
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -0400157
Bob Peterson1f466a42008-03-10 18:17:47 -0500158 lskipval = (old_state & GFS2_BLKST_USED) ? LBITSKIP00 : LBITSKIP55;
159 g1 = (goal / GFS2_NBBY);
160 start = buffer + g1;
161 byte = start;
162 end = buffer + buflen;
163 g2 = ALIGN(g1, sizeof(unsigned long));
164 plong = (unsigned long *)(buffer + g2);
165 startbit = bit = (goal % GFS2_NBBY) * GFS2_BIT_SIZE;
166 misaligned = g2 - g1;
167 if (!misaligned)
168 goto ulong_aligned;
169/* parse the bitmap a byte at a time */
170misaligned:
171 while (byte < end) {
172 if (((*byte >> bit) & GFS2_BIT_MASK) == old_state) {
173 return goal +
174 (((byte - start) * GFS2_NBBY) +
175 ((bit - startbit) >> 1));
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -0400176 }
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -0400177 bit += GFS2_BIT_SIZE;
Bob Peterson1f466a42008-03-10 18:17:47 -0500178 if (bit >= GFS2_NBBY * GFS2_BIT_SIZE) {
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -0400179 bit = 0;
180 byte++;
Bob Peterson1f466a42008-03-10 18:17:47 -0500181 misaligned--;
182 if (!misaligned) {
183 plong = (unsigned long *)byte;
184 goto ulong_aligned;
185 }
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -0400186 }
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -0400187 }
Bob Peterson1f466a42008-03-10 18:17:47 -0500188 return BFITNOENT;
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -0400189
Bob Peterson1f466a42008-03-10 18:17:47 -0500190/* parse the bitmap a unsigned long at a time */
191ulong_aligned:
192 /* Stop at "end - 1" or else prefetch can go past the end and segfault.
193 We could "if" it but we'd lose some of the performance gained.
194 This way will only slow down searching the very last 4/8 bytes
195 depending on architecture. I've experimented with several ways
196 of writing this section such as using an else before the goto
197 but this one seems to be the fastest. */
Bob Peterson17c15da2008-06-18 11:30:40 -0500198 while ((unsigned char *)plong < end - sizeof(unsigned long)) {
Bob Peterson1f466a42008-03-10 18:17:47 -0500199 prefetch(plong + 1);
200 if (((*plong) & LBITMASK) != lskipval)
201 break;
202 plong++;
203 }
204 if ((unsigned char *)plong < end) {
205 byte = (const u8 *)plong;
206 misaligned += sizeof(unsigned long) - 1;
207 goto misaligned;
208 }
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -0400209 return BFITNOENT;
210}
211
212/**
213 * gfs2_bitcount - count the number of bits in a certain state
214 * @buffer: the buffer that holds the bitmaps
215 * @buflen: the length (in bytes) of the buffer
216 * @state: the state of the block we're looking for
217 *
218 * Returns: The number of bits
219 */
220
Steven Whitehouse110acf32008-01-29 13:30:20 +0000221static u32 gfs2_bitcount(struct gfs2_rgrpd *rgd, const u8 *buffer,
222 unsigned int buflen, u8 state)
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -0400223{
Steven Whitehouse110acf32008-01-29 13:30:20 +0000224 const u8 *byte = buffer;
225 const u8 *end = buffer + buflen;
226 const u8 state1 = state << 2;
227 const u8 state2 = state << 4;
228 const u8 state3 = state << 6;
Steven Whitehousecd915492006-09-04 12:49:07 -0400229 u32 count = 0;
Steven Whitehouse88c8ab1f2006-05-18 13:52:39 -0400230
231 for (; byte < end; byte++) {
232 if (((*byte) & 0x03) == state)
233 count++;
234 if (((*byte) & 0x0C) == state1)
235 count++;
236 if (((*byte) & 0x30) == state2)
237 count++;
238 if (((*byte) & 0xC0) == state3)
239 count++;
240 }
241
242 return count;
243}
244
David Teiglandb3b94fa2006-01-16 16:50:04 +0000245/**
246 * gfs2_rgrp_verify - Verify that a resource group is consistent
247 * @sdp: the filesystem
248 * @rgd: the rgrp
249 *
250 */
251
252void gfs2_rgrp_verify(struct gfs2_rgrpd *rgd)
253{
254 struct gfs2_sbd *sdp = rgd->rd_sbd;
255 struct gfs2_bitmap *bi = NULL;
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100256 u32 length = rgd->rd_length;
Steven Whitehousecd915492006-09-04 12:49:07 -0400257 u32 count[4], tmp;
David Teiglandb3b94fa2006-01-16 16:50:04 +0000258 int buf, x;
259
Steven Whitehousecd915492006-09-04 12:49:07 -0400260 memset(count, 0, 4 * sizeof(u32));
David Teiglandb3b94fa2006-01-16 16:50:04 +0000261
262 /* Count # blocks in each of 4 possible allocation states */
263 for (buf = 0; buf < length; buf++) {
264 bi = rgd->rd_bits + buf;
265 for (x = 0; x < 4; x++)
266 count[x] += gfs2_bitcount(rgd,
267 bi->bi_bh->b_data +
268 bi->bi_offset,
269 bi->bi_len, x);
270 }
271
Steven Whitehousecfc8b542008-11-04 10:25:13 +0000272 if (count[0] != rgd->rd_free) {
David Teiglandb3b94fa2006-01-16 16:50:04 +0000273 if (gfs2_consist_rgrpd(rgd))
274 fs_err(sdp, "free data mismatch: %u != %u\n",
Steven Whitehousecfc8b542008-11-04 10:25:13 +0000275 count[0], rgd->rd_free);
David Teiglandb3b94fa2006-01-16 16:50:04 +0000276 return;
277 }
278
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100279 tmp = rgd->rd_data -
Steven Whitehousecfc8b542008-11-04 10:25:13 +0000280 rgd->rd_free -
David Teiglandb3b94fa2006-01-16 16:50:04 +0000281 rgd->rd_rg.rg_dinodes;
Steven Whitehousefeaa7bb2006-06-14 15:32:57 -0400282 if (count[1] + count[2] != tmp) {
David Teiglandb3b94fa2006-01-16 16:50:04 +0000283 if (gfs2_consist_rgrpd(rgd))
284 fs_err(sdp, "used data mismatch: %u != %u\n",
285 count[1], tmp);
286 return;
287 }
288
David Teiglandb3b94fa2006-01-16 16:50:04 +0000289 if (count[3] != rgd->rd_rg.rg_dinodes) {
290 if (gfs2_consist_rgrpd(rgd))
291 fs_err(sdp, "used metadata mismatch: %u != %u\n",
292 count[3], rgd->rd_rg.rg_dinodes);
293 return;
294 }
Steven Whitehousefeaa7bb2006-06-14 15:32:57 -0400295
296 if (count[2] > count[3]) {
297 if (gfs2_consist_rgrpd(rgd))
298 fs_err(sdp, "unlinked inodes > inodes: %u\n",
299 count[2]);
300 return;
301 }
302
David Teiglandb3b94fa2006-01-16 16:50:04 +0000303}
304
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100305static inline int rgrp_contains_block(struct gfs2_rgrpd *rgd, u64 block)
David Teiglandb3b94fa2006-01-16 16:50:04 +0000306{
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100307 u64 first = rgd->rd_data0;
308 u64 last = first + rgd->rd_data;
Steven Whitehouse16910422006-09-05 11:15:45 -0400309 return first <= block && block < last;
David Teiglandb3b94fa2006-01-16 16:50:04 +0000310}
311
312/**
313 * gfs2_blk2rgrpd - Find resource group for a given data/meta block number
314 * @sdp: The GFS2 superblock
315 * @n: The data block number
316 *
317 * Returns: The resource group, or NULL if not found
318 */
319
Steven Whitehousecd915492006-09-04 12:49:07 -0400320struct gfs2_rgrpd *gfs2_blk2rgrpd(struct gfs2_sbd *sdp, u64 blk)
David Teiglandb3b94fa2006-01-16 16:50:04 +0000321{
322 struct gfs2_rgrpd *rgd;
323
324 spin_lock(&sdp->sd_rindex_spin);
325
326 list_for_each_entry(rgd, &sdp->sd_rindex_mru_list, rd_list_mru) {
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100327 if (rgrp_contains_block(rgd, blk)) {
David Teiglandb3b94fa2006-01-16 16:50:04 +0000328 list_move(&rgd->rd_list_mru, &sdp->sd_rindex_mru_list);
329 spin_unlock(&sdp->sd_rindex_spin);
330 return rgd;
331 }
332 }
333
334 spin_unlock(&sdp->sd_rindex_spin);
335
336 return NULL;
337}
338
339/**
340 * gfs2_rgrpd_get_first - get the first Resource Group in the filesystem
341 * @sdp: The GFS2 superblock
342 *
343 * Returns: The first rgrp in the filesystem
344 */
345
346struct gfs2_rgrpd *gfs2_rgrpd_get_first(struct gfs2_sbd *sdp)
347{
348 gfs2_assert(sdp, !list_empty(&sdp->sd_rindex_list));
349 return list_entry(sdp->sd_rindex_list.next, struct gfs2_rgrpd, rd_list);
350}
351
352/**
353 * gfs2_rgrpd_get_next - get the next RG
354 * @rgd: A RG
355 *
356 * Returns: The next rgrp
357 */
358
359struct gfs2_rgrpd *gfs2_rgrpd_get_next(struct gfs2_rgrpd *rgd)
360{
361 if (rgd->rd_list.next == &rgd->rd_sbd->sd_rindex_list)
362 return NULL;
363 return list_entry(rgd->rd_list.next, struct gfs2_rgrpd, rd_list);
364}
365
366static void clear_rgrpdi(struct gfs2_sbd *sdp)
367{
368 struct list_head *head;
369 struct gfs2_rgrpd *rgd;
370 struct gfs2_glock *gl;
371
372 spin_lock(&sdp->sd_rindex_spin);
373 sdp->sd_rindex_forward = NULL;
David Teiglandb3b94fa2006-01-16 16:50:04 +0000374 spin_unlock(&sdp->sd_rindex_spin);
375
376 head = &sdp->sd_rindex_list;
377 while (!list_empty(head)) {
378 rgd = list_entry(head->next, struct gfs2_rgrpd, rd_list);
379 gl = rgd->rd_gl;
380
381 list_del(&rgd->rd_list);
382 list_del(&rgd->rd_list_mru);
383
384 if (gl) {
Steven Whitehouse5c676f62006-02-27 17:23:27 -0500385 gl->gl_object = NULL;
David Teiglandb3b94fa2006-01-16 16:50:04 +0000386 gfs2_glock_put(gl);
387 }
388
389 kfree(rgd->rd_bits);
Bob Peterson6bdd9be2008-01-28 17:20:26 -0600390 kmem_cache_free(gfs2_rgrpd_cachep, rgd);
David Teiglandb3b94fa2006-01-16 16:50:04 +0000391 }
392}
393
394void gfs2_clear_rgrpd(struct gfs2_sbd *sdp)
395{
Steven Whitehousef55ab262006-02-21 12:51:39 +0000396 mutex_lock(&sdp->sd_rindex_mutex);
David Teiglandb3b94fa2006-01-16 16:50:04 +0000397 clear_rgrpdi(sdp);
Steven Whitehousef55ab262006-02-21 12:51:39 +0000398 mutex_unlock(&sdp->sd_rindex_mutex);
David Teiglandb3b94fa2006-01-16 16:50:04 +0000399}
400
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100401static void gfs2_rindex_print(const struct gfs2_rgrpd *rgd)
402{
403 printk(KERN_INFO " ri_addr = %llu\n", (unsigned long long)rgd->rd_addr);
404 printk(KERN_INFO " ri_length = %u\n", rgd->rd_length);
405 printk(KERN_INFO " ri_data0 = %llu\n", (unsigned long long)rgd->rd_data0);
406 printk(KERN_INFO " ri_data = %u\n", rgd->rd_data);
407 printk(KERN_INFO " ri_bitbytes = %u\n", rgd->rd_bitbytes);
408}
409
David Teiglandb3b94fa2006-01-16 16:50:04 +0000410/**
411 * gfs2_compute_bitstructs - Compute the bitmap sizes
412 * @rgd: The resource group descriptor
413 *
414 * Calculates bitmap descriptors, one for each block that contains bitmap data
415 *
416 * Returns: errno
417 */
418
419static int compute_bitstructs(struct gfs2_rgrpd *rgd)
420{
421 struct gfs2_sbd *sdp = rgd->rd_sbd;
422 struct gfs2_bitmap *bi;
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100423 u32 length = rgd->rd_length; /* # blocks in hdr & bitmap */
Steven Whitehousecd915492006-09-04 12:49:07 -0400424 u32 bytes_left, bytes;
David Teiglandb3b94fa2006-01-16 16:50:04 +0000425 int x;
426
Steven Whitehousefeaa7bb2006-06-14 15:32:57 -0400427 if (!length)
428 return -EINVAL;
429
Steven Whitehousedd894be2006-07-27 14:29:00 -0400430 rgd->rd_bits = kcalloc(length, sizeof(struct gfs2_bitmap), GFP_NOFS);
David Teiglandb3b94fa2006-01-16 16:50:04 +0000431 if (!rgd->rd_bits)
432 return -ENOMEM;
433
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100434 bytes_left = rgd->rd_bitbytes;
David Teiglandb3b94fa2006-01-16 16:50:04 +0000435
436 for (x = 0; x < length; x++) {
437 bi = rgd->rd_bits + x;
438
439 /* small rgrp; bitmap stored completely in header block */
440 if (length == 1) {
441 bytes = bytes_left;
442 bi->bi_offset = sizeof(struct gfs2_rgrp);
443 bi->bi_start = 0;
444 bi->bi_len = bytes;
445 /* header block */
446 } else if (x == 0) {
447 bytes = sdp->sd_sb.sb_bsize - sizeof(struct gfs2_rgrp);
448 bi->bi_offset = sizeof(struct gfs2_rgrp);
449 bi->bi_start = 0;
450 bi->bi_len = bytes;
451 /* last block */
452 } else if (x + 1 == length) {
453 bytes = bytes_left;
454 bi->bi_offset = sizeof(struct gfs2_meta_header);
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100455 bi->bi_start = rgd->rd_bitbytes - bytes_left;
David Teiglandb3b94fa2006-01-16 16:50:04 +0000456 bi->bi_len = bytes;
457 /* other blocks */
458 } else {
Steven Whitehouse568f4c92006-02-27 12:00:42 -0500459 bytes = sdp->sd_sb.sb_bsize -
460 sizeof(struct gfs2_meta_header);
David Teiglandb3b94fa2006-01-16 16:50:04 +0000461 bi->bi_offset = sizeof(struct gfs2_meta_header);
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100462 bi->bi_start = rgd->rd_bitbytes - bytes_left;
David Teiglandb3b94fa2006-01-16 16:50:04 +0000463 bi->bi_len = bytes;
464 }
465
466 bytes_left -= bytes;
467 }
468
469 if (bytes_left) {
470 gfs2_consist_rgrpd(rgd);
471 return -EIO;
472 }
473 bi = rgd->rd_bits + (length - 1);
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100474 if ((bi->bi_start + bi->bi_len) * GFS2_NBBY != rgd->rd_data) {
David Teiglandb3b94fa2006-01-16 16:50:04 +0000475 if (gfs2_consist_rgrpd(rgd)) {
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100476 gfs2_rindex_print(rgd);
David Teiglandb3b94fa2006-01-16 16:50:04 +0000477 fs_err(sdp, "start=%u len=%u offset=%u\n",
478 bi->bi_start, bi->bi_len, bi->bi_offset);
479 }
480 return -EIO;
481 }
482
483 return 0;
484}
485
486/**
Robert Peterson7ae8fa82007-05-09 09:37:57 -0500487 * gfs2_ri_total - Total up the file system space, according to the rindex.
488 *
489 */
490u64 gfs2_ri_total(struct gfs2_sbd *sdp)
491{
492 u64 total_data = 0;
493 struct inode *inode = sdp->sd_rindex;
494 struct gfs2_inode *ip = GFS2_I(inode);
Robert Peterson7ae8fa82007-05-09 09:37:57 -0500495 char buf[sizeof(struct gfs2_rindex)];
496 struct file_ra_state ra_state;
497 int error, rgrps;
498
499 mutex_lock(&sdp->sd_rindex_mutex);
500 file_ra_state_init(&ra_state, inode->i_mapping);
501 for (rgrps = 0;; rgrps++) {
502 loff_t pos = rgrps * sizeof(struct gfs2_rindex);
503
Steven Whitehousec9e98882008-11-04 09:47:33 +0000504 if (pos + sizeof(struct gfs2_rindex) >= ip->i_disksize)
Robert Peterson7ae8fa82007-05-09 09:37:57 -0500505 break;
506 error = gfs2_internal_read(ip, &ra_state, buf, &pos,
507 sizeof(struct gfs2_rindex));
508 if (error != sizeof(struct gfs2_rindex))
509 break;
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100510 total_data += be32_to_cpu(((struct gfs2_rindex *)buf)->ri_data);
Robert Peterson7ae8fa82007-05-09 09:37:57 -0500511 }
512 mutex_unlock(&sdp->sd_rindex_mutex);
513 return total_data;
514}
515
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100516static void gfs2_rindex_in(struct gfs2_rgrpd *rgd, const void *buf)
517{
518 const struct gfs2_rindex *str = buf;
519
520 rgd->rd_addr = be64_to_cpu(str->ri_addr);
521 rgd->rd_length = be32_to_cpu(str->ri_length);
522 rgd->rd_data0 = be64_to_cpu(str->ri_data0);
523 rgd->rd_data = be32_to_cpu(str->ri_data);
524 rgd->rd_bitbytes = be32_to_cpu(str->ri_bitbytes);
525}
526
Robert Peterson7ae8fa82007-05-09 09:37:57 -0500527/**
Robert Peterson6c532672007-05-10 16:54:38 -0500528 * read_rindex_entry - Pull in a new resource index entry from the disk
David Teiglandb3b94fa2006-01-16 16:50:04 +0000529 * @gl: The glock covering the rindex inode
530 *
Robert Peterson6c532672007-05-10 16:54:38 -0500531 * Returns: 0 on success, error code otherwise
532 */
533
534static int read_rindex_entry(struct gfs2_inode *ip,
535 struct file_ra_state *ra_state)
536{
537 struct gfs2_sbd *sdp = GFS2_SB(&ip->i_inode);
538 loff_t pos = sdp->sd_rgrps * sizeof(struct gfs2_rindex);
539 char buf[sizeof(struct gfs2_rindex)];
540 int error;
541 struct gfs2_rgrpd *rgd;
542
543 error = gfs2_internal_read(ip, ra_state, buf, &pos,
544 sizeof(struct gfs2_rindex));
545 if (!error)
546 return 0;
547 if (error != sizeof(struct gfs2_rindex)) {
548 if (error > 0)
549 error = -EIO;
550 return error;
551 }
552
Bob Peterson6bdd9be2008-01-28 17:20:26 -0600553 rgd = kmem_cache_zalloc(gfs2_rgrpd_cachep, GFP_NOFS);
Robert Peterson6c532672007-05-10 16:54:38 -0500554 error = -ENOMEM;
555 if (!rgd)
556 return error;
557
558 mutex_init(&rgd->rd_mutex);
559 lops_init_le(&rgd->rd_le, &gfs2_rg_lops);
560 rgd->rd_sbd = sdp;
561
562 list_add_tail(&rgd->rd_list, &sdp->sd_rindex_list);
563 list_add_tail(&rgd->rd_list_mru, &sdp->sd_rindex_mru_list);
564
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100565 gfs2_rindex_in(rgd, buf);
Robert Peterson6c532672007-05-10 16:54:38 -0500566 error = compute_bitstructs(rgd);
567 if (error)
568 return error;
569
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100570 error = gfs2_glock_get(sdp, rgd->rd_addr,
Robert Peterson6c532672007-05-10 16:54:38 -0500571 &gfs2_rgrp_glops, CREATE, &rgd->rd_gl);
572 if (error)
573 return error;
574
575 rgd->rd_gl->gl_object = rgd;
Bob Petersoncf45b752008-01-31 10:31:39 -0600576 rgd->rd_flags &= ~GFS2_RDF_UPTODATE;
Steven Whitehousec8cdf472007-06-08 10:05:33 +0100577 rgd->rd_flags |= GFS2_RDF_CHECK;
Robert Peterson6c532672007-05-10 16:54:38 -0500578 return error;
579}
580
581/**
582 * gfs2_ri_update - Pull in a new resource index from the disk
583 * @ip: pointer to the rindex inode
584 *
David Teiglandb3b94fa2006-01-16 16:50:04 +0000585 * Returns: 0 on successful update, error code otherwise
586 */
587
588static int gfs2_ri_update(struct gfs2_inode *ip)
589{
Steven Whitehousefeaa7bb2006-06-14 15:32:57 -0400590 struct gfs2_sbd *sdp = GFS2_SB(&ip->i_inode);
591 struct inode *inode = &ip->i_inode;
Steven Whitehousef42faf42006-01-30 18:34:10 +0000592 struct file_ra_state ra_state;
Steven Whitehousec9e98882008-11-04 09:47:33 +0000593 u64 rgrp_count = ip->i_disksize;
David Teiglandb3b94fa2006-01-16 16:50:04 +0000594 int error;
595
Robert Petersoncd81a4b2007-05-14 12:42:18 -0500596 if (do_div(rgrp_count, sizeof(struct gfs2_rindex))) {
David Teiglandb3b94fa2006-01-16 16:50:04 +0000597 gfs2_consist_inode(ip);
598 return -EIO;
599 }
600
601 clear_rgrpdi(sdp);
602
Steven Whitehousef42faf42006-01-30 18:34:10 +0000603 file_ra_state_init(&ra_state, inode->i_mapping);
Robert Petersoncd81a4b2007-05-14 12:42:18 -0500604 for (sdp->sd_rgrps = 0; sdp->sd_rgrps < rgrp_count; sdp->sd_rgrps++) {
Robert Peterson6c532672007-05-10 16:54:38 -0500605 error = read_rindex_entry(ip, &ra_state);
606 if (error) {
607 clear_rgrpdi(sdp);
608 return error;
David Teiglandb3b94fa2006-01-16 16:50:04 +0000609 }
David Teiglandb3b94fa2006-01-16 16:50:04 +0000610 }
611
Bob Petersoncf45b752008-01-31 10:31:39 -0600612 sdp->sd_rindex_uptodate = 1;
David Teiglandb3b94fa2006-01-16 16:50:04 +0000613 return 0;
Robert Peterson6c532672007-05-10 16:54:38 -0500614}
David Teiglandb3b94fa2006-01-16 16:50:04 +0000615
Robert Peterson6c532672007-05-10 16:54:38 -0500616/**
617 * gfs2_ri_update_special - Pull in a new resource index from the disk
618 *
619 * This is a special version that's safe to call from gfs2_inplace_reserve_i.
620 * In this case we know that we don't have any resource groups in memory yet.
621 *
622 * @ip: pointer to the rindex inode
623 *
624 * Returns: 0 on successful update, error code otherwise
625 */
626static int gfs2_ri_update_special(struct gfs2_inode *ip)
627{
628 struct gfs2_sbd *sdp = GFS2_SB(&ip->i_inode);
629 struct inode *inode = &ip->i_inode;
630 struct file_ra_state ra_state;
631 int error;
632
633 file_ra_state_init(&ra_state, inode->i_mapping);
634 for (sdp->sd_rgrps = 0;; sdp->sd_rgrps++) {
635 /* Ignore partials */
636 if ((sdp->sd_rgrps + 1) * sizeof(struct gfs2_rindex) >
Steven Whitehousec9e98882008-11-04 09:47:33 +0000637 ip->i_disksize)
Robert Peterson6c532672007-05-10 16:54:38 -0500638 break;
639 error = read_rindex_entry(ip, &ra_state);
640 if (error) {
641 clear_rgrpdi(sdp);
642 return error;
643 }
644 }
645
Bob Petersoncf45b752008-01-31 10:31:39 -0600646 sdp->sd_rindex_uptodate = 1;
Robert Peterson6c532672007-05-10 16:54:38 -0500647 return 0;
David Teiglandb3b94fa2006-01-16 16:50:04 +0000648}
649
650/**
651 * gfs2_rindex_hold - Grab a lock on the rindex
652 * @sdp: The GFS2 superblock
653 * @ri_gh: the glock holder
654 *
655 * We grab a lock on the rindex inode to make sure that it doesn't
656 * change whilst we are performing an operation. We keep this lock
657 * for quite long periods of time compared to other locks. This
658 * doesn't matter, since it is shared and it is very, very rarely
659 * accessed in the exclusive mode (i.e. only when expanding the filesystem).
660 *
661 * This makes sure that we're using the latest copy of the resource index
662 * special file, which might have been updated if someone expanded the
663 * filesystem (via gfs2_grow utility), which adds new resource groups.
664 *
665 * Returns: 0 on success, error code otherwise
666 */
667
668int gfs2_rindex_hold(struct gfs2_sbd *sdp, struct gfs2_holder *ri_gh)
669{
Steven Whitehousefeaa7bb2006-06-14 15:32:57 -0400670 struct gfs2_inode *ip = GFS2_I(sdp->sd_rindex);
David Teiglandb3b94fa2006-01-16 16:50:04 +0000671 struct gfs2_glock *gl = ip->i_gl;
672 int error;
673
674 error = gfs2_glock_nq_init(gl, LM_ST_SHARED, 0, ri_gh);
675 if (error)
676 return error;
677
678 /* Read new copy from disk if we don't have the latest */
Bob Petersoncf45b752008-01-31 10:31:39 -0600679 if (!sdp->sd_rindex_uptodate) {
Steven Whitehousef55ab262006-02-21 12:51:39 +0000680 mutex_lock(&sdp->sd_rindex_mutex);
Bob Petersoncf45b752008-01-31 10:31:39 -0600681 if (!sdp->sd_rindex_uptodate) {
David Teiglandb3b94fa2006-01-16 16:50:04 +0000682 error = gfs2_ri_update(ip);
683 if (error)
684 gfs2_glock_dq_uninit(ri_gh);
685 }
Steven Whitehousef55ab262006-02-21 12:51:39 +0000686 mutex_unlock(&sdp->sd_rindex_mutex);
David Teiglandb3b94fa2006-01-16 16:50:04 +0000687 }
688
689 return error;
690}
691
Bob Peterson42d52e32008-01-28 18:38:07 -0600692static void gfs2_rgrp_in(struct gfs2_rgrpd *rgd, const void *buf)
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100693{
694 const struct gfs2_rgrp *str = buf;
Bob Peterson42d52e32008-01-28 18:38:07 -0600695 struct gfs2_rgrp_host *rg = &rgd->rd_rg;
696 u32 rg_flags;
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100697
Bob Peterson42d52e32008-01-28 18:38:07 -0600698 rg_flags = be32_to_cpu(str->rg_flags);
699 if (rg_flags & GFS2_RGF_NOALLOC)
700 rgd->rd_flags |= GFS2_RDF_NOALLOC;
701 else
702 rgd->rd_flags &= ~GFS2_RDF_NOALLOC;
Steven Whitehousecfc8b542008-11-04 10:25:13 +0000703 rgd->rd_free = be32_to_cpu(str->rg_free);
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100704 rg->rg_dinodes = be32_to_cpu(str->rg_dinodes);
Steven Whitehoused8b71f72008-11-04 10:19:03 +0000705 rgd->rd_igeneration = be64_to_cpu(str->rg_igeneration);
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100706}
707
Bob Peterson42d52e32008-01-28 18:38:07 -0600708static void gfs2_rgrp_out(struct gfs2_rgrpd *rgd, void *buf)
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100709{
710 struct gfs2_rgrp *str = buf;
Bob Peterson42d52e32008-01-28 18:38:07 -0600711 struct gfs2_rgrp_host *rg = &rgd->rd_rg;
712 u32 rg_flags = 0;
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100713
Bob Peterson42d52e32008-01-28 18:38:07 -0600714 if (rgd->rd_flags & GFS2_RDF_NOALLOC)
715 rg_flags |= GFS2_RGF_NOALLOC;
716 str->rg_flags = cpu_to_be32(rg_flags);
Steven Whitehousecfc8b542008-11-04 10:25:13 +0000717 str->rg_free = cpu_to_be32(rgd->rd_free);
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100718 str->rg_dinodes = cpu_to_be32(rg->rg_dinodes);
719 str->__pad = cpu_to_be32(0);
Steven Whitehoused8b71f72008-11-04 10:19:03 +0000720 str->rg_igeneration = cpu_to_be64(rgd->rd_igeneration);
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100721 memset(&str->rg_reserved, 0, sizeof(str->rg_reserved));
722}
723
David Teiglandb3b94fa2006-01-16 16:50:04 +0000724/**
725 * gfs2_rgrp_bh_get - Read in a RG's header and bitmaps
726 * @rgd: the struct gfs2_rgrpd describing the RG to read in
727 *
728 * Read in all of a Resource Group's header and bitmap blocks.
729 * Caller must eventually call gfs2_rgrp_relse() to free the bitmaps.
730 *
731 * Returns: errno
732 */
733
734int gfs2_rgrp_bh_get(struct gfs2_rgrpd *rgd)
735{
736 struct gfs2_sbd *sdp = rgd->rd_sbd;
737 struct gfs2_glock *gl = rgd->rd_gl;
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100738 unsigned int length = rgd->rd_length;
David Teiglandb3b94fa2006-01-16 16:50:04 +0000739 struct gfs2_bitmap *bi;
740 unsigned int x, y;
741 int error;
742
Steven Whitehousef55ab262006-02-21 12:51:39 +0000743 mutex_lock(&rgd->rd_mutex);
David Teiglandb3b94fa2006-01-16 16:50:04 +0000744
745 spin_lock(&sdp->sd_rindex_spin);
746 if (rgd->rd_bh_count) {
747 rgd->rd_bh_count++;
748 spin_unlock(&sdp->sd_rindex_spin);
Steven Whitehousef55ab262006-02-21 12:51:39 +0000749 mutex_unlock(&rgd->rd_mutex);
David Teiglandb3b94fa2006-01-16 16:50:04 +0000750 return 0;
751 }
752 spin_unlock(&sdp->sd_rindex_spin);
753
754 for (x = 0; x < length; x++) {
755 bi = rgd->rd_bits + x;
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100756 error = gfs2_meta_read(gl, rgd->rd_addr + x, 0, &bi->bi_bh);
David Teiglandb3b94fa2006-01-16 16:50:04 +0000757 if (error)
758 goto fail;
759 }
760
761 for (y = length; y--;) {
762 bi = rgd->rd_bits + y;
Steven Whitehouse7276b3b2006-09-21 17:05:23 -0400763 error = gfs2_meta_wait(sdp, bi->bi_bh);
David Teiglandb3b94fa2006-01-16 16:50:04 +0000764 if (error)
765 goto fail;
Steven Whitehousefeaa7bb2006-06-14 15:32:57 -0400766 if (gfs2_metatype_check(sdp, bi->bi_bh, y ? GFS2_METATYPE_RB :
David Teiglandb3b94fa2006-01-16 16:50:04 +0000767 GFS2_METATYPE_RG)) {
768 error = -EIO;
769 goto fail;
770 }
771 }
772
Bob Petersoncf45b752008-01-31 10:31:39 -0600773 if (!(rgd->rd_flags & GFS2_RDF_UPTODATE)) {
Bob Peterson42d52e32008-01-28 18:38:07 -0600774 gfs2_rgrp_in(rgd, (rgd->rd_bits[0].bi_bh)->b_data);
Bob Petersoncf45b752008-01-31 10:31:39 -0600775 rgd->rd_flags |= GFS2_RDF_UPTODATE;
David Teiglandb3b94fa2006-01-16 16:50:04 +0000776 }
777
778 spin_lock(&sdp->sd_rindex_spin);
Steven Whitehousecfc8b542008-11-04 10:25:13 +0000779 rgd->rd_free_clone = rgd->rd_free;
David Teiglandb3b94fa2006-01-16 16:50:04 +0000780 rgd->rd_bh_count++;
781 spin_unlock(&sdp->sd_rindex_spin);
782
Steven Whitehousef55ab262006-02-21 12:51:39 +0000783 mutex_unlock(&rgd->rd_mutex);
David Teiglandb3b94fa2006-01-16 16:50:04 +0000784
785 return 0;
786
Steven Whitehousefeaa7bb2006-06-14 15:32:57 -0400787fail:
David Teiglandb3b94fa2006-01-16 16:50:04 +0000788 while (x--) {
789 bi = rgd->rd_bits + x;
790 brelse(bi->bi_bh);
791 bi->bi_bh = NULL;
792 gfs2_assert_warn(sdp, !bi->bi_clone);
793 }
Steven Whitehousef55ab262006-02-21 12:51:39 +0000794 mutex_unlock(&rgd->rd_mutex);
David Teiglandb3b94fa2006-01-16 16:50:04 +0000795
796 return error;
797}
798
799void gfs2_rgrp_bh_hold(struct gfs2_rgrpd *rgd)
800{
801 struct gfs2_sbd *sdp = rgd->rd_sbd;
802
803 spin_lock(&sdp->sd_rindex_spin);
804 gfs2_assert_warn(rgd->rd_sbd, rgd->rd_bh_count);
805 rgd->rd_bh_count++;
806 spin_unlock(&sdp->sd_rindex_spin);
807}
808
809/**
810 * gfs2_rgrp_bh_put - Release RG bitmaps read in with gfs2_rgrp_bh_get()
811 * @rgd: the struct gfs2_rgrpd describing the RG to read in
812 *
813 */
814
815void gfs2_rgrp_bh_put(struct gfs2_rgrpd *rgd)
816{
817 struct gfs2_sbd *sdp = rgd->rd_sbd;
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100818 int x, length = rgd->rd_length;
David Teiglandb3b94fa2006-01-16 16:50:04 +0000819
820 spin_lock(&sdp->sd_rindex_spin);
821 gfs2_assert_warn(rgd->rd_sbd, rgd->rd_bh_count);
822 if (--rgd->rd_bh_count) {
823 spin_unlock(&sdp->sd_rindex_spin);
824 return;
825 }
826
827 for (x = 0; x < length; x++) {
828 struct gfs2_bitmap *bi = rgd->rd_bits + x;
829 kfree(bi->bi_clone);
830 bi->bi_clone = NULL;
831 brelse(bi->bi_bh);
832 bi->bi_bh = NULL;
833 }
834
835 spin_unlock(&sdp->sd_rindex_spin);
836}
837
838void gfs2_rgrp_repolish_clones(struct gfs2_rgrpd *rgd)
839{
840 struct gfs2_sbd *sdp = rgd->rd_sbd;
Steven Whitehousebb8d8a62007-06-01 14:11:58 +0100841 unsigned int length = rgd->rd_length;
David Teiglandb3b94fa2006-01-16 16:50:04 +0000842 unsigned int x;
843
844 for (x = 0; x < length; x++) {
845 struct gfs2_bitmap *bi = rgd->rd_bits + x;
846 if (!bi->bi_clone)
847 continue;
848 memcpy(bi->bi_clone + bi->bi_offset,
Steven Whitehousefeaa7bb2006-06-14 15:32:57 -0400849 bi->bi_bh->b_data + bi->bi_offset, bi->bi_len);
David Teiglandb3b94fa2006-01-16 16:50:04 +0000850 }
851
852 spin_lock(&sdp->sd_rindex_spin);
Steven Whitehousecfc8b542008-11-04 10:25:13 +0000853 rgd->rd_free_clone = rgd->rd_free;
David Teiglandb3b94fa2006-01-16 16:50:04 +0000854 spin_unlock(&sdp->sd_rindex_spin);
855}
856
857/**
858 * gfs2_alloc_get - get the struct gfs2_alloc structure for an inode
859 * @ip: the incore GFS2 inode structure
860 *
861 * Returns: the struct gfs2_alloc
862 */
863
864struct gfs2_alloc *gfs2_alloc_get(struct gfs2_inode *ip)
865{
Steven Whitehouse6dbd8222008-01-10 15:18:55 +0000866 BUG_ON(ip->i_alloc != NULL);
867 ip->i_alloc = kzalloc(sizeof(struct gfs2_alloc), GFP_KERNEL);
868 return ip->i_alloc;
David Teiglandb3b94fa2006-01-16 16:50:04 +0000869}
870
871/**
David Teiglandb3b94fa2006-01-16 16:50:04 +0000872 * try_rgrp_fit - See if a given reservation will fit in a given RG
873 * @rgd: the RG data
874 * @al: the struct gfs2_alloc structure describing the reservation
875 *
876 * If there's room for the requested blocks to be allocated from the RG:
David Teiglandb3b94fa2006-01-16 16:50:04 +0000877 * Sets the $al_rgd field in @al.
878 *
879 * Returns: 1 on success (it fits), 0 on failure (it doesn't fit)
880 */
881
882static int try_rgrp_fit(struct gfs2_rgrpd *rgd, struct gfs2_alloc *al)
883{
884 struct gfs2_sbd *sdp = rgd->rd_sbd;
885 int ret = 0;
886
Bob Peterson42d52e32008-01-28 18:38:07 -0600887 if (rgd->rd_flags & GFS2_RDF_NOALLOC)
Steven Whitehousea43a4902007-04-02 10:48:17 +0100888 return 0;
889
David Teiglandb3b94fa2006-01-16 16:50:04 +0000890 spin_lock(&sdp->sd_rindex_spin);
891 if (rgd->rd_free_clone >= al->al_requested) {
892 al->al_rgd = rgd;
893 ret = 1;
894 }
895 spin_unlock(&sdp->sd_rindex_spin);
896
897 return ret;
898}
899
900/**
Steven Whitehousec8cdf472007-06-08 10:05:33 +0100901 * try_rgrp_unlink - Look for any unlinked, allocated, but unused inodes
902 * @rgd: The rgrp
903 *
904 * Returns: The inode, if one has been found
905 */
906
907static struct inode *try_rgrp_unlink(struct gfs2_rgrpd *rgd, u64 *last_unlinked)
908{
909 struct inode *inode;
Bob Peterson6760bdc2007-07-24 14:09:32 -0500910 u32 goal = 0, block;
Wendy Chengbb9bcf02007-06-27 17:07:08 -0400911 u64 no_addr;
Bob Peterson5f3eae72007-08-08 16:52:09 -0500912 struct gfs2_sbd *sdp = rgd->rd_sbd;
Steven Whitehouseb45e41d2008-02-06 10:11:15 +0000913 unsigned int n;
Steven Whitehousec8cdf472007-06-08 10:05:33 +0100914
915 for(;;) {
Bob Peterson24c73872007-07-12 16:58:50 -0500916 if (goal >= rgd->rd_data)
917 break;
Bob Peterson5f3eae72007-08-08 16:52:09 -0500918 down_write(&sdp->sd_log_flush_lock);
Steven Whitehouseb45e41d2008-02-06 10:11:15 +0000919 n = 1;
Bob Peterson6760bdc2007-07-24 14:09:32 -0500920 block = rgblk_search(rgd, goal, GFS2_BLKST_UNLINKED,
Steven Whitehouseb45e41d2008-02-06 10:11:15 +0000921 GFS2_BLKST_UNLINKED, &n);
Bob Peterson5f3eae72007-08-08 16:52:09 -0500922 up_write(&sdp->sd_log_flush_lock);
Bob Peterson6760bdc2007-07-24 14:09:32 -0500923 if (block == BFITNOENT)
Bob Peterson24c73872007-07-12 16:58:50 -0500924 break;
Bob Peterson6760bdc2007-07-24 14:09:32 -0500925 /* rgblk_search can return a block < goal, so we need to
926 keep it marching forward. */
927 no_addr = block + rgd->rd_data0;
Bob Peterson24c73872007-07-12 16:58:50 -0500928 goal++;
Bob Peterson6760bdc2007-07-24 14:09:32 -0500929 if (*last_unlinked != NO_BLOCK && no_addr <= *last_unlinked)
Steven Whitehousec8cdf472007-06-08 10:05:33 +0100930 continue;
Wendy Chengbb9bcf02007-06-27 17:07:08 -0400931 *last_unlinked = no_addr;
932 inode = gfs2_inode_lookup(rgd->rd_sbd->sd_vfs, DT_UNKNOWN,
Benjamin Marzinski7a9f53b2007-09-18 13:33:18 -0500933 no_addr, -1, 1);
Steven Whitehousec8cdf472007-06-08 10:05:33 +0100934 if (!IS_ERR(inode))
935 return inode;
936 }
937
938 rgd->rd_flags &= ~GFS2_RDF_CHECK;
939 return NULL;
940}
941
942/**
David Teiglandb3b94fa2006-01-16 16:50:04 +0000943 * recent_rgrp_next - get next RG from "recent" list
944 * @cur_rgd: current rgrp
David Teiglandb3b94fa2006-01-16 16:50:04 +0000945 *
946 * Returns: The next rgrp in the recent list
947 */
948
Steven Whitehouse9cabcdb2008-07-10 15:54:12 +0100949static struct gfs2_rgrpd *recent_rgrp_next(struct gfs2_rgrpd *cur_rgd)
David Teiglandb3b94fa2006-01-16 16:50:04 +0000950{
951 struct gfs2_sbd *sdp = cur_rgd->rd_sbd;
952 struct list_head *head;
953 struct gfs2_rgrpd *rgd;
954
955 spin_lock(&sdp->sd_rindex_spin);
Steven Whitehouse9cabcdb2008-07-10 15:54:12 +0100956 head = &sdp->sd_rindex_mru_list;
957 if (unlikely(cur_rgd->rd_list_mru.next == head)) {
958 spin_unlock(&sdp->sd_rindex_spin);
959 return NULL;
David Teiglandb3b94fa2006-01-16 16:50:04 +0000960 }
Steven Whitehouse9cabcdb2008-07-10 15:54:12 +0100961 rgd = list_entry(cur_rgd->rd_list_mru.next, struct gfs2_rgrpd, rd_list_mru);
David Teiglandb3b94fa2006-01-16 16:50:04 +0000962 spin_unlock(&sdp->sd_rindex_spin);
David Teiglandb3b94fa2006-01-16 16:50:04 +0000963 return rgd;
964}
965
966/**
David Teiglandb3b94fa2006-01-16 16:50:04 +0000967 * forward_rgrp_get - get an rgrp to try next from full list
968 * @sdp: The GFS2 superblock
969 *
970 * Returns: The rgrp to try next
971 */
972
973static struct gfs2_rgrpd *forward_rgrp_get(struct gfs2_sbd *sdp)
974{
975 struct gfs2_rgrpd *rgd;
976 unsigned int journals = gfs2_jindex_size(sdp);
977 unsigned int rg = 0, x;
978
979 spin_lock(&sdp->sd_rindex_spin);
980
981 rgd = sdp->sd_rindex_forward;
982 if (!rgd) {
983 if (sdp->sd_rgrps >= journals)
984 rg = sdp->sd_rgrps * sdp->sd_jdesc->jd_jid / journals;
985
Steven Whitehouseb8e1aab2006-08-22 16:25:50 -0400986 for (x = 0, rgd = gfs2_rgrpd_get_first(sdp); x < rg;
David Teiglandb3b94fa2006-01-16 16:50:04 +0000987 x++, rgd = gfs2_rgrpd_get_next(rgd))
988 /* Do Nothing */;
989
990 sdp->sd_rindex_forward = rgd;
991 }
992
993 spin_unlock(&sdp->sd_rindex_spin);
994
995 return rgd;
996}
997
998/**
999 * forward_rgrp_set - set the forward rgrp pointer
1000 * @sdp: the filesystem
1001 * @rgd: The new forward rgrp
1002 *
1003 */
1004
1005static void forward_rgrp_set(struct gfs2_sbd *sdp, struct gfs2_rgrpd *rgd)
1006{
1007 spin_lock(&sdp->sd_rindex_spin);
1008 sdp->sd_rindex_forward = rgd;
1009 spin_unlock(&sdp->sd_rindex_spin);
1010}
1011
1012/**
1013 * get_local_rgrp - Choose and lock a rgrp for allocation
1014 * @ip: the inode to reserve space for
1015 * @rgp: the chosen and locked rgrp
1016 *
1017 * Try to acquire rgrp in way which avoids contending with others.
1018 *
1019 * Returns: errno
1020 */
1021
Steven Whitehousec8cdf472007-06-08 10:05:33 +01001022static struct inode *get_local_rgrp(struct gfs2_inode *ip, u64 *last_unlinked)
David Teiglandb3b94fa2006-01-16 16:50:04 +00001023{
Steven Whitehousec8cdf472007-06-08 10:05:33 +01001024 struct inode *inode = NULL;
Steven Whitehousefeaa7bb2006-06-14 15:32:57 -04001025 struct gfs2_sbd *sdp = GFS2_SB(&ip->i_inode);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001026 struct gfs2_rgrpd *rgd, *begin = NULL;
Steven Whitehouse6dbd8222008-01-10 15:18:55 +00001027 struct gfs2_alloc *al = ip->i_alloc;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001028 int flags = LM_FLAG_TRY;
1029 int skipped = 0;
1030 int loops = 0;
Abhijith Das292c8c12007-11-29 14:13:54 -06001031 int error, rg_locked;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001032
Steven Whitehouse9cabcdb2008-07-10 15:54:12 +01001033 rgd = gfs2_blk2rgrpd(sdp, ip->i_goal);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001034
1035 while (rgd) {
Abhijith Das292c8c12007-11-29 14:13:54 -06001036 rg_locked = 0;
1037
1038 if (gfs2_glock_is_locked_by_me(rgd->rd_gl)) {
1039 rg_locked = 1;
1040 error = 0;
1041 } else {
1042 error = gfs2_glock_nq_init(rgd->rd_gl, LM_ST_EXCLUSIVE,
1043 LM_FLAG_TRY, &al->al_rgd_gh);
1044 }
David Teiglandb3b94fa2006-01-16 16:50:04 +00001045 switch (error) {
1046 case 0:
1047 if (try_rgrp_fit(rgd, al))
1048 goto out;
Steven Whitehousec8cdf472007-06-08 10:05:33 +01001049 if (rgd->rd_flags & GFS2_RDF_CHECK)
1050 inode = try_rgrp_unlink(rgd, last_unlinked);
Abhijith Das292c8c12007-11-29 14:13:54 -06001051 if (!rg_locked)
1052 gfs2_glock_dq_uninit(&al->al_rgd_gh);
Steven Whitehousec8cdf472007-06-08 10:05:33 +01001053 if (inode)
1054 return inode;
Steven Whitehouse9cabcdb2008-07-10 15:54:12 +01001055 /* fall through */
David Teiglandb3b94fa2006-01-16 16:50:04 +00001056 case GLR_TRYFAILED:
Steven Whitehouse9cabcdb2008-07-10 15:54:12 +01001057 rgd = recent_rgrp_next(rgd);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001058 break;
1059
1060 default:
Steven Whitehousec8cdf472007-06-08 10:05:33 +01001061 return ERR_PTR(error);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001062 }
1063 }
1064
1065 /* Go through full list of rgrps */
1066
1067 begin = rgd = forward_rgrp_get(sdp);
1068
1069 for (;;) {
Abhijith Das292c8c12007-11-29 14:13:54 -06001070 rg_locked = 0;
1071
1072 if (gfs2_glock_is_locked_by_me(rgd->rd_gl)) {
1073 rg_locked = 1;
1074 error = 0;
1075 } else {
1076 error = gfs2_glock_nq_init(rgd->rd_gl, LM_ST_EXCLUSIVE, flags,
1077 &al->al_rgd_gh);
1078 }
David Teiglandb3b94fa2006-01-16 16:50:04 +00001079 switch (error) {
1080 case 0:
1081 if (try_rgrp_fit(rgd, al))
1082 goto out;
Steven Whitehousec8cdf472007-06-08 10:05:33 +01001083 if (rgd->rd_flags & GFS2_RDF_CHECK)
1084 inode = try_rgrp_unlink(rgd, last_unlinked);
Abhijith Das292c8c12007-11-29 14:13:54 -06001085 if (!rg_locked)
1086 gfs2_glock_dq_uninit(&al->al_rgd_gh);
Steven Whitehousec8cdf472007-06-08 10:05:33 +01001087 if (inode)
1088 return inode;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001089 break;
1090
1091 case GLR_TRYFAILED:
1092 skipped++;
1093 break;
1094
1095 default:
Steven Whitehousec8cdf472007-06-08 10:05:33 +01001096 return ERR_PTR(error);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001097 }
1098
1099 rgd = gfs2_rgrpd_get_next(rgd);
1100 if (!rgd)
1101 rgd = gfs2_rgrpd_get_first(sdp);
1102
1103 if (rgd == begin) {
Benjamin Marzinski172e0452007-03-23 14:51:56 -06001104 if (++loops >= 3)
Steven Whitehousec8cdf472007-06-08 10:05:33 +01001105 return ERR_PTR(-ENOSPC);
Benjamin Marzinski172e0452007-03-23 14:51:56 -06001106 if (!skipped)
1107 loops++;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001108 flags = 0;
Benjamin Marzinski172e0452007-03-23 14:51:56 -06001109 if (loops == 2)
1110 gfs2_log_flush(sdp, NULL);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001111 }
1112 }
1113
Steven Whitehousefeaa7bb2006-06-14 15:32:57 -04001114out:
David Teiglandb3b94fa2006-01-16 16:50:04 +00001115 if (begin) {
Steven Whitehouse9cabcdb2008-07-10 15:54:12 +01001116 spin_lock(&sdp->sd_rindex_spin);
1117 list_move(&rgd->rd_list_mru, &sdp->sd_rindex_mru_list);
1118 spin_unlock(&sdp->sd_rindex_spin);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001119 rgd = gfs2_rgrpd_get_next(rgd);
1120 if (!rgd)
1121 rgd = gfs2_rgrpd_get_first(sdp);
1122 forward_rgrp_set(sdp, rgd);
1123 }
1124
Steven Whitehousec8cdf472007-06-08 10:05:33 +01001125 return NULL;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001126}
1127
1128/**
1129 * gfs2_inplace_reserve_i - Reserve space in the filesystem
1130 * @ip: the inode to reserve space for
1131 *
1132 * Returns: errno
1133 */
1134
1135int gfs2_inplace_reserve_i(struct gfs2_inode *ip, char *file, unsigned int line)
1136{
Steven Whitehousefeaa7bb2006-06-14 15:32:57 -04001137 struct gfs2_sbd *sdp = GFS2_SB(&ip->i_inode);
Steven Whitehouse6dbd8222008-01-10 15:18:55 +00001138 struct gfs2_alloc *al = ip->i_alloc;
Steven Whitehousec8cdf472007-06-08 10:05:33 +01001139 struct inode *inode;
Robert Peterson7ae8fa82007-05-09 09:37:57 -05001140 int error = 0;
Bob Peterson6760bdc2007-07-24 14:09:32 -05001141 u64 last_unlinked = NO_BLOCK;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001142
1143 if (gfs2_assert_warn(sdp, al->al_requested))
1144 return -EINVAL;
1145
Steven Whitehousec8cdf472007-06-08 10:05:33 +01001146try_again:
Robert Peterson7ae8fa82007-05-09 09:37:57 -05001147 /* We need to hold the rindex unless the inode we're using is
1148 the rindex itself, in which case it's already held. */
1149 if (ip != GFS2_I(sdp->sd_rindex))
1150 error = gfs2_rindex_hold(sdp, &al->al_ri_gh);
1151 else if (!sdp->sd_rgrps) /* We may not have the rindex read in, so: */
Robert Peterson6c532672007-05-10 16:54:38 -05001152 error = gfs2_ri_update_special(ip);
Robert Peterson7ae8fa82007-05-09 09:37:57 -05001153
David Teiglandb3b94fa2006-01-16 16:50:04 +00001154 if (error)
1155 return error;
1156
Steven Whitehousec8cdf472007-06-08 10:05:33 +01001157 inode = get_local_rgrp(ip, &last_unlinked);
1158 if (inode) {
Robert Peterson7ae8fa82007-05-09 09:37:57 -05001159 if (ip != GFS2_I(sdp->sd_rindex))
1160 gfs2_glock_dq_uninit(&al->al_ri_gh);
Steven Whitehousec8cdf472007-06-08 10:05:33 +01001161 if (IS_ERR(inode))
1162 return PTR_ERR(inode);
1163 iput(inode);
1164 gfs2_log_flush(sdp, NULL);
1165 goto try_again;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001166 }
1167
1168 al->al_file = file;
1169 al->al_line = line;
1170
1171 return 0;
1172}
1173
1174/**
1175 * gfs2_inplace_release - release an inplace reservation
1176 * @ip: the inode the reservation was taken out on
1177 *
1178 * Release a reservation made by gfs2_inplace_reserve().
1179 */
1180
1181void gfs2_inplace_release(struct gfs2_inode *ip)
1182{
Steven Whitehousefeaa7bb2006-06-14 15:32:57 -04001183 struct gfs2_sbd *sdp = GFS2_SB(&ip->i_inode);
Steven Whitehouse6dbd8222008-01-10 15:18:55 +00001184 struct gfs2_alloc *al = ip->i_alloc;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001185
1186 if (gfs2_assert_warn(sdp, al->al_alloced <= al->al_requested) == -1)
1187 fs_warn(sdp, "al_alloced = %u, al_requested = %u "
1188 "al_file = %s, al_line = %u\n",
1189 al->al_alloced, al->al_requested, al->al_file,
1190 al->al_line);
1191
1192 al->al_rgd = NULL;
Abhijith Das292c8c12007-11-29 14:13:54 -06001193 if (al->al_rgd_gh.gh_gl)
1194 gfs2_glock_dq_uninit(&al->al_rgd_gh);
Robert Peterson7ae8fa82007-05-09 09:37:57 -05001195 if (ip != GFS2_I(sdp->sd_rindex))
1196 gfs2_glock_dq_uninit(&al->al_ri_gh);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001197}
1198
1199/**
1200 * gfs2_get_block_type - Check a block in a RG is of given type
1201 * @rgd: the resource group holding the block
1202 * @block: the block number
1203 *
1204 * Returns: The block type (GFS2_BLKST_*)
1205 */
1206
Steven Whitehousecd915492006-09-04 12:49:07 -04001207unsigned char gfs2_get_block_type(struct gfs2_rgrpd *rgd, u64 block)
David Teiglandb3b94fa2006-01-16 16:50:04 +00001208{
1209 struct gfs2_bitmap *bi = NULL;
Steven Whitehousecd915492006-09-04 12:49:07 -04001210 u32 length, rgrp_block, buf_block;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001211 unsigned int buf;
1212 unsigned char type;
1213
Steven Whitehousebb8d8a62007-06-01 14:11:58 +01001214 length = rgd->rd_length;
1215 rgrp_block = block - rgd->rd_data0;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001216
1217 for (buf = 0; buf < length; buf++) {
1218 bi = rgd->rd_bits + buf;
1219 if (rgrp_block < (bi->bi_start + bi->bi_len) * GFS2_NBBY)
1220 break;
1221 }
1222
1223 gfs2_assert(rgd->rd_sbd, buf < length);
1224 buf_block = rgrp_block - bi->bi_start * GFS2_NBBY;
1225
Steven Whitehousefeaa7bb2006-06-14 15:32:57 -04001226 type = gfs2_testbit(rgd, bi->bi_bh->b_data + bi->bi_offset,
David Teiglandb3b94fa2006-01-16 16:50:04 +00001227 bi->bi_len, buf_block);
1228
1229 return type;
1230}
1231
1232/**
1233 * rgblk_search - find a block in @old_state, change allocation
1234 * state to @new_state
1235 * @rgd: the resource group descriptor
1236 * @goal: the goal block within the RG (start here to search for avail block)
1237 * @old_state: GFS2_BLKST_XXX the before-allocation state to find
1238 * @new_state: GFS2_BLKST_XXX the after-allocation block state
Steven Whitehouseb45e41d2008-02-06 10:11:15 +00001239 * @n: The extent length
David Teiglandb3b94fa2006-01-16 16:50:04 +00001240 *
1241 * Walk rgrp's bitmap to find bits that represent a block in @old_state.
1242 * Add the found bitmap buffer to the transaction.
1243 * Set the found bits to @new_state to change block's allocation state.
1244 *
1245 * This function never fails, because we wouldn't call it unless we
1246 * know (from reservation results, etc.) that a block is available.
1247 *
1248 * Scope of @goal and returned block is just within rgrp, not the whole
1249 * filesystem.
1250 *
1251 * Returns: the block number allocated
1252 */
1253
Steven Whitehousecd915492006-09-04 12:49:07 -04001254static u32 rgblk_search(struct gfs2_rgrpd *rgd, u32 goal,
Steven Whitehouseb45e41d2008-02-06 10:11:15 +00001255 unsigned char old_state, unsigned char new_state,
1256 unsigned int *n)
David Teiglandb3b94fa2006-01-16 16:50:04 +00001257{
1258 struct gfs2_bitmap *bi = NULL;
Steven Whitehouseb45e41d2008-02-06 10:11:15 +00001259 const u32 length = rgd->rd_length;
Steven Whitehousecd915492006-09-04 12:49:07 -04001260 u32 blk = 0;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001261 unsigned int buf, x;
Steven Whitehouseb45e41d2008-02-06 10:11:15 +00001262 const unsigned int elen = *n;
1263 const u8 *buffer;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001264
Steven Whitehouseb45e41d2008-02-06 10:11:15 +00001265 *n = 0;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001266 /* Find bitmap block that contains bits for goal block */
1267 for (buf = 0; buf < length; buf++) {
1268 bi = rgd->rd_bits + buf;
1269 if (goal < (bi->bi_start + bi->bi_len) * GFS2_NBBY)
1270 break;
1271 }
1272
1273 gfs2_assert(rgd->rd_sbd, buf < length);
1274
1275 /* Convert scope of "goal" from rgrp-wide to within found bit block */
1276 goal -= bi->bi_start * GFS2_NBBY;
1277
1278 /* Search (up to entire) bitmap in this rgrp for allocatable block.
1279 "x <= length", instead of "x < length", because we typically start
1280 the search in the middle of a bit block, but if we can't find an
1281 allocatable block anywhere else, we want to be able wrap around and
1282 search in the first part of our first-searched bit block. */
1283 for (x = 0; x <= length; x++) {
Bob Peterson5f3eae72007-08-08 16:52:09 -05001284 /* The GFS2_BLKST_UNLINKED state doesn't apply to the clone
1285 bitmaps, so we must search the originals for that. */
Steven Whitehouseb45e41d2008-02-06 10:11:15 +00001286 buffer = bi->bi_bh->b_data + bi->bi_offset;
Bob Peterson5f3eae72007-08-08 16:52:09 -05001287 if (old_state != GFS2_BLKST_UNLINKED && bi->bi_clone)
Steven Whitehouse110acf32008-01-29 13:30:20 +00001288 buffer = bi->bi_clone + bi->bi_offset;
1289
1290 blk = gfs2_bitfit(buffer, bi->bi_len, goal, old_state);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001291 if (blk != BFITNOENT)
1292 break;
1293
1294 /* Try next bitmap block (wrap back to rgrp header if at end) */
1295 buf = (buf + 1) % length;
1296 bi = rgd->rd_bits + buf;
1297 goal = 0;
1298 }
1299
Bob Peterson6760bdc2007-07-24 14:09:32 -05001300 if (blk != BFITNOENT && old_state != new_state) {
Steven Whitehouseb45e41d2008-02-06 10:11:15 +00001301 *n = 1;
Steven Whitehousec8cdf472007-06-08 10:05:33 +01001302 gfs2_trans_add_bh(rgd->rd_gl, bi->bi_bh, 1);
Steven Whitehouseb45e41d2008-02-06 10:11:15 +00001303 gfs2_setbit(rgd, bi->bi_bh->b_data, bi->bi_clone, bi->bi_offset,
David Teiglandb3b94fa2006-01-16 16:50:04 +00001304 bi->bi_len, blk, new_state);
Steven Whitehouse9b8c81d2008-02-22 16:09:31 +00001305 goal = blk;
1306 while (*n < elen) {
Steven Whitehouseb45e41d2008-02-06 10:11:15 +00001307 goal++;
Steven Whitehouse9b8c81d2008-02-22 16:09:31 +00001308 if (goal >= (bi->bi_len * GFS2_NBBY))
Steven Whitehouseb45e41d2008-02-06 10:11:15 +00001309 break;
1310 if (gfs2_testbit(rgd, buffer, bi->bi_len, goal) !=
1311 GFS2_BLKST_FREE)
1312 break;
Steven Whitehouseb45e41d2008-02-06 10:11:15 +00001313 gfs2_setbit(rgd, bi->bi_bh->b_data, bi->bi_clone,
Steven Whitehouse9b8c81d2008-02-22 16:09:31 +00001314 bi->bi_offset, bi->bi_len, goal,
1315 new_state);
1316 (*n)++;
Steven Whitehouseb45e41d2008-02-06 10:11:15 +00001317 }
Steven Whitehousec8cdf472007-06-08 10:05:33 +01001318 }
David Teiglandb3b94fa2006-01-16 16:50:04 +00001319
Steven Whitehouse6eefaf62007-07-17 10:26:56 +01001320 return (blk == BFITNOENT) ? blk : (bi->bi_start * GFS2_NBBY) + blk;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001321}
1322
1323/**
1324 * rgblk_free - Change alloc state of given block(s)
1325 * @sdp: the filesystem
1326 * @bstart: the start of a run of blocks to free
1327 * @blen: the length of the block run (all must lie within ONE RG!)
1328 * @new_state: GFS2_BLKST_XXX the after-allocation block state
1329 *
1330 * Returns: Resource group containing the block(s)
1331 */
1332
Steven Whitehousecd915492006-09-04 12:49:07 -04001333static struct gfs2_rgrpd *rgblk_free(struct gfs2_sbd *sdp, u64 bstart,
1334 u32 blen, unsigned char new_state)
David Teiglandb3b94fa2006-01-16 16:50:04 +00001335{
1336 struct gfs2_rgrpd *rgd;
1337 struct gfs2_bitmap *bi = NULL;
Steven Whitehousecd915492006-09-04 12:49:07 -04001338 u32 length, rgrp_blk, buf_blk;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001339 unsigned int buf;
1340
1341 rgd = gfs2_blk2rgrpd(sdp, bstart);
1342 if (!rgd) {
1343 if (gfs2_consist(sdp))
Steven Whitehouse382066d2006-05-24 10:22:09 -04001344 fs_err(sdp, "block = %llu\n", (unsigned long long)bstart);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001345 return NULL;
1346 }
1347
Steven Whitehousebb8d8a62007-06-01 14:11:58 +01001348 length = rgd->rd_length;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001349
Steven Whitehousebb8d8a62007-06-01 14:11:58 +01001350 rgrp_blk = bstart - rgd->rd_data0;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001351
1352 while (blen--) {
1353 for (buf = 0; buf < length; buf++) {
1354 bi = rgd->rd_bits + buf;
1355 if (rgrp_blk < (bi->bi_start + bi->bi_len) * GFS2_NBBY)
1356 break;
1357 }
1358
1359 gfs2_assert(rgd->rd_sbd, buf < length);
1360
1361 buf_blk = rgrp_blk - bi->bi_start * GFS2_NBBY;
1362 rgrp_blk++;
1363
1364 if (!bi->bi_clone) {
1365 bi->bi_clone = kmalloc(bi->bi_bh->b_size,
Steven Whitehousedd894be2006-07-27 14:29:00 -04001366 GFP_NOFS | __GFP_NOFAIL);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001367 memcpy(bi->bi_clone + bi->bi_offset,
1368 bi->bi_bh->b_data + bi->bi_offset,
1369 bi->bi_len);
1370 }
Steven Whitehoused4e9c4c2006-01-18 11:19:28 +00001371 gfs2_trans_add_bh(rgd->rd_gl, bi->bi_bh, 1);
Steven Whitehouseb45e41d2008-02-06 10:11:15 +00001372 gfs2_setbit(rgd, bi->bi_bh->b_data, NULL, bi->bi_offset,
David Teiglandb3b94fa2006-01-16 16:50:04 +00001373 bi->bi_len, buf_blk, new_state);
1374 }
1375
1376 return rgd;
1377}
1378
1379/**
Steven Whitehouse16394312008-02-01 14:52:30 +00001380 * gfs2_alloc_block - Allocate a block
1381 * @ip: the inode to allocate the block for
David Teiglandb3b94fa2006-01-16 16:50:04 +00001382 *
1383 * Returns: the allocated block
1384 */
1385
Steven Whitehouseb45e41d2008-02-06 10:11:15 +00001386u64 gfs2_alloc_block(struct gfs2_inode *ip, unsigned int *n)
David Teiglandb3b94fa2006-01-16 16:50:04 +00001387{
Steven Whitehousefeaa7bb2006-06-14 15:32:57 -04001388 struct gfs2_sbd *sdp = GFS2_SB(&ip->i_inode);
Steven Whitehouse6dbd8222008-01-10 15:18:55 +00001389 struct gfs2_alloc *al = ip->i_alloc;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001390 struct gfs2_rgrpd *rgd = al->al_rgd;
Steven Whitehousecd915492006-09-04 12:49:07 -04001391 u32 goal, blk;
1392 u64 block;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001393
Steven Whitehousece276b02008-02-06 09:25:45 +00001394 if (rgrp_contains_block(rgd, ip->i_goal))
1395 goal = ip->i_goal - rgd->rd_data0;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001396 else
Steven Whitehouseac576cc2008-02-01 10:34:15 +00001397 goal = rgd->rd_last_alloc;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001398
Steven Whitehouseb45e41d2008-02-06 10:11:15 +00001399 blk = rgblk_search(rgd, goal, GFS2_BLKST_FREE, GFS2_BLKST_USED, n);
Steven Whitehouse6eefaf62007-07-17 10:26:56 +01001400 BUG_ON(blk == BFITNOENT);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001401
Steven Whitehouseb45e41d2008-02-06 10:11:15 +00001402 rgd->rd_last_alloc = blk;
Steven Whitehousebb8d8a62007-06-01 14:11:58 +01001403 block = rgd->rd_data0 + blk;
Steven Whitehousece276b02008-02-06 09:25:45 +00001404 ip->i_goal = block;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001405
Steven Whitehousecfc8b542008-11-04 10:25:13 +00001406 gfs2_assert_withdraw(sdp, rgd->rd_free >= *n);
1407 rgd->rd_free -= *n;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001408
Steven Whitehoused4e9c4c2006-01-18 11:19:28 +00001409 gfs2_trans_add_bh(rgd->rd_gl, rgd->rd_bits[0].bi_bh, 1);
Bob Peterson42d52e32008-01-28 18:38:07 -06001410 gfs2_rgrp_out(rgd, rgd->rd_bits[0].bi_bh->b_data);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001411
Steven Whitehouseb45e41d2008-02-06 10:11:15 +00001412 al->al_alloced += *n;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001413
Andrew Pricead99f772008-05-01 11:55:38 +01001414 gfs2_statfs_change(sdp, 0, -(s64)*n, 0);
Steven Whitehouseb45e41d2008-02-06 10:11:15 +00001415 gfs2_quota_change(ip, *n, ip->i_inode.i_uid, ip->i_inode.i_gid);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001416
1417 spin_lock(&sdp->sd_rindex_spin);
Steven Whitehouseb45e41d2008-02-06 10:11:15 +00001418 rgd->rd_free_clone -= *n;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001419 spin_unlock(&sdp->sd_rindex_spin);
1420
1421 return block;
1422}
1423
1424/**
1425 * gfs2_alloc_di - Allocate a dinode
1426 * @dip: the directory that the inode is going in
1427 *
1428 * Returns: the block allocated
1429 */
1430
Steven Whitehouse4340fe62006-07-11 09:46:33 -04001431u64 gfs2_alloc_di(struct gfs2_inode *dip, u64 *generation)
David Teiglandb3b94fa2006-01-16 16:50:04 +00001432{
Steven Whitehousefeaa7bb2006-06-14 15:32:57 -04001433 struct gfs2_sbd *sdp = GFS2_SB(&dip->i_inode);
Steven Whitehouse6dbd8222008-01-10 15:18:55 +00001434 struct gfs2_alloc *al = dip->i_alloc;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001435 struct gfs2_rgrpd *rgd = al->al_rgd;
Steven Whitehouse4340fe62006-07-11 09:46:33 -04001436 u32 blk;
1437 u64 block;
Steven Whitehouseb45e41d2008-02-06 10:11:15 +00001438 unsigned int n = 1;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001439
Steven Whitehouseac576cc2008-02-01 10:34:15 +00001440 blk = rgblk_search(rgd, rgd->rd_last_alloc,
Steven Whitehouseb45e41d2008-02-06 10:11:15 +00001441 GFS2_BLKST_FREE, GFS2_BLKST_DINODE, &n);
Steven Whitehouse6eefaf62007-07-17 10:26:56 +01001442 BUG_ON(blk == BFITNOENT);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001443
Steven Whitehouseac576cc2008-02-01 10:34:15 +00001444 rgd->rd_last_alloc = blk;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001445
Steven Whitehousebb8d8a62007-06-01 14:11:58 +01001446 block = rgd->rd_data0 + blk;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001447
Steven Whitehousecfc8b542008-11-04 10:25:13 +00001448 gfs2_assert_withdraw(sdp, rgd->rd_free);
1449 rgd->rd_free--;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001450 rgd->rd_rg.rg_dinodes++;
Steven Whitehoused8b71f72008-11-04 10:19:03 +00001451 *generation = rgd->rd_igeneration++;
Steven Whitehoused4e9c4c2006-01-18 11:19:28 +00001452 gfs2_trans_add_bh(rgd->rd_gl, rgd->rd_bits[0].bi_bh, 1);
Bob Peterson42d52e32008-01-28 18:38:07 -06001453 gfs2_rgrp_out(rgd, rgd->rd_bits[0].bi_bh->b_data);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001454
1455 al->al_alloced++;
1456
1457 gfs2_statfs_change(sdp, 0, -1, +1);
Steven Whitehouse5731be52008-02-01 13:16:55 +00001458 gfs2_trans_add_unrevoke(sdp, block, 1);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001459
1460 spin_lock(&sdp->sd_rindex_spin);
1461 rgd->rd_free_clone--;
1462 spin_unlock(&sdp->sd_rindex_spin);
1463
1464 return block;
1465}
1466
1467/**
1468 * gfs2_free_data - free a contiguous run of data block(s)
1469 * @ip: the inode these blocks are being freed from
1470 * @bstart: first block of a run of contiguous blocks
1471 * @blen: the length of the block run
1472 *
1473 */
1474
Steven Whitehousecd915492006-09-04 12:49:07 -04001475void gfs2_free_data(struct gfs2_inode *ip, u64 bstart, u32 blen)
David Teiglandb3b94fa2006-01-16 16:50:04 +00001476{
Steven Whitehousefeaa7bb2006-06-14 15:32:57 -04001477 struct gfs2_sbd *sdp = GFS2_SB(&ip->i_inode);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001478 struct gfs2_rgrpd *rgd;
1479
1480 rgd = rgblk_free(sdp, bstart, blen, GFS2_BLKST_FREE);
1481 if (!rgd)
1482 return;
1483
Steven Whitehousecfc8b542008-11-04 10:25:13 +00001484 rgd->rd_free += blen;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001485
Steven Whitehoused4e9c4c2006-01-18 11:19:28 +00001486 gfs2_trans_add_bh(rgd->rd_gl, rgd->rd_bits[0].bi_bh, 1);
Bob Peterson42d52e32008-01-28 18:38:07 -06001487 gfs2_rgrp_out(rgd, rgd->rd_bits[0].bi_bh->b_data);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001488
1489 gfs2_trans_add_rg(rgd);
1490
1491 gfs2_statfs_change(sdp, 0, +blen, 0);
Steven Whitehouse2933f922006-11-01 13:23:29 -05001492 gfs2_quota_change(ip, -(s64)blen, ip->i_inode.i_uid, ip->i_inode.i_gid);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001493}
1494
1495/**
1496 * gfs2_free_meta - free a contiguous run of data block(s)
1497 * @ip: the inode these blocks are being freed from
1498 * @bstart: first block of a run of contiguous blocks
1499 * @blen: the length of the block run
1500 *
1501 */
1502
Steven Whitehousecd915492006-09-04 12:49:07 -04001503void gfs2_free_meta(struct gfs2_inode *ip, u64 bstart, u32 blen)
David Teiglandb3b94fa2006-01-16 16:50:04 +00001504{
Steven Whitehousefeaa7bb2006-06-14 15:32:57 -04001505 struct gfs2_sbd *sdp = GFS2_SB(&ip->i_inode);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001506 struct gfs2_rgrpd *rgd;
1507
1508 rgd = rgblk_free(sdp, bstart, blen, GFS2_BLKST_FREE);
1509 if (!rgd)
1510 return;
1511
Steven Whitehousecfc8b542008-11-04 10:25:13 +00001512 rgd->rd_free += blen;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001513
Steven Whitehoused4e9c4c2006-01-18 11:19:28 +00001514 gfs2_trans_add_bh(rgd->rd_gl, rgd->rd_bits[0].bi_bh, 1);
Bob Peterson42d52e32008-01-28 18:38:07 -06001515 gfs2_rgrp_out(rgd, rgd->rd_bits[0].bi_bh->b_data);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001516
1517 gfs2_trans_add_rg(rgd);
1518
1519 gfs2_statfs_change(sdp, 0, +blen, 0);
Steven Whitehouse2933f922006-11-01 13:23:29 -05001520 gfs2_quota_change(ip, -(s64)blen, ip->i_inode.i_uid, ip->i_inode.i_gid);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001521 gfs2_meta_wipe(ip, bstart, blen);
1522}
1523
Steven Whitehousefeaa7bb2006-06-14 15:32:57 -04001524void gfs2_unlink_di(struct inode *inode)
1525{
1526 struct gfs2_inode *ip = GFS2_I(inode);
1527 struct gfs2_sbd *sdp = GFS2_SB(inode);
1528 struct gfs2_rgrpd *rgd;
Steven Whitehousedbb7cae2007-05-15 15:37:50 +01001529 u64 blkno = ip->i_no_addr;
Steven Whitehousefeaa7bb2006-06-14 15:32:57 -04001530
1531 rgd = rgblk_free(sdp, blkno, 1, GFS2_BLKST_UNLINKED);
1532 if (!rgd)
1533 return;
1534 gfs2_trans_add_bh(rgd->rd_gl, rgd->rd_bits[0].bi_bh, 1);
Bob Peterson42d52e32008-01-28 18:38:07 -06001535 gfs2_rgrp_out(rgd, rgd->rd_bits[0].bi_bh->b_data);
Steven Whitehousefeaa7bb2006-06-14 15:32:57 -04001536 gfs2_trans_add_rg(rgd);
1537}
1538
Steven Whitehousecd915492006-09-04 12:49:07 -04001539static void gfs2_free_uninit_di(struct gfs2_rgrpd *rgd, u64 blkno)
David Teiglandb3b94fa2006-01-16 16:50:04 +00001540{
1541 struct gfs2_sbd *sdp = rgd->rd_sbd;
1542 struct gfs2_rgrpd *tmp_rgd;
1543
1544 tmp_rgd = rgblk_free(sdp, blkno, 1, GFS2_BLKST_FREE);
1545 if (!tmp_rgd)
1546 return;
1547 gfs2_assert_withdraw(sdp, rgd == tmp_rgd);
1548
1549 if (!rgd->rd_rg.rg_dinodes)
1550 gfs2_consist_rgrpd(rgd);
1551 rgd->rd_rg.rg_dinodes--;
Steven Whitehousecfc8b542008-11-04 10:25:13 +00001552 rgd->rd_free++;
David Teiglandb3b94fa2006-01-16 16:50:04 +00001553
Steven Whitehoused4e9c4c2006-01-18 11:19:28 +00001554 gfs2_trans_add_bh(rgd->rd_gl, rgd->rd_bits[0].bi_bh, 1);
Bob Peterson42d52e32008-01-28 18:38:07 -06001555 gfs2_rgrp_out(rgd, rgd->rd_bits[0].bi_bh->b_data);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001556
1557 gfs2_statfs_change(sdp, 0, +1, -1);
1558 gfs2_trans_add_rg(rgd);
1559}
1560
David Teiglandb3b94fa2006-01-16 16:50:04 +00001561
1562void gfs2_free_di(struct gfs2_rgrpd *rgd, struct gfs2_inode *ip)
1563{
Steven Whitehousedbb7cae2007-05-15 15:37:50 +01001564 gfs2_free_uninit_di(rgd, ip->i_no_addr);
Steven Whitehouse2933f922006-11-01 13:23:29 -05001565 gfs2_quota_change(ip, -1, ip->i_inode.i_uid, ip->i_inode.i_gid);
Steven Whitehousedbb7cae2007-05-15 15:37:50 +01001566 gfs2_meta_wipe(ip, ip->i_no_addr, 1);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001567}
1568
1569/**
1570 * gfs2_rlist_add - add a RG to a list of RGs
1571 * @sdp: the filesystem
1572 * @rlist: the list of resource groups
1573 * @block: the block
1574 *
1575 * Figure out what RG a block belongs to and add that RG to the list
1576 *
1577 * FIXME: Don't use NOFAIL
1578 *
1579 */
1580
1581void gfs2_rlist_add(struct gfs2_sbd *sdp, struct gfs2_rgrp_list *rlist,
Steven Whitehousecd915492006-09-04 12:49:07 -04001582 u64 block)
David Teiglandb3b94fa2006-01-16 16:50:04 +00001583{
1584 struct gfs2_rgrpd *rgd;
1585 struct gfs2_rgrpd **tmp;
1586 unsigned int new_space;
1587 unsigned int x;
1588
1589 if (gfs2_assert_warn(sdp, !rlist->rl_ghs))
1590 return;
1591
1592 rgd = gfs2_blk2rgrpd(sdp, block);
1593 if (!rgd) {
1594 if (gfs2_consist(sdp))
Steven Whitehouse382066d2006-05-24 10:22:09 -04001595 fs_err(sdp, "block = %llu\n", (unsigned long long)block);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001596 return;
1597 }
1598
1599 for (x = 0; x < rlist->rl_rgrps; x++)
1600 if (rlist->rl_rgd[x] == rgd)
1601 return;
1602
1603 if (rlist->rl_rgrps == rlist->rl_space) {
1604 new_space = rlist->rl_space + 10;
1605
1606 tmp = kcalloc(new_space, sizeof(struct gfs2_rgrpd *),
Steven Whitehousedd894be2006-07-27 14:29:00 -04001607 GFP_NOFS | __GFP_NOFAIL);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001608
1609 if (rlist->rl_rgd) {
1610 memcpy(tmp, rlist->rl_rgd,
1611 rlist->rl_space * sizeof(struct gfs2_rgrpd *));
1612 kfree(rlist->rl_rgd);
1613 }
1614
1615 rlist->rl_space = new_space;
1616 rlist->rl_rgd = tmp;
1617 }
1618
1619 rlist->rl_rgd[rlist->rl_rgrps++] = rgd;
1620}
1621
1622/**
1623 * gfs2_rlist_alloc - all RGs have been added to the rlist, now allocate
1624 * and initialize an array of glock holders for them
1625 * @rlist: the list of resource groups
1626 * @state: the lock state to acquire the RG lock in
1627 * @flags: the modifier flags for the holder structures
1628 *
1629 * FIXME: Don't use NOFAIL
1630 *
1631 */
1632
Bob Petersonfe6c9912008-01-28 11:13:02 -06001633void gfs2_rlist_alloc(struct gfs2_rgrp_list *rlist, unsigned int state)
David Teiglandb3b94fa2006-01-16 16:50:04 +00001634{
1635 unsigned int x;
1636
1637 rlist->rl_ghs = kcalloc(rlist->rl_rgrps, sizeof(struct gfs2_holder),
Steven Whitehousedd894be2006-07-27 14:29:00 -04001638 GFP_NOFS | __GFP_NOFAIL);
David Teiglandb3b94fa2006-01-16 16:50:04 +00001639 for (x = 0; x < rlist->rl_rgrps; x++)
1640 gfs2_holder_init(rlist->rl_rgd[x]->rd_gl,
Bob Petersonfe6c9912008-01-28 11:13:02 -06001641 state, 0,
David Teiglandb3b94fa2006-01-16 16:50:04 +00001642 &rlist->rl_ghs[x]);
1643}
1644
1645/**
1646 * gfs2_rlist_free - free a resource group list
1647 * @list: the list of resource groups
1648 *
1649 */
1650
1651void gfs2_rlist_free(struct gfs2_rgrp_list *rlist)
1652{
1653 unsigned int x;
1654
1655 kfree(rlist->rl_rgd);
1656
1657 if (rlist->rl_ghs) {
1658 for (x = 0; x < rlist->rl_rgrps; x++)
1659 gfs2_holder_uninit(&rlist->rl_ghs[x]);
1660 kfree(rlist->rl_ghs);
1661 }
1662}
1663