libfdt.h revision 9537
1/*
2 * libfdt - Flat Device Tree manipulation
3 * Copyright (C) 2006 David Gibson, IBM Corporation.
4 *
5 *     Redistribution and use in source and binary forms, with or
6 *     without modification, are permitted provided that the following
7 *     conditions are met:
8 *
9 *     1. Redistributions of source code must retain the above
10 *        copyright notice, this list of conditions and the following
11 *        disclaimer.
12 *     2. Redistributions in binary form must reproduce the above
13 *        copyright notice, this list of conditions and the following
14 *        disclaimer in the documentation and/or other materials
15 *        provided with the distribution.
16 *
17 *     THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND
18 *     CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES,
19 *     INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
20 *     MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
21 *     DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
22 *     CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
23 *     SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
24 *     NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
25 *     LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
26 *     HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27 *     CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
28 *     OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
29 *     EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30 */
31#ifndef _LIBFDT_H
32#define _LIBFDT_H
33
34#ifdef __cplusplus
35extern "C" {
36#endif
37
38#include <fdt.h>
39#include <libfdt_env.h>
40
41#define FDT_FIRST_SUPPORTED_VERSION	0x10
42#define FDT_LAST_SUPPORTED_VERSION	0x11
43
44/* Error codes: informative error codes */
45#define FDT_ERR_NOTFOUND	1
46        /* FDT_ERR_NOTFOUND: The requested node or property does not exist */
47#define FDT_ERR_EXISTS		2
48        /* FDT_ERR_EXISTS: Attemped to create a node or property which
49         * already exists */
50#define FDT_ERR_NOSPACE		3
51        /* FDT_ERR_NOSPACE: Operation needed to expand the device
52         * tree, but its buffer did not have sufficient space to
53         * contain the expanded tree. Use fdt_open_into() to move the
54         * device tree to a buffer with more space. */
55
56/* Error codes: codes for bad parameters */
57#define FDT_ERR_BADOFFSET	4
58        /* FDT_ERR_BADOFFSET: Function was passed a structure block
59         * offset which is out-of-bounds, or which points to an
60         * unsuitable part of the structure for the operation. */
61#define FDT_ERR_BADPATH		5
62        /* FDT_ERR_BADPATH: Function was passed a badly formatted path
63         * (e.g. missing a leading / for a function which requires an
64         * absolute path) */
65#define FDT_ERR_BADPHANDLE	6
66        /* FDT_ERR_BADPHANDLE: Function was passed an invalid phandle
67         * value.  phandle values of 0 and -1 are not permitted. */
68#define FDT_ERR_BADSTATE	7
69        /* FDT_ERR_BADSTATE: Function was passed an incomplete device
70         * tree created by the sequential-write functions, which is
71         * not sufficiently complete for the requested operation. */
72
73/* Error codes: codes for bad device tree blobs */
74#define FDT_ERR_TRUNCATED	8
75        /* FDT_ERR_TRUNCATED: Structure block of the given device tree
76         * ends without an FDT_END tag. */
77#define FDT_ERR_BADMAGIC	9
78        /* FDT_ERR_BADMAGIC: Given "device tree" appears not to be a
79         * device tree at all - it is missing the flattened device
80         * tree magic number. */
81#define FDT_ERR_BADVERSION	10
82        /* FDT_ERR_BADVERSION: Given device tree has a version which
83         * can't be handled by the requested operation.  For
84         * read-write functions, this may mean that fdt_open_into() is
85         * required to convert the tree to the expected version. */
86#define FDT_ERR_BADSTRUCTURE	11
87        /* FDT_ERR_BADSTRUCTURE: Given device tree has a corrupt
88         * structure block or other serious error (e.g. misnested
89         * nodes, or subnodes preceding properties). */
90#define FDT_ERR_BADLAYOUT	12
91        /* FDT_ERR_BADLAYOUT: For read-write functions, the given
92         * device tree has it's sub-blocks in an order that the
93         * function can't handle (memory reserve map, then structure,
94         * then strings).  Use fdt_open_into() to reorganize the tree
95         * into a form suitable for the read-write operations. */
96
97/* "Can't happen" error indicating a bug in libfdt */
98#define FDT_ERR_INTERNAL	13
99        /* FDT_ERR_INTERNAL: libfdt has failed an internal assertion.
100         * Should never be returned, if it is, it indicates a bug in
101         * libfdt itself. */
102
103#define FDT_ERR_MAX		13
104
105/**********************************************************************/
106/* Low-level functions (you probably don't need these)                */
107/**********************************************************************/
108
109const void *fdt_offset_ptr(const void *fdt, int offset, unsigned int checklen);
110static inline void *fdt_offset_ptr_w(void *fdt, int offset, int checklen)
111{
112        return (void *)(uintptr_t)fdt_offset_ptr(fdt, offset, checklen);
113}
114
115uint32_t fdt_next_tag(const void *fdt, int offset, int *nextoffset);
116
117/**********************************************************************/
118/* Traversal functions                                                */
119/**********************************************************************/
120
121int fdt_next_node(const void *fdt, int offset, int *depth);
122
123/**********************************************************************/
124/* General functions                                                  */
125/**********************************************************************/
126
127#define fdt_get_header(fdt, field) \
128        (fdt32_to_cpu(((const struct fdt_header *)(fdt))->field))
129#define fdt_magic(fdt) 			(fdt_get_header(fdt, magic))
130#define fdt_totalsize(fdt)		(fdt_get_header(fdt, totalsize))
131#define fdt_off_dt_struct(fdt)		(fdt_get_header(fdt, off_dt_struct))
132#define fdt_off_dt_strings(fdt)		(fdt_get_header(fdt, off_dt_strings))
133#define fdt_off_mem_rsvmap(fdt)		(fdt_get_header(fdt, off_mem_rsvmap))
134#define fdt_version(fdt)		(fdt_get_header(fdt, version))
135#define fdt_last_comp_version(fdt) 	(fdt_get_header(fdt, last_comp_version))
136#define fdt_boot_cpuid_phys(fdt) 	(fdt_get_header(fdt, boot_cpuid_phys))
137#define fdt_size_dt_strings(fdt) 	(fdt_get_header(fdt, size_dt_strings))
138#define fdt_size_dt_struct(fdt)		(fdt_get_header(fdt, size_dt_struct))
139
140#define __fdt_set_hdr(name) \
141        static inline void fdt_set_##name(void *fdt, uint32_t val) \
142        { \
143                struct fdt_header *fdth = (struct fdt_header*)fdt; \
144                fdth->name = cpu_to_fdt32(val); \
145        }
146__fdt_set_hdr(magic);
147__fdt_set_hdr(totalsize);
148__fdt_set_hdr(off_dt_struct);
149__fdt_set_hdr(off_dt_strings);
150__fdt_set_hdr(off_mem_rsvmap);
151__fdt_set_hdr(version);
152__fdt_set_hdr(last_comp_version);
153__fdt_set_hdr(boot_cpuid_phys);
154__fdt_set_hdr(size_dt_strings);
155__fdt_set_hdr(size_dt_struct);
156#undef __fdt_set_hdr
157
158/**
159 * fdt_check_header - sanity check a device tree or possible device tree
160 * @fdt: pointer to data which might be a flattened device tree
161 *
162 * fdt_check_header() checks that the given buffer contains what
163 * appears to be a flattened device tree with sane information in its
164 * header.
165 *
166 * returns:
167 *     0, if the buffer appears to contain a valid device tree
168 *     -FDT_ERR_BADMAGIC,
169 *     -FDT_ERR_BADVERSION,
170 *     -FDT_ERR_BADSTATE, standard meanings, as above
171 */
172int fdt_check_header(const void *fdt);
173
174/**
175 * fdt_move - move a device tree around in memory
176 * @fdt: pointer to the device tree to move
177 * @buf: pointer to memory where the device is to be moved
178 * @bufsize: size of the memory space at buf
179 *
180 * fdt_move() relocates, if possible, the device tree blob located at
181 * fdt to the buffer at buf of size bufsize.  The buffer may overlap
182 * with the existing device tree blob at fdt.  Therefore,
183 *     fdt_move(fdt, fdt, fdt_totalsize(fdt))
184 * should always succeed.
185 *
186 * returns:
187 *     0, on success
188 *     -FDT_ERR_NOSPACE, bufsize is insufficient to contain the device tree
189 *     -FDT_ERR_BADMAGIC,
190 *     -FDT_ERR_BADVERSION,
191 *     -FDT_ERR_BADSTATE, standard meanings
192 */
193int fdt_move(const void *fdt, void *buf, int bufsize);
194
195/**********************************************************************/
196/* Read-only functions                                                */
197/**********************************************************************/
198
199/**
200 * fdt_string - retrieve a string from the strings block of a device tree
201 * @fdt: pointer to the device tree blob
202 * @stroffset: offset of the string within the strings block (native endian)
203 *
204 * fdt_string() retrieves a pointer to a single string from the
205 * strings block of the device tree blob at fdt.
206 *
207 * returns:
208 *     a pointer to the string, on success
209 *     NULL, if stroffset is out of bounds
210 */
211const char *fdt_string(const void *fdt, int stroffset);
212
213/**
214 * fdt_num_mem_rsv - retrieve the number of memory reserve map entries
215 * @fdt: pointer to the device tree blob
216 *
217 * Returns the number of entries in the device tree blob's memory
218 * reservation map.  This does not include the terminating 0,0 entry
219 * or any other (0,0) entries reserved for expansion.
220 *
221 * returns:
222 *     the number of entries
223 */
224int fdt_num_mem_rsv(const void *fdt);
225
226/**
227 * fdt_get_mem_rsv - retrieve one memory reserve map entry
228 * @fdt: pointer to the device tree blob
229 * @address, @size: pointers to 64-bit variables
230 *
231 * On success, *address and *size will contain the address and size of
232 * the n-th reserve map entry from the device tree blob, in
233 * native-endian format.
234 *
235 * returns:
236 *     0, on success
237 *     -FDT_ERR_BADMAGIC,
238 *     -FDT_ERR_BADVERSION,
239 *     -FDT_ERR_BADSTATE, standard meanings
240 */
241int fdt_get_mem_rsv(const void *fdt, int n, uint64_t *address, uint64_t *size);
242
243/**
244 * fdt_subnode_offset_namelen - find a subnode based on substring
245 * @fdt: pointer to the device tree blob
246 * @parentoffset: structure block offset of a node
247 * @name: name of the subnode to locate
248 * @namelen: number of characters of name to consider
249 *
250 * Identical to fdt_subnode_offset(), but only examine the first
251 * namelen characters of name for matching the subnode name.  This is
252 * useful for finding subnodes based on a portion of a larger string,
253 * such as a full path.
254 */
255int fdt_subnode_offset_namelen(const void *fdt, int parentoffset,
256                               const char *name, int namelen);
257/**
258 * fdt_subnode_offset - find a subnode of a given node
259 * @fdt: pointer to the device tree blob
260 * @parentoffset: structure block offset of a node
261 * @name: name of the subnode to locate
262 *
263 * fdt_subnode_offset() finds a subnode of the node at structure block
264 * offset parentoffset with the given name.  name may include a unit
265 * address, in which case fdt_subnode_offset() will find the subnode
266 * with that unit address, or the unit address may be omitted, in
267 * which case fdt_subnode_offset() will find an arbitrary subnode
268 * whose name excluding unit address matches the given name.
269 *
270 * returns:
271 *	structure block offset of the requested subnode (>=0), on success
272 *	-FDT_ERR_NOTFOUND, if the requested subnode does not exist
273 *	-FDT_ERR_BADOFFSET, if parentoffset did not point to an FDT_BEGIN_NODE tag
274 *      -FDT_ERR_BADMAGIC,
275 *	-FDT_ERR_BADVERSION,
276 *	-FDT_ERR_BADSTATE,
277 *	-FDT_ERR_BADSTRUCTURE,
278 *	-FDT_ERR_TRUNCATED, standard meanings.
279 */
280int fdt_subnode_offset(const void *fdt, int parentoffset, const char *name);
281
282/**
283 * fdt_path_offset - find a tree node by its full path
284 * @fdt: pointer to the device tree blob
285 * @path: full path of the node to locate
286 *
287 * fdt_path_offset() finds a node of a given path in the device tree.
288 * Each path component may omit the unit address portion, but the
289 * results of this are undefined if any such path component is
290 * ambiguous (that is if there are multiple nodes at the relevant
291 * level matching the given component, differentiated only by unit
292 * address).
293 *
294 * returns:
295 *	structure block offset of the node with the requested path (>=0), on success
296 *	-FDT_ERR_BADPATH, given path does not begin with '/' or is invalid
297 *	-FDT_ERR_NOTFOUND, if the requested node does not exist
298 *      -FDT_ERR_BADMAGIC,
299 *	-FDT_ERR_BADVERSION,
300 *	-FDT_ERR_BADSTATE,
301 *	-FDT_ERR_BADSTRUCTURE,
302 *	-FDT_ERR_TRUNCATED, standard meanings.
303 */
304int fdt_path_offset(const void *fdt, const char *path);
305
306/**
307 * fdt_get_name - retrieve the name of a given node
308 * @fdt: pointer to the device tree blob
309 * @nodeoffset: structure block offset of the starting node
310 * @lenp: pointer to an integer variable (will be overwritten) or NULL
311 *
312 * fdt_get_name() retrieves the name (including unit address) of the
313 * device tree node at structure block offset nodeoffset.  If lenp is
314 * non-NULL, the length of this name is also returned, in the integer
315 * pointed to by lenp.
316 *
317 * returns:
318 *	pointer to the node's name, on success
319 *		If lenp is non-NULL, *lenp contains the length of that name (>=0)
320 *	NULL, on error
321 *		if lenp is non-NULL *lenp contains an error code (<0):
322 *		-FDT_ERR_BADOFFSET, nodeoffset did not point to FDT_BEGIN_NODE tag
323 *		-FDT_ERR_BADMAGIC,
324 *		-FDT_ERR_BADVERSION,
325 *		-FDT_ERR_BADSTATE, standard meanings
326 */
327const char *fdt_get_name(const void *fdt, int nodeoffset, int *lenp);
328
329/**
330 * fdt_first_property_offset - find the offset of a node's first property
331 * @fdt: pointer to the device tree blob
332 * @nodeoffset: structure block offset of a node
333 *
334 * fdt_first_property_offset() finds the first property of the node at
335 * the given structure block offset.
336 *
337 * returns:
338 *	structure block offset of the property (>=0), on success
339 *	-FDT_ERR_NOTFOUND, if the requested node has no properties
340 *	-FDT_ERR_BADOFFSET, if nodeoffset did not point to an FDT_BEGIN_NODE tag
341 *      -FDT_ERR_BADMAGIC,
342 *	-FDT_ERR_BADVERSION,
343 *	-FDT_ERR_BADSTATE,
344 *	-FDT_ERR_BADSTRUCTURE,
345 *	-FDT_ERR_TRUNCATED, standard meanings.
346 */
347int fdt_first_property_offset(const void *fdt, int nodeoffset);
348
349/**
350 * fdt_next_property_offset - step through a node's properties
351 * @fdt: pointer to the device tree blob
352 * @offset: structure block offset of a property
353 *
354 * fdt_next_property_offset() finds the property immediately after the
355 * one at the given structure block offset.  This will be a property
356 * of the same node as the given property.
357 *
358 * returns:
359 *	structure block offset of the next property (>=0), on success
360 *	-FDT_ERR_NOTFOUND, if the given property is the last in its node
361 *	-FDT_ERR_BADOFFSET, if nodeoffset did not point to an FDT_PROP tag
362 *      -FDT_ERR_BADMAGIC,
363 *	-FDT_ERR_BADVERSION,
364 *	-FDT_ERR_BADSTATE,
365 *	-FDT_ERR_BADSTRUCTURE,
366 *	-FDT_ERR_TRUNCATED, standard meanings.
367 */
368int fdt_next_property_offset(const void *fdt, int offset);
369
370/**
371 * fdt_get_property_by_offset - retrieve the property at a given offset
372 * @fdt: pointer to the device tree blob
373 * @offset: offset of the property to retrieve
374 * @lenp: pointer to an integer variable (will be overwritten) or NULL
375 *
376 * fdt_get_property_by_offset() retrieves a pointer to the
377 * fdt_property structure within the device tree blob at the given
378 * offset.  If lenp is non-NULL, the length of the property value is
379 * also returned, in the integer pointed to by lenp.
380 *
381 * returns:
382 *	pointer to the structure representing the property
383 *		if lenp is non-NULL, *lenp contains the length of the property
384 *		value (>=0)
385 *	NULL, on error
386 *		if lenp is non-NULL, *lenp contains an error code (<0):
387 *		-FDT_ERR_BADOFFSET, nodeoffset did not point to FDT_PROP tag
388 *		-FDT_ERR_BADMAGIC,
389 *		-FDT_ERR_BADVERSION,
390 *		-FDT_ERR_BADSTATE,
391 *		-FDT_ERR_BADSTRUCTURE,
392 *		-FDT_ERR_TRUNCATED, standard meanings
393 */
394const struct fdt_property *fdt_get_property_by_offset(const void *fdt,
395                                                      int offset,
396                                                      int *lenp);
397
398/**
399 * fdt_get_property_namelen - find a property based on substring
400 * @fdt: pointer to the device tree blob
401 * @nodeoffset: offset of the node whose property to find
402 * @name: name of the property to find
403 * @namelen: number of characters of name to consider
404 * @lenp: pointer to an integer variable (will be overwritten) or NULL
405 *
406 * Identical to fdt_get_property_namelen(), but only examine the first
407 * namelen characters of name for matching the property name.
408 */
409const struct fdt_property *fdt_get_property_namelen(const void *fdt,
410                                                    int nodeoffset,
411                                                    const char *name,
412                                                    int namelen, int *lenp);
413
414/**
415 * fdt_get_property - find a given property in a given node
416 * @fdt: pointer to the device tree blob
417 * @nodeoffset: offset of the node whose property to find
418 * @name: name of the property to find
419 * @lenp: pointer to an integer variable (will be overwritten) or NULL
420 *
421 * fdt_get_property() retrieves a pointer to the fdt_property
422 * structure within the device tree blob corresponding to the property
423 * named 'name' of the node at offset nodeoffset.  If lenp is
424 * non-NULL, the length of the property value is also returned, in the
425 * integer pointed to by lenp.
426 *
427 * returns:
428 *	pointer to the structure representing the property
429 *		if lenp is non-NULL, *lenp contains the length of the property
430 *		value (>=0)
431 *	NULL, on error
432 *		if lenp is non-NULL, *lenp contains an error code (<0):
433 *		-FDT_ERR_NOTFOUND, node does not have named property
434 *		-FDT_ERR_BADOFFSET, nodeoffset did not point to FDT_BEGIN_NODE tag
435 *		-FDT_ERR_BADMAGIC,
436 *		-FDT_ERR_BADVERSION,
437 *		-FDT_ERR_BADSTATE,
438 *		-FDT_ERR_BADSTRUCTURE,
439 *		-FDT_ERR_TRUNCATED, standard meanings
440 */
441const struct fdt_property *fdt_get_property(const void *fdt, int nodeoffset,
442                                            const char *name, int *lenp);
443static inline struct fdt_property *fdt_get_property_w(void *fdt, int nodeoffset,
444                                                      const char *name,
445                                                      int *lenp)
446{
447        return (struct fdt_property *)(uintptr_t)
448                fdt_get_property(fdt, nodeoffset, name, lenp);
449}
450
451/**
452 * fdt_getprop_by_offset - retrieve the value of a property at a given offset
453 * @fdt: pointer to the device tree blob
454 * @ffset: offset of the property to read
455 * @namep: pointer to a string variable (will be overwritten) or NULL
456 * @lenp: pointer to an integer variable (will be overwritten) or NULL
457 *
458 * fdt_getprop_by_offset() retrieves a pointer to the value of the
459 * property at structure block offset 'offset' (this will be a pointer
460 * to within the device blob itself, not a copy of the value).  If
461 * lenp is non-NULL, the length of the property value is also
462 * returned, in the integer pointed to by lenp.  If namep is non-NULL,
463 * the property's namne will also be returned in the char * pointed to
464 * by namep (this will be a pointer to within the device tree's string
465 * block, not a new copy of the name).
466 *
467 * returns:
468 *	pointer to the property's value
469 *		if lenp is non-NULL, *lenp contains the length of the property
470 *		value (>=0)
471 *		if namep is non-NULL *namep contiains a pointer to the property
472 *		name.
473 *	NULL, on error
474 *		if lenp is non-NULL, *lenp contains an error code (<0):
475 *		-FDT_ERR_BADOFFSET, nodeoffset did not point to FDT_PROP tag
476 *		-FDT_ERR_BADMAGIC,
477 *		-FDT_ERR_BADVERSION,
478 *		-FDT_ERR_BADSTATE,
479 *		-FDT_ERR_BADSTRUCTURE,
480 *		-FDT_ERR_TRUNCATED, standard meanings
481 */
482const void *fdt_getprop_by_offset(const void *fdt, int offset,
483                                  const char **namep, int *lenp);
484
485/**
486 * fdt_getprop_namelen - get property value based on substring
487 * @fdt: pointer to the device tree blob
488 * @nodeoffset: offset of the node whose property to find
489 * @name: name of the property to find
490 * @namelen: number of characters of name to consider
491 * @lenp: pointer to an integer variable (will be overwritten) or NULL
492 *
493 * Identical to fdt_getprop(), but only examine the first namelen
494 * characters of name for matching the property name.
495 */
496const void *fdt_getprop_namelen(const void *fdt, int nodeoffset,
497                                const char *name, int namelen, int *lenp);
498
499/**
500 * fdt_getprop - retrieve the value of a given property
501 * @fdt: pointer to the device tree blob
502 * @nodeoffset: offset of the node whose property to find
503 * @name: name of the property to find
504 * @lenp: pointer to an integer variable (will be overwritten) or NULL
505 *
506 * fdt_getprop() retrieves a pointer to the value of the property
507 * named 'name' of the node at offset nodeoffset (this will be a
508 * pointer to within the device blob itself, not a copy of the value).
509 * If lenp is non-NULL, the length of the property value is also
510 * returned, in the integer pointed to by lenp.
511 *
512 * returns:
513 *	pointer to the property's value
514 *		if lenp is non-NULL, *lenp contains the length of the property
515 *		value (>=0)
516 *	NULL, on error
517 *		if lenp is non-NULL, *lenp contains an error code (<0):
518 *		-FDT_ERR_NOTFOUND, node does not have named property
519 *		-FDT_ERR_BADOFFSET, nodeoffset did not point to FDT_BEGIN_NODE tag
520 *		-FDT_ERR_BADMAGIC,
521 *		-FDT_ERR_BADVERSION,
522 *		-FDT_ERR_BADSTATE,
523 *		-FDT_ERR_BADSTRUCTURE,
524 *		-FDT_ERR_TRUNCATED, standard meanings
525 */
526const void *fdt_getprop(const void *fdt, int nodeoffset,
527                        const char *name, int *lenp);
528static inline void *fdt_getprop_w(void *fdt, int nodeoffset,
529                                  const char *name, int *lenp)
530{
531        return (void *)(uintptr_t)fdt_getprop(fdt, nodeoffset, name, lenp);
532}
533
534/**
535 * fdt_get_phandle - retrieve the phandle of a given node
536 * @fdt: pointer to the device tree blob
537 * @nodeoffset: structure block offset of the node
538 *
539 * fdt_get_phandle() retrieves the phandle of the device tree node at
540 * structure block offset nodeoffset.
541 *
542 * returns:
543 *	the phandle of the node at nodeoffset, on success (!= 0, != -1)
544 *	0, if the node has no phandle, or another error occurs
545 */
546uint32_t fdt_get_phandle(const void *fdt, int nodeoffset);
547
548/**
549 * fdt_get_alias_namelen - get alias based on substring
550 * @fdt: pointer to the device tree blob
551 * @name: name of the alias th look up
552 * @namelen: number of characters of name to consider
553 *
554 * Identical to fdt_get_alias(), but only examine the first namelen
555 * characters of name for matching the alias name.
556 */
557const char *fdt_get_alias_namelen(const void *fdt,
558                                  const char *name, int namelen);
559
560/**
561 * fdt_get_alias - retreive the path referenced by a given alias
562 * @fdt: pointer to the device tree blob
563 * @name: name of the alias th look up
564 *
565 * fdt_get_alias() retrieves the value of a given alias.  That is, the
566 * value of the property named 'name' in the node /aliases.
567 *
568 * returns:
569 *	a pointer to the expansion of the alias named 'name', of it exists
570 *	NULL, if the given alias or the /aliases node does not exist
571 */
572const char *fdt_get_alias(const void *fdt, const char *name);
573
574/**
575 * fdt_get_path - determine the full path of a node
576 * @fdt: pointer to the device tree blob
577 * @nodeoffset: offset of the node whose path to find
578 * @buf: character buffer to contain the returned path (will be overwritten)
579 * @buflen: size of the character buffer at buf
580 *
581 * fdt_get_path() computes the full path of the node at offset
582 * nodeoffset, and records that path in the buffer at buf.
583 *
584 * NOTE: This function is expensive, as it must scan the device tree
585 * structure from the start to nodeoffset.
586 *
587 * returns:
588 *	0, on success
589 *		buf contains the absolute path of the node at
590 *		nodeoffset, as a NUL-terminated string.
591 * 	-FDT_ERR_BADOFFSET, nodeoffset does not refer to a BEGIN_NODE tag
592 *	-FDT_ERR_NOSPACE, the path of the given node is longer than (bufsize-1)
593 *		characters and will not fit in the given buffer.
594 *	-FDT_ERR_BADMAGIC,
595 *	-FDT_ERR_BADVERSION,
596 *	-FDT_ERR_BADSTATE,
597 *	-FDT_ERR_BADSTRUCTURE, standard meanings
598 */
599int fdt_get_path(const void *fdt, int nodeoffset, char *buf, int buflen);
600
601/**
602 * fdt_supernode_atdepth_offset - find a specific ancestor of a node
603 * @fdt: pointer to the device tree blob
604 * @nodeoffset: offset of the node whose parent to find
605 * @supernodedepth: depth of the ancestor to find
606 * @nodedepth: pointer to an integer variable (will be overwritten) or NULL
607 *
608 * fdt_supernode_atdepth_offset() finds an ancestor of the given node
609 * at a specific depth from the root (where the root itself has depth
610 * 0, its immediate subnodes depth 1 and so forth).  So
611 *	fdt_supernode_atdepth_offset(fdt, nodeoffset, 0, NULL);
612 * will always return 0, the offset of the root node.  If the node at
613 * nodeoffset has depth D, then:
614 *	fdt_supernode_atdepth_offset(fdt, nodeoffset, D, NULL);
615 * will return nodeoffset itself.
616 *
617 * NOTE: This function is expensive, as it must scan the device tree
618 * structure from the start to nodeoffset.
619 *
620 * returns:
621
622 *	structure block offset of the node at node offset's ancestor
623 *		of depth supernodedepth (>=0), on success
624 * 	-FDT_ERR_BADOFFSET, nodeoffset does not refer to a BEGIN_NODE tag
625*	-FDT_ERR_NOTFOUND, supernodedepth was greater than the depth of nodeoffset
626 *	-FDT_ERR_BADMAGIC,
627 *	-FDT_ERR_BADVERSION,
628 *	-FDT_ERR_BADSTATE,
629 *	-FDT_ERR_BADSTRUCTURE, standard meanings
630 */
631int fdt_supernode_atdepth_offset(const void *fdt, int nodeoffset,
632                                 int supernodedepth, int *nodedepth);
633
634/**
635 * fdt_node_depth - find the depth of a given node
636 * @fdt: pointer to the device tree blob
637 * @nodeoffset: offset of the node whose parent to find
638 *
639 * fdt_node_depth() finds the depth of a given node.  The root node
640 * has depth 0, its immediate subnodes depth 1 and so forth.
641 *
642 * NOTE: This function is expensive, as it must scan the device tree
643 * structure from the start to nodeoffset.
644 *
645 * returns:
646 *	depth of the node at nodeoffset (>=0), on success
647 * 	-FDT_ERR_BADOFFSET, nodeoffset does not refer to a BEGIN_NODE tag
648 *	-FDT_ERR_BADMAGIC,
649 *	-FDT_ERR_BADVERSION,
650 *	-FDT_ERR_BADSTATE,
651 *	-FDT_ERR_BADSTRUCTURE, standard meanings
652 */
653int fdt_node_depth(const void *fdt, int nodeoffset);
654
655/**
656 * fdt_parent_offset - find the parent of a given node
657 * @fdt: pointer to the device tree blob
658 * @nodeoffset: offset of the node whose parent to find
659 *
660 * fdt_parent_offset() locates the parent node of a given node (that
661 * is, it finds the offset of the node which contains the node at
662 * nodeoffset as a subnode).
663 *
664 * NOTE: This function is expensive, as it must scan the device tree
665 * structure from the start to nodeoffset, *twice*.
666 *
667 * returns:
668 *	structure block offset of the parent of the node at nodeoffset
669 *		(>=0), on success
670 * 	-FDT_ERR_BADOFFSET, nodeoffset does not refer to a BEGIN_NODE tag
671 *	-FDT_ERR_BADMAGIC,
672 *	-FDT_ERR_BADVERSION,
673 *	-FDT_ERR_BADSTATE,
674 *	-FDT_ERR_BADSTRUCTURE, standard meanings
675 */
676int fdt_parent_offset(const void *fdt, int nodeoffset);
677
678/**
679 * fdt_node_offset_by_prop_value - find nodes with a given property value
680 * @fdt: pointer to the device tree blob
681 * @startoffset: only find nodes after this offset
682 * @propname: property name to check
683 * @propval: property value to search for
684 * @proplen: length of the value in propval
685 *
686 * fdt_node_offset_by_prop_value() returns the offset of the first
687 * node after startoffset, which has a property named propname whose
688 * value is of length proplen and has value equal to propval; or if
689 * startoffset is -1, the very first such node in the tree.
690 *
691 * To iterate through all nodes matching the criterion, the following
692 * idiom can be used:
693 *	offset = fdt_node_offset_by_prop_value(fdt, -1, propname,
694 *					       propval, proplen);
695 *	while (offset != -FDT_ERR_NOTFOUND) {
696 *		// other code here
697 *		offset = fdt_node_offset_by_prop_value(fdt, offset, propname,
698 *						       propval, proplen);
699 *	}
700 *
701 * Note the -1 in the first call to the function, if 0 is used here
702 * instead, the function will never locate the root node, even if it
703 * matches the criterion.
704 *
705 * returns:
706 *	structure block offset of the located node (>= 0, >startoffset),
707 *		 on success
708 *	-FDT_ERR_NOTFOUND, no node matching the criterion exists in the
709 *		tree after startoffset
710 * 	-FDT_ERR_BADOFFSET, nodeoffset does not refer to a BEGIN_NODE tag
711 *	-FDT_ERR_BADMAGIC,
712 *	-FDT_ERR_BADVERSION,
713 *	-FDT_ERR_BADSTATE,
714 *	-FDT_ERR_BADSTRUCTURE, standard meanings
715 */
716int fdt_node_offset_by_prop_value(const void *fdt, int startoffset,
717                                  const char *propname,
718                                  const void *propval, int proplen);
719
720/**
721 * fdt_node_offset_by_phandle - find the node with a given phandle
722 * @fdt: pointer to the device tree blob
723 * @phandle: phandle value
724 *
725 * fdt_node_offset_by_phandle() returns the offset of the node
726 * which has the given phandle value.  If there is more than one node
727 * in the tree with the given phandle (an invalid tree), results are
728 * undefined.
729 *
730 * returns:
731 *	structure block offset of the located node (>= 0), on success
732 *	-FDT_ERR_NOTFOUND, no node with that phandle exists
733 *	-FDT_ERR_BADPHANDLE, given phandle value was invalid (0 or -1)
734 *	-FDT_ERR_BADMAGIC,
735 *	-FDT_ERR_BADVERSION,
736 *	-FDT_ERR_BADSTATE,
737 *	-FDT_ERR_BADSTRUCTURE, standard meanings
738 */
739int fdt_node_offset_by_phandle(const void *fdt, uint32_t phandle);
740
741/**
742 * fdt_node_check_compatible: check a node's compatible property
743 * @fdt: pointer to the device tree blob
744 * @nodeoffset: offset of a tree node
745 * @compatible: string to match against
746 *
747 *
748 * fdt_node_check_compatible() returns 0 if the given node contains a
749 * 'compatible' property with the given string as one of its elements,
750 * it returns non-zero otherwise, or on error.
751 *
752 * returns:
753 *	0, if the node has a 'compatible' property listing the given string
754 *	1, if the node has a 'compatible' property, but it does not list
755 *		the given string
756 *	-FDT_ERR_NOTFOUND, if the given node has no 'compatible' property
757 * 	-FDT_ERR_BADOFFSET, if nodeoffset does not refer to a BEGIN_NODE tag
758 *	-FDT_ERR_BADMAGIC,
759 *	-FDT_ERR_BADVERSION,
760 *	-FDT_ERR_BADSTATE,
761 *	-FDT_ERR_BADSTRUCTURE, standard meanings
762 */
763int fdt_node_check_compatible(const void *fdt, int nodeoffset,
764                              const char *compatible);
765
766/**
767 * fdt_node_offset_by_compatible - find nodes with a given 'compatible' value
768 * @fdt: pointer to the device tree blob
769 * @startoffset: only find nodes after this offset
770 * @compatible: 'compatible' string to match against
771 *
772 * fdt_node_offset_by_compatible() returns the offset of the first
773 * node after startoffset, which has a 'compatible' property which
774 * lists the given compatible string; or if startoffset is -1, the
775 * very first such node in the tree.
776 *
777 * To iterate through all nodes matching the criterion, the following
778 * idiom can be used:
779 *	offset = fdt_node_offset_by_compatible(fdt, -1, compatible);
780 *	while (offset != -FDT_ERR_NOTFOUND) {
781 *		// other code here
782 *		offset = fdt_node_offset_by_compatible(fdt, offset, compatible);
783 *	}
784 *
785 * Note the -1 in the first call to the function, if 0 is used here
786 * instead, the function will never locate the root node, even if it
787 * matches the criterion.
788 *
789 * returns:
790 *	structure block offset of the located node (>= 0, >startoffset),
791 *		 on success
792 *	-FDT_ERR_NOTFOUND, no node matching the criterion exists in the
793 *		tree after startoffset
794 * 	-FDT_ERR_BADOFFSET, nodeoffset does not refer to a BEGIN_NODE tag
795 *	-FDT_ERR_BADMAGIC,
796 *	-FDT_ERR_BADVERSION,
797 *	-FDT_ERR_BADSTATE,
798 *	-FDT_ERR_BADSTRUCTURE, standard meanings
799 */
800int fdt_node_offset_by_compatible(const void *fdt, int startoffset,
801                                  const char *compatible);
802
803/**********************************************************************/
804/* Write-in-place functions                                           */
805/**********************************************************************/
806
807/**
808 * fdt_setprop_inplace - change a property's value, but not its size
809 * @fdt: pointer to the device tree blob
810 * @nodeoffset: offset of the node whose property to change
811 * @name: name of the property to change
812 * @val: pointer to data to replace the property value with
813 * @len: length of the property value
814 *
815 * fdt_setprop_inplace() replaces the value of a given property with
816 * the data in val, of length len.  This function cannot change the
817 * size of a property, and so will only work if len is equal to the
818 * current length of the property.
819 *
820 * This function will alter only the bytes in the blob which contain
821 * the given property value, and will not alter or move any other part
822 * of the tree.
823 *
824 * returns:
825 *	0, on success
826 *	-FDT_ERR_NOSPACE, if len is not equal to the property's current length
827 *	-FDT_ERR_NOTFOUND, node does not have the named property
828 *	-FDT_ERR_BADOFFSET, nodeoffset did not point to FDT_BEGIN_NODE tag
829 *	-FDT_ERR_BADMAGIC,
830 *	-FDT_ERR_BADVERSION,
831 *	-FDT_ERR_BADSTATE,
832 *	-FDT_ERR_BADSTRUCTURE,
833 *	-FDT_ERR_TRUNCATED, standard meanings
834 */
835int fdt_setprop_inplace(void *fdt, int nodeoffset, const char *name,
836                        const void *val, int len);
837
838/**
839 * fdt_setprop_inplace_u32 - change the value of a 32-bit integer property
840 * @fdt: pointer to the device tree blob
841 * @nodeoffset: offset of the node whose property to change
842 * @name: name of the property to change
843 * @val: 32-bit integer value to replace the property with
844 *
845 * fdt_setprop_inplace_u32() replaces the value of a given property
846 * with the 32-bit integer value in val, converting val to big-endian
847 * if necessary.  This function cannot change the size of a property,
848 * and so will only work if the property already exists and has length
849 * 4.
850 *
851 * This function will alter only the bytes in the blob which contain
852 * the given property value, and will not alter or move any other part
853 * of the tree.
854 *
855 * returns:
856 *	0, on success
857 *	-FDT_ERR_NOSPACE, if the property's length is not equal to 4
858 *	-FDT_ERR_NOTFOUND, node does not have the named property
859 *	-FDT_ERR_BADOFFSET, nodeoffset did not point to FDT_BEGIN_NODE tag
860 *	-FDT_ERR_BADMAGIC,
861 *	-FDT_ERR_BADVERSION,
862 *	-FDT_ERR_BADSTATE,
863 *	-FDT_ERR_BADSTRUCTURE,
864 *	-FDT_ERR_TRUNCATED, standard meanings
865 */
866static inline int fdt_setprop_inplace_u32(void *fdt, int nodeoffset,
867                                          const char *name, uint32_t val)
868{
869        fdt32_t tmp = cpu_to_fdt32(val);
870        return fdt_setprop_inplace(fdt, nodeoffset, name, &tmp, sizeof(tmp));
871}
872
873/**
874 * fdt_setprop_inplace_u64 - change the value of a 64-bit integer property
875 * @fdt: pointer to the device tree blob
876 * @nodeoffset: offset of the node whose property to change
877 * @name: name of the property to change
878 * @val: 64-bit integer value to replace the property with
879 *
880 * fdt_setprop_inplace_u64() replaces the value of a given property
881 * with the 64-bit integer value in val, converting val to big-endian
882 * if necessary.  This function cannot change the size of a property,
883 * and so will only work if the property already exists and has length
884 * 8.
885 *
886 * This function will alter only the bytes in the blob which contain
887 * the given property value, and will not alter or move any other part
888 * of the tree.
889 *
890 * returns:
891 *	0, on success
892 *	-FDT_ERR_NOSPACE, if the property's length is not equal to 8
893 *	-FDT_ERR_NOTFOUND, node does not have the named property
894 *	-FDT_ERR_BADOFFSET, nodeoffset did not point to FDT_BEGIN_NODE tag
895 *	-FDT_ERR_BADMAGIC,
896 *	-FDT_ERR_BADVERSION,
897 *	-FDT_ERR_BADSTATE,
898 *	-FDT_ERR_BADSTRUCTURE,
899 *	-FDT_ERR_TRUNCATED, standard meanings
900 */
901static inline int fdt_setprop_inplace_u64(void *fdt, int nodeoffset,
902                                          const char *name, uint64_t val)
903{
904        fdt64_t tmp = cpu_to_fdt64(val);
905        return fdt_setprop_inplace(fdt, nodeoffset, name, &tmp, sizeof(tmp));
906}
907
908/**
909 * fdt_setprop_inplace_cell - change the value of a single-cell property
910 *
911 * This is an alternative name for fdt_setprop_inplace_u32()
912 */
913static inline int fdt_setprop_inplace_cell(void *fdt, int nodeoffset,
914                                           const char *name, uint32_t val)
915{
916        return fdt_setprop_inplace_u32(fdt, nodeoffset, name, val);
917}
918
919/**
920 * fdt_nop_property - replace a property with nop tags
921 * @fdt: pointer to the device tree blob
922 * @nodeoffset: offset of the node whose property to nop
923 * @name: name of the property to nop
924 *
925 * fdt_nop_property() will replace a given property's representation
926 * in the blob with FDT_NOP tags, effectively removing it from the
927 * tree.
928 *
929 * This function will alter only the bytes in the blob which contain
930 * the property, and will not alter or move any other part of the
931 * tree.
932 *
933 * returns:
934 *	0, on success
935 *	-FDT_ERR_NOTFOUND, node does not have the named property
936 *	-FDT_ERR_BADOFFSET, nodeoffset did not point to FDT_BEGIN_NODE tag
937 *	-FDT_ERR_BADMAGIC,
938 *	-FDT_ERR_BADVERSION,
939 *	-FDT_ERR_BADSTATE,
940 *	-FDT_ERR_BADSTRUCTURE,
941 *	-FDT_ERR_TRUNCATED, standard meanings
942 */
943int fdt_nop_property(void *fdt, int nodeoffset, const char *name);
944
945/**
946 * fdt_nop_node - replace a node (subtree) with nop tags
947 * @fdt: pointer to the device tree blob
948 * @nodeoffset: offset of the node to nop
949 *
950 * fdt_nop_node() will replace a given node's representation in the
951 * blob, including all its subnodes, if any, with FDT_NOP tags,
952 * effectively removing it from the tree.
953 *
954 * This function will alter only the bytes in the blob which contain
955 * the node and its properties and subnodes, and will not alter or
956 * move any other part of the tree.
957 *
958 * returns:
959 *	0, on success
960 *	-FDT_ERR_BADOFFSET, nodeoffset did not point to FDT_BEGIN_NODE tag
961 *	-FDT_ERR_BADMAGIC,
962 *	-FDT_ERR_BADVERSION,
963 *	-FDT_ERR_BADSTATE,
964 *	-FDT_ERR_BADSTRUCTURE,
965 *	-FDT_ERR_TRUNCATED, standard meanings
966 */
967int fdt_nop_node(void *fdt, int nodeoffset);
968
969/**********************************************************************/
970/* Sequential write functions                                         */
971/**********************************************************************/
972
973int fdt_create(void *buf, int bufsize);
974int fdt_add_reservemap_entry(void *fdt, uint64_t addr, uint64_t size);
975int fdt_finish_reservemap(void *fdt);
976int fdt_begin_node(void *fdt, const char *name);
977int fdt_property(void *fdt, const char *name, const void *val, int len);
978static inline int fdt_property_u32(void *fdt, const char *name, uint32_t val)
979{
980        fdt32_t tmp = cpu_to_fdt32(val);
981        return fdt_property(fdt, name, &tmp, sizeof(tmp));
982}
983static inline int fdt_property_u64(void *fdt, const char *name, uint64_t val)
984{
985        fdt64_t tmp = cpu_to_fdt64(val);
986        return fdt_property(fdt, name, &tmp, sizeof(tmp));
987}
988static inline int fdt_property_cell(void *fdt, const char *name, uint32_t val)
989{
990        return fdt_property_u32(fdt, name, val);
991}
992#define fdt_property_string(fdt, name, str) \
993        fdt_property(fdt, name, str, strlen(str)+1)
994int fdt_end_node(void *fdt);
995int fdt_finish(void *fdt);
996
997/**********************************************************************/
998/* Read-write functions                                               */
999/**********************************************************************/
1000
1001int fdt_create_empty_tree(void *buf, int bufsize);
1002int fdt_open_into(const void *fdt, void *buf, int bufsize);
1003int fdt_pack(void *fdt);
1004
1005/**
1006 * fdt_add_mem_rsv - add one memory reserve map entry
1007 * @fdt: pointer to the device tree blob
1008 * @address, @size: 64-bit values (native endian)
1009 *
1010 * Adds a reserve map entry to the given blob reserving a region at
1011 * address address of length size.
1012 *
1013 * This function will insert data into the reserve map and will
1014 * therefore change the indexes of some entries in the table.
1015 *
1016 * returns:
1017 *	0, on success
1018 *	-FDT_ERR_NOSPACE, there is insufficient free space in the blob to
1019 *		contain the new reservation entry
1020 *	-FDT_ERR_BADMAGIC,
1021 *	-FDT_ERR_BADVERSION,
1022 *	-FDT_ERR_BADSTATE,
1023 *	-FDT_ERR_BADSTRUCTURE,
1024 *	-FDT_ERR_BADLAYOUT,
1025 *	-FDT_ERR_TRUNCATED, standard meanings
1026 */
1027int fdt_add_mem_rsv(void *fdt, uint64_t address, uint64_t size);
1028
1029/**
1030 * fdt_del_mem_rsv - remove a memory reserve map entry
1031 * @fdt: pointer to the device tree blob
1032 * @n: entry to remove
1033 *
1034 * fdt_del_mem_rsv() removes the n-th memory reserve map entry from
1035 * the blob.
1036 *
1037 * This function will delete data from the reservation table and will
1038 * therefore change the indexes of some entries in the table.
1039 *
1040 * returns:
1041 *	0, on success
1042 *	-FDT_ERR_NOTFOUND, there is no entry of the given index (i.e. there
1043 *		are less than n+1 reserve map entries)
1044 *	-FDT_ERR_BADMAGIC,
1045 *	-FDT_ERR_BADVERSION,
1046 *	-FDT_ERR_BADSTATE,
1047 *	-FDT_ERR_BADSTRUCTURE,
1048 *	-FDT_ERR_BADLAYOUT,
1049 *	-FDT_ERR_TRUNCATED, standard meanings
1050 */
1051int fdt_del_mem_rsv(void *fdt, int n);
1052
1053/**
1054 * fdt_set_name - change the name of a given node
1055 * @fdt: pointer to the device tree blob
1056 * @nodeoffset: structure block offset of a node
1057 * @name: name to give the node
1058 *
1059 * fdt_set_name() replaces the name (including unit address, if any)
1060 * of the given node with the given string.  NOTE: this function can't
1061 * efficiently check if the new name is unique amongst the given
1062 * node's siblings; results are undefined if this function is invoked
1063 * with a name equal to one of the given node's siblings.
1064 *
1065 * This function may insert or delete data from the blob, and will
1066 * therefore change the offsets of some existing nodes.
1067 *
1068 * returns:
1069 *	0, on success
1070 *	-FDT_ERR_NOSPACE, there is insufficient free space in the blob
1071 *		to contain the new name
1072 *	-FDT_ERR_BADOFFSET, nodeoffset did not point to FDT_BEGIN_NODE tag
1073 *	-FDT_ERR_BADMAGIC,
1074 *	-FDT_ERR_BADVERSION,
1075 *	-FDT_ERR_BADSTATE, standard meanings
1076 */
1077int fdt_set_name(void *fdt, int nodeoffset, const char *name);
1078
1079/**
1080 * fdt_setprop - create or change a property
1081 * @fdt: pointer to the device tree blob
1082 * @nodeoffset: offset of the node whose property to change
1083 * @name: name of the property to change
1084 * @val: pointer to data to set the property value to
1085 * @len: length of the property value
1086 *
1087 * fdt_setprop() sets the value of the named property in the given
1088 * node to the given value and length, creating the property if it
1089 * does not already exist.
1090 *
1091 * This function may insert or delete data from the blob, and will
1092 * therefore change the offsets of some existing nodes.
1093 *
1094 * returns:
1095 *	0, on success
1096 *	-FDT_ERR_NOSPACE, there is insufficient free space in the blob to
1097 *		contain the new property value
1098 *	-FDT_ERR_BADOFFSET, nodeoffset did not point to FDT_BEGIN_NODE tag
1099 *	-FDT_ERR_BADLAYOUT,
1100 *	-FDT_ERR_BADMAGIC,
1101 *	-FDT_ERR_BADVERSION,
1102 *	-FDT_ERR_BADSTATE,
1103 *	-FDT_ERR_BADSTRUCTURE,
1104 *	-FDT_ERR_BADLAYOUT,
1105 *	-FDT_ERR_TRUNCATED, standard meanings
1106 */
1107int fdt_setprop(void *fdt, int nodeoffset, const char *name,
1108                const void *val, int len);
1109
1110/**
1111 * fdt_setprop_u32 - set a property to a 32-bit integer
1112 * @fdt: pointer to the device tree blob
1113 * @nodeoffset: offset of the node whose property to change
1114 * @name: name of the property to change
1115 * @val: 32-bit integer value for the property (native endian)
1116 *
1117 * fdt_setprop_u32() sets the value of the named property in the given
1118 * node to the given 32-bit integer value (converting to big-endian if
1119 * necessary), or creates a new property with that value if it does
1120 * not already exist.
1121 *
1122 * This function may insert or delete data from the blob, and will
1123 * therefore change the offsets of some existing nodes.
1124 *
1125 * returns:
1126 *	0, on success
1127 *	-FDT_ERR_NOSPACE, there is insufficient free space in the blob to
1128 *		contain the new property value
1129 *	-FDT_ERR_BADOFFSET, nodeoffset did not point to FDT_BEGIN_NODE tag
1130 *	-FDT_ERR_BADLAYOUT,
1131 *	-FDT_ERR_BADMAGIC,
1132 *	-FDT_ERR_BADVERSION,
1133 *	-FDT_ERR_BADSTATE,
1134 *	-FDT_ERR_BADSTRUCTURE,
1135 *	-FDT_ERR_BADLAYOUT,
1136 *	-FDT_ERR_TRUNCATED, standard meanings
1137 */
1138static inline int fdt_setprop_u32(void *fdt, int nodeoffset, const char *name,
1139                                  uint32_t val)
1140{
1141        fdt32_t tmp = cpu_to_fdt32(val);
1142        return fdt_setprop(fdt, nodeoffset, name, &tmp, sizeof(tmp));
1143}
1144
1145/**
1146 * fdt_setprop_u64 - set a property to a 64-bit integer
1147 * @fdt: pointer to the device tree blob
1148 * @nodeoffset: offset of the node whose property to change
1149 * @name: name of the property to change
1150 * @val: 64-bit integer value for the property (native endian)
1151 *
1152 * fdt_setprop_u64() sets the value of the named property in the given
1153 * node to the given 64-bit integer value (converting to big-endian if
1154 * necessary), or creates a new property with that value if it does
1155 * not already exist.
1156 *
1157 * This function may insert or delete data from the blob, and will
1158 * therefore change the offsets of some existing nodes.
1159 *
1160 * returns:
1161 *	0, on success
1162 *	-FDT_ERR_NOSPACE, there is insufficient free space in the blob to
1163 *		contain the new property value
1164 *	-FDT_ERR_BADOFFSET, nodeoffset did not point to FDT_BEGIN_NODE tag
1165 *	-FDT_ERR_BADLAYOUT,
1166 *	-FDT_ERR_BADMAGIC,
1167 *	-FDT_ERR_BADVERSION,
1168 *	-FDT_ERR_BADSTATE,
1169 *	-FDT_ERR_BADSTRUCTURE,
1170 *	-FDT_ERR_BADLAYOUT,
1171 *	-FDT_ERR_TRUNCATED, standard meanings
1172 */
1173static inline int fdt_setprop_u64(void *fdt, int nodeoffset, const char *name,
1174                                  uint64_t val)
1175{
1176        fdt64_t tmp = cpu_to_fdt64(val);
1177        return fdt_setprop(fdt, nodeoffset, name, &tmp, sizeof(tmp));
1178}
1179
1180/**
1181 * fdt_setprop_cell - set a property to a single cell value
1182 *
1183 * This is an alternative name for fdt_setprop_u32()
1184 */
1185static inline int fdt_setprop_cell(void *fdt, int nodeoffset, const char *name,
1186                                   uint32_t val)
1187{
1188        return fdt_setprop_u32(fdt, nodeoffset, name, val);
1189}
1190
1191/**
1192 * fdt_setprop_string - set a property to a string value
1193 * @fdt: pointer to the device tree blob
1194 * @nodeoffset: offset of the node whose property to change
1195 * @name: name of the property to change
1196 * @str: string value for the property
1197 *
1198 * fdt_setprop_string() sets the value of the named property in the
1199 * given node to the given string value (using the length of the
1200 * string to determine the new length of the property), or creates a
1201 * new property with that value if it does not already exist.
1202 *
1203 * This function may insert or delete data from the blob, and will
1204 * therefore change the offsets of some existing nodes.
1205 *
1206 * returns:
1207 *	0, on success
1208 *	-FDT_ERR_NOSPACE, there is insufficient free space in the blob to
1209 *		contain the new property value
1210 *	-FDT_ERR_BADOFFSET, nodeoffset did not point to FDT_BEGIN_NODE tag
1211 *	-FDT_ERR_BADLAYOUT,
1212 *	-FDT_ERR_BADMAGIC,
1213 *	-FDT_ERR_BADVERSION,
1214 *	-FDT_ERR_BADSTATE,
1215 *	-FDT_ERR_BADSTRUCTURE,
1216 *	-FDT_ERR_BADLAYOUT,
1217 *	-FDT_ERR_TRUNCATED, standard meanings
1218 */
1219#define fdt_setprop_string(fdt, nodeoffset, name, str) \
1220        fdt_setprop((fdt), (nodeoffset), (name), (str), strlen(str)+1)
1221
1222/**
1223 * fdt_appendprop - append to or create a property
1224 * @fdt: pointer to the device tree blob
1225 * @nodeoffset: offset of the node whose property to change
1226 * @name: name of the property to append to
1227 * @val: pointer to data to append to the property value
1228 * @len: length of the data to append to the property value
1229 *
1230 * fdt_appendprop() appends the value to the named property in the
1231 * given node, creating the property if it does not already exist.
1232 *
1233 * This function may insert data into the blob, and will therefore
1234 * change the offsets of some existing nodes.
1235 *
1236 * returns:
1237 *	0, on success
1238 *	-FDT_ERR_NOSPACE, there is insufficient free space in the blob to
1239 *		contain the new property value
1240 *	-FDT_ERR_BADOFFSET, nodeoffset did not point to FDT_BEGIN_NODE tag
1241 *	-FDT_ERR_BADLAYOUT,
1242 *	-FDT_ERR_BADMAGIC,
1243 *	-FDT_ERR_BADVERSION,
1244 *	-FDT_ERR_BADSTATE,
1245 *	-FDT_ERR_BADSTRUCTURE,
1246 *	-FDT_ERR_BADLAYOUT,
1247 *	-FDT_ERR_TRUNCATED, standard meanings
1248 */
1249int fdt_appendprop(void *fdt, int nodeoffset, const char *name,
1250                   const void *val, int len);
1251
1252/**
1253 * fdt_appendprop_u32 - append a 32-bit integer value to a property
1254 * @fdt: pointer to the device tree blob
1255 * @nodeoffset: offset of the node whose property to change
1256 * @name: name of the property to change
1257 * @val: 32-bit integer value to append to the property (native endian)
1258 *
1259 * fdt_appendprop_u32() appends the given 32-bit integer value
1260 * (converting to big-endian if necessary) to the value of the named
1261 * property in the given node, or creates a new property with that
1262 * value if it does not already exist.
1263 *
1264 * This function may insert data into the blob, and will therefore
1265 * change the offsets of some existing nodes.
1266 *
1267 * returns:
1268 *	0, on success
1269 *	-FDT_ERR_NOSPACE, there is insufficient free space in the blob to
1270 *		contain the new property value
1271 *	-FDT_ERR_BADOFFSET, nodeoffset did not point to FDT_BEGIN_NODE tag
1272 *	-FDT_ERR_BADLAYOUT,
1273 *	-FDT_ERR_BADMAGIC,
1274 *	-FDT_ERR_BADVERSION,
1275 *	-FDT_ERR_BADSTATE,
1276 *	-FDT_ERR_BADSTRUCTURE,
1277 *	-FDT_ERR_BADLAYOUT,
1278 *	-FDT_ERR_TRUNCATED, standard meanings
1279 */
1280static inline int fdt_appendprop_u32(void *fdt, int nodeoffset,
1281                                     const char *name, uint32_t val)
1282{
1283        fdt32_t tmp = cpu_to_fdt32(val);
1284        return fdt_appendprop(fdt, nodeoffset, name, &tmp, sizeof(tmp));
1285}
1286
1287/**
1288 * fdt_appendprop_u64 - append a 64-bit integer value to a property
1289 * @fdt: pointer to the device tree blob
1290 * @nodeoffset: offset of the node whose property to change
1291 * @name: name of the property to change
1292 * @val: 64-bit integer value to append to the property (native endian)
1293 *
1294 * fdt_appendprop_u64() appends the given 64-bit integer value
1295 * (converting to big-endian if necessary) to the value of the named
1296 * property in the given node, or creates a new property with that
1297 * value if it does not already exist.
1298 *
1299 * This function may insert data into the blob, and will therefore
1300 * change the offsets of some existing nodes.
1301 *
1302 * returns:
1303 *	0, on success
1304 *	-FDT_ERR_NOSPACE, there is insufficient free space in the blob to
1305 *		contain the new property value
1306 *	-FDT_ERR_BADOFFSET, nodeoffset did not point to FDT_BEGIN_NODE tag
1307 *	-FDT_ERR_BADLAYOUT,
1308 *	-FDT_ERR_BADMAGIC,
1309 *	-FDT_ERR_BADVERSION,
1310 *	-FDT_ERR_BADSTATE,
1311 *	-FDT_ERR_BADSTRUCTURE,
1312 *	-FDT_ERR_BADLAYOUT,
1313 *	-FDT_ERR_TRUNCATED, standard meanings
1314 */
1315static inline int fdt_appendprop_u64(void *fdt, int nodeoffset,
1316                                     const char *name, uint64_t val)
1317{
1318        fdt64_t tmp = cpu_to_fdt64(val);
1319        return fdt_appendprop(fdt, nodeoffset, name, &tmp, sizeof(tmp));
1320}
1321
1322/**
1323 * fdt_appendprop_cell - append a single cell value to a property
1324 *
1325 * This is an alternative name for fdt_appendprop_u32()
1326 */
1327static inline int fdt_appendprop_cell(void *fdt, int nodeoffset,
1328                                      const char *name, uint32_t val)
1329{
1330        return fdt_appendprop_u32(fdt, nodeoffset, name, val);
1331}
1332
1333/**
1334 * fdt_appendprop_string - append a string to a property
1335 * @fdt: pointer to the device tree blob
1336 * @nodeoffset: offset of the node whose property to change
1337 * @name: name of the property to change
1338 * @str: string value to append to the property
1339 *
1340 * fdt_appendprop_string() appends the given string to the value of
1341 * the named property in the given node, or creates a new property
1342 * with that value if it does not already exist.
1343 *
1344 * This function may insert data into the blob, and will therefore
1345 * change the offsets of some existing nodes.
1346 *
1347 * returns:
1348 *	0, on success
1349 *	-FDT_ERR_NOSPACE, there is insufficient free space in the blob to
1350 *		contain the new property value
1351 *	-FDT_ERR_BADOFFSET, nodeoffset did not point to FDT_BEGIN_NODE tag
1352 *	-FDT_ERR_BADLAYOUT,
1353 *	-FDT_ERR_BADMAGIC,
1354 *	-FDT_ERR_BADVERSION,
1355 *	-FDT_ERR_BADSTATE,
1356 *	-FDT_ERR_BADSTRUCTURE,
1357 *	-FDT_ERR_BADLAYOUT,
1358 *	-FDT_ERR_TRUNCATED, standard meanings
1359 */
1360#define fdt_appendprop_string(fdt, nodeoffset, name, str) \
1361        fdt_appendprop((fdt), (nodeoffset), (name), (str), strlen(str)+1)
1362
1363/**
1364 * fdt_delprop - delete a property
1365 * @fdt: pointer to the device tree blob
1366 * @nodeoffset: offset of the node whose property to nop
1367 * @name: name of the property to nop
1368 *
1369 * fdt_del_property() will delete the given property.
1370 *
1371 * This function will delete data from the blob, and will therefore
1372 * change the offsets of some existing nodes.
1373 *
1374 * returns:
1375 *	0, on success
1376 *	-FDT_ERR_NOTFOUND, node does not have the named property
1377 *	-FDT_ERR_BADOFFSET, nodeoffset did not point to FDT_BEGIN_NODE tag
1378 *	-FDT_ERR_BADLAYOUT,
1379 *	-FDT_ERR_BADMAGIC,
1380 *	-FDT_ERR_BADVERSION,
1381 *	-FDT_ERR_BADSTATE,
1382 *	-FDT_ERR_BADSTRUCTURE,
1383 *	-FDT_ERR_TRUNCATED, standard meanings
1384 */
1385int fdt_delprop(void *fdt, int nodeoffset, const char *name);
1386
1387/**
1388 * fdt_add_subnode_namelen - creates a new node based on substring
1389 * @fdt: pointer to the device tree blob
1390 * @parentoffset: structure block offset of a node
1391 * @name: name of the subnode to locate
1392 * @namelen: number of characters of name to consider
1393 *
1394 * Identical to fdt_add_subnode(), but use only the first namelen
1395 * characters of name as the name of the new node.  This is useful for
1396 * creating subnodes based on a portion of a larger string, such as a
1397 * full path.
1398 */
1399int fdt_add_subnode_namelen(void *fdt, int parentoffset,
1400                            const char *name, int namelen);
1401
1402/**
1403 * fdt_add_subnode - creates a new node
1404 * @fdt: pointer to the device tree blob
1405 * @parentoffset: structure block offset of a node
1406 * @name: name of the subnode to locate
1407 *
1408 * fdt_add_subnode() creates a new node as a subnode of the node at
1409 * structure block offset parentoffset, with the given name (which
1410 * should include the unit address, if any).
1411 *
1412 * This function will insert data into the blob, and will therefore
1413 * change the offsets of some existing nodes.
1414
1415 * returns:
1416 *	structure block offset of the created nodeequested subnode (>=0), on success
1417 *	-FDT_ERR_NOTFOUND, if the requested subnode does not exist
1418 *	-FDT_ERR_BADOFFSET, if parentoffset did not point to an FDT_BEGIN_NODE tag
1419 *	-FDT_ERR_EXISTS, if the node at parentoffset already has a subnode of
1420 *		the given name
1421 *	-FDT_ERR_NOSPACE, if there is insufficient free space in the
1422 *		blob to contain the new node
1423 *	-FDT_ERR_NOSPACE
1424 *	-FDT_ERR_BADLAYOUT
1425 *      -FDT_ERR_BADMAGIC,
1426 *	-FDT_ERR_BADVERSION,
1427 *	-FDT_ERR_BADSTATE,
1428 *	-FDT_ERR_BADSTRUCTURE,
1429 *	-FDT_ERR_TRUNCATED, standard meanings.
1430 */
1431int fdt_add_subnode(void *fdt, int parentoffset, const char *name);
1432
1433/**
1434 * fdt_del_node - delete a node (subtree)
1435 * @fdt: pointer to the device tree blob
1436 * @nodeoffset: offset of the node to nop
1437 *
1438 * fdt_del_node() will remove the given node, including all its
1439 * subnodes if any, from the blob.
1440 *
1441 * This function will delete data from the blob, and will therefore
1442 * change the offsets of some existing nodes.
1443 *
1444 * returns:
1445 *	0, on success
1446 *	-FDT_ERR_BADOFFSET, nodeoffset did not point to FDT_BEGIN_NODE tag
1447 *	-FDT_ERR_BADLAYOUT,
1448 *	-FDT_ERR_BADMAGIC,
1449 *	-FDT_ERR_BADVERSION,
1450 *	-FDT_ERR_BADSTATE,
1451 *	-FDT_ERR_BADSTRUCTURE,
1452 *	-FDT_ERR_TRUNCATED, standard meanings
1453 */
1454int fdt_del_node(void *fdt, int nodeoffset);
1455
1456/**********************************************************************/
1457/* Debugging / informational functions                                */
1458/**********************************************************************/
1459
1460const char *fdt_strerror(int errval);
1461
1462#ifdef __cplusplus
1463}
1464#endif
1465
1466#endif /* _LIBFDT_H */
1467