plconvert.c
1 // Mac OS X: clang -F<path-to-CFLite-framework> -framework CoreFoundation Examples/plconvert.c -o plconvert 2 // note: When running this sample, be sure to set the environment variable DYLD_FRAMEWORK_PATH to point to the directory containing your new version of CoreFoundation. 3 // e.g. 4 // DYLD_FRAMEWORK_PATH=/tmp/CF-Root ./plconvert <input> <output> 5 // 6 // Linux: clang -I/usr/local/include -L/usr/local/lib -lCoreFoundation plconvert.c -o plconvert 7 8 /* 9 This example shows usage of CFString, CFData, and other CFPropertyList types. It takes two arguments: 10 1. A property list file to read, in either binary or XML property list format. 11 2. A file name to write a converted property list file to. 12 If the first input is binary, the output is XML and vice-versa. 13 */ 14 15 #include <sys/types.h> 16 #include <sys/stat.h> 17 #include <fcntl.h> 18 #include <string.h> 19 #include <stdio.h> 20 #include <unistd.h> 21 22 #include <CoreFoundation/CoreFoundation.h> 23 24 static void logIt(CFStringRef format, ...) { 25 va_list args; 26 va_start(args, format); 27 CFStringRef str = CFStringCreateWithFormatAndArguments(kCFAllocatorSystemDefault, NULL, format, args); 28 if (!str) return; 29 30 CFIndex blen = CFStringGetMaximumSizeForEncoding(CFStringGetLength(str), kCFStringEncodingUTF8); 31 char *buf = str ? (char *)malloc(blen + 1) : 0; 32 if (buf) { 33 Boolean converted = CFStringGetCString(str, buf, blen, kCFStringEncodingUTF8); 34 if (converted) { 35 // null-terminate 36 buf[blen] = 0; 37 printf("%s\n", buf); 38 } 39 } 40 if (buf) free(buf); 41 if (str) CFRelease(str); va_end(args); 42 } 43 44 static CFMutableDataRef createDataFromFile(const char *fname) { 45 int fd = open(fname, O_RDONLY); 46 CFMutableDataRef res = CFDataCreateMutable(kCFAllocatorSystemDefault, 0); 47 char buf[4096]; 48 49 ssize_t amountRead; 50 while ((amountRead = read(fd, buf, 4096)) > 0) { 51 CFDataAppendBytes(res, (const UInt8 *)buf, amountRead); 52 } 53 54 close(fd); 55 return res; 56 } 57 58 static bool writeDataToFile(CFDataRef data, const char *fname) { 59 int fd = open(fname, O_WRONLY | O_CREAT | O_TRUNC, 0666); 60 if (fd < 0) { 61 printf("There was an error creating the file: %d", errno); 62 return false; 63 } 64 int dataLen = CFDataGetLength(data); 65 int w = write(fd, CFDataGetBytePtr(data), dataLen); 66 fsync(fd); 67 close(fd); 68 if (w != dataLen) return false; 69 return true; 70 } 71 72 int main(int argc, char **argv) { 73 74 if (argc != 3) { 75 printf("Usage: plconvert <in file> <out file>\nIf the in file is an XML property list, convert to binary property list in out file. If the in file is a binary property list, convert to XML property list in out file.\n"); 76 } else { 77 CFMutableDataRef plistData = createDataFromFile(argv[1]); 78 if (!plistData) { 79 printf("Unable to create data from file name: %s", argv[1]); 80 } else { 81 CFPropertyListFormat fmt; 82 CFErrorRef err; 83 CFPropertyListRef plist = CFPropertyListCreateWithData(kCFAllocatorSystemDefault, (CFDataRef)plistData, 0, &fmt, &err); 84 if (!plist) { 85 logIt(CFSTR("Unable to create property list from data: %@"), err); 86 } else { 87 logIt(CFSTR("Property list contents:\n%@"), plist); 88 if (fmt == kCFPropertyListBinaryFormat_v1_0) { 89 logIt(CFSTR("Converting to XML property list at: %s"), argv[2]); 90 fmt = kCFPropertyListXMLFormat_v1_0; 91 } else if (fmt == kCFPropertyListXMLFormat_v1_0) { 92 logIt(CFSTR("Converting to binary property list at: %s"), argv[2]); 93 fmt = kCFPropertyListBinaryFormat_v1_0; 94 } else { 95 logIt(CFSTR("Unknown property list format! Not converting output format.")); 96 } 97 98 CFDataRef outputData = CFPropertyListCreateData(kCFAllocatorSystemDefault, plist, fmt, 0, &err); 99 if (!outputData) { 100 logIt(CFSTR("Unable to write property list to data: %@"), err); 101 } else { 102 bool success = writeDataToFile(outputData, argv[2]); 103 if (!success) { 104 logIt(CFSTR("Unable to write data to file")); 105 } 106 CFRelease(outputData); 107 } 108 CFRelease(plist); 109 } 110 CFRelease(plistData); 111 } 112 } 113 }