1/* 2 * Copyright (c) 2011,2014 Apple Inc. All Rights Reserved. 3 * 4 * @APPLE_LICENSE_HEADER_START@ 5 * 6 * This file contains Original Code and/or Modifications of Original Code 7 * as defined in and that are subject to the Apple Public Source License 8 * Version 2.0 (the 'License'). You may not use this file except in 9 * compliance with the License. Please obtain a copy of the License at 10 * http://www.opensource.apple.com/apsl/ and read it before using this 11 * file. 12 * 13 * The Original Code and all software distributed under the License are 14 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER 15 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES, 16 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY, 17 * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT. 18 * Please see the License for the specific language governing rights and 19 * limitations under the License. 20 * 21 * @APPLE_LICENSE_HEADER_END@ 22 */ 23 24#include "Utilities.h" 25#include "SecTransform.h" 26#include <sys/sysctl.h> 27#include <syslog.h> 28#include <dispatch/dispatch.h> 29 30void MyDispatchAsync(dispatch_queue_t queue, void(^block)(void)) 31{ 32 fprintf(stderr, "Running job on queue %p\n", queue); 33 dispatch_async(queue, block); 34} 35 36 37 38dispatch_queue_t MyDispatchQueueCreate(const char* name, dispatch_queue_attr_t attr) 39{ 40 dispatch_queue_t result = dispatch_queue_create(name, attr); 41 // fprintf(stderr, "Created queue %s as %p\n", name, result); 42 return result; 43} 44 45 46 47static CFErrorRef CreateErrorRefCore(CFStringRef domain, int errorCode, const char* format, va_list ap) 48{ 49 CFStringRef fmt = CFStringCreateWithCString(NULL, format, kCFStringEncodingUTF8); 50 CFStringRef str = CFStringCreateWithFormatAndArguments(NULL, NULL, fmt, ap); 51 va_end(ap); 52 CFRelease(fmt); 53 54 CFStringRef keys[] = {kCFErrorDescriptionKey}; 55 CFStringRef values[] = {str}; 56 57 CFErrorRef result = CFErrorCreateWithUserInfoKeysAndValues(NULL, domain, errorCode, (const void**) keys, (const void**) values, 1); 58 CFRelease(str); 59 60 return result; 61} 62 63 64 65CFErrorRef CreateGenericErrorRef(CFStringRef domain, int errorCode, const char* format, ...) 66{ 67 va_list ap; 68 va_start(ap, format); 69 return CreateErrorRefCore(domain, errorCode, format, ap); 70} 71 72 73 74CFErrorRef CreateSecTransformErrorRef(int errorCode, const char* format, ...) 75{ 76 // create a CFError in the SecTransform error domain. You can add an explanation, which is cool. 77 va_list ap; 78 va_start(ap, format); 79 80 return CreateErrorRefCore(kSecTransformErrorDomain, errorCode, format, ap); 81} 82 83 84 85CFErrorRef CreateSecTransformErrorRefWithCFType(int errorCode, CFTypeRef message) 86{ 87 CFStringRef keys[] = {kCFErrorLocalizedDescriptionKey}; 88 CFTypeRef values[] = {message}; 89 return CFErrorCreateWithUserInfoKeysAndValues(NULL, kSecTransformErrorDomain, errorCode, (const void**) keys, (const void**) values, 1); 90} 91 92 93 94CFTypeRef gAnnotatedRef = NULL; 95 96CFTypeRef DebugRetain(const void* owner, CFTypeRef type) 97{ 98 CFTypeRef result = CFRetain(type); 99 if (type == gAnnotatedRef) 100 { 101 fprintf(stderr, "Object %p was retained by object %p, count = %ld\n", type, owner, CFGetRetainCount(type)); 102 } 103 104 return result; 105} 106 107 108 109void DebugRelease(const void* owner, CFTypeRef type) 110{ 111 if (type == gAnnotatedRef) 112 { 113 fprintf(stderr, "Object %p was released by object %p, count = %ld\n", type, owner, CFGetRetainCount(type) - 1); 114 } 115 116 CFRelease(type); 117} 118 119// Cribbed from _dispatch_bug and altered a bit 120void transforms_bug(size_t line, long val) 121{ 122 static dispatch_once_t pred; 123 static char os_build[16]; 124 static void *last_seen; 125 void *ra = __builtin_return_address(0); 126 dispatch_once(&pred, ^{ 127#ifdef __APPLE__ 128 int mib[] = { CTL_KERN, KERN_OSVERSION }; 129 size_t bufsz = sizeof(os_build); 130 sysctl(mib, 2, os_build, &bufsz, NULL, 0); 131#else 132 os_build[0] = '\0'; 133#endif 134 }); 135 if (last_seen != ra) { 136 last_seen = ra; 137 syslog(LOG_NOTICE, "BUG in SecTransforms: %s - %p - %lu - %lu", os_build, last_seen, (unsigned long)line, val); 138 } 139} 140