@@ -1221,14 +1221,20 @@ CFArrayRef _CFXDGCreateDataDirectoriesPaths(void) {
1221
1221
// $XDG_DATA_DIRS defines the preference-ordered set of base directories to search for data files in addition to the $XDG_DATA_HOME base directory. The directories in $XDG_DATA_DIRS should be seperated with a colon ':'.
1222
1222
// If $XDG_DATA_DIRS is either not set or empty, a value equal to /usr/local/share/:/usr/share/ should be used.
1223
1223
const char * dataDirectoriesPaths = __CFgetenv ("XDG_DATA_DIRS" );
1224
+ CFStringRef defaultPath [2 ];
1225
+ defaultPath [0 ] = CFSTR ("/usr/local/share" );
1226
+ defaultPath [1 ] = CFSTR ("/usr/share" );
1224
1227
if ((dataDirectoriesPaths == NULL ) || (dataDirectoriesPaths [0 ] == '\0' )) {
1225
1228
// Environmental variable not set. Return default value.
1226
- CFStringRef defaultPath [2 ];
1227
- defaultPath [0 ] = CFStringCreateWithCString (kCFAllocatorSystemDefault , "/usr/local/share/" , _kCFXDGStringEncoding );
1228
- defaultPath [1 ] = CFStringCreateWithCString (kCFAllocatorSystemDefault , "/usr/share/" , _kCFXDGStringEncoding );
1229
1229
return CFArrayCreate (kCFAllocatorSystemDefault , (const void * * )defaultPath , 2 , & kCFTypeArrayCallBacks );
1230
1230
}
1231
- return _CFTokenizeStringToCFArrayOfCFStrings (dataDirectoriesPaths , ':' );
1231
+ CFArrayRef dataDirPathsArray = _CFCreateCFArrayByTokenizingString (dataDirectoriesPaths , ':' );
1232
+ if (CFArrayGetCount (dataDirPathsArray ) == 0 ) {
1233
+ CFStringRef logMessage = CFSTR ("Value set in XDG_DATA_DIRS variable not honoured. Returning the default." );
1234
+ CFLog (kCFLogLevelWarning , CFSTR ("%@" ), logMessage );
1235
+ return CFArrayCreate (kCFAllocatorSystemDefault , (const void * * )defaultPath , 2 , & kCFTypeArrayCallBacks );
1236
+ }
1237
+ return dataDirPathsArray ;
1232
1238
}
1233
1239
1234
1240
@@ -1238,13 +1244,19 @@ CFArrayRef _CFXDGCreateConfigDirectoriesPaths(void) {
1238
1244
// $XDG_CONFIG_DIRS defines the preference-ordered set of base directories to search for configuration files in addition to the $XDG_CONFIG_HOME base directory. The directories in $XDG_CONFIG_DIRS should be seperated with a colon ':'.
1239
1245
// If $XDG_CONFIG_DIRS is either not set or empty, a value equal to /etc/xdg should be used.
1240
1246
const char * configDirectoriesPaths = __CFgetenv ("XDG_CONFIG_DIRS" );
1247
+ CFStringRef defaultPath [1 ];
1248
+ defaultPath [0 ] = CFSTR ("/etc/xdg" );
1241
1249
if ((configDirectoriesPaths == NULL ) || (configDirectoriesPaths [0 ] == '\0' )) {
1242
1250
//Environmental variable not set. Return default value.
1243
- CFStringRef defaultPath [1 ];
1244
- defaultPath [0 ] = CFStringCreateWithCString (kCFAllocatorSystemDefault , "/etc/xdg" , _kCFXDGStringEncoding );
1245
1251
return CFArrayCreate (kCFAllocatorSystemDefault , (const void * * )defaultPath , 1 , & kCFTypeArrayCallBacks );
1246
1252
}
1247
- return _CFTokenizeStringToCFArrayOfCFStrings (configDirectoriesPaths , ':' );
1253
+ CFArrayRef configDirPathsArray = _CFCreateCFArrayByTokenizingString (configDirectoriesPaths , ':' );
1254
+ if (CFArrayGetCount (configDirPathsArray ) == 0 ) {
1255
+ CFStringRef logMessage = CFSTR ("Value set in XDG_CONFIG_DIRS variable not honoured. Returning the default." );
1256
+ CFLog (kCFLogLevelWarning , CFSTR ("%@" ), logMessage );
1257
+ return CFArrayCreate (kCFAllocatorSystemDefault , (const void * * )defaultPath , 1 , & kCFTypeArrayCallBacks );
1258
+ }
1259
+ return configDirPathsArray ;
1248
1260
}
1249
1261
1250
1262
/// a single base directory relative to which user-specific non-essential (cached) data should be written. This directory is defined by the environment variable $XDG_CACHE_HOME.
@@ -1276,7 +1288,7 @@ CFStringRef _CFXDGCreateRuntimeDirectoryPath(void) {
1276
1288
}
1277
1289
1278
1290
1279
- CF_PRIVATE CFArrayRef _CFTokenizeStringToCFArrayOfCFStrings (const char * values , char delimiter ) {
1291
+ CF_PRIVATE CFArrayRef _CFCreateCFArrayByTokenizingString (const char * values , char delimiter ) {
1280
1292
size_t pathCount = 0 ;
1281
1293
char * tmpDirectoriesPaths = (char * )values ;
1282
1294
char * last_colon = 0 ;
@@ -1292,6 +1304,9 @@ CF_PRIVATE CFArrayRef _CFTokenizeStringToCFArrayOfCFStrings(const char *values,
1292
1304
}
1293
1305
// Add count for trailing path unless ending with colon.
1294
1306
pathCount += last_colon < (values + strlen (values ) - 1 );
1307
+ if (pathCount > 64 ) {
1308
+ return CFArrayCreate (kCFAllocatorSystemDefault , NULL , 0 , & kCFTypeArrayCallBacks );
1309
+ }
1295
1310
if (pathCount > 0 )
1296
1311
{
1297
1312
size_t validPathCount = 0 ;
@@ -1304,16 +1319,25 @@ CF_PRIVATE CFArrayRef _CFTokenizeStringToCFArrayOfCFStrings(const char *values,
1304
1319
while (path )
1305
1320
{
1306
1321
assert (validPathCount < pathCount );
1307
- CFStringRef dirPath = CFStringCreateWithCString (kCFAllocatorSystemDefault , strdup (path ), _kCFXDGStringEncoding );
1322
+ char * pathString = strdup (path );
1323
+ CFStringRef dirPath = CFStringCreateWithCString (kCFAllocatorSystemDefault , pathString , _kCFXDGStringEncoding );
1308
1324
CFStringRef slash = CFSTR ("/" );
1309
1325
CFStringRef tilde = CFSTR ("~" );
1310
1326
// Check for absolutePath, if not ignore.
1311
1327
if (CFStringHasPrefix (dirPath , slash ) || CFStringHasPrefix (dirPath , tilde ) ) {
1312
1328
pathList [validPathCount ++ ] = dirPath ;
1329
+ } else {
1330
+ CFRelease (dirPath );
1313
1331
}
1314
- path = strtok (0 , delimiterStr );
1332
+ path = strtok (NULL , delimiterStr );
1333
+ free (pathString );
1334
+ }
1335
+ free (copyDirPath );
1336
+ CFArrayRef pathArray = CFArrayCreate (kCFAllocatorSystemDefault , (const void * * )pathList , validPathCount , & kCFTypeArrayCallBacks );
1337
+ for (int i = 0 ; i < validPathCount ; i ++ ) {
1338
+ CFRelease (pathList [i ]);
1315
1339
}
1316
- return CFArrayCreate ( kCFAllocatorSystemDefault , ( const void * * ) pathList , validPathCount , & kCFTypeArrayCallBacks ) ;
1340
+ return pathArray ;
1317
1341
}
1318
1342
return CFArrayCreate (kCFAllocatorSystemDefault , NULL , 0 , & kCFTypeArrayCallBacks );
1319
1343
}
0 commit comments