CCCrypto расшифровывает: ровно на один блок меньше

Я пытаюсь расшифровать строку, зашифрованную скриптом golang. Шифрование - CBC, размер ключа 256. 16 байтов длиной iv включают в начале зашифрованного текста, как предположил Голанг Док. Все работает отлично, за исключением кодов objc, всегда теряющих последний блок. например, когда я ожидаю возврата 80 байт, но получаю только 64, ожидаю 128, но получаю 112. Любой совет? Спасибо!

код Голанга

func encrypt(text_s, key_s string) byte[] {

    text := []byte(text_s)

    // padding text
    n := aes.BlockSize - (len(text) % aes.BlockSize)
    log.Println("Need to pad:", n)

    if n != aes.BlockSize || n != 0 {
        text = append([]byte(strings.Repeat(" ", n)), text...)
    }

    log.Println("to encrypt:'", string(text), "'")
    log.Println("padded length:", len(text))

    key  := []byte(key_s)[:32]
    block, _ := aes.NewCipher(key)

    // if err != nil {
    //  panic(err)
    // }

    ret := make([]byte, aes.BlockSize + len(text))
    iv  := ret[:aes.BlockSize]

    if _, err := io.ReadFull(rand.Reader, iv); err != nil {
        panic(err)
    }

    cbc := cipher.NewCBCEncrypter(block, iv)
    cbc.CryptBlocks(ret[aes.BlockSize:], text)

    return ret
}

коды объектов:

    - (NSData *)decrypt:(NSData*)data{
    if (!key) {
        key = [[_token substringToIndex:32] dataUsingEncoding:NSUTF8StringEncoding];
    }

//    NSLog(@"decodbase64 :%@",[[NSString alloc] initWithData:data encoding:NSASCIIStringEncoding]);
//    NSString *key = _token;
//    
//    char keyPtr[kCCKeySizeAES256 + 1]; // room for terminator (unused)

    // 'key' should be 32 bytes for AES256, will be null-padded otherwise
//    bzero(keyPtr, sizeof(keyPtr)); // fill with zeroes (for padding)

//    BOOL patchNeeded = ([_token length] > kCCKeySizeAES256);
//    NSLog(@"need patch? %@", patchNeeded ? @"YES": @"NO");
//    
//    if (patchNeeded) {
//        key = [_token substringToIndex:kCCKeySizeAES256]; // Ensure that the key isn't longer than what's needed (kCCKeySizeAES256)
//    }

    // fetch key data
//    [key getCString:keyPtr maxLength:sizeof(keyPtr) encoding:NSASCIIStringEncoding];

//    if (patchNeeded) {
//        // Previous iOS version than iOS7 set the first char to '\0' if the key was longer than kCCKeySizeAES256
//        keyPtr[0] = '\0';  
//    }

    size_t dataLength   = [data length] - kCCBlockSizeAES128;
    NSData *iv          = [data subdataWithRange:NSMakeRange(0, kCCBlockSizeAES128)];
    NSData *encrypted   = [data subdataWithRange:NSMakeRange(kCCBlockSizeAES128, dataLength)];

    //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(dataLength);
    NSMutableData *ret = [NSMutableData dataWithLength:dataLength + kCCBlockSizeAES128];

    size_t numBytesDecrypted = 0;
    CCCryptorStatus status = CCCrypt(kCCDecrypt, kCCAlgorithmAES,
                                          kCCOptionPKCS7Padding,
                                          [key bytes],
                                          kCCKeySizeAES256,
                                          [iv bytes],
                                          [encrypted bytes], dataLength, /* input */
                                          [ret mutableBytes], [ret length], /* output */
                                          &numBytesDecrypted
                                          );

    NSLog(@"err: %d", status);
    NSLog(@"dataLength: %d, num: %d", (int)dataLength, (int)numBytesDecrypted);
    if (status == kCCSuccess) {
        //the returned NSData takes ownership of the buffer and will free it on deallocation
        return ret;
    }

//    free(buffer); //free the buffer;
    return nil;
}

1 ответ

Решение

Оказывается, проблема в опции дешифрования:

CCCryptorStatus status = CCCrypt(kCCDecrypt, kCCAlgorithmAES,
                                          0, // change to 0 solve the problem
                                          [key bytes],
                                          kCCKeySizeAES256,
                                          [iv bytes],
                                          [encrypted bytes], dataLength, /* input */
                                          [ret mutableBytes], [ret length], /* output */
                                          &numBytesDecrypted
                                          );
Другие вопросы по тегам