Merge pull request #506 from andrewcsmith/patch-2
[supercollider.git] / common / SC_StandAloneInfo_Darwin.cpp
blob4269af637923b8204acd7f5ce10507a2d96b1796
1 #if defined(__APPLE__) || defined(SC_IPHONE)
3 #include <sys/param.h>
4 #include <stdexcept>
5 #include <cstring> // for strncpy
6 #include <mach-o/dyld.h> // for _NSGetExecutablePath
7 #include <libgen.h>
8 #include <stdlib.h>
10 #include <CoreFoundation/CFString.h>
11 #include <CoreFoundation/CFBundle.h>
12 //#include <CoreServices/CoreServices.h>
14 #include "SC_StandAloneInfo_Darwin.h"
16 bool SC_StandAloneInfo::haveCheckedBundleStatus;
17 char SC_StandAloneInfo::dirPath[PATH_MAX];
19 void SC_StandAloneInfo::SC_StandAloneInfoInit() {
20 char relDir[PATH_MAX];
21 CFStringEncoding encoding = kCFStringEncodingASCII;
22 if(!haveCheckedBundleStatus) {
23 haveCheckedBundleStatus = true;
25 CFURLRef enablerURL = CFBundleCopyResourceURL (
26 CFBundleGetMainBundle(),
27 CFSTR("SCClassLibrary"),
28 NULL,
29 NULL
31 if( !enablerURL ) {
32 enablerURL = CFBundleCopyResourceURL (
33 CFBundleGetMainBundle(),
34 CFSTR("sclang.app"),
35 NULL,
36 NULL
39 if ( enablerURL ) {
40 // If sclang or SuperCollider binary is run within the .app bundle,
41 // this is how we find the Resources path.
42 CFStringRef rawPath = CFURLCopyFileSystemPath(enablerURL, kCFURLPOSIXPathStyle);
43 rawPath = CFStringCreateWithFormat(NULL, NULL, CFSTR("%@/.."), rawPath);
44 CFStringGetCString(rawPath, relDir, PATH_MAX, encoding);
45 } else {
46 // when sclang is run from a symlink, the resource URL above will not be found,
47 // so we need to find the path of the executable.
48 uint32_t bufsize = PATH_MAX, *bufsizep = &bufsize;
49 if(_NSGetExecutablePath(relDir, bufsizep)==0) {
50 realpath(relDir, dirPath); // resolve symlink
51 char *dir = dirname(dirPath);
52 strcpy(dirPath, dir);
53 return;
54 } else {
55 // in case it failed, fall back to current directory
56 getcwd(dirPath, PATH_MAX);
59 realpath(relDir, dirPath);
63 bool SC_StandAloneInfo::IsStandAlone() {
64 #ifdef SC_STANDALONE
65 return true;
66 #else
67 return false;
68 #endif
71 void SC_StandAloneInfo::GetResourceDir(char* pathBuf, int length)
73 if ( !haveCheckedBundleStatus )
75 SC_StandAloneInfoInit();
77 strncpy(pathBuf, dirPath, length);
80 #endif