summaryrefslogtreecommitdiffstats
path: root/cpukit/dtc/libfdt/fdt_ro.c
diff options
context:
space:
mode:
authorThierry Reding <treding@nvidia.com>2019-03-20 16:10:03 +0100
committerSebastian Huber <sebastian.huber@embedded-brains.de>2020-03-02 07:52:19 +0100
commita0dea6447c061896fdf468b5d492060e7108d5cb (patch)
treeb320618fe25321f227683283fe1e6880829874d5 /cpukit/dtc/libfdt/fdt_ro.c
parentlibfdt: Fix FDT_ERR_NOTFOUND typos in documentation (diff)
downloadrtems-a0dea6447c061896fdf468b5d492060e7108d5cb.tar.bz2
libfdt: Add phandle generation helper
The new fdt_generate_phandle() function can be used to generate a new, unused phandle given a specific device tree blob. The implementation is somewhat naive in that it simply walks the entire device tree to find the highest phandle value and then returns a phandle value one higher than that. A more clever implementation might try to find holes in the current set of phandle values and fill them. But this implementation is relatively simple and works reliably. Also add a test that validates that phandles generated by this new API are indeed unique. Signed-off-by: Thierry Reding <treding@nvidia.com> Message-Id: <20190320151003.28941-1-thierry.reding@gmail.com> Signed-off-by: David Gibson <david@gibson.dropbear.id.au>
Diffstat (limited to 'cpukit/dtc/libfdt/fdt_ro.c')
-rw-r--r--cpukit/dtc/libfdt/fdt_ro.c31
1 files changed, 31 insertions, 0 deletions
diff --git a/cpukit/dtc/libfdt/fdt_ro.c b/cpukit/dtc/libfdt/fdt_ro.c
index eafc142828..97cdcda0db 100644
--- a/cpukit/dtc/libfdt/fdt_ro.c
+++ b/cpukit/dtc/libfdt/fdt_ro.c
@@ -170,6 +170,37 @@ uint32_t fdt_get_max_phandle(const void *fdt)
return 0;
}
+int fdt_generate_phandle(const void *fdt, uint32_t *phandle)
+{
+ uint32_t max = 0;
+ int offset = -1;
+
+ while (true) {
+ uint32_t value;
+
+ offset = fdt_next_node(fdt, offset, NULL);
+ if (offset < 0) {
+ if (offset == -FDT_ERR_NOTFOUND)
+ break;
+
+ return offset;
+ }
+
+ value = fdt_get_phandle(fdt, offset);
+
+ if (value > max)
+ max = value;
+ }
+
+ if (max == FDT_MAX_PHANDLE)
+ return -FDT_ERR_NOPHANDLES;
+
+ if (phandle)
+ *phandle = max + 1;
+
+ return 0;
+}
+
static const struct fdt_reserve_entry *fdt_mem_rsv(const void *fdt, int n)
{
int offset = n * sizeof(struct fdt_reserve_entry);