diff options
author | Christoph Hellwig <hch@lst.de> | 2011-07-13 07:43:48 -0400 |
---|---|---|
committer | Christoph Hellwig <hch@lst.de> | 2011-07-13 07:43:48 -0400 |
commit | 5792664070c62479b088e4909000582de3686396 (patch) | |
tree | 900e7d35b33da062fe8fad5694539fdad8c59266 | |
parent | 2bcf6e970f5a88fa05dced5eeb0326e13d93c4a1 (diff) |
xfs: reshuffle dir2 headers
Replace the current mess of dir2 headers with just three that have a clear
purpose:
- xfs_dir2_format.h for all format definitions, including the inline helpers
to access our variable size structures
- xfs_dir2_priv.h for all prototypes that are internal to the dir2 code
and not needed by anything outside of the directory code. For this
purpose xfs_da_btree.c, and phase6.c in xfs_repair are considered part
of the directory code.
- xfs_dir2.h for the public interface to the directory code
In addition to the reshuffle I have also update the comments to not only
match the new file structure, but also to describe the directory format
better.
Signed-off-by: Christoph Hellwig <hch@lst.de>
Reviewed-by: Alex Elder <aelder@sgi.com>
Reviewed-by: Dave Chinner <dchinner@redhat.com>
-rw-r--r-- | fs/xfs/xfs_bmap.c | 4 | ||||
-rw-r--r-- | fs/xfs/xfs_da_btree.c | 9 | ||||
-rw-r--r-- | fs/xfs/xfs_dir2.c | 9 | ||||
-rw-r--r-- | fs/xfs/xfs_dir2.h | 54 | ||||
-rw-r--r-- | fs/xfs/xfs_dir2_block.c | 7 | ||||
-rw-r--r-- | fs/xfs/xfs_dir2_block.h | 93 | ||||
-rw-r--r-- | fs/xfs/xfs_dir2_data.c | 7 | ||||
-rw-r--r-- | fs/xfs/xfs_dir2_data.h | 182 | ||||
-rw-r--r-- | fs/xfs/xfs_dir2_format.h | 595 | ||||
-rw-r--r-- | fs/xfs/xfs_dir2_leaf.c | 8 | ||||
-rw-r--r-- | fs/xfs/xfs_dir2_leaf.h | 281 | ||||
-rw-r--r-- | fs/xfs/xfs_dir2_node.c | 8 | ||||
-rw-r--r-- | fs/xfs/xfs_dir2_node.h | 100 | ||||
-rw-r--r-- | fs/xfs/xfs_dir2_priv.h | 135 | ||||
-rw-r--r-- | fs/xfs/xfs_dir2_sf.c | 8 | ||||
-rw-r--r-- | fs/xfs/xfs_dir2_sf.h | 151 |
16 files changed, 751 insertions, 900 deletions
diff --git a/fs/xfs/xfs_bmap.c b/fs/xfs/xfs_bmap.c index 2ce6aa644e7e..c51a3f903633 100644 --- a/fs/xfs/xfs_bmap.c +++ b/fs/xfs/xfs_bmap.c | |||
@@ -29,15 +29,11 @@ | |||
29 | #include "xfs_bmap_btree.h" | 29 | #include "xfs_bmap_btree.h" |
30 | #include "xfs_alloc_btree.h" | 30 | #include "xfs_alloc_btree.h" |
31 | #include "xfs_ialloc_btree.h" | 31 | #include "xfs_ialloc_btree.h" |
32 | #include "xfs_dir2_sf.h" | ||
33 | #include "xfs_dinode.h" | 32 | #include "xfs_dinode.h" |
34 | #include "xfs_inode.h" | 33 | #include "xfs_inode.h" |
35 | #include "xfs_btree.h" | 34 | #include "xfs_btree.h" |
36 | #include "xfs_mount.h" | 35 | #include "xfs_mount.h" |
37 | #include "xfs_itable.h" | 36 | #include "xfs_itable.h" |
38 | #include "xfs_dir2_data.h" | ||
39 | #include "xfs_dir2_leaf.h" | ||
40 | #include "xfs_dir2_block.h" | ||
41 | #include "xfs_inode_item.h" | 37 | #include "xfs_inode_item.h" |
42 | #include "xfs_extfree_item.h" | 38 | #include "xfs_extfree_item.h" |
43 | #include "xfs_alloc.h" | 39 | #include "xfs_alloc.h" |
diff --git a/fs/xfs/xfs_da_btree.c b/fs/xfs/xfs_da_btree.c index 18425717cbe6..a58a6410c58d 100644 --- a/fs/xfs/xfs_da_btree.c +++ b/fs/xfs/xfs_da_btree.c | |||
@@ -24,11 +24,12 @@ | |||
24 | #include "xfs_trans.h" | 24 | #include "xfs_trans.h" |
25 | #include "xfs_sb.h" | 25 | #include "xfs_sb.h" |
26 | #include "xfs_ag.h" | 26 | #include "xfs_ag.h" |
27 | #include "xfs_dir2.h" | ||
28 | #include "xfs_mount.h" | 27 | #include "xfs_mount.h" |
29 | #include "xfs_da_btree.h" | 28 | #include "xfs_da_btree.h" |
30 | #include "xfs_bmap_btree.h" | 29 | #include "xfs_bmap_btree.h" |
31 | #include "xfs_dir2_sf.h" | 30 | #include "xfs_dir2.h" |
31 | #include "xfs_dir2_format.h" | ||
32 | #include "xfs_dir2_priv.h" | ||
32 | #include "xfs_dinode.h" | 33 | #include "xfs_dinode.h" |
33 | #include "xfs_inode.h" | 34 | #include "xfs_inode.h" |
34 | #include "xfs_inode_item.h" | 35 | #include "xfs_inode_item.h" |
@@ -36,10 +37,6 @@ | |||
36 | #include "xfs_bmap.h" | 37 | #include "xfs_bmap.h" |
37 | #include "xfs_attr.h" | 38 | #include "xfs_attr.h" |
38 | #include "xfs_attr_leaf.h" | 39 | #include "xfs_attr_leaf.h" |
39 | #include "xfs_dir2_data.h" | ||
40 | #include "xfs_dir2_leaf.h" | ||
41 | #include "xfs_dir2_block.h" | ||
42 | #include "xfs_dir2_node.h" | ||
43 | #include "xfs_error.h" | 40 | #include "xfs_error.h" |
44 | #include "xfs_trace.h" | 41 | #include "xfs_trace.h" |
45 | 42 | ||
diff --git a/fs/xfs/xfs_dir2.c b/fs/xfs/xfs_dir2.c index 0dee57812f45..6effbeb24e5a 100644 --- a/fs/xfs/xfs_dir2.c +++ b/fs/xfs/xfs_dir2.c | |||
@@ -24,20 +24,17 @@ | |||
24 | #include "xfs_trans.h" | 24 | #include "xfs_trans.h" |
25 | #include "xfs_sb.h" | 25 | #include "xfs_sb.h" |
26 | #include "xfs_ag.h" | 26 | #include "xfs_ag.h" |
27 | #include "xfs_dir2.h" | ||
28 | #include "xfs_mount.h" | 27 | #include "xfs_mount.h" |
29 | #include "xfs_da_btree.h" | 28 | #include "xfs_da_btree.h" |
30 | #include "xfs_bmap_btree.h" | 29 | #include "xfs_bmap_btree.h" |
31 | #include "xfs_alloc_btree.h" | 30 | #include "xfs_alloc_btree.h" |
32 | #include "xfs_dir2_sf.h" | ||
33 | #include "xfs_dinode.h" | 31 | #include "xfs_dinode.h" |
34 | #include "xfs_inode.h" | 32 | #include "xfs_inode.h" |
35 | #include "xfs_inode_item.h" | 33 | #include "xfs_inode_item.h" |
36 | #include "xfs_bmap.h" | 34 | #include "xfs_bmap.h" |
37 | #include "xfs_dir2_data.h" | 35 | #include "xfs_dir2.h" |
38 | #include "xfs_dir2_leaf.h" | 36 | #include "xfs_dir2_format.h" |
39 | #include "xfs_dir2_block.h" | 37 | #include "xfs_dir2_priv.h" |
40 | #include "xfs_dir2_node.h" | ||
41 | #include "xfs_error.h" | 38 | #include "xfs_error.h" |
42 | #include "xfs_vnodeops.h" | 39 | #include "xfs_vnodeops.h" |
43 | #include "xfs_trace.h" | 40 | #include "xfs_trace.h" |
diff --git a/fs/xfs/xfs_dir2.h b/fs/xfs/xfs_dir2.h index 74a3b1057685..e937d9991c18 100644 --- a/fs/xfs/xfs_dir2.h +++ b/fs/xfs/xfs_dir2.h | |||
@@ -16,49 +16,14 @@ | |||
16 | * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA | 16 | * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA |
17 | */ | 17 | */ |
18 | #ifndef __XFS_DIR2_H__ | 18 | #ifndef __XFS_DIR2_H__ |
19 | #define __XFS_DIR2_H__ | 19 | #define __XFS_DIR2_H__ |
20 | 20 | ||
21 | struct uio; | ||
22 | struct xfs_dabuf; | ||
23 | struct xfs_da_args; | ||
24 | struct xfs_dir2_put_args; | ||
25 | struct xfs_bmap_free; | 21 | struct xfs_bmap_free; |
22 | struct xfs_da_args; | ||
26 | struct xfs_inode; | 23 | struct xfs_inode; |
27 | struct xfs_mount; | 24 | struct xfs_mount; |
28 | struct xfs_trans; | 25 | struct xfs_trans; |
29 | 26 | ||
30 | /* | ||
31 | * Directory version 2. | ||
32 | * There are 4 possible formats: | ||
33 | * shortform | ||
34 | * single block - data with embedded leaf at the end | ||
35 | * multiple data blocks, single leaf+freeindex block | ||
36 | * data blocks, node&leaf blocks (btree), freeindex blocks | ||
37 | * | ||
38 | * The shortform format is in xfs_dir2_sf.h. | ||
39 | * The single block format is in xfs_dir2_block.h. | ||
40 | * The data block format is in xfs_dir2_data.h. | ||
41 | * The leaf and freeindex block formats are in xfs_dir2_leaf.h. | ||
42 | * Node blocks are the same as the other version, in xfs_da_btree.h. | ||
43 | */ | ||
44 | |||
45 | /* | ||
46 | * Byte offset in data block and shortform entry. | ||
47 | */ | ||
48 | typedef __uint16_t xfs_dir2_data_off_t; | ||
49 | #define NULLDATAOFF 0xffffU | ||
50 | typedef uint xfs_dir2_data_aoff_t; /* argument form */ | ||
51 | |||
52 | /* | ||
53 | * Directory block number (logical dirblk in file) | ||
54 | */ | ||
55 | typedef __uint32_t xfs_dir2_db_t; | ||
56 | |||
57 | /* | ||
58 | * Byte offset in a directory. | ||
59 | */ | ||
60 | typedef xfs_off_t xfs_dir2_off_t; | ||
61 | |||
62 | extern struct xfs_name xfs_name_dotdot; | 27 | extern struct xfs_name xfs_name_dotdot; |
63 | 28 | ||
64 | /* | 29 | /* |
@@ -86,21 +51,10 @@ extern int xfs_dir_replace(struct xfs_trans *tp, struct xfs_inode *dp, | |||
86 | struct xfs_bmap_free *flist, xfs_extlen_t tot); | 51 | struct xfs_bmap_free *flist, xfs_extlen_t tot); |
87 | extern int xfs_dir_canenter(struct xfs_trans *tp, struct xfs_inode *dp, | 52 | extern int xfs_dir_canenter(struct xfs_trans *tp, struct xfs_inode *dp, |
88 | struct xfs_name *name, uint resblks); | 53 | struct xfs_name *name, uint resblks); |
89 | extern int xfs_dir_ino_validate(struct xfs_mount *mp, xfs_ino_t ino); | ||
90 | 54 | ||
91 | /* | 55 | /* |
92 | * Utility routines for v2 directories. | 56 | * Direct call from the bmap code, bypassing the generic directory layer. |
93 | */ | 57 | */ |
94 | extern int xfs_dir2_grow_inode(struct xfs_da_args *args, int space, | 58 | extern int xfs_dir2_sf_to_block(struct xfs_da_args *args); |
95 | xfs_dir2_db_t *dbp); | ||
96 | extern int xfs_dir2_isblock(struct xfs_trans *tp, struct xfs_inode *dp, | ||
97 | int *vp); | ||
98 | extern int xfs_dir2_isleaf(struct xfs_trans *tp, struct xfs_inode *dp, | ||
99 | int *vp); | ||
100 | extern int xfs_dir2_shrink_inode(struct xfs_da_args *args, xfs_dir2_db_t db, | ||
101 | struct xfs_dabuf *bp); | ||
102 | |||
103 | extern int xfs_dir_cilookup_result(struct xfs_da_args *args, | ||
104 | const unsigned char *name, int len); | ||
105 | 59 | ||
106 | #endif /* __XFS_DIR2_H__ */ | 60 | #endif /* __XFS_DIR2_H__ */ |
diff --git a/fs/xfs/xfs_dir2_block.c b/fs/xfs/xfs_dir2_block.c index 70fb0cb6bd69..9245e029b8ea 100644 --- a/fs/xfs/xfs_dir2_block.c +++ b/fs/xfs/xfs_dir2_block.c | |||
@@ -23,17 +23,14 @@ | |||
23 | #include "xfs_trans.h" | 23 | #include "xfs_trans.h" |
24 | #include "xfs_sb.h" | 24 | #include "xfs_sb.h" |
25 | #include "xfs_ag.h" | 25 | #include "xfs_ag.h" |
26 | #include "xfs_dir2.h" | ||
27 | #include "xfs_mount.h" | 26 | #include "xfs_mount.h" |
28 | #include "xfs_da_btree.h" | 27 | #include "xfs_da_btree.h" |
29 | #include "xfs_bmap_btree.h" | 28 | #include "xfs_bmap_btree.h" |
30 | #include "xfs_dir2_sf.h" | ||
31 | #include "xfs_dinode.h" | 29 | #include "xfs_dinode.h" |
32 | #include "xfs_inode.h" | 30 | #include "xfs_inode.h" |
33 | #include "xfs_inode_item.h" | 31 | #include "xfs_inode_item.h" |
34 | #include "xfs_dir2_data.h" | 32 | #include "xfs_dir2_format.h" |
35 | #include "xfs_dir2_leaf.h" | 33 | #include "xfs_dir2_priv.h" |
36 | #include "xfs_dir2_block.h" | ||
37 | #include "xfs_error.h" | 34 | #include "xfs_error.h" |
38 | #include "xfs_trace.h" | 35 | #include "xfs_trace.h" |
39 | 36 | ||
diff --git a/fs/xfs/xfs_dir2_block.h b/fs/xfs/xfs_dir2_block.h deleted file mode 100644 index de59677e38ba..000000000000 --- a/fs/xfs/xfs_dir2_block.h +++ /dev/null | |||
@@ -1,93 +0,0 @@ | |||
1 | /* | ||
2 | * Copyright (c) 2000-2001,2005 Silicon Graphics, Inc. | ||
3 | * All Rights Reserved. | ||
4 | * | ||
5 | * This program is free software; you can redistribute it and/or | ||
6 | * modify it under the terms of the GNU General Public License as | ||
7 | * published by the Free Software Foundation. | ||
8 | * | ||
9 | * This program is distributed in the hope that it would be useful, | ||
10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
12 | * GNU General Public License for more details. | ||
13 | * | ||
14 | * You should have received a copy of the GNU General Public License | ||
15 | * along with this program; if not, write the Free Software Foundation, | ||
16 | * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA | ||
17 | */ | ||
18 | #ifndef __XFS_DIR2_BLOCK_H__ | ||
19 | #define __XFS_DIR2_BLOCK_H__ | ||
20 | |||
21 | /* | ||
22 | * Directory version 2, single block format structures. | ||
23 | * | ||
24 | * The single block format looks like the following drawing on disk: | ||
25 | * | ||
26 | * +-------------------------------------------------+ | ||
27 | * | xfs_dir2_data_hdr_t | | ||
28 | * +-------------------------------------------------+ | ||
29 | * | xfs_dir2_data_entry_t OR xfs_dir2_data_unused_t | | ||
30 | * | xfs_dir2_data_entry_t OR xfs_dir2_data_unused_t | | ||
31 | * | xfs_dir2_data_entry_t OR xfs_dir2_data_unused_t | | ||
32 | * | ... | | ||
33 | * +-------------------------------------------------+ | ||
34 | * | unused space | | ||
35 | * +-------------------------------------------------+ | ||
36 | * | ... | | ||
37 | * | xfs_dir2_leaf_entry_t | | ||
38 | * | xfs_dir2_leaf_entry_t | | ||
39 | * +-------------------------------------------------+ | ||
40 | * | xfs_dir2_block_tail_t | | ||
41 | * +-------------------------------------------------+ | ||
42 | * | ||
43 | * As all the entries are variable size structures the accessors in this | ||
44 | * file and xfs_dir2_data.h should be used to iterate over them. | ||
45 | */ | ||
46 | struct uio; | ||
47 | struct xfs_dabuf; | ||
48 | struct xfs_da_args; | ||
49 | struct xfs_dir2_data_hdr; | ||
50 | struct xfs_dir2_leaf_entry; | ||
51 | struct xfs_inode; | ||
52 | struct xfs_mount; | ||
53 | struct xfs_trans; | ||
54 | |||
55 | #define XFS_DIR2_BLOCK_MAGIC 0x58443242 /* XD2B: for one block dirs */ | ||
56 | |||
57 | typedef struct xfs_dir2_block_tail { | ||
58 | __be32 count; /* count of leaf entries */ | ||
59 | __be32 stale; /* count of stale lf entries */ | ||
60 | } xfs_dir2_block_tail_t; | ||
61 | |||
62 | /* | ||
63 | * Pointer to the leaf header embedded in a data block (1-block format) | ||
64 | */ | ||
65 | static inline xfs_dir2_block_tail_t * | ||
66 | xfs_dir2_block_tail_p(struct xfs_mount *mp, xfs_dir2_data_hdr_t *hdr) | ||
67 | { | ||
68 | return ((xfs_dir2_block_tail_t *)((char *)hdr + mp->m_dirblksize)) - 1; | ||
69 | } | ||
70 | |||
71 | /* | ||
72 | * Pointer to the leaf entries embedded in a data block (1-block format) | ||
73 | */ | ||
74 | static inline struct xfs_dir2_leaf_entry * | ||
75 | xfs_dir2_block_leaf_p(xfs_dir2_block_tail_t *btp) | ||
76 | { | ||
77 | return ((struct xfs_dir2_leaf_entry *)btp) - be32_to_cpu(btp->count); | ||
78 | } | ||
79 | |||
80 | /* | ||
81 | * Function declarations. | ||
82 | */ | ||
83 | extern int xfs_dir2_block_addname(struct xfs_da_args *args); | ||
84 | extern int xfs_dir2_block_getdents(struct xfs_inode *dp, void *dirent, | ||
85 | xfs_off_t *offset, filldir_t filldir); | ||
86 | extern int xfs_dir2_block_lookup(struct xfs_da_args *args); | ||
87 | extern int xfs_dir2_block_removename(struct xfs_da_args *args); | ||
88 | extern int xfs_dir2_block_replace(struct xfs_da_args *args); | ||
89 | extern int xfs_dir2_leaf_to_block(struct xfs_da_args *args, | ||
90 | struct xfs_dabuf *lbp, struct xfs_dabuf *dbp); | ||
91 | extern int xfs_dir2_sf_to_block(struct xfs_da_args *args); | ||
92 | |||
93 | #endif /* __XFS_DIR2_BLOCK_H__ */ | ||
diff --git a/fs/xfs/xfs_dir2_data.c b/fs/xfs/xfs_dir2_data.c index 32dca4c531a6..5bbe2a8a023f 100644 --- a/fs/xfs/xfs_dir2_data.c +++ b/fs/xfs/xfs_dir2_data.c | |||
@@ -23,16 +23,13 @@ | |||
23 | #include "xfs_trans.h" | 23 | #include "xfs_trans.h" |
24 | #include "xfs_sb.h" | 24 | #include "xfs_sb.h" |
25 | #include "xfs_ag.h" | 25 | #include "xfs_ag.h" |
26 | #include "xfs_dir2.h" | ||
27 | #include "xfs_mount.h" | 26 | #include "xfs_mount.h" |
28 | #include "xfs_da_btree.h" | 27 | #include "xfs_da_btree.h" |
29 | #include "xfs_bmap_btree.h" | 28 | #include "xfs_bmap_btree.h" |
30 | #include "xfs_dir2_sf.h" | ||
31 | #include "xfs_dinode.h" | 29 | #include "xfs_dinode.h" |
32 | #include "xfs_inode.h" | 30 | #include "xfs_inode.h" |
33 | #include "xfs_dir2_data.h" | 31 | #include "xfs_dir2_format.h" |
34 | #include "xfs_dir2_leaf.h" | 32 | #include "xfs_dir2_priv.h" |
35 | #include "xfs_dir2_block.h" | ||
36 | #include "xfs_error.h" | 33 | #include "xfs_error.h" |
37 | 34 | ||
38 | STATIC xfs_dir2_data_free_t * | 35 | STATIC xfs_dir2_data_free_t * |
diff --git a/fs/xfs/xfs_dir2_data.h b/fs/xfs/xfs_dir2_data.h deleted file mode 100644 index c50512584ebf..000000000000 --- a/fs/xfs/xfs_dir2_data.h +++ /dev/null | |||
@@ -1,182 +0,0 @@ | |||
1 | /* | ||
2 | * Copyright (c) 2000,2005 Silicon Graphics, Inc. | ||
3 | * All Rights Reserved. | ||
4 | * | ||
5 | * This program is free software; you can redistribute it and/or | ||
6 | * modify it under the terms of the GNU General Public License as | ||
7 | * published by the Free Software Foundation. | ||
8 | * | ||
9 | * This program is distributed in the hope that it would be useful, | ||
10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
12 | * GNU General Public License for more details. | ||
13 | * | ||
14 | * You should have received a copy of the GNU General Public License | ||
15 | * along with this program; if not, write the Free Software Foundation, | ||
16 | * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA | ||
17 | */ | ||
18 | #ifndef __XFS_DIR2_DATA_H__ | ||
19 | #define __XFS_DIR2_DATA_H__ | ||
20 | |||
21 | /* | ||
22 | * Directory format 2, data block structures. | ||
23 | * | ||
24 | * A pure data block looks like the following drawing on disk: | ||
25 | * | ||
26 | * +-------------------------------------------------+ | ||
27 | * | xfs_dir2_data_hdr_t | | ||
28 | * +-------------------------------------------------+ | ||
29 | * | xfs_dir2_data_entry_t OR xfs_dir2_data_unused_t | | ||
30 | * | xfs_dir2_data_entry_t OR xfs_dir2_data_unused_t | | ||
31 | * | xfs_dir2_data_entry_t OR xfs_dir2_data_unused_t | | ||
32 | * | ... | | ||
33 | * +-------------------------------------------------+ | ||
34 | * | unused space | | ||
35 | * +-------------------------------------------------+ | ||
36 | * | ||
37 | * As all the entries are variable size structures the accessors in this | ||
38 | * file should be used to iterate over them. | ||
39 | */ | ||
40 | |||
41 | struct xfs_dabuf; | ||
42 | struct xfs_da_args; | ||
43 | struct xfs_inode; | ||
44 | struct xfs_trans; | ||
45 | |||
46 | /* | ||
47 | * Constants. | ||
48 | */ | ||
49 | #define XFS_DIR2_DATA_MAGIC 0x58443244 /* XD2D: for multiblock dirs */ | ||
50 | #define XFS_DIR2_DATA_ALIGN_LOG 3 /* i.e., 8 bytes */ | ||
51 | #define XFS_DIR2_DATA_ALIGN (1 << XFS_DIR2_DATA_ALIGN_LOG) | ||
52 | #define XFS_DIR2_DATA_FREE_TAG 0xffff | ||
53 | #define XFS_DIR2_DATA_FD_COUNT 3 | ||
54 | |||
55 | /* | ||
56 | * Directory address space divided into sections, | ||
57 | * spaces separated by 32GB. | ||
58 | */ | ||
59 | #define XFS_DIR2_SPACE_SIZE (1ULL << (32 + XFS_DIR2_DATA_ALIGN_LOG)) | ||
60 | #define XFS_DIR2_DATA_SPACE 0 | ||
61 | #define XFS_DIR2_DATA_OFFSET (XFS_DIR2_DATA_SPACE * XFS_DIR2_SPACE_SIZE) | ||
62 | #define XFS_DIR2_DATA_FIRSTDB(mp) \ | ||
63 | xfs_dir2_byte_to_db(mp, XFS_DIR2_DATA_OFFSET) | ||
64 | |||
65 | /* | ||
66 | * Offsets of . and .. in data space (always block 0) | ||
67 | */ | ||
68 | #define XFS_DIR2_DATA_DOT_OFFSET \ | ||
69 | ((xfs_dir2_data_aoff_t)sizeof(xfs_dir2_data_hdr_t)) | ||
70 | #define XFS_DIR2_DATA_DOTDOT_OFFSET \ | ||
71 | (XFS_DIR2_DATA_DOT_OFFSET + xfs_dir2_data_entsize(1)) | ||
72 | #define XFS_DIR2_DATA_FIRST_OFFSET \ | ||
73 | (XFS_DIR2_DATA_DOTDOT_OFFSET + xfs_dir2_data_entsize(2)) | ||
74 | |||
75 | /* | ||
76 | * Structures. | ||
77 | */ | ||
78 | |||
79 | /* | ||
80 | * Describe a free area in the data block. | ||
81 | * The freespace will be formatted as a xfs_dir2_data_unused_t. | ||
82 | */ | ||
83 | typedef struct xfs_dir2_data_free { | ||
84 | __be16 offset; /* start of freespace */ | ||
85 | __be16 length; /* length of freespace */ | ||
86 | } xfs_dir2_data_free_t; | ||
87 | |||
88 | /* | ||
89 | * Header for the data blocks. | ||
90 | * Always at the beginning of a directory-sized block. | ||
91 | * The code knows that XFS_DIR2_DATA_FD_COUNT is 3. | ||
92 | */ | ||
93 | typedef struct xfs_dir2_data_hdr { | ||
94 | __be32 magic; /* XFS_DIR2_DATA_MAGIC */ | ||
95 | /* or XFS_DIR2_BLOCK_MAGIC */ | ||
96 | xfs_dir2_data_free_t bestfree[XFS_DIR2_DATA_FD_COUNT]; | ||
97 | } xfs_dir2_data_hdr_t; | ||
98 | |||
99 | /* | ||
100 | * Active entry in a data block. Aligned to 8 bytes. | ||
101 | * | ||
102 | * After the variable length name field there is a 2 byte tag field, which | ||
103 | * can be accessed using xfs_dir2_data_entry_tag_p. | ||
104 | */ | ||
105 | typedef struct xfs_dir2_data_entry { | ||
106 | __be64 inumber; /* inode number */ | ||
107 | __u8 namelen; /* name length */ | ||
108 | __u8 name[]; /* name bytes, no null */ | ||
109 | /* __be16 tag; */ /* starting offset of us */ | ||
110 | } xfs_dir2_data_entry_t; | ||
111 | |||
112 | /* | ||
113 | * Unused entry in a data block. Aligned to 8 bytes. | ||
114 | * Tag appears as the last 2 bytes. | ||
115 | */ | ||
116 | typedef struct xfs_dir2_data_unused { | ||
117 | __be16 freetag; /* XFS_DIR2_DATA_FREE_TAG */ | ||
118 | __be16 length; /* total free length */ | ||
119 | /* variable offset */ | ||
120 | __be16 tag; /* starting offset of us */ | ||
121 | } xfs_dir2_data_unused_t; | ||
122 | |||
123 | /* | ||
124 | * Size of a data entry. | ||
125 | */ | ||
126 | static inline int xfs_dir2_data_entsize(int n) | ||
127 | { | ||
128 | return (int)roundup(offsetof(xfs_dir2_data_entry_t, name[0]) + (n) + \ | ||
129 | (uint)sizeof(xfs_dir2_data_off_t), XFS_DIR2_DATA_ALIGN); | ||
130 | } | ||
131 | |||
132 | /* | ||
133 | * Pointer to an entry's tag word. | ||
134 | */ | ||
135 | static inline __be16 * | ||
136 | xfs_dir2_data_entry_tag_p(xfs_dir2_data_entry_t *dep) | ||
137 | { | ||
138 | return (__be16 *)((char *)dep + | ||
139 | xfs_dir2_data_entsize(dep->namelen) - sizeof(__be16)); | ||
140 | } | ||
141 | |||
142 | /* | ||
143 | * Pointer to a freespace's tag word. | ||
144 | */ | ||
145 | static inline __be16 * | ||
146 | xfs_dir2_data_unused_tag_p(xfs_dir2_data_unused_t *dup) | ||
147 | { | ||
148 | return (__be16 *)((char *)dup + | ||
149 | be16_to_cpu(dup->length) - sizeof(__be16)); | ||
150 | } | ||
151 | |||
152 | /* | ||
153 | * Function declarations. | ||
154 | */ | ||
155 | #ifdef DEBUG | ||
156 | extern void xfs_dir2_data_check(struct xfs_inode *dp, struct xfs_dabuf *bp); | ||
157 | #else | ||
158 | #define xfs_dir2_data_check(dp,bp) | ||
159 | #endif | ||
160 | extern xfs_dir2_data_free_t *xfs_dir2_data_freeinsert(xfs_dir2_data_hdr_t *hdr, | ||
161 | xfs_dir2_data_unused_t *dup, int *loghead); | ||
162 | extern void xfs_dir2_data_freescan(struct xfs_mount *mp, | ||
163 | xfs_dir2_data_hdr_t *hdr, int *loghead); | ||
164 | extern int xfs_dir2_data_init(struct xfs_da_args *args, xfs_dir2_db_t blkno, | ||
165 | struct xfs_dabuf **bpp); | ||
166 | extern void xfs_dir2_data_log_entry(struct xfs_trans *tp, struct xfs_dabuf *bp, | ||
167 | xfs_dir2_data_entry_t *dep); | ||
168 | extern void xfs_dir2_data_log_header(struct xfs_trans *tp, | ||
169 | struct xfs_dabuf *bp); | ||
170 | extern void xfs_dir2_data_log_unused(struct xfs_trans *tp, struct xfs_dabuf *bp, | ||
171 | xfs_dir2_data_unused_t *dup); | ||
172 | extern void xfs_dir2_data_make_free(struct xfs_trans *tp, struct xfs_dabuf *bp, | ||
173 | xfs_dir2_data_aoff_t offset, | ||
174 | xfs_dir2_data_aoff_t len, int *needlogp, | ||
175 | int *needscanp); | ||
176 | extern void xfs_dir2_data_use_free(struct xfs_trans *tp, struct xfs_dabuf *bp, | ||
177 | xfs_dir2_data_unused_t *dup, | ||
178 | xfs_dir2_data_aoff_t offset, | ||
179 | xfs_dir2_data_aoff_t len, int *needlogp, | ||
180 | int *needscanp); | ||
181 | |||
182 | #endif /* __XFS_DIR2_DATA_H__ */ | ||
diff --git a/fs/xfs/xfs_dir2_format.h b/fs/xfs/xfs_dir2_format.h new file mode 100644 index 000000000000..c3c4839eebd6 --- /dev/null +++ b/fs/xfs/xfs_dir2_format.h | |||
@@ -0,0 +1,595 @@ | |||
1 | /* | ||
2 | * Copyright (c) 2000-2001,2005 Silicon Graphics, Inc. | ||
3 | * All Rights Reserved. | ||
4 | * | ||
5 | * This program is free software; you can redistribute it and/or | ||
6 | * modify it under the terms of the GNU General Public License as | ||
7 | * published by the Free Software Foundation. | ||
8 | * | ||
9 | * This program is distributed in the hope that it would be useful, | ||
10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
12 | * GNU General Public License for more details. | ||
13 | * | ||
14 | * You should have received a copy of the GNU General Public License | ||
15 | * along with this program; if not, write the Free Software Foundation, | ||
16 | * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA | ||
17 | */ | ||
18 | #ifndef __XFS_DIR2_FORMAT_H__ | ||
19 | #define __XFS_DIR2_FORMAT_H__ | ||
20 | |||
21 | /* | ||
22 | * Directory version 2. | ||
23 | * | ||
24 | * There are 4 possible formats: | ||
25 | * - shortform - embedded into the inode | ||
26 | * - single block - data with embedded leaf at the end | ||
27 | * - multiple data blocks, single leaf+freeindex block | ||
28 | * - data blocks, node and leaf blocks (btree), freeindex blocks | ||
29 | * | ||
30 | * Note: many node blocks structures and constants are shared with the attr | ||
31 | * code and defined in xfs_da_btree.h. | ||
32 | */ | ||
33 | |||
34 | #define XFS_DIR2_BLOCK_MAGIC 0x58443242 /* XD2B: single block dirs */ | ||
35 | #define XFS_DIR2_DATA_MAGIC 0x58443244 /* XD2D: multiblock dirs */ | ||
36 | #define XFS_DIR2_FREE_MAGIC 0x58443246 /* XD2F: free index blocks */ | ||
37 | |||
38 | /* | ||
39 | * Byte offset in data block and shortform entry. | ||
40 | */ | ||
41 | typedef __uint16_t xfs_dir2_data_off_t; | ||
42 | #define NULLDATAOFF 0xffffU | ||
43 | typedef uint xfs_dir2_data_aoff_t; /* argument form */ | ||
44 | |||
45 | /* | ||
46 | * Normalized offset (in a data block) of the entry, really xfs_dir2_data_off_t. | ||
47 | * Only need 16 bits, this is the byte offset into the single block form. | ||
48 | */ | ||
49 | typedef struct { __uint8_t i[2]; } __arch_pack xfs_dir2_sf_off_t; | ||
50 | |||
51 | /* | ||
52 | * Offset in data space of a data entry. | ||
53 | */ | ||
54 | typedef __uint32_t xfs_dir2_dataptr_t; | ||
55 | #define XFS_DIR2_MAX_DATAPTR ((xfs_dir2_dataptr_t)0xffffffff) | ||
56 | #define XFS_DIR2_NULL_DATAPTR ((xfs_dir2_dataptr_t)0) | ||
57 | |||
58 | /* | ||
59 | * Byte offset in a directory. | ||
60 | */ | ||
61 | typedef xfs_off_t xfs_dir2_off_t; | ||
62 | |||
63 | /* | ||
64 | * Directory block number (logical dirblk in file) | ||
65 | */ | ||
66 | typedef __uint32_t xfs_dir2_db_t; | ||
67 | |||
68 | /* | ||
69 | * Inode number stored as 8 8-bit values. | ||
70 | */ | ||
71 | typedef struct { __uint8_t i[8]; } xfs_dir2_ino8_t; | ||
72 | |||
73 | /* | ||
74 | * Inode number stored as 4 8-bit values. | ||
75 | * Works a lot of the time, when all the inode numbers in a directory | ||
76 | * fit in 32 bits. | ||
77 | */ | ||
78 | typedef struct { __uint8_t i[4]; } xfs_dir2_ino4_t; | ||
79 | |||
80 | typedef union { | ||
81 | xfs_dir2_ino8_t i8; | ||
82 | xfs_dir2_ino4_t i4; | ||
83 | } xfs_dir2_inou_t; | ||
84 | #define XFS_DIR2_MAX_SHORT_INUM ((xfs_ino_t)0xffffffffULL) | ||
85 | |||
86 | /* | ||
87 | * Directory layout when stored internal to an inode. | ||
88 | * | ||
89 | * Small directories are packed as tightly as possible so as to fit into the | ||
90 | * literal area of the inode. These "shortform" directories consist of a | ||
91 | * single xfs_dir2_sf_hdr header followed by zero or more xfs_dir2_sf_entry | ||
92 | * structures. Due the different inode number storage size and the variable | ||
93 | * length name field in the xfs_dir2_sf_entry all these structure are | ||
94 | * variable length, and the accessors in this file should be used to iterate | ||
95 | * over them. | ||
96 | */ | ||
97 | typedef struct xfs_dir2_sf_hdr { | ||
98 | __uint8_t count; /* count of entries */ | ||
99 | __uint8_t i8count; /* count of 8-byte inode #s */ | ||
100 | xfs_dir2_inou_t parent; /* parent dir inode number */ | ||
101 | } __arch_pack xfs_dir2_sf_hdr_t; | ||
102 | |||
103 | typedef struct xfs_dir2_sf_entry { | ||
104 | __u8 namelen; /* actual name length */ | ||
105 | xfs_dir2_sf_off_t offset; /* saved offset */ | ||
106 | __u8 name[]; /* name, variable size */ | ||
107 | /* | ||
108 | * A xfs_dir2_ino8_t or xfs_dir2_ino4_t follows here, at a | ||
109 | * variable offset after the name. | ||
110 | */ | ||
111 | } __arch_pack xfs_dir2_sf_entry_t; | ||
112 | |||
113 | static inline int xfs_dir2_sf_hdr_size(int i8count) | ||
114 | { | ||
115 | return sizeof(struct xfs_dir2_sf_hdr) - | ||
116 | (i8count == 0) * | ||
117 | (sizeof(xfs_dir2_ino8_t) - sizeof(xfs_dir2_ino4_t)); | ||
118 | } | ||
119 | |||
120 | static inline xfs_dir2_data_aoff_t | ||
121 | xfs_dir2_sf_get_offset(xfs_dir2_sf_entry_t *sfep) | ||
122 | { | ||
123 | return get_unaligned_be16(&sfep->offset.i); | ||
124 | } | ||
125 | |||
126 | static inline void | ||
127 | xfs_dir2_sf_put_offset(xfs_dir2_sf_entry_t *sfep, xfs_dir2_data_aoff_t off) | ||
128 | { | ||
129 | put_unaligned_be16(off, &sfep->offset.i); | ||
130 | } | ||
131 | |||
132 | static inline int | ||
133 | xfs_dir2_sf_entsize(struct xfs_dir2_sf_hdr *hdr, int len) | ||
134 | { | ||
135 | return sizeof(struct xfs_dir2_sf_entry) + /* namelen + offset */ | ||
136 | len + /* name */ | ||
137 | (hdr->i8count ? /* ino */ | ||
138 | sizeof(xfs_dir2_ino8_t) : | ||
139 | sizeof(xfs_dir2_ino4_t)); | ||
140 | } | ||
141 | |||
142 | static inline struct xfs_dir2_sf_entry * | ||
143 | xfs_dir2_sf_firstentry(struct xfs_dir2_sf_hdr *hdr) | ||
144 | { | ||
145 | return (struct xfs_dir2_sf_entry *) | ||
146 | ((char *)hdr + xfs_dir2_sf_hdr_size(hdr->i8count)); | ||
147 | } | ||
148 | |||
149 | static inline struct xfs_dir2_sf_entry * | ||
150 | xfs_dir2_sf_nextentry(struct xfs_dir2_sf_hdr *hdr, | ||
151 | struct xfs_dir2_sf_entry *sfep) | ||
152 | { | ||
153 | return (struct xfs_dir2_sf_entry *) | ||
154 | ((char *)sfep + xfs_dir2_sf_entsize(hdr, sfep->namelen)); | ||
155 | } | ||
156 | |||
157 | |||
158 | /* | ||
159 | * Data block structures. | ||
160 | * | ||
161 | * A pure data block looks like the following drawing on disk: | ||
162 | * | ||
163 | * +-------------------------------------------------+ | ||
164 | * | xfs_dir2_data_hdr_t | | ||
165 | * +-------------------------------------------------+ | ||
166 | * | xfs_dir2_data_entry_t OR xfs_dir2_data_unused_t | | ||
167 | * | xfs_dir2_data_entry_t OR xfs_dir2_data_unused_t | | ||
168 | * | xfs_dir2_data_entry_t OR xfs_dir2_data_unused_t | | ||
169 | * | ... | | ||
170 | * +-------------------------------------------------+ | ||
171 | * | unused space | | ||
172 | * +-------------------------------------------------+ | ||
173 | * | ||
174 | * As all the entries are variable size structures the accessors below should | ||
175 | * be used to iterate over them. | ||
176 | * | ||
177 | * In addition to the pure data blocks for the data and node formats, | ||
178 | * most structures are also used for the combined data/freespace "block" | ||
179 | * format below. | ||
180 | */ | ||
181 | |||
182 | #define XFS_DIR2_DATA_ALIGN_LOG 3 /* i.e., 8 bytes */ | ||
183 | #define XFS_DIR2_DATA_ALIGN (1 << XFS_DIR2_DATA_ALIGN_LOG) | ||
184 | #define XFS_DIR2_DATA_FREE_TAG 0xffff | ||
185 | #define XFS_DIR2_DATA_FD_COUNT 3 | ||
186 | |||
187 | /* | ||
188 | * Directory address space divided into sections, | ||
189 | * spaces separated by 32GB. | ||
190 | */ | ||
191 | #define XFS_DIR2_SPACE_SIZE (1ULL << (32 + XFS_DIR2_DATA_ALIGN_LOG)) | ||
192 | #define XFS_DIR2_DATA_SPACE 0 | ||
193 | #define XFS_DIR2_DATA_OFFSET (XFS_DIR2_DATA_SPACE * XFS_DIR2_SPACE_SIZE) | ||
194 | #define XFS_DIR2_DATA_FIRSTDB(mp) \ | ||
195 | xfs_dir2_byte_to_db(mp, XFS_DIR2_DATA_OFFSET) | ||
196 | |||
197 | /* | ||
198 | * Offsets of . and .. in data space (always block 0) | ||
199 | */ | ||
200 | #define XFS_DIR2_DATA_DOT_OFFSET \ | ||
201 | ((xfs_dir2_data_aoff_t)sizeof(struct xfs_dir2_data_hdr)) | ||
202 | #define XFS_DIR2_DATA_DOTDOT_OFFSET \ | ||
203 | (XFS_DIR2_DATA_DOT_OFFSET + xfs_dir2_data_entsize(1)) | ||
204 | #define XFS_DIR2_DATA_FIRST_OFFSET \ | ||
205 | (XFS_DIR2_DATA_DOTDOT_OFFSET + xfs_dir2_data_entsize(2)) | ||
206 | |||
207 | /* | ||
208 | * Describe a free area in the data block. | ||
209 | * | ||
210 | * The freespace will be formatted as a xfs_dir2_data_unused_t. | ||
211 | */ | ||
212 | typedef struct xfs_dir2_data_free { | ||
213 | __be16 offset; /* start of freespace */ | ||
214 | __be16 length; /* length of freespace */ | ||
215 | } xfs_dir2_data_free_t; | ||
216 | |||
217 | /* | ||
218 | * Header for the data blocks. | ||
219 | * | ||
220 | * The code knows that XFS_DIR2_DATA_FD_COUNT is 3. | ||
221 | */ | ||
222 | typedef struct xfs_dir2_data_hdr { | ||
223 | __be32 magic; /* XFS_DIR2_DATA_MAGIC or */ | ||
224 | /* XFS_DIR2_BLOCK_MAGIC */ | ||
225 | xfs_dir2_data_free_t bestfree[XFS_DIR2_DATA_FD_COUNT]; | ||
226 | } xfs_dir2_data_hdr_t; | ||
227 | |||
228 | /* | ||
229 | * Active entry in a data block. | ||
230 | * | ||
231 | * Aligned to 8 bytes. After the variable length name field there is a | ||
232 | * 2 byte tag field, which can be accessed using xfs_dir2_data_entry_tag_p. | ||
233 | */ | ||
234 | typedef struct xfs_dir2_data_entry { | ||
235 | __be64 inumber; /* inode number */ | ||
236 | __u8 namelen; /* name length */ | ||
237 | __u8 name[]; /* name bytes, no null */ | ||
238 | /* __be16 tag; */ /* starting offset of us */ | ||
239 | } xfs_dir2_data_entry_t; | ||
240 | |||
241 | /* | ||
242 | * Unused entry in a data block. | ||
243 | * | ||
244 | * Aligned to 8 bytes. Tag appears as the last 2 bytes and must be accessed | ||
245 | * using xfs_dir2_data_unused_tag_p. | ||
246 | */ | ||
247 | typedef struct xfs_dir2_data_unused { | ||
248 | __be16 freetag; /* XFS_DIR2_DATA_FREE_TAG */ | ||
249 | __be16 length; /* total free length */ | ||
250 | /* variable offset */ | ||
251 | __be16 tag; /* starting offset of us */ | ||
252 | } xfs_dir2_data_unused_t; | ||
253 | |||
254 | /* | ||
255 | * Size of a data entry. | ||
256 | */ | ||
257 | static inline int xfs_dir2_data_entsize(int n) | ||
258 | { | ||
259 | return (int)roundup(offsetof(struct xfs_dir2_data_entry, name[0]) + n + | ||
260 | (uint)sizeof(xfs_dir2_data_off_t), XFS_DIR2_DATA_ALIGN); | ||
261 | } | ||
262 | |||
263 | /* | ||
264 | * Pointer to an entry's tag word. | ||
265 | */ | ||
266 | static inline __be16 * | ||
267 | xfs_dir2_data_entry_tag_p(struct xfs_dir2_data_entry *dep) | ||
268 | { | ||
269 | return (__be16 *)((char *)dep + | ||
270 | xfs_dir2_data_entsize(dep->namelen) - sizeof(__be16)); | ||
271 | } | ||
272 | |||
273 | /* | ||
274 | * Pointer to a freespace's tag word. | ||
275 | */ | ||
276 | static inline __be16 * | ||
277 | xfs_dir2_data_unused_tag_p(struct xfs_dir2_data_unused *dup) | ||
278 | { | ||
279 | return (__be16 *)((char *)dup + | ||
280 | be16_to_cpu(dup->length) - sizeof(__be16)); | ||
281 | } | ||
282 | |||
283 | /* | ||
284 | * Leaf block structures. | ||
285 | * | ||
286 | * A pure leaf block looks like the following drawing on disk: | ||
287 | * | ||
288 | * +---------------------------+ | ||
289 | * | xfs_dir2_leaf_hdr_t | | ||
290 | * +---------------------------+ | ||
291 | * | xfs_dir2_leaf_entry_t | | ||
292 | * | xfs_dir2_leaf_entry_t | | ||
293 | * | xfs_dir2_leaf_entry_t | | ||
294 | * | xfs_dir2_leaf_entry_t | | ||
295 | * | ... | | ||
296 | * +---------------------------+ | ||
297 | * | xfs_dir2_data_off_t | | ||
298 | * | xfs_dir2_data_off_t | | ||
299 | * | xfs_dir2_data_off_t | | ||
300 | * | ... | | ||
301 | * +---------------------------+ | ||
302 | * | xfs_dir2_leaf_tail_t | | ||
303 | * +---------------------------+ | ||
304 | * | ||
305 | * The xfs_dir2_data_off_t members (bests) and tail are at the end of the block | ||
306 | * for single-leaf (magic = XFS_DIR2_LEAF1_MAGIC) blocks only, but not present | ||
307 | * for directories with separate leaf nodes and free space blocks | ||
308 | * (magic = XFS_DIR2_LEAFN_MAGIC). | ||
309 | * | ||
310 | * As all the entries are variable size structures the accessors below should | ||
311 | * be used to iterate over them. | ||
312 | */ | ||
313 | |||
314 | /* | ||
315 | * Offset of the leaf/node space. First block in this space | ||
316 | * is the btree root. | ||
317 | */ | ||
318 | #define XFS_DIR2_LEAF_SPACE 1 | ||
319 | #define XFS_DIR2_LEAF_OFFSET (XFS_DIR2_LEAF_SPACE * XFS_DIR2_SPACE_SIZE) | ||
320 | #define XFS_DIR2_LEAF_FIRSTDB(mp) \ | ||
321 | xfs_dir2_byte_to_db(mp, XFS_DIR2_LEAF_OFFSET) | ||
322 | |||
323 | /* | ||
324 | * Leaf block header. | ||
325 | */ | ||
326 | typedef struct xfs_dir2_leaf_hdr { | ||
327 | xfs_da_blkinfo_t info; /* header for da routines */ | ||
328 | __be16 count; /* count of entries */ | ||
329 | __be16 stale; /* count of stale entries */ | ||
330 | } xfs_dir2_leaf_hdr_t; | ||
331 | |||
332 | /* | ||
333 | * Leaf block entry. | ||
334 | */ | ||
335 | typedef struct xfs_dir2_leaf_entry { | ||
336 | __be32 hashval; /* hash value of name */ | ||
337 | __be32 address; /* address of data entry */ | ||
338 | } xfs_dir2_leaf_entry_t; | ||
339 | |||
340 | /* | ||
341 | * Leaf block tail. | ||
342 | */ | ||
343 | typedef struct xfs_dir2_leaf_tail { | ||
344 | __be32 bestcount; | ||
345 | } xfs_dir2_leaf_tail_t; | ||
346 | |||
347 | /* | ||
348 | * Leaf block. | ||
349 | */ | ||
350 | typedef struct xfs_dir2_leaf { | ||
351 | xfs_dir2_leaf_hdr_t hdr; /* leaf header */ | ||
352 | xfs_dir2_leaf_entry_t ents[]; /* entries */ | ||
353 | } xfs_dir2_leaf_t; | ||
354 | |||
355 | /* | ||
356 | * DB blocks here are logical directory block numbers, not filesystem blocks. | ||
357 | */ | ||
358 | |||
359 | static inline int xfs_dir2_max_leaf_ents(struct xfs_mount *mp) | ||
360 | { | ||
361 | return (mp->m_dirblksize - (uint)sizeof(struct xfs_dir2_leaf_hdr)) / | ||
362 | (uint)sizeof(struct xfs_dir2_leaf_entry); | ||
363 | } | ||
364 | |||
365 | /* | ||
366 | * Get address of the bestcount field in the single-leaf block. | ||
367 | */ | ||
368 | static inline struct xfs_dir2_leaf_tail * | ||
369 | xfs_dir2_leaf_tail_p(struct xfs_mount *mp, struct xfs_dir2_leaf *lp) | ||
370 | { | ||
371 | return (struct xfs_dir2_leaf_tail *) | ||
372 | ((char *)lp + mp->m_dirblksize - | ||
373 | sizeof(struct xfs_dir2_leaf_tail)); | ||
374 | } | ||
375 | |||
376 | /* | ||
377 | * Get address of the bests array in the single-leaf block. | ||
378 | */ | ||
379 | static inline __be16 * | ||
380 | xfs_dir2_leaf_bests_p(struct xfs_dir2_leaf_tail *ltp) | ||
381 | { | ||
382 | return (__be16 *)ltp - be32_to_cpu(ltp->bestcount); | ||
383 | } | ||
384 | |||
385 | /* | ||
386 | * Convert dataptr to byte in file space | ||
387 | */ | ||
388 | static inline xfs_dir2_off_t | ||
389 | xfs_dir2_dataptr_to_byte(struct xfs_mount *mp, xfs_dir2_dataptr_t dp) | ||
390 | { | ||
391 | return (xfs_dir2_off_t)dp << XFS_DIR2_DATA_ALIGN_LOG; | ||
392 | } | ||
393 | |||
394 | /* | ||
395 | * Convert byte in file space to dataptr. It had better be aligned. | ||
396 | */ | ||
397 | static inline xfs_dir2_dataptr_t | ||
398 | xfs_dir2_byte_to_dataptr(struct xfs_mount *mp, xfs_dir2_off_t by) | ||
399 | { | ||
400 | return (xfs_dir2_dataptr_t)(by >> XFS_DIR2_DATA_ALIGN_LOG); | ||
401 | } | ||
402 | |||
403 | /* | ||
404 | * Convert byte in space to (DB) block | ||
405 | */ | ||
406 | static inline xfs_dir2_db_t | ||
407 | xfs_dir2_byte_to_db(struct xfs_mount *mp, xfs_dir2_off_t by) | ||
408 | { | ||
409 | return (xfs_dir2_db_t) | ||
410 | (by >> (mp->m_sb.sb_blocklog + mp->m_sb.sb_dirblklog)); | ||
411 | } | ||
412 | |||
413 | /* | ||
414 | * Convert dataptr to a block number | ||
415 | */ | ||
416 | static inline xfs_dir2_db_t | ||
417 | xfs_dir2_dataptr_to_db(struct xfs_mount *mp, xfs_dir2_dataptr_t dp) | ||
418 | { | ||
419 | return xfs_dir2_byte_to_db(mp, xfs_dir2_dataptr_to_byte(mp, dp)); | ||
420 | } | ||
421 | |||
422 | /* | ||
423 | * Convert byte in space to offset in a block | ||
424 | */ | ||
425 | static inline xfs_dir2_data_aoff_t | ||
426 | xfs_dir2_byte_to_off(struct xfs_mount *mp, xfs_dir2_off_t by) | ||
427 | { | ||
428 | return (xfs_dir2_data_aoff_t)(by & | ||
429 | ((1 << (mp->m_sb.sb_blocklog + mp->m_sb.sb_dirblklog)) - 1)); | ||
430 | } | ||
431 | |||
432 | /* | ||
433 | * Convert dataptr to a byte offset in a block | ||
434 | */ | ||
435 | static inline xfs_dir2_data_aoff_t | ||
436 | xfs_dir2_dataptr_to_off(struct xfs_mount *mp, xfs_dir2_dataptr_t dp) | ||
437 | { | ||
438 | return xfs_dir2_byte_to_off(mp, xfs_dir2_dataptr_to_byte(mp, dp)); | ||
439 | } | ||
440 | |||
441 | /* | ||
442 | * Convert block and offset to byte in space | ||
443 | */ | ||
444 | static inline xfs_dir2_off_t | ||
445 | xfs_dir2_db_off_to_byte(struct xfs_mount *mp, xfs_dir2_db_t db, | ||
446 | xfs_dir2_data_aoff_t o) | ||
447 | { | ||
448 | return ((xfs_dir2_off_t)db << | ||
449 | (mp->m_sb.sb_blocklog + mp->m_sb.sb_dirblklog)) + o; | ||
450 | } | ||
451 | |||
452 | /* | ||
453 | * Convert block (DB) to block (dablk) | ||
454 | */ | ||
455 | static inline xfs_dablk_t | ||
456 | xfs_dir2_db_to_da(struct xfs_mount *mp, xfs_dir2_db_t db) | ||
457 | { | ||
458 | return (xfs_dablk_t)(db << mp->m_sb.sb_dirblklog); | ||
459 | } | ||
460 | |||
461 | /* | ||
462 | * Convert byte in space to (DA) block | ||
463 | */ | ||
464 | static inline xfs_dablk_t | ||
465 | xfs_dir2_byte_to_da(struct xfs_mount *mp, xfs_dir2_off_t by) | ||
466 | { | ||
467 | return xfs_dir2_db_to_da(mp, xfs_dir2_byte_to_db(mp, by)); | ||
468 | } | ||
469 | |||
470 | /* | ||
471 | * Convert block and offset to dataptr | ||
472 | */ | ||
473 | static inline xfs_dir2_dataptr_t | ||
474 | xfs_dir2_db_off_to_dataptr(struct xfs_mount *mp, xfs_dir2_db_t db, | ||
475 | xfs_dir2_data_aoff_t o) | ||
476 | { | ||
477 | return xfs_dir2_byte_to_dataptr(mp, xfs_dir2_db_off_to_byte(mp, db, o)); | ||
478 | } | ||
479 | |||
480 | /* | ||
481 | * Convert block (dablk) to block (DB) | ||
482 | */ | ||
483 | static inline xfs_dir2_db_t | ||
484 | xfs_dir2_da_to_db(struct xfs_mount *mp, xfs_dablk_t da) | ||
485 | { | ||
486 | return (xfs_dir2_db_t)(da >> mp->m_sb.sb_dirblklog); | ||
487 | } | ||
488 | |||
489 | /* | ||
490 | * Convert block (dablk) to byte offset in space | ||
491 | */ | ||
492 | static inline xfs_dir2_off_t | ||
493 | xfs_dir2_da_to_byte(struct xfs_mount *mp, xfs_dablk_t da) | ||
494 | { | ||
495 | return xfs_dir2_db_off_to_byte(mp, xfs_dir2_da_to_db(mp, da), 0); | ||
496 | } | ||
497 | |||
498 | /* | ||
499 | * Free space block defintions for the node format. | ||
500 | */ | ||
501 | |||
502 | /* | ||
503 | * Offset of the freespace index. | ||
504 | */ | ||
505 | #define XFS_DIR2_FREE_SPACE 2 | ||
506 | #define XFS_DIR2_FREE_OFFSET (XFS_DIR2_FREE_SPACE * XFS_DIR2_SPACE_SIZE) | ||
507 | #define XFS_DIR2_FREE_FIRSTDB(mp) \ | ||
508 | xfs_dir2_byte_to_db(mp, XFS_DIR2_FREE_OFFSET) | ||
509 | |||
510 | typedef struct xfs_dir2_free_hdr { | ||
511 | __be32 magic; /* XFS_DIR2_FREE_MAGIC */ | ||
512 | __be32 firstdb; /* db of first entry */ | ||
513 | __be32 nvalid; /* count of valid entries */ | ||
514 | __be32 nused; /* count of used entries */ | ||
515 | } xfs_dir2_free_hdr_t; | ||
516 | |||
517 | typedef struct xfs_dir2_free { | ||
518 | xfs_dir2_free_hdr_t hdr; /* block header */ | ||
519 | __be16 bests[1]; /* best free counts */ | ||
520 | /* unused entries are -1 */ | ||
521 | } xfs_dir2_free_t; | ||
522 | |||
523 | #define XFS_DIR2_MAX_FREE_BESTS(mp) \ | ||
524 | (((mp)->m_dirblksize - (uint)sizeof(struct xfs_dir2_free_hdr)) / \ | ||
525 | (uint)sizeof(xfs_dir2_data_off_t)) | ||
526 | |||
527 | /* | ||
528 | * Convert data space db to the corresponding free db. | ||
529 | */ | ||
530 | static inline xfs_dir2_db_t | ||
531 | xfs_dir2_db_to_fdb(struct xfs_mount *mp, xfs_dir2_db_t db) | ||
532 | { | ||
533 | return XFS_DIR2_FREE_FIRSTDB(mp) + db / XFS_DIR2_MAX_FREE_BESTS(mp); | ||
534 | } | ||
535 | |||
536 | /* | ||
537 | * Convert data space db to the corresponding index in a free db. | ||
538 | */ | ||
539 | static inline int | ||
540 | xfs_dir2_db_to_fdindex(struct xfs_mount *mp, xfs_dir2_db_t db) | ||
541 | { | ||
542 | return db % XFS_DIR2_MAX_FREE_BESTS(mp); | ||
543 | } | ||
544 | |||
545 | /* | ||
546 | * Single block format. | ||
547 | * | ||
548 | * The single block format looks like the following drawing on disk: | ||
549 | * | ||
550 | * +-------------------------------------------------+ | ||
551 | * | xfs_dir2_data_hdr_t | | ||
552 | * +-------------------------------------------------+ | ||
553 | * | xfs_dir2_data_entry_t OR xfs_dir2_data_unused_t | | ||
554 | * | xfs_dir2_data_entry_t OR xfs_dir2_data_unused_t | | ||
555 | * | xfs_dir2_data_entry_t OR xfs_dir2_data_unused_t : | ||
556 | * | ... | | ||
557 | * +-------------------------------------------------+ | ||
558 | * | unused space | | ||
559 | * +-------------------------------------------------+ | ||
560 | * | ... | | ||
561 | * | xfs_dir2_leaf_entry_t | | ||
562 | * | xfs_dir2_leaf_entry_t | | ||
563 | * +-------------------------------------------------+ | ||
564 | * | xfs_dir2_block_tail_t | | ||
565 | * +-------------------------------------------------+ | ||
566 | * | ||
567 | * As all the entries are variable size structures the accessors below should | ||
568 | * be used to iterate over them. | ||
569 | */ | ||
570 | |||
571 | typedef struct xfs_dir2_block_tail { | ||
572 | __be32 count; /* count of leaf entries */ | ||
573 | __be32 stale; /* count of stale lf entries */ | ||
574 | } xfs_dir2_block_tail_t; | ||
575 | |||
576 | /* | ||
577 | * Pointer to the leaf header embedded in a data block (1-block format) | ||
578 | */ | ||
579 | static inline struct xfs_dir2_block_tail * | ||
580 | xfs_dir2_block_tail_p(struct xfs_mount *mp, struct xfs_dir2_data_hdr *hdr) | ||
581 | { | ||
582 | return ((struct xfs_dir2_block_tail *) | ||
583 | ((char *)hdr + mp->m_dirblksize)) - 1; | ||
584 | } | ||
585 | |||
586 | /* | ||
587 | * Pointer to the leaf entries embedded in a data block (1-block format) | ||
588 | */ | ||
589 | static inline struct xfs_dir2_leaf_entry * | ||
590 | xfs_dir2_block_leaf_p(struct xfs_dir2_block_tail *btp) | ||
591 | { | ||
592 | return ((struct xfs_dir2_leaf_entry *)btp) - be32_to_cpu(btp->count); | ||
593 | } | ||
594 | |||
595 | #endif /* __XFS_DIR2_FORMAT_H__ */ | ||
diff --git a/fs/xfs/xfs_dir2_leaf.c b/fs/xfs/xfs_dir2_leaf.c index d629b888ca28..487036d3751b 100644 --- a/fs/xfs/xfs_dir2_leaf.c +++ b/fs/xfs/xfs_dir2_leaf.c | |||
@@ -24,18 +24,14 @@ | |||
24 | #include "xfs_trans.h" | 24 | #include "xfs_trans.h" |
25 | #include "xfs_sb.h" | 25 | #include "xfs_sb.h" |
26 | #include "xfs_ag.h" | 26 | #include "xfs_ag.h" |
27 | #include "xfs_dir2.h" | ||
28 | #include "xfs_mount.h" | 27 | #include "xfs_mount.h" |
29 | #include "xfs_da_btree.h" | 28 | #include "xfs_da_btree.h" |
30 | #include "xfs_bmap_btree.h" | 29 | #include "xfs_bmap_btree.h" |
31 | #include "xfs_dir2_sf.h" | ||
32 | #include "xfs_dinode.h" | 30 | #include "xfs_dinode.h" |
33 | #include "xfs_inode.h" | 31 | #include "xfs_inode.h" |
34 | #include "xfs_bmap.h" | 32 | #include "xfs_bmap.h" |
35 | #include "xfs_dir2_data.h" | 33 | #include "xfs_dir2_format.h" |
36 | #include "xfs_dir2_leaf.h" | 34 | #include "xfs_dir2_priv.h" |
37 | #include "xfs_dir2_block.h" | ||
38 | #include "xfs_dir2_node.h" | ||
39 | #include "xfs_error.h" | 35 | #include "xfs_error.h" |
40 | #include "xfs_trace.h" | 36 | #include "xfs_trace.h" |
41 | 37 | ||
diff --git a/fs/xfs/xfs_dir2_leaf.h b/fs/xfs/xfs_dir2_leaf.h deleted file mode 100644 index 140281adc7e5..000000000000 --- a/fs/xfs/xfs_dir2_leaf.h +++ /dev/null | |||
@@ -1,281 +0,0 @@ | |||
1 | /* | ||
2 | * Copyright (c) 2000-2001,2005 Silicon Graphics, Inc. | ||
3 | * All Rights Reserved. | ||
4 | * | ||
5 | * This program is free software; you can redistribute it and/or | ||
6 | * modify it under the terms of the GNU General Public License as | ||
7 | * published by the Free Software Foundation. | ||
8 | * | ||
9 | * This program is distributed in the hope that it would be useful, | ||
10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
12 | * GNU General Public License for more details. | ||
13 | * | ||
14 | * You should have received a copy of the GNU General Public License | ||
15 | * along with this program; if not, write the Free Software Foundation, | ||
16 | * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA | ||
17 | */ | ||
18 | #ifndef __XFS_DIR2_LEAF_H__ | ||
19 | #define __XFS_DIR2_LEAF_H__ | ||
20 | |||
21 | /* | ||
22 | * Directory format 2, leaf block structures. | ||
23 | * | ||
24 | * A pure data block looks like the following drawing on disk: | ||
25 | * | ||
26 | * +---------------------------+ | ||
27 | * | xfs_dir2_leaf_hdr_t | | ||
28 | * +---------------------------+ | ||
29 | * | xfs_dir2_leaf_entry_t | | ||
30 | * | xfs_dir2_leaf_entry_t | | ||
31 | * | xfs_dir2_leaf_entry_t | | ||
32 | * | xfs_dir2_leaf_entry_t | | ||
33 | * | ... | | ||
34 | * +---------------------------+ | ||
35 | * | xfs_dir2_data_off_t | | ||
36 | * | xfs_dir2_data_off_t | | ||
37 | * | xfs_dir2_data_off_t | | ||
38 | * | ... | | ||
39 | * +---------------------------+ | ||
40 | * | xfs_dir2_leaf_tail_t | | ||
41 | * +---------------------------+ | ||
42 | * | ||
43 | * The bests (xfs_dir2_data_off_t members) and tail are at the end of the | ||
44 | * block for single-leaf only (magic = XFS_DIR2_LEAF1_MAGIC not | ||
45 | * XFS_DIR2_LEAFN_MAGIC). | ||
46 | * | ||
47 | * As all the entries are variable size structures the accessors in this | ||
48 | * file should be used to iterate over them. | ||
49 | */ | ||
50 | |||
51 | struct uio; | ||
52 | struct xfs_dabuf; | ||
53 | struct xfs_da_args; | ||
54 | struct xfs_inode; | ||
55 | struct xfs_mount; | ||
56 | struct xfs_trans; | ||
57 | |||
58 | /* | ||
59 | * Offset of the leaf/node space. First block in this space | ||
60 | * is the btree root. | ||
61 | */ | ||
62 | #define XFS_DIR2_LEAF_SPACE 1 | ||
63 | #define XFS_DIR2_LEAF_OFFSET (XFS_DIR2_LEAF_SPACE * XFS_DIR2_SPACE_SIZE) | ||
64 | #define XFS_DIR2_LEAF_FIRSTDB(mp) \ | ||
65 | xfs_dir2_byte_to_db(mp, XFS_DIR2_LEAF_OFFSET) | ||
66 | |||
67 | /* | ||
68 | * Offset in data space of a data entry. | ||
69 | */ | ||
70 | typedef __uint32_t xfs_dir2_dataptr_t; | ||
71 | #define XFS_DIR2_MAX_DATAPTR ((xfs_dir2_dataptr_t)0xffffffff) | ||
72 | #define XFS_DIR2_NULL_DATAPTR ((xfs_dir2_dataptr_t)0) | ||
73 | |||
74 | /* | ||
75 | * Leaf block header. | ||
76 | */ | ||
77 | typedef struct xfs_dir2_leaf_hdr { | ||
78 | xfs_da_blkinfo_t info; /* header for da routines */ | ||
79 | __be16 count; /* count of entries */ | ||
80 | __be16 stale; /* count of stale entries */ | ||
81 | } xfs_dir2_leaf_hdr_t; | ||
82 | |||
83 | /* | ||
84 | * Leaf block entry. | ||
85 | */ | ||
86 | typedef struct xfs_dir2_leaf_entry { | ||
87 | __be32 hashval; /* hash value of name */ | ||
88 | __be32 address; /* address of data entry */ | ||
89 | } xfs_dir2_leaf_entry_t; | ||
90 | |||
91 | /* | ||
92 | * Leaf block tail. | ||
93 | */ | ||
94 | typedef struct xfs_dir2_leaf_tail { | ||
95 | __be32 bestcount; | ||
96 | } xfs_dir2_leaf_tail_t; | ||
97 | |||
98 | /* | ||
99 | * Leaf block. | ||
100 | */ | ||
101 | typedef struct xfs_dir2_leaf { | ||
102 | xfs_dir2_leaf_hdr_t hdr; /* leaf header */ | ||
103 | xfs_dir2_leaf_entry_t ents[]; /* entries */ | ||
104 | } xfs_dir2_leaf_t; | ||
105 | |||
106 | /* | ||
107 | * DB blocks here are logical directory block numbers, not filesystem blocks. | ||
108 | */ | ||
109 | |||
110 | static inline int xfs_dir2_max_leaf_ents(struct xfs_mount *mp) | ||
111 | { | ||
112 | return (int)(((mp)->m_dirblksize - (uint)sizeof(xfs_dir2_leaf_hdr_t)) / | ||
113 | (uint)sizeof(xfs_dir2_leaf_entry_t)); | ||
114 | } | ||
115 | |||
116 | /* | ||
117 | * Get address of the bestcount field in the single-leaf block. | ||
118 | */ | ||
119 | static inline xfs_dir2_leaf_tail_t * | ||
120 | xfs_dir2_leaf_tail_p(struct xfs_mount *mp, xfs_dir2_leaf_t *lp) | ||
121 | { | ||
122 | return (xfs_dir2_leaf_tail_t *) | ||
123 | ((char *)(lp) + (mp)->m_dirblksize - | ||
124 | (uint)sizeof(xfs_dir2_leaf_tail_t)); | ||
125 | } | ||
126 | |||
127 | /* | ||
128 | * Get address of the bests array in the single-leaf block. | ||
129 | */ | ||
130 | static inline __be16 * | ||
131 | xfs_dir2_leaf_bests_p(xfs_dir2_leaf_tail_t *ltp) | ||
132 | { | ||
133 | return (__be16 *)ltp - be32_to_cpu(ltp->bestcount); | ||
134 | } | ||
135 | |||
136 | /* | ||
137 | * Convert dataptr to byte in file space | ||
138 | */ | ||
139 | static inline xfs_dir2_off_t | ||
140 | xfs_dir2_dataptr_to_byte(struct xfs_mount *mp, xfs_dir2_dataptr_t dp) | ||
141 | { | ||
142 | return (xfs_dir2_off_t)(dp) << XFS_DIR2_DATA_ALIGN_LOG; | ||
143 | } | ||
144 | |||
145 | /* | ||
146 | * Convert byte in file space to dataptr. It had better be aligned. | ||
147 | */ | ||
148 | static inline xfs_dir2_dataptr_t | ||
149 | xfs_dir2_byte_to_dataptr(struct xfs_mount *mp, xfs_dir2_off_t by) | ||
150 | { | ||
151 | return (xfs_dir2_dataptr_t)((by) >> XFS_DIR2_DATA_ALIGN_LOG); | ||
152 | } | ||
153 | |||
154 | /* | ||
155 | * Convert byte in space to (DB) block | ||
156 | */ | ||
157 | static inline xfs_dir2_db_t | ||
158 | xfs_dir2_byte_to_db(struct xfs_mount *mp, xfs_dir2_off_t by) | ||
159 | { | ||
160 | return (xfs_dir2_db_t)((by) >> \ | ||
161 | ((mp)->m_sb.sb_blocklog + (mp)->m_sb.sb_dirblklog)); | ||
162 | } | ||
163 | |||
164 | /* | ||
165 | * Convert dataptr to a block number | ||
166 | */ | ||
167 | static inline xfs_dir2_db_t | ||
168 | xfs_dir2_dataptr_to_db(struct xfs_mount *mp, xfs_dir2_dataptr_t dp) | ||
169 | { | ||
170 | return xfs_dir2_byte_to_db(mp, xfs_dir2_dataptr_to_byte(mp, dp)); | ||
171 | } | ||
172 | |||
173 | /* | ||
174 | * Convert byte in space to offset in a block | ||
175 | */ | ||
176 | static inline xfs_dir2_data_aoff_t | ||
177 | xfs_dir2_byte_to_off(struct xfs_mount *mp, xfs_dir2_off_t by) | ||
178 | { | ||
179 | return (xfs_dir2_data_aoff_t)((by) & \ | ||
180 | ((1 << ((mp)->m_sb.sb_blocklog + (mp)->m_sb.sb_dirblklog)) - 1)); | ||
181 | } | ||
182 | |||
183 | /* | ||
184 | * Convert dataptr to a byte offset in a block | ||
185 | */ | ||
186 | static inline xfs_dir2_data_aoff_t | ||
187 | xfs_dir2_dataptr_to_off(struct xfs_mount *mp, xfs_dir2_dataptr_t dp) | ||
188 | { | ||
189 | return xfs_dir2_byte_to_off(mp, xfs_dir2_dataptr_to_byte(mp, dp)); | ||
190 | } | ||
191 | |||
192 | /* | ||
193 | * Convert block and offset to byte in space | ||
194 | */ | ||
195 | static inline xfs_dir2_off_t | ||
196 | xfs_dir2_db_off_to_byte(struct xfs_mount *mp, xfs_dir2_db_t db, | ||
197 | xfs_dir2_data_aoff_t o) | ||
198 | { | ||
199 | return ((xfs_dir2_off_t)(db) << \ | ||
200 | ((mp)->m_sb.sb_blocklog + (mp)->m_sb.sb_dirblklog)) + (o); | ||
201 | } | ||
202 | |||
203 | /* | ||
204 | * Convert block (DB) to block (dablk) | ||
205 | */ | ||
206 | static inline xfs_dablk_t | ||
207 | xfs_dir2_db_to_da(struct xfs_mount *mp, xfs_dir2_db_t db) | ||
208 | { | ||
209 | return (xfs_dablk_t)((db) << (mp)->m_sb.sb_dirblklog); | ||
210 | } | ||
211 | |||
212 | /* | ||
213 | * Convert byte in space to (DA) block | ||
214 | */ | ||
215 | static inline xfs_dablk_t | ||
216 | xfs_dir2_byte_to_da(struct xfs_mount *mp, xfs_dir2_off_t by) | ||
217 | { | ||
218 | return xfs_dir2_db_to_da(mp, xfs_dir2_byte_to_db(mp, by)); | ||
219 | } | ||
220 | |||
221 | /* | ||
222 | * Convert block and offset to dataptr | ||
223 | */ | ||
224 | static inline xfs_dir2_dataptr_t | ||
225 | xfs_dir2_db_off_to_dataptr(struct xfs_mount *mp, xfs_dir2_db_t db, | ||
226 | xfs_dir2_data_aoff_t o) | ||
227 | { | ||
228 | return xfs_dir2_byte_to_dataptr(mp, xfs_dir2_db_off_to_byte(mp, db, o)); | ||
229 | } | ||
230 | |||
231 | /* | ||
232 | * Convert block (dablk) to block (DB) | ||
233 | */ | ||
234 | static inline xfs_dir2_db_t | ||
235 | xfs_dir2_da_to_db(struct xfs_mount *mp, xfs_dablk_t da) | ||
236 | { | ||
237 | return (xfs_dir2_db_t)((da) >> (mp)->m_sb.sb_dirblklog); | ||
238 | } | ||
239 | |||
240 | /* | ||
241 | * Convert block (dablk) to byte offset in space | ||
242 | */ | ||
243 | static inline xfs_dir2_off_t | ||
244 | xfs_dir2_da_to_byte(struct xfs_mount *mp, xfs_dablk_t da) | ||
245 | { | ||
246 | return xfs_dir2_db_off_to_byte(mp, xfs_dir2_da_to_db(mp, da), 0); | ||
247 | } | ||
248 | |||
249 | /* | ||
250 | * Function declarations. | ||
251 | */ | ||
252 | extern int xfs_dir2_block_to_leaf(struct xfs_da_args *args, | ||
253 | struct xfs_dabuf *dbp); | ||
254 | extern int xfs_dir2_leaf_addname(struct xfs_da_args *args); | ||
255 | extern void xfs_dir2_leaf_compact(struct xfs_da_args *args, | ||
256 | struct xfs_dabuf *bp); | ||
257 | extern void xfs_dir2_leaf_compact_x1(struct xfs_dabuf *bp, int *indexp, | ||
258 | int *lowstalep, int *highstalep, | ||
259 | int *lowlogp, int *highlogp); | ||
260 | extern int xfs_dir2_leaf_getdents(struct xfs_inode *dp, void *dirent, | ||
261 | size_t bufsize, xfs_off_t *offset, | ||
262 | filldir_t filldir); | ||
263 | extern int xfs_dir2_leaf_init(struct xfs_da_args *args, xfs_dir2_db_t bno, | ||
264 | struct xfs_dabuf **bpp, int magic); | ||
265 | extern void xfs_dir2_leaf_log_ents(struct xfs_trans *tp, struct xfs_dabuf *bp, | ||
266 | int first, int last); | ||
267 | extern void xfs_dir2_leaf_log_header(struct xfs_trans *tp, | ||
268 | struct xfs_dabuf *bp); | ||
269 | extern int xfs_dir2_leaf_lookup(struct xfs_da_args *args); | ||
270 | extern int xfs_dir2_leaf_removename(struct xfs_da_args *args); | ||
271 | extern int xfs_dir2_leaf_replace(struct xfs_da_args *args); | ||
272 | extern int xfs_dir2_leaf_search_hash(struct xfs_da_args *args, | ||
273 | struct xfs_dabuf *lbp); | ||
274 | extern int xfs_dir2_leaf_trim_data(struct xfs_da_args *args, | ||
275 | struct xfs_dabuf *lbp, xfs_dir2_db_t db); | ||
276 | extern xfs_dir2_leaf_entry_t *xfs_dir2_leaf_find_entry(xfs_dir2_leaf_t *, int, | ||
277 | int, int, int, | ||
278 | int *, int *); | ||
279 | extern int xfs_dir2_node_to_leaf(struct xfs_da_state *state); | ||
280 | |||
281 | #endif /* __XFS_DIR2_LEAF_H__ */ | ||
diff --git a/fs/xfs/xfs_dir2_node.c b/fs/xfs/xfs_dir2_node.c index 14571cdeb33f..ec0a23e96705 100644 --- a/fs/xfs/xfs_dir2_node.c +++ b/fs/xfs/xfs_dir2_node.c | |||
@@ -23,18 +23,14 @@ | |||
23 | #include "xfs_trans.h" | 23 | #include "xfs_trans.h" |
24 | #include "xfs_sb.h" | 24 | #include "xfs_sb.h" |
25 | #include "xfs_ag.h" | 25 | #include "xfs_ag.h" |
26 | #include "xfs_dir2.h" | ||
27 | #include "xfs_mount.h" | 26 | #include "xfs_mount.h" |
28 | #include "xfs_da_btree.h" | 27 | #include "xfs_da_btree.h" |
29 | #include "xfs_bmap_btree.h" | 28 | #include "xfs_bmap_btree.h" |
30 | #include "xfs_dir2_sf.h" | ||
31 | #include "xfs_dinode.h" | 29 | #include "xfs_dinode.h" |
32 | #include "xfs_inode.h" | 30 | #include "xfs_inode.h" |
33 | #include "xfs_bmap.h" | 31 | #include "xfs_bmap.h" |
34 | #include "xfs_dir2_data.h" | 32 | #include "xfs_dir2_format.h" |
35 | #include "xfs_dir2_leaf.h" | 33 | #include "xfs_dir2_priv.h" |
36 | #include "xfs_dir2_block.h" | ||
37 | #include "xfs_dir2_node.h" | ||
38 | #include "xfs_error.h" | 34 | #include "xfs_error.h" |
39 | #include "xfs_trace.h" | 35 | #include "xfs_trace.h" |
40 | 36 | ||
diff --git a/fs/xfs/xfs_dir2_node.h b/fs/xfs/xfs_dir2_node.h deleted file mode 100644 index 82dfe7147195..000000000000 --- a/fs/xfs/xfs_dir2_node.h +++ /dev/null | |||
@@ -1,100 +0,0 @@ | |||
1 | /* | ||
2 | * Copyright (c) 2000,2005 Silicon Graphics, Inc. | ||
3 | * All Rights Reserved. | ||
4 | * | ||
5 | * This program is free software; you can redistribute it and/or | ||
6 | * modify it under the terms of the GNU General Public License as | ||
7 | * published by the Free Software Foundation. | ||
8 | * | ||
9 | * This program is distributed in the hope that it would be useful, | ||
10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
12 | * GNU General Public License for more details. | ||
13 | * | ||
14 | * You should have received a copy of the GNU General Public License | ||
15 | * along with this program; if not, write the Free Software Foundation, | ||
16 | * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA | ||
17 | */ | ||
18 | #ifndef __XFS_DIR2_NODE_H__ | ||
19 | #define __XFS_DIR2_NODE_H__ | ||
20 | |||
21 | /* | ||
22 | * Directory version 2, btree node format structures | ||
23 | */ | ||
24 | |||
25 | struct uio; | ||
26 | struct xfs_dabuf; | ||
27 | struct xfs_da_args; | ||
28 | struct xfs_da_state; | ||
29 | struct xfs_da_state_blk; | ||
30 | struct xfs_inode; | ||
31 | struct xfs_trans; | ||
32 | |||
33 | /* | ||
34 | * Offset of the freespace index. | ||
35 | */ | ||
36 | #define XFS_DIR2_FREE_SPACE 2 | ||
37 | #define XFS_DIR2_FREE_OFFSET (XFS_DIR2_FREE_SPACE * XFS_DIR2_SPACE_SIZE) | ||
38 | #define XFS_DIR2_FREE_FIRSTDB(mp) \ | ||
39 | xfs_dir2_byte_to_db(mp, XFS_DIR2_FREE_OFFSET) | ||
40 | |||
41 | #define XFS_DIR2_FREE_MAGIC 0x58443246 /* XD2F */ | ||
42 | |||
43 | typedef struct xfs_dir2_free_hdr { | ||
44 | __be32 magic; /* XFS_DIR2_FREE_MAGIC */ | ||
45 | __be32 firstdb; /* db of first entry */ | ||
46 | __be32 nvalid; /* count of valid entries */ | ||
47 | __be32 nused; /* count of used entries */ | ||
48 | } xfs_dir2_free_hdr_t; | ||
49 | |||
50 | typedef struct xfs_dir2_free { | ||
51 | xfs_dir2_free_hdr_t hdr; /* block header */ | ||
52 | __be16 bests[1]; /* best free counts */ | ||
53 | /* unused entries are -1 */ | ||
54 | } xfs_dir2_free_t; | ||
55 | |||
56 | #define XFS_DIR2_MAX_FREE_BESTS(mp) \ | ||
57 | (((mp)->m_dirblksize - (uint)sizeof(xfs_dir2_free_hdr_t)) / \ | ||
58 | (uint)sizeof(xfs_dir2_data_off_t)) | ||
59 | |||
60 | /* | ||
61 | * Convert data space db to the corresponding free db. | ||
62 | */ | ||
63 | static inline xfs_dir2_db_t | ||
64 | xfs_dir2_db_to_fdb(struct xfs_mount *mp, xfs_dir2_db_t db) | ||
65 | { | ||
66 | return (XFS_DIR2_FREE_FIRSTDB(mp) + (db) / XFS_DIR2_MAX_FREE_BESTS(mp)); | ||
67 | } | ||
68 | |||
69 | /* | ||
70 | * Convert data space db to the corresponding index in a free db. | ||
71 | */ | ||
72 | static inline int | ||
73 | xfs_dir2_db_to_fdindex(struct xfs_mount *mp, xfs_dir2_db_t db) | ||
74 | { | ||
75 | return ((db) % XFS_DIR2_MAX_FREE_BESTS(mp)); | ||
76 | } | ||
77 | |||
78 | extern int xfs_dir2_leaf_to_node(struct xfs_da_args *args, | ||
79 | struct xfs_dabuf *lbp); | ||
80 | extern xfs_dahash_t xfs_dir2_leafn_lasthash(struct xfs_dabuf *bp, int *count); | ||
81 | extern int xfs_dir2_leafn_lookup_int(struct xfs_dabuf *bp, | ||
82 | struct xfs_da_args *args, int *indexp, | ||
83 | struct xfs_da_state *state); | ||
84 | extern int xfs_dir2_leafn_order(struct xfs_dabuf *leaf1_bp, | ||
85 | struct xfs_dabuf *leaf2_bp); | ||
86 | extern int xfs_dir2_leafn_split(struct xfs_da_state *state, | ||
87 | struct xfs_da_state_blk *oldblk, | ||
88 | struct xfs_da_state_blk *newblk); | ||
89 | extern int xfs_dir2_leafn_toosmall(struct xfs_da_state *state, int *action); | ||
90 | extern void xfs_dir2_leafn_unbalance(struct xfs_da_state *state, | ||
91 | struct xfs_da_state_blk *drop_blk, | ||
92 | struct xfs_da_state_blk *save_blk); | ||
93 | extern int xfs_dir2_node_addname(struct xfs_da_args *args); | ||
94 | extern int xfs_dir2_node_lookup(struct xfs_da_args *args); | ||
95 | extern int xfs_dir2_node_removename(struct xfs_da_args *args); | ||
96 | extern int xfs_dir2_node_replace(struct xfs_da_args *args); | ||
97 | extern int xfs_dir2_node_trim_free(struct xfs_da_args *args, xfs_fileoff_t fo, | ||
98 | int *rvalp); | ||
99 | |||
100 | #endif /* __XFS_DIR2_NODE_H__ */ | ||
diff --git a/fs/xfs/xfs_dir2_priv.h b/fs/xfs/xfs_dir2_priv.h new file mode 100644 index 000000000000..067f403ecf8a --- /dev/null +++ b/fs/xfs/xfs_dir2_priv.h | |||
@@ -0,0 +1,135 @@ | |||
1 | /* | ||
2 | * Copyright (c) 2000-2001,2005 Silicon Graphics, Inc. | ||
3 | * All Rights Reserved. | ||
4 | * | ||
5 | * This program is free software; you can redistribute it and/or | ||
6 | * modify it under the terms of the GNU General Public License as | ||
7 | * published by the Free Software Foundation. | ||
8 | * | ||
9 | * This program is distributed in the hope that it would be useful, | ||
10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
12 | * GNU General Public License for more details. | ||
13 | * | ||
14 | * You should have received a copy of the GNU General Public License | ||
15 | * along with this program; if not, write the Free Software Foundation, | ||
16 | * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA | ||
17 | */ | ||
18 | #ifndef __XFS_DIR2_PRIV_H__ | ||
19 | #define __XFS_DIR2_PRIV_H__ | ||
20 | |||
21 | /* xfs_dir2.c */ | ||
22 | extern int xfs_dir_ino_validate(struct xfs_mount *mp, xfs_ino_t ino); | ||
23 | extern int xfs_dir2_isblock(struct xfs_trans *tp, struct xfs_inode *dp, int *r); | ||
24 | extern int xfs_dir2_isleaf(struct xfs_trans *tp, struct xfs_inode *dp, int *r); | ||
25 | extern int xfs_dir2_grow_inode(struct xfs_da_args *args, int space, | ||
26 | xfs_dir2_db_t *dbp); | ||
27 | extern int xfs_dir2_shrink_inode(struct xfs_da_args *args, xfs_dir2_db_t db, | ||
28 | struct xfs_dabuf *bp); | ||
29 | extern int xfs_dir_cilookup_result(struct xfs_da_args *args, | ||
30 | const unsigned char *name, int len); | ||
31 | |||
32 | /* xfs_dir2_block.c */ | ||
33 | extern int xfs_dir2_block_addname(struct xfs_da_args *args); | ||
34 | extern int xfs_dir2_block_getdents(struct xfs_inode *dp, void *dirent, | ||
35 | xfs_off_t *offset, filldir_t filldir); | ||
36 | extern int xfs_dir2_block_lookup(struct xfs_da_args *args); | ||
37 | extern int xfs_dir2_block_removename(struct xfs_da_args *args); | ||
38 | extern int xfs_dir2_block_replace(struct xfs_da_args *args); | ||
39 | extern int xfs_dir2_leaf_to_block(struct xfs_da_args *args, | ||
40 | struct xfs_dabuf *lbp, struct xfs_dabuf *dbp); | ||
41 | |||
42 | /* xfs_dir2_data.c */ | ||
43 | #ifdef DEBUG | ||
44 | extern void xfs_dir2_data_check(struct xfs_inode *dp, struct xfs_dabuf *bp); | ||
45 | #else | ||
46 | #define xfs_dir2_data_check(dp,bp) | ||
47 | #endif | ||
48 | extern struct xfs_dir2_data_free * | ||
49 | xfs_dir2_data_freeinsert(struct xfs_dir2_data_hdr *hdr, | ||
50 | struct xfs_dir2_data_unused *dup, int *loghead); | ||
51 | extern void xfs_dir2_data_freescan(struct xfs_mount *mp, | ||
52 | struct xfs_dir2_data_hdr *hdr, int *loghead); | ||
53 | extern int xfs_dir2_data_init(struct xfs_da_args *args, xfs_dir2_db_t blkno, | ||
54 | struct xfs_dabuf **bpp); | ||
55 | extern void xfs_dir2_data_log_entry(struct xfs_trans *tp, struct xfs_dabuf *bp, | ||
56 | struct xfs_dir2_data_entry *dep); | ||
57 | extern void xfs_dir2_data_log_header(struct xfs_trans *tp, | ||
58 | struct xfs_dabuf *bp); | ||
59 | extern void xfs_dir2_data_log_unused(struct xfs_trans *tp, struct xfs_dabuf *bp, | ||
60 | struct xfs_dir2_data_unused *dup); | ||
61 | extern void xfs_dir2_data_make_free(struct xfs_trans *tp, struct xfs_dabuf *bp, | ||
62 | xfs_dir2_data_aoff_t offset, xfs_dir2_data_aoff_t len, | ||
63 | int *needlogp, int *needscanp); | ||
64 | extern void xfs_dir2_data_use_free(struct xfs_trans *tp, struct xfs_dabuf *bp, | ||
65 | struct xfs_dir2_data_unused *dup, xfs_dir2_data_aoff_t offset, | ||
66 | xfs_dir2_data_aoff_t len, int *needlogp, int *needscanp); | ||
67 | |||
68 | /* xfs_dir2_leaf.c */ | ||
69 | extern int xfs_dir2_block_to_leaf(struct xfs_da_args *args, | ||
70 | struct xfs_dabuf *dbp); | ||
71 | extern int xfs_dir2_leaf_addname(struct xfs_da_args *args); | ||
72 | extern void xfs_dir2_leaf_compact(struct xfs_da_args *args, | ||
73 | struct xfs_dabuf *bp); | ||
74 | extern void xfs_dir2_leaf_compact_x1(struct xfs_dabuf *bp, int *indexp, | ||
75 | int *lowstalep, int *highstalep, int *lowlogp, int *highlogp); | ||
76 | extern int xfs_dir2_leaf_getdents(struct xfs_inode *dp, void *dirent, | ||
77 | size_t bufsize, xfs_off_t *offset, filldir_t filldir); | ||
78 | extern int xfs_dir2_leaf_init(struct xfs_da_args *args, xfs_dir2_db_t bno, | ||
79 | struct xfs_dabuf **bpp, int magic); | ||
80 | extern void xfs_dir2_leaf_log_ents(struct xfs_trans *tp, struct xfs_dabuf *bp, | ||
81 | int first, int last); | ||
82 | extern void xfs_dir2_leaf_log_header(struct xfs_trans *tp, | ||
83 | struct xfs_dabuf *bp); | ||
84 | extern int xfs_dir2_leaf_lookup(struct xfs_da_args *args); | ||
85 | extern int xfs_dir2_leaf_removename(struct xfs_da_args *args); | ||
86 | extern int xfs_dir2_leaf_replace(struct xfs_da_args *args); | ||
87 | extern int xfs_dir2_leaf_search_hash(struct xfs_da_args *args, | ||
88 | struct xfs_dabuf *lbp); | ||
89 | extern int xfs_dir2_leaf_trim_data(struct xfs_da_args *args, | ||
90 | struct xfs_dabuf *lbp, xfs_dir2_db_t db); | ||
91 | extern struct xfs_dir2_leaf_entry * | ||
92 | xfs_dir2_leaf_find_entry(struct xfs_dir2_leaf *leaf, int index, int compact, | ||
93 | int lowstale, int highstale, | ||
94 | int *lfloglow, int *lfloghigh); | ||
95 | extern int xfs_dir2_node_to_leaf(struct xfs_da_state *state); | ||
96 | |||
97 | /* xfs_dir2_node.c */ | ||
98 | extern int xfs_dir2_leaf_to_node(struct xfs_da_args *args, | ||
99 | struct xfs_dabuf *lbp); | ||
100 | extern xfs_dahash_t xfs_dir2_leafn_lasthash(struct xfs_dabuf *bp, int *count); | ||
101 | extern int xfs_dir2_leafn_lookup_int(struct xfs_dabuf *bp, | ||
102 | struct xfs_da_args *args, int *indexp, | ||
103 | struct xfs_da_state *state); | ||
104 | extern int xfs_dir2_leafn_order(struct xfs_dabuf *leaf1_bp, | ||
105 | struct xfs_dabuf *leaf2_bp); | ||
106 | extern int xfs_dir2_leafn_split(struct xfs_da_state *state, | ||
107 | struct xfs_da_state_blk *oldblk, struct xfs_da_state_blk *newblk); | ||
108 | extern int xfs_dir2_leafn_toosmall(struct xfs_da_state *state, int *action); | ||
109 | extern void xfs_dir2_leafn_unbalance(struct xfs_da_state *state, | ||
110 | struct xfs_da_state_blk *drop_blk, | ||
111 | struct xfs_da_state_blk *save_blk); | ||
112 | extern int xfs_dir2_node_addname(struct xfs_da_args *args); | ||
113 | extern int xfs_dir2_node_lookup(struct xfs_da_args *args); | ||
114 | extern int xfs_dir2_node_removename(struct xfs_da_args *args); | ||
115 | extern int xfs_dir2_node_replace(struct xfs_da_args *args); | ||
116 | extern int xfs_dir2_node_trim_free(struct xfs_da_args *args, xfs_fileoff_t fo, | ||
117 | int *rvalp); | ||
118 | |||
119 | /* xfs_dir2_sf.c */ | ||
120 | extern xfs_ino_t xfs_dir2_sf_get_parent_ino(struct xfs_dir2_sf_hdr *sfp); | ||
121 | extern xfs_ino_t xfs_dir2_sfe_get_ino(struct xfs_dir2_sf_hdr *sfp, | ||
122 | struct xfs_dir2_sf_entry *sfep); | ||
123 | extern int xfs_dir2_block_sfsize(struct xfs_inode *dp, | ||
124 | struct xfs_dir2_data_hdr *block, struct xfs_dir2_sf_hdr *sfhp); | ||
125 | extern int xfs_dir2_block_to_sf(struct xfs_da_args *args, struct xfs_dabuf *bp, | ||
126 | int size, xfs_dir2_sf_hdr_t *sfhp); | ||
127 | extern int xfs_dir2_sf_addname(struct xfs_da_args *args); | ||
128 | extern int xfs_dir2_sf_create(struct xfs_da_args *args, xfs_ino_t pino); | ||
129 | extern int xfs_dir2_sf_getdents(struct xfs_inode *dp, void *dirent, | ||
130 | xfs_off_t *offset, filldir_t filldir); | ||
131 | extern int xfs_dir2_sf_lookup(struct xfs_da_args *args); | ||
132 | extern int xfs_dir2_sf_removename(struct xfs_da_args *args); | ||
133 | extern int xfs_dir2_sf_replace(struct xfs_da_args *args); | ||
134 | |||
135 | #endif /* __XFS_DIR2_PRIV_H__ */ | ||
diff --git a/fs/xfs/xfs_dir2_sf.c b/fs/xfs/xfs_dir2_sf.c index 9d3dff2ae4c5..79d05e84e296 100644 --- a/fs/xfs/xfs_dir2_sf.c +++ b/fs/xfs/xfs_dir2_sf.c | |||
@@ -23,18 +23,16 @@ | |||
23 | #include "xfs_trans.h" | 23 | #include "xfs_trans.h" |
24 | #include "xfs_sb.h" | 24 | #include "xfs_sb.h" |
25 | #include "xfs_ag.h" | 25 | #include "xfs_ag.h" |
26 | #include "xfs_dir2.h" | ||
27 | #include "xfs_mount.h" | 26 | #include "xfs_mount.h" |
28 | #include "xfs_da_btree.h" | 27 | #include "xfs_da_btree.h" |
29 | #include "xfs_bmap_btree.h" | 28 | #include "xfs_bmap_btree.h" |
30 | #include "xfs_dir2_sf.h" | ||
31 | #include "xfs_dinode.h" | 29 | #include "xfs_dinode.h" |
32 | #include "xfs_inode.h" | 30 | #include "xfs_inode.h" |
33 | #include "xfs_inode_item.h" | 31 | #include "xfs_inode_item.h" |
34 | #include "xfs_error.h" | 32 | #include "xfs_error.h" |
35 | #include "xfs_dir2_data.h" | 33 | #include "xfs_dir2.h" |
36 | #include "xfs_dir2_leaf.h" | 34 | #include "xfs_dir2_format.h" |
37 | #include "xfs_dir2_block.h" | 35 | #include "xfs_dir2_priv.h" |
38 | #include "xfs_trace.h" | 36 | #include "xfs_trace.h" |
39 | 37 | ||
40 | /* | 38 | /* |
diff --git a/fs/xfs/xfs_dir2_sf.h b/fs/xfs/xfs_dir2_sf.h deleted file mode 100644 index 26f062912395..000000000000 --- a/fs/xfs/xfs_dir2_sf.h +++ /dev/null | |||
@@ -1,151 +0,0 @@ | |||
1 | /* | ||
2 | * Copyright (c) 2000-2001,2005 Silicon Graphics, Inc. | ||
3 | * All Rights Reserved. | ||
4 | * | ||
5 | * This program is free software; you can redistribute it and/or | ||
6 | * modify it under the terms of the GNU General Public License as | ||
7 | * published by the Free Software Foundation. | ||
8 | * | ||
9 | * This program is distributed in the hope that it would be useful, | ||
10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
12 | * GNU General Public License for more details. | ||
13 | * | ||
14 | * You should have received a copy of the GNU General Public License | ||
15 | * along with this program; if not, write the Free Software Foundation, | ||
16 | * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA | ||
17 | */ | ||
18 | #ifndef __XFS_DIR2_SF_H__ | ||
19 | #define __XFS_DIR2_SF_H__ | ||
20 | |||
21 | /* | ||
22 | * Directory layout when stored internal to an inode. | ||
23 | * | ||
24 | * Small directories are packed as tightly as possible so as to fit into the | ||
25 | * literal area of the inode. They consist of a single xfs_dir2_sf_hdr header | ||
26 | * followed by zero or more xfs_dir2_sf_entry structures. Due the different | ||
27 | * inode number storage size and the variable length name field in | ||
28 | * the xfs_dir2_sf_entry all these structure are variable length, and the | ||
29 | * accessors in this file should be used to iterate over them. | ||
30 | */ | ||
31 | |||
32 | struct uio; | ||
33 | struct xfs_dabuf; | ||
34 | struct xfs_da_args; | ||
35 | struct xfs_dir2_data_hdr; | ||
36 | struct xfs_inode; | ||
37 | struct xfs_mount; | ||
38 | struct xfs_trans; | ||
39 | |||
40 | /* | ||
41 | * Inode number stored as 8 8-bit values. | ||
42 | */ | ||
43 | typedef struct { __uint8_t i[8]; } xfs_dir2_ino8_t; | ||
44 | |||
45 | /* | ||
46 | * Inode number stored as 4 8-bit values. | ||
47 | * Works a lot of the time, when all the inode numbers in a directory | ||
48 | * fit in 32 bits. | ||
49 | */ | ||
50 | typedef struct { __uint8_t i[4]; } xfs_dir2_ino4_t; | ||
51 | |||
52 | typedef union { | ||
53 | xfs_dir2_ino8_t i8; | ||
54 | xfs_dir2_ino4_t i4; | ||
55 | } xfs_dir2_inou_t; | ||
56 | #define XFS_DIR2_MAX_SHORT_INUM ((xfs_ino_t)0xffffffffULL) | ||
57 | |||
58 | /* | ||
59 | * Normalized offset (in a data block) of the entry, really xfs_dir2_data_off_t. | ||
60 | * Only need 16 bits, this is the byte offset into the single block form. | ||
61 | */ | ||
62 | typedef struct { __uint8_t i[2]; } __arch_pack xfs_dir2_sf_off_t; | ||
63 | |||
64 | /* | ||
65 | * The parent directory has a dedicated field, and the self-pointer must | ||
66 | * be calculated on the fly. | ||
67 | * | ||
68 | * Entries are packed toward the top as tightly as possible, and thus may | ||
69 | * be misaligned. Care needs to be taken to access them through special | ||
70 | * helpers or copy them into aligned variables first. | ||
71 | */ | ||
72 | typedef struct xfs_dir2_sf_hdr { | ||
73 | __uint8_t count; /* count of entries */ | ||
74 | __uint8_t i8count; /* count of 8-byte inode #s */ | ||
75 | xfs_dir2_inou_t parent; /* parent dir inode number */ | ||
76 | } __arch_pack xfs_dir2_sf_hdr_t; | ||
77 | |||
78 | typedef struct xfs_dir2_sf_entry { | ||
79 | __u8 namelen; /* actual name length */ | ||
80 | xfs_dir2_sf_off_t offset; /* saved offset */ | ||
81 | __u8 name[]; /* name, variable size */ | ||
82 | /* | ||
83 | * A xfs_dir2_ino8_t or xfs_dir2_ino4_t follows here, at a | ||
84 | * variable offset after the name. | ||
85 | */ | ||
86 | } __arch_pack xfs_dir2_sf_entry_t; | ||
87 | |||
88 | static inline int xfs_dir2_sf_hdr_size(int i8count) | ||
89 | { | ||
90 | return ((uint)sizeof(xfs_dir2_sf_hdr_t) - \ | ||
91 | ((i8count) == 0) * \ | ||
92 | ((uint)sizeof(xfs_dir2_ino8_t) - (uint)sizeof(xfs_dir2_ino4_t))); | ||
93 | } | ||
94 | |||
95 | static inline xfs_dir2_data_aoff_t | ||
96 | xfs_dir2_sf_get_offset(xfs_dir2_sf_entry_t *sfep) | ||
97 | { | ||
98 | return get_unaligned_be16(&sfep->offset.i); | ||
99 | } | ||
100 | |||
101 | static inline void | ||
102 | xfs_dir2_sf_put_offset(xfs_dir2_sf_entry_t *sfep, xfs_dir2_data_aoff_t off) | ||
103 | { | ||
104 | put_unaligned_be16(off, &sfep->offset.i); | ||
105 | } | ||
106 | |||
107 | static inline int | ||
108 | xfs_dir2_sf_entsize(struct xfs_dir2_sf_hdr *hdr, int len) | ||
109 | { | ||
110 | return sizeof(struct xfs_dir2_sf_entry) + /* namelen + offset */ | ||
111 | len + /* name */ | ||
112 | (hdr->i8count ? /* ino */ | ||
113 | sizeof(xfs_dir2_ino8_t) : | ||
114 | sizeof(xfs_dir2_ino4_t)); | ||
115 | } | ||
116 | |||
117 | static inline struct xfs_dir2_sf_entry * | ||
118 | xfs_dir2_sf_firstentry(struct xfs_dir2_sf_hdr *hdr) | ||
119 | { | ||
120 | return (struct xfs_dir2_sf_entry *) | ||
121 | ((char *)hdr + xfs_dir2_sf_hdr_size(hdr->i8count)); | ||
122 | } | ||
123 | |||
124 | static inline struct xfs_dir2_sf_entry * | ||
125 | xfs_dir2_sf_nextentry(struct xfs_dir2_sf_hdr *hdr, | ||
126 | struct xfs_dir2_sf_entry *sfep) | ||
127 | { | ||
128 | return (struct xfs_dir2_sf_entry *) | ||
129 | ((char *)sfep + xfs_dir2_sf_entsize(hdr, sfep->namelen)); | ||
130 | } | ||
131 | |||
132 | /* | ||
133 | * Functions. | ||
134 | */ | ||
135 | extern xfs_ino_t xfs_dir2_sf_get_parent_ino(struct xfs_dir2_sf_hdr *sfp); | ||
136 | extern xfs_ino_t xfs_dir2_sfe_get_ino(struct xfs_dir2_sf_hdr *sfp, | ||
137 | struct xfs_dir2_sf_entry *sfep); | ||
138 | extern int xfs_dir2_block_sfsize(struct xfs_inode *dp, | ||
139 | struct xfs_dir2_data_hdr *block, | ||
140 | xfs_dir2_sf_hdr_t *sfhp); | ||
141 | extern int xfs_dir2_block_to_sf(struct xfs_da_args *args, struct xfs_dabuf *bp, | ||
142 | int size, xfs_dir2_sf_hdr_t *sfhp); | ||
143 | extern int xfs_dir2_sf_addname(struct xfs_da_args *args); | ||
144 | extern int xfs_dir2_sf_create(struct xfs_da_args *args, xfs_ino_t pino); | ||
145 | extern int xfs_dir2_sf_getdents(struct xfs_inode *dp, void *dirent, | ||
146 | xfs_off_t *offset, filldir_t filldir); | ||
147 | extern int xfs_dir2_sf_lookup(struct xfs_da_args *args); | ||
148 | extern int xfs_dir2_sf_removename(struct xfs_da_args *args); | ||
149 | extern int xfs_dir2_sf_replace(struct xfs_da_args *args); | ||
150 | |||
151 | #endif /* __XFS_DIR2_SF_H__ */ | ||