Do what I say and nobody gets hurt!
At my day job, I work on a Windows application that supervises high power solid state microwave generators. (The actual controlling part is done by multiple embedded PIC24-based boards, which is a good thing considering the issues Windows has given us over the years.)
At some point, we switched from building a 32-bit version of this application to a 64-bit version. The compiler started complaining about various things dealing with “ints” which were not 64-bits, so the engineer put in #ifdef code like this:
#ifdef _NI_mswin64_ unsigned __int64 length = 0; #else unsigned int length = 0; #endif
That took care of the warnings since it would now use either a native “int” or a 64-bit int, depending on the target.
Today I ran across this and wondered why C wasn’t just taking care of things. A C library routine that returns an “int” should always expect an int, whether that int is 16-bits (like on Arduino), 32-bits or 64-bits on the system. I decided to look in to this, and saw the culprits were things like this:
length = strlen (pathName);
Surely if strlen() returned an int, it should not need to be changed to an “unsigned __int64” to work.
And indeed, C already does take care of this, if you do what it tells you to do. strlen does NOT return an int:
size_t strlen ( const char * str );
size_t is a special C data type that is “whatever type of number it needs to be.” And by simply changing all the #ifdef’d code to actually use the data type the C library call specifies, all the errors go away and the #ifdefs can be removed.
size_t length = 0;
A better, more stricter compiler might have complained about using an “int” to catch something coming back as “size_t.”
Oh wait. It did. We just chose to solve it a different way.
Until next time…