Browse Source

fix decryptMetadata

Marino Faggiana 7 years ago
parent
commit
a462259e3e

+ 2 - 0
Nextcloud.xcodeproj/project.pbxproj

@@ -1132,6 +1132,7 @@
 		F78964AA1EBB576C00403E13 /* JDStatusBarStyle.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = JDStatusBarStyle.m; sourceTree = "<group>"; };
 		F78964AB1EBB576C00403E13 /* JDStatusBarView.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = JDStatusBarView.h; sourceTree = "<group>"; };
 		F78964AC1EBB576C00403E13 /* JDStatusBarView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = JDStatusBarView.m; sourceTree = "<group>"; };
+		F78AF5E21F82837C00B2E7CE /* CommonCryptorSPI.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = CommonCryptorSPI.h; sourceTree = "<group>"; };
 		F78BFEDE1D31126B00E513CF /* MainInterface.storyboard */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.storyboard; path = MainInterface.storyboard; sourceTree = "<group>"; };
 		F78D6F431F0B7CB9002F9619 /* es-MX */ = {isa = PBXFileReference; lastKnownFileType = text.plist.strings; name = "es-MX"; path = "es-MX.lproj/CTAssetsPicker.strings"; sourceTree = "<group>"; };
 		F78D6F441F0B7CB9002F9619 /* es-MX */ = {isa = PBXFileReference; lastKnownFileType = text.plist.strings; name = "es-MX"; path = "es-MX.lproj/SwiftWebVC.strings"; sourceTree = "<group>"; };
@@ -2999,6 +3000,7 @@
 			children = (
 				F72756701F7153FC0011E2FC /* NCClientEncryption.h */,
 				F72756711F7153FC0011E2FC /* NCClientEncryption.m */,
+				F78AF5E21F82837C00B2E7CE /* CommonCryptorSPI.h */,
 				F7FE125C1BAC03FB0041924B /* CCBKPasscode.h */,
 				F7FE125D1BAC03FB0041924B /* CCBKPasscode.m */,
 				F7F801001D98205A007537BC /* CCCertificate.h */,

+ 315 - 0
iOSClient/Security/CommonCryptorSPI.h

@@ -0,0 +1,315 @@
+/*
+ * Copyright (c) 2010 Apple Inc. All Rights Reserved.
+ *
+ * @APPLE_LICENSE_HEADER_START@
+ *
+ * This file contains Original Code and/or Modifications of Original Code
+ * as defined in and that are subject to the Apple Public Source License
+ * Version 2.0 (the 'License'). You may not use this file except in
+ * compliance with the License. Please obtain a copy of the License at
+ * http://www.opensource.apple.com/apsl/ and read it before using this
+ * file.
+ *
+ * The Original Code and all software distributed under the License are
+ * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
+ * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
+ * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
+ * Please see the License for the specific language governing rights and
+ * limitations under the License.
+ *
+ * @APPLE_LICENSE_HEADER_END@
+ */
+
+#ifndef    _CC_CryptorSPI_H_
+#define _CC_CryptorSPI_H_
+
+#include <sys/types.h>
+#include <sys/param.h>
+#include <stdint.h>
+
+#include <string.h>
+#ifdef KERNEL
+#include <machine/limits.h>
+#else
+#include <limits.h>
+#include <stdlib.h>
+#endif /* KERNEL */
+#include <Availability.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+    
+    /*
+     This is an SPI header.  It includes some work in progress implementation notes that
+     will be removed when this is promoted to an API set.
+     */
+    
+    /*
+     Private Ciphers
+     */
+    
+    /* Lion SPI name for no padding.  Defining for compatibility.  Is now
+     ccNoPadding in CommonCryptor.h
+     */
+    
+    enum {
+        ccDefaultPadding            = 0,
+    };
+    
+    
+    enum {
+        kCCAlgorithmAES128NoHardware = 20,
+        kCCAlgorithmAES128WithHardware = 21
+    };
+    
+    /*
+     Private Modes
+     */
+    enum {
+        kCCModeGCM        = 11,
+    };
+    
+    /*
+     Private Paddings
+     */
+    enum {
+        ccCBCCTS1            = 10,
+        ccCBCCTS2            = 11,
+        ccCBCCTS3            = 12,
+    };
+    
+    /*
+     Private Cryptor direction (op)
+     */
+    enum {
+        kCCBoth        = 3,
+    };
+    
+    
+    
+    
+    /*
+     Supports a mode call of
+     int mode_setup(int cipher, const unsigned char *IV, const unsigned char *key, int keylen,
+     const unsigned char *tweak, int tweaklen, int num_rounds, int options, mode_context *ctx);
+     */
+    
+    /* User supplied space for the CryptorRef */
+    
+    CCCryptorStatus CCCryptorCreateFromDataWithMode(
+                                                    CCOperation     op,                /* kCCEncrypt, kCCEncrypt, kCCBoth (default for BlockMode) */
+                                                    CCMode            mode,
+                                                    CCAlgorithm        alg,
+                                                    CCPadding        padding,
+                                                    const void         *iv,            /* optional initialization vector */
+                                                    const void         *key,            /* raw key material */
+                                                    size_t             keyLength,
+                                                    const void         *tweak,            /* raw tweak material */
+                                                    size_t             tweakLength,
+                                                    int                numRounds,
+                                                    CCModeOptions     options,
+                                                    const void        *data,            /* caller-supplied memory */
+                                                    size_t            dataLength,        /* length of data in bytes */
+                                                    CCCryptorRef    *cryptorRef,    /* RETURNED */
+                                                    size_t            *dataUsed)        /* optional, RETURNED */
+    __OSX_AVAILABLE_STARTING(__MAC_10_7, __IPHONE_5_0);
+    
+    
+    /*
+     Assuming we can use existing CCCryptorCreateFromData for all modes serviced by these:
+     int mode_encrypt(const unsigned char *pt, unsigned char *ct, unsigned long len, mode_context *ctx);
+     int mode_decrypt(const unsigned char *ct, unsigned char *pt, unsigned long len, mode_context *ctx);
+     */
+    
+    /*
+     Block mode encrypt and decrypt interfaces for IV tweaked blocks (XTS and CBC)
+     
+     int mode_encrypt_tweaked(const unsigned char *pt, unsigned long len, unsigned char *ct, const unsigned char *tweak, mode_context *ctx);
+     int mode_decrypt_tweaked(const unsigned char *ct, unsigned long len, unsigned char *pt, const unsigned char *tweak, mode_context *ctx);
+     */
+    
+    CCCryptorStatus CCCryptorEncryptDataBlock(
+                                              CCCryptorRef cryptorRef,
+                                              const void *iv,
+                                              const void *dataIn,
+                                              size_t dataInLength,
+                                              void *dataOut)
+    __OSX_AVAILABLE_STARTING(__MAC_10_7, __IPHONE_5_0);
+    
+    
+    CCCryptorStatus CCCryptorDecryptDataBlock(
+                                              CCCryptorRef cryptorRef,
+                                              const void *iv,
+                                              const void *dataIn,
+                                              size_t dataInLength,
+                                              void *dataOut)
+    __OSX_AVAILABLE_STARTING(__MAC_10_7, __IPHONE_5_0);
+    
+    /*
+     Assuming we can use the existing CCCryptorRelease() interface for
+     int mode_done(mode_context *ctx);
+     */
+    
+    /*
+     Not surfacing these other than with CCCryptorReset()
+     
+     int mode_setiv(const unsigned char *IV, unsigned long len, mode_context *ctx);
+     int mode_getiv(const unsigned char *IV, unsigned long *len, mode_context *ctx);
+     */
+    
+    /*
+     DES key utilities
+     */
+    
+    CCCryptorStatus CCDesIsWeakKey(
+                                   void *key,
+                                   size_t Length)
+    __OSX_AVAILABLE_STARTING(__MAC_10_7, __IPHONE_5_0);
+    
+    void CCDesSetOddParity(
+                           void *key,
+                           size_t Length)
+    __OSX_AVAILABLE_STARTING(__MAC_10_7, __IPHONE_5_0);
+    
+    uint32_t CCDesCBCCksum(void *input, void *output,
+                           size_t length, void *key, size_t keylen,
+                           void *ivec)
+    __OSX_AVAILABLE_STARTING(__MAC_10_7, __IPHONE_5_0);
+    
+    
+    /*
+     * returns a cipher blocksize length iv in the provided iv buffer.
+     */
+    
+    CCCryptorStatus
+    CCCryptorGetIV(CCCryptorRef cryptorRef, void *iv)
+    __OSX_AVAILABLE_STARTING(__MAC_10_7, __IPHONE_5_0);
+    
+    /*
+     GCM Support Interfaces
+     
+     Use CCCryptorCreateWithMode() with the kCCModeGCM selector to initialize
+     a CryptoRef.  Only kCCAlgorithmAES128 can be used with GCM and these
+     functions.  IV Setting etc will be ignored from CCCryptorCreateWithMode().
+     Use the CCCryptorGCMAddIV() routine below for IV setup.
+     */
+    
+    /*
+     This adds the initial vector octets from iv of length ivLen to the GCM
+     CCCryptorRef. You can call this function as many times as required to
+     process the entire IV.
+     */
+    
+    CCCryptorStatus
+    CCCryptorGCMAddIV(CCCryptorRef cryptorRef,
+                      const void         *iv,
+                      size_t ivLen)
+    __OSX_AVAILABLE_STARTING(__MAC_10_8, __IPHONE_5_0);
+    
+    /*
+     Additional Authentication Data
+     After the entire IV has been processed, the additional authentication
+     data can be processed. Unlike the IV, a packet/session does not require
+     additional authentication data (AAD) for security. The AAD is meant to
+     be used as side–channel data you want to be authenticated with the packet.
+     Note: once you begin adding AAD to the GCM CCCryptorRef you cannot return
+     to adding IV data until the state has been reset.
+     */
+    
+    CCCryptorStatus
+    CCCryptorGCMAddAAD(CCCryptorRef cryptorRef,
+                       const void         *aData,
+                       size_t aDataLen)
+    __OSX_AVAILABLE_STARTING(__MAC_10_8, __IPHONE_6_0);
+    
+    // Maintain the old symbol with incorrect camel-case for now.
+    CCCryptorStatus
+    CCCryptorGCMaddAAD(CCCryptorRef cryptorRef,
+                       const void         *aData,
+                       size_t aDataLen)
+    __OSX_AVAILABLE_STARTING(__MAC_10_8, __IPHONE_6_0);
+    
+    // This is for old iOS5 clients
+    CCCryptorStatus
+    CCCryptorGCMAddADD(CCCryptorRef cryptorRef,
+                       const void         *aData,
+                       size_t aDataLen)
+    __OSX_AVAILABLE_STARTING(__MAC_10_8, __IPHONE_5_0);
+    
+    
+    CCCryptorStatus CCCryptorGCMEncrypt(
+                                        CCCryptorRef cryptorRef,
+                                        const void *dataIn,
+                                        size_t dataInLength,
+                                        void *dataOut)
+    __OSX_AVAILABLE_STARTING(__MAC_10_8, __IPHONE_5_0);
+    
+    
+    CCCryptorStatus CCCryptorGCMDecrypt(
+                                        CCCryptorRef cryptorRef,
+                                        const void *dataIn,
+                                        size_t dataInLength,
+                                        void *dataOut)
+    __OSX_AVAILABLE_STARTING(__MAC_10_8, __IPHONE_5_0);
+    
+    /*
+     This terminates the GCM state gcm and stores the tag in tag of length
+     taglen octets.
+     */
+    
+    CCCryptorStatus CCCryptorGCMFinal(
+                                      CCCryptorRef cryptorRef,
+                                      const void *tag,
+                                      size_t *tagLength)
+    __OSX_AVAILABLE_STARTING(__MAC_10_8, __IPHONE_5_0);
+    
+    /*
+     This will reset the GCM CCCryptorRef to the state that CCCryptorCreateWithMode()
+     left it. The user would then call CCCryptorGCMAddIV(), CCCryptorGCMaddAAD(), etc.
+     */
+    
+    CCCryptorStatus CCCryptorGCMReset(
+                                      CCCryptorRef cryptorRef)
+    __OSX_AVAILABLE_STARTING(__MAC_10_8, __IPHONE_5_0);
+    
+    /*
+     This will initialize the GCM state with the given key, IV and AAD value
+     then proceed to encrypt or decrypt the message text and store the final
+     message tag. The definition of the variables is the same as it is for all
+     the manual functions. If you are processing many packets under the same
+     key you shouldn’t use this function as it invokes the pre–computation
+     with each call.
+     */
+    
+    CCCryptorStatus CCCryptorGCM(
+                                 CCOperation     op,                /* kCCEncrypt, kCCDecrypt */
+                                 CCAlgorithm        alg,
+                                 const void         *key,            /* raw key material */
+                                 size_t             keyLength,
+                                 const void         *iv,
+                                 size_t             ivLen,
+                                 const void         *aData,
+                                 size_t             aDataLen,
+                                 const void         *dataIn,
+                                 size_t             dataInLength,
+                                 void             *dataOut,
+                                 const void         *tag,
+                                 size_t             *tagLength)
+    __OSX_AVAILABLE_STARTING(__MAC_10_8, __IPHONE_5_0);
+    
+    
+    void CC_RC4_set_key(void *ctx, int len, const unsigned char *data)
+    __OSX_AVAILABLE_STARTING(__MAC_10_4, __IPHONE_5_0);
+    
+    void CC_RC4(void *ctx, unsigned long len, const unsigned char *indata,
+                unsigned char *outdata)
+    __OSX_AVAILABLE_STARTING(__MAC_10_4, __IPHONE_5_0);
+    
+    
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* _CC_CryptorSPI_H_ */

+ 26 - 25
iOSClient/Security/NCClientEncryption.m

@@ -27,7 +27,7 @@
 #import <CommonCrypto/CommonCryptor.h>
 #import <CommonCrypto/CommonDigest.h>
 #import <Security/Security.h>
-
+#import "CommonCryptorSPI.h"
 
 #import <openssl/x509.h>
 #import <openssl/bio.h>
@@ -251,30 +251,27 @@ cleanup:
 
 - (void)decryptMetadata:(tableMetadata *)metadata activeUrl:(NSString *)activeUrl
 {
-    //NSData *data = [[NSFileManager defaultManager] contentsAtPath:[NSString stringWithFormat:@"%@/%@", activeUrl, metadata.fileID]];
+    NSData *data = [[NSFileManager defaultManager] contentsAtPath:[NSString stringWithFormat:@"%@/%@", activeUrl, metadata.fileID]];
     
-    NSData *data = [@"I love Nextcloud Android and iOS" dataUsingEncoding:NSUTF8StringEncoding];
     NSData *keyData = [[NSData alloc] initWithBase64EncodedString:@"bGzWfQBj2lE4ZnysDWwsIg==" options:0];
     NSData *initVectorData = [[NSData alloc] initWithBase64EncodedString:@"rTBECYNekKF+a1HR7z32/Q==" options:0];
     
     // Encrypt
-    NSData *encryptedData = cipherOperation(data, keyData, initVectorData, kCCEncrypt);
-    NSString *base64Encoded = [encryptedData base64EncodedStringWithOptions:0];
+    //NSData *encryptedData = cipherOperation(data, keyData, initVectorData, kCCEncrypt);
+    //NSString *base64Encoded = [encryptedData base64EncodedStringWithOptions:0];
     
-    NSLog(@"%@", base64Encoded);
+    //NSLog(@"%@", base64Encoded);
     
     // Decrypt
-    //NSData *decryptedData = cipherOperation(data, keyData, initVectorData, kCCDecrypt);
+    NSData *decryptedData = cipherOperation(data, keyData, initVectorData, kCCDecrypt);
 
-    //if (decryptedData != nil)
-    // [decryptedData writeToFile:[NSString stringWithFormat:@"%@/%@", activeUrl, @"decrypted.jpg"] atomically:YES];
+    if (decryptedData != nil)
+        [decryptedData writeToFile:[NSString stringWithFormat:@"%@/%@", activeUrl, @"decrypted.jpg"] atomically:YES];
 }
 
 NSData *cipherOperation(NSData *contentData, NSData *keyData, NSData *initVectorData, CCOperation operation)
 {
-    size_t operationSize = contentData.length + kCCBlockSizeAES128;
-    void *operationBytes = malloc(operationSize);
-    size_t actualOutSize = 0;
+    NSMutableData *dataOut = [NSMutableData dataWithLength:contentData.length];
     
     // setup key
     unsigned char cKey[kCCKeySizeAES128];
@@ -286,23 +283,27 @@ NSData *cipherOperation(NSData *contentData, NSData *keyData, NSData *initVector
     bzero(cIv, kCCBlockSizeAES128);
     [initVectorData getBytes:cIv length:kCCBlockSizeAES128];
     
-    CCCryptorStatus cryptStatus = CCCrypt(operation,
-                                          kCCAlgorithmAES128,
-                                          kCCOptionPKCS7Padding,
-                                          cKey,
-                                          kCCKeySizeAES128,
-                                          cIv,
-                                          contentData.bytes,
-                                          contentData.length,
-                                          operationBytes,
-                                          operationSize,
-                                          &actualOutSize);
+    NSMutableData *tag = [NSMutableData dataWithLength:kCCBlockSizeAES128];
+    size_t  tagLength = kCCBlockSizeAES128;
+    
+    CCCryptorStatus cryptStatus = CCCryptorGCM(operation,
+                                               kCCAlgorithmAES128,
+                                               cKey,
+                                               kCCKeySizeAES128,
+                                               cIv,
+                                               kCCBlockSizeAES128,
+                                               nil,
+                                               0,
+                                               contentData.bytes,
+                                               contentData.length,
+                                               dataOut.mutableBytes,
+                                               tag.bytes,
+                                               &tagLength);
     
     if (cryptStatus == kCCSuccess) {
-        return [NSData dataWithBytesNoCopy:operationBytes length:actualOutSize];
+        return [NSData dataWithBytesNoCopy:(void *)dataOut.bytes length:dataOut.length];
     }
     
-    free(operationBytes);
     return nil;
 }