C and size_t and 64-bits

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;
    unsigned int length = 0;

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…

5 thoughts on “C and size_t and 64-bits

  1. William Astle

    It doesn’t help that historically, the stuff that uses size_t did use int so there’s a lot of code examples, etc., that do that int thing. Even more fun when you encounter ssize_t.

    More confusion from having a 64 bit system that use 32 bit integers which is, I think, what stuff Windows does. (“LP64” rather than “ILP64”)

    Extra points for getting printf() and friends to work some of those fancy types without cross platform integer size mismatches.

    1. Allen Huffman Post author

      The compiler warnings from printf() are frustrating. Code I write for PIC24 will give warnings when I test it out in Windows, and vise versa.

  2. James Jones

    Yes. Definitely look up even library calls you think you know in the standard. (Goodness knows I have to.) <stdint.h>, or better still, <inttypes.h>, since it has #defines for macros that expand to the format conversion strings named to match the stdint.h typedefs, is your friend.


Leave a Reply

This site uses Akismet to reduce spam. Learn how your comment data is processed.