On Thu, Apr 24, 2008 at 08:37:43PM -0400, Robert C. Seacord wrote:
> The original impetus for this came from a check in a sprint() function 
> from Plan 9.  Because of the API, there was no way to test if the len 
> was out of bounds, but the developers wanted to make sure they weren't 
> wrapping the stack on some architectures that have their stacks in high 
> memory.

It sounds like there are two issues here: a problem with the API (ideally
it would be possible to do a proper length check, though sometimes these
are legacy issues that one is stuck with), and a problem with the way the
test is coded.  A portable-in-practice way to do checks on pointer
addresses of this kind is to cast the pointers to unsigned integers of the
appropriate length before doing the arithmetic.  In C, unsigned types are
guaranteed to obey the rules of modulo 2**N arithmetic, where N is the
number of bits.

(I say "portable in practice" because things like segmented architectures
raise other issues, but for a flat address space on a conventional
processor that has an integral type the same size as a pointer type,
you should be OK).

> It seems like a reasonable test to make, the code used to work, and they 
> got burned on the silent change in behavior.

Unfortunately, C is not designed that way, which makes it rather
surprising that Plan 9 was burned by this (it has architects who should
know better, given their role in the definition of C).  These are not
new issues; they were fought over back in the late 1980s, and we have
the rules we do because otherwise, anyone wanting to write fast code
would need to use Fortran, as the "consistency" you are asking for
would mean that everything aliases everything so it's unsafe to use
registers.


Reply via email to