views:

65

answers:

3

I initially thought that 64 bit instructions would not work on OS-X 10.5.

I wrote a little test program and compiled it with GCC -m64. I used long long for my 64 bit integers.

The assembly instructions used look like they are 64 bit. eg. imultq and movq 8(%rbp),%rax.

I seems to work.

I am only using printf to display the 64 bit values using %lld.

  1. Is this the expected behaviour?
  2. Are there any gotcha's that would cause this to fail?
  3. Am I allowed to ask multiple questions in a question?
  4. Does this work on other OS's?
+2  A: 

Mac OS X 10.5 supports 64-bit user-land applications pretty well. In fact, Xcode runs in 64-bit in 10.5 on a compatible architecture.

It's only the built-in applications (Finder, Safari, frameworks, daemons etc.) also have the 64-bit version in 10.6.

KennyTM
A: 

Meta: I don't like to see answers deleted. I guess this has been discussed somewhere.

Anyway, KennyTM and the other kind sole got me started and although one answer was deleted, I appreciated your efforts.

  1. It looks like this is expected behaviour on the Mac, and it even seems to work on a 32-bit Linux as well (although I have not tested extensively)

  2. Yep. GCC behaves different (at least in my limited observation) for 32 (-m32) and 64 (-m64) bit modes. In 32 bit, I was able to access variable arguments using an array. In 64 bit mode this just does not work.

I have learnt that you MUST access variable parameters using va_list as defined by stdarg.h because it works in both modes.

Now I have a command-line program that runs and passes all of my test cases in 32 bit and 64 bit modes on Mac OS-X.

The program implements a linked list garbage collector sweeping 16-byte aligned malloc-allocated objects from a global list as well as machine registers and the stack - actually, there are extra registers in 64 bit mode, so I still have a bit of work to do.

Objects are either a collection of 32 or 64 bit words which link together to form LISP/Scheme-like data structures.

In summary, it is a complex program that does a lot of messing with pointers and it works the same under 32 and 64 bit modes.

  1. Asking multiple questions does not get you all the answers you might want.

  2. It seems to work, as I wrote, on Linux.

Again, thank you for helping me with this.

philcolbourn
+2  A: 

Just to make this completely clear, here is the situation for 32- and 64-bit executables on OS X:

  • Both 32- and 64-bit user space executables can be run on both 32- and 64-bit kernels in OS X 10.6, without emulation. On 10.4 and 10.5, both 32- and 64-bit executables can run on the 32-bit kernel. (This is not true on Windows)

  • The user space system libraries and frameworks are built 32/64-bit fat on 10.5 and 10.6. You can link against them normally, whether you're building for 32-bit, 64-bit, or both. A few libraries (basically the POSIX layer) are also built 32/64-bit fat on 10.4, but many of them are not.

  • On 10.6, the build tools produce 64-bit executables by default. On 10.5 and earlier, the default is 32-bit.

  • On 10.6, executables that are built fat will run the 64-bit side by default. On 10.5 and earlier, the 32-bit side is executed by default.

  • You can always manually specify which slice of a fat executable to use by using the arch command. eg. arch -arch i386 someCommandToRunThatIWantToRunIn32BitMode. For application bundles, you can either launch them from the command line, or there is a preference if you "get info" on the application.

  • OS X and Linux use the LP64 model for 64-bit executables. Pointers and long are 64 bits wide, int is still 32 bits, and long long is still 64 bits. (Windows uses the LLP64 model instead -- long is 32 bits wide in 64 bit Windows).

Stephen Canon
Looks like you answered it thoroughly. Thanks. A follow up if you have time: how do you use the LP64 model - is that a gcc option?
philcolbourn
Any of the compilers on a system that uses the LP64 model (OS X, Linux, others) will generate 64-bit code using that model by default. If they didn't, this would cause incompatibility between programs built with different compilers. The 64-bit model used is a property of the system's ABI, not something that you (generally) want to change via a compiler switch.
Stephen Canon