LinuxQuestions.org

LinuxQuestions.org (/questions/)
-   Programming (http://www.linuxquestions.org/questions/programming-9/)
-   -   Determining if a system is 32bit or 64bit via C language. (http://www.linuxquestions.org/questions/programming-9/determining-if-a-system-is-32bit-or-64bit-via-c-language-4175425992/)

Lsatenstein 09-06-2012 12:35 PM

Determining if a system is 32bit or 64bit via C language.
 
I need to do something like this

If (sizeof(long) == 8)
typedef unsigned int uintxx;
else
typedef unsigned long uintxx;

The problem is that a typedef may not be part of a if/else expression.

Is there a defined compiler library constant that I may use for linux gcc compiler.

Is there a preprocessor variable I could test?


I found this, which does not work with gcc

#if (!(defined __LP64__ || defined __LLP64__)||( defined _WIN32 && !defined _WIN64 ))
// we are compiling for a 32-bit system
typedef unsigned long uintxx;
#else
// we are compiling for a 64-bit system
typedef unsigned int uintxx;
#endif

eSelix 09-06-2012 05:32 PM

Quote:

The problem is that a typedef may not be part of a if/else expression.
Yes, because types must be fully defined during compilation, without that compiler doesn't known how many memory should reserve for variable, and "if" statement is executing when program is already compiled and running. Anyway, determining architecture by size of long type is not a reliable way, this size is dependend on compiler and can change in the future. Better method is using predefined macros, in gcc you have that
Code:

#ifdef __x86_64
  // 64bit
#elif defined __i386
  // 32bit
#else
  // Unknown
#endif

Also if you need an exactly bit length variable, you can use types created for that, there are int64_t, int32_t, int16_t or int8_t, with specified bit length - they are defined in <stdint.h>

sundialsvcs 09-06-2012 06:23 PM

The "#ifdef" approach is the only one that will actually work, because it determines at compile time which block of source-code will actually be submitted to the compiler.

However, "don't make work for yourself." :) Every language system out there has "platform independence" capabilities and there's a lot of very detailed documentation about both the relevant issues and their "don't ask why, just do this..." solutions. There's also a boat-load of existing open source software out there which shows you, for your particular environment whatever-it-is, exactly how it's correctly done.

"Actum Ne Agas ... Do Not Do A Thing Already Done."

NevemTeve 09-07-2012 07:36 AM

Note: For a start, what is 32 or 64 bit? Size of int? or that of long / long long / ptr?

Different possibilities are possible, eg:

short=int=ptr=16 long=32 (code: SIP16-L32 or simply L32, eg: MS-DOS 'small' modell)
short=int=16 long=ptr=32 (code: SI16-LP32 or simply LP32, eg: MS-DOS 'large' modell)
short=16, int=long=ptr=32 (code: S16-ILP32 or simply ILP32, eg: Unix32, Windows32 (older versions without any 64-bit type))
short=16, int=long=ptr=32, long long=64 (code: S16-ILP32-LL64 or simply LL64, eg: Unix32, Windows32)
short=16, int=32, long=long long=ptr=64 (code: S16-I32-LP64 or simply LP64, eg: Unix64)
short=16, int=long=32, long long=ptr=64 (code: S16-I32-LP64 or simply LLP64, eg: Windows64)

conclusion: if you want fixed-size integers, use intNN_t (uintNN_t) from stdint.h/inttypes.h, and if you want a 'pointer compatible' integer, use predefined types like 'ptrdiff_t', 'size_t', 'ssize_t', 'intptr_t', 'uintptr_t'


All times are GMT -5. The time now is 05:28 PM.