Question about Pointer Behaviour
Background: For my knitting machine, I want to add a camera as sensor. The camera is ESP32 (Tensilica) based and I use the Arduino environment for this. Which uses the GnuC++, as far as I know. Unfortunately I updated board definitions for ESP32 and since some code does not work anymore as before. The routine is part of a Forth compiler.
It is unclear to me, if this is the result of
a) changed compiler optimation strategies
b) changed definition of size_t
c) an alignment problem of the pointer. (Not at a 4 byte boundary)
d) the pHere++ was formerly done before the right side of the line and is now done afterward (As I thought would be the idea.)
.... typedef int32_t cell_t; ... cell_t* pHere; // HERE, points to the next free position in // Forth Space .... void _does(void) { *pHere++ = SUBROUTINE_IDX; // Store location for a subroutine call // *pHere++ = (size_t)pHere + sizeof(cell_t); // **used to work **Code beginnt in übernächster Zelle *pHere++ = (size_t)pHere + 2*sizeof(cell_t); // **works now** Code beginnt in übernächster Zelle *pHere++ = EXIT_IDX; // Start Subroutine coding, entry must point to this location! }
Actually, I don't understand, why this ever worked before. Codes in this Forth machine are 32bit. As far as I understand, size_t is long long integer. I don't understand, why this was chosen.
Perhaps, someone can give me some hints. I don't want to create new further problems.
Thank you!
Christof
Comments
size_t
is an unsigned integer type that will hold the size of any possible object. On a 32 bit system (like most modern MCUs) it will typically be a 32 bit unsigned integer. However, if you've changed compilers recently then it's possible that the new compiler has a different definition forsize_t
. If it's now using 64 bits forsize_t
then perhaps it also needs 64 bits forcell
. Indeed, I would have defined thecell_t
type astypedef intptr_t cell_t;
, as that says that a cell has to be able to hold a pointer (so on 64 bit machines it should be 64 bits).Thank you!
I still don't understand, why the old code was able to compile the correct address which is pHere+8bytes.
The right-side is evaluated first, so the post-increment always happens after the assignment. If the compiler did otherwise, then it was likely a bug.
All other things, seems irrelevant (aligment, size of size_t, have nothing to do with it).
To me, the commented line that "used to work" didn't worked, or maybe it worked because of a side effect of something else (compiler bug ?).
Anyway, the line "works now" seems correct, if that location should point to the location after EXIT_IDX, then adding 2 * sizeof(cell_it) is correct, because on the right side, pHere still points to the location before the post-increment (so 4 bytes to skip the current location + 4 bytes to skip EXIT_IDX location). With the commented line, it will point to the location of EXIT_IDX.
That if I haven't missed something.
Thank you!
Your comment makes totally sense for me. Though I find it very strange that those compensating bugs in compiler and code has worked for several years?!