lkml.org 
[lkml]   [2013]   [Aug]   [29]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
Patch in this message
/
From
Subject[PATCH] of/fdt: Clean up casting in unflattening path
Date
The flat tree unflatting path is using unsigned longs to carry around
virtual address pointers to the device tree and the allocated memory
used to unpack it. This is a little insane since every access to them
needs to be cast to a pointer type before using it. This patch changes
the data type to void* for the 'start' and 'mem' pointers and reworks
the unflattening functions to use those values directly which results in
slightly simpler code.

Signed-off-by: Grant Likely <grant.likely@linaro.org>
---
drivers/of/fdt.c | 63 +++++++++++++++++++++++++++-----------------------------
1 file changed, 30 insertions(+), 33 deletions(-)

diff --git a/drivers/of/fdt.c b/drivers/of/fdt.c
index d49b3e8..55b028f 100644
--- a/drivers/of/fdt.c
+++ b/drivers/of/fdt.c
@@ -126,13 +126,13 @@ int of_fdt_match(struct boot_param_header *blob, unsigned long node,
return score;
}

-static void *unflatten_dt_alloc(unsigned long *mem, unsigned long size,
+static void *unflatten_dt_alloc(void **mem, unsigned long size,
unsigned long align)
{
void *res;

- *mem = ALIGN(*mem, align);
- res = (void *)*mem;
+ *mem = PTR_ALIGN(*mem, align);
+ res = *mem;
*mem += size;

return res;
@@ -147,9 +147,9 @@ static void *unflatten_dt_alloc(unsigned long *mem, unsigned long size,
* @allnextpp: pointer to ->allnext from last allocated device_node
* @fpsize: Size of the node path up at the current depth.
*/
-static unsigned long unflatten_dt_node(struct boot_param_header *blob,
- unsigned long mem,
- unsigned long *p,
+static void * unflatten_dt_node(struct boot_param_header *blob,
+ void *mem,
+ void **p,
struct device_node *dad,
struct device_node ***allnextpp,
unsigned long fpsize)
@@ -162,15 +162,15 @@ static unsigned long unflatten_dt_node(struct boot_param_header *blob,
int has_name = 0;
int new_format = 0;

- tag = be32_to_cpup((__be32 *)(*p));
+ tag = be32_to_cpup(*p);
if (tag != OF_DT_BEGIN_NODE) {
pr_err("Weird tag at start of node: %x\n", tag);
return mem;
}
*p += 4;
- pathp = (char *)*p;
+ pathp = *p;
l = allocl = strlen(pathp) + 1;
- *p = ALIGN(*p + l, 4);
+ *p = PTR_ALIGN(*p + l, 4);

/* version 0x10 has a more compact unit name here instead of the full
* path. we accumulate the full path size using "fpsize", we'll rebuild
@@ -240,7 +240,7 @@ static unsigned long unflatten_dt_node(struct boot_param_header *blob,
u32 sz, noff;
char *pname;

- tag = be32_to_cpup((__be32 *)(*p));
+ tag = be32_to_cpup(*p);
if (tag == OF_DT_NOP) {
*p += 4;
continue;
@@ -248,11 +248,11 @@ static unsigned long unflatten_dt_node(struct boot_param_header *blob,
if (tag != OF_DT_PROP)
break;
*p += 4;
- sz = be32_to_cpup((__be32 *)(*p));
- noff = be32_to_cpup((__be32 *)((*p) + 4));
+ sz = be32_to_cpup(*p);
+ noff = be32_to_cpup(*p + 4);
*p += 8;
if (be32_to_cpu(blob->version) < 0x10)
- *p = ALIGN(*p, sz >= 8 ? 8 : 4);
+ *p = PTR_ALIGN(*p, sz >= 8 ? 8 : 4);

pname = of_fdt_get_string(blob, noff);
if (pname == NULL) {
@@ -282,11 +282,11 @@ static unsigned long unflatten_dt_node(struct boot_param_header *blob,
np->phandle = be32_to_cpup((__be32 *)*p);
pp->name = pname;
pp->length = sz;
- pp->value = (void *)*p;
+ pp->value = *p;
*prev_pp = pp;
prev_pp = &pp->next;
}
- *p = ALIGN((*p) + sz, 4);
+ *p = PTR_ALIGN((*p) + sz, 4);
}
/* with version 0x10 we may not have the name property, recreate
* it here from the unit name if absent
@@ -335,7 +335,7 @@ static unsigned long unflatten_dt_node(struct boot_param_header *blob,
else
mem = unflatten_dt_node(blob, mem, p, np, allnextpp,
fpsize);
- tag = be32_to_cpup((__be32 *)(*p));
+ tag = be32_to_cpup(*p);
}
if (tag != OF_DT_END_NODE) {
pr_err("Weird tag at end of node: %x\n", tag);
@@ -361,7 +361,8 @@ static void __unflatten_device_tree(struct boot_param_header *blob,
struct device_node **mynodes,
void * (*dt_alloc)(u64 size, u64 align))
{
- unsigned long start, mem, size;
+ unsigned long size;
+ void *start, *mem;
struct device_node **allnextp = mynodes;

pr_debug(" -> unflatten_device_tree()\n");
@@ -382,32 +383,28 @@ static void __unflatten_device_tree(struct boot_param_header *blob,
}

/* First pass, scan for size */
- start = ((unsigned long)blob) +
- be32_to_cpu(blob->off_dt_struct);
- size = unflatten_dt_node(blob, 0, &start, NULL, NULL, 0);
- size = (size | 3) + 1;
+ start = ((void *)blob) + be32_to_cpu(blob->off_dt_struct);
+ size = (unsigned long)unflatten_dt_node(blob, 0, &start, NULL, NULL, 0);
+ size = ALIGN(size, 4);

pr_debug(" size is %lx, allocating...\n", size);

/* Allocate memory for the expanded device tree */
- mem = (unsigned long)
- dt_alloc(size + 4, __alignof__(struct device_node));
+ mem = dt_alloc(size + 4, __alignof__(struct device_node));
+ memset(mem, 0, size);

- memset((void *)mem, 0, size);
+ *(__be32 *)(mem + size) = cpu_to_be32(0xdeadbeef);

- ((__be32 *)mem)[size / 4] = cpu_to_be32(0xdeadbeef);
-
- pr_debug(" unflattening %lx...\n", mem);
+ pr_debug(" unflattening %p...\n", mem);

/* Second pass, do actual unflattening */
- start = ((unsigned long)blob) +
- be32_to_cpu(blob->off_dt_struct);
+ start = ((void *)blob) + be32_to_cpu(blob->off_dt_struct);
unflatten_dt_node(blob, mem, &start, NULL, &allnextp, 0);
- if (be32_to_cpup((__be32 *)start) != OF_DT_END)
- pr_warning("Weird tag at end of tree: %08x\n", *((u32 *)start));
- if (be32_to_cpu(((__be32 *)mem)[size / 4]) != 0xdeadbeef)
+ if (be32_to_cpup(start) != OF_DT_END)
+ pr_warning("Weird tag at end of tree: %08x\n", be32_to_cpup(start));
+ if (be32_to_cpup(mem + size) != 0xdeadbeef)
pr_warning("End of tree marker overwritten: %08x\n",
- be32_to_cpu(((__be32 *)mem)[size / 4]));
+ be32_to_cpu(mem + size));
*allnextp = NULL;

pr_debug(" <- unflatten_device_tree()\n");
--
1.8.1.2


\
 
 \ /
  Last update: 2013-08-29 16:01    [W:0.030 / U:2.516 seconds]
©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site