아무도 문자열을 암호화하고 암호화 된 데이터로 다른 문자열을 반환 할 수있는 올바른 방향으로 나를 가리킬 수 있습니까? (AES256 암호화를 시도해 왔습니다.) 두 개의 NSString 인스턴스를 사용하는 메서드를 작성하고 싶습니다. 하나는 암호화 할 메시지이고 다른 하나는 암호화 할 ‘암호’입니다. 생성해야 할 것 같습니다. 암호화 된 데이터와 함께 암호가 제공되는 경우 되돌릴 수있는 방식으로 암호가있는 암호화 키. 그런 다음 메서드는 암호화 된 데이터에서 생성 된 NSString을 반환해야합니다.
이 게시물의 첫 번째 댓글에 자세히 설명 된 기술을 시도했지만 지금까지 운이 없었습니다. Apple의 CryptoExercise 에는 확실히 뭔가가 있지만 이해할 수는 없습니다. CCCrypt 에 대한 많은 참조를 보았지만 모든 경우에 실패했습니다.
또한 암호화 된 문자열을 해독 할 수 있어야하지만 kCCEncrypt / kCCDecrypt만큼 간단하기를 바랍니다.
답변
코드를 게시하지 않았기 때문에 어떤 문제가 발생했는지 정확히 알기가 어렵습니다. 그러나 링크하는 블로그 게시물 CCCrypt()
은 컴파일 오류를 일으킨 각 호출에서 추가 쉼표를 제외하고는 꽤 괜찮은 것처럼 보입니다 .
이 게시물에 대한 이후의 의견에는 저에게 적합한이 코드가 포함되어 있으며 좀 더 간단 해 보입니다. NSData 카테고리에 대한 코드를 포함하면 다음과 같이 작성할 수 있습니다. (참고 : printf()
호출은 다양한 지점에서 데이터 상태를 보여주기위한 것입니다. 실제 애플리케이션에서는 이러한 값을 인쇄하는 것이 합리적이지 않습니다. .)
int main (int argc, const char * argv[]) {
NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];
NSString *key = @"my password";
NSString *secret = @"text to encrypt";
NSData *plain = [secret dataUsingEncoding:NSUTF8StringEncoding];
NSData *cipher = [plain AES256EncryptWithKey:key];
printf("%s\n", [[cipher description] UTF8String]);
plain = [cipher AES256DecryptWithKey:key];
printf("%s\n", [[plain description] UTF8String]);
printf("%s\n", [[[NSString alloc] initWithData:plain encoding:NSUTF8StringEncoding] UTF8String]);
[pool drain];
return 0;
}
이 코드와 암호화 된 데이터가 항상 NSString으로 잘 변환되는 것은 아니라는 사실을 감안할 때 필요한 기능을 순방향 및 역방향으로 래핑하는 두 가지 메서드를 작성하는 것이 더 편리 할 수 있습니다.
- (NSData*) encryptString:(NSString*)plaintext withKey:(NSString*)key {
return [[plaintext dataUsingEncoding:NSUTF8StringEncoding] AES256EncryptWithKey:key];
}
- (NSString*) decryptData:(NSData*)ciphertext withKey:(NSString*)key {
return [[[NSString alloc] initWithData:[ciphertext AES256DecryptWithKey:key]
encoding:NSUTF8StringEncoding] autorelease];
}
이것은 Snow Leopard에서 확실히 작동하며 @Boz 는 CommonCrypto가 iPhone의 Core OS의 일부 라고 보고합니다. 10.4와 10.5는 모두를 가지고 /usr/include/CommonCrypto
있지만 10.5에는 man 페이지가 CCCryptor.3cc
있고 10.4에는 그렇지 않으므로 YMMV.
편집 : 안전한 무손실 변환을 사용하여 암호화 된 데이터 바이트를 문자열 (원하는 경우)로 나타내는 Base64 인코딩 사용에 대한이 후속 질문 을 참조하십시오 .
답변
Jeff LaMarche의 블로그 에서 찾은 솔루션 과 몇 가지 힌트 를 사용하는 NSData 및 NSString에 대한 범주 모음을 모았습니다. 여기 Stack Overflow에서 Quinn Taylor의 .
범주를 사용하여 NSData를 확장하여 AES256 암호화를 제공하고 NSString의 확장을 BASE64로 암호화 된 데이터를 문자열로 안전하게 제공합니다.
다음은 문자열 암호화 사용법을 보여주는 예입니다.
NSString *plainString = @"This string will be encrypted";
NSString *key = @"YourEncryptionKey"; // should be provided by a user
NSLog( @"Original String: %@", plainString );
NSString *encryptedString = [plainString AES256EncryptWithKey:key];
NSLog( @"Encrypted String: %@", encryptedString );
NSLog( @"Decrypted String: %@", [encryptedString AES256DecryptWithKey:key] );
여기에서 전체 소스 코드를 얻으십시오.
모든 유용한 힌트에 감사드립니다!
-마이클
답변
@owlstead, “주어진 답변 중 하나의 암호화 된 보안 변종”에 대한 귀하의 요청과 관련하여 RNCryptor 를 참조하십시오 . 요청한 작업을 정확히 수행하도록 설계되었으며 여기에 나열된 코드의 문제에 대한 응답으로 구축되었습니다.
RNCryptor는 솔트와 함께 PBKDF2를 사용하고, 임의의 IV를 제공하고, HMAC (PBKDF2에서 자체 솔트로 생성됨)를 연결합니다. 동기 및 비동기 작업을 지원합니다.
답변
나는 그의 답변을 업데이트하기 위해 @QuinnTaylor에서 조금 기다렸지 만 그가 업데이트하지 않았기 때문에 여기에 답변이 좀 더 명확하고 XCode7에로드되는 방식 (아마도 그 이상)이 있습니다. Cocoa 응용 프로그램에서 이것을 사용했지만 iOS 응용 프로그램에서도 잘 작동합니다. ARC 오류가 없습니다.
AppDelegate.m 또는 AppDelegate.mm 파일의 @implementation 섹션 앞에 붙여 넣으십시오.
#import <CommonCrypto/CommonCryptor.h>
@implementation NSData (AES256)
- (NSData *)AES256EncryptWithKey:(NSString *)key {
// 'key' should be 32 bytes for AES256, will be null-padded otherwise
char keyPtr[kCCKeySizeAES256+1]; // room for terminator (unused)
bzero(keyPtr, sizeof(keyPtr)); // fill with zeroes (for padding)
// fetch key data
[key getCString:keyPtr maxLength:sizeof(keyPtr) encoding:NSUTF8StringEncoding];
NSUInteger dataLength = [self length];
//See the doc: For block ciphers, the output size will always be less than or
//equal to the input size plus the size of one block.
//That's why we need to add the size of one block here
size_t bufferSize = dataLength + kCCBlockSizeAES128;
void *buffer = malloc(bufferSize);
size_t numBytesEncrypted = 0;
CCCryptorStatus cryptStatus = CCCrypt(kCCEncrypt, kCCAlgorithmAES128, kCCOptionPKCS7Padding,
keyPtr, kCCKeySizeAES256,
NULL /* initialization vector (optional) */,
[self bytes], dataLength, /* input */
buffer, bufferSize, /* output */
&numBytesEncrypted);
if (cryptStatus == kCCSuccess) {
//the returned NSData takes ownership of the buffer and will free it on deallocation
return [NSData dataWithBytesNoCopy:buffer length:numBytesEncrypted];
}
free(buffer); //free the buffer;
return nil;
}
- (NSData *)AES256DecryptWithKey:(NSString *)key {
// 'key' should be 32 bytes for AES256, will be null-padded otherwise
char keyPtr[kCCKeySizeAES256+1]; // room for terminator (unused)
bzero(keyPtr, sizeof(keyPtr)); // fill with zeroes (for padding)
// fetch key data
[key getCString:keyPtr maxLength:sizeof(keyPtr) encoding:NSUTF8StringEncoding];
NSUInteger dataLength = [self length];
//See the doc: For block ciphers, the output size will always be less than or
//equal to the input size plus the size of one block.
//That's why we need to add the size of one block here
size_t bufferSize = dataLength + kCCBlockSizeAES128;
void *buffer = malloc(bufferSize);
size_t numBytesDecrypted = 0;
CCCryptorStatus cryptStatus = CCCrypt(kCCDecrypt, kCCAlgorithmAES128, kCCOptionPKCS7Padding,
keyPtr, kCCKeySizeAES256,
NULL /* initialization vector (optional) */,
[self bytes], dataLength, /* input */
buffer, bufferSize, /* output */
&numBytesDecrypted);
if (cryptStatus == kCCSuccess) {
//the returned NSData takes ownership of the buffer and will free it on deallocation
return [NSData dataWithBytesNoCopy:buffer length:numBytesDecrypted];
}
free(buffer); //free the buffer;
return nil;
}
@end
원하는 @implementation 클래스에이 두 함수를 붙여 넣습니다. 제 경우에는 AppDelegate.mm 또는 AppDelegate.m 파일에서 @implementation AppDelegate를 선택했습니다.
- (NSString *) encryptString:(NSString*)plaintext withKey:(NSString*)key {
NSData *data = [[plaintext dataUsingEncoding:NSUTF8StringEncoding] AES256EncryptWithKey:key];
return [data base64EncodedStringWithOptions:kNilOptions];
}
- (NSString *) decryptString:(NSString *)ciphertext withKey:(NSString*)key {
NSData *data = [[NSData alloc] initWithBase64EncodedString:ciphertext options:kNilOptions];
return [[NSString alloc] initWithData:[data AES256DecryptWithKey:key] encoding:NSUTF8StringEncoding];
}
답변
Please use the below mentioned URL to encrypt string using AES excryption with
key and IV values.