1  /* SPDX-License-Identifier: GPL-2.0 */
2  #ifndef _LINUX_XBC_H
3  #define _LINUX_XBC_H
4  /*
5   * Extra Boot Config
6   * Copyright (C) 2019 Linaro Ltd.
7   * Author: Masami Hiramatsu <mhiramat@kernel.org>
8   */
9  
10  #ifdef __KERNEL__
11  #include <linux/kernel.h>
12  #include <linux/types.h>
13  bool __init cmdline_has_extra_options(void);
14  #else /* !__KERNEL__ */
15  /*
16   * NOTE: This is only for tools/bootconfig, because tools/bootconfig will
17   * run the parser sanity test.
18   * This does NOT mean linux/bootconfig.h is available in the user space.
19   * However, if you change this file, please make sure the tools/bootconfig
20   * has no issue on building and running.
21   */
22  #endif
23  
24  #define BOOTCONFIG_MAGIC	"#BOOTCONFIG\n"
25  #define BOOTCONFIG_MAGIC_LEN	12
26  #define BOOTCONFIG_ALIGN_SHIFT	2
27  #define BOOTCONFIG_ALIGN	(1 << BOOTCONFIG_ALIGN_SHIFT)
28  #define BOOTCONFIG_ALIGN_MASK	(BOOTCONFIG_ALIGN - 1)
29  
30  /**
31   * xbc_calc_checksum() - Calculate checksum of bootconfig
32   * @data: Bootconfig data.
33   * @size: The size of the bootconfig data.
34   *
35   * Calculate the checksum value of the bootconfig data.
36   * The checksum will be used with the BOOTCONFIG_MAGIC and the size for
37   * embedding the bootconfig in the initrd image.
38   */
xbc_calc_checksum(void * data,uint32_t size)39  static inline __init uint32_t xbc_calc_checksum(void *data, uint32_t size)
40  {
41  	unsigned char *p = data;
42  	uint32_t ret = 0;
43  
44  	while (size--)
45  		ret += *p++;
46  
47  	return ret;
48  }
49  
50  /* XBC tree node */
51  struct xbc_node {
52  	uint16_t next;
53  	uint16_t child;
54  	uint16_t parent;
55  	uint16_t data;
56  } __attribute__ ((__packed__));
57  
58  #define XBC_KEY		0
59  #define XBC_VALUE	(1 << 15)
60  /* Maximum size of boot config is 32KB - 1 */
61  #define XBC_DATA_MAX	(XBC_VALUE - 1)
62  
63  #define XBC_NODE_MAX	8192
64  #define XBC_KEYLEN_MAX	256
65  #define XBC_DEPTH_MAX	16
66  
67  /* Node tree access raw APIs */
68  struct xbc_node * __init xbc_root_node(void);
69  int __init xbc_node_index(struct xbc_node *node);
70  struct xbc_node * __init xbc_node_get_parent(struct xbc_node *node);
71  struct xbc_node * __init xbc_node_get_child(struct xbc_node *node);
72  struct xbc_node * __init xbc_node_get_next(struct xbc_node *node);
73  const char * __init xbc_node_get_data(struct xbc_node *node);
74  
75  /**
76   * xbc_node_is_value() - Test the node is a value node
77   * @node: An XBC node.
78   *
79   * Test the @node is a value node and return true if a value node, false if not.
80   */
xbc_node_is_value(struct xbc_node * node)81  static inline __init bool xbc_node_is_value(struct xbc_node *node)
82  {
83  	return node->data & XBC_VALUE;
84  }
85  
86  /**
87   * xbc_node_is_key() - Test the node is a key node
88   * @node: An XBC node.
89   *
90   * Test the @node is a key node and return true if a key node, false if not.
91   */
xbc_node_is_key(struct xbc_node * node)92  static inline __init bool xbc_node_is_key(struct xbc_node *node)
93  {
94  	return !xbc_node_is_value(node);
95  }
96  
97  /**
98   * xbc_node_is_array() - Test the node is an arraied value node
99   * @node: An XBC node.
100   *
101   * Test the @node is an arraied value node.
102   */
xbc_node_is_array(struct xbc_node * node)103  static inline __init bool xbc_node_is_array(struct xbc_node *node)
104  {
105  	return xbc_node_is_value(node) && node->child != 0;
106  }
107  
108  /**
109   * xbc_node_is_leaf() - Test the node is a leaf key node
110   * @node: An XBC node.
111   *
112   * Test the @node is a leaf key node which is a key node and has a value node
113   * or no child. Returns true if it is a leaf node, or false if not.
114   * Note that the leaf node can have subkey nodes in addition to the
115   * value node.
116   */
xbc_node_is_leaf(struct xbc_node * node)117  static inline __init bool xbc_node_is_leaf(struct xbc_node *node)
118  {
119  	return xbc_node_is_key(node) &&
120  		(!node->child || xbc_node_is_value(xbc_node_get_child(node)));
121  }
122  
123  /* Tree-based key-value access APIs */
124  struct xbc_node * __init xbc_node_find_subkey(struct xbc_node *parent,
125  					     const char *key);
126  
127  const char * __init xbc_node_find_value(struct xbc_node *parent,
128  					const char *key,
129  					struct xbc_node **vnode);
130  
131  struct xbc_node * __init xbc_node_find_next_leaf(struct xbc_node *root,
132  						 struct xbc_node *leaf);
133  
134  const char * __init xbc_node_find_next_key_value(struct xbc_node *root,
135  						 struct xbc_node **leaf);
136  
137  /**
138   * xbc_find_value() - Find a value which matches the key
139   * @key: Search key
140   * @vnode: A container pointer of XBC value node.
141   *
142   * Search a value whose key matches @key from whole of XBC tree and return
143   * the value if found. Found value node is stored in *@vnode.
144   * Note that this can return 0-length string and store NULL in *@vnode for
145   * key-only (non-value) entry.
146   */
147  static inline const char * __init
xbc_find_value(const char * key,struct xbc_node ** vnode)148  xbc_find_value(const char *key, struct xbc_node **vnode)
149  {
150  	return xbc_node_find_value(NULL, key, vnode);
151  }
152  
153  /**
154   * xbc_find_node() - Find a node which matches the key
155   * @key: Search key
156   *
157   * Search a (key) node whose key matches @key from whole of XBC tree and
158   * return the node if found. If not found, returns NULL.
159   */
xbc_find_node(const char * key)160  static inline struct xbc_node * __init xbc_find_node(const char *key)
161  {
162  	return xbc_node_find_subkey(NULL, key);
163  }
164  
165  /**
166   * xbc_node_get_subkey() - Return the first subkey node if exists
167   * @node: Parent node
168   *
169   * Return the first subkey node of the @node. If the @node has no child
170   * or only value node, this will return NULL.
171   */
xbc_node_get_subkey(struct xbc_node * node)172  static inline struct xbc_node * __init xbc_node_get_subkey(struct xbc_node *node)
173  {
174  	struct xbc_node *child = xbc_node_get_child(node);
175  
176  	if (child && xbc_node_is_value(child))
177  		return xbc_node_get_next(child);
178  	else
179  		return child;
180  }
181  
182  /**
183   * xbc_array_for_each_value() - Iterate value nodes on an array
184   * @anode: An XBC arraied value node
185   * @value: A value
186   *
187   * Iterate array value nodes and values starts from @anode. This is expected to
188   * be used with xbc_find_value() and xbc_node_find_value(), so that user can
189   * process each array entry node.
190   */
191  #define xbc_array_for_each_value(anode, value)				\
192  	for (value = xbc_node_get_data(anode); anode != NULL ;		\
193  	     anode = xbc_node_get_child(anode),				\
194  	     value = anode ? xbc_node_get_data(anode) : NULL)
195  
196  /**
197   * xbc_node_for_each_child() - Iterate child nodes
198   * @parent: An XBC node.
199   * @child: Iterated XBC node.
200   *
201   * Iterate child nodes of @parent. Each child nodes are stored to @child.
202   * The @child can be mixture of a value node and subkey nodes.
203   */
204  #define xbc_node_for_each_child(parent, child)				\
205  	for (child = xbc_node_get_child(parent); child != NULL ;	\
206  	     child = xbc_node_get_next(child))
207  
208  /**
209   * xbc_node_for_each_subkey() - Iterate child subkey nodes
210   * @parent: An XBC node.
211   * @child: Iterated XBC node.
212   *
213   * Iterate subkey nodes of @parent. Each child nodes are stored to @child.
214   * The @child is only the subkey node.
215   */
216  #define xbc_node_for_each_subkey(parent, child)				\
217  	for (child = xbc_node_get_subkey(parent); child != NULL ;	\
218  	     child = xbc_node_get_next(child))
219  
220  /**
221   * xbc_node_for_each_array_value() - Iterate array entries of geven key
222   * @node: An XBC node.
223   * @key: A key string searched under @node
224   * @anode: Iterated XBC node of array entry.
225   * @value: Iterated value of array entry.
226   *
227   * Iterate array entries of given @key under @node. Each array entry node
228   * is stored to @anode and @value. If the @node doesn't have @key node,
229   * it does nothing.
230   * Note that even if the found key node has only one value (not array)
231   * this executes block once. However, if the found key node has no value
232   * (key-only node), this does nothing. So don't use this for testing the
233   * key-value pair existence.
234   */
235  #define xbc_node_for_each_array_value(node, key, anode, value)		\
236  	for (value = xbc_node_find_value(node, key, &anode); value != NULL; \
237  	     anode = xbc_node_get_child(anode),				\
238  	     value = anode ? xbc_node_get_data(anode) : NULL)
239  
240  /**
241   * xbc_node_for_each_key_value() - Iterate key-value pairs under a node
242   * @node: An XBC node.
243   * @knode: Iterated key node
244   * @value: Iterated value string
245   *
246   * Iterate key-value pairs under @node. Each key node and value string are
247   * stored in @knode and @value respectively.
248   */
249  #define xbc_node_for_each_key_value(node, knode, value)			\
250  	for (knode = NULL, value = xbc_node_find_next_key_value(node, &knode);\
251  	     knode != NULL; value = xbc_node_find_next_key_value(node, &knode))
252  
253  /**
254   * xbc_for_each_key_value() - Iterate key-value pairs
255   * @knode: Iterated key node
256   * @value: Iterated value string
257   *
258   * Iterate key-value pairs in whole XBC tree. Each key node and value string
259   * are stored in @knode and @value respectively.
260   */
261  #define xbc_for_each_key_value(knode, value)				\
262  	xbc_node_for_each_key_value(NULL, knode, value)
263  
264  /* Compose partial key */
265  int __init xbc_node_compose_key_after(struct xbc_node *root,
266  			struct xbc_node *node, char *buf, size_t size);
267  
268  /**
269   * xbc_node_compose_key() - Compose full key string of the XBC node
270   * @node: An XBC node.
271   * @buf: A buffer to store the key.
272   * @size: The size of the @buf.
273   *
274   * Compose the full-length key of the @node into @buf. Returns the total
275   * length of the key stored in @buf. Or returns -EINVAL if @node is NULL,
276   * and -ERANGE if the key depth is deeper than max depth.
277   */
xbc_node_compose_key(struct xbc_node * node,char * buf,size_t size)278  static inline int __init xbc_node_compose_key(struct xbc_node *node,
279  					      char *buf, size_t size)
280  {
281  	return xbc_node_compose_key_after(NULL, node, buf, size);
282  }
283  
284  /* XBC node initializer */
285  int __init xbc_init(const char *buf, size_t size, const char **emsg, int *epos);
286  
287  /* XBC node and size information */
288  int __init xbc_get_info(int *node_size, size_t *data_size);
289  
290  /* XBC cleanup data structures */
291  void __init _xbc_exit(bool early);
292  
xbc_exit(void)293  static inline void xbc_exit(void)
294  {
295  	_xbc_exit(false);
296  }
297  
298  /* XBC embedded bootconfig data in kernel */
299  #ifdef CONFIG_BOOT_CONFIG_EMBED
300  const char * __init xbc_get_embedded_bootconfig(size_t *size);
301  #else
xbc_get_embedded_bootconfig(size_t * size)302  static inline const char *xbc_get_embedded_bootconfig(size_t *size)
303  {
304  	return NULL;
305  }
306  #endif
307  
308  #endif
309