summaryrefslogtreecommitdiff
path: root/src/node_crypto.h
diff options
context:
space:
mode:
authorFedor Indutny <fedor.indutny@gmail.com>2012-07-07 16:20:23 -0400
committerFedor Indutny <fedor.indutny@gmail.com>2012-09-05 02:01:54 +0400
commit8e0c830cd0038577e36456d3e027a4150d68c933 (patch)
treefbd197fd1d8447aaa63a9897b240b5a61a4336fa /src/node_crypto.h
parent790d651f0dfae13f1e2b799820ab18ac09f251b7 (diff)
downloadnode-new-8e0c830cd0038577e36456d3e027a4150d68c933.tar.gz
tls: async session storage
Diffstat (limited to 'src/node_crypto.h')
-rw-r--r--src/node_crypto.h71
1 files changed, 70 insertions, 1 deletions
diff --git a/src/node_crypto.h b/src/node_crypto.h
index fe433596ac..91fbb2249b 100644
--- a/src/node_crypto.h
+++ b/src/node_crypto.h
@@ -49,6 +49,9 @@ namespace crypto {
static X509_STORE* root_cert_store;
+// Forward declaration
+class Connection;
+
class SecureContext : ObjectWrap {
public:
static void Initialize(v8::Handle<v8::Object> target);
@@ -58,6 +61,8 @@ class SecureContext : ObjectWrap {
X509_STORE *ca_store_;
protected:
+ static const int kMaxSessionSize = 10 * 1024;
+
static v8::Handle<v8::Value> New(const v8::Arguments& args);
static v8::Handle<v8::Value> Init(const v8::Arguments& args);
static v8::Handle<v8::Value> SetKey(const v8::Arguments& args);
@@ -71,6 +76,12 @@ class SecureContext : ObjectWrap {
static v8::Handle<v8::Value> Close(const v8::Arguments& args);
static v8::Handle<v8::Value> LoadPKCS12(const v8::Arguments& args);
+ static SSL_SESSION* GetSessionCallback(SSL* s,
+ unsigned char* key,
+ int len,
+ int* copy);
+ static int NewSessionCallback(SSL* s, SSL_SESSION* sess);
+
SecureContext() : ObjectWrap() {
ctx_ = NULL;
ca_store_ = NULL;
@@ -100,6 +111,51 @@ class SecureContext : ObjectWrap {
private:
};
+class ClientHelloParser {
+ public:
+ enum FrameType {
+ kChangeCipherSpec = 20,
+ kAlert = 21,
+ kHandshake = 22,
+ kApplicationData = 23,
+ kOther = 255
+ };
+
+ enum HandshakeType {
+ kClientHello = 1
+ };
+
+ enum ParseState {
+ kWaiting,
+ kTLSHeader,
+ kSSLHeader,
+ kPaused,
+ kEnded
+ };
+
+ ClientHelloParser(Connection* c) : conn_(c),
+ state_(kWaiting),
+ offset_(0),
+ body_offset_(0),
+ written_(0) {
+ }
+
+ size_t Write(const uint8_t* data, size_t len);
+ void Finish();
+
+ inline bool ended() { return state_ == kEnded; }
+
+ private:
+ Connection* conn_;
+ ParseState state_;
+ size_t frame_len_;
+
+ uint8_t data_[18432];
+ size_t offset_;
+ size_t body_offset_;
+ size_t written_;
+};
+
class Connection : ObjectWrap {
public:
static void Initialize(v8::Handle<v8::Object> target);
@@ -126,6 +182,7 @@ class Connection : ObjectWrap {
static v8::Handle<v8::Value> GetPeerCertificate(const v8::Arguments& args);
static v8::Handle<v8::Value> GetSession(const v8::Arguments& args);
static v8::Handle<v8::Value> SetSession(const v8::Arguments& args);
+ static v8::Handle<v8::Value> LoadSession(const v8::Arguments& args);
static v8::Handle<v8::Value> IsSessionReused(const v8::Arguments& args);
static v8::Handle<v8::Value> IsInitFinished(const v8::Arguments& args);
static v8::Handle<v8::Value> VerifyError(const v8::Arguments& args);
@@ -168,9 +225,10 @@ class Connection : ObjectWrap {
return ss;
}
- Connection() : ObjectWrap() {
+ Connection() : ObjectWrap(), hello_parser_(this) {
bio_read_ = bio_write_ = NULL;
ssl_ = NULL;
+ next_sess_ = NULL;
}
~Connection() {
@@ -179,6 +237,11 @@ class Connection : ObjectWrap {
ssl_ = NULL;
}
+ if (next_sess_ != NULL) {
+ SSL_SESSION_free(next_sess_);
+ next_sess_ = NULL;
+ }
+
#ifdef OPENSSL_NPN_NEGOTIATED
if (!npnProtos_.IsEmpty()) npnProtos_.Dispose();
if (!selectedNPNProto_.IsEmpty()) selectedNPNProto_.Dispose();
@@ -198,7 +261,13 @@ class Connection : ObjectWrap {
BIO *bio_write_;
SSL *ssl_;
+ ClientHelloParser hello_parser_;
+
bool is_server_; /* coverity[member_decl] */
+ SSL_SESSION* next_sess_;
+
+ friend class ClientHelloParser;
+ friend class SecureContext;
};
void InitCrypto(v8::Handle<v8::Object> target);