[U-Boot] fdt performance

Michael Pratt mpratt at chromium.org
Sun Oct 20 20:18:49 CEST 2013


Hi Wolfgang,

On Fri, Oct 18, 2013 at 4:11 PM, Wolfgang Denk <wd at denx.de> wrote:

> Dear Andre,
>
> In message <
> CAPfzE3a2ne-xcjKUTK8WS78V0yxuSd50wSQvm1rSPgNUfwP4Ow at mail.gmail.com> you
> wrote:
> >
> > >> Some of the checks in fdt_offset_ptr also look useless, such as if
> > >> ((offset + len) < offset) which will always be false, or
> > >> if (p + len < p)
> > >
> > > What happens if the "offset" or "p" point to addresses close to the
> > > upper end of the address space, and adding "len" makes it wrap around?
> >
> > I'm not sure how particular U-Boot is about this, but the C standard
> > doesn't specify what to do in the situation of signed overflow, so
>
> These are no signed numbers, right?
>
> > it's possible that these checks could be simply optimised away. The
>
> This is not hwat happens.
>

Actually, it is my understanding that the "if (p + len < p)" can be
optimized away.  This exact case is discussed in the LWN article "GCC and
pointer overflows"[1].

Basically, the C standard states that pointer arithmetic should not cause
overflow, thus allowing the compiler to assume that "p + len" must always
be greater than "p".

The exact wording can be found in section 6.5.6 "Additive operators",
statement 8 of the C99 specification:

> If both the pointer operand and the result point to elements of the same
> array object, or one past the last element of the array object, the
> evaluation shall not produce an overflow; otherwise, the behavior is
> undefined.


Thus, this use of pointer overflow is undefined.

This has nothing to do with GCC.  It's a standard C question. Inmy
> understanding, the expression "offset + len" (with "offset" being
> "int", and "len" being "unsigned int"), will give an "unsigned int";
> the comparison willt hen also be done using "unsigned int" data types.
>

I agree this expression ((offset + len) < offset) is safe, since it will
used unsigned ints.  Since "int" and "unsigned int" have the same rank,
"offset" will be converted to an unsigned int before the addition.  This
comes from section 6.3.1.8 in the C99 specification:

> Otherwise, if the operand that has unsigned integer type has rank greater
> or equal to the rank of the type of the other operand, then the operand
> with signed integer type is converted to the type of the operand with
> unsigned integer type.


 [1]: http://lwn.net/Articles/278137/

Regards,
Michael Pratt


More information about the U-Boot mailing list