mirror of
https://github.com/MariaDB/server.git
synced 2025-01-17 04:22:27 +01:00
f0aacbca63
- Replace SawTooth copyright header with MySQL's - Bug#19209 Test 'rpl_openssl' hangs on Windows - Spurious "2013 Connection to server lost" errors fixed yaSSL doesn't close socket anymore, that is left to the application extra/yassl/README: Import patch yassl.diff extra/yassl/include/buffer.hpp: Import patch yassl.diff extra/yassl/include/cert_wrapper.hpp: Import patch yassl.diff extra/yassl/include/crypto_wrapper.hpp: Import patch yassl.diff extra/yassl/include/factory.hpp: Import patch yassl.diff extra/yassl/include/handshake.hpp: Import patch yassl.diff extra/yassl/include/lock.hpp: Import patch yassl.diff extra/yassl/include/log.hpp: Import patch yassl.diff extra/yassl/include/openssl/ssl.h: Import patch yassl.diff extra/yassl/include/socket_wrapper.hpp: Import patch yassl.diff extra/yassl/include/timer.hpp: Import patch yassl.diff extra/yassl/include/yassl.hpp: Import patch yassl.diff extra/yassl/include/yassl_error.hpp: Import patch yassl.diff extra/yassl/include/yassl_imp.hpp: Import patch yassl.diff extra/yassl/include/yassl_int.hpp: Import patch yassl.diff extra/yassl/include/yassl_types.hpp: Import patch yassl.diff extra/yassl/src/buffer.cpp: Import patch yassl.diff extra/yassl/src/cert_wrapper.cpp: Import patch yassl.diff extra/yassl/src/crypto_wrapper.cpp: Import patch yassl.diff extra/yassl/src/handshake.cpp: Import patch yassl.diff extra/yassl/src/lock.cpp: Import patch yassl.diff extra/yassl/src/log.cpp: Import patch yassl.diff extra/yassl/src/socket_wrapper.cpp: Import patch yassl.diff extra/yassl/src/ssl.cpp: Import patch yassl.diff extra/yassl/src/template_instnt.cpp: Import patch yassl.diff extra/yassl/src/timer.cpp: Import patch yassl.diff extra/yassl/src/yassl.cpp: Import patch yassl.diff extra/yassl/src/yassl_error.cpp: Import patch yassl.diff extra/yassl/src/yassl_imp.cpp: Import patch yassl.diff extra/yassl/src/yassl_int.cpp: Import patch yassl.diff extra/yassl/taocrypt/include/aes.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/algebra.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/arc4.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/asn.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/block.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/blowfish.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/coding.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/des.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/dh.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/dsa.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/error.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/file.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/hash.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/hmac.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/integer.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/kernelc.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/md2.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/md4.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/md5.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/misc.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/modarith.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/modes.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/pwdbased.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/random.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/ripemd.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/rsa.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/runtime.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/sha.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/twofish.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/type_traits.hpp: Import patch yassl.diff extra/yassl/taocrypt/include/types.hpp: Import patch yassl.diff extra/yassl/taocrypt/mySTL/algorithm.hpp: Import patch yassl.diff extra/yassl/taocrypt/mySTL/helpers.hpp: Import patch yassl.diff extra/yassl/taocrypt/mySTL/list.hpp: Import patch yassl.diff extra/yassl/taocrypt/mySTL/memory.hpp: Import patch yassl.diff extra/yassl/taocrypt/mySTL/memory_array.hpp: Import patch yassl.diff extra/yassl/taocrypt/mySTL/pair.hpp: Import patch yassl.diff extra/yassl/taocrypt/mySTL/stdexcept.hpp: Import patch yassl.diff extra/yassl/taocrypt/mySTL/vector.hpp: Import patch yassl.diff extra/yassl/taocrypt/src/aes.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/aestables.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/algebra.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/arc4.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/asn.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/bftables.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/blowfish.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/coding.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/crypto.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/des.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/dh.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/dsa.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/file.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/hash.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/integer.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/md2.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/md4.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/md5.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/misc.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/random.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/ripemd.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/rsa.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/sha.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/template_instnt.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/tftables.cpp: Import patch yassl.diff extra/yassl/taocrypt/src/twofish.cpp: Import patch yassl.diff
682 lines
19 KiB
C++
682 lines
19 KiB
C++
/*
|
|
Copyright (C) 2000-2007 MySQL AB
|
|
|
|
This program is free software; you can redistribute it and/or modify
|
|
it under the terms of the GNU General Public License as published by
|
|
the Free Software Foundation; version 2 of the License.
|
|
|
|
This program is distributed in the hope that it will be useful,
|
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
GNU General Public License for more details.
|
|
|
|
You should have received a copy of the GNU General Public License
|
|
along with this program; see the file COPYING. If not, write to the
|
|
Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston,
|
|
MA 02110-1301 USA.
|
|
*/
|
|
|
|
|
|
/* yaSSL internal header defines SSL supporting types not specified in the
|
|
* draft along with type conversion functions and openssl compatibility
|
|
*/
|
|
|
|
|
|
#ifndef yaSSL_INT_HPP
|
|
#define yaSSL_INT_HPP
|
|
|
|
#include "yassl_imp.hpp"
|
|
#include "yassl_error.hpp"
|
|
#include "crypto_wrapper.hpp"
|
|
#include "cert_wrapper.hpp"
|
|
#include "log.hpp"
|
|
#include "lock.hpp"
|
|
#include "openssl/ssl.h" // ASN1_STRING and DH
|
|
|
|
// Check if _POSIX_THREADS should be forced
|
|
#if !defined(_POSIX_THREADS) && (defined(__NETWARE__) || defined(__hpux))
|
|
// HPUX does not define _POSIX_THREADS as it's not _fully_ implemented
|
|
// Netware supports pthreads but does not announce it
|
|
#define _POSIX_THREADS
|
|
#endif
|
|
|
|
#ifdef _POSIX_THREADS
|
|
#include <pthread.h>
|
|
#endif
|
|
|
|
|
|
namespace STL = STL_NAMESPACE;
|
|
|
|
|
|
namespace yaSSL {
|
|
|
|
|
|
// State Machine for Record Layer Protocol
|
|
enum RecordLayerState {
|
|
recordNotReady = 0, // fatal error, no more processing
|
|
recordReady
|
|
};
|
|
|
|
|
|
// State Machine for HandShake Protocol
|
|
enum HandShakeState {
|
|
handShakeNotReady = 0, // fatal error, no more processing
|
|
preHandshake, // initial state
|
|
inHandshake, // handshake started
|
|
handShakeReady // handshake done
|
|
};
|
|
|
|
|
|
// client input HandShake state, use if HandShakeState == inHandShake
|
|
enum ClientState {
|
|
serverNull = 0,
|
|
serverHelloComplete,
|
|
serverCertComplete,
|
|
serverKeyExchangeComplete,
|
|
serverHelloDoneComplete,
|
|
serverFinishedComplete
|
|
};
|
|
|
|
|
|
// server input HandShake state, use if HandShakeState == inHandShake
|
|
enum ServerState {
|
|
clientNull = 0,
|
|
clientHelloComplete,
|
|
clientKeyExchangeComplete,
|
|
clientFinishedComplete
|
|
};
|
|
|
|
|
|
// client connect state for nonblocking restart
|
|
enum ConnectState {
|
|
CONNECT_BEGIN = 0,
|
|
CLIENT_HELLO_SENT,
|
|
FIRST_REPLY_DONE,
|
|
FINISHED_DONE,
|
|
SECOND_REPLY_DONE
|
|
};
|
|
|
|
|
|
// server accpet state for nonblocking restart
|
|
enum AcceptState {
|
|
ACCEPT_BEGIN = 0,
|
|
ACCEPT_FIRST_REPLY_DONE,
|
|
SERVER_HELLO_DONE,
|
|
ACCEPT_SECOND_REPLY_DONE,
|
|
ACCEPT_FINISHED_DONE,
|
|
ACCEPT_THIRD_REPLY_DONE
|
|
};
|
|
|
|
|
|
// combines all states
|
|
class States {
|
|
RecordLayerState recordLayer_;
|
|
HandShakeState handshakeLayer_;
|
|
ClientState clientState_;
|
|
ServerState serverState_;
|
|
ConnectState connectState_;
|
|
AcceptState acceptState_;
|
|
char errorString_[MAX_ERROR_SZ];
|
|
YasslError what_;
|
|
public:
|
|
States();
|
|
|
|
const RecordLayerState& getRecord() const;
|
|
const HandShakeState& getHandShake() const;
|
|
const ClientState& getClient() const;
|
|
const ServerState& getServer() const;
|
|
const ConnectState& GetConnect() const;
|
|
const AcceptState& GetAccept() const;
|
|
const char* getString() const;
|
|
YasslError What() const;
|
|
|
|
RecordLayerState& useRecord();
|
|
HandShakeState& useHandShake();
|
|
ClientState& useClient();
|
|
ServerState& useServer();
|
|
ConnectState& UseConnect();
|
|
AcceptState& UseAccept();
|
|
char* useString();
|
|
void SetError(YasslError);
|
|
private:
|
|
States(const States&); // hide copy
|
|
States& operator=(const States&); // and assign
|
|
};
|
|
|
|
|
|
// holds all factories
|
|
class sslFactory {
|
|
MessageFactory messageFactory_; // creates new messages by type
|
|
HandShakeFactory handShakeFactory_; // creates new handshake types
|
|
ServerKeyFactory serverKeyFactory_; // creates new server key types
|
|
ClientKeyFactory clientKeyFactory_; // creates new client key types
|
|
|
|
sslFactory(); // only GetSSL_Factory creates
|
|
public:
|
|
const MessageFactory& getMessage() const;
|
|
const HandShakeFactory& getHandShake() const;
|
|
const ServerKeyFactory& getServerKey() const;
|
|
const ClientKeyFactory& getClientKey() const;
|
|
|
|
friend sslFactory& GetSSL_Factory(); // singleton creator
|
|
private:
|
|
sslFactory(const sslFactory&); // hide copy
|
|
sslFactory& operator=(const sslFactory&); // and assign
|
|
};
|
|
|
|
|
|
#undef X509_NAME // wincrypt.h clash
|
|
|
|
// openSSL X509 names
|
|
class X509_NAME {
|
|
char* name_;
|
|
size_t sz_;
|
|
ASN1_STRING entry_;
|
|
public:
|
|
X509_NAME(const char*, size_t sz);
|
|
~X509_NAME();
|
|
|
|
const char* GetName() const;
|
|
ASN1_STRING* GetEntry(int i);
|
|
size_t GetLength() const;
|
|
private:
|
|
X509_NAME(const X509_NAME&); // hide copy
|
|
X509_NAME& operator=(const X509_NAME&); // and assign
|
|
};
|
|
|
|
|
|
class StringHolder {
|
|
ASN1_STRING asnString_;
|
|
public:
|
|
StringHolder(const char* str, int sz);
|
|
~StringHolder();
|
|
|
|
ASN1_STRING* GetString();
|
|
private:
|
|
StringHolder(const StringHolder&); // hide copy
|
|
StringHolder& operator=(const StringHolder&); // and assign
|
|
};
|
|
|
|
|
|
// openSSL X509
|
|
class X509 {
|
|
X509_NAME issuer_;
|
|
X509_NAME subject_;
|
|
StringHolder beforeDate_; // not valid before
|
|
StringHolder afterDate_; // not valid after
|
|
public:
|
|
X509(const char* i, size_t, const char* s, size_t,
|
|
const char* b, int, const char* a, int);
|
|
~X509() {}
|
|
|
|
X509_NAME* GetIssuer();
|
|
X509_NAME* GetSubject();
|
|
|
|
ASN1_STRING* GetBefore();
|
|
ASN1_STRING* GetAfter();
|
|
|
|
private:
|
|
X509(const X509&); // hide copy
|
|
X509& operator=(const X509&); // and assign
|
|
};
|
|
|
|
|
|
// openSSL bignum
|
|
struct BIGNUM {
|
|
/*
|
|
gcc 2.96 fix: because of two Integer classes (yaSSL::Integer and
|
|
TaoCrypt::Integer), we need to explicitly state the namespace
|
|
here to let gcc 2.96 deduce the correct type.
|
|
*/
|
|
yaSSL::Integer int_;
|
|
void assign(const byte* b, uint s) { int_.assign(b,s); }
|
|
};
|
|
|
|
|
|
// openSSL session
|
|
class SSL_SESSION {
|
|
opaque sessionID_[ID_LEN];
|
|
opaque master_secret_[SECRET_LEN];
|
|
Cipher suite_[SUITE_LEN];
|
|
uint bornOn_; // create time in seconds
|
|
uint timeout_; // timeout in seconds
|
|
RandomPool& random_; // will clean master secret
|
|
X509* peerX509_;
|
|
public:
|
|
explicit SSL_SESSION(RandomPool&);
|
|
SSL_SESSION(const SSL&, RandomPool&);
|
|
~SSL_SESSION();
|
|
|
|
const opaque* GetID() const;
|
|
const opaque* GetSecret() const;
|
|
const Cipher* GetSuite() const;
|
|
uint GetBornOn() const;
|
|
uint GetTimeOut() const;
|
|
X509* GetPeerX509() const;
|
|
void SetTimeOut(uint);
|
|
|
|
SSL_SESSION& operator=(const SSL_SESSION&); // allow assign for resumption
|
|
private:
|
|
SSL_SESSION(const SSL_SESSION&); // hide copy
|
|
|
|
void CopyX509(X509*);
|
|
};
|
|
|
|
|
|
// holds all sessions
|
|
class Sessions {
|
|
STL::list<SSL_SESSION*> list_;
|
|
RandomPool random_; // for session cleaning
|
|
Mutex mutex_; // no-op for single threaded
|
|
|
|
Sessions() {} // only GetSessions can create
|
|
public:
|
|
SSL_SESSION* lookup(const opaque*, SSL_SESSION* copy = 0);
|
|
void add(const SSL&);
|
|
void remove(const opaque*);
|
|
|
|
~Sessions();
|
|
|
|
friend Sessions& GetSessions(); // singleton creator
|
|
private:
|
|
Sessions(const Sessions&); // hide copy
|
|
Sessions& operator=(const Sessions&); // and assign
|
|
};
|
|
|
|
|
|
#ifdef _POSIX_THREADS
|
|
typedef pthread_t THREAD_ID_T;
|
|
#else
|
|
typedef DWORD THREAD_ID_T;
|
|
#endif
|
|
|
|
// thread error data
|
|
struct ThreadError {
|
|
THREAD_ID_T threadID_;
|
|
int errorID_;
|
|
};
|
|
|
|
|
|
// holds all errors
|
|
class Errors {
|
|
STL::list<ThreadError> list_;
|
|
Mutex mutex_;
|
|
|
|
Errors() {} // only GetErrors can create
|
|
public:
|
|
int Lookup(bool peek); // self lookup
|
|
void Add(int);
|
|
void Remove(); // remove self
|
|
|
|
~Errors() {}
|
|
|
|
friend Errors& GetErrors(); // singleton creator
|
|
private:
|
|
Errors(const Errors&); // hide copy
|
|
Errors& operator=(const Errors); // and assign
|
|
};
|
|
|
|
|
|
Sessions& GetSessions(); // forward singletons
|
|
sslFactory& GetSSL_Factory();
|
|
Errors& GetErrors();
|
|
|
|
|
|
// openSSL method and context types
|
|
class SSL_METHOD {
|
|
ProtocolVersion version_;
|
|
ConnectionEnd side_;
|
|
bool verifyPeer_; // request or send certificate
|
|
bool verifyNone_; // whether to verify certificate
|
|
bool failNoCert_;
|
|
bool multipleProtocol_; // for SSLv23 compatibility
|
|
public:
|
|
SSL_METHOD(ConnectionEnd ce, ProtocolVersion pv,
|
|
bool multipleProtocol = false);
|
|
|
|
ProtocolVersion getVersion() const;
|
|
ConnectionEnd getSide() const;
|
|
|
|
void setVerifyPeer();
|
|
void setVerifyNone();
|
|
void setFailNoCert();
|
|
|
|
bool verifyPeer() const;
|
|
bool verifyNone() const;
|
|
bool failNoCert() const;
|
|
bool multipleProtocol() const;
|
|
private:
|
|
SSL_METHOD(const SSL_METHOD&); // hide copy
|
|
SSL_METHOD& operator=(const SSL_METHOD&); // and assign
|
|
};
|
|
|
|
|
|
struct Ciphers {
|
|
bool setSuites_; // user set suites from default
|
|
byte suites_[MAX_SUITE_SZ]; // new suites
|
|
int suiteSz_; // suite length in bytes
|
|
|
|
Ciphers() : setSuites_(false), suiteSz_(0) {}
|
|
};
|
|
|
|
|
|
struct DH; // forward
|
|
|
|
|
|
// save for SSL construction
|
|
struct DH_Parms {
|
|
Integer p_;
|
|
Integer g_;
|
|
bool set_; // if set by user
|
|
|
|
DH_Parms() : set_(false) {}
|
|
};
|
|
|
|
|
|
enum StatsField {
|
|
Accept, Connect, AcceptGood, ConnectGood, AcceptRenegotiate,
|
|
ConnectRenegotiate, Hits, CbHits, CacheFull, Misses, Timeouts, Number,
|
|
GetCacheSize, VerifyMode, VerifyDepth
|
|
};
|
|
|
|
|
|
// SSL stats
|
|
struct Stats {
|
|
long accept_;
|
|
long connect_;
|
|
long acceptGood_;
|
|
long connectGood_;
|
|
long acceptRenegotiate_;
|
|
long connectRenegotiate_;
|
|
|
|
long hits_;
|
|
long cbHits_;
|
|
long cacheFull_;
|
|
long misses_;
|
|
long timeouts_;
|
|
long number_;
|
|
long getCacheSize_;
|
|
|
|
int verifyMode_;
|
|
int verifyDepth_;
|
|
public:
|
|
Stats() : accept_(0), connect_(0), acceptGood_(0), connectGood_(0),
|
|
acceptRenegotiate_(0), connectRenegotiate_(0), hits_(0), cbHits_(0),
|
|
cacheFull_(0), misses_(0), timeouts_(0), number_(0), getCacheSize_(0),
|
|
verifyMode_(0), verifyDepth_(0)
|
|
{}
|
|
private:
|
|
Stats(const Stats&); // hide copy
|
|
Stats& operator=(const Stats&); // and assign
|
|
};
|
|
|
|
|
|
// the SSL context
|
|
class SSL_CTX {
|
|
public:
|
|
typedef STL::list<x509*> CertList;
|
|
private:
|
|
SSL_METHOD* method_;
|
|
x509* certificate_;
|
|
x509* privateKey_;
|
|
CertList caList_;
|
|
Ciphers ciphers_;
|
|
DH_Parms dhParms_;
|
|
pem_password_cb passwordCb_;
|
|
void* userData_;
|
|
bool sessionCacheOff_;
|
|
Stats stats_;
|
|
Mutex mutex_; // for Stats
|
|
public:
|
|
explicit SSL_CTX(SSL_METHOD* meth);
|
|
~SSL_CTX();
|
|
|
|
const x509* getCert() const;
|
|
const x509* getKey() const;
|
|
const SSL_METHOD* getMethod() const;
|
|
const Ciphers& GetCiphers() const;
|
|
const DH_Parms& GetDH_Parms() const;
|
|
const Stats& GetStats() const;
|
|
pem_password_cb GetPasswordCb() const;
|
|
void* GetUserData() const;
|
|
bool GetSessionCacheOff() const;
|
|
|
|
void setVerifyPeer();
|
|
void setVerifyNone();
|
|
void setFailNoCert();
|
|
bool SetCipherList(const char*);
|
|
bool SetDH(const DH&);
|
|
void SetPasswordCb(pem_password_cb cb);
|
|
void SetUserData(void*);
|
|
void SetSessionCacheOff();
|
|
|
|
void IncrementStats(StatsField);
|
|
void AddCA(x509* ca);
|
|
const CertList& GetCA_List() const;
|
|
|
|
friend int read_file(SSL_CTX*, const char*, int, CertType);
|
|
private:
|
|
SSL_CTX(const SSL_CTX&); // hide copy
|
|
SSL_CTX& operator=(const SSL_CTX&); // and assign
|
|
};
|
|
|
|
|
|
// holds all cryptographic types
|
|
class Crypto {
|
|
Digest* digest_; // agreed upon digest
|
|
BulkCipher* cipher_; // agreed upon cipher
|
|
DiffieHellman* dh_; // dh parms
|
|
RandomPool random_; // random number generator
|
|
CertManager cert_; // manages certificates
|
|
public:
|
|
explicit Crypto();
|
|
~Crypto();
|
|
|
|
const Digest& get_digest() const;
|
|
const BulkCipher& get_cipher() const;
|
|
const DiffieHellman& get_dh() const;
|
|
const RandomPool& get_random() const;
|
|
const CertManager& get_certManager() const;
|
|
|
|
Digest& use_digest();
|
|
BulkCipher& use_cipher();
|
|
DiffieHellman& use_dh();
|
|
RandomPool& use_random();
|
|
CertManager& use_certManager();
|
|
|
|
void SetDH(DiffieHellman*);
|
|
void SetDH(const DH_Parms&);
|
|
void setDigest(Digest*);
|
|
void setCipher(BulkCipher*);
|
|
|
|
bool DhSet();
|
|
private:
|
|
Crypto(const Crypto&); // hide copy
|
|
Crypto& operator=(const Crypto&); // and assign
|
|
};
|
|
|
|
|
|
// holds all handshake and verify hashes
|
|
class sslHashes {
|
|
MD5 md5HandShake_; // md5 handshake hash
|
|
SHA shaHandShake_; // sha handshake hash
|
|
Finished verify_; // peer's verify hash
|
|
Hashes certVerify_; // peer's cert verify hash
|
|
public:
|
|
sslHashes() {}
|
|
|
|
const MD5& get_MD5() const;
|
|
const SHA& get_SHA() const;
|
|
const Finished& get_verify() const;
|
|
const Hashes& get_certVerify() const;
|
|
|
|
MD5& use_MD5();
|
|
SHA& use_SHA();
|
|
Finished& use_verify();
|
|
Hashes& use_certVerify();
|
|
private:
|
|
sslHashes(const sslHashes&); // hide copy
|
|
sslHashes& operator=(const sslHashes&); // and assign
|
|
};
|
|
|
|
|
|
// holds input and output buffers
|
|
class Buffers {
|
|
public:
|
|
typedef STL::list<input_buffer*> inputList;
|
|
typedef STL::list<output_buffer*> outputList;
|
|
private:
|
|
inputList dataList_; // list of users app data / handshake
|
|
outputList handShakeList_; // buffered handshake msgs
|
|
input_buffer* rawInput_; // buffered raw input yet to process
|
|
public:
|
|
Buffers();
|
|
~Buffers();
|
|
|
|
const inputList& getData() const;
|
|
const outputList& getHandShake() const;
|
|
|
|
inputList& useData();
|
|
outputList& useHandShake();
|
|
|
|
void SetRawInput(input_buffer*); // takes ownership
|
|
input_buffer* TakeRawInput(); // takes ownership
|
|
private:
|
|
Buffers(const Buffers&); // hide copy
|
|
Buffers& operator=(const Buffers&); // and assign
|
|
};
|
|
|
|
|
|
// wraps security parameters
|
|
class Security {
|
|
Connection conn_; // connection information
|
|
Parameters parms_; // may be pending
|
|
SSL_SESSION resumeSession_; // if resuming
|
|
SSL_CTX* ctx_; // context used to init
|
|
bool resuming_; // trying to resume
|
|
public:
|
|
Security(ProtocolVersion, RandomPool&, ConnectionEnd, const Ciphers&,
|
|
SSL_CTX*, bool);
|
|
|
|
const SSL_CTX* GetContext() const;
|
|
const Connection& get_connection() const;
|
|
const Parameters& get_parms() const;
|
|
const SSL_SESSION& get_resume() const;
|
|
bool get_resuming() const;
|
|
|
|
Connection& use_connection();
|
|
Parameters& use_parms();
|
|
SSL_SESSION& use_resume();
|
|
|
|
void set_resuming(bool b);
|
|
private:
|
|
Security(const Security&); // hide copy
|
|
Security& operator=(const Security&); // and assign
|
|
};
|
|
|
|
|
|
// THE SSL type
|
|
class SSL {
|
|
Crypto crypto_; // agreed crypto agents
|
|
Security secure_; // Connection and Session parms
|
|
States states_; // Record and HandShake states
|
|
sslHashes hashes_; // handshake, finished hashes
|
|
Socket socket_; // socket wrapper
|
|
Buffers buffers_; // buffered handshakes and data
|
|
Log log_; // logger
|
|
|
|
// optimization variables
|
|
bool has_data_; // buffered data ready?
|
|
public:
|
|
SSL(SSL_CTX* ctx);
|
|
|
|
// gets and uses
|
|
const Crypto& getCrypto() const;
|
|
const Security& getSecurity() const;
|
|
const States& getStates() const;
|
|
const sslHashes& getHashes() const;
|
|
const sslFactory& getFactory() const;
|
|
const Socket& getSocket() const;
|
|
YasslError GetError() const;
|
|
bool GetMultiProtocol() const;
|
|
bool CompressionOn() const;
|
|
|
|
Crypto& useCrypto();
|
|
Security& useSecurity();
|
|
States& useStates();
|
|
sslHashes& useHashes();
|
|
Socket& useSocket();
|
|
Log& useLog();
|
|
Buffers& useBuffers();
|
|
|
|
bool HasData() const;
|
|
|
|
// sets
|
|
void set_pending(Cipher suite);
|
|
void set_random(const opaque*, ConnectionEnd);
|
|
void set_sessionID(const opaque*);
|
|
void set_session(SSL_SESSION*);
|
|
void set_preMaster(const opaque*, uint);
|
|
void set_masterSecret(const opaque*);
|
|
void SetError(YasslError);
|
|
int SetCompression();
|
|
void UnSetCompression();
|
|
|
|
// helpers
|
|
bool isTLS() const;
|
|
bool isTLSv1_1() const;
|
|
void order_error();
|
|
void makeMasterSecret();
|
|
void makeTLSMasterSecret();
|
|
void addData(input_buffer* data);
|
|
void fillData(Data&);
|
|
void PeekData(Data&);
|
|
void addBuffer(output_buffer* b);
|
|
void flushBuffer();
|
|
void verifyState(const RecordLayerHeader&);
|
|
void verifyState(const HandShakeHeader&);
|
|
void verifyState(ClientState);
|
|
void verifyState(ServerState);
|
|
void verfiyHandShakeComplete();
|
|
void matchSuite(const opaque*, uint length);
|
|
void deriveKeys();
|
|
void deriveTLSKeys();
|
|
void Send(const byte*, uint);
|
|
|
|
uint bufferedData();
|
|
uint get_SEQIncrement(bool);
|
|
|
|
const byte* get_macSecret(bool);
|
|
private:
|
|
void storeKeys(const opaque*);
|
|
void setKeys();
|
|
void verifyClientState(HandShakeType);
|
|
void verifyServerState(HandShakeType);
|
|
|
|
SSL(const SSL&); // hide copy
|
|
const SSL& operator=(const SSL&); // and assign
|
|
};
|
|
|
|
|
|
// compression
|
|
int Compress(const byte*, int, input_buffer&);
|
|
int DeCompress(input_buffer&, int, input_buffer&);
|
|
|
|
|
|
// conversion functions
|
|
void c32to24(uint32, uint24&);
|
|
void c24to32(const uint24, uint32&);
|
|
|
|
uint32 c24to32(const uint24);
|
|
|
|
void ato16(const opaque*, uint16&);
|
|
void ato24(const opaque*, uint24&);
|
|
|
|
void c16toa(uint16, opaque*);
|
|
void c24toa(const uint24, opaque*);
|
|
void c32toa(uint32 u32, opaque*);
|
|
|
|
|
|
} // naemspace
|
|
|
|
#endif // yaSSL_INT_HPP
|