Building for x86_64 on MacOS X 10.5

I am trying to build JUCE for x86_64 architecture on a system with MacOS 10.5

It turned out that the following code compiles just file for 32bit systems (juce_mac_Files.mm)

//==============================================================================
OSType PlatformUtilities::getTypeOfFile (const String& filename)
{
    const ScopedAutoReleasePool pool;

#if JUCE_IPHONE || (defined (MAC_OS_X_VERSION_10_5) && MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_5)
    NSDictionary* fileDict = [[NSFileManager defaultManager] attributesOfItemAtPath: juceStringToNS (filename) error: nil];
#else
    NSDictionary* fileDict = [[NSFileManager defaultManager] fileAttributesAtPath: juceStringToNS (filename) traverseLink: NO];
#endif
    return (OSType) [fileDict objectForKey: NSFileHFSTypeCode];
}

but when compiling for 64 bit the last return complains that it is casting a pointer (64bit) into a OSType, which is defined in MacTypes.h as a four characters value even for 64bit systems.

Digging further, I found the method fileHFSTypeCode of NSDictionary which seems to do the job of obtaining the desired OSType, rather than having to rely on the generic objectForKey.

I replaced the last line above with the following

return [fileDict fileHFSTypeCode];

and it worked like a charm without complaints. I suggest you to do the same.

In addition, when compiling for x86_64 as explained in the previous post, I found some errors related to this code found in juce_mac_NSViewComponentPeer.mm:

void juce_setKioskComponent (Component* kioskModeComponent, bool enableOrDisable, bool allowMenusAndBars)
{
    // Very annoyingly, this function has to use the old SetSystemUIMode function,
    // which is in Carbon.framework. But, because there's no Cocoa equivalent, it
    // is apparently still available in 64-bit apps..
    if (enableOrDisable)
    {
        SetSystemUIMode (kUIModeAllSuppressed, allowMenusAndBars ? kUIOptionAutoShowMenuBar : 0);
        kioskModeComponent->setBounds (Desktop::getInstance().getMainMonitorArea (false));
    }
    else
    {
        SetSystemUIMode (kUIModeNormal, 0);
    }
}

Since I trusted the comment that says that the call is available for 64-bit apps, I searched for places where the Carbon.h header should have been included but it has been not for some reason. Surprisingly, I found that the only place where Carbon.h is included is in the code to add support for hosting VST plug-ins in the application.

Since normally I have

#define JUCE_PLUGINHOST_VST 0

because I don’t need to host VST plug-ins, I tried to #define that macro to 1 and ended up successfully compiling the code!

My opinion here is that, when compiling 32-bits application, prototypes and enum values for SetSystemUIMode are included somewhere along the path. This is not true for 64-bits compilations, which in my opinion need an explicit inclusion of Carbon.h somewhere, in order to have those symbols defined.

Thanks for those - very useful! You’re right about the carbon header - it just needs adding to juce_mac_NativeIncludes.h, I’ll get that fixed up.

I think it would be a good idea to put that inclusion under condition of JUCE_SUPPORT_CARBON being true

JUCE_SUPPORT_CARBON is more about supporting carbon UIs, not about linking to the carbon library. Including/linking to carbon isn’t really something you’d need to disable because it should compile ok on all targets.

Some more difficulties on this subject: since I am targeting a 10.4 deployment, there are some typedefs conflicting in juce_mac_NativeIncludes.h, namely:

#if MACOS_10_4_OR_EARLIER
 #include <GLUT/glut.h>
 typedef int NSInteger;
 typedef unsigned int NSUInteger;
#endif

Those typedefs seem to override some already defined ones, but the compiler does not complain for 32bits because the types match.

This is not true for 64bit, where the types don’t match. In fact, I get a conflict with the following snippet of code, taken from NSObjCRuntime.h (line 110):

#if __LP64__ || NS_BUILD_32_LIKE_64
typedef long NSInteger;
typedef unsigned long NSUInteger;
#else
typedef int NSInteger;
typedef unsigned int NSUInteger;
#endif

As you can see, those typedefs are different for 64 bit compilations, thus maybe you should add the case to your #ifdefs, or either remove them completely since they are already defined somewhere else?

Maybe it’s something needed for systems earlier than 10.4?

Ah, yes. I think they can actually be removed now.

In the old days they were needed because they weren’t always provided by the carbon headers, but now that the build always includes the obj-c runtime, it looks like they’ll always be there. Thanks!

[quote=“yfede”]In addition, when compiling for x86_64 as explained in the previous post, I found some errors related to this code found in juce_mac_NSViewComponentPeer.mm:

void juce_setKioskComponent (Component* kioskModeComponent, bool enableOrDisable, bool allowMenusAndBars)
{
    // Very annoyingly, this function has to use the old SetSystemUIMode function,
    // which is in Carbon.framework. But, because there's no Cocoa equivalent, it
    // is apparently still available in 64-bit apps..
    if (enableOrDisable)
    {
        SetSystemUIMode (kUIModeAllSuppressed, allowMenusAndBars ? kUIOptionAutoShowMenuBar : 0);
        kioskModeComponent->setBounds (Desktop::getInstance().getMainMonitorArea (false));
    }
    else
    {
        SetSystemUIMode (kUIModeNormal, 0);
    }
}

Since I trusted the comment that says that the call is available for 64-bit apps, I searched for places where the Carbon.h header should have been included but it has been not for some reason. Surprisingly, I found that the only place where Carbon.h is included is in the code to add support for hosting VST plug-ins in the application.

Since normally I have

#define JUCE_PLUGINHOST_VST 0

because I don’t need to host VST plug-ins, I tried to #define that macro to 1 and ended up successfully compiling the code!

My opinion here is that, when compiling 32-bits application, prototypes and enum values for SetSystemUIMode are included somewhere along the path. This is not true for 64-bits compilations, which in my opinion need an explicit inclusion of Carbon.h somewhere, in order to have those symbols defined.[/quote]

Hi yfede,
Thanks for the tip. It helped me solve the errors. :smiley:

Hello

I’m working against the tip (note: not the head revsion) in OS 10.6. Attempting to build a 64bit version of the library results in the same error in juce_setKioskComponent mentioned above. The response was that Carbon.h needed to be added to the Mac native includes header file. Doing this on my end indeed fixes the problem. I checked the latest revision of juce_mac_NativeIncludes.h in the tip, and it doesn’t appear to include Carbon.h. I was wondering if Carbon.h is meant to be included some other way, or if it is still an issue in the latest tip revision.

Thanks.

…umm, yes it does, at line 61 (?)

:facepalm: Yes, of course it does. Not sure how I missed that. Sorry for the noise.

Hi Jules!

There is still a problem building for 10.5 SDK … I just found this with Juce 1.52 building 64-bit code (I was working with Juce 1.50 before, I’m just updating to Juce 1.52 for the new year!)…

Building juce_mac_NativeCode.mm…

CompileC ../../bin/Juce.build/Debug/Juce.build/Objects-normal/x86_64/juce_mac_NativeCode.o ../../src/native/juce_mac_NativeCode.mm normal x86_64 objective-c++ com.apple.compilers.gcc.4_2
...
/Users/xxx/juce/Builds/MacOSX/../../src/native/mac/juce_mac_NSViewComponentPeer.mm: In function 'void juce::juce_setKioskComponent(juce::Component*, bool, bool)':
/Users/xxx/juce/Builds/MacOSX/../../src/native/mac/juce_mac_NSViewComponentPeer.mm:1676: error: 'kUIModeAllSuppressed' was not declared in this scope

etc.

My workaround for now is to always include <Carbon/Carbon.h> in juce_mac_NativeIncludes.h … which obviously isn’t ideal!

Hoping you can fix this. :slight_smile:

Best wishes,

Pete

Not sure I understand… If you’re targeting 10.5, then Carbon.h is always included in juce_mac_NativeIncludes.h… It’s only if you’re targeting 10.6 that it isn’t, because it doesn’t need it (?)

Are you using the version I checked in yesterday?

Hi Jules!

I’m using software grabbed from the tip, midway through the afternoon.

Base SDK Mac OS X 10.5
64-bit (x86_64)

The code in juce_mac_NativeIncludes.h is like this … I got it compiling by removing the conditional bits!

#if JUCE_BUILD_MISC && (JUCE_PLUGINHOST_VST || JUCE_PLUGINHOST_AU) \
    && ! (defined (MAC_OS_X_VERSION_10_6) && MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_6)
  #include <Carbon/Carbon.h>
#endif

I guess I’m probably missing something… :slight_smile:

Pete

yes… exactly. If you’re NOT targeting 10.6, then it includes carbon.h. Or am I being thick…?

Hi Jules!

My configuration that ** fails ** for ** 64-bit ** (but OK for 32-bit):

  • set Base SDK to 10.5 or 10.6
  • set Deployment Target to ** 10.5 **

My configuration that ** works ** for 64-bit (and 32-bit)

  • set Base SDK to 10.6
  • set Deployment Target to ** 10.6 **

So, the logic is somehow wrong on the deployment target; I can’t quite figure-out why!
If you simply build Juce library in debug mode for 64-bit architecture for 10.5 target, you’ll see the same problem! :slight_smile:

On a separate note… might I request you add 64-bit to supported architectures for target for Juce library in future builds…?

Best wishes,

Pete

Sorry, I was just being thick - that line only gets compiled if the plugin host stuff is enabled. I’ll sort it out…

Cheers Jules. :slight_smile:

Pete