OLD | NEW |
---|---|
(Empty) | |
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | |
2 // Use of this source code is governed by a BSD-style license that can be | |
3 // found in the LICENSE file. | |
4 | |
5 #include "base/ios/device_util.h" | |
6 | |
7 #import <CommonCrypto/CommonDigest.h> | |
8 #import <Foundation/Foundation.h> | |
9 | |
10 #include <ifaddrs.h> | |
11 #include <net/if_dl.h> | |
12 #include <string.h> | |
13 #include <sys/socket.h> | |
14 #include <sys/sysctl.h> | |
15 | |
16 #include "base/logging.h" | |
17 #include "base/mac/scoped_cftyperef.h" | |
18 #include "base/memory/scoped_ptr.h" | |
19 #include "base/sys_string_conversions.h" | |
20 | |
21 namespace { | |
22 | |
23 // Client ID key in the user preferences. | |
24 NSString* kClientIdPreferenceKey = @"ChromiumClientID"; | |
stuartmorgan
2012/07/25 11:48:59
NSString* const
Chen Yu
2012/07/25 12:44:55
Done.
| |
25 // Default salt for device ids. | |
26 const char* const kDefaultSalt = "Salt"; | |
27 | |
28 } // namespace | |
29 | |
30 namespace ios { | |
31 namespace device_util { | |
32 | |
33 std::string GetPlatform() { | |
34 std::string result; | |
35 | |
36 size_t size = 0; | |
37 sysctlbyname("hw.machine", NULL, &size, NULL, 0); | |
38 scoped_array<char> machine(new char[size]); | |
39 if (sysctlbyname("hw.machine", machine.get(), &size, NULL, 0) == 0) | |
40 result = machine.get(); | |
41 | |
42 return result; | |
43 } | |
44 | |
45 bool IsRunningOnHighRamDevice() { | |
46 bool result = false; | |
47 | |
48 u_int64_t value = 0; | |
49 size_t size = sizeof(value); | |
50 if (sysctlbyname("hw.memsize", &value, &size, NULL, 0) == 0) { | |
51 // Anything >= 250M, call high ram. | |
52 result = (value >= 250 * 1024 * 1024); | |
53 } | |
54 | |
55 return result; | |
56 } | |
57 | |
58 bool IsSingleCoreDevice() { | |
59 static bool is_init_check = false; | |
60 static bool is_single_core_device = false; | |
61 if (!is_init_check) { | |
62 // "iPhone2,1" is an iPhone 3GS, "iPad1,1" is an iPad 1, and "iPhone3,1" is | |
63 // an iPhone 4. | |
64 NSArray* single_core_devices = | |
65 [NSArray arrayWithObjects:@"iPhone2,1", @"iPad1,1", @"iPhone3,1", nil]; | |
66 is_single_core_device = | |
67 [single_core_devices containsObject: | |
stuartmorgan
2012/07/25 11:48:59
Move this up to the previous line, and reduce the
Chen Yu
2012/07/25 12:44:55
Done.
| |
68 base::SysUTF8ToNSString(GetPlatform())]; | |
69 is_init_check = true; | |
70 } | |
71 return is_single_core_device; | |
72 } | |
73 | |
74 std::string GetMacAddress(std::string ifName) { | |
75 NSMutableString* mac_string = [NSMutableString string]; | |
76 | |
77 struct ifaddrs* addrs; | |
78 if (getifaddrs(&addrs) == 0) { | |
79 struct ifaddrs* cursor = addrs; | |
80 while (cursor != 0) { | |
81 if ((cursor->ifa_addr->sa_family == AF_LINK) && | |
82 strcmp(ifName.c_str(), cursor->ifa_name) == 0) { | |
83 const struct sockaddr_dl* dlAddr = | |
84 (const struct sockaddr_dl*)cursor->ifa_addr; | |
85 const unsigned char* base = | |
86 (const unsigned char*)&dlAddr->sdl_data[dlAddr->sdl_nlen]; | |
87 int sdl_alen = dlAddr->sdl_alen; | |
88 for (int i = 0; i < sdl_alen; ++i) { | |
89 if (i != 0) | |
90 [mac_string appendString:@":"]; | |
91 [mac_string appendFormat:@"%02X", base[i]]; | |
92 } | |
93 break; | |
94 } | |
95 cursor = cursor->ifa_next; | |
96 } | |
97 freeifaddrs(addrs); | |
98 } | |
99 return std::string([mac_string UTF8String]);; | |
100 } | |
101 | |
102 std::string GetRandomId() { | |
103 base::mac::ScopedCFTypeRef<CFUUIDRef> | |
104 uuid_object(CFUUIDCreate(kCFAllocatorDefault)); | |
105 // Get the string representation of CFUUID object. | |
106 base::mac::ScopedCFTypeRef<CFStringRef> uuid_string( | |
107 CFUUIDCreateString(kCFAllocatorDefault, uuid_object)); | |
108 return base::SysCFStringRefToUTF8(uuid_string); | |
109 } | |
110 | |
111 std::string GetDeviceIdentifier(const char* const salt) { | |
112 NSUserDefaults* defaults = [NSUserDefaults standardUserDefaults]; | |
113 NSString* client_id = [defaults stringForKey:kClientIdPreferenceKey]; | |
114 | |
115 if (!client_id) { | |
116 client_id = base::SysUTF8ToNSString(GetRandomId()); | |
117 [defaults setObject:client_id forKey:kClientIdPreferenceKey]; | |
118 [defaults synchronize]; | |
119 } | |
120 | |
121 NSData* data = [[NSString stringWithFormat:@"%@%s", client_id, | |
122 salt ? salt : kDefaultSalt] dataUsingEncoding:NSUTF8StringEncoding]; | |
123 | |
124 DCHECK(CC_SHA256_DIGEST_LENGTH >= 16); | |
125 unsigned char hash[CC_SHA256_DIGEST_LENGTH]; | |
126 void* result = CC_SHA256([data bytes], [data length], hash); | |
127 DCHECK(result == hash); | |
128 CFUUIDBytes* uuid_bytes = static_cast<CFUUIDBytes*>(result); | |
129 | |
130 base::mac::ScopedCFTypeRef<CFUUIDRef> | |
131 uuid_object(CFUUIDCreateFromUUIDBytes(kCFAllocatorDefault, *uuid_bytes)); | |
132 base::mac::ScopedCFTypeRef<CFStringRef> device_id( | |
133 CFUUIDCreateString(kCFAllocatorDefault, uuid_object)); | |
134 return base::SysCFStringRefToUTF8(device_id); | |
135 } | |
136 | |
137 } // namespace device_util | |
138 } // namespace ios | |
OLD | NEW |