Blame view

fs/btrfs/delayed-ref.h 6 KB
56bec294d   Chris Mason   Btrfs: do extent ...
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
  /*
   * Copyright (C) 2008 Oracle.  All rights reserved.
   *
   * This program is free software; you can redistribute it and/or
   * modify it under the terms of the GNU General Public
   * License v2 as published by the Free Software Foundation.
   *
   * This program is distributed in the hope that it will be useful,
   * but WITHOUT ANY WARRANTY; without even the implied warranty of
   * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
   * General Public License for more details.
   *
   * You should have received a copy of the GNU General Public
   * License along with this program; if not, write to the
   * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
   * Boston, MA 021110-1307, USA.
   */
  #ifndef __DELAYED_REF__
  #define __DELAYED_REF__
  
  /* these are the possible values of struct btrfs_delayed_ref->action */
  #define BTRFS_ADD_DELAYED_REF    1 /* add one backref to the tree */
  #define BTRFS_DROP_DELAYED_REF   2 /* delete one backref from the tree */
  #define BTRFS_ADD_DELAYED_EXTENT 3 /* record a full extent allocation */
1a81af4d1   Chris Mason   Btrfs: make sure ...
25
  #define BTRFS_UPDATE_DELAYED_HEAD 4 /* not changing ref count on head ref */
56bec294d   Chris Mason   Btrfs: do extent ...
26
27
28
29
30
31
  
  struct btrfs_delayed_ref_node {
  	struct rb_node rb_node;
  
  	/* the starting bytenr of the extent */
  	u64 bytenr;
56bec294d   Chris Mason   Btrfs: do extent ...
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
  	/* the size of the extent */
  	u64 num_bytes;
  
  	/* ref count on this data structure */
  	atomic_t refs;
  
  	/*
  	 * how many refs is this entry adding or deleting.  For
  	 * head refs, this may be a negative number because it is keeping
  	 * track of the total mods done to the reference count.
  	 * For individual refs, this will always be a positive number
  	 *
  	 * It may be more than one, since it is possible for a single
  	 * parent to have more than one ref on an extent
  	 */
  	int ref_mod;
5d4f98a28   Yan Zheng   Btrfs: Mixed back...
48
49
  	unsigned int action:8;
  	unsigned int type:8;
56bec294d   Chris Mason   Btrfs: do extent ...
50
  	/* is this node still in the rbtree? */
5d4f98a28   Yan Zheng   Btrfs: Mixed back...
51
  	unsigned int is_head:1;
56bec294d   Chris Mason   Btrfs: do extent ...
52
53
  	unsigned int in_tree:1;
  };
5d4f98a28   Yan Zheng   Btrfs: Mixed back...
54
55
56
57
58
59
60
  struct btrfs_delayed_extent_op {
  	struct btrfs_disk_key key;
  	u64 flags_to_set;
  	unsigned int update_key:1;
  	unsigned int update_flags:1;
  	unsigned int is_data:1;
  };
56bec294d   Chris Mason   Btrfs: do extent ...
61
62
63
64
65
66
67
68
69
70
71
72
73
74
  /*
   * the head refs are used to hold a lock on a given extent, which allows us
   * to make sure that only one process is running the delayed refs
   * at a time for a single extent.  They also store the sum of all the
   * reference count modifications we've queued up.
   */
  struct btrfs_delayed_ref_head {
  	struct btrfs_delayed_ref_node node;
  
  	/*
  	 * the mutex is held while running the refs, and it is also
  	 * held when checking the sum of reference modifications.
  	 */
  	struct mutex mutex;
c3e69d58e   Chris Mason   Btrfs: process th...
75
  	struct list_head cluster;
5d4f98a28   Yan Zheng   Btrfs: Mixed back...
76
  	struct btrfs_delayed_extent_op *extent_op;
56bec294d   Chris Mason   Btrfs: do extent ...
77
78
79
80
81
82
83
84
85
86
87
88
89
  	/*
  	 * when a new extent is allocated, it is just reserved in memory
  	 * The actual extent isn't inserted into the extent allocation tree
  	 * until the delayed ref is processed.  must_insert_reserved is
  	 * used to flag a delayed ref so the accounting can be updated
  	 * when a full insert is done.
  	 *
  	 * It is possible the extent will be freed before it is ever
  	 * inserted into the extent allocation tree.  In this case
  	 * we need to update the in ram accounting to properly reflect
  	 * the free has happened.
  	 */
  	unsigned int must_insert_reserved:1;
5d4f98a28   Yan Zheng   Btrfs: Mixed back...
90
  	unsigned int is_data:1;
56bec294d   Chris Mason   Btrfs: do extent ...
91
  };
5d4f98a28   Yan Zheng   Btrfs: Mixed back...
92
  struct btrfs_delayed_tree_ref {
56bec294d   Chris Mason   Btrfs: do extent ...
93
  	struct btrfs_delayed_ref_node node;
5d4f98a28   Yan Zheng   Btrfs: Mixed back...
94
95
96
97
98
99
  	union {
  		u64 root;
  		u64 parent;
  	};
  	int level;
  };
56bec294d   Chris Mason   Btrfs: do extent ...
100

5d4f98a28   Yan Zheng   Btrfs: Mixed back...
101
102
103
104
105
106
107
108
  struct btrfs_delayed_data_ref {
  	struct btrfs_delayed_ref_node node;
  	union {
  		u64 root;
  		u64 parent;
  	};
  	u64 objectid;
  	u64 offset;
56bec294d   Chris Mason   Btrfs: do extent ...
109
110
111
112
113
114
115
116
117
118
119
120
  };
  
  struct btrfs_delayed_ref_root {
  	struct rb_root root;
  
  	/* this spin lock protects the rbtree and the entries inside */
  	spinlock_t lock;
  
  	/* how many delayed ref updates we've queued, used by the
  	 * throttling code
  	 */
  	unsigned long num_entries;
c3e69d58e   Chris Mason   Btrfs: process th...
121
122
123
124
125
  	/* total number of head nodes in tree */
  	unsigned long num_heads;
  
  	/* total number of head nodes ready for processing */
  	unsigned long num_heads_ready;
56bec294d   Chris Mason   Btrfs: do extent ...
126
127
128
129
130
131
  	/*
  	 * set when the tree is flushing before a transaction commit,
  	 * used by the throttling code to decide if new updates need
  	 * to be run right away
  	 */
  	int flushing;
c3e69d58e   Chris Mason   Btrfs: process th...
132
133
  
  	u64 run_delayed_start;
56bec294d   Chris Mason   Btrfs: do extent ...
134
135
136
137
138
139
140
141
142
143
  };
  
  static inline void btrfs_put_delayed_ref(struct btrfs_delayed_ref_node *ref)
  {
  	WARN_ON(atomic_read(&ref->refs) == 0);
  	if (atomic_dec_and_test(&ref->refs)) {
  		WARN_ON(ref->in_tree);
  		kfree(ref);
  	}
  }
5d4f98a28   Yan Zheng   Btrfs: Mixed back...
144
145
146
147
148
149
150
151
152
153
154
155
  int btrfs_add_delayed_tree_ref(struct btrfs_trans_handle *trans,
  			       u64 bytenr, u64 num_bytes, u64 parent,
  			       u64 ref_root, int level, int action,
  			       struct btrfs_delayed_extent_op *extent_op);
  int btrfs_add_delayed_data_ref(struct btrfs_trans_handle *trans,
  			       u64 bytenr, u64 num_bytes,
  			       u64 parent, u64 ref_root,
  			       u64 owner, u64 offset, int action,
  			       struct btrfs_delayed_extent_op *extent_op);
  int btrfs_add_delayed_extent_op(struct btrfs_trans_handle *trans,
  				u64 bytenr, u64 num_bytes,
  				struct btrfs_delayed_extent_op *extent_op);
56bec294d   Chris Mason   Btrfs: do extent ...
156

1887be66d   Chris Mason   Btrfs: try to cle...
157
158
  struct btrfs_delayed_ref_head *
  btrfs_find_delayed_ref_head(struct btrfs_trans_handle *trans, u64 bytenr);
c3e69d58e   Chris Mason   Btrfs: process th...
159
160
161
162
  int btrfs_delayed_ref_lock(struct btrfs_trans_handle *trans,
  			   struct btrfs_delayed_ref_head *head);
  int btrfs_find_ref_cluster(struct btrfs_trans_handle *trans,
  			   struct list_head *cluster, u64 search_start);
56bec294d   Chris Mason   Btrfs: do extent ...
163
164
165
166
167
168
  /*
   * a node might live in a head or a regular ref, this lets you
   * test for the proper type to use.
   */
  static int btrfs_delayed_ref_is_head(struct btrfs_delayed_ref_node *node)
  {
5d4f98a28   Yan Zheng   Btrfs: Mixed back...
169
  	return node->is_head;
56bec294d   Chris Mason   Btrfs: do extent ...
170
171
172
173
174
  }
  
  /*
   * helper functions to cast a node into its container
   */
5d4f98a28   Yan Zheng   Btrfs: Mixed back...
175
176
  static inline struct btrfs_delayed_tree_ref *
  btrfs_delayed_node_to_tree_ref(struct btrfs_delayed_ref_node *node)
56bec294d   Chris Mason   Btrfs: do extent ...
177
178
  {
  	WARN_ON(btrfs_delayed_ref_is_head(node));
5d4f98a28   Yan Zheng   Btrfs: Mixed back...
179
180
  	return container_of(node, struct btrfs_delayed_tree_ref, node);
  }
56bec294d   Chris Mason   Btrfs: do extent ...
181

5d4f98a28   Yan Zheng   Btrfs: Mixed back...
182
183
184
185
186
  static inline struct btrfs_delayed_data_ref *
  btrfs_delayed_node_to_data_ref(struct btrfs_delayed_ref_node *node)
  {
  	WARN_ON(btrfs_delayed_ref_is_head(node));
  	return container_of(node, struct btrfs_delayed_data_ref, node);
56bec294d   Chris Mason   Btrfs: do extent ...
187
188
189
190
191
192
193
  }
  
  static inline struct btrfs_delayed_ref_head *
  btrfs_delayed_node_to_head(struct btrfs_delayed_ref_node *node)
  {
  	WARN_ON(!btrfs_delayed_ref_is_head(node));
  	return container_of(node, struct btrfs_delayed_ref_head, node);
56bec294d   Chris Mason   Btrfs: do extent ...
194
195
  }
  #endif