+++ /dev/null
-//
-// CFGrowlAdditions.c
-// Growl
-//
-// Created by Mac-arena the Bored Zo on Wed Jun 18 2004.
-// Copyright 2005-2006 The Growl Project.
-//
-// This file is under the BSD License, refer to License.txt for details
-
-#include <Carbon/Carbon.h>
-#include <unistd.h>
-#include <netinet/in.h>
-#include <arpa/inet.h>
-#include <netdb.h>
-#include "CFGrowlAdditions.h"
-
-#ifndef MIN
-# define MIN(a,b) ((a) < (b) ? (a) : (b))
-#endif
-
-//extern Boolean CFStringGetFileSystemRepresentation(CFStringRef str) __attribute__((weak_import));
-extern CFIndex CFStringGetMaximumSizeOfFileSystemRepresentation(CFStringRef string) __attribute__((weak_import));
-
-char *createFileSystemRepresentationOfString(CFStringRef str) {
- char *buffer;
-#if MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_4
- /* CFStringGetFileSystemRepresentation will cause a link error despite the weak_import attribute above on 10.5 when compiling with 10.2 compatibility using gcc 3.3.
- * PPC will therefore always use the 10.3 and below method of creating a file system representation.
- */
- if (1/*CFStringGetFileSystemRepresentation*/) {
- CFIndex size = CFStringGetMaximumSizeOfFileSystemRepresentation(str);
- buffer = malloc(size);
- CFStringGetFileSystemRepresentation(str, buffer, size);
- } else
-#endif
- {
- buffer = malloc(512);
- CFURLRef url = CFURLCreateWithFileSystemPath(kCFAllocatorDefault, str, kCFURLPOSIXPathStyle, false);
- if (!CFURLGetFileSystemRepresentation(url, false, (UInt8 *)buffer, 512)) {
- free(buffer);
- buffer = NULL;
- }
- CFRelease(url);
- }
- return buffer;
-}
-
-STRING_TYPE createStringWithDate(CFDateRef date) {
- CFLocaleRef locale = CFLocaleCopyCurrent();
- CFDateFormatterRef dateFormatter = CFDateFormatterCreate(kCFAllocatorDefault,
- locale,
- kCFDateFormatterMediumStyle,
- kCFDateFormatterMediumStyle);
- CFRelease(locale);
- CFStringRef dateString = CFDateFormatterCreateStringWithDate(kCFAllocatorDefault,
- dateFormatter,
- date);
- CFRelease(dateFormatter);
- return dateString;
-}
-
-STRING_TYPE createStringWithContentsOfFile(CFStringRef filename, CFStringEncoding encoding) {
- CFStringRef str = NULL;
-
- char *path = createFileSystemRepresentationOfString(filename);
- if (path) {
- FILE *fp = fopen(path, "rb");
- if (fp) {
- fseek(fp, 0, SEEK_END);
- unsigned long size = ftell(fp);
- fseek(fp, 0, SEEK_SET);
- unsigned char *buffer = malloc(size);
- if (buffer && fread(buffer, 1, size, fp) == size)
- str = CFStringCreateWithBytes(kCFAllocatorDefault, buffer, size, encoding, true);
- fclose(fp);
- }
- free(path);
- }
-
- return str;
-}
-
-STRING_TYPE createStringWithStringAndCharacterAndString(STRING_TYPE str0, UniChar ch, STRING_TYPE str1) {
- CFStringRef cfstr0 = (CFStringRef)str0;
- CFStringRef cfstr1 = (CFStringRef)str1;
- CFIndex len0 = (cfstr0 ? CFStringGetLength(cfstr0) : 0);
- CFIndex len1 = (cfstr1 ? CFStringGetLength(cfstr1) : 0);
- size_t length = (len0 + (ch != 0xffff) + len1);
-
- UniChar *buf = malloc(sizeof(UniChar) * length);
- size_t i = 0U;
-
- if (cfstr0) {
- CFStringGetCharacters(cfstr0, CFRangeMake(0, len0), buf);
- i += len0;
- }
- if (ch != 0xffff)
- buf[i++] = ch;
- if (cfstr1)
- CFStringGetCharacters(cfstr1, CFRangeMake(0, len1), &buf[i]);
-
- return CFStringCreateWithCharactersNoCopy(kCFAllocatorDefault, buf, length, /*contentsDeallocator*/ kCFAllocatorMalloc);
-}
-
-char *copyCString(STRING_TYPE str, CFStringEncoding encoding) {
- CFIndex size = CFStringGetMaximumSizeForEncoding(CFStringGetLength(str), encoding) + 1;
- char *buffer = calloc(size, 1);
- CFStringGetCString(str, buffer, size, encoding);
- return buffer;
-}
-
-STRING_TYPE copyCurrentProcessName(void) {
- ProcessSerialNumber PSN = { 0, kCurrentProcess };
- CFStringRef name = NULL;
- OSStatus err = CopyProcessName(&PSN, &name);
- if (err != noErr) {
- NSLog(CFSTR("in copyCurrentProcessName in CFGrowlAdditions: Could not get process name because CopyProcessName returned %li"), (long)err);
- name = NULL;
- }
- return name;
-}
-
-URL_TYPE copyCurrentProcessURL(void) {
- ProcessSerialNumber psn = { 0, kCurrentProcess };
- FSRef fsref;
- CFURLRef URL = NULL;
- OSStatus err = GetProcessBundleLocation(&psn, &fsref);
- if (err != noErr) {
- NSLog(CFSTR("in copyCurrentProcessURL in CFGrowlAdditions: Could not get application location, because GetProcessBundleLocation returned %li\n"), (long)err);
- } else {
- URL = CFURLCreateFromFSRef(kCFAllocatorDefault, &fsref);
- }
- return URL;
-}
-STRING_TYPE copyCurrentProcessPath(void) {
- CFURLRef URL = copyCurrentProcessURL();
- CFStringRef path = CFURLCopyFileSystemPath(URL, kCFURLPOSIXPathStyle);
- CFRelease(URL);
- return path;
-}
-
-URL_TYPE copyTemporaryFolderURL(void) {
- FSRef ref;
- CFURLRef url = NULL;
-
- OSStatus err = FSFindFolder(kOnAppropriateDisk, kTemporaryFolderType, kCreateFolder, &ref);
- if (err != noErr)
- NSLog(CFSTR("in copyTemporaryFolderPath in CFGrowlAdditions: Could not locate temporary folder because FSFindFolder returned %li"), (long)err);
- else
- url = CFURLCreateFromFSRef(kCFAllocatorDefault, &ref);
-
- return url;
-}
-STRING_TYPE copyTemporaryFolderPath(void) {
- CFStringRef path = NULL;
-
- CFURLRef url = copyTemporaryFolderURL();
- if (url) {
- path = CFURLCopyFileSystemPath(url, kCFURLPOSIXPathStyle);
- CFRelease(url);
- }
-
- return path;
-}
-
-DATA_TYPE readFile(const char *filename)
-{
- CFDataRef data;
- // read the file into a CFDataRef
- FILE *fp = fopen(filename, "r");
- if (fp) {
- fseek(fp, 0, SEEK_END);
- long dataLength = ftell(fp);
- fseek(fp, 0, SEEK_SET);
- unsigned char *fileData = malloc(dataLength);
- fread(fileData, 1, dataLength, fp);
- fclose(fp);
- data = CFDataCreateWithBytesNoCopy(kCFAllocatorDefault, fileData, dataLength, kCFAllocatorMalloc);
- } else
- data = NULL;
-
- return data;
-}
-
-URL_TYPE copyURLForApplication(STRING_TYPE appName)
-{
- CFURLRef appURL = NULL;
- OSStatus err = LSFindApplicationForInfo(/*inCreator*/ kLSUnknownCreator,
- /*inBundleID*/ NULL,
- /*inName*/ appName,
- /*outAppRef*/ NULL,
- /*outAppURL*/ &appURL);
- return (err == noErr) ? appURL : NULL;
-}
-
-STRING_TYPE createStringWithAddressData(DATA_TYPE aAddressData) {
- struct sockaddr *socketAddress = (struct sockaddr *)CFDataGetBytePtr(aAddressData);
- // IPv6 Addresses are "FFFF:FFFF:FFFF:FFFF:FFFF:FFFF:FFFF:FFFF"
- // at max, which is 40 bytes (0-terminated)
- // IPv4 Addresses are "255.255.255.255" at max which is smaller
- char stringBuffer[40];
- CFStringRef addressAsString = NULL;
- if (socketAddress->sa_family == AF_INET) {
- struct sockaddr_in *ipv4 = (struct sockaddr_in *)socketAddress;
- if (inet_ntop(AF_INET, &(ipv4->sin_addr), stringBuffer, 40))
- addressAsString = CFStringCreateWithFormat(kCFAllocatorDefault, NULL, CFSTR("%s:%d"), stringBuffer, ipv4->sin_port);
- else
- addressAsString = CFSTR("IPv4 un-ntopable");
- } else if (socketAddress->sa_family == AF_INET6) {
- struct sockaddr_in6 *ipv6 = (struct sockaddr_in6 *)socketAddress;
- if (inet_ntop(AF_INET6, &(ipv6->sin6_addr), stringBuffer, 40))
- // Suggested IPv6 format (see http://www.faqs.org/rfcs/rfc2732.html)
- addressAsString = CFStringCreateWithFormat(kCFAllocatorDefault, NULL, CFSTR("[%s]:%d"), stringBuffer, ipv6->sin6_port);
- else
- addressAsString = CFSTR("IPv6 un-ntopable");
- } else
- addressAsString = CFSTR("neither IPv6 nor IPv4");
-
- return addressAsString;
-}
-
-STRING_TYPE createHostNameForAddressData(DATA_TYPE aAddressData) {
- char hostname[NI_MAXHOST];
- struct sockaddr *socketAddress = (struct sockaddr *)CFDataGetBytePtr(aAddressData);
- if (getnameinfo(socketAddress, (socklen_t)CFDataGetLength(aAddressData),
- hostname, (socklen_t)sizeof(hostname),
- /*serv*/ NULL, /*servlen*/ 0,
- NI_NAMEREQD))
- return NULL;
- else
- return CFStringCreateWithCString(kCFAllocatorDefault, hostname, kCFStringEncodingASCII);
-}
-
-DATA_TYPE copyIconDataForPath(STRING_TYPE path) {
- CFDataRef data = NULL;
-
- //false is probably safest, and is harmless when the object really is a directory.
- CFURLRef URL = CFURLCreateWithFileSystemPath(kCFAllocatorDefault, path, kCFURLPOSIXPathStyle, /*isDirectory*/ false);
- if (URL) {
- data = copyIconDataForURL(URL);
- CFRelease(URL);
- }
-
- return data;
-}
-
-DATA_TYPE copyIconDataForURL(URL_TYPE URL)
-{
- CFDataRef data = NULL;
-
- if (URL) {
- FSRef ref;
- if (CFURLGetFSRef(URL, &ref)) {
- IconRef icon = NULL;
- SInt16 label_noOneCares;
- OSStatus err = GetIconRefFromFileInfo(&ref,
- /*inFileNameLength*/ 0U, /*inFileName*/ NULL,
- kFSCatInfoNone, /*inCatalogInfo*/ NULL,
- kIconServicesNoBadgeFlag | kIconServicesUpdateIfNeededFlag,
- &icon,
- &label_noOneCares);
- if (err != noErr) {
- NSLog(CFSTR("in copyIconDataForURL in CFGrowlAdditions: could not get icon for %@: GetIconRefFromFileInfo returned %li\n"), URL, (long)err);
- } else {
- IconFamilyHandle fam = NULL;
- err = IconRefToIconFamily(icon, kSelectorAllAvailableData, &fam);
- if (err != noErr) {
- NSLog(CFSTR("in copyIconDataForURL in CFGrowlAdditions: could not get icon for %@: IconRefToIconFamily returned %li\n"), URL, (long)err);
- } else {
- HLock((Handle)fam);
- data = CFDataCreate(kCFAllocatorDefault, (const UInt8 *)*(Handle)fam, GetHandleSize((Handle)fam));
- HUnlock((Handle)fam);
- DisposeHandle((Handle)fam);
- }
- ReleaseIconRef(icon);
- }
- }
- }
-
- return data;
-}
-
-URL_TYPE createURLByMakingDirectoryAtURLWithName(URL_TYPE parent, STRING_TYPE name)
-{
- CFURLRef newDirectory = NULL;
-
- CFAllocatorRef allocator = parent ? CFGetAllocator(parent) : name ? CFGetAllocator(name) : kCFAllocatorDefault;
-
- if (parent) parent = CFRetain(parent);
- else {
- char *cwdBytes = alloca(PATH_MAX);
- getcwd(cwdBytes, PATH_MAX);
- parent = CFURLCreateFromFileSystemRepresentation(allocator, (const unsigned char *)cwdBytes, strlen(cwdBytes), /*isDirectory*/ true);
- if (!name) {
- newDirectory = parent;
- goto end;
- }
- }
- if (!parent)
- NSLog(CFSTR("in createURLByMakingDirectoryAtURLWithName in CFGrowlAdditions: parent directory URL is NULL (please tell the Growl developers)\n"), parent);
- else {
- if (name)
- name = CFRetain(name);
- else {
- name = CFURLCopyLastPathComponent(parent);
- CFURLRef newParent = CFURLCreateCopyDeletingLastPathComponent(allocator, parent);
- CFRelease(parent);
- parent = newParent;
- }
-
- if (!name)
- NSLog(CFSTR("in createURLByMakingDirectoryAtURLWithName in CFGrowlAdditions: name of directory to create is NULL (please tell the Growl developers)\n"), parent);
- else {
- FSRef parentRef;
- if (!CFURLGetFSRef(parent, &parentRef))
- NSLog(CFSTR("in createURLByMakingDirectoryAtURLWithName in CFGrowlAdditions: could not create FSRef for parent directory at %@ (please tell the Growl developers)\n"), parent);
- else {
- FSRef newDirectoryRef;
-
- struct HFSUniStr255 nameUnicode;
- CFRange range = { 0, MIN(CFStringGetLength(name), USHRT_MAX) };
- CFStringGetCharacters(name, range, nameUnicode.unicode);
- nameUnicode.length = range.length;
-
- struct FSRefParam refPB = {
- .ref = &parentRef,
- .nameLength = nameUnicode.length,
- .name = nameUnicode.unicode,
- .whichInfo = kFSCatInfoNone,
- .catInfo = NULL,
- .textEncodingHint = kTextEncodingUnknown,
- .newRef = &newDirectoryRef,
- };
-
- OSStatus err = PBCreateDirectoryUnicodeSync(&refPB);
- if (err == dupFNErr) {
- //dupFNErr == file (or folder) exists already. this is fine.
- err = PBMakeFSRefUnicodeSync(&refPB);
- }
- if (err == noErr) {
- NSLog(CFSTR("PBCreateDirectoryUnicodeSync or PBMakeFSRefUnicodeSync returned %li; calling CFURLCreateFromFSRef"), (long)err); //XXX
- newDirectory = CFURLCreateFromFSRef(allocator, &newDirectoryRef);
- NSLog(CFSTR("CFURLCreateFromFSRef returned %@"), newDirectory); //XXX
- } else
- NSLog(CFSTR("in createURLByMakingDirectoryAtURLWithName in CFGrowlAdditions: could not create directory '%@' in parent directory at %@: FSCreateDirectoryUnicode returned %li (please tell the Growl developers)"), name, parent, (long)err);
- }
-
- } //if (name)
- if(parent)
- CFRelease(parent);
- if(name)
- CFRelease(name);
- } //if (parent)
-
-end:
- return newDirectory;
-}
-
-#ifndef COPYFORK_BUFSIZE
-# define COPYFORK_BUFSIZE 5242880U /*5 MiB*/
-#endif
-
-static OSStatus copyFork(const struct HFSUniStr255 *forkName, const FSRef *srcFile, const FSRef *destDir, const struct HFSUniStr255 *destName, FSRef *outDestFile) {
- OSStatus err, closeErr;
- struct FSForkIOParam srcPB = {
- .ref = srcFile,
- .forkNameLength = forkName->length,
- .forkName = forkName->unicode,
- .permissions = fsRdPerm,
- };
- unsigned char debuggingPathBuf[PATH_MAX] = "";
- OSStatus debuggingPathErr;
-
- err = PBOpenForkSync(&srcPB);
- if (err != noErr) {
- debuggingPathErr = FSRefMakePath(srcFile, debuggingPathBuf, PATH_MAX);
- if (debuggingPathErr != noErr)
- snprintf((char *)debuggingPathBuf, PATH_MAX, "(could not get path for source file: FSRefMakePath returned %li)", (long)debuggingPathErr);
- NSLog(CFSTR("in copyFork in CFGrowlAdditions: PBOpenForkSync (source: %s) returned %li"), debuggingPathBuf, (long)err);
- } else {
- FSRef destFile;
-
- /*the first thing to do is get the name of the destination file, if one
- * wasn't provided.
- *and while we're at it, we get the catalogue info as well.
- */
- struct FSCatalogInfo catInfo;
- struct FSRefParam refPB = {
- .ref = srcFile,
- .whichInfo = kFSCatInfoGettableInfo & kFSCatInfoSettableInfo,
- .catInfo = &catInfo,
- .spec = NULL,
- .parentRef = NULL,
- .outName = destName ? NULL : (struct HFSUniStr255 *)(destName = alloca(sizeof(struct HFSUniStr255))),
- };
-
- err = PBGetCatalogInfoSync(&refPB);
- if (err != noErr) {
- debuggingPathErr = FSRefMakePath(srcFile, debuggingPathBuf, PATH_MAX);
- if (debuggingPathErr != noErr)
- snprintf((char *)debuggingPathBuf, PATH_MAX, "(could not get path for source file: FSRefMakePath returned %li)", (long)debuggingPathErr);
- NSLog(CFSTR("in copyFork in CFGrowlAdditions: PBGetCatalogInfoSync (source: %s) returned %li"), debuggingPathBuf, (long)err);
- } else {
- refPB.ref = destDir;
- refPB.nameLength = destName->length;
- refPB.name = destName->unicode;
- refPB.textEncodingHint = kTextEncodingUnknown;
- refPB.newRef = &destFile;
-
- const char *functionName = "PBMakeFSRefUnicodeSync"; //for error-reporting message
-
- err = PBMakeFSRefUnicodeSync(&refPB);
- if ((err != noErr) && (err != fnfErr)) {
- handleMakeFSRefError:
- debuggingPathErr = FSRefMakePath(destDir, debuggingPathBuf, PATH_MAX);
- if (debuggingPathErr != noErr)
- snprintf((char *)debuggingPathBuf, PATH_MAX, "(could not get path for destination directory: FSRefMakePath returned %li)", (long)debuggingPathErr);
-
- //get filename too
- CFStringRef debuggingFilename = CFStringCreateWithCharactersNoCopy(kCFAllocatorDefault,
- destName->unicode,
- destName->length,
- /*contentsDeallocator*/ kCFAllocatorNull);
- if (!debuggingFilename)
- debuggingFilename = CFStringCreateWithCStringNoCopy(kCFAllocatorDefault, "(could not get filename for destination file: CFStringCreateWithCharactersNoCopy returned NULL)", kCFStringEncodingASCII, /*contentsDeallocator*/ kCFAllocatorNull);
-
- NSLog(CFSTR("in copyFork in CFGrowlAdditions: %s (destination: %s/%@) returned %li"), functionName, debuggingPathBuf, debuggingFilename, (long)err);
-
- if (debuggingFilename) CFRelease(debuggingFilename);
- } else {
- //that file doesn't exist in that folder; create it.
- err = PBCreateFileUnicodeSync(&refPB);
- if (err == noErr) {
- /*make sure the Finder knows about the new file.
- *FNNotify returns a status code too, but this isn't an
- * essential step, so we just ignore it.
- */
- FNNotify(destDir, kFNDirectoryModifiedMessage, kNilOptions);
- } else if (err == dupFNErr) {
- /*dupFNErr: the file already exists.
- *we can safely ignore this error.
- */
- err = noErr;
- } else {
- functionName = "PBCreateFileUnicodeSync";
- goto handleMakeFSRefError;
- }
- }
- }
- if (err == noErr) {
- if (outDestFile)
- memcpy(outDestFile, &destFile, sizeof(destFile));
-
- struct FSForkIOParam destPB = {
- .ref = &destFile,
- .forkNameLength = forkName->length,
- .forkName = forkName->unicode,
- .permissions = fsWrPerm,
- };
- err = PBOpenForkSync(&destPB);
- NSLog(CFSTR("in copyFork in CFGrowlAdditions: PBOpenForkSync (dest) returned %li"), (long)err);
- if (err != noErr) {
- debuggingPathErr = FSRefMakePath(&destFile, debuggingPathBuf, PATH_MAX);
- if (debuggingPathErr != noErr)
- snprintf((char *)debuggingPathBuf, PATH_MAX, "(could not get path for dest file: FSRefMakePath returned %li)", (long)debuggingPathErr);
- NSLog(CFSTR("in copyFork in CFGrowlAdditions: PBOpenForkSync (destination: %s) returned %li"), debuggingPathBuf, (long)err);
- } else {
- void *buf = malloc(COPYFORK_BUFSIZE);
- if (buf) {
- srcPB.buffer = destPB.buffer = buf;
- srcPB.requestCount = COPYFORK_BUFSIZE;
- while (err == noErr) {
- err = PBReadForkSync(&srcPB);
- if (err == eofErr) {
- err = noErr;
- if (srcPB.actualCount == 0)
- break;
- }
- if (err != noErr) {
- debuggingPathErr = FSRefMakePath(&destFile, debuggingPathBuf, PATH_MAX);
- if (debuggingPathErr != noErr)
- snprintf((char *)debuggingPathBuf, PATH_MAX, "(could not get path for source file: FSRefMakePath returned %li)", (long)debuggingPathErr);
- NSLog(CFSTR("in copyFork in CFGrowlAdditions: PBReadForkSync (source: %s) returned %li"), debuggingPathBuf, (long)err);
- } else {
- destPB.requestCount = srcPB.actualCount;
- err = PBWriteForkSync(&destPB);
- if (err != noErr) {
- debuggingPathErr = FSRefMakePath(&destFile, debuggingPathBuf, PATH_MAX);
- if (debuggingPathErr != noErr)
- snprintf((char *)debuggingPathBuf, PATH_MAX, "(could not get path for dest file: FSRefMakePath returned %li)", (long)debuggingPathErr);
- NSLog(CFSTR("in copyFork in CFGrowlAdditions: PBWriteForkSync (destination: %s) returned %li"), debuggingPathBuf, (long)err);
- }
- }
- }
-
- free(buf);
- }
-
- closeErr = PBCloseForkSync(&destPB);
- if (closeErr != noErr) {
- debuggingPathErr = FSRefMakePath(&destFile, debuggingPathBuf, PATH_MAX);
- if (debuggingPathErr != noErr)
- snprintf((char *)debuggingPathBuf, PATH_MAX, "(could not get path for dest file: FSRefMakePath returned %li)", (long)debuggingPathErr);
- NSLog(CFSTR("in copyFork in CFGrowlAdditions: PBCloseForkSync (destination: %s) returned %li"), debuggingPathBuf, (long)err);
- }
- if (err == noErr) err = closeErr;
- }
- }
-
- closeErr = PBCloseForkSync(&srcPB);
- if (closeErr != noErr) {
- debuggingPathErr = FSRefMakePath(&destFile, debuggingPathBuf, PATH_MAX);
- if (debuggingPathErr != noErr)
- snprintf((char *)debuggingPathBuf, PATH_MAX, "(could not get path for source file: FSRefMakePath returned %li)", (long)debuggingPathErr);
- NSLog(CFSTR("in copyFork in CFGrowlAdditions: PBCloseForkSync (source: %s) returned %li"), debuggingPathBuf, (long)err);
- }
- if (err == noErr) err = closeErr;
- }
-
- return err;
-}
-
-static OSStatus GrowlCopyObjectSync(const FSRef *fileRef, const FSRef *destRef, FSRef *destFileRef) {
- OSStatus err;
- struct HFSUniStr255 forkName;
- struct FSForkIOParam forkPB = {
- .ref = fileRef,
- .forkIterator = {
- .initialize = 0
- },
- .outForkName = &forkName,
- };
-
- do {
- err = PBIterateForksSync(&forkPB);
- NSLog(CFSTR("PBIterateForksSync returned %li"), (long)err);
- if (err != noErr) {
- if (err != errFSNoMoreItems)
- NSLog(CFSTR("in GrowlCopyObjectSync in CFGrowlAdditions: PBIterateForksSync returned %li"), (long)err);
- } else {
- err = copyFork(&forkName, fileRef, destRef, /*destName*/ NULL, /*outDestFile*/ destFileRef);
- //copyFork prints its own error messages
- }
- } while (err == noErr);
- if (err == errFSNoMoreItems) err = noErr;
-
- return err;
-}
-
-URL_TYPE createURLByCopyingFileFromURLToDirectoryURL(URL_TYPE file, URL_TYPE dest)
-{
- CFURLRef destFileURL = NULL;
-
- FSRef fileRef, destRef, destFileRef;
- Boolean gotFileRef = CFURLGetFSRef(file, &fileRef);
- Boolean gotDestRef = CFURLGetFSRef(dest, &destRef);
- if (!gotFileRef)
- NSLog(CFSTR("in createURLByCopyingFileFromURLToDirectoryURL in CFGrowlAdditions: CFURLGetFSRef failed with source URL %@"), file);
- else if (!gotDestRef)
- NSLog(CFSTR("in createURLByCopyingFileFromURLToDirectoryURL in CFGrowlAdditions: CFURLGetFSRef failed with destination URL %@"), dest);
- else {
- OSStatus err;
-
- /*
- * 10.2 has a problem with weak symbols in frameworks so we use
- * MAC_OS_X_VERSION_MIN_REQUIRED >= 10.3.
- */
-#if defined(NSAppKitVersionNumber10_3) && MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_4 && MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_3
- if (FSCopyObjectSync) {
- err = FSCopyObjectSync(&fileRef, &destRef, /*destName*/ NULL, &destFileRef, kFSFileOperationOverwrite);
- } else {
-#endif
- err = GrowlCopyObjectSync(&fileRef, &destRef, &destFileRef);
-#if defined(NSAppKitVersionNumber10_3) && MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_4 && MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_3
- }
-#endif
-
- if (err == noErr)
- destFileURL = CFURLCreateFromFSRef(kCFAllocatorDefault, &destFileRef);
- else
- NSLog(CFSTR("in createURLByCopyingFileFromURLToDirectoryURL in CFGrowlAdditions: CopyObjectSync returned %li for source URL %@"), (long)err, file);
- }
-
- return destFileURL;
-}
-
-PLIST_TYPE createPropertyListFromURL(URL_TYPE file, u_int32_t mutability, CFPropertyListFormat *outFormat, STRING_TYPE *outErrorString)
-{
- CFPropertyListRef plist = NULL;
-
- if (!file)
- NSLog(CFSTR("in createPropertyListFromURL in CFGrowlAdditions: cannot read from a NULL URL"));
- else {
- CFReadStreamRef stream = CFReadStreamCreateWithFile(kCFAllocatorDefault, file);
- if (!stream)
- NSLog(CFSTR("in createPropertyListFromURL in CFGrowlAdditions: could not create stream for reading from URL %@"), file);
- else {
- if (!CFReadStreamOpen(stream))
- NSLog(CFSTR("in createPropertyListFromURL in CFGrowlAdditions: could not open stream for reading from URL %@"), file);
- else {
- CFPropertyListFormat format;
- CFStringRef errorString = NULL;
-
- plist = CFPropertyListCreateFromStream(kCFAllocatorDefault,
- stream,
- /*streamLength*/ 0,
- mutability,
- &format,
- &errorString);
- if (!plist)
- NSLog(CFSTR("in createPropertyListFromURL in CFGrowlAdditions: could not read property list from URL %@ (error string: %@)"), file, errorString);
-
- if (outFormat) *outFormat = format;
- if (errorString) {
- if (outErrorString)
- *outErrorString = errorString;
- else
- CFRelease(errorString);
- }
-
- CFReadStreamClose(stream);
- }
-
- CFRelease(stream);
- }
- }
-
- return plist;
-}