NSSystemDirectories.c [plain text]
#include <NSSystemDirectories.h>
#include <stdlib.h>
#include <string.h>
#include <sys/param.h>
#include <unistd.h>
#define NSUserDomainIndex 0
#define NSLocalDomainIndex 1
#define NSNetworkDomainIndex 2
#define NSSystemDomainIndex 3
#define numDomains (NSSystemDomainIndex + 1)
#define DomainMask ((1 << numDomains) - 1)
#define addNextRoot(x) (*(x) == '/' || *(x) == 0)
#define Network "/Network"
#define System "/System"
#define Tilde "~"
#define NSApplicationDirectoryBase "/Applications"
#define NSDemoApplicationDirectoryBase "/Applications/Demos"
#define NSDeveloperApplicationDirectoryBase "/Developer/Applications"
#define NSAdminApplicationDirectoryBase "/Applications/Utilities"
#define NSLibraryDirectoryBase "/Library"
#define NSDeveloperDirectoryBase "/Developer"
#define NSUserDirectoryBase "/Users"
#define NSDocumentationDirectoryBase "/Library/Documentation"
#define NSDocumentDirectoryBase "/Documents"
#define NSCoreServiceDirectoryBase "/Library/CoreServices"
#define NSAutosavedDocumentsDirectoryBase "/Library/Autosave Information"
#define NSDesktopDirectoryBase "/Desktop"
#define NSCachesDirectoryBase "/Library/Caches"
#define NSInputMethodsDirectoryBase "/Library/Input Methods"
#define NSMoviesDirectoryBase "/Movies"
#define NSMusicDirectoryBase "/Music"
#define NSPicturesDirectoryBase "/Pictures"
#define NSPrinterDescriptionDirectoryBase "/Library/Printers/PPDs"
#define NSSharedPublicDirectoryBase "/Public"
#define NSPreferencePanesDirectoryBase "/Library/PreferencePanes"
#define NSApplicationSupportDirectoryBase "/Library/Application Support"
#define NSDownloadsDirectoryBase "/Downloads"
static const char * const prefixAll[] = {
Tilde,
"",
Network,
""
};
static const char * const prefixAllSystem[] = {
Tilde,
"",
Network,
System
};
static const char * const prefixNoUserSystem[] = {
NULL,
"",
Network,
NULL
};
static const char * const prefixNoNetwork[] = {
Tilde,
"",
NULL,
System
};
static const char * const prefixSystemOnly[] = {
NULL,
NULL,
NULL,
System
};
static const char * const prefixUserOnly[] = {
Tilde,
NULL,
NULL,
NULL
};
static const char * const _prefixNetwork4[] = {
Network,
Network,
Network,
Network
};
static const char * const _prefixNone4[] = {
"",
"",
"",
""
};
static const char * const _prefixTilde4[] = {
Tilde,
Tilde,
Tilde,
Tilde
};
static const char * const * const prefixAllApplicationsDirectory[] = {
_prefixTilde4,
_prefixNone4,
_prefixNetwork4,
_prefixNone4
};
static const char * const baseAllApplicationsDirectory[] = {
NSApplicationDirectoryBase,
NSAdminApplicationDirectoryBase,
NSDeveloperApplicationDirectoryBase,
NSDemoApplicationDirectoryBase
};
static const char * const _prefixNetwork2[] = {
Network,
Network
};
static const char * const _prefixNone2[] = {
"",
""
};
static const char * const _prefixSystemNone2[] = {
System,
""
};
static const char * const _prefixTilde2[] = {
Tilde,
Tilde
};
static const char * const * const prefixAllLibrariesDirectory[] = {
_prefixTilde2,
_prefixNone2,
_prefixNetwork2,
_prefixSystemNone2
};
static const char * const baseAllLibrariesDirectory[] = {
NSLibraryDirectoryBase,
NSDeveloperDirectoryBase
};
static struct {
int pathsPerDomain;
const void * const * const prefix;
const void * const base;
} dirInfo[] = {
{ 1,
(const void * const * const)prefixAll,
(const void * const)NSApplicationDirectoryBase
},
{ 1,
(const void * const * const)prefixAll,
(const void * const)NSDemoApplicationDirectoryBase
},
{ 1,
(const void * const * const)prefixAll,
(const void * const)NSDeveloperApplicationDirectoryBase
},
{ 1,
(const void * const * const)prefixAll,
(const void * const)NSAdminApplicationDirectoryBase
},
{ 1,
(const void * const * const)prefixAllSystem,
(const void * const)NSLibraryDirectoryBase
},
{ 1,
(const void * const * const)prefixAll,
(const void * const)NSDeveloperDirectoryBase
},
{ 1,
(const void * const * const)prefixNoUserSystem,
(const void * const)NSUserDirectoryBase
},
{ 1,
(const void * const * const)prefixAllSystem,
(const void * const)NSDocumentationDirectoryBase
},
{ 1,
(const void * const * const)prefixUserOnly,
(const void * const)NSDocumentDirectoryBase
},
{ 1,
(const void * const * const)prefixSystemOnly,
(const void * const)NSCoreServiceDirectoryBase
},
{ 1,
(const void * const * const)prefixUserOnly,
(const void * const)NSAutosavedDocumentsDirectoryBase
},
{ 1,
(const void * const * const)prefixUserOnly,
(const void * const)NSDesktopDirectoryBase
},
{ 1,
(const void * const * const)prefixAll,
(const void * const)NSCachesDirectoryBase
},
{ 1,
(const void * const * const)prefixAll,
(const void * const)NSApplicationSupportDirectoryBase
},
{ 1,
(const void * const * const)prefixUserOnly,
(const void * const)NSDownloadsDirectoryBase
},
{ 1,
(const void * const * const)prefixAll,
(const void * const)NSInputMethodsDirectoryBase
},
{ 1,
(const void * const * const)prefixUserOnly,
(const void * const)NSMoviesDirectoryBase
},
{ 1,
(const void * const * const)prefixUserOnly,
(const void * const)NSMusicDirectoryBase
},
{ 1,
(const void * const * const)prefixUserOnly,
(const void * const)NSPicturesDirectoryBase
},
{ 1,
(const void * const * const)prefixSystemOnly,
(const void * const)NSPrinterDescriptionDirectoryBase
},
{ 1,
(const void * const * const)prefixUserOnly,
(const void * const)NSSharedPublicDirectoryBase
},
{ 1,
(const void * const * const)prefixNoNetwork,
(const void * const)NSPreferencePanesDirectoryBase
},
{ 4,
(const void * const * const)prefixAllApplicationsDirectory,
(const void * const)baseAllApplicationsDirectory
},
{ 2,
(const void * const * const)prefixAllLibrariesDirectory,
(const void * const)baseAllLibrariesDirectory
}
};
#define Index(dir) (((dir) >= NSApplicationDirectory && (dir) <= NSPreferencePanesDirectory) ? ((dir) - 1) : (((dir) >= NSAllApplicationsDirectory && (dir) <= NSAllLibrariesDirectory) ? ((dir) - NSAllApplicationsDirectory + NSPreferencePanesDirectory) : -1))
#define invalidDomains 0x00 // some domains may be invalid on non-Mach systems
#define ByteMask 0xff
#define DirShift 24
#define IndexShift 16
NSSearchPathEnumerationState NSStartSearchPathEnumeration(NSSearchPathDirectory dir, NSSearchPathDomainMask domainMask) {
int i;
if((i = Index(dir)) < 0) {
return 0;
}
domainMask = domainMask & DomainMask & ~invalidDomains;
if ((domainMask & (NSLocalDomainMask | NSSystemDomainMask)) == (NSLocalDomainMask | NSSystemDomainMask) && dirInfo[i].prefix[NSLocalDomainIndex] == dirInfo[i].prefix[NSSystemDomainIndex]) {
domainMask &= ~NSSystemDomainMask;
}
return (dir << DirShift) + domainMask;
}
NSSearchPathEnumerationState NSGetNextSearchPathEnumeration(NSSearchPathEnumerationState state, char *path) {
static const char *nextRoot = NULL;
int dir = (state >> DirShift) & ByteMask;
int domainMask = state & DomainMask;
int domain, i, n;
const char *prefix, *base;
if ((i = Index(dir)) < 0 || (domain = ffs(domainMask)) == 0)
return 0;
domain--;
if ((n = dirInfo[i].pathsPerDomain) == 1) {
const char * const *p = (const char * const *)dirInfo[i].prefix;
for (;;) { domainMask &= ~(1 << domain);
if ((prefix = p[domain]) != NULL) {
break;
}
if ((domain = ffs(domainMask)) == 0) {
return 0;
}
domain--; }
base = (const char *)dirInfo[i].base;
state = (dir << DirShift) + domainMask;
} else { const char * const **p = (const char * const **)dirInfo[i].prefix;
const char * const *b = (const char * const *)dirInfo[i].base;
int dirIndex = (state >> IndexShift) & ByteMask;
if (dirIndex >= n) { domainMask &= ~(1 << domain);
if ((domain = ffs(domainMask)) == 0) {
return 0;
}
domain--; dirIndex = 0;
}
prefix = p[domain][dirIndex];
base = b[dirIndex];
state = (dir << DirShift) + (++dirIndex << IndexShift) + domainMask;
}
if (addNextRoot(prefix)) {
if (nextRoot == NULL) { if (!issetugid() && (nextRoot = getenv("NEXT_ROOT")) != NULL) {
nextRoot = strdup(nextRoot);
}
if (nextRoot == NULL) {
nextRoot = "";
}
}
strlcpy(path, nextRoot, PATH_MAX);
} else {
*path = 0;
}
strlcat(path, prefix, PATH_MAX);
strlcat(path, base, PATH_MAX);
return state;
}