openssl_wrapper.m 6.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186
  1. //
  2. // openssl_wrapper.m
  3. // ThirdDemoApp
  4. //
  5. // Created by Xu Hanjie on 11-1-20.
  6. // Copyright 2011 __MyCompanyName__. All rights reserved.
  7. //
  8. #import "openssl_wrapper.h"
  9. #import "rsa.h"
  10. #include "pem.h"
  11. #include "md5.h"
  12. #include "bio.h"
  13. #include "sha.h"
  14. #include <string.h>
  15. int rsa_sign_with_private_key_pem(char *message, int message_length
  16. , unsigned char *signature, unsigned int *signature_length
  17. , char *private_key_file_path, BOOL rsa2)
  18. {
  19. unsigned char shabuf[(rsa2?(SHA256_DIGEST_LENGTH):(SHA_DIGEST_LENGTH))];
  20. if (rsa2) {
  21. SHA256((unsigned char *)message, message_length, shabuf);
  22. } else {
  23. SHA1((unsigned char *)message, message_length, shabuf);
  24. }
  25. int success = 0;
  26. BIO *bio_private = NULL;
  27. RSA *rsa_private = NULL;
  28. bio_private = BIO_new(BIO_s_file());
  29. BIO_read_filename(bio_private, private_key_file_path);
  30. rsa_private = PEM_read_bio_RSAPrivateKey(bio_private, NULL, NULL, "");
  31. if (rsa_private != nil) {
  32. if (1 == RSA_check_key(rsa_private))
  33. {
  34. int rsa_sign_valid = RSA_sign((rsa2?(NID_sha256):(NID_sha1))
  35. , shabuf, (rsa2?(SHA256_DIGEST_LENGTH):(SHA_DIGEST_LENGTH))
  36. , signature, signature_length
  37. , rsa_private);
  38. if (1 == rsa_sign_valid)
  39. {
  40. success = 1;
  41. }
  42. }
  43. BIO_free_all(bio_private);
  44. }
  45. else {
  46. NSLog(@"rsa_private read error : private key is NULL");
  47. }
  48. return success;
  49. }
  50. int rsa_verify_with_public_key_pem(char *message, int message_length
  51. , unsigned char *signature, unsigned int signature_length
  52. , char *public_key_file_path, BOOL rsa2)
  53. {
  54. unsigned char shabuf[(rsa2?(SHA256_DIGEST_LENGTH):(SHA_DIGEST_LENGTH))];
  55. if (rsa2) {
  56. SHA256((unsigned char *)message, message_length, shabuf);
  57. } else {
  58. SHA1((unsigned char *)message, message_length, shabuf);
  59. }
  60. BIO *bio_public = NULL;
  61. RSA *rsa_public = NULL;
  62. bio_public = BIO_new(BIO_s_file());
  63. BIO_read_filename(bio_public, public_key_file_path);
  64. rsa_public = PEM_read_bio_RSA_PUBKEY(bio_public, NULL, NULL, NULL);
  65. int rsa_verify_valid = RSA_verify((rsa2?(NID_sha256):(NID_sha1))
  66. , shabuf, (rsa2?(SHA256_DIGEST_LENGTH):(SHA_DIGEST_LENGTH))
  67. , signature, signature_length
  68. , rsa_public);
  69. BIO_free_all(bio_public);
  70. if (1 == rsa_verify_valid)
  71. {
  72. return 1;
  73. }
  74. return 0;
  75. }
  76. NSString *base64StringFromData(NSData *signature)
  77. {
  78. int signatureLength = (int)[signature length];
  79. unsigned char *outputBuffer = (unsigned char *)malloc(2 * 4 * (signatureLength / 3 + 1));
  80. int outputLength = EVP_EncodeBlock(outputBuffer, [signature bytes], signatureLength);
  81. outputBuffer[outputLength] = '\0';
  82. NSString *base64String = [NSString stringWithCString:(char *)outputBuffer encoding:NSASCIIStringEncoding];
  83. free(outputBuffer);
  84. return base64String;
  85. }
  86. NSData *dataFromBase64String(NSString *base64String)
  87. {
  88. int stringLength = (int)[base64String length];
  89. const unsigned char *strBuffer = (const unsigned char *)[base64String UTF8String];
  90. unsigned char *outputBuffer = (unsigned char *)malloc(2 * 3 * (stringLength / 4 + 1));
  91. int outputLength = EVP_DecodeBlock(outputBuffer, strBuffer, stringLength);
  92. int zeroByteCounter = 0;
  93. for (int i = stringLength - 1; i >= 0; i--)
  94. {
  95. if (strBuffer[i] == '=')
  96. {
  97. zeroByteCounter++;
  98. }
  99. else
  100. {
  101. break;
  102. }
  103. }
  104. NSData *data = [[NSData alloc] initWithBytes:outputBuffer length:outputLength - zeroByteCounter];
  105. free(outputBuffer);
  106. return data;
  107. }
  108. NSString *rsaSignString(NSString *stringToSign, NSString *privateKeyFilePath, BOOL *signSuccess, BOOL rsa2)
  109. {
  110. const char *message = [stringToSign cStringUsingEncoding:NSUTF8StringEncoding];
  111. int messageLength = (int)strlen(message);
  112. unsigned char *sig = (unsigned char *)malloc(256);
  113. unsigned int sig_len;
  114. char *filePath = (char *)[privateKeyFilePath cStringUsingEncoding:NSUTF8StringEncoding];
  115. int sign_ok = rsa_sign_with_private_key_pem((char *)message, messageLength
  116. , sig, &sig_len
  117. , filePath, rsa2);
  118. NSString *signedString = nil;
  119. if (1 == sign_ok)
  120. {
  121. *signSuccess = YES;
  122. signedString = base64StringFromData([NSData dataWithBytes:sig length:sig_len]);
  123. }
  124. else
  125. {
  126. *signSuccess = NO;
  127. }
  128. free(sig);
  129. return signedString;
  130. }
  131. void rsaVerifyString(NSString *stringToVerify, NSString *signature, NSString *publicKeyFilePath, BOOL *verifySuccess, BOOL rsa2)
  132. {
  133. const char *message = [stringToVerify cStringUsingEncoding:NSUTF8StringEncoding];
  134. int messageLength = (int)[stringToVerify lengthOfBytesUsingEncoding:NSUTF8StringEncoding];
  135. NSData *signatureData = dataFromBase64String(signature);
  136. unsigned char *sig = (unsigned char *)[signatureData bytes];
  137. unsigned int sig_len = (int)[signatureData length];
  138. char *filePath = (char *)[publicKeyFilePath cStringUsingEncoding:NSUTF8StringEncoding];
  139. int verify_ok = rsa_verify_with_public_key_pem((char *)message, messageLength
  140. , sig, sig_len
  141. , filePath, rsa2);
  142. if (1 == verify_ok)
  143. {
  144. *verifySuccess = YES;
  145. }
  146. else
  147. {
  148. *verifySuccess = NO;
  149. }
  150. }
  151. NSString *formattedPEMString(NSString *originalString)
  152. {
  153. NSString *trimmedString = [originalString stringByReplacingOccurrencesOfString:@"\n" withString:@""];
  154. const char *c = [trimmedString UTF8String];
  155. int len = (int)[trimmedString length];
  156. NSMutableString *result = [NSMutableString string];
  157. [result appendString:@"-----BEGIN PRIVATE KEY-----\n"];
  158. int index = 0;
  159. while (index < len) {
  160. char cc = c[index];
  161. [result appendFormat:@"%c", cc];
  162. if ( (index+1) % 64 == 0)
  163. {
  164. [result appendString:@"\n"];
  165. }
  166. index++;
  167. }
  168. [result appendString:@"\n-----END PRIVATE KEY-----"];
  169. return result;
  170. }