Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
xiphi1978
linux
提交
74493f7a
L
linux
项目概览
xiphi1978
/
linux
通知
2
Star
0
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
L
linux
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
提交
Issue看板
体验新版 GitCode,发现更多精彩内容 >>
提交
74493f7a
编写于
12月 11, 2007
作者:
C
Chris Mason
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
Btrfs: Implement generation numbers in block pointers
Signed-off-by:
N
Chris Mason
<
chris.mason@oracle.com
>
上级
17636e03
变更
3
隐藏空白更改
内联
并排
Showing
3 changed file
with
115 addition
and
8 deletion
+115
-8
fs/btrfs/ctree.c
fs/btrfs/ctree.c
+16
-0
fs/btrfs/ctree.h
fs/btrfs/ctree.h
+41
-6
fs/btrfs/extent-tree.c
fs/btrfs/extent-tree.c
+58
-2
未找到文件。
fs/btrfs/ctree.c
浏览文件 @
74493f7a
...
...
@@ -114,6 +114,9 @@ static int __btrfs_cow_block(struct btrfs_trans_handle *trans,
}
else
{
btrfs_set_node_blockptr
(
parent
,
parent_slot
,
cow
->
start
);
WARN_ON
(
trans
->
transid
==
0
);
btrfs_set_node_ptr_generation
(
parent
,
parent_slot
,
trans
->
transid
);
btrfs_mark_buffer_dirty
(
parent
);
WARN_ON
(
btrfs_header_generation
(
parent
)
!=
trans
->
transid
);
btrfs_free_extent
(
trans
,
root
,
buf
->
start
,
buf
->
len
,
1
);
...
...
@@ -967,6 +970,7 @@ int btrfs_search_slot(struct btrfs_trans_handle *trans, struct btrfs_root
{
struct
extent_buffer
*
b
;
u64
bytenr
;
u64
ptr_gen
;
int
slot
;
int
ret
;
int
level
;
...
...
@@ -1031,10 +1035,18 @@ int btrfs_search_slot(struct btrfs_trans_handle *trans, struct btrfs_root
if
(
level
==
lowest_level
)
break
;
bytenr
=
btrfs_node_blockptr
(
b
,
slot
);
ptr_gen
=
btrfs_node_ptr_generation
(
b
,
slot
);
if
(
should_reada
)
reada_for_search
(
root
,
p
,
level
,
slot
);
b
=
read_tree_block
(
root
,
bytenr
,
btrfs_level_size
(
root
,
level
-
1
));
if
(
ptr_gen
!=
btrfs_header_generation
(
b
))
{
printk
(
"block %llu bad gen wanted %llu "
"found %llu
\n
"
,
(
unsigned
long
long
)
b
->
start
,
(
unsigned
long
long
)
ptr_gen
,
(
unsigned
long
long
)
btrfs_header_generation
(
b
));
}
}
else
{
p
->
slots
[
level
]
=
slot
;
if
(
ins_len
>
0
&&
btrfs_leaf_free_space
(
root
,
b
)
<
...
...
@@ -1218,6 +1230,8 @@ static int insert_new_root(struct btrfs_trans_handle *trans,
btrfs_node_key
(
lower
,
&
lower_key
,
0
);
btrfs_set_node_key
(
c
,
&
lower_key
,
0
);
btrfs_set_node_blockptr
(
c
,
0
,
lower
->
start
);
WARN_ON
(
btrfs_header_generation
(
lower
)
==
0
);
btrfs_set_node_ptr_generation
(
c
,
0
,
btrfs_header_generation
(
lower
));
btrfs_mark_buffer_dirty
(
c
);
...
...
@@ -1261,6 +1275,8 @@ static int insert_ptr(struct btrfs_trans_handle *trans, struct btrfs_root
}
btrfs_set_node_key
(
lower
,
key
,
slot
);
btrfs_set_node_blockptr
(
lower
,
slot
,
bytenr
);
WARN_ON
(
trans
->
transid
==
0
);
btrfs_set_node_ptr_generation
(
lower
,
slot
,
trans
->
transid
);
btrfs_set_header_nritems
(
lower
,
nritems
+
1
);
btrfs_mark_buffer_dirty
(
lower
);
return
0
;
...
...
fs/btrfs/ctree.h
浏览文件 @
74493f7a
...
...
@@ -110,7 +110,7 @@ struct btrfs_header {
#define BTRFS_MAX_LEVEL 8
#define BTRFS_NODEPTRS_PER_BLOCK(r) (((r)->nodesize - \
sizeof(struct btrfs_header)) / \
(sizeof(struct btrfs_disk_key) + sizeof(u64)
))
sizeof(struct btrfs_key_ptr
))
#define __BTRFS_LEAF_DATA_SIZE(bs) ((bs) - sizeof(struct btrfs_header))
#define BTRFS_LEAF_DATA_SIZE(r) (__BTRFS_LEAF_DATA_SIZE(r->leafsize))
#define BTRFS_MAX_INLINE_DATA_SIZE(r) (BTRFS_LEAF_DATA_SIZE(r) - \
...
...
@@ -168,6 +168,7 @@ struct btrfs_leaf {
struct
btrfs_key_ptr
{
struct
btrfs_disk_key
key
;
__le64
blockptr
;
__le64
generation
;
}
__attribute__
((
__packed__
));
struct
btrfs_node
{
...
...
@@ -196,7 +197,13 @@ struct btrfs_path {
*/
struct
btrfs_extent_item
{
__le32
refs
;
__le64
owner
;
}
__attribute__
((
__packed__
));
struct
btrfs_extent_ref
{
__le64
root
;
__le64
generation
;
__le64
objectid
;
__le64
offset
;
}
__attribute__
((
__packed__
));
struct
btrfs_inode_timespec
{
...
...
@@ -402,12 +409,13 @@ struct btrfs_root {
* are used, and how many references there are to each block
*/
#define BTRFS_EXTENT_ITEM_KEY 33
#define BTRFS_EXTENT_REF_KEY 34
/*
* block groups give us hints into the extent allocation trees. Which
* blocks are free etc etc
*/
#define BTRFS_BLOCK_GROUP_ITEM_KEY
34
#define BTRFS_BLOCK_GROUP_ITEM_KEY
50
/*
* string items are for debugging. They just store a short string of
...
...
@@ -529,15 +537,25 @@ BTRFS_SETGET_FUNCS(timespec_nsec, struct btrfs_inode_timespec, nsec, 32);
/* struct btrfs_extent_item */
BTRFS_SETGET_FUNCS
(
extent_refs
,
struct
btrfs_extent_item
,
refs
,
32
);
BTRFS_SETGET_FUNCS
(
extent_owner
,
struct
btrfs_extent_item
,
owner
,
64
);
/* struct btrfs_extent_ref */
BTRFS_SETGET_FUNCS
(
ref_root
,
struct
btrfs_extent_ref
,
root
,
64
);
BTRFS_SETGET_FUNCS
(
ref_generation
,
struct
btrfs_extent_ref
,
generation
,
64
);
BTRFS_SETGET_FUNCS
(
ref_objectid
,
struct
btrfs_extent_ref
,
objectid
,
64
);
BTRFS_SETGET_FUNCS
(
ref_offset
,
struct
btrfs_extent_ref
,
offset
,
64
);
BTRFS_SETGET_STACK_FUNCS
(
ref_root
,
struct
btrfs_extent_ref
,
root
,
64
);
BTRFS_SETGET_STACK_FUNCS
(
ref_generation
,
struct
btrfs_extent_ref
,
generation
,
64
);
BTRFS_SETGET_STACK_FUNCS
(
ref_objectid
,
struct
btrfs_extent_ref
,
objectid
,
64
);
BTRFS_SETGET_STACK_FUNCS
(
ref_offset
,
struct
btrfs_extent_ref
,
offset
,
64
);
BTRFS_SETGET_STACK_FUNCS
(
stack_extent_refs
,
struct
btrfs_extent_item
,
refs
,
32
);
BTRFS_SETGET_STACK_FUNCS
(
stack_extent_owner
,
struct
btrfs_extent_item
,
owner
,
64
);
/* struct btrfs_node */
BTRFS_SETGET_FUNCS
(
key_blockptr
,
struct
btrfs_key_ptr
,
blockptr
,
64
);
BTRFS_SETGET_FUNCS
(
key_generation
,
struct
btrfs_key_ptr
,
generation
,
64
);
static
inline
u64
btrfs_node_blockptr
(
struct
extent_buffer
*
eb
,
int
nr
)
{
...
...
@@ -556,6 +574,23 @@ static inline void btrfs_set_node_blockptr(struct extent_buffer *eb,
btrfs_set_key_blockptr
(
eb
,
(
struct
btrfs_key_ptr
*
)
ptr
,
val
);
}
static
inline
u64
btrfs_node_ptr_generation
(
struct
extent_buffer
*
eb
,
int
nr
)
{
unsigned
long
ptr
;
ptr
=
offsetof
(
struct
btrfs_node
,
ptrs
)
+
sizeof
(
struct
btrfs_key_ptr
)
*
nr
;
return
btrfs_key_generation
(
eb
,
(
struct
btrfs_key_ptr
*
)
ptr
);
}
static
inline
void
btrfs_set_node_ptr_generation
(
struct
extent_buffer
*
eb
,
int
nr
,
u64
val
)
{
unsigned
long
ptr
;
ptr
=
offsetof
(
struct
btrfs_node
,
ptrs
)
+
sizeof
(
struct
btrfs_key_ptr
)
*
nr
;
btrfs_set_key_generation
(
eb
,
(
struct
btrfs_key_ptr
*
)
ptr
,
val
);
}
static
inline
unsigned
long
btrfs_node_key_ptr_offset
(
int
nr
)
{
return
offsetof
(
struct
btrfs_node
,
ptrs
)
+
...
...
fs/btrfs/extent-tree.c
浏览文件 @
74493f7a
...
...
@@ -17,6 +17,7 @@
*/
#include <linux/sched.h>
#include "hash.h"
#include "ctree.h"
#include "disk-io.h"
#include "print-tree.h"
...
...
@@ -352,9 +353,63 @@ struct btrfs_block_group_cache *btrfs_find_block_group(struct btrfs_root *root,
return
found_group
;
}
static
u64
hash_extent_ref
(
u64
root_objectid
,
u64
root_generation
,
u64
owner
,
u64
owner_offset
)
{
u32
high_crc
=
~
(
u32
)
0
;
u32
low_crc
=
~
(
u32
)
0
;
__le64
lenum
;
lenum
=
cpu_to_le64
(
root_objectid
);
high_crc
=
crc32c
(
high_crc
,
&
lenum
,
sizeof
(
lenum
));
lenum
=
cpu_to_le64
(
root_generation
);
high_crc
=
crc32c
(
high_crc
,
&
lenum
,
sizeof
(
lenum
));
lenum
=
cpu_to_le64
(
owner
);
low_crc
=
crc32c
(
low_crc
,
&
lenum
,
sizeof
(
lenum
));
lenum
=
cpu_to_le64
(
owner_offset
);
low_crc
=
crc32c
(
low_crc
,
&
lenum
,
sizeof
(
lenum
));
return
((
u64
)
high_crc
<<
32
)
|
(
u64
)
low_crc
;
}
int
insert_extent_ref
(
struct
btrfs_trans_handle
*
trans
,
struct
btrfs_root
*
root
,
struct
btrfs_path
*
path
,
u64
bytenr
,
u64
root_objectid
,
u64
root_generation
,
u64
owner
,
u64
owner_offset
)
{
u64
hash
;
struct
btrfs_key
key
;
struct
btrfs_extent_ref
ref
;
struct
extent_buffer
*
l
;
struct
btrfs_extent_item
*
item
;
int
ret
;
btrfs_set_stack_ref_root
(
&
ref
,
root_objectid
);
btrfs_set_stack_ref_generation
(
&
ref
,
root_generation
);
btrfs_set_stack_ref_objectid
(
&
ref
,
owner
);
btrfs_set_stack_ref_offset
(
&
ref
,
owner_offset
);
ret
=
btrfs_name_hash
(
&
ref
,
sizeof
(
ref
),
&
hash
);
key
.
offset
=
hash
;
key
.
objectid
=
bytenr
;
key
.
type
=
BTRFS_EXTENT_REF_KEY
;
ret
=
btrfs_insert_empty_item
(
trans
,
root
,
path
,
&
key
,
sizeof
(
ref
));
while
(
ret
==
-
EEXIST
)
{
}
}
int
btrfs_inc_extent_ref
(
struct
btrfs_trans_handle
*
trans
,
struct
btrfs_root
*
root
,
u64
bytenr
,
u64
num_bytes
)
u64
bytenr
,
u64
num_bytes
,
u64
root_objectid
,
u64
root_generation
,
u64
owner
,
u64
owner_offset
)
{
struct
btrfs_path
*
path
;
int
ret
;
...
...
@@ -386,9 +441,10 @@ int btrfs_inc_extent_ref(struct btrfs_trans_handle *trans,
btrfs_mark_buffer_dirty
(
path
->
nodes
[
0
]);
btrfs_release_path
(
root
->
fs_info
->
extent_root
,
path
);
btrfs_free_path
(
path
);
finish_current_insert
(
trans
,
root
->
fs_info
->
extent_root
);
del_pending_extents
(
trans
,
root
->
fs_info
->
extent_root
);
btrfs_free_path
(
path
);
return
0
;
}
...
...
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录