aboutsummaryrefslogtreecommitdiffstats
path: root/fs/ocfs2/alloc.h
diff options
context:
space:
mode:
Diffstat (limited to 'fs/ocfs2/alloc.h')
-rw-r--r--fs/ocfs2/alloc.h95
1 files changed, 88 insertions, 7 deletions
diff --git a/fs/ocfs2/alloc.h b/fs/ocfs2/alloc.h
index 42ff94bd8011..70257c84cfbe 100644
--- a/fs/ocfs2/alloc.h
+++ b/fs/ocfs2/alloc.h
@@ -26,30 +26,102 @@
26#ifndef OCFS2_ALLOC_H 26#ifndef OCFS2_ALLOC_H
27#define OCFS2_ALLOC_H 27#define OCFS2_ALLOC_H
28 28
29
30/*
31 * For xattr tree leaf, we limit the leaf byte size to be 64K.
32 */
33#define OCFS2_MAX_XATTR_TREE_LEAF_SIZE 65536
34
35/*
36 * ocfs2_extent_tree and ocfs2_extent_tree_operations are used to abstract
37 * the b-tree operations in ocfs2. Now all the b-tree operations are not
38 * limited to ocfs2_dinode only. Any data which need to allocate clusters
39 * to store can use b-tree. And it only needs to implement its ocfs2_extent_tree
40 * and operation.
41 *
42 * ocfs2_extent_tree becomes the first-class object for extent tree
43 * manipulation. Callers of the alloc.c code need to fill it via one of
44 * the ocfs2_init_*_extent_tree() operations below.
45 *
46 * ocfs2_extent_tree contains info for the root of the b-tree, it must have a
47 * root ocfs2_extent_list and a root_bh so that they can be used in the b-tree
48 * functions.
49 * ocfs2_extent_tree_operations abstract the normal operations we do for
50 * the root of extent b-tree.
51 */
52struct ocfs2_extent_tree_operations;
53struct ocfs2_extent_tree {
54 struct ocfs2_extent_tree_operations *et_ops;
55 struct buffer_head *et_root_bh;
56 struct ocfs2_extent_list *et_root_el;
57 void *et_object;
58 unsigned int et_max_leaf_clusters;
59};
60
61/*
62 * ocfs2_init_*_extent_tree() will fill an ocfs2_extent_tree from the
63 * specified object buffer.
64 */
65void ocfs2_init_dinode_extent_tree(struct ocfs2_extent_tree *et,
66 struct inode *inode,
67 struct buffer_head *bh);
68void ocfs2_init_xattr_tree_extent_tree(struct ocfs2_extent_tree *et,
69 struct inode *inode,
70 struct buffer_head *bh);
71void ocfs2_init_xattr_value_extent_tree(struct ocfs2_extent_tree *et,
72 struct inode *inode,
73 struct buffer_head *bh,
74 struct ocfs2_xattr_value_root *xv);
75
29struct ocfs2_alloc_context; 76struct ocfs2_alloc_context;
30int ocfs2_insert_extent(struct ocfs2_super *osb, 77int ocfs2_insert_extent(struct ocfs2_super *osb,
31 handle_t *handle, 78 handle_t *handle,
32 struct inode *inode, 79 struct inode *inode,
33 struct buffer_head *fe_bh, 80 struct ocfs2_extent_tree *et,
34 u32 cpos, 81 u32 cpos,
35 u64 start_blk, 82 u64 start_blk,
36 u32 new_clusters, 83 u32 new_clusters,
37 u8 flags, 84 u8 flags,
38 struct ocfs2_alloc_context *meta_ac); 85 struct ocfs2_alloc_context *meta_ac);
86
87enum ocfs2_alloc_restarted {
88 RESTART_NONE = 0,
89 RESTART_TRANS,
90 RESTART_META
91};
92int ocfs2_add_clusters_in_btree(struct ocfs2_super *osb,
93 struct inode *inode,
94 u32 *logical_offset,
95 u32 clusters_to_add,
96 int mark_unwritten,
97 struct ocfs2_extent_tree *et,
98 handle_t *handle,
99 struct ocfs2_alloc_context *data_ac,
100 struct ocfs2_alloc_context *meta_ac,
101 enum ocfs2_alloc_restarted *reason_ret);
39struct ocfs2_cached_dealloc_ctxt; 102struct ocfs2_cached_dealloc_ctxt;
40int ocfs2_mark_extent_written(struct inode *inode, struct buffer_head *di_bh, 103int ocfs2_mark_extent_written(struct inode *inode,
104 struct ocfs2_extent_tree *et,
41 handle_t *handle, u32 cpos, u32 len, u32 phys, 105 handle_t *handle, u32 cpos, u32 len, u32 phys,
42 struct ocfs2_alloc_context *meta_ac, 106 struct ocfs2_alloc_context *meta_ac,
43 struct ocfs2_cached_dealloc_ctxt *dealloc); 107 struct ocfs2_cached_dealloc_ctxt *dealloc);
44int ocfs2_remove_extent(struct inode *inode, struct buffer_head *di_bh, 108int ocfs2_remove_extent(struct inode *inode,
109 struct ocfs2_extent_tree *et,
45 u32 cpos, u32 len, handle_t *handle, 110 u32 cpos, u32 len, handle_t *handle,
46 struct ocfs2_alloc_context *meta_ac, 111 struct ocfs2_alloc_context *meta_ac,
47 struct ocfs2_cached_dealloc_ctxt *dealloc); 112 struct ocfs2_cached_dealloc_ctxt *dealloc);
48int ocfs2_num_free_extents(struct ocfs2_super *osb, 113int ocfs2_num_free_extents(struct ocfs2_super *osb,
49 struct inode *inode, 114 struct inode *inode,
50 struct ocfs2_dinode *fe); 115 struct ocfs2_extent_tree *et);
51/* how many new metadata chunks would an allocation need at maximum? */ 116
52static inline int ocfs2_extend_meta_needed(struct ocfs2_dinode *fe) 117/*
118 * how many new metadata chunks would an allocation need at maximum?
119 *
120 * Please note that the caller must make sure that root_el is the root
121 * of extent tree. So for an inode, it should be &fe->id2.i_list. Otherwise
122 * the result may be wrong.
123 */
124static inline int ocfs2_extend_meta_needed(struct ocfs2_extent_list *root_el)
53{ 125{
54 /* 126 /*
55 * Rather than do all the work of determining how much we need 127 * Rather than do all the work of determining how much we need
@@ -59,7 +131,7 @@ static inline int ocfs2_extend_meta_needed(struct ocfs2_dinode *fe)
59 * new tree_depth==0 extent_block, and one block at the new 131 * new tree_depth==0 extent_block, and one block at the new
60 * top-of-the tree. 132 * top-of-the tree.
61 */ 133 */
62 return le16_to_cpu(fe->id2.i_list.l_tree_depth) + 2; 134 return le16_to_cpu(root_el->l_tree_depth) + 2;
63} 135}
64 136
65void ocfs2_dinode_new_extent_list(struct inode *inode, struct ocfs2_dinode *di); 137void ocfs2_dinode_new_extent_list(struct inode *inode, struct ocfs2_dinode *di);
@@ -146,4 +218,13 @@ static inline unsigned int ocfs2_rec_clusters(struct ocfs2_extent_list *el,
146 return le16_to_cpu(rec->e_leaf_clusters); 218 return le16_to_cpu(rec->e_leaf_clusters);
147} 219}
148 220
221/*
222 * This is only valid for leaf nodes, which are the only ones that can
223 * have empty extents anyway.
224 */
225static inline int ocfs2_is_empty_extent(struct ocfs2_extent_rec *rec)
226{
227 return !rec->e_leaf_clusters;
228}
229
149#endif /* OCFS2_ALLOC_H */ 230#endif /* OCFS2_ALLOC_H */