Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(122)

Side by Side Diff: util/mac/launchd.mm

Issue 438673003: Add CFPropertyToLaunchData() and its test (Closed) Base URL: https://chromium.googlesource.com/crashpad/crashpad@master
Patch Set: Rebase Created 6 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « util/mac/launchd.h ('k') | util/mac/launchd_test.mm » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
(Empty)
1 // Copyright 2014 The Crashpad Authors. All rights reserved.
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
6 //
7 // http://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
14
15 #include "util/mac/launchd.h"
16
17 #import <Foundation/Foundation.h>
18
19 #include "base/mac/foundation_util.h"
20 #include "base/mac/scoped_launch_data.h"
21 #include "base/mac/scoped_cftyperef.h"
22 #include "base/strings/sys_string_conversions.h"
23
24 namespace crashpad {
25
26 launch_data_t CFPropertyToLaunchData(CFPropertyListRef property_cf) {
27 // This function mixes Foundation and Core Foundation access to property list
28 // elements according to which is more convenient and correct for any specific
29 // task.
30
31 launch_data_t data_launch = NULL;
32 CFTypeID type_id_cf = CFGetTypeID(property_cf);
33
34 if (type_id_cf == CFDictionaryGetTypeID()) {
35 NSDictionary* dictionary_ns = base::mac::CFToNSCast(
36 base::mac::CFCastStrict<CFDictionaryRef>(property_cf));
37 base::mac::ScopedLaunchData dictionary_launch(
38 launch_data_alloc(LAUNCH_DATA_DICTIONARY));
39
40 for (NSString* key in dictionary_ns) {
41 if (![key isKindOfClass:[NSString class]]) {
42 return NULL;
43 }
44
45 CFPropertyListRef value_cf =
46 static_cast<CFPropertyListRef>([dictionary_ns objectForKey:key]);
47 launch_data_t value_launch = CFPropertyToLaunchData(value_cf);
48 if (!value_launch) {
49 return NULL;
50 }
51
52 launch_data_dict_insert(
53 dictionary_launch, value_launch, [key UTF8String]);
54 }
55
56 data_launch = dictionary_launch.release();
57
58 } else if (type_id_cf == CFArrayGetTypeID()) {
59 NSArray* array_ns =
60 base::mac::CFToNSCast(base::mac::CFCastStrict<CFArrayRef>(property_cf));
61 base::mac::ScopedLaunchData array_launch(
62 launch_data_alloc(LAUNCH_DATA_ARRAY));
63 size_t index = 0;
64
65 for (id element_ns in array_ns) {
66 CFPropertyListRef element_cf = static_cast<CFPropertyListRef>(element_ns);
67 launch_data_t element_launch = CFPropertyToLaunchData(element_cf);
68 if (!element_launch) {
69 return NULL;
70 }
71
72 launch_data_array_set_index(array_launch, element_launch, index++);
73 }
74
75 data_launch = array_launch.release();
76
77 } else if (type_id_cf == CFNumberGetTypeID()) {
78 CFNumberRef number_cf = base::mac::CFCastStrict<CFNumberRef>(property_cf);
79 NSNumber* number_ns = base::mac::CFToNSCast(number_cf);
80 switch (CFNumberGetType(number_cf)) {
81 case kCFNumberSInt8Type:
82 case kCFNumberSInt16Type:
83 case kCFNumberSInt32Type:
84 case kCFNumberSInt64Type:
85 case kCFNumberCharType:
86 case kCFNumberShortType:
87 case kCFNumberIntType:
88 case kCFNumberLongType:
89 case kCFNumberLongLongType:
90 case kCFNumberCFIndexType:
91 case kCFNumberNSIntegerType: {
92 data_launch = launch_data_new_integer([number_ns longLongValue]);
93 break;
94 }
95
96 case kCFNumberFloat32Type:
97 case kCFNumberFloat64Type:
98 case kCFNumberFloatType:
99 case kCFNumberDoubleType: {
100 data_launch = launch_data_new_real([number_ns doubleValue]);
101 break;
102 }
103
104 default: { return NULL; }
105 }
106
107 } else if (type_id_cf == CFBooleanGetTypeID()) {
108 CFBooleanRef boolean_cf =
109 base::mac::CFCastStrict<CFBooleanRef>(property_cf);
110 data_launch = launch_data_new_bool(CFBooleanGetValue(boolean_cf));
111
112 } else if (type_id_cf == CFStringGetTypeID()) {
113 NSString* string_ns = base::mac::CFToNSCast(
114 base::mac::CFCastStrict<CFStringRef>(property_cf));
115
116 // -fileSystemRepresentation might be more correct than -UTF8String, because
117 // these strings can hold paths. The analogous function in launchctl,
118 // CF2launch_data (10.9.2 launchd-842.90.1/support/launchctl.c), uses UTF-8
119 // instead of filesystem encoding, so do the same here. Note that there’s
120 // another occurrence of -UTF8String above, used for dictionary keys.
121 data_launch = launch_data_new_string([string_ns UTF8String]);
122
123 } else if (type_id_cf == CFDataGetTypeID()) {
124 NSData* data_ns =
125 base::mac::CFToNSCast(base::mac::CFCastStrict<CFDataRef>(property_cf));
126 data_launch = launch_data_new_opaque([data_ns bytes], [data_ns length]);
127 } else {
128 base::ScopedCFTypeRef<CFStringRef> type_name_cf(
129 CFCopyTypeIDDescription(type_id_cf));
130 DLOG(ERROR) << "unable to convert CFTypeID " << type_id_cf << " ("
131 << base::SysCFStringRefToUTF8(type_name_cf) << ")";
132 }
133
134 return data_launch;
135 }
136
137 } // namespace crashpad
OLDNEW
« no previous file with comments | « util/mac/launchd.h ('k') | util/mac/launchd_test.mm » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698