* [PATCH 0/3] Extent buffer accessor macros cleanup
@ 2019-08-20 16:58 David Sterba
2019-08-20 16:58 ` [PATCH 1/3] btrfs: define separate btrfs_set/get_XX helpers David Sterba
` (2 more replies)
0 siblings, 3 replies; 4+ messages in thread
From: David Sterba @ 2019-08-20 16:58 UTC (permalink / raw)
To: linux-btrfs; +Cc: David Sterba
Remove some conditions from eb accessors, eg. when the token pointer is
known to be valid, or when the eb/token pair does not change inside the
functions.
David Sterba (3):
btrfs: define separate btrfs_set/get_XX helpers
btrfs: assume valid token for btrfs_set/get_token helpers
btrfs: tie extent buffer and it's token together
fs/btrfs/ctree.c | 27 +++++++--------
fs/btrfs/ctree.h | 19 ++++-------
fs/btrfs/inode.c | 2 +-
fs/btrfs/struct-funcs.c | 73 ++++++++++++++++++++++++++++++++++-------
fs/btrfs/tree-log.c | 7 ++--
5 files changed, 83 insertions(+), 45 deletions(-)
--
2.22.0
^ permalink raw reply [flat|nested] 4+ messages in thread
* [PATCH 1/3] btrfs: define separate btrfs_set/get_XX helpers
2019-08-20 16:58 [PATCH 0/3] Extent buffer accessor macros cleanup David Sterba
@ 2019-08-20 16:58 ` David Sterba
2019-08-20 16:58 ` [PATCH 2/3] btrfs: assume valid token for btrfs_set/get_token helpers David Sterba
2019-08-20 16:58 ` [PATCH 3/3] btrfs: tie extent buffer and it's token together David Sterba
2 siblings, 0 replies; 4+ messages in thread
From: David Sterba @ 2019-08-20 16:58 UTC (permalink / raw)
To: linux-btrfs; +Cc: David Sterba
There are helpers for all type widths defined via macro and optionally
can use a token which is a cached pointer to avoid repeated mapping of
the extent buffer.
The token value is known at compile time, when it's valid it's always
address of a local variable, otherwise it's NULL passed by the
token-less helpers.
This can be utilized to remove some branching as the helpers are used
frequently.
Signed-off-by: David Sterba <dsterba@suse.com>
---
fs/btrfs/ctree.h | 15 ++++--------
fs/btrfs/struct-funcs.c | 51 +++++++++++++++++++++++++++++++++++++++++
2 files changed, 55 insertions(+), 11 deletions(-)
diff --git a/fs/btrfs/ctree.h b/fs/btrfs/ctree.h
index b161224b5a0b..74233b193e89 100644
--- a/fs/btrfs/ctree.h
+++ b/fs/btrfs/ctree.h
@@ -1364,17 +1364,10 @@ u##bits btrfs_get_token_##bits(const struct extent_buffer *eb, \
void btrfs_set_token_##bits(struct extent_buffer *eb, const void *ptr, \
unsigned long off, u##bits val, \
struct btrfs_map_token *token); \
-static inline u##bits btrfs_get_##bits(const struct extent_buffer *eb, \
- const void *ptr, \
- unsigned long off) \
-{ \
- return btrfs_get_token_##bits(eb, ptr, off, NULL); \
-} \
-static inline void btrfs_set_##bits(struct extent_buffer *eb, void *ptr,\
- unsigned long off, u##bits val) \
-{ \
- btrfs_set_token_##bits(eb, ptr, off, val, NULL); \
-}
+u##bits btrfs_get_##bits(const struct extent_buffer *eb, \
+ const void *ptr, unsigned long off); \
+void btrfs_set_##bits(struct extent_buffer *eb, void *ptr, \
+ unsigned long off, u##bits val);
DECLARE_BTRFS_SETGET_BITS(8)
DECLARE_BTRFS_SETGET_BITS(16)
diff --git a/fs/btrfs/struct-funcs.c b/fs/btrfs/struct-funcs.c
index 4c13b737f568..e63936e4c1e0 100644
--- a/fs/btrfs/struct-funcs.c
+++ b/fs/btrfs/struct-funcs.c
@@ -33,6 +33,8 @@ static inline void put_unaligned_le8(u8 val, void *p)
*
* The extent buffer api is used to do the page spanning work required to
* have a metadata blocksize different from the page size.
+ *
+ * There are 2 variants defined, one with a token pointer and one without.
*/
#define DEFINE_BTRFS_SETGET_BITS(bits) \
@@ -75,6 +77,31 @@ u##bits btrfs_get_token_##bits(const struct extent_buffer *eb, \
} \
return res; \
} \
+u##bits btrfs_get_##bits(const struct extent_buffer *eb, \
+ const void *ptr, unsigned long off) \
+{ \
+ unsigned long part_offset = (unsigned long)ptr; \
+ unsigned long offset = part_offset + off; \
+ void *p; \
+ int err; \
+ char *kaddr; \
+ unsigned long map_start; \
+ unsigned long map_len; \
+ int size = sizeof(u##bits); \
+ u##bits res; \
+ \
+ err = map_private_extent_buffer(eb, offset, size, \
+ &kaddr, &map_start, &map_len); \
+ if (err) { \
+ __le##bits leres; \
+ \
+ read_extent_buffer(eb, &leres, offset, size); \
+ return le##bits##_to_cpu(leres); \
+ } \
+ p = kaddr + part_offset - map_start; \
+ res = get_unaligned_le##bits(p + off); \
+ return res; \
+} \
void btrfs_set_token_##bits(struct extent_buffer *eb, \
const void *ptr, unsigned long off, \
u##bits val, \
@@ -113,6 +140,30 @@ void btrfs_set_token_##bits(struct extent_buffer *eb, \
token->offset = map_start; \
token->eb = eb; \
} \
+} \
+void btrfs_set_##bits(struct extent_buffer *eb, void *ptr, \
+ unsigned long off, u##bits val) \
+{ \
+ unsigned long part_offset = (unsigned long)ptr; \
+ unsigned long offset = part_offset + off; \
+ void *p; \
+ int err; \
+ char *kaddr; \
+ unsigned long map_start; \
+ unsigned long map_len; \
+ int size = sizeof(u##bits); \
+ \
+ err = map_private_extent_buffer(eb, offset, size, \
+ &kaddr, &map_start, &map_len); \
+ if (err) { \
+ __le##bits val2; \
+ \
+ val2 = cpu_to_le##bits(val); \
+ write_extent_buffer(eb, &val2, offset, size); \
+ return; \
+ } \
+ p = kaddr + part_offset - map_start; \
+ put_unaligned_le##bits(val, p + off); \
}
DEFINE_BTRFS_SETGET_BITS(8)
--
2.22.0
^ permalink raw reply related [flat|nested] 4+ messages in thread
* [PATCH 2/3] btrfs: assume valid token for btrfs_set/get_token helpers
2019-08-20 16:58 [PATCH 0/3] Extent buffer accessor macros cleanup David Sterba
2019-08-20 16:58 ` [PATCH 1/3] btrfs: define separate btrfs_set/get_XX helpers David Sterba
@ 2019-08-20 16:58 ` David Sterba
2019-08-20 16:58 ` [PATCH 3/3] btrfs: tie extent buffer and it's token together David Sterba
2 siblings, 0 replies; 4+ messages in thread
From: David Sterba @ 2019-08-20 16:58 UTC (permalink / raw)
To: linux-btrfs; +Cc: David Sterba
Now that we can safely assume that the token is always a valid pointer,
remove the branches that check that.
Signed-off-by: David Sterba <dsterba@suse.com>
---
fs/btrfs/struct-funcs.c | 24 ++++++++++++------------
1 file changed, 12 insertions(+), 12 deletions(-)
diff --git a/fs/btrfs/struct-funcs.c b/fs/btrfs/struct-funcs.c
index e63936e4c1e0..3a29b911d2e2 100644
--- a/fs/btrfs/struct-funcs.c
+++ b/fs/btrfs/struct-funcs.c
@@ -52,7 +52,9 @@ u##bits btrfs_get_token_##bits(const struct extent_buffer *eb, \
int size = sizeof(u##bits); \
u##bits res; \
\
- if (token && token->kaddr && token->offset <= offset && \
+ ASSERT(token); \
+ \
+ if (token->kaddr && token->offset <= offset && \
token->eb == eb && \
(token->offset + PAGE_SIZE >= offset + size)) { \
kaddr = token->kaddr; \
@@ -70,11 +72,9 @@ u##bits btrfs_get_token_##bits(const struct extent_buffer *eb, \
} \
p = kaddr + part_offset - map_start; \
res = get_unaligned_le##bits(p + off); \
- if (token) { \
- token->kaddr = kaddr; \
- token->offset = map_start; \
- token->eb = eb; \
- } \
+ token->kaddr = kaddr; \
+ token->offset = map_start; \
+ token->eb = eb; \
return res; \
} \
u##bits btrfs_get_##bits(const struct extent_buffer *eb, \
@@ -116,7 +116,9 @@ void btrfs_set_token_##bits(struct extent_buffer *eb, \
unsigned long map_len; \
int size = sizeof(u##bits); \
\
- if (token && token->kaddr && token->offset <= offset && \
+ ASSERT(token); \
+ \
+ if (token->kaddr && token->offset <= offset && \
token->eb == eb && \
(token->offset + PAGE_SIZE >= offset + size)) { \
kaddr = token->kaddr; \
@@ -135,11 +137,9 @@ void btrfs_set_token_##bits(struct extent_buffer *eb, \
} \
p = kaddr + part_offset - map_start; \
put_unaligned_le##bits(val, p + off); \
- if (token) { \
- token->kaddr = kaddr; \
- token->offset = map_start; \
- token->eb = eb; \
- } \
+ token->kaddr = kaddr; \
+ token->offset = map_start; \
+ token->eb = eb; \
} \
void btrfs_set_##bits(struct extent_buffer *eb, void *ptr, \
unsigned long off, u##bits val) \
--
2.22.0
^ permalink raw reply related [flat|nested] 4+ messages in thread
* [PATCH 3/3] btrfs: tie extent buffer and it's token together
2019-08-20 16:58 [PATCH 0/3] Extent buffer accessor macros cleanup David Sterba
2019-08-20 16:58 ` [PATCH 1/3] btrfs: define separate btrfs_set/get_XX helpers David Sterba
2019-08-20 16:58 ` [PATCH 2/3] btrfs: assume valid token for btrfs_set/get_token helpers David Sterba
@ 2019-08-20 16:58 ` David Sterba
2 siblings, 0 replies; 4+ messages in thread
From: David Sterba @ 2019-08-20 16:58 UTC (permalink / raw)
To: linux-btrfs; +Cc: David Sterba
Further simplifaction of the get/set helpers is possible when the token
is uniquely tied to an extent buffer. A condition and an assignment can
be avoided.
The initializations are moved closer to the first use when the extent
buffer is valid. There's one exception in __push_leaf_left where the
token is reused.
Signed-off-by: David Sterba <dsterba@suse.com>
---
fs/btrfs/ctree.c | 27 +++++++++++----------------
fs/btrfs/ctree.h | 4 +++-
fs/btrfs/inode.c | 2 +-
fs/btrfs/struct-funcs.c | 6 ++----
fs/btrfs/tree-log.c | 7 +++----
5 files changed, 20 insertions(+), 26 deletions(-)
diff --git a/fs/btrfs/ctree.c b/fs/btrfs/ctree.c
index a2f3cd7a619c..7dbd2341967c 100644
--- a/fs/btrfs/ctree.c
+++ b/fs/btrfs/ctree.c
@@ -3574,7 +3574,7 @@ static int leaf_space_used(struct extent_buffer *l, int start, int nr)
if (!nr)
return 0;
- btrfs_init_map_token(&token);
+ btrfs_init_map_token(&token, l);
start_item = btrfs_item_nr(start);
end_item = btrfs_item_nr(end);
data_len = btrfs_token_item_offset(l, start_item, &token) +
@@ -3632,8 +3632,6 @@ static noinline int __push_leaf_right(struct btrfs_path *path,
u32 data_end;
u32 this_item_size;
- btrfs_init_map_token(&token);
-
if (empty)
nr = 0;
else
@@ -3706,6 +3704,7 @@ static noinline int __push_leaf_right(struct btrfs_path *path,
push_items * sizeof(struct btrfs_item));
/* update the item pointers */
+ btrfs_init_map_token(&token, right);
right_nritems += push_items;
btrfs_set_header_nritems(right, right_nritems);
push_space = BTRFS_LEAF_DATA_SIZE(fs_info);
@@ -3860,8 +3859,6 @@ static noinline int __push_leaf_left(struct btrfs_path *path, int data_size,
u32 old_left_item_size;
struct btrfs_map_token token;
- btrfs_init_map_token(&token);
-
if (empty)
nr = min(right_nritems, max_slot);
else
@@ -3915,6 +3912,7 @@ static noinline int __push_leaf_left(struct btrfs_path *path, int data_size,
old_left_nritems = btrfs_header_nritems(left);
BUG_ON(old_left_nritems <= 0);
+ btrfs_init_map_token(&token, left);
old_left_item_size = btrfs_item_offset_nr(left, old_left_nritems - 1);
for (i = old_left_nritems; i < old_left_nritems + push_items; i++) {
u32 ioff;
@@ -3946,6 +3944,8 @@ static noinline int __push_leaf_left(struct btrfs_path *path, int data_size,
(btrfs_header_nritems(right) - push_items) *
sizeof(struct btrfs_item));
}
+
+ btrfs_init_map_token(&token, right);
right_nritems -= push_items;
btrfs_set_header_nritems(right, right_nritems);
push_space = BTRFS_LEAF_DATA_SIZE(fs_info);
@@ -4076,8 +4076,6 @@ static noinline void copy_for_split(struct btrfs_trans_handle *trans,
struct btrfs_disk_key disk_key;
struct btrfs_map_token token;
- btrfs_init_map_token(&token);
-
nritems = nritems - mid;
btrfs_set_header_nritems(right, nritems);
data_copy_size = btrfs_item_end_nr(l, mid) - leaf_data_end(l);
@@ -4093,6 +4091,7 @@ static noinline void copy_for_split(struct btrfs_trans_handle *trans,
rt_data_off = BTRFS_LEAF_DATA_SIZE(fs_info) - btrfs_item_end_nr(l, mid);
+ btrfs_init_map_token(&token, right);
for (i = 0; i < nritems; i++) {
struct btrfs_item *item = btrfs_item_nr(i);
u32 ioff;
@@ -4576,8 +4575,6 @@ void btrfs_truncate_item(struct btrfs_path *path, u32 new_size, int from_end)
int i;
struct btrfs_map_token token;
- btrfs_init_map_token(&token);
-
leaf = path->nodes[0];
slot = path->slots[0];
@@ -4599,6 +4596,7 @@ void btrfs_truncate_item(struct btrfs_path *path, u32 new_size, int from_end)
* item0..itemN ... dataN.offset..dataN.size .. data0.size
*/
/* first correct the data pointers */
+ btrfs_init_map_token(&token, leaf);
for (i = slot; i < nritems; i++) {
u32 ioff;
item = btrfs_item_nr(i);
@@ -4673,8 +4671,6 @@ void btrfs_extend_item(struct btrfs_path *path, u32 data_size)
int i;
struct btrfs_map_token token;
- btrfs_init_map_token(&token);
-
leaf = path->nodes[0];
nritems = btrfs_header_nritems(leaf);
@@ -4699,6 +4695,7 @@ void btrfs_extend_item(struct btrfs_path *path, u32 data_size)
* item0..itemN ... dataN.offset..dataN.size .. data0.size
*/
/* first correct the data pointers */
+ btrfs_init_map_token(&token, leaf);
for (i = slot; i < nritems; i++) {
u32 ioff;
item = btrfs_item_nr(i);
@@ -4750,8 +4747,6 @@ void setup_items_for_insert(struct btrfs_root *root, struct btrfs_path *path,
}
btrfs_unlock_up_safe(path, 1);
- btrfs_init_map_token(&token);
-
leaf = path->nodes[0];
slot = path->slots[0];
@@ -4765,6 +4760,7 @@ void setup_items_for_insert(struct btrfs_root *root, struct btrfs_path *path,
BUG();
}
+ btrfs_init_map_token(&token, leaf);
if (slot != nritems) {
unsigned int old_data = btrfs_item_end_nr(leaf, slot);
@@ -4971,9 +4967,6 @@ int btrfs_del_items(struct btrfs_trans_handle *trans, struct btrfs_root *root,
int wret;
int i;
u32 nritems;
- struct btrfs_map_token token;
-
- btrfs_init_map_token(&token);
leaf = path->nodes[0];
last_off = btrfs_item_offset_nr(leaf, slot + nr - 1);
@@ -4985,12 +4978,14 @@ int btrfs_del_items(struct btrfs_trans_handle *trans, struct btrfs_root *root,
if (slot + nr != nritems) {
int data_end = leaf_data_end(leaf);
+ struct btrfs_map_token token;
memmove_extent_buffer(leaf, BTRFS_LEAF_DATA_OFFSET +
data_end + dsize,
BTRFS_LEAF_DATA_OFFSET + data_end,
last_off - data_end);
+ btrfs_init_map_token(&token, leaf);
for (i = slot + nr; i < nritems; i++) {
u32 ioff;
diff --git a/fs/btrfs/ctree.h b/fs/btrfs/ctree.h
index 74233b193e89..b5fc948fdfce 100644
--- a/fs/btrfs/ctree.h
+++ b/fs/btrfs/ctree.h
@@ -1332,8 +1332,10 @@ struct btrfs_map_token {
#define BTRFS_BYTES_TO_BLKS(fs_info, bytes) \
((bytes) >> (fs_info)->sb->s_blocksize_bits)
-static inline void btrfs_init_map_token (struct btrfs_map_token *token)
+static inline void btrfs_init_map_token(struct btrfs_map_token *token,
+ struct extent_buffer *eb)
{
+ token->eb = eb;
token->kaddr = NULL;
}
diff --git a/fs/btrfs/inode.c b/fs/btrfs/inode.c
index c094c7977b93..7e77c2ef076a 100644
--- a/fs/btrfs/inode.c
+++ b/fs/btrfs/inode.c
@@ -3831,7 +3831,7 @@ static void fill_inode_item(struct btrfs_trans_handle *trans,
{
struct btrfs_map_token token;
- btrfs_init_map_token(&token);
+ btrfs_init_map_token(&token, leaf);
btrfs_set_token_inode_uid(leaf, item, i_uid_read(inode), &token);
btrfs_set_token_inode_gid(leaf, item, i_gid_read(inode), &token);
diff --git a/fs/btrfs/struct-funcs.c b/fs/btrfs/struct-funcs.c
index 3a29b911d2e2..73f7987143df 100644
--- a/fs/btrfs/struct-funcs.c
+++ b/fs/btrfs/struct-funcs.c
@@ -53,9 +53,9 @@ u##bits btrfs_get_token_##bits(const struct extent_buffer *eb, \
u##bits res; \
\
ASSERT(token); \
+ ASSERT(token->eb == eb); \
\
if (token->kaddr && token->offset <= offset && \
- token->eb == eb && \
(token->offset + PAGE_SIZE >= offset + size)) { \
kaddr = token->kaddr; \
p = kaddr + part_offset - token->offset; \
@@ -74,7 +74,6 @@ u##bits btrfs_get_token_##bits(const struct extent_buffer *eb, \
res = get_unaligned_le##bits(p + off); \
token->kaddr = kaddr; \
token->offset = map_start; \
- token->eb = eb; \
return res; \
} \
u##bits btrfs_get_##bits(const struct extent_buffer *eb, \
@@ -117,9 +116,9 @@ void btrfs_set_token_##bits(struct extent_buffer *eb, \
int size = sizeof(u##bits); \
\
ASSERT(token); \
+ ASSERT(token->eb == eb); \
\
if (token->kaddr && token->offset <= offset && \
- token->eb == eb && \
(token->offset + PAGE_SIZE >= offset + size)) { \
kaddr = token->kaddr; \
p = kaddr + part_offset - token->offset; \
@@ -139,7 +138,6 @@ void btrfs_set_token_##bits(struct extent_buffer *eb, \
put_unaligned_le##bits(val, p + off); \
token->kaddr = kaddr; \
token->offset = map_start; \
- token->eb = eb; \
} \
void btrfs_set_##bits(struct extent_buffer *eb, void *ptr, \
unsigned long off, u##bits val) \
diff --git a/fs/btrfs/tree-log.c b/fs/btrfs/tree-log.c
index 19a4b9dc669f..fdc52daf1baf 100644
--- a/fs/btrfs/tree-log.c
+++ b/fs/btrfs/tree-log.c
@@ -505,7 +505,7 @@ static noinline int overwrite_item(struct btrfs_trans_handle *trans,
ino_size != 0) {
struct btrfs_map_token token;
- btrfs_init_map_token(&token);
+ btrfs_init_map_token(&token, dst_eb);
btrfs_set_token_inode_size(dst_eb, dst_item,
ino_size, &token);
}
@@ -3842,7 +3842,7 @@ static void fill_inode_item(struct btrfs_trans_handle *trans,
{
struct btrfs_map_token token;
- btrfs_init_map_token(&token);
+ btrfs_init_map_token(&token, leaf);
if (log_inode_only) {
/* set the generation to zero so the recover code
@@ -4302,8 +4302,6 @@ static int log_one_extent(struct btrfs_trans_handle *trans,
if (ret)
return ret;
- btrfs_init_map_token(&token);
-
ret = __btrfs_drop_extents(trans, log, &inode->vfs_inode, path, em->start,
em->start + em->len, NULL, 0, 1,
sizeof(*fi), &extent_inserted);
@@ -4321,6 +4319,7 @@ static int log_one_extent(struct btrfs_trans_handle *trans,
return ret;
}
leaf = path->nodes[0];
+ btrfs_init_map_token(&token, leaf);
fi = btrfs_item_ptr(leaf, path->slots[0],
struct btrfs_file_extent_item);
--
2.22.0
^ permalink raw reply related [flat|nested] 4+ messages in thread
end of thread, other threads:[~2019-08-20 16:58 UTC | newest]
Thread overview: 4+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2019-08-20 16:58 [PATCH 0/3] Extent buffer accessor macros cleanup David Sterba
2019-08-20 16:58 ` [PATCH 1/3] btrfs: define separate btrfs_set/get_XX helpers David Sterba
2019-08-20 16:58 ` [PATCH 2/3] btrfs: assume valid token for btrfs_set/get_token helpers David Sterba
2019-08-20 16:58 ` [PATCH 3/3] btrfs: tie extent buffer and it's token together David Sterba
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).