[*] Preparing for ECC support

This commit is contained in:
Reece Wilson 2021-09-18 21:10:25 +01:00
parent c4567f4c8c
commit 9dd195949a
23 changed files with 633 additions and 148 deletions

View File

@ -9,7 +9,7 @@
namespace Aurora::Crypto::AES namespace Aurora::Crypto::AES
{ {
AUKN_SYM AuUInt GetSafeCipherPadding(const Memory::MemoryViewRead & plainText); AUKN_SYM AuUInt GetSafeCipherPadding(const Memory::MemoryViewRead &plainText);
// Remember: AES works in chunks of 128 bits // Remember: AES works in chunks of 128 bits
// IVS are 16 bytes long // IVS are 16 bytes long
@ -20,17 +20,17 @@ namespace Aurora::Crypto::AES
// It is not the end of the world if an IV is made public by design // It is not the end of the world if an IV is made public by design
// Keys must be random // Keys must be random
// Initialization vectors could be derived from SHA1, Tiger, or SHA2 digests // Initialization vectors could be derived from SHA1, Tiger, or SHA2 digests
AUKN_SYM bool Encrypt(const Memory::MemoryViewRead & plainText, AUKN_SYM bool Encrypt(const Memory::MemoryViewRead &plainText,
const Memory::MemoryViewRead & inIv, const Memory::MemoryViewRead &inIv,
const Memory::MemoryViewWrite & outIv, const Memory::MemoryViewWrite &outIv,
const Memory::MemoryViewRead & inKey, const Memory::MemoryViewRead &inKey,
AuList<AuUInt8> &out, AuList<AuUInt8> &out,
bool auCoolCodePadding); bool auCoolCodePadding);
AUKN_SYM bool Decrypt(const Memory::MemoryViewRead & cipherText, AUKN_SYM bool Decrypt(const Memory::MemoryViewRead &cipherText,
const Memory::MemoryViewRead & inIv, const Memory::MemoryViewRead &inIv,
const Memory::MemoryViewWrite & outIv, const Memory::MemoryViewWrite &outIv,
const Memory::MemoryViewRead & inKey, const Memory::MemoryViewRead &inKey,
AuList<AuUInt8>& plainText, AuList<AuUInt8> &plainText,
bool auCoolCodePadding); bool auCoolCodePadding);
} }

View File

@ -17,18 +17,18 @@ namespace Aurora::Crypto::CA
class ICertificateStore class ICertificateStore
{ {
public: public:
virtual void AddSignature(const AuSPtr<RSA::IRSAPublic>& CA, virtual void AddSignature(const AuSPtr<RSA::IRSAPublic> &CA,
const AuList<AuUInt8>& sig, const AuList<AuUInt8> &sig,
EHashType method, EHashType method,
EPaddingType type) = 0; EPaddingType type) = 0;
virtual void AddPublicCert(const X509::Certificate& cert) = 0; virtual void AddPublicCert(const X509::Certificate &cert) = 0;
/// For future support of http gets of the CA list /// For future support of http gets of the CA list
virtual bool& AllowHTTPTree() = 0; virtual bool& AllowHTTPTree() = 0;
virtual bool CheckKey(const AuSPtr<RSA::IRSAPublic>& pub) = 0; virtual bool CheckKey(const AuSPtr<RSA::IRSAPublic> &pub) = 0;
virtual bool CheckCert(const X509::Certificate& cert) = 0; virtual bool CheckCert(const X509::Certificate &cert) = 0;
}; };

View File

@ -1,13 +0,0 @@
/***
Copyright (C) 2021 J Reece Wilson (a/k/a "Reece"). All rights reserved.
File: 25519.hpp
Date: 2021-6-11
Author: Reece
***/
#pragma once
namespace Aurora::Crypto::ECC::C25519
{
}

View File

@ -7,46 +7,14 @@
***/ ***/
#pragma once #pragma once
#include "IECCPublic.hpp"
#include "IECCPrivate.hpp"
#include "EECCCurve.hpp"
namespace Aurora::Crypto::ECC namespace Aurora::Crypto::ECC
{ {
class IECCPublic
{
public:
virtual bool Verify(const Memory::MemoryViewRead &payload,
const Memory::MemoryViewRead &signature) = 0;
virtual bool AsPublicECC(AuList<AuUInt8> &out) = 0;
};
class IECCPrivate
{
public:
virtual bool Sign(const Memory::MemoryViewRead &payload,
EHashType method,
AuList<AuUInt8> &out) = 0;
virtual bool ECDH(const AuSPtr<IECCPublic> &partnerPublic,
AuList<AuUInt8> &sharedKey) = 0;
virtual bool AsPublicECC(AuList<AuUInt8> &out) = 0;
virtual bool AsPrivateECC(AuList<AuUInt8> &out) = 0;
};
enum EECCCurve
{
eCurve256,
eCurve384,
eCurve521,
eCurveX25519,
eCurveEd25519
};
AUKN_SHARED_API(NewECC, IECCPrivate, EECCCurve curve); AUKN_SHARED_API(NewECC, IECCPrivate, EECCCurve curve);
AUKN_SHARED_API(OpenPrivateECC, IECCPrivate, EECCCurve curve, const Memory::MemoryViewRead &pk); AUKN_SHARED_API(OpenPrivateECC, IECCPrivate, EECCCurve curve, const Memory::MemoryViewRead &pk);
AUKN_SHARED_API(OpenPublicECC, IECCPublic, EECCCurve curve, const Memory::MemoryViewRead &pk); AUKN_SHARED_API(OpenPublicECC, IECCPublic, EECCCurve curve, const Memory::MemoryViewRead &pk);
AUKN_SHARED_API(OpenPublicECCFromCert, IECCPublic, EECCCurve curve, const Memory::MemoryViewRead &certificate); AUKN_SHARED_API(OpenPublicECCFromCert, IECCPublic, EECCCurve curve, const Memory::MemoryViewRead &certificate);
} }
#include "25519/25519.hpp"
#include "NIST/NIST.hpp"

View File

@ -0,0 +1,20 @@
/***
Copyright (C) 2021 J Reece Wilson (a/k/a "Reece"). All rights reserved.
File: EECCCurve.hpp
Date: 2021-9-18
Author: Reece
***/
#pragma once
namespace Aurora::Crypto::ECC
{
enum EECCCurve
{
eCurve256,
eCurve384,
eCurve521,
eCurveX25519,
eCurveEd25519
};
}

View File

@ -0,0 +1,30 @@
/***
Copyright (C) 2021 J Reece Wilson (a/k/a "Reece"). All rights reserved.
File: IECCPrivate.hpp
Date: 2021-9-18
Author: Reece
***/
#pragma once
namespace Aurora::Crypto::ECC
{
class IECCPrivate
{
public:
virtual bool Sign(const Memory::MemoryViewRead &plainText,
EHashType method,
AuList<AuUInt8> &out) = 0;
virtual bool Sign(const Memory::MemoryViewRead &hash,
AuList<AuUInt8> &out) = 0;
virtual bool ECDH(const AuSPtr<IECCPublic> &partnerPublic,
AuList<AuUInt8> &sharedKey) = 0;
virtual bool AsPublicECC(AuList<AuUInt8> &out) = 0;
virtual bool AsPrivateECC(AuList<AuUInt8> &out) = 0;
virtual EECCCurve GetType() override;
};
}

View File

@ -0,0 +1,27 @@
/***
Copyright (C) 2021 J Reece Wilson (a/k/a "Reece"). All rights reserved.
File: IECCPublic.hpp
Date: 2021-9-18
Author: Reece
***/
#pragma once
namespace Aurora::Crypto::ECC
{
class IECCPublic
{
public:
virtual bool Verify(const Memory::MemoryViewRead &hash,
const Memory::MemoryViewRead &signature) = 0;
virtual bool Verify(const Memory::MemoryViewRead &plaintext,
const Memory::MemoryViewRead &signature,
EHashType method) = 0;
virtual bool AsPublicECC(AuList<AuUInt8> &out) = 0;
virtual EECCCurve GetType() = 0;
};
}

View File

@ -1,13 +0,0 @@
/***
Copyright (C) 2021 J Reece Wilson (a/k/a "Reece"). All rights reserved.
File: NIST.hpp
Date: 2021-6-11
Author: Reece
***/
#pragma once
namespace Aurora::Crypto::ECC::NIST
{
}

View File

@ -73,34 +73,39 @@ namespace Aurora::Memory
this->length = length; this->length = length;
} }
AuUInt ToPointer() AuUInt ToPointer() const
{ {
return reinterpret_cast<AuUInt>(ptr); return reinterpret_cast<AuUInt>(ptr);
} }
AuUInt ToLength() AuUInt ToLength() const
{ {
return length; return length;
} }
template<typename T> template<typename T>
AuUInt ToCount() AuUInt ToCount() const
{ {
return length / sizeof(T); return length / sizeof(T);
} }
template<typename T> template<typename T>
T *Begin() T *Begin() const
{ {
return reinterpret_cast<T *>(ptr); return reinterpret_cast<T *>(ptr);
} }
template<typename T> template<typename T>
T *End() T *End() const
{ {
return Begin<T>() + ToCount<T>(); return Begin<T>() + ToCount<T>();
} }
bool HasMemory() const
{
return ptr && length;
}
Void_t /*const*/ ptr; Void_t /*const*/ ptr;
AuUInt /*const*/ length; AuUInt /*const*/ length;
}; };

View File

@ -14,7 +14,7 @@ namespace Aurora::Registry
/** /**
* This registry implementation is a fairly reliable, small scale, preference, and app variable database * This registry implementation is a fairly reliable, small scale, preference, and app variable database
* Do not consider this as a replacement for a "real" high performance kvp database, it is not, it's a small cache backed document serializer for settings * Do not consider this as a replacement for a "real" high performance kvp database, it is not, it's a small cache backed document serializer for user profiles
* *
* Basic use case:-------------------------------------------------------------- * Basic use case:--------------------------------------------------------------
* -> AllocRegistry() * -> AllocRegistry()

View File

@ -448,6 +448,28 @@ static inline bool AuTryResize(T &list, AuUInt length)
} }
} }
template<typename T>
static inline bool AuTryDownsize(T &list, AuUInt length)
{
try
{
if constexpr (std::is_same_v<T, Aurora::Memory::ByteBuffer>)
{
return list.Resize(length);
}
else
{
list.resize(length);
list.shrink_to_fit();
return true;
}
}
catch (...)
{
return false;
}
}
static inline AuString AuReplaceAll(AuString &str, const AuString &from, const AuString &to) static inline AuString AuReplaceAll(AuString &str, const AuString &from, const AuString &to)
{ {
size_t start_pos = 0; size_t start_pos = 0;

View File

@ -13,7 +13,7 @@
namespace Aurora::Crypto::AES namespace Aurora::Crypto::AES
{ {
AUKN_SYM AuUInt GetSafeCipherPadding(const Memory::MemoryViewRead & parameters) AUKN_SYM AuUInt GetSafeCipherPadding(const Memory::MemoryViewRead &parameters)
{ {
auto tptr = reinterpret_cast<const unsigned char *>(parameters.ptr); auto tptr = reinterpret_cast<const unsigned char *>(parameters.ptr);
@ -139,10 +139,10 @@ namespace Aurora::Crypto::AES
return true; return true;
} }
AUKN_SYM bool Encrypt(const Memory::MemoryViewRead & plainText, AUKN_SYM bool Encrypt(const Memory::MemoryViewRead &plainText,
const Memory::MemoryViewRead & inIv, const Memory::MemoryViewRead &inIv,
const Memory::MemoryViewWrite & outIv, const Memory::MemoryViewWrite & outIv,
const Memory::MemoryViewRead & inKey, const Memory::MemoryViewRead &inKey,
AuList<AuUInt8> &out, AuList<AuUInt8> &out,
bool auCoolCodePadding) bool auCoolCodePadding)
{ {
@ -254,10 +254,10 @@ namespace Aurora::Crypto::AES
} }
AUKN_SYM bool Decrypt(const Memory::MemoryViewRead & cipherText, AUKN_SYM bool Decrypt(const Memory::MemoryViewRead &cipherText,
const Memory::MemoryViewRead & inIv, const Memory::MemoryViewRead &inIv,
const Memory::MemoryViewWrite & outIv, const Memory::MemoryViewWrite &outIv,
const Memory::MemoryViewRead & inKey, const Memory::MemoryViewRead &inKey,
AuList<AuUInt8> &plainText, AuList<AuUInt8> &plainText,
bool safe) bool safe)
{ {

View File

@ -5,4 +5,5 @@
Date: 2021-6-12 Date: 2021-6-12
Author: Reece Author: Reece
***/ ***/
#include <RuntimeInternal.hpp>
#include "Crypto.hpp" #include "Crypto.hpp"

View File

@ -7,3 +7,45 @@
***/ ***/
#pragma once #pragma once
#include <tomcrypt.h>
#include <Extensions/LTC/LTCExtensions.hpp>
#include <Crypto.hpp>
namespace Aurora::Crypto
{
static int PaddingToType(EPaddingType type)
{
switch (type)
{
case EPaddingType::ePaddingNone:
return 0;
case EPaddingType::ePKCS_1_5:
return LTC_PKCS_1_V1_5;
case EPaddingType::ePKCS_1_5_NA1:
return LTC_PKCS_1_V1_5_NA1;
case EPaddingType::ePKCS_OAEP:
return LTC_PKCS_1_OAEP;
case EPaddingType::ePKCS_1_PSS:
return LTC_PKCS_1_PSS;
default:
return 0xFF;
}
}
static int HashMethodToId(EHashType type)
{
switch (type)
{
case EHashType::eTiger_24_192:
return ::Crypto::gHashTiger;
case EHashType::eSHA1_20_160:
return ::Crypto::gHashSha1;
case EHashType::eSHA2_32_256:
return ::Crypto::gHashSha256;
case EHashType::eSHA2_64_512:
return ::Crypto::gHashSha512;
default:
return 0xFF;
}
}
}

View File

@ -6,6 +6,7 @@
Author: Reece Author: Reece
***/ ***/
#pragma once #pragma once
#include "../Crypto.hpp"
namespace Aurora::Crypto::ECC namespace Aurora::Crypto::ECC
{ {

View File

@ -8,8 +8,58 @@
#include <RuntimeInternal.hpp> #include <RuntimeInternal.hpp>
#include "ECC.hpp" #include "ECC.hpp"
#include "ECCCurves.hpp" #include "ECCCurves.hpp"
#include <tomcrypt.h>
namespace Aurora::Crypto::ECC namespace Aurora::Crypto::ECC
{ {
static const ltc_ecc_curve kNistp256 =
{
/* prime */ "FFFFFFFF00000001000000000000000000000000FFFFFFFFFFFFFFFFFFFFFFFF",
/* A */ "FFFFFFFF00000001000000000000000000000000FFFFFFFFFFFFFFFFFFFFFFFC",
/* B */ "5AC635D8AA3A93E7B3EBBD55769886BC651D06B0CC53B0F63BCE3C3E27D2604B",
/* order */ "FFFFFFFF00000000FFFFFFFFFFFFFFFFBCE6FAADA7179E84F3B9CAC2FC632551",
/* Gx */ "6B17D1F2E12C4247F8BCE6E563A440F277037D812DEB33A0F4A13945D898C296",
/* Gy */ "4FE342E2FE1A7F9B8EE7EB4A7C0F9E162BCE33576B315ECECBB6406837BF51F5",
/* cofactor */ 1,
/* OID */ "1.2.840.10045.3.1.7"
};
static const ltc_ecc_curve kNistp384 =
{
/* prime */ "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFFFF0000000000000000FFFFFFFF",
/* A */ "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFFFF0000000000000000FFFFFFFC",
/* B */ "B3312FA7E23EE7E4988E056BE3F82D19181D9C6EFE8141120314088F5013875AC656398D8A2ED19D2A85C8EDD3EC2AEF",
/* order */ "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFC7634D81F4372DDF581A0DB248B0A77AECEC196ACCC52973",
/* Gx */ "AA87CA22BE8B05378EB1C71EF320AD746E1D3B628BA79B9859F741E082542A385502F25DBF55296C3A545E3872760AB7",
/* Gy */ "3617DE4A96262C6F5D9E98BF9292DC29F8F41DBD289A147CE9DA3113B5F0B8C00A60B1CE1D7E819D7A431D7C90EA0E5F",
/* cofactor */ 1,
/* OID */ "1.3.132.0.34"
};
static const ltc_ecc_curve kNistp521 =
{
/* prime */ "01FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF",
/* A */ "01FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFC",
/* B */ "0051953EB9618E1C9A1F929A21A0B68540EEA2DA725B99B315F3B8B489918EF109E156193951EC7E937B1652C0BD3BB1BF073573DF883D2C34F1EF451FD46B503F00",
/* order */ "01FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFA51868783BF2F966B7FCC0148F709A5D03BB5C9B8899C47AEBB6FB71E91386409",
/* Gx */ "00C6858E06B70404E9CD9E3ECB662395B4429C648139053FB521F828AF606B4D3DBAA14B5E77EFE75928FE1DC127A2FFA8DE3348B3C1856A429BF97E7E31C2E5BD66",
/* Gy */ "011839296A789A3BC0045C8A5FB42C7D1BD998F54449579B446817AFBD17273E662C97EE72995EF42640C550B9013FAD0761353C7086A272C24088BE94769FD16650",
/* cofactor */ 1,
/* OID */ "1.3.132.0.35"
};
AuOptional<const ltc_ecc_curve *> GetECCCurve(EECCCurve curve)
{
switch (curve)
{
case EECCCurve::eCurve256:
return &kNistp256;
case EECCCurve::eCurve384:
return &kNistp384;
case EECCCurve::eCurve521:
return &kNistp521;
default:
return {};
}
}
} }

View File

@ -9,5 +9,5 @@
namespace Aurora::Crypto::ECC namespace Aurora::Crypto::ECC
{ {
AuOptional<const ltc_ecc_curve *> GetECCCurve(EECCCurve curve);
} }

View File

@ -12,5 +12,347 @@
namespace Aurora::Crypto::ECC namespace Aurora::Crypto::ECC
{ {
static bool ExportECCKey(const ecc_key &key, bool pub, DerBuffer &out)
{
if (!AuTryResize(out, 4096))
{
return false;
}
unsigned long actualSize = out.size();
auto ret = ecc_export_openssl(out.data(), &actualSize, pub ? PK_PUBLIC : PK_PRIVATE, &key);
if (ret != CRYPT_OK)
{
SysPushErrorCrypt("{}", ret);
return false;
}
if (!AuTryResize(out, actualSize))
{
SysPushErrorMem();
return false;
}
return true;
}
class PublicECCImpl : public IECCPublic
{
public:
PublicECCImpl(EECCCurve type, ecc_key &key);
~PublicECCImpl();
bool Verify(const Memory::MemoryViewRead &hash,
const Memory::MemoryViewRead &signature) override;
bool Verify(const Memory::MemoryViewRead &plaintext,
const Memory::MemoryViewRead &signature,
EHashType method) override;
bool AsPublicECC(AuList<AuUInt8> &out) override;
bool Export(bool pub, DerBuffer &out);
EECCCurve GetType() override;
const ecc_key &GetKey();
private:
ecc_key _key;
EECCCurve _type;
};
PublicECCImpl::PublicECCImpl(EECCCurve type, ecc_key &key) : _key(key), _type(_type)
{
}
PublicECCImpl::~PublicECCImpl()
{
ecc_free(&_key);
}
EECCCurve PublicECCImpl::GetType()
{
return _type;
}
bool PublicECCImpl::Verify(const Memory::MemoryViewRead &hash,
const Memory::MemoryViewRead &signature)
{
int ok = 0;
if (!hash.HasMemory())
{
SysPushErrorParam();
return {};
}
if (!signature.HasMemory())
{
SysPushErrorParam();
return {};
}
auto ret = ecc_verify_hash_ex(reinterpret_cast<const unsigned char *>(hash.ptr), hash.length,
reinterpret_cast<const unsigned char *>(signature.ptr), signature.length,
LTC_ECCSIG_ETH27, &ok, &_key);
if (ret != CRYPT_OK)
{
SysPushErrorCrypt("{}", ret);
return false;
}
return ok == 1;
}
bool PublicECCImpl::Verify(const Memory::MemoryViewRead &plaintext,
const Memory::MemoryViewRead &signature,
EHashType method)
{
if (!plaintext.HasMemory())
{
SysPushErrorParam();
return {};
}
if (!signature.HasMemory())
{
SysPushErrorParam();
return {};
}
int hash = HashMethodToId(method);
if (hash == 0xFF)
{
SysPushErrorCrypt("invalid hash {}", method);
return false;
}
AuList<AuUInt8> hashVec;
if (!AuTryResize(hashVec, 128))
{
SysPushErrorMem();
return false;
}
unsigned long hashSize = hashVec.size();
auto ret = hash_memory(hash,
reinterpret_cast<const unsigned char *>(plaintext.ptr), plaintext.length,
reinterpret_cast<unsigned char *>(hashVec.data()), &hashSize);
if (ret != CRYPT_OK)
{
SysPushErrorCrypt("{}", ret);
return false;
}
return Verify({hashVec}, signature);
}
bool PublicECCImpl::AsPublicECC(AuList<AuUInt8> &out)
{
return Export(true, out);
}
bool PublicECCImpl::Export(bool pub, DerBuffer &out)
{
return ExportECCKey(_key, pub, out);
}
const ecc_key &PublicECCImpl::GetKey()
{
return _key;
}
class PrivateECCImpl : public IECCPrivate
{
public:
PrivateECCImpl(EECCCurve type, ecc_key &key);
~PrivateECCImpl();
bool Sign(const Memory::MemoryViewRead &plainText,
EHashType method,
AuList<AuUInt8> &out) override;
bool Sign(const Memory::MemoryViewRead &hash,
AuList<AuUInt8> &out) override;
bool ECDH(const AuSPtr<IECCPublic> &partnerPublic,
AuList<AuUInt8> &sharedKey) override;
bool AsPublicECC(AuList<AuUInt8> &out) override;
bool AsPrivateECC(AuList<AuUInt8> &out) override;
EECCCurve GetType() override;
private:
ecc_key _key;
EECCCurve _type;
};
PrivateECCImpl::PrivateECCImpl(EECCCurve type, ecc_key &key) : _key(key)
{
}
PrivateECCImpl::~PrivateECCImpl()
{
ecc_free(&_key);
}
EECCCurve PrivateECCImpl::GetType()
{
return _type;
}
bool PrivateECCImpl::Sign(const Memory::MemoryViewRead &plainText,
EHashType method,
AuList<AuUInt8> &out)
{
prng_state yarrow_prng;
const int salt = 0;
if (!plainText.HasMemory())
{
SysPushErrorParam();
return {};
}
int hash = HashMethodToId(method);
if (hash == 0xFF)
{
SysPushErrorCrypt("invalid hash {}", method);
return false;
}
if (!AuTryResize(out, 1024))
{
SysPushErrorMem();
return false;
}
AuList<AuUInt8> hashVec;
if (!AuTryResize(hashVec, 128))
{
SysPushErrorMem();
return false;
}
unsigned long hashSize = hashVec.size();
auto ret = hash_memory(hash,
reinterpret_cast<const unsigned char *>(plainText.ptr), plainText.length,
reinterpret_cast<unsigned char *>(hashVec.data()), &hashSize);
if (ret != CRYPT_OK)
{
SysPushErrorCrypt("{}", ret);
return false;
}
return Sign(hashVec, out);
}
bool PrivateECCImpl::Sign(const Memory::MemoryViewRead &hash,
AuList<AuUInt8> &out)
{
prng_state yarrow_prng;
const int salt = 0;
if (!hash.HasMemory())
{
SysPushErrorParam();
return {};
}
if (!AuTryResize(out, 1024))
{
SysPushErrorMem();
return false;
}
unsigned long len = out.size();
auto ret = ecc_sign_hash_ex(reinterpret_cast<const unsigned char *>(hash.ptr), hash.length,
out.data(), &len,
&yarrow_prng,
::Crypto::gPrngYarrow,
LTC_ECCSIG_ETH27,
nullptr,
&_key);
if (ret != CRYPT_OK)
{
SysPushErrorCrypt("{}", ret);
return false;
}
if (!AuTryResize(out, len))
{
SysPushErrorMem();
return false;
}
return true;
}
bool PrivateECCImpl::ECDH(const AuSPtr<IECCPublic> &partnerPublic,
AuList<AuUInt8> &sharedKey)
{
AuList<AuUInt8> sharedSecret;
if (!AuTryResize(sharedSecret, 128))
{
SysPushErrorMem();
return false;
}
if (partnerPublic->GetType() == this->GetType())
{
SysPushErrorCrypto("Can not EDCH with incompatible curve curve type (noting, ed25519 requires translation to x25519)");
return false;
}
unsigned long actualSize = sharedSecret.size();
auto ret = ecc_shared_secret(&_key, &(std::reinterpret_pointer_cast<PublicECCImpl>(partnerPublic)->GetKey()), sharedSecret.data(), &actualSize);
if (ret != CRYPT_OK)
{
SysPushErrorCrypt("{}", ret);
return false;
}
sharedSecret.resize(actualSize);
return true;
}
bool PrivateECCImpl::AsPublicECC(AuList<AuUInt8> &out)
{
return ExportECCKey(_key, true, out);
}
bool PrivateECCImpl::AsPrivateECC(AuList<AuUInt8> &out)
{
return ExportECCKey(_key, false, out);
}
template<typename Type_t>
static Type_t *NewECC(EECCCurve curve, const AuList<AuUInt8> &pub)
{
ecc_key in {};
auto ret = ecc_import_openssl(pub.data(), pub.size(), &in);
if (ret != CRYPT_OK)
{
SysPushErrorCrypto("{}", ret);
return nullptr;
}
auto out = _new Type_t(curve, in);
if (!out)
{
ecc_free(&in);
}
return out;
}
} }

View File

@ -6,9 +6,7 @@
Author: Reece Author: Reece
***/ ***/
#pragma once #pragma once
#include <tomcrypt.h> #include "../Crypto.hpp"
#include <Crypto.hpp>
#include <Extensions/LTC/LTCExtensions.hpp>
namespace Aurora::Crypto::RSA namespace Aurora::Crypto::RSA
{ {
@ -85,40 +83,4 @@ namespace Aurora::Crypto::RSA
return true; return true;
} }
static int PaddingToType(EPaddingType type)
{
switch (type)
{
case EPaddingType::ePaddingNone:
return 0;
case EPaddingType::ePKCS_1_5:
return LTC_PKCS_1_V1_5;
case EPaddingType::ePKCS_1_5_NA1:
return LTC_PKCS_1_V1_5_NA1;
case EPaddingType::ePKCS_OAEP:
return LTC_PKCS_1_OAEP;
case EPaddingType::ePKCS_1_PSS:
return LTC_PKCS_1_PSS;
default:
return 0xFF;
}
}
static int HashMethodToId(EHashType type)
{
switch (type)
{
case EHashType::eTiger_24_192:
return ::Crypto::gHashTiger;
case EHashType::eSHA1_20_160:
return ::Crypto::gHashSha1;
case EHashType::eSHA2_32_256:
return ::Crypto::gHashSha256;
case EHashType::eSHA2_64_512:
return ::Crypto::gHashSha512;
default:
return 0xFF;
}
}
} }

View File

@ -31,6 +31,12 @@ namespace Aurora::Crypto::RSA
prng_state yarrow_prng; prng_state yarrow_prng;
const int salt = 0; const int salt = 0;
if (!payload.HasMemory())
{
SysPushErrorParam();
return {};
}
int padding = PaddingToType(type); int padding = PaddingToType(type);
if (padding == 0xFF) if (padding == 0xFF)
{ {
@ -88,10 +94,16 @@ namespace Aurora::Crypto::RSA
return true; return true;
} }
bool PrivateRSA::Decrypt(const Memory::MemoryViewRead & payload, bool PrivateRSA::Decrypt(const Memory::MemoryViewRead &payload,
EPaddingType type, EPaddingType type,
AuList<AuUInt8> &out) AuList<AuUInt8> &out)
{ {
if (!payload.HasMemory())
{
SysPushErrorParam();
return {};
}
int padding = PaddingToType(type); int padding = PaddingToType(type);
if (padding == 0xFF) if (padding == 0xFF)
{ {

View File

@ -25,11 +25,24 @@ namespace Aurora::Crypto::RSA
} }
} }
bool PublicRSA::Verify(const Memory::MemoryViewRead & payload, bool PublicRSA::Verify(const Memory::MemoryViewRead &payload,
const Memory::MemoryViewRead & signature, const Memory::MemoryViewRead &signature,
EHashType method, EHashType method,
EPaddingType type) EPaddingType type)
{ {
if (!payload.HasMemory())
{
SysPushErrorParam();
return {};
}
if (!signature.HasMemory())
{
SysPushErrorParam();
return {};
}
int padding = PaddingToType(type); int padding = PaddingToType(type);
if (padding == 0xFF) if (padding == 0xFF)
{ {
@ -75,12 +88,18 @@ namespace Aurora::Crypto::RSA
return ok == 1; return ok == 1;
} }
bool PublicRSA::Encrypt(const Memory::MemoryViewRead & plainText, bool PublicRSA::Encrypt(const Memory::MemoryViewRead &plainText,
EPaddingType type, EPaddingType type,
AuList<AuUInt8> &out) AuList<AuUInt8> &out)
{ {
prng_state yarrow_prng; prng_state yarrow_prng;
if (!plainText.HasMemory())
{
SysPushErrorParam();
return {};
}
int padding = PaddingToType(type); int padding = PaddingToType(type);
if (padding == 0xFF) if (padding == 0xFF)
{ {

View File

@ -120,7 +120,6 @@ namespace Aurora::IO::FS
return true; return true;
} }
AuSPtr<FileHandle> NtAsyncFileStream::GetHandle() AuSPtr<FileHandle> NtAsyncFileStream::GetHandle()
{ {
return handle_; return handle_;
@ -184,6 +183,10 @@ namespace Aurora::IO::FS
bool NtAsyncFileTransaction::StartRead(AuUInt64 offset, void *buffer, AuUInt32 length) bool NtAsyncFileTransaction::StartRead(AuUInt64 offset, void *buffer, AuUInt32 length)
{ {
if (this->latch_)
{
return {};
}
this->latch_ = {}; this->latch_ = {};
this->lastAbstractStat_ = length; this->lastAbstractStat_ = length;
this->lastAbstractOffset_ = offset; this->lastAbstractOffset_ = offset;
@ -196,6 +199,10 @@ namespace Aurora::IO::FS
bool NtAsyncFileTransaction::StartWrite(AuUInt64 offset, const void *buffer, AuUInt32 length) bool NtAsyncFileTransaction::StartWrite(AuUInt64 offset, const void *buffer, AuUInt32 length)
{ {
if (this->latch_)
{
return {};
}
this->latch_ = {}; this->latch_ = {};
this->lastAbstractStat_ = length; this->lastAbstractStat_ = length;
this->lastAbstractOffset_ = offset; this->lastAbstractOffset_ = offset;

View File

@ -86,10 +86,10 @@ Problem one:
Problem Two: Problem Two:
Moving to or from linux, macos, bsd, and win32 under varous kernels, there is no one Moving to or from linux, macos, bsd, and win32 under varous kernels, there is no one
standard (even in posix land) for the key thread primitives everybody be using. standard (even in posix land) for the key thread primitives.
Bonus point NT: Bonus point NT:
The userland CriticalSection set of APIs generally suck, lacking timeouts and try lock The userland CriticalSection/CV set of APIs suck, lacking timeouts and try lock
Bonus point UNIX: Bonus point UNIX:
No wait multiple mechanism No wait multiple mechanism
@ -134,21 +134,23 @@ The networking stack supports a handful of architectural paradigms
We suspect most developers delegate IO to a worker thread, don't wish to deal with an extern We suspect most developers delegate IO to a worker thread, don't wish to deal with an extern
async model nor want excessively buffered streams, therefore the FIO API implements a read/write async model nor want excessively buffered streams, therefore the FIO API implements a read/write
seekable C-like interface in a file stream object. An alternative AFIO namespace exists for the seekable C-like file stream interface. An alternative AFIO namespace exists for the few platforms
few platforms that provide posix AIO, win32 overlap, or linux's io syscalls. that provide posix AIO, win32 overlap, or linux's io syscalls.
File stream, buffered read/write utilities, stat, exists, copy, move, remove, and itr backed File stream, buffered read/write utilities, stat, exists, copy, move, remove, and readdir backed
by the best platform specific blocking apis. by the best platform specific blocking apis.
Guaranteed 64-bit file pointer safety across seek functions. Guaranteed 64-bit file pointer safety across seek functions.
[Open]Write to a file under a path of missing directories guarantees creation of missing sub [Open]Write to a file under a path of missing directories guarantees creation of missing sub
directorieis. directories.
### Paths ### Paths
We assume all paths are messy. Incorrect splitters, double splitters, relative paths, and We assume all paths are messy. Incorrect splitters, double splitters, relative paths, and
keywords are resolved internally. No such URL or path builder, data structure to hold a keywords are resolved internally. No such URL or path builder, data structure to hold a
tokenized representation, or similar concept exists in the codebase. All string 'paths' are tokenized representation, or similar concept exists in the codebase. All string 'paths' are
simply expanded, similar to 'fullpath', at time of usage. simply expanded, similar to MSCRT 'fullpath'/UNIX 'realpath', at time of usage.
Path tokens include: Path tokens include:
[0] == '.' = cwd [0] == '.' = cwd
@ -184,14 +186,15 @@ process spawning, file opening, and url opening functionality.
## Locale ## Locale
Encoding and decoding UTF-8, UTF-16, UTF-32, GBK, GB-2312, and SJIS support using platform Encoding and decoding UTF-8, UTF-16, UTF-32, GBK, GB-2312, and SJIS support using platform
specific APIs. Fetch system language and country backed by environment variables, platform specific APIs. Fetch system language and country backed by environment variables, the OS
specific apis, the unix locale env variable, and/or the provided overload mechanism. system configuration, the unix locale env variable, and/or the provided overload mechanism.
## Philosophies ## Philosophies
- Assume C++17 language support in the language driver - Assume C++17 language support in the language driver
- To avoid reinventing the wheel, solve the large issues nobody is tackling - To avoid reinventing the wheel, solve the large issues nobody is tackling, and accept
third party solutions weighted against relevant legal constraints and developer time
- Use AuXXX type bindings for std types, allow customers to overload the std namespace - Use AuXXX type bindings for std types, allow customers to overload the std namespace
@ -220,4 +223,4 @@ specific apis, the unix locale env variable, and/or the provided overload mechan
-> Writing a [D]TLS/allocator stack would take too much time -> Writing a [D]TLS/allocator stack would take too much time
-> Linking against external allocators, small cross-platform utilities, and -> Linking against external allocators, small cross-platform utilities, and
so on is probably fine so on is probably fine
-> Feel free to shim libcurl instead of inventing yet another http stack -> Shim libcurl instead of inventing yet another http stack