ctree.h 7.9 KB
Newer Older
1 2 3
#ifndef __CTREE__
#define __CTREE__

4
#include "list.h"
C
Chris Mason 已提交
5
#include "kerncompat.h"
6

7
#define CTREE_BLOCKSIZE 1024
8

9 10 11 12 13 14 15 16 17
/*
 * the key defines the order in the tree, and so it also defines (optimal)
 * block layout.  objectid corresonds to the inode number.  The flags
 * tells us things about the object, and is a kind of stream selector.
 * so for a given inode, keys with flags of 1 might refer to the inode
 * data, flags of 2 may point to file data in the btree and flags == 3
 * may point to extents.
 *
 * offset is the starting byte offset for this key in the stream.
C
Chris Mason 已提交
18 19 20 21
 *
 * btrfs_disk_key is in disk byte order.  struct btrfs_key is always
 * in cpu native order.  Otherwise they are identical and their sizes
 * should be the same (ie both packed)
22
 */
C
Chris Mason 已提交
23 24 25 26 27 28 29
struct btrfs_disk_key {
	__le64 objectid;
	__le32 flags;
	__le64 offset;
} __attribute__ ((__packed__));

struct btrfs_key {
30 31 32 33 34
	u64 objectid;
	u32 flags;
	u64 offset;
} __attribute__ ((__packed__));

35 36 37
/*
 * every tree block (leaf or node) starts with this header.
 */
38 39 40 41 42 43 44 45
struct btrfs_header {
	__le64 fsid[2]; /* FS specific uuid */
	__le64 blocknr; /* which block this node is supposed to live in */
	__le64 parentid; /* objectid of the tree root */
	__le32 csum;
	__le32 ham;
	__le16 nritems;
	__le16 flags;
46
	/* generation flags to be added */
47 48
} __attribute__ ((__packed__));

49
#define MAX_LEVEL 8
50
#define NODEPTRS_PER_BLOCK ((CTREE_BLOCKSIZE - sizeof(struct btrfs_header)) / \
C
Chris Mason 已提交
51
			    (sizeof(struct btrfs_disk_key) + sizeof(u64)))
52 53

struct tree_buffer;
54

55 56 57 58 59
/*
 * in ram representation of the tree.  extent_root is used for all allocations
 * and for the extent tree extent_root root.  current_insert is used
 * only for the extent tree.
 */
60 61
struct ctree_root {
	struct tree_buffer *node;
62
	struct tree_buffer *commit_root;
63
	struct ctree_root *extent_root;
C
Chris Mason 已提交
64 65
	struct btrfs_key current_insert;
	struct btrfs_key last_insert;
66 67
	int fp;
	struct radix_tree_root cache_radix;
68
	struct radix_tree_root pinned_radix;
69 70 71
	struct list_head trans;
	struct list_head cache;
	int cache_size;
72 73
};

74 75 76
/*
 * describes a tree on disk
 */
77 78 79 80
struct ctree_root_info {
	u64 fsid[2]; /* FS specific uuid */
	u64 blocknr; /* blocknr of this block */
	u64 objectid; /* inode number of this root */
81
	u64 tree_root; /* the tree root block */
82 83 84 85 86
	u32 csum;
	u32 ham;
	u64 snapuuid[2]; /* root specific uuid */
} __attribute__ ((__packed__));

87 88 89 90
/*
 * the super block basically lists the main trees of the FS
 * it currently lacks any block count etc etc
 */
C
Chris Mason 已提交
91 92 93 94 95
struct ctree_super_block {
	struct ctree_root_info root_info;
	struct ctree_root_info extent_info;
} __attribute__ ((__packed__));

96 97 98 99 100
/*
 * A leaf is full of items.  The exact type of item is defined by
 * the key flags parameter.  offset and size tell us where to find
 * the item in the leaf (relative to the start of the data area)
 */
C
Chris Mason 已提交
101
struct btrfs_item {
C
Chris Mason 已提交
102
	struct btrfs_disk_key key;
C
Chris Mason 已提交
103 104
	__le16 offset;
	__le16 size;
105 106
} __attribute__ ((__packed__));

107 108 109 110 111 112 113
/*
 * leaves have an item area and a data area:
 * [item0, item1....itemN] [free space] [dataN...data1, data0]
 *
 * The data is separate from the items to get the keys closer together
 * during searches.
 */
114
#define LEAF_DATA_SIZE (CTREE_BLOCKSIZE - sizeof(struct btrfs_header))
115
struct leaf {
116
	struct btrfs_header header;
117
	union {
C
Chris Mason 已提交
118 119
		struct btrfs_item items[LEAF_DATA_SIZE/
				        sizeof(struct btrfs_item)];
120
		u8 data[CTREE_BLOCKSIZE-sizeof(struct btrfs_header)];
121 122 123
	};
} __attribute__ ((__packed__));

124 125 126 127
/*
 * all non-leaf blocks are nodes, they hold only keys and pointers to
 * other blocks
 */
128
struct node {
129
	struct btrfs_header header;
C
Chris Mason 已提交
130
	struct btrfs_disk_key keys[NODEPTRS_PER_BLOCK];
131 132 133
	u64 blockptrs[NODEPTRS_PER_BLOCK];
} __attribute__ ((__packed__));

134 135 136 137
/*
 * items in the extent btree are used to record the objectid of the
 * owner of the block and the number of references
 */
138 139 140 141 142
struct extent_item {
	u32 refs;
	u64 owner;
} __attribute__ ((__packed__));

143 144 145 146 147 148 149 150
/*
 * ctree_paths remember the path taken from the root down to the leaf.
 * level 0 is always the leaf, and nodes[1...MAX_LEVEL] will point
 * to any other levels that are present.
 *
 * The slots array records the index of the item or block pointer
 * used while walking the tree.
 */
151 152 153 154
struct ctree_path {
	struct tree_buffer *nodes[MAX_LEVEL];
	int slots[MAX_LEVEL];
};
C
Chris Mason 已提交
155

C
Chris Mason 已提交
156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180
static inline u16 btrfs_item_offset(struct btrfs_item *item)
{
	return le16_to_cpu(item->offset);
}

static inline void btrfs_set_item_offset(struct btrfs_item *item, u16 val)
{
	item->offset = cpu_to_le16(val);
}

static inline u16 btrfs_item_end(struct btrfs_item *item)
{
	return le16_to_cpu(item->offset) + le16_to_cpu(item->size);
}

static inline u16 btrfs_item_size(struct btrfs_item *item)
{
	return le16_to_cpu(item->size);
}

static inline void btrfs_set_item_size(struct btrfs_item *item, u16 val)
{
	item->size = cpu_to_le16(val);
}

C
Chris Mason 已提交
181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229
static inline void btrfs_disk_key_to_cpu(struct btrfs_key *cpu,
					 struct btrfs_disk_key *disk)
{
	cpu->offset = le64_to_cpu(disk->offset);
	cpu->flags = le32_to_cpu(disk->flags);
	cpu->objectid = le64_to_cpu(disk->objectid);
}

static inline void btrfs_cpu_key_to_disk(struct btrfs_disk_key *disk,
					 struct btrfs_key *cpu)
{
	disk->offset = cpu_to_le64(cpu->offset);
	disk->flags = cpu_to_le32(cpu->flags);
	disk->objectid = cpu_to_le64(cpu->objectid);
}

static inline u64 btrfs_key_objectid(struct btrfs_disk_key *disk)
{
	return le64_to_cpu(disk->objectid);
}

static inline void btrfs_set_key_objectid(struct btrfs_disk_key *disk,
					  u64 val)
{
	disk->objectid = cpu_to_le64(val);
}

static inline u64 btrfs_key_offset(struct btrfs_disk_key *disk)
{
	return le64_to_cpu(disk->offset);
}

static inline void btrfs_set_key_offset(struct btrfs_disk_key *disk,
					  u64 val)
{
	disk->offset = cpu_to_le64(val);
}

static inline u32 btrfs_key_flags(struct btrfs_disk_key *disk)
{
	return le32_to_cpu(disk->flags);
}

static inline void btrfs_set_key_flags(struct btrfs_disk_key *disk,
					  u32 val)
{
	disk->flags = cpu_to_le32(val);
}

230
static inline u64 btrfs_header_blocknr(struct btrfs_header *h)
231
{
232
	return le64_to_cpu(h->blocknr);
233 234
}

235
static inline void btrfs_set_header_blocknr(struct btrfs_header *h, u64 blocknr)
236
{
237
	h->blocknr = cpu_to_le64(blocknr);
238 239
}

240
static inline u64 btrfs_header_parentid(struct btrfs_header *h)
241
{
242
	return le64_to_cpu(h->parentid);
243 244
}

245 246
static inline void btrfs_set_header_parentid(struct btrfs_header *h,
					     u64 parentid)
247
{
248
	h->parentid = cpu_to_le64(parentid);
249 250
}

251
static inline u16 btrfs_header_nritems(struct btrfs_header *h)
252
{
253
	return le16_to_cpu(h->nritems);
254 255
}

256
static inline void btrfs_set_header_nritems(struct btrfs_header *h, u16 val)
257
{
258
	h->nritems = cpu_to_le16(val);
259 260
}

261
static inline u16 btrfs_header_flags(struct btrfs_header *h)
262
{
263
	return le16_to_cpu(h->flags);
264 265
}

266
static inline void btrfs_set_header_flags(struct btrfs_header *h, u16 val)
267
{
268
	h->flags = cpu_to_le16(val);
269 270
}

271
static inline int btrfs_header_level(struct btrfs_header *h)
272 273 274 275
{
	return btrfs_header_flags(h) & (MAX_LEVEL - 1);
}

276
static inline void btrfs_set_header_level(struct btrfs_header *h, int level)
277
{
278
	u16 flags;
279 280 281 282 283 284 285 286 287 288
	BUG_ON(level > MAX_LEVEL);
	flags = btrfs_header_flags(h) & ~(MAX_LEVEL - 1);
	btrfs_set_header_flags(h, flags | level);
}

static inline int btrfs_is_leaf(struct node *n)
{
	return (btrfs_header_level(&n->header) == 0);
}

C
Chris Mason 已提交
289
struct tree_buffer *alloc_free_block(struct ctree_root *root);
C
Chris Mason 已提交
290
int btrfs_inc_ref(struct ctree_root *root, struct tree_buffer *buf);
C
Chris Mason 已提交
291
int free_extent(struct ctree_root *root, u64 blocknr, u64 num_blocks);
C
Chris Mason 已提交
292 293
int search_slot(struct ctree_root *root, struct btrfs_key *key,
		struct ctree_path *p, int ins_len, int cow);
C
Chris Mason 已提交
294 295 296
void release_path(struct ctree_root *root, struct ctree_path *p);
void init_path(struct ctree_path *p);
int del_item(struct ctree_root *root, struct ctree_path *path);
C
Chris Mason 已提交
297 298
int insert_item(struct ctree_root *root, struct btrfs_key *key,
		void *data, int data_size);
C
Chris Mason 已提交
299 300
int next_leaf(struct ctree_root *root, struct ctree_path *path);
int leaf_free_space(struct leaf *leaf);
301 302
int btrfs_drop_snapshot(struct ctree_root *root, struct tree_buffer *snap);
int btrfs_finish_extent_commit(struct ctree_root *root);
303
#endif