xref: /aosp_15_r20/external/f2fs-tools/fsck/xattr.h (revision 59bfda1f02d633cd6b8b69f31eee485d40f6eef6)
1 /**
2  * xattr.h
3  *
4  * Many parts of codes are copied from Linux kernel/fs/f2fs.
5  *
6  * Copyright (C) 2015 Huawei Ltd.
7  * Witten by:
8  *   Hou Pengyang <[email protected]>
9  *   Liu Shuoran <[email protected]>
10  *   Jaegeuk Kim <[email protected]>
11  *
12  * This program is free software; you can redistribute it and/or modify
13  * it under the terms of the GNU General Public License version 2 as
14  * published by the Free Software Foundation.
15  */
16 #ifndef _XATTR_H_
17 #define _XATTR_H_
18 
19 #include "f2fs.h"
20 #ifdef HAVE_SYS_XATTR_H
21 #include <sys/xattr.h>
22 #endif
23 
24 struct f2fs_xattr_header {
25 	__le32 h_magic;		/* magic number for identification */
26 	__le32 h_refcount;	/* reference count */
27 	__u32 h_sloadd[4];	/* zero right now */
28 };
29 
30 struct f2fs_xattr_entry {
31 	__u8 e_name_index;
32 	__u8 e_name_len;
33 	__le16 e_value_size;	/* size of attribute value */
34 	char e_name[0];		/* attribute name */
35 };
36 
37 #define FSCRYPT_CONTEXT_V1 1
38 #define FSCRYPT_CONTEXT_V2 2
39 #ifndef FSCRYPT_KEY_DESCRIPTOR_SIZE
40 #define FSCRYPT_KEY_DESCRIPTOR_SIZE 8
41 #endif
42 #ifndef FSCRYPT_KEY_IDENTIFIER_SIZE
43 #define FSCRYPT_KEY_IDENTIFIER_SIZE	16
44 #endif
45 #define FSCRYPT_FILE_NONCE_SIZE 16
46 #define F2FS_XATTR_NAME_ENCRYPTION_CONTEXT    "c"
47 
48 struct fscrypt_context_v1 {
49 	u8 version; /* FSCRYPT_CONTEXT_V1 */
50 	u8 contents_encryption_mode;
51 	u8 filenames_encryption_mode;
52 	u8 flags;
53 	u8 master_key_descriptor[FSCRYPT_KEY_DESCRIPTOR_SIZE];
54 	u8 nonce[FSCRYPT_FILE_NONCE_SIZE];
55 };
56 
57 struct fscrypt_context_v2 {
58 	u8 version; /* FSCRYPT_CONTEXT_V2 */
59 	u8 contents_encryption_mode;
60 	u8 filenames_encryption_mode;
61 	u8 flags;
62 	u8 __reserved[4];
63 	u8 master_key_identifier[FSCRYPT_KEY_IDENTIFIER_SIZE];
64 	u8 nonce[FSCRYPT_FILE_NONCE_SIZE];
65 };
66 
67 union fscrypt_context {
68 	u8 version;
69 	struct fscrypt_context_v1 v1;
70 	struct fscrypt_context_v2 v2;
71 };
72 
73 static_assert(sizeof(struct fscrypt_context_v1) == 28, "");
74 static_assert(sizeof(struct fscrypt_context_v2) == 40, "");
75 
76 /*
77 * Return the size expected for the given fscrypt_context based on its version
78 * number, or 0 if the context version is unrecognized.
79 */
fscrypt_context_size(const union fscrypt_context * ctx)80 static inline int fscrypt_context_size(const union fscrypt_context *ctx)
81 {
82 	switch (ctx->version) {
83 	case FSCRYPT_CONTEXT_V1:
84 		return sizeof(ctx->v1);
85 	case FSCRYPT_CONTEXT_V2:
86 		return sizeof(ctx->v2);
87 	default:
88 		MSG(0, "Unsupported fscrypt_context format!\n");
89 	}
90 	return 0;
91 }
92 
93 struct fsverity_descriptor_location {
94 	__le32 version;
95 	__le32 size;
96 	__le64 pos;
97 };
98 
99 static_assert(sizeof(struct fsverity_descriptor_location) == 16, "");
100 
101 #define F2FS_ACL_VERSION	0x0001
102 
103 struct f2fs_acl_entry {
104 	__le16 e_tag;
105 	__le16 e_perm;
106 	__le32 e_id;
107 };
108 
109 struct f2fs_acl_entry_short {
110 	__le16 e_tag;
111 	__le16 e_perm;
112 };
113 
114 struct f2fs_acl_header {
115 	__le32 a_version;
116 };
117 
f2fs_acl_count(int size)118 static inline int f2fs_acl_count(int size)
119 {
120 	ssize_t s;
121 	size -= sizeof(struct f2fs_acl_header);
122 	s = size - 4 * sizeof(struct f2fs_acl_entry_short);
123 	if (s < 0) {
124 		if (size % sizeof(struct f2fs_acl_entry_short))
125 			return -1;
126 		return size / sizeof(struct f2fs_acl_entry_short);
127 	} else {
128 		if (s % sizeof(struct f2fs_acl_entry))
129 			return -1;
130 		return s / sizeof(struct f2fs_acl_entry) + 4;
131 	}
132 }
133 
134 #ifndef XATTR_USER_PREFIX
135 #define XATTR_USER_PREFIX	"user."
136 #endif
137 #ifndef XATTR_SECURITY_PREFIX
138 #define XATTR_SECURITY_PREFIX	"security."
139 #endif
140 #ifndef XATTR_TRUSTED_PREFIX
141 #define XATTR_TRUSTED_PREFIX	"trusted."
142 #endif
143 
144 #ifndef XATTR_CREATE
145 #define XATTR_CREATE 0x1
146 #endif
147 #ifndef XATTR_REPLACE
148 #define XATTR_REPLACE 0x2
149 #endif
150 
151 #define XATTR_ROUND	(3)
152 
153 #define XATTR_SELINUX_SUFFIX "selinux"
154 #define F2FS_XATTR_INDEX_USER			1
155 #define F2FS_XATTR_INDEX_POSIX_ACL_ACCESS	2
156 #define F2FS_XATTR_INDEX_POSIX_ACL_DEFAULT	3
157 #define F2FS_XATTR_INDEX_TRUSTED		4
158 #define F2FS_XATTR_INDEX_LUSTRE			5
159 #define F2FS_XATTR_INDEX_SECURITY		6
160 #define F2FS_XATTR_INDEX_ENCRYPTION		9
161 #define F2FS_XATTR_INDEX_VERITY			11
162 
163 #define F2FS_XATTR_NAME_VERITY			"v"
164 
165 #define IS_XATTR_LAST_ENTRY(entry) (*(__u32 *)(entry) == 0)
166 
167 #define XATTR_HDR(ptr)		((struct f2fs_xattr_header *)(ptr))
168 #define XATTR_ENTRY(ptr) 	((struct f2fs_xattr_entry *)(ptr))
169 #define F2FS_XATTR_MAGIC	0xF2F52011
170 
171 #define XATTR_NEXT_ENTRY(entry) ((struct f2fs_xattr_entry *) ((char *)(entry) +\
172 					ENTRY_SIZE(entry)))
173 #define XATTR_FIRST_ENTRY(ptr)	(XATTR_ENTRY(XATTR_HDR(ptr) + 1))
174 
175 #define XATTR_ALIGN(size)	((size + XATTR_ROUND) & ~XATTR_ROUND)
176 
177 #define ENTRY_SIZE(entry) (XATTR_ALIGN(sizeof(struct f2fs_xattr_entry) + \
178 			entry->e_name_len + le16_to_cpu(entry->e_value_size)))
179 
180 #define list_for_each_xattr(entry, addr) \
181 	for (entry = XATTR_FIRST_ENTRY(addr); \
182 			!IS_XATTR_LAST_ENTRY(entry); \
183 			entry = XATTR_NEXT_ENTRY(entry))
184 
185 #define VALID_XATTR_BLOCK_SIZE	(F2FS_BLKSIZE - sizeof(struct node_footer))
186 
187 #define XATTR_SIZE(i)		((le32_to_cpu((i)->i_xattr_nid) ?	\
188 					VALID_XATTR_BLOCK_SIZE : 0) +	\
189 						(inline_xattr_size(i)))
190 
191 #define MIN_OFFSET	XATTR_ALIGN(F2FS_BLKSIZE -		\
192 		sizeof(struct node_footer) - sizeof(__u32))
193 
194 #define MAX_VALUE_LEN	(MIN_OFFSET -				\
195 		sizeof(struct f2fs_xattr_header) -		\
196 		sizeof(struct f2fs_xattr_entry))
197 
198 #define MAX_INLINE_XATTR_SIZE						\
199 			(DEF_ADDRS_PER_INODE -				\
200 			F2FS_TOTAL_EXTRA_ATTR_SIZE / sizeof(__le32) -	\
201 			DEF_INLINE_RESERVED_SIZE -			\
202 			MIN_INLINE_DENTRY_SIZE / sizeof(__le32))
203 #endif
204