react-native-quick-crypto 1.0.10 → 1.0.12
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/android/CMakeLists.txt +16 -0
- package/cpp/argon2/HybridArgon2.cpp +103 -0
- package/cpp/argon2/HybridArgon2.hpp +32 -0
- package/cpp/certificate/HybridCertificate.cpp +42 -0
- package/cpp/certificate/HybridCertificate.hpp +16 -0
- package/cpp/cipher/CCMCipher.cpp +4 -1
- package/cpp/cipher/ChaCha20Cipher.cpp +3 -1
- package/cpp/cipher/ChaCha20Poly1305Cipher.cpp +5 -5
- package/cpp/cipher/ChaCha20Poly1305Cipher.hpp +1 -2
- package/cpp/cipher/HybridCipher.cpp +68 -1
- package/cpp/cipher/HybridCipher.hpp +6 -0
- package/cpp/cipher/HybridRsaCipher.cpp +0 -13
- package/cpp/cipher/XChaCha20Poly1305Cipher.cpp +7 -5
- package/cpp/cipher/XChaCha20Poly1305Cipher.hpp +1 -2
- package/cpp/cipher/XSalsa20Cipher.cpp +4 -0
- package/cpp/cipher/XSalsa20Poly1305Cipher.cpp +7 -5
- package/cpp/cipher/XSalsa20Poly1305Cipher.hpp +1 -2
- package/cpp/dh/HybridDhKeyPair.cpp +179 -0
- package/cpp/dh/HybridDhKeyPair.hpp +37 -0
- package/cpp/dsa/HybridDsaKeyPair.cpp +128 -0
- package/cpp/dsa/HybridDsaKeyPair.hpp +32 -0
- package/cpp/ecdh/HybridECDH.cpp +42 -120
- package/cpp/ecdh/HybridECDH.hpp +1 -0
- package/cpp/keys/HybridKeyObjectHandle.cpp +150 -128
- package/cpp/keys/HybridKeyObjectHandle.hpp +6 -3
- package/cpp/keys/KeyObjectData.hpp +2 -0
- package/cpp/kmac/HybridKmac.cpp +83 -0
- package/cpp/kmac/HybridKmac.hpp +31 -0
- package/cpp/mldsa/HybridMlDsaKeyPair.cpp +11 -20
- package/cpp/mldsa/HybridMlDsaKeyPair.hpp +4 -2
- package/cpp/mlkem/HybridMlKemKeyPair.cpp +319 -0
- package/cpp/mlkem/HybridMlKemKeyPair.hpp +48 -0
- package/cpp/prime/HybridPrime.cpp +81 -0
- package/cpp/prime/HybridPrime.hpp +20 -0
- package/cpp/sign/SignUtils.hpp +9 -26
- package/cpp/utils/QuickCryptoUtils.cpp +44 -0
- package/cpp/utils/QuickCryptoUtils.hpp +39 -0
- package/cpp/x509/HybridX509Certificate.cpp +174 -0
- package/cpp/x509/HybridX509Certificate.hpp +51 -0
- package/lib/commonjs/argon2.js +39 -0
- package/lib/commonjs/argon2.js.map +1 -0
- package/lib/commonjs/certificate.js +35 -0
- package/lib/commonjs/certificate.js.map +1 -0
- package/lib/commonjs/cipher.js +23 -2
- package/lib/commonjs/cipher.js.map +1 -1
- package/lib/commonjs/dhKeyPair.js +109 -0
- package/lib/commonjs/dhKeyPair.js.map +1 -0
- package/lib/commonjs/dsa.js +92 -0
- package/lib/commonjs/dsa.js.map +1 -0
- package/lib/commonjs/ec.js +18 -18
- package/lib/commonjs/ec.js.map +1 -1
- package/lib/commonjs/ecdh.js +37 -0
- package/lib/commonjs/ecdh.js.map +1 -1
- package/lib/commonjs/ed.js +9 -9
- package/lib/commonjs/ed.js.map +1 -1
- package/lib/commonjs/hash.js +17 -12
- package/lib/commonjs/hash.js.map +1 -1
- package/lib/commonjs/hkdf.js.map +1 -1
- package/lib/commonjs/index.js +57 -0
- package/lib/commonjs/index.js.map +1 -1
- package/lib/commonjs/keys/classes.js +11 -9
- package/lib/commonjs/keys/classes.js.map +1 -1
- package/lib/commonjs/keys/generateKeyPair.js +11 -0
- package/lib/commonjs/keys/generateKeyPair.js.map +1 -1
- package/lib/commonjs/keys/index.js +24 -0
- package/lib/commonjs/keys/index.js.map +1 -1
- package/lib/commonjs/keys/signVerify.js +0 -2
- package/lib/commonjs/keys/signVerify.js.map +1 -1
- package/lib/commonjs/mlkem.js +219 -0
- package/lib/commonjs/mlkem.js.map +1 -0
- package/lib/commonjs/pbkdf2.js +18 -1
- package/lib/commonjs/pbkdf2.js.map +1 -1
- package/lib/commonjs/prime.js +84 -0
- package/lib/commonjs/prime.js.map +1 -0
- package/lib/commonjs/rsa.js +7 -7
- package/lib/commonjs/rsa.js.map +1 -1
- package/lib/commonjs/specs/argon2.nitro.js +6 -0
- package/lib/commonjs/specs/argon2.nitro.js.map +1 -0
- package/lib/commonjs/specs/certificate.nitro.js +6 -0
- package/lib/commonjs/specs/certificate.nitro.js.map +1 -0
- package/lib/commonjs/specs/dhKeyPair.nitro.js +6 -0
- package/lib/commonjs/specs/dhKeyPair.nitro.js.map +1 -0
- package/lib/commonjs/specs/dsaKeyPair.nitro.js +6 -0
- package/lib/commonjs/specs/dsaKeyPair.nitro.js.map +1 -0
- package/lib/commonjs/specs/kmac.nitro.js +6 -0
- package/lib/commonjs/specs/kmac.nitro.js.map +1 -0
- package/lib/commonjs/specs/mlKemKeyPair.nitro.js +6 -0
- package/lib/commonjs/specs/mlKemKeyPair.nitro.js.map +1 -0
- package/lib/commonjs/specs/prime.nitro.js +6 -0
- package/lib/commonjs/specs/prime.nitro.js.map +1 -0
- package/lib/commonjs/specs/x509certificate.nitro.js +6 -0
- package/lib/commonjs/specs/x509certificate.nitro.js.map +1 -0
- package/lib/commonjs/subtle.js +385 -114
- package/lib/commonjs/subtle.js.map +1 -1
- package/lib/commonjs/utils/conversion.js +3 -3
- package/lib/commonjs/utils/conversion.js.map +1 -1
- package/lib/commonjs/utils/hashnames.js +31 -0
- package/lib/commonjs/utils/hashnames.js.map +1 -1
- package/lib/commonjs/utils/types.js.map +1 -1
- package/lib/commonjs/x509certificate.js +189 -0
- package/lib/commonjs/x509certificate.js.map +1 -0
- package/lib/module/argon2.js +34 -0
- package/lib/module/argon2.js.map +1 -0
- package/lib/module/certificate.js +30 -0
- package/lib/module/certificate.js.map +1 -0
- package/lib/module/cipher.js +23 -3
- package/lib/module/cipher.js.map +1 -1
- package/lib/module/dhKeyPair.js +102 -0
- package/lib/module/dhKeyPair.js.map +1 -0
- package/lib/module/dsa.js +85 -0
- package/lib/module/dsa.js.map +1 -0
- package/lib/module/ec.js +6 -6
- package/lib/module/ec.js.map +1 -1
- package/lib/module/ecdh.js +37 -0
- package/lib/module/ecdh.js.map +1 -1
- package/lib/module/ed.js +1 -1
- package/lib/module/ed.js.map +1 -1
- package/lib/module/hash.js +17 -12
- package/lib/module/hash.js.map +1 -1
- package/lib/module/hkdf.js.map +1 -1
- package/lib/module/index.js +15 -0
- package/lib/module/index.js.map +1 -1
- package/lib/module/keys/classes.js +11 -9
- package/lib/module/keys/classes.js.map +1 -1
- package/lib/module/keys/generateKeyPair.js +11 -0
- package/lib/module/keys/generateKeyPair.js.map +1 -1
- package/lib/module/keys/index.js +25 -1
- package/lib/module/keys/index.js.map +1 -1
- package/lib/module/keys/signVerify.js +0 -2
- package/lib/module/keys/signVerify.js.map +1 -1
- package/lib/module/mlkem.js +211 -0
- package/lib/module/mlkem.js.map +1 -0
- package/lib/module/pbkdf2.js +18 -1
- package/lib/module/pbkdf2.js.map +1 -1
- package/lib/module/prime.js +77 -0
- package/lib/module/prime.js.map +1 -0
- package/lib/module/rsa.js +1 -1
- package/lib/module/rsa.js.map +1 -1
- package/lib/module/specs/argon2.nitro.js +4 -0
- package/lib/module/specs/argon2.nitro.js.map +1 -0
- package/lib/module/specs/certificate.nitro.js +4 -0
- package/lib/module/specs/certificate.nitro.js.map +1 -0
- package/lib/module/specs/dhKeyPair.nitro.js +4 -0
- package/lib/module/specs/dhKeyPair.nitro.js.map +1 -0
- package/lib/module/specs/dsaKeyPair.nitro.js +4 -0
- package/lib/module/specs/dsaKeyPair.nitro.js.map +1 -0
- package/lib/module/specs/kmac.nitro.js +4 -0
- package/lib/module/specs/kmac.nitro.js.map +1 -0
- package/lib/module/specs/mlKemKeyPair.nitro.js +4 -0
- package/lib/module/specs/mlKemKeyPair.nitro.js.map +1 -0
- package/lib/module/specs/prime.nitro.js +4 -0
- package/lib/module/specs/prime.nitro.js.map +1 -0
- package/lib/module/specs/x509certificate.nitro.js +4 -0
- package/lib/module/specs/x509certificate.nitro.js.map +1 -0
- package/lib/module/subtle.js +386 -116
- package/lib/module/subtle.js.map +1 -1
- package/lib/module/utils/conversion.js +3 -4
- package/lib/module/utils/conversion.js.map +1 -1
- package/lib/module/utils/hashnames.js +31 -0
- package/lib/module/utils/hashnames.js.map +1 -1
- package/lib/module/utils/types.js.map +1 -1
- package/lib/module/x509certificate.js +184 -0
- package/lib/module/x509certificate.js.map +1 -0
- package/lib/tsconfig.tsbuildinfo +1 -1
- package/lib/typescript/argon2.d.ts +16 -0
- package/lib/typescript/argon2.d.ts.map +1 -0
- package/lib/typescript/certificate.d.ts +8 -0
- package/lib/typescript/certificate.d.ts.map +1 -0
- package/lib/typescript/cipher.d.ts +15 -0
- package/lib/typescript/cipher.d.ts.map +1 -1
- package/lib/typescript/dhKeyPair.d.ts +19 -0
- package/lib/typescript/dhKeyPair.d.ts.map +1 -0
- package/lib/typescript/dsa.d.ts +19 -0
- package/lib/typescript/dsa.d.ts.map +1 -0
- package/lib/typescript/ec.d.ts +1 -1
- package/lib/typescript/ec.d.ts.map +1 -1
- package/lib/typescript/ecdh.d.ts +3 -0
- package/lib/typescript/ecdh.d.ts.map +1 -1
- package/lib/typescript/ed.d.ts +1 -1
- package/lib/typescript/ed.d.ts.map +1 -1
- package/lib/typescript/hash.d.ts.map +1 -1
- package/lib/typescript/hkdf.d.ts +2 -6
- package/lib/typescript/hkdf.d.ts.map +1 -1
- package/lib/typescript/index.d.ts +32 -4
- package/lib/typescript/index.d.ts.map +1 -1
- package/lib/typescript/keys/classes.d.ts +7 -5
- package/lib/typescript/keys/classes.d.ts.map +1 -1
- package/lib/typescript/keys/generateKeyPair.d.ts.map +1 -1
- package/lib/typescript/keys/index.d.ts +2 -2
- package/lib/typescript/keys/index.d.ts.map +1 -1
- package/lib/typescript/keys/signVerify.d.ts.map +1 -1
- package/lib/typescript/mlkem.d.ts +30 -0
- package/lib/typescript/mlkem.d.ts.map +1 -0
- package/lib/typescript/pbkdf2.d.ts +2 -2
- package/lib/typescript/pbkdf2.d.ts.map +1 -1
- package/lib/typescript/prime.d.ts +19 -0
- package/lib/typescript/prime.d.ts.map +1 -0
- package/lib/typescript/rsa.d.ts +1 -1
- package/lib/typescript/rsa.d.ts.map +1 -1
- package/lib/typescript/specs/argon2.nitro.d.ts +9 -0
- package/lib/typescript/specs/argon2.nitro.d.ts.map +1 -0
- package/lib/typescript/specs/certificate.nitro.d.ts +10 -0
- package/lib/typescript/specs/certificate.nitro.d.ts.map +1 -0
- package/lib/typescript/specs/cipher.nitro.d.ts +9 -0
- package/lib/typescript/specs/cipher.nitro.d.ts.map +1 -1
- package/lib/typescript/specs/dhKeyPair.nitro.d.ts +14 -0
- package/lib/typescript/specs/dhKeyPair.nitro.d.ts.map +1 -0
- package/lib/typescript/specs/dsaKeyPair.nitro.d.ts +13 -0
- package/lib/typescript/specs/dsaKeyPair.nitro.d.ts.map +1 -0
- package/lib/typescript/specs/ecdh.nitro.d.ts +1 -0
- package/lib/typescript/specs/ecdh.nitro.d.ts.map +1 -1
- package/lib/typescript/specs/keyObjectHandle.nitro.d.ts +1 -0
- package/lib/typescript/specs/keyObjectHandle.nitro.d.ts.map +1 -1
- package/lib/typescript/specs/kmac.nitro.d.ts +10 -0
- package/lib/typescript/specs/kmac.nitro.d.ts.map +1 -0
- package/lib/typescript/specs/mlKemKeyPair.nitro.d.ts +18 -0
- package/lib/typescript/specs/mlKemKeyPair.nitro.d.ts.map +1 -0
- package/lib/typescript/specs/prime.nitro.d.ts +11 -0
- package/lib/typescript/specs/prime.nitro.d.ts.map +1 -0
- package/lib/typescript/specs/x509certificate.nitro.d.ts +34 -0
- package/lib/typescript/specs/x509certificate.nitro.d.ts.map +1 -0
- package/lib/typescript/subtle.d.ts +12 -0
- package/lib/typescript/subtle.d.ts.map +1 -1
- package/lib/typescript/utils/conversion.d.ts.map +1 -1
- package/lib/typescript/utils/hashnames.d.ts +1 -1
- package/lib/typescript/utils/hashnames.d.ts.map +1 -1
- package/lib/typescript/utils/types.d.ts +25 -9
- package/lib/typescript/utils/types.d.ts.map +1 -1
- package/lib/typescript/x509certificate.d.ts +64 -0
- package/lib/typescript/x509certificate.d.ts.map +1 -0
- package/nitrogen/generated/android/QuickCrypto+autolinking.cmake +8 -0
- package/nitrogen/generated/android/QuickCryptoOnLoad.cpp +80 -0
- package/nitrogen/generated/ios/QuickCryptoAutolinking.mm +80 -0
- package/nitrogen/generated/shared/c++/AsymmetricKeyType.hpp +12 -0
- package/nitrogen/generated/shared/c++/CipherInfo.hpp +104 -0
- package/nitrogen/generated/shared/c++/HybridArgon2Spec.cpp +22 -0
- package/nitrogen/generated/shared/c++/HybridArgon2Spec.hpp +66 -0
- package/nitrogen/generated/shared/c++/HybridCertificateSpec.cpp +23 -0
- package/nitrogen/generated/shared/c++/HybridCertificateSpec.hpp +64 -0
- package/nitrogen/generated/shared/c++/HybridCipherSpec.cpp +1 -0
- package/nitrogen/generated/shared/c++/HybridCipherSpec.hpp +4 -0
- package/nitrogen/generated/shared/c++/HybridDhKeyPairSpec.cpp +27 -0
- package/nitrogen/generated/shared/c++/HybridDhKeyPairSpec.hpp +69 -0
- package/nitrogen/generated/shared/c++/HybridDsaKeyPairSpec.cpp +26 -0
- package/nitrogen/generated/shared/c++/HybridDsaKeyPairSpec.hpp +68 -0
- package/nitrogen/generated/shared/c++/HybridECDHSpec.cpp +1 -0
- package/nitrogen/generated/shared/c++/HybridECDHSpec.hpp +1 -0
- package/nitrogen/generated/shared/c++/HybridKeyObjectHandleSpec.cpp +1 -0
- package/nitrogen/generated/shared/c++/HybridKeyObjectHandleSpec.hpp +1 -0
- package/nitrogen/generated/shared/c++/HybridKmacSpec.cpp +23 -0
- package/nitrogen/generated/shared/c++/HybridKmacSpec.hpp +66 -0
- package/nitrogen/generated/shared/c++/HybridMlKemKeyPairSpec.cpp +31 -0
- package/nitrogen/generated/shared/c++/HybridMlKemKeyPairSpec.hpp +74 -0
- package/nitrogen/generated/shared/c++/HybridPrimeSpec.cpp +24 -0
- package/nitrogen/generated/shared/c++/HybridPrimeSpec.hpp +67 -0
- package/nitrogen/generated/shared/c++/HybridX509CertificateHandleSpec.cpp +46 -0
- package/nitrogen/generated/shared/c++/HybridX509CertificateHandleSpec.hpp +96 -0
- package/package.json +4 -1
- package/src/argon2.ts +83 -0
- package/src/certificate.ts +41 -0
- package/src/cipher.ts +41 -3
- package/src/dhKeyPair.ts +156 -0
- package/src/dsa.ts +129 -0
- package/src/ec.ts +9 -9
- package/src/ecdh.ts +59 -0
- package/src/ed.ts +2 -2
- package/src/hash.ts +34 -11
- package/src/hkdf.ts +2 -7
- package/src/index.ts +16 -0
- package/src/keys/classes.ts +26 -14
- package/src/keys/generateKeyPair.ts +14 -0
- package/src/keys/index.ts +37 -2
- package/src/keys/signVerify.ts +0 -5
- package/src/mlkem.ts +350 -0
- package/src/pbkdf2.ts +34 -5
- package/src/prime.ts +134 -0
- package/src/rsa.ts +1 -1
- package/src/specs/argon2.nitro.ts +29 -0
- package/src/specs/certificate.nitro.ts +8 -0
- package/src/specs/cipher.nitro.ts +14 -0
- package/src/specs/dhKeyPair.nitro.ts +14 -0
- package/src/specs/dsaKeyPair.nitro.ts +13 -0
- package/src/specs/ecdh.nitro.ts +1 -0
- package/src/specs/keyObjectHandle.nitro.ts +5 -0
- package/src/specs/kmac.nitro.ts +12 -0
- package/src/specs/mlKemKeyPair.nitro.ts +32 -0
- package/src/specs/prime.nitro.ts +18 -0
- package/src/specs/x509certificate.nitro.ts +38 -0
- package/src/subtle.ts +821 -136
- package/src/utils/conversion.ts +10 -4
- package/src/utils/hashnames.ts +33 -2
- package/src/utils/types.ts +64 -8
- package/src/x509certificate.ts +277 -0
package/android/CMakeLists.txt
CHANGED
|
@@ -25,7 +25,9 @@ endif()
|
|
|
25
25
|
add_library(
|
|
26
26
|
${PACKAGE_NAME} SHARED
|
|
27
27
|
src/main/cpp/cpp-adapter.cpp
|
|
28
|
+
../cpp/argon2/HybridArgon2.cpp
|
|
28
29
|
../cpp/blake3/HybridBlake3.cpp
|
|
30
|
+
../cpp/certificate/HybridCertificate.cpp
|
|
29
31
|
../cpp/cipher/CCMCipher.cpp
|
|
30
32
|
../cpp/cipher/GCMCipher.cpp
|
|
31
33
|
../cpp/cipher/HybridCipher.cpp
|
|
@@ -37,22 +39,29 @@ add_library(
|
|
|
37
39
|
../cpp/cipher/ChaCha20Cipher.cpp
|
|
38
40
|
../cpp/cipher/ChaCha20Poly1305Cipher.cpp
|
|
39
41
|
../cpp/dh/HybridDiffieHellman.cpp
|
|
42
|
+
../cpp/dh/HybridDhKeyPair.cpp
|
|
43
|
+
../cpp/dsa/HybridDsaKeyPair.cpp
|
|
40
44
|
../cpp/ec/HybridEcKeyPair.cpp
|
|
41
45
|
../cpp/ecdh/HybridECDH.cpp
|
|
42
46
|
../cpp/ed25519/HybridEdKeyPair.cpp
|
|
43
47
|
../cpp/hash/HybridHash.cpp
|
|
44
48
|
../cpp/hmac/HybridHmac.cpp
|
|
45
49
|
../cpp/hkdf/HybridHkdf.cpp
|
|
50
|
+
../cpp/kmac/HybridKmac.cpp
|
|
46
51
|
../cpp/keys/HybridKeyObjectHandle.cpp
|
|
47
52
|
../cpp/keys/KeyObjectData.cpp
|
|
48
53
|
../cpp/mldsa/HybridMlDsaKeyPair.cpp
|
|
54
|
+
../cpp/mlkem/HybridMlKemKeyPair.cpp
|
|
49
55
|
../cpp/pbkdf2/HybridPbkdf2.cpp
|
|
56
|
+
../cpp/prime/HybridPrime.cpp
|
|
50
57
|
../cpp/random/HybridRandom.cpp
|
|
51
58
|
../cpp/rsa/HybridRsaKeyPair.cpp
|
|
52
59
|
../cpp/scrypt/HybridScrypt.cpp
|
|
53
60
|
../cpp/sign/HybridSignHandle.cpp
|
|
54
61
|
../cpp/sign/HybridVerifyHandle.cpp
|
|
62
|
+
../cpp/x509/HybridX509Certificate.cpp
|
|
55
63
|
../cpp/utils/HybridUtils.cpp
|
|
64
|
+
../cpp/utils/QuickCryptoUtils.cpp
|
|
56
65
|
${BLAKE3_SOURCES}
|
|
57
66
|
../deps/fastpbkdf2/fastpbkdf2.c
|
|
58
67
|
../deps/ncrypto/src/aead.cpp
|
|
@@ -66,23 +75,30 @@ include(${CMAKE_SOURCE_DIR}/../nitrogen/generated/android/QuickCrypto+autolinkin
|
|
|
66
75
|
# local includes
|
|
67
76
|
include_directories(
|
|
68
77
|
"src/main/cpp"
|
|
78
|
+
"../cpp/argon2"
|
|
69
79
|
"../cpp/blake3"
|
|
80
|
+
"../cpp/certificate"
|
|
70
81
|
"../cpp/cipher"
|
|
71
82
|
"../cpp/dh"
|
|
83
|
+
"../cpp/dsa"
|
|
72
84
|
"../cpp/ec"
|
|
73
85
|
"../cpp/ecdh"
|
|
74
86
|
"../cpp/ed25519"
|
|
75
87
|
"../cpp/hash"
|
|
76
88
|
"../cpp/hkdf"
|
|
77
89
|
"../cpp/hmac"
|
|
90
|
+
"../cpp/kmac"
|
|
78
91
|
"../cpp/keys"
|
|
79
92
|
"../cpp/mldsa"
|
|
93
|
+
"../cpp/mlkem"
|
|
80
94
|
"../cpp/pbkdf2"
|
|
95
|
+
"../cpp/prime"
|
|
81
96
|
"../cpp/random"
|
|
82
97
|
"../cpp/rsa"
|
|
83
98
|
"../cpp/sign"
|
|
84
99
|
"../cpp/scrypt"
|
|
85
100
|
"../cpp/utils"
|
|
101
|
+
"../cpp/x509"
|
|
86
102
|
"../deps/blake3/c"
|
|
87
103
|
"../deps/fastpbkdf2"
|
|
88
104
|
"../deps/ncrypto/include"
|
|
@@ -0,0 +1,103 @@
|
|
|
1
|
+
#include <NitroModules/ArrayBuffer.hpp>
|
|
2
|
+
#include <memory>
|
|
3
|
+
#include <ncrypto.h>
|
|
4
|
+
#include <openssl/err.h>
|
|
5
|
+
#include <openssl/opensslv.h>
|
|
6
|
+
#include <string>
|
|
7
|
+
|
|
8
|
+
#include "HybridArgon2.hpp"
|
|
9
|
+
#include "QuickCryptoUtils.hpp"
|
|
10
|
+
|
|
11
|
+
namespace margelo::nitro::crypto {
|
|
12
|
+
|
|
13
|
+
#if OPENSSL_VERSION_NUMBER >= 0x30200000L
|
|
14
|
+
#ifndef OPENSSL_NO_ARGON2
|
|
15
|
+
|
|
16
|
+
static ncrypto::Argon2Type parseAlgorithm(const std::string& algo) {
|
|
17
|
+
if (algo == "argon2d")
|
|
18
|
+
return ncrypto::Argon2Type::ARGON2D;
|
|
19
|
+
if (algo == "argon2i")
|
|
20
|
+
return ncrypto::Argon2Type::ARGON2I;
|
|
21
|
+
if (algo == "argon2id")
|
|
22
|
+
return ncrypto::Argon2Type::ARGON2ID;
|
|
23
|
+
throw std::runtime_error("Unknown argon2 algorithm: " + algo);
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
static std::shared_ptr<ArrayBuffer> hashImpl(const std::string& algorithm, const std::shared_ptr<ArrayBuffer>& message,
|
|
27
|
+
const std::shared_ptr<ArrayBuffer>& nonce, double parallelism, double tagLength, double memory,
|
|
28
|
+
double passes, double version, const std::optional<std::shared_ptr<ArrayBuffer>>& secret,
|
|
29
|
+
const std::optional<std::shared_ptr<ArrayBuffer>>& associatedData) {
|
|
30
|
+
|
|
31
|
+
auto type = parseAlgorithm(algorithm);
|
|
32
|
+
|
|
33
|
+
ncrypto::Buffer<const char> passBuf{message->size() > 0 ? reinterpret_cast<const char*>(message->data()) : "", message->size()};
|
|
34
|
+
|
|
35
|
+
ncrypto::Buffer<const unsigned char> saltBuf{nonce->size() > 0 ? reinterpret_cast<const unsigned char*>(nonce->data())
|
|
36
|
+
: reinterpret_cast<const unsigned char*>(""),
|
|
37
|
+
nonce->size()};
|
|
38
|
+
|
|
39
|
+
ncrypto::Buffer<const unsigned char> secretBuf{nullptr, 0};
|
|
40
|
+
if (secret.has_value() && secret.value()->size() > 0) {
|
|
41
|
+
secretBuf = {reinterpret_cast<const unsigned char*>(secret.value()->data()), secret.value()->size()};
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
ncrypto::Buffer<const unsigned char> adBuf{nullptr, 0};
|
|
45
|
+
if (associatedData.has_value() && associatedData.value()->size() > 0) {
|
|
46
|
+
adBuf = {reinterpret_cast<const unsigned char*>(associatedData.value()->data()), associatedData.value()->size()};
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
auto result =
|
|
50
|
+
ncrypto::argon2(passBuf, saltBuf, static_cast<uint32_t>(parallelism), static_cast<size_t>(tagLength), static_cast<uint32_t>(memory),
|
|
51
|
+
static_cast<uint32_t>(passes), static_cast<uint32_t>(version), secretBuf, adBuf, type);
|
|
52
|
+
|
|
53
|
+
if (!result) {
|
|
54
|
+
unsigned long err = ERR_peek_last_error();
|
|
55
|
+
const char* reason = err ? ERR_reason_error_string(err) : nullptr;
|
|
56
|
+
throw std::runtime_error(reason ? std::string("Argon2 operation failed: ") + reason : "Argon2 operation failed");
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
return ToNativeArrayBuffer(reinterpret_cast<const uint8_t*>(result.get()), result.size());
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
#endif // OPENSSL_NO_ARGON2
|
|
63
|
+
#endif // OPENSSL_VERSION_NUMBER
|
|
64
|
+
|
|
65
|
+
std::shared_ptr<Promise<std::shared_ptr<ArrayBuffer>>>
|
|
66
|
+
HybridArgon2::hash(const std::string& algorithm, const std::shared_ptr<ArrayBuffer>& message, const std::shared_ptr<ArrayBuffer>& nonce,
|
|
67
|
+
double parallelism, double tagLength, double memory, double passes, double version,
|
|
68
|
+
const std::optional<std::shared_ptr<ArrayBuffer>>& secret,
|
|
69
|
+
const std::optional<std::shared_ptr<ArrayBuffer>>& associatedData) {
|
|
70
|
+
#if OPENSSL_VERSION_NUMBER >= 0x30200000L && !defined(OPENSSL_NO_ARGON2)
|
|
71
|
+
auto nativeMessage = ToNativeArrayBuffer(message);
|
|
72
|
+
auto nativeNonce = ToNativeArrayBuffer(nonce);
|
|
73
|
+
std::optional<std::shared_ptr<ArrayBuffer>> nativeSecret;
|
|
74
|
+
if (secret.has_value()) {
|
|
75
|
+
nativeSecret = ToNativeArrayBuffer(secret.value());
|
|
76
|
+
}
|
|
77
|
+
std::optional<std::shared_ptr<ArrayBuffer>> nativeAd;
|
|
78
|
+
if (associatedData.has_value()) {
|
|
79
|
+
nativeAd = ToNativeArrayBuffer(associatedData.value());
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
return Promise<std::shared_ptr<ArrayBuffer>>::async([algorithm, nativeMessage, nativeNonce, parallelism, tagLength, memory, passes,
|
|
83
|
+
version, nativeSecret = std::move(nativeSecret), nativeAd = std::move(nativeAd)]() {
|
|
84
|
+
return hashImpl(algorithm, nativeMessage, nativeNonce, parallelism, tagLength, memory, passes, version, nativeSecret, nativeAd);
|
|
85
|
+
});
|
|
86
|
+
#else
|
|
87
|
+
throw std::runtime_error("Argon2 is not supported (requires OpenSSL 3.2+)");
|
|
88
|
+
#endif
|
|
89
|
+
}
|
|
90
|
+
|
|
91
|
+
std::shared_ptr<ArrayBuffer> HybridArgon2::hashSync(const std::string& algorithm, const std::shared_ptr<ArrayBuffer>& message,
|
|
92
|
+
const std::shared_ptr<ArrayBuffer>& nonce, double parallelism, double tagLength,
|
|
93
|
+
double memory, double passes, double version,
|
|
94
|
+
const std::optional<std::shared_ptr<ArrayBuffer>>& secret,
|
|
95
|
+
const std::optional<std::shared_ptr<ArrayBuffer>>& associatedData) {
|
|
96
|
+
#if OPENSSL_VERSION_NUMBER >= 0x30200000L && !defined(OPENSSL_NO_ARGON2)
|
|
97
|
+
return hashImpl(algorithm, message, nonce, parallelism, tagLength, memory, passes, version, secret, associatedData);
|
|
98
|
+
#else
|
|
99
|
+
throw std::runtime_error("Argon2 is not supported (requires OpenSSL 3.2+)");
|
|
100
|
+
#endif
|
|
101
|
+
}
|
|
102
|
+
|
|
103
|
+
} // namespace margelo::nitro::crypto
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
#pragma once
|
|
2
|
+
|
|
3
|
+
#include <NitroModules/ArrayBuffer.hpp>
|
|
4
|
+
#include <NitroModules/Promise.hpp>
|
|
5
|
+
#include <memory>
|
|
6
|
+
#include <optional>
|
|
7
|
+
#include <string>
|
|
8
|
+
|
|
9
|
+
#include "HybridArgon2Spec.hpp"
|
|
10
|
+
|
|
11
|
+
namespace margelo::nitro::crypto {
|
|
12
|
+
|
|
13
|
+
using namespace facebook;
|
|
14
|
+
|
|
15
|
+
class HybridArgon2 : public HybridArgon2Spec {
|
|
16
|
+
public:
|
|
17
|
+
HybridArgon2() : HybridObject(TAG) {}
|
|
18
|
+
|
|
19
|
+
public:
|
|
20
|
+
std::shared_ptr<Promise<std::shared_ptr<ArrayBuffer>>> hash(const std::string& algorithm, const std::shared_ptr<ArrayBuffer>& message,
|
|
21
|
+
const std::shared_ptr<ArrayBuffer>& nonce, double parallelism,
|
|
22
|
+
double tagLength, double memory, double passes, double version,
|
|
23
|
+
const std::optional<std::shared_ptr<ArrayBuffer>>& secret,
|
|
24
|
+
const std::optional<std::shared_ptr<ArrayBuffer>>& associatedData) override;
|
|
25
|
+
|
|
26
|
+
std::shared_ptr<ArrayBuffer> hashSync(const std::string& algorithm, const std::shared_ptr<ArrayBuffer>& message,
|
|
27
|
+
const std::shared_ptr<ArrayBuffer>& nonce, double parallelism, double tagLength, double memory,
|
|
28
|
+
double passes, double version, const std::optional<std::shared_ptr<ArrayBuffer>>& secret,
|
|
29
|
+
const std::optional<std::shared_ptr<ArrayBuffer>>& associatedData) override;
|
|
30
|
+
};
|
|
31
|
+
|
|
32
|
+
} // namespace margelo::nitro::crypto
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
#include "HybridCertificate.hpp"
|
|
2
|
+
#include "QuickCryptoUtils.hpp"
|
|
3
|
+
#include <ncrypto.h>
|
|
4
|
+
#include <openssl/crypto.h>
|
|
5
|
+
|
|
6
|
+
namespace margelo::nitro::crypto {
|
|
7
|
+
|
|
8
|
+
bool HybridCertificate::verifySpkac(const std::shared_ptr<ArrayBuffer>& spkac) {
|
|
9
|
+
return ncrypto::VerifySpkac(reinterpret_cast<const char*>(spkac->data()), spkac->size());
|
|
10
|
+
}
|
|
11
|
+
|
|
12
|
+
std::shared_ptr<ArrayBuffer> HybridCertificate::exportPublicKey(const std::shared_ptr<ArrayBuffer>& spkac) {
|
|
13
|
+
auto bio = ncrypto::ExportPublicKey(reinterpret_cast<const char*>(spkac->data()), spkac->size());
|
|
14
|
+
|
|
15
|
+
if (!bio) {
|
|
16
|
+
auto empty = new uint8_t[0];
|
|
17
|
+
return std::make_shared<NativeArrayBuffer>(empty, 0, [empty]() { delete[] empty; });
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
BUF_MEM* mem = bio;
|
|
21
|
+
if (!mem || mem->length == 0) {
|
|
22
|
+
auto empty = new uint8_t[0];
|
|
23
|
+
return std::make_shared<NativeArrayBuffer>(empty, 0, [empty]() { delete[] empty; });
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
return ToNativeArrayBuffer(reinterpret_cast<const uint8_t*>(mem->data), mem->length);
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
std::shared_ptr<ArrayBuffer> HybridCertificate::exportChallenge(const std::shared_ptr<ArrayBuffer>& spkac) {
|
|
30
|
+
auto buf = ncrypto::ExportChallenge(reinterpret_cast<const char*>(spkac->data()), spkac->size());
|
|
31
|
+
|
|
32
|
+
if (buf.data == nullptr) {
|
|
33
|
+
auto empty = new uint8_t[0];
|
|
34
|
+
return std::make_shared<NativeArrayBuffer>(empty, 0, [empty]() { delete[] empty; });
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
auto result = ToNativeArrayBuffer(reinterpret_cast<const uint8_t*>(buf.data), buf.len);
|
|
38
|
+
OPENSSL_free(buf.data);
|
|
39
|
+
return result;
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
} // namespace margelo::nitro::crypto
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
#pragma once
|
|
2
|
+
|
|
3
|
+
#include "HybridCertificateSpec.hpp"
|
|
4
|
+
|
|
5
|
+
namespace margelo::nitro::crypto {
|
|
6
|
+
|
|
7
|
+
class HybridCertificate : public HybridCertificateSpec {
|
|
8
|
+
public:
|
|
9
|
+
HybridCertificate() : HybridObject(TAG) {}
|
|
10
|
+
|
|
11
|
+
bool verifySpkac(const std::shared_ptr<ArrayBuffer>& spkac) override;
|
|
12
|
+
std::shared_ptr<ArrayBuffer> exportPublicKey(const std::shared_ptr<ArrayBuffer>& spkac) override;
|
|
13
|
+
std::shared_ptr<ArrayBuffer> exportChallenge(const std::shared_ptr<ArrayBuffer>& spkac) override;
|
|
14
|
+
};
|
|
15
|
+
|
|
16
|
+
} // namespace margelo::nitro::crypto
|
package/cpp/cipher/CCMCipher.cpp
CHANGED
|
@@ -54,6 +54,7 @@ void CCMCipher::init(const std::shared_ptr<ArrayBuffer> cipher_key, const std::s
|
|
|
54
54
|
|
|
55
55
|
std::shared_ptr<ArrayBuffer> CCMCipher::update(const std::shared_ptr<ArrayBuffer>& data) {
|
|
56
56
|
checkCtx();
|
|
57
|
+
checkNotFinalized();
|
|
57
58
|
auto native_data = ToNativeArrayBuffer(data);
|
|
58
59
|
size_t in_len = native_data->size();
|
|
59
60
|
if (in_len < 0 || in_len > INT_MAX) {
|
|
@@ -104,10 +105,11 @@ std::shared_ptr<ArrayBuffer> CCMCipher::update(const std::shared_ptr<ArrayBuffer
|
|
|
104
105
|
|
|
105
106
|
std::shared_ptr<ArrayBuffer> CCMCipher::final() {
|
|
106
107
|
checkCtx();
|
|
108
|
+
checkNotFinalized();
|
|
107
109
|
|
|
108
110
|
// CCM decryption does not use final. Verification happens in the last update call.
|
|
109
111
|
if (!is_cipher) {
|
|
110
|
-
|
|
112
|
+
is_finalized = true;
|
|
111
113
|
unsigned char* empty_output = new unsigned char[0];
|
|
112
114
|
return std::make_shared<NativeArrayBuffer>(empty_output, 0, [=]() { delete[] empty_output; });
|
|
113
115
|
}
|
|
@@ -138,6 +140,7 @@ std::shared_ptr<ArrayBuffer> CCMCipher::final() {
|
|
|
138
140
|
throw std::runtime_error("Failed to get auth tag after finalization: " + std::string(err_buf));
|
|
139
141
|
}
|
|
140
142
|
auth_tag_state = kAuthTagKnown;
|
|
143
|
+
is_finalized = true;
|
|
141
144
|
|
|
142
145
|
unsigned char* final_output = out_buf.release();
|
|
143
146
|
return std::make_shared<NativeArrayBuffer>(final_output, out_len, [=]() { delete[] final_output; });
|
|
@@ -64,6 +64,7 @@ void ChaCha20Cipher::init(const std::shared_ptr<ArrayBuffer> cipher_key, const s
|
|
|
64
64
|
|
|
65
65
|
std::shared_ptr<ArrayBuffer> ChaCha20Cipher::update(const std::shared_ptr<ArrayBuffer>& data) {
|
|
66
66
|
checkCtx();
|
|
67
|
+
checkNotFinalized();
|
|
67
68
|
auto native_data = ToNativeArrayBuffer(data);
|
|
68
69
|
size_t in_len = native_data->size();
|
|
69
70
|
if (in_len > INT_MAX) {
|
|
@@ -89,7 +90,8 @@ std::shared_ptr<ArrayBuffer> ChaCha20Cipher::update(const std::shared_ptr<ArrayB
|
|
|
89
90
|
|
|
90
91
|
std::shared_ptr<ArrayBuffer> ChaCha20Cipher::final() {
|
|
91
92
|
checkCtx();
|
|
92
|
-
|
|
93
|
+
checkNotFinalized();
|
|
94
|
+
is_finalized = true;
|
|
93
95
|
unsigned char* empty_output = new unsigned char[0];
|
|
94
96
|
return std::make_shared<NativeArrayBuffer>(empty_output, 0, [=]() { delete[] empty_output; });
|
|
95
97
|
}
|
|
@@ -60,13 +60,12 @@ void ChaCha20Poly1305Cipher::init(const std::shared_ptr<ArrayBuffer> cipher_key,
|
|
|
60
60
|
ctx = nullptr;
|
|
61
61
|
throw std::runtime_error("ChaCha20Poly1305Cipher: Failed to set key/IV: " + std::string(err_buf));
|
|
62
62
|
}
|
|
63
|
-
|
|
64
|
-
// Reset final_called flag
|
|
65
|
-
final_called = false;
|
|
63
|
+
is_finalized = false;
|
|
66
64
|
}
|
|
67
65
|
|
|
68
66
|
std::shared_ptr<ArrayBuffer> ChaCha20Poly1305Cipher::update(const std::shared_ptr<ArrayBuffer>& data) {
|
|
69
67
|
checkCtx();
|
|
68
|
+
checkNotFinalized();
|
|
70
69
|
auto native_data = ToNativeArrayBuffer(data);
|
|
71
70
|
size_t in_len = native_data->size();
|
|
72
71
|
if (in_len > INT_MAX) {
|
|
@@ -92,6 +91,7 @@ std::shared_ptr<ArrayBuffer> ChaCha20Poly1305Cipher::update(const std::shared_pt
|
|
|
92
91
|
|
|
93
92
|
std::shared_ptr<ArrayBuffer> ChaCha20Poly1305Cipher::final() {
|
|
94
93
|
checkCtx();
|
|
94
|
+
checkNotFinalized();
|
|
95
95
|
|
|
96
96
|
// For ChaCha20-Poly1305, we need to call final to generate the tag
|
|
97
97
|
int out_len = 0;
|
|
@@ -105,7 +105,7 @@ std::shared_ptr<ArrayBuffer> ChaCha20Poly1305Cipher::final() {
|
|
|
105
105
|
throw std::runtime_error("ChaCha20Poly1305Cipher: Failed to finalize: " + std::string(err_buf));
|
|
106
106
|
}
|
|
107
107
|
|
|
108
|
-
|
|
108
|
+
is_finalized = true;
|
|
109
109
|
return std::make_shared<NativeArrayBuffer>(out, out_len, [=]() { delete[] out; });
|
|
110
110
|
}
|
|
111
111
|
|
|
@@ -130,7 +130,7 @@ std::shared_ptr<ArrayBuffer> ChaCha20Poly1305Cipher::getAuthTag() {
|
|
|
130
130
|
if (!is_cipher) {
|
|
131
131
|
throw std::runtime_error("getAuthTag can only be called during encryption");
|
|
132
132
|
}
|
|
133
|
-
if (!
|
|
133
|
+
if (!is_finalized) {
|
|
134
134
|
throw std::runtime_error("getAuthTag must be called after final()");
|
|
135
135
|
}
|
|
136
136
|
|
|
@@ -6,7 +6,7 @@ namespace margelo::nitro::crypto {
|
|
|
6
6
|
|
|
7
7
|
class ChaCha20Poly1305Cipher : public HybridCipher {
|
|
8
8
|
public:
|
|
9
|
-
ChaCha20Poly1305Cipher() : HybridObject(TAG)
|
|
9
|
+
ChaCha20Poly1305Cipher() : HybridObject(TAG) {}
|
|
10
10
|
~ChaCha20Poly1305Cipher() {
|
|
11
11
|
// Let parent destructor free the context
|
|
12
12
|
ctx = nullptr;
|
|
@@ -24,7 +24,6 @@ class ChaCha20Poly1305Cipher : public HybridCipher {
|
|
|
24
24
|
static constexpr int kKeySize = 32;
|
|
25
25
|
static constexpr int kNonceSize = 12;
|
|
26
26
|
static constexpr int kTagSize = 16; // Poly1305 tag is always 16 bytes
|
|
27
|
-
bool final_called;
|
|
28
27
|
};
|
|
29
28
|
|
|
30
29
|
} // namespace margelo::nitro::crypto
|
|
@@ -8,6 +8,7 @@
|
|
|
8
8
|
#include "HybridCipher.hpp"
|
|
9
9
|
#include "QuickCryptoUtils.hpp"
|
|
10
10
|
|
|
11
|
+
#include <ncrypto.h>
|
|
11
12
|
#include <openssl/err.h>
|
|
12
13
|
#include <openssl/evp.h>
|
|
13
14
|
|
|
@@ -26,6 +27,12 @@ void HybridCipher::checkCtx() const {
|
|
|
26
27
|
}
|
|
27
28
|
}
|
|
28
29
|
|
|
30
|
+
void HybridCipher::checkNotFinalized() const {
|
|
31
|
+
if (is_finalized) {
|
|
32
|
+
throw std::runtime_error("Unsupported state or unable to authenticate data");
|
|
33
|
+
}
|
|
34
|
+
}
|
|
35
|
+
|
|
29
36
|
bool HybridCipher::maybePassAuthTagToOpenSSL() {
|
|
30
37
|
if (auth_tag_state == kAuthTagKnown) {
|
|
31
38
|
OSSL_PARAM params[] = {OSSL_PARAM_construct_octet_string(OSSL_CIPHER_PARAM_AEAD_TAG, auth_tag, auth_tag_len),
|
|
@@ -47,6 +54,7 @@ void HybridCipher::init(const std::shared_ptr<ArrayBuffer> cipher_key, const std
|
|
|
47
54
|
EVP_CIPHER_CTX_free(ctx);
|
|
48
55
|
ctx = nullptr;
|
|
49
56
|
}
|
|
57
|
+
is_finalized = false;
|
|
50
58
|
|
|
51
59
|
// 1. Get cipher implementation by name
|
|
52
60
|
const EVP_CIPHER* cipher = EVP_get_cipherbyname(cipher_type.c_str());
|
|
@@ -99,6 +107,7 @@ void HybridCipher::init(const std::shared_ptr<ArrayBuffer> cipher_key, const std
|
|
|
99
107
|
std::shared_ptr<ArrayBuffer> HybridCipher::update(const std::shared_ptr<ArrayBuffer>& data) {
|
|
100
108
|
auto native_data = ToNativeArrayBuffer(data);
|
|
101
109
|
checkCtx();
|
|
110
|
+
checkNotFinalized();
|
|
102
111
|
size_t in_len = native_data->size();
|
|
103
112
|
if (in_len > INT_MAX) {
|
|
104
113
|
throw std::runtime_error("Message too long");
|
|
@@ -124,6 +133,7 @@ std::shared_ptr<ArrayBuffer> HybridCipher::update(const std::shared_ptr<ArrayBuf
|
|
|
124
133
|
|
|
125
134
|
std::shared_ptr<ArrayBuffer> HybridCipher::final() {
|
|
126
135
|
checkCtx();
|
|
136
|
+
checkNotFinalized();
|
|
127
137
|
// Block size is max output size for final, unless EVP_CIPH_NO_PADDING is set
|
|
128
138
|
int block_size = EVP_CIPHER_CTX_block_size(ctx);
|
|
129
139
|
if (block_size <= 0)
|
|
@@ -148,8 +158,8 @@ std::shared_ptr<ArrayBuffer> HybridCipher::final() {
|
|
|
148
158
|
|
|
149
159
|
// Context should NOT be freed here. It might be needed for getAuthTag() for GCM/OCB.
|
|
150
160
|
// The context will be freed by the destructor (~HybridCipher) when the object goes out of scope.
|
|
161
|
+
is_finalized = true;
|
|
151
162
|
|
|
152
|
-
// Return the shared_ptr<NativeArrayBuffer> (implicit upcast to shared_ptr<ArrayBuffer>)
|
|
153
163
|
return native_final_chunk;
|
|
154
164
|
}
|
|
155
165
|
|
|
@@ -336,4 +346,61 @@ std::vector<std::string> HybridCipher::getSupportedCiphers() {
|
|
|
336
346
|
return cipher_names;
|
|
337
347
|
}
|
|
338
348
|
|
|
349
|
+
std::optional<CipherInfo> HybridCipher::getCipherInfo(const std::string& name, std::optional<double> keyLength,
|
|
350
|
+
std::optional<double> ivLength) {
|
|
351
|
+
auto cipher = ncrypto::Cipher::FromName(name.c_str());
|
|
352
|
+
if (!cipher)
|
|
353
|
+
return std::nullopt;
|
|
354
|
+
|
|
355
|
+
size_t iv_length = cipher.getIvLength();
|
|
356
|
+
size_t key_length = cipher.getKeyLength();
|
|
357
|
+
|
|
358
|
+
if (keyLength.has_value() || ivLength.has_value()) {
|
|
359
|
+
auto ctx = ncrypto::CipherCtxPointer::New();
|
|
360
|
+
if (!ctx.init(cipher, true))
|
|
361
|
+
return std::nullopt;
|
|
362
|
+
|
|
363
|
+
if (keyLength.has_value()) {
|
|
364
|
+
size_t check_len = static_cast<size_t>(keyLength.value());
|
|
365
|
+
if (!ctx.setKeyLength(check_len))
|
|
366
|
+
return std::nullopt;
|
|
367
|
+
key_length = check_len;
|
|
368
|
+
}
|
|
369
|
+
|
|
370
|
+
if (ivLength.has_value()) {
|
|
371
|
+
size_t check_len = static_cast<size_t>(ivLength.value());
|
|
372
|
+
if (cipher.isCcmMode()) {
|
|
373
|
+
if (check_len < 7 || check_len > 13)
|
|
374
|
+
return std::nullopt;
|
|
375
|
+
} else if (cipher.isGcmMode()) {
|
|
376
|
+
// GCM accepts flexible IV lengths
|
|
377
|
+
} else if (cipher.isOcbMode()) {
|
|
378
|
+
if (!ctx.setIvLength(check_len))
|
|
379
|
+
return std::nullopt;
|
|
380
|
+
} else {
|
|
381
|
+
if (check_len != iv_length)
|
|
382
|
+
return std::nullopt;
|
|
383
|
+
}
|
|
384
|
+
iv_length = check_len;
|
|
385
|
+
}
|
|
386
|
+
}
|
|
387
|
+
|
|
388
|
+
std::string name_str(cipher.getName());
|
|
389
|
+
std::transform(name_str.begin(), name_str.end(), name_str.begin(), ::tolower);
|
|
390
|
+
|
|
391
|
+
std::string mode_str(cipher.getModeLabel());
|
|
392
|
+
|
|
393
|
+
std::optional<double> block_size = std::nullopt;
|
|
394
|
+
if (!cipher.isStreamMode()) {
|
|
395
|
+
block_size = static_cast<double>(cipher.getBlockSize());
|
|
396
|
+
}
|
|
397
|
+
|
|
398
|
+
std::optional<double> iv_len = std::nullopt;
|
|
399
|
+
if (iv_length != 0) {
|
|
400
|
+
iv_len = static_cast<double>(iv_length);
|
|
401
|
+
}
|
|
402
|
+
|
|
403
|
+
return CipherInfo{name_str, static_cast<double>(cipher.getNid()), mode_str, static_cast<double>(key_length), block_size, iv_len};
|
|
404
|
+
}
|
|
405
|
+
|
|
339
406
|
} // namespace margelo::nitro::crypto
|
|
@@ -8,6 +8,7 @@
|
|
|
8
8
|
#include <string>
|
|
9
9
|
#include <vector>
|
|
10
10
|
|
|
11
|
+
#include "CipherInfo.hpp"
|
|
11
12
|
#include "HybridCipherSpec.hpp"
|
|
12
13
|
|
|
13
14
|
namespace margelo::nitro::crypto {
|
|
@@ -40,6 +41,9 @@ class HybridCipher : public HybridCipherSpec {
|
|
|
40
41
|
|
|
41
42
|
std::vector<std::string> getSupportedCiphers() override;
|
|
42
43
|
|
|
44
|
+
std::optional<CipherInfo> getCipherInfo(const std::string& name, std::optional<double> keyLength,
|
|
45
|
+
std::optional<double> ivLength) override;
|
|
46
|
+
|
|
43
47
|
protected:
|
|
44
48
|
// Protected enums for state management
|
|
45
49
|
enum CipherKind { kCipher, kDecipher };
|
|
@@ -49,6 +53,7 @@ class HybridCipher : public HybridCipherSpec {
|
|
|
49
53
|
protected:
|
|
50
54
|
// Properties
|
|
51
55
|
bool is_cipher = true;
|
|
56
|
+
bool is_finalized = false;
|
|
52
57
|
std::string cipher_type;
|
|
53
58
|
EVP_CIPHER_CTX* ctx = nullptr;
|
|
54
59
|
bool pending_auth_failed = false;
|
|
@@ -62,6 +67,7 @@ class HybridCipher : public HybridCipherSpec {
|
|
|
62
67
|
// Methods
|
|
63
68
|
int getMode();
|
|
64
69
|
void checkCtx() const;
|
|
70
|
+
void checkNotFinalized() const;
|
|
65
71
|
bool maybePassAuthTagToOpenSSL();
|
|
66
72
|
};
|
|
67
73
|
|
|
@@ -14,19 +14,6 @@ using margelo::nitro::NativeArrayBuffer;
|
|
|
14
14
|
constexpr int kRsaPkcs1Padding = 1;
|
|
15
15
|
constexpr int kRsaOaepPadding = 4;
|
|
16
16
|
|
|
17
|
-
const EVP_MD* getDigestByName(const std::string& hashAlgorithm) {
|
|
18
|
-
if (hashAlgorithm == "SHA-1" || hashAlgorithm == "SHA1" || hashAlgorithm == "sha1" || hashAlgorithm == "sha-1") {
|
|
19
|
-
return EVP_sha1();
|
|
20
|
-
} else if (hashAlgorithm == "SHA-256" || hashAlgorithm == "SHA256" || hashAlgorithm == "sha256" || hashAlgorithm == "sha-256") {
|
|
21
|
-
return EVP_sha256();
|
|
22
|
-
} else if (hashAlgorithm == "SHA-384" || hashAlgorithm == "SHA384" || hashAlgorithm == "sha384" || hashAlgorithm == "sha-384") {
|
|
23
|
-
return EVP_sha384();
|
|
24
|
-
} else if (hashAlgorithm == "SHA-512" || hashAlgorithm == "SHA512" || hashAlgorithm == "sha512" || hashAlgorithm == "sha-512") {
|
|
25
|
-
return EVP_sha512();
|
|
26
|
-
}
|
|
27
|
-
throw std::runtime_error("Unsupported hash algorithm: " + hashAlgorithm);
|
|
28
|
-
}
|
|
29
|
-
|
|
30
17
|
int toOpenSSLPadding(int padding) {
|
|
31
18
|
switch (padding) {
|
|
32
19
|
case kRsaPkcs1Padding:
|
|
@@ -45,10 +45,11 @@ void XChaCha20Poly1305Cipher::init(const std::shared_ptr<ArrayBuffer> cipher_key
|
|
|
45
45
|
|
|
46
46
|
data_buffer_.clear();
|
|
47
47
|
aad_.clear();
|
|
48
|
-
|
|
48
|
+
is_finalized = false;
|
|
49
49
|
}
|
|
50
50
|
|
|
51
51
|
std::shared_ptr<ArrayBuffer> XChaCha20Poly1305Cipher::update(const std::shared_ptr<ArrayBuffer>& data) {
|
|
52
|
+
checkNotFinalized();
|
|
52
53
|
#ifndef BLSALLOC_SODIUM
|
|
53
54
|
throw std::runtime_error("XChaCha20Poly1305Cipher: libsodium must be enabled (BLSALLOC_SODIUM)");
|
|
54
55
|
#else
|
|
@@ -64,6 +65,7 @@ std::shared_ptr<ArrayBuffer> XChaCha20Poly1305Cipher::update(const std::shared_p
|
|
|
64
65
|
}
|
|
65
66
|
|
|
66
67
|
std::shared_ptr<ArrayBuffer> XChaCha20Poly1305Cipher::final() {
|
|
68
|
+
checkNotFinalized();
|
|
67
69
|
#ifndef BLSALLOC_SODIUM
|
|
68
70
|
throw std::runtime_error("XChaCha20Poly1305Cipher: libsodium must be enabled (BLSALLOC_SODIUM)");
|
|
69
71
|
#else
|
|
@@ -80,12 +82,12 @@ std::shared_ptr<ArrayBuffer> XChaCha20Poly1305Cipher::final() {
|
|
|
80
82
|
throw std::runtime_error("XChaCha20Poly1305Cipher: encryption failed");
|
|
81
83
|
}
|
|
82
84
|
|
|
83
|
-
|
|
85
|
+
is_finalized = true;
|
|
84
86
|
size_t ct_len = data_buffer_.size();
|
|
85
87
|
return std::make_shared<NativeArrayBuffer>(ciphertext, ct_len, [=]() { delete[] ciphertext; });
|
|
86
88
|
} else {
|
|
87
89
|
if (data_buffer_.empty()) {
|
|
88
|
-
|
|
90
|
+
is_finalized = true;
|
|
89
91
|
return std::make_shared<NativeArrayBuffer>(nullptr, 0, nullptr);
|
|
90
92
|
}
|
|
91
93
|
|
|
@@ -101,7 +103,7 @@ std::shared_ptr<ArrayBuffer> XChaCha20Poly1305Cipher::final() {
|
|
|
101
103
|
throw std::runtime_error("XChaCha20Poly1305Cipher: decryption failed - authentication tag mismatch");
|
|
102
104
|
}
|
|
103
105
|
|
|
104
|
-
|
|
106
|
+
is_finalized = true;
|
|
105
107
|
size_t pt_len = data_buffer_.size();
|
|
106
108
|
return std::make_shared<NativeArrayBuffer>(plaintext, pt_len, [=]() { delete[] plaintext; });
|
|
107
109
|
}
|
|
@@ -126,7 +128,7 @@ std::shared_ptr<ArrayBuffer> XChaCha20Poly1305Cipher::getAuthTag() {
|
|
|
126
128
|
if (!is_cipher) {
|
|
127
129
|
throw std::runtime_error("getAuthTag can only be called during encryption");
|
|
128
130
|
}
|
|
129
|
-
if (!
|
|
131
|
+
if (!is_finalized) {
|
|
130
132
|
throw std::runtime_error("getAuthTag must be called after final()");
|
|
131
133
|
}
|
|
132
134
|
|
|
@@ -16,7 +16,7 @@ namespace margelo::nitro::crypto {
|
|
|
16
16
|
|
|
17
17
|
class XChaCha20Poly1305Cipher : public HybridCipher {
|
|
18
18
|
public:
|
|
19
|
-
XChaCha20Poly1305Cipher() : HybridObject(TAG)
|
|
19
|
+
XChaCha20Poly1305Cipher() : HybridObject(TAG) {}
|
|
20
20
|
~XChaCha20Poly1305Cipher();
|
|
21
21
|
|
|
22
22
|
void init(const std::shared_ptr<ArrayBuffer> cipher_key, const std::shared_ptr<ArrayBuffer> iv) override;
|
|
@@ -37,7 +37,6 @@ class XChaCha20Poly1305Cipher : public HybridCipher {
|
|
|
37
37
|
std::vector<uint8_t> aad_;
|
|
38
38
|
std::vector<uint8_t> data_buffer_;
|
|
39
39
|
uint8_t auth_tag_[kTagSize];
|
|
40
|
-
bool final_called_;
|
|
41
40
|
};
|
|
42
41
|
|
|
43
42
|
} // namespace margelo::nitro::crypto
|
|
@@ -28,12 +28,14 @@ void XSalsa20Cipher::init(const std::shared_ptr<ArrayBuffer> cipher_key, const s
|
|
|
28
28
|
// Copy key and nonce data
|
|
29
29
|
std::memcpy(key, native_key->data(), crypto_stream_KEYBYTES);
|
|
30
30
|
std::memcpy(nonce, native_iv->data(), crypto_stream_NONCEBYTES);
|
|
31
|
+
is_finalized = false;
|
|
31
32
|
}
|
|
32
33
|
|
|
33
34
|
/**
|
|
34
35
|
* xsalsa20 call to sodium implementation
|
|
35
36
|
*/
|
|
36
37
|
std::shared_ptr<ArrayBuffer> XSalsa20Cipher::update(const std::shared_ptr<ArrayBuffer>& data) {
|
|
38
|
+
checkNotFinalized();
|
|
37
39
|
#ifndef BLSALLOC_SODIUM
|
|
38
40
|
throw std::runtime_error("XSalsa20Cipher: libsodium must be enabled to use this cipher (BLSALLOC_SODIUM is not defined).");
|
|
39
41
|
#else
|
|
@@ -51,9 +53,11 @@ std::shared_ptr<ArrayBuffer> XSalsa20Cipher::update(const std::shared_ptr<ArrayB
|
|
|
51
53
|
* xsalsa20 does not have a final step, returns empty buffer
|
|
52
54
|
*/
|
|
53
55
|
std::shared_ptr<ArrayBuffer> XSalsa20Cipher::final() {
|
|
56
|
+
checkNotFinalized();
|
|
54
57
|
#ifndef BLSALLOC_SODIUM
|
|
55
58
|
throw std::runtime_error("XSalsa20Cipher: libsodium must be enabled to use this cipher (BLSALLOC_SODIUM is not defined).");
|
|
56
59
|
#else
|
|
60
|
+
is_finalized = true;
|
|
57
61
|
return std::make_shared<NativeArrayBuffer>(nullptr, 0, nullptr);
|
|
58
62
|
#endif
|
|
59
63
|
}
|