Guest User

Untitled

a guest
Apr 17th, 2018
247
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 7.54 KB | None | 0 0
  1. /*Copyright (c) 2007 Extendmac, LLC. <support@extendmac.com>
  2.  
  3. Permission is hereby granted, free of charge, to any person
  4. obtaining a copy of this software and associated documentation
  5. files (the "Software"), to deal in the Software without
  6. restriction, including without limitation the rights to use,
  7. copy, modify, merge, publish, distribute, sublicense, and/or sell
  8. copies of the Software, and to permit persons to whom the
  9. Software is furnished to do so, subject to the following
  10. conditions:
  11.  
  12. The above copyright notice and this permission notice shall be
  13. included in all copies or substantial portions of the Software.
  14.  
  15. THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
  16. EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
  17. OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
  18. NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
  19. HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
  20. WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
  21. FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
  22. OTHER DEALINGS IN THE SOFTWARE.
  23. */
  24.  
  25. #import "EMKeychain.h"
  26.  
  27. @interface EMKeychainItem (Private)
  28. - (BOOL)modifyAttributeWithTag:(SecItemAttr)attributeTag toBeString:(NSString *)newStringValue;
  29. @end
  30.  
  31. @implementation EMKeychainItem
  32.  
  33. static BOOL _logErrors;
  34.  
  35. + (void)lockKeychain {
  36. SecKeychainLock(NULL);
  37. }
  38. + (void)unlockKeychain {
  39. SecKeychainUnlock(NULL, 0, NULL, NO);
  40. }
  41. + (void)setLogsErrors:(BOOL)flag {
  42. _logErrors = flag;
  43. }
  44.  
  45. - (id)initWithCoreKeychainItem:(SecKeychainItemRef)item username:(NSString *)username password:(NSString *)password {
  46. if (self = [super init]) {
  47. coreKeychainItem = item;
  48. [self setValue:username forKey:@"myUsername"];
  49. [self setValue:password forKey:@"myPassword"];
  50. }
  51. return self;
  52. }
  53.  
  54. - (NSString *)password {
  55. return myPassword;
  56. }
  57. - (NSString *)username {
  58. return myUsername;
  59. }
  60. - (NSString *)label {
  61. return myLabel;
  62. }
  63.  
  64. - (BOOL)setPassword:(NSString *)newPasswordString {
  65. if (!newPasswordString)
  66. return NO;
  67.  
  68. [self willChangeValueForKey:@"password"];
  69. [myPassword autorelease];
  70. myPassword = [newPasswordString copy];
  71. [self didChangeValueForKey:@"password"];
  72.  
  73. const char *newPassword = [newPasswordString UTF8String];
  74. OSStatus returnStatus = SecKeychainItemModifyAttributesAndData(coreKeychainItem, NULL, strlen(newPassword), (void *)newPassword);
  75. return (returnStatus == noErr);
  76. }
  77. - (BOOL)setUsername:(NSString *)newUsername {
  78. [self willChangeValueForKey:@"username"];
  79. [myUsername autorelease];
  80. myUsername = [newUsername copy];
  81. [self didChangeValueForKey:@"username"];
  82.  
  83. return [self modifyAttributeWithTag:kSecAccountItemAttr toBeString:newUsername];
  84. }
  85. - (BOOL)setLabel:(NSString *)newLabel {
  86. [self willChangeValueForKey:@"label"];
  87. [myLabel autorelease];
  88. myLabel = [newLabel copy];
  89. [self didChangeValueForKey:@"label"];
  90.  
  91. return [self modifyAttributeWithTag:kSecLabelItemAttr toBeString:newLabel];
  92. }
  93. - (void)dealloc {
  94. [myPassword release];
  95. [myUsername release];
  96. [myLabel release];
  97.  
  98. [super dealloc];
  99. }
  100. @end
  101.  
  102. @implementation EMKeychainItem (Private)
  103. - (BOOL)modifyAttributeWithTag:(SecItemAttr)attributeTag toBeString:(NSString *)newStringValue {
  104. const char *newValue = [newStringValue UTF8String];
  105. SecKeychainAttribute attributes[1];
  106. attributes[0].tag = attributeTag;
  107. attributes[0].length = strlen(newValue);
  108. attributes[0].data = (void *)newValue;
  109.  
  110. SecKeychainAttributeList list;
  111. list.count = 1;
  112. list.attr = attributes;
  113.  
  114. OSStatus returnStatus = SecKeychainItemModifyAttributesAndData(coreKeychainItem, &list, 0, NULL);
  115. return (returnStatus == noErr);
  116. }
  117. @end
  118.  
  119. @implementation EMGenericKeychainItem
  120.  
  121. + (EMGenericKeychainItem *)genericKeychainItemForService:(NSString *)serviceNameString withUsername:(NSString *)usernameString {
  122. if (!usernameString || [usernameString length] == 0)
  123. return nil;
  124.  
  125. const char *serviceName = [serviceNameString UTF8String];
  126. const char *username = [usernameString UTF8String];
  127.  
  128. UInt32 passwordLength = 0;
  129. char *password = nil;
  130.  
  131. SecKeychainItemRef item = nil;
  132. OSStatus returnStatus = SecKeychainFindGenericPassword(NULL, strlen(serviceName), serviceName, strlen(username), username, &passwordLength, (void **)&password, &item);
  133. if (returnStatus != noErr || !item) {
  134. if (_logErrors)
  135. NSLog(@"Error (%@) - %s", NSStringFromSelector(_cmd), GetMacOSStatusErrorString(returnStatus));
  136.  
  137. return nil;
  138. }
  139. NSString *passwordString = [NSString stringWithCString:password length:passwordLength];
  140. SecKeychainItemFreeContent(NULL, password);
  141.  
  142. return [EMGenericKeychainItem genericKeychainItem:item forServiceName:serviceNameString username:usernameString password:passwordString];
  143. }
  144.  
  145. + (EMGenericKeychainItem *)addGenericKeychainItemForService:(NSString *)serviceNameString withUsername:(NSString *)usernameString password:(NSString *)passwordString {
  146. if (!usernameString || [usernameString length] == 0 || !serviceNameString || [serviceNameString length] == 0)
  147. return nil;
  148.  
  149. const char *serviceName = [serviceNameString UTF8String];
  150. const char *username = [usernameString UTF8String];
  151. const char *password = [passwordString UTF8String];
  152.  
  153. SecKeychainItemRef item = nil;
  154. OSStatus returnStatus = SecKeychainAddGenericPassword(NULL, strlen(serviceName), serviceName, strlen(username), username, strlen(password), (void *)password, &item);
  155.  
  156. if (returnStatus != noErr || !item) {
  157. NSLog(@"Error (%@) - %s", NSStringFromSelector(_cmd), GetMacOSStatusErrorString(returnStatus));
  158. return nil;
  159. }
  160. return [EMGenericKeychainItem genericKeychainItem:item forServiceName:serviceNameString username:usernameString password:passwordString];
  161. }
  162.  
  163. + (void) setKeychainPassword:(NSString*)password forUsername:(NSString*)username service:(NSString*)serviceName {
  164. EMKeychainItem *item = [EMGenericKeychainItem genericKeychainItemForService:serviceName withUsername:username];
  165. if (item == nil)
  166. item = [EMGenericKeychainItem addGenericKeychainItemForService:serviceName withUsername:username password:password];
  167. else
  168. [item setPassword:password];
  169. }
  170.  
  171. + (NSString*) passwordForUsername:(NSString*)username service:(NSString*)serviceName {
  172. return [[EMGenericKeychainItem genericKeychainItemForService:serviceName withUsername:username] password];
  173. }
  174.  
  175. - (id)initWithCoreKeychainItem:(SecKeychainItemRef)item serviceName:(NSString *)serviceName username:(NSString *)username password:(NSString *)password {
  176. if (self = [super initWithCoreKeychainItem:item username:username password:password]) {
  177. [self setValue:serviceName forKey:@"myServiceName"];
  178. }
  179. return self;
  180. }
  181. + (id)genericKeychainItem:(SecKeychainItemRef)item forServiceName:(NSString *)serviceName username:(NSString *)username password:(NSString *)password {
  182. return [[[EMGenericKeychainItem alloc] initWithCoreKeychainItem:item serviceName:serviceName username:username password:password] autorelease];
  183. }
  184. - (NSString *)serviceName {
  185. return myServiceName;
  186. }
  187.  
  188. - (BOOL)setServiceName:(NSString *)newServiceName {
  189. [self willChangeValueForKey:@"serviceName"];
  190. [myServiceName autorelease];
  191. myServiceName = [newServiceName copy];
  192. [self didChangeValueForKey:@"serviceName"];
  193.  
  194. return [self modifyAttributeWithTag:kSecServiceItemAttr toBeString:newServiceName];
  195. }
  196. - (void)dealloc {
  197. [myServiceName release];
  198. [super dealloc];
  199. }
  200. @end
  201.  
  202. @implementation EMInternetKeychainItem
  203. + (EMInternetKeychainItem *)internetKeychainItemForServer:(NSString *)serverString withUsername:(NSString *)usernameString path:(NSString *)pathString port:(int)port protocol:(SecProtocolType)protocol {
  204. if (!usernameString || [usernameString length] == 0 || !serverString || [serverString length] == 0)
  205. return nil;
  206.  
  207. const char *server = [serverString UTF8String];
  208. const char *username = [usernameString U
Add Comment
Please, Sign In to add comment