[79538] branches/gsoc11-rev-upgrade/base/src/pextlib1.0/Pextlib.c

Clemens Lang cal at macports.org
Fri Jun 17 04:30:36 PDT 2011

On Fri, Jun 17, 2011 at 02:15:07AM -0500, Ryan Schmidt wrote:
> Aren't there 5 Mach-O magic numbers?
> > > 0xFEEDFACE: ppc
> > > 0xFEEDFACF: ppc64
> > > 0xCEFAEDFE: i386
> > > 0xCFFAEDFE: x86_64
> > > 0xCAFEBABE: any combination of two or more architectures
> > 6 since you're counting the byteswapped versions.
> > #define FAT_CIGAM	0xbebafeca

There's this[1] document on developer.apple.com describing the headers
of Mach-O and Universal Binary Mach-O files. If I read it right it says:

"Values for integer types in all Mach-O data structures are written
using the host CPU’s byte ordering scheme, except for fat_header and
fat_arch, which are written in big-endian byte order."

This means: non-universal runnable binary on x86* will actually have
either 0xfeedface or 0xfeedfacf (both in little endian) as magic number.
However, writing 0xfeedface or 0xfeedfacf into the code will also store
this number in little endian on these architectures, so
	magic == MH_MAGIC || magic == MH_MAGIC_64
will work just fine on these architectures. ppc and ppc64 binaries on
x86* would not be recognoized by this code (but then, do we have any
occassion where we're cross-compiling code to ppc just to run it under
rosetta later?)

On PPC or PPC64 architectures the magic number will be 0xfeedface or
0xfeedfacf in big endian and writing 0xfeedface into the code will
store the number in big endian, so the comparison again succeeds. From
what I know there's no way to run i386 or x86_64 binaries on PPC(64), so
we can safely ignore this.

When encountering universal binaries, the magic number will be
0xcafebabe in big endian, which is why I copare magic with the
big-endian version of FAT_MAGIC by using
	magic == htonl(FAT_MAGIC).
On PPC, htonl does nothing, on Intel it will swap the byte order (Apple
apparently call it byte sex in some of their code) from the
little endian memory-resident FAT_MAGIC constant to the big endian
version read from the file, so the comparison should again succeed.

> I'm simply listing the 5 magic numbers I've actually seen for Mach-O
> files, and describing them. Does that 6th type actually exist? I have
> not encountered it before.

[1] says FAT_CIGAM is for use only when you're on little endian systems
and want to check for a universal binaries' header. It will never be
encountered in a universal binary itself.

> > But you only strictly need 3 and you can derive the other 3.
> Sure, but it didn't look like the code did that. 

I think it implicitly does. Correct me if I'm wrong.

> > Of course, since this code is only going to work on Mach-O platforms
> > anyway, you might as well wrap the whole thing in #ifdef __MACH__
> > and include the headers mentioned in the comment.

Good idea, will probably do that. Didn't know there was a constant for

Regards, Clemens

[1] http://developer.apple.com/library/mac/#documentation/DeveloperTools/Conceptual/MachORuntime/Reference/reference.html
Clemens Lang
GSoC Student

More information about the macports-dev mailing list