1 // Copyright Joyent, Inc. and other Node contributors.
3 // Permission is hereby granted, free of charge, to any person obtaining a
4 // copy of this software and associated documentation files (the
5 // "Software"), to deal in the Software without restriction, including
6 // without limitation the rights to use, copy, modify, merge, publish,
7 // distribute, sublicense, and/or sell copies of the Software, and to permit
8 // persons to whom the Software is furnished to do so, subject to the
9 // following conditions:
11 // The above copyright notice and this permission notice shall be included
12 // in all copies or substantial portions of the Software.
14 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
15 // OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN
17 // NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
18 // DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
19 // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
20 // USE OR OTHER DEALINGS IN THE SOFTWARE.
22 #include "node_crypto.h"
23 #include "node_crypto_groups.h"
27 #include "node_buffer.h"
28 #include "string_bytes.h"
32 #define strcasecmp _stricmp
38 #if OPENSSL_VERSION_NUMBER >= 0x10000000L
39 # define OPENSSL_CONST const
41 # define OPENSSL_CONST
44 #define ASSERT_IS_STRING_OR_BUFFER(val) \
45 if (!Buffer::HasInstance(val) && !val->IsString()) { \
46 return ThrowException(Exception::TypeError(String::New( \
47 "Not a string or buffer"))); \
50 #define ASSERT_IS_BUFFER(val) \
51 if (!Buffer::HasInstance(val)) { \
52 return ThrowException(Exception::TypeError(String::New("Not a buffer"))); \
55 static const char PUBLIC_KEY_PFX[] = "-----BEGIN PUBLIC KEY-----";
56 static const int PUBLIC_KEY_PFX_LEN = sizeof(PUBLIC_KEY_PFX) - 1;
57 static const char PUBRSA_KEY_PFX[] = "-----BEGIN RSA PUBLIC KEY-----";
58 static const int PUBRSA_KEY_PFX_LEN = sizeof(PUBRSA_KEY_PFX) - 1;
59 static const int X509_NAME_FLAGS = ASN1_STRFLGS_ESC_CTRL
60 | ASN1_STRFLGS_ESC_MSB
61 | XN_FLAG_SEP_MULTILINE
66 const char* root_certs[] = {
67 #include "node_root_certs.h" // NOLINT(build/include_order)
75 // Forcibly clear OpenSSL's error stack on return. This stops stale errors
76 // from popping up later in the lifecycle of crypto operations where they
77 // would cause spurious failures. It's a rather blunt method, though.
78 // ERR_clear_error() isn't necessarily cheap either.
79 struct ClearErrorOnReturn {
80 ~ClearErrorOnReturn() { ERR_clear_error(); }
83 static Persistent<String> errno_symbol;
84 static Persistent<String> syscall_symbol;
85 static Persistent<String> subject_symbol;
86 static Persistent<String> subjectaltname_symbol;
87 static Persistent<String> modulus_symbol;
88 static Persistent<String> exponent_symbol;
89 static Persistent<String> issuer_symbol;
90 static Persistent<String> valid_from_symbol;
91 static Persistent<String> valid_to_symbol;
92 static Persistent<String> fingerprint_symbol;
93 static Persistent<String> name_symbol;
94 static Persistent<String> version_symbol;
95 static Persistent<String> ext_key_usage_symbol;
96 static Persistent<String> onhandshakestart_sym;
97 static Persistent<String> onhandshakedone_sym;
98 static Persistent<String> onclienthello_sym;
99 static Persistent<String> onnewsession_sym;
100 static Persistent<String> sessionid_sym;
102 static Persistent<FunctionTemplate> secure_context_constructor;
104 static uv_rwlock_t* locks;
107 static void crypto_threadid_cb(CRYPTO_THREADID* tid) {
108 CRYPTO_THREADID_set_numeric(tid, uv_thread_self());
112 static void crypto_lock_init(void) {
115 n = CRYPTO_num_locks();
116 locks = new uv_rwlock_t[n];
118 for (i = 0; i < n; i++)
119 if (uv_rwlock_init(locks + i))
124 static void crypto_lock_cb(int mode, int n, const char* file, int line) {
125 assert((mode & CRYPTO_LOCK) || (mode & CRYPTO_UNLOCK));
126 assert((mode & CRYPTO_READ) || (mode & CRYPTO_WRITE));
128 if (mode & CRYPTO_LOCK) {
129 if (mode & CRYPTO_READ)
130 uv_rwlock_rdlock(locks + n);
132 uv_rwlock_wrlock(locks + n);
134 if (mode & CRYPTO_READ)
135 uv_rwlock_rdunlock(locks + n);
137 uv_rwlock_wrunlock(locks + n);
142 Handle<Value> ThrowCryptoErrorHelper(unsigned long err, bool is_type_error) {
145 ERR_error_string_n(err, errmsg, sizeof(errmsg));
146 return is_type_error ? ThrowTypeError(errmsg) : ThrowError(errmsg);
150 Handle<Value> ThrowCryptoError(unsigned long err) {
151 return ThrowCryptoErrorHelper(err, false);
155 Handle<Value> ThrowCryptoTypeError(unsigned long err) {
156 return ThrowCryptoErrorHelper(err, true);
160 // Ensure that OpenSSL has enough entropy (at least 256 bits) for its PRNG.
161 // The entropy pool starts out empty and needs to fill up before the PRNG
162 // can be used securely. Once the pool is filled, it never dries up again;
163 // its contents is stirred and reused when necessary.
165 // OpenSSL normally fills the pool automatically but not when someone starts
166 // generating random numbers before the pool is full: in that case OpenSSL
167 // keeps lowering the entropy estimate to thwart attackers trying to guess
168 // the initial state of the PRNG.
170 // When that happens, we will have to wait until enough entropy is available.
171 // That should normally never take longer than a few milliseconds.
173 // OpenSSL draws from /dev/random and /dev/urandom. While /dev/random may
174 // block pending "true" randomness, /dev/urandom is a CSPRNG that doesn't
175 // block under normal circumstances.
177 // The only time when /dev/urandom may conceivably block is right after boot,
178 // when the whole system is still low on entropy. That's not something we can
179 // do anything about.
180 inline void CheckEntropy() {
182 int status = RAND_status();
183 assert(status >= 0); // Cannot fail.
186 if (RAND_poll() == 0) // Give up, RAND_poll() not supported.
192 bool EntropySource(unsigned char* buffer, size_t length) {
193 // Ensure that OpenSSL's PRNG is properly seeded.
195 // RAND_bytes() can return 0 to indicate that the entropy data is not truly
196 // random. That's okay, it's still better than V8's stock source of entropy,
197 // which is /dev/urandom on UNIX platforms and the current time on Windows.
198 return RAND_bytes(buffer, length) != -1;
202 void SecureContext::Initialize(Handle<Object> target) {
205 Local<FunctionTemplate> t = FunctionTemplate::New(SecureContext::New);
206 secure_context_constructor = Persistent<FunctionTemplate>::New(t);
208 t->InstanceTemplate()->SetInternalFieldCount(1);
209 t->SetClassName(String::NewSymbol("SecureContext"));
211 NODE_SET_PROTOTYPE_METHOD(t, "init", SecureContext::Init);
212 NODE_SET_PROTOTYPE_METHOD(t, "setKey", SecureContext::SetKey);
213 NODE_SET_PROTOTYPE_METHOD(t, "setCert", SecureContext::SetCert);
214 NODE_SET_PROTOTYPE_METHOD(t, "addCACert", SecureContext::AddCACert);
215 NODE_SET_PROTOTYPE_METHOD(t, "addCRL", SecureContext::AddCRL);
216 NODE_SET_PROTOTYPE_METHOD(t, "addRootCerts", SecureContext::AddRootCerts);
217 NODE_SET_PROTOTYPE_METHOD(t, "setCiphers", SecureContext::SetCiphers);
218 NODE_SET_PROTOTYPE_METHOD(t, "setOptions", SecureContext::SetOptions);
219 NODE_SET_PROTOTYPE_METHOD(t, "setSessionIdContext",
220 SecureContext::SetSessionIdContext);
221 NODE_SET_PROTOTYPE_METHOD(t, "close", SecureContext::Close);
222 NODE_SET_PROTOTYPE_METHOD(t, "loadPKCS12", SecureContext::LoadPKCS12);
224 target->Set(String::NewSymbol("SecureContext"), t->GetFunction());
228 Handle<Value> SecureContext::New(const Arguments& args) {
230 SecureContext *p = new SecureContext();
231 p->Wrap(args.Holder());
236 Handle<Value> SecureContext::Init(const Arguments& args) {
239 SecureContext *sc = ObjectWrap::Unwrap<SecureContext>(args.Holder());
241 OPENSSL_CONST SSL_METHOD *method = SSLv23_method();
243 if (args.Length() == 1 && args[0]->IsString()) {
244 String::Utf8Value sslmethod(args[0]);
246 if (strcmp(*sslmethod, "SSLv2_method") == 0) {
247 #ifndef OPENSSL_NO_SSL2
248 method = SSLv2_method();
250 return ThrowException(Exception::Error(String::New("SSLv2 methods disabled")));
252 } else if (strcmp(*sslmethod, "SSLv2_server_method") == 0) {
253 #ifndef OPENSSL_NO_SSL2
254 method = SSLv2_server_method();
256 return ThrowException(Exception::Error(String::New("SSLv2 methods disabled")));
258 } else if (strcmp(*sslmethod, "SSLv2_client_method") == 0) {
259 #ifndef OPENSSL_NO_SSL2
260 method = SSLv2_client_method();
262 return ThrowException(Exception::Error(String::New("SSLv2 methods disabled")));
264 } else if (strcmp(*sslmethod, "SSLv3_method") == 0) {
265 method = SSLv3_method();
266 } else if (strcmp(*sslmethod, "SSLv3_server_method") == 0) {
267 method = SSLv3_server_method();
268 } else if (strcmp(*sslmethod, "SSLv3_client_method") == 0) {
269 method = SSLv3_client_method();
270 } else if (strcmp(*sslmethod, "SSLv23_method") == 0) {
271 method = SSLv23_method();
272 } else if (strcmp(*sslmethod, "SSLv23_server_method") == 0) {
273 method = SSLv23_server_method();
274 } else if (strcmp(*sslmethod, "SSLv23_client_method") == 0) {
275 method = SSLv23_client_method();
276 } else if (strcmp(*sslmethod, "TLSv1_method") == 0) {
277 method = TLSv1_method();
278 } else if (strcmp(*sslmethod, "TLSv1_server_method") == 0) {
279 method = TLSv1_server_method();
280 } else if (strcmp(*sslmethod, "TLSv1_client_method") == 0) {
281 method = TLSv1_client_method();
283 return ThrowException(Exception::Error(String::New("Unknown method")));
287 sc->ctx_ = SSL_CTX_new(method);
289 // SSL session cache configuration
290 SSL_CTX_set_session_cache_mode(sc->ctx_,
291 SSL_SESS_CACHE_SERVER |
292 SSL_SESS_CACHE_NO_INTERNAL |
293 SSL_SESS_CACHE_NO_AUTO_CLEAR);
294 SSL_CTX_sess_set_get_cb(sc->ctx_, GetSessionCallback);
295 SSL_CTX_sess_set_new_cb(sc->ctx_, NewSessionCallback);
297 sc->ca_store_ = NULL;
302 SSL_SESSION* SecureContext::GetSessionCallback(SSL* s,
308 Connection* p = static_cast<Connection*>(SSL_get_app_data(s));
311 SSL_SESSION* sess = p->next_sess_;
312 p->next_sess_ = NULL;
318 void SessionDataFree(char* data, void* hint) {
323 int SecureContext::NewSessionCallback(SSL* s, SSL_SESSION* sess) {
326 Connection* p = static_cast<Connection*>(SSL_get_app_data(s));
328 // Check if session is small enough to be stored
329 int size = i2d_SSL_SESSION(sess, NULL);
330 if (size > kMaxSessionSize) return 0;
333 char* serialized = new char[size];
334 unsigned char* pserialized = reinterpret_cast<unsigned char*>(serialized);
335 memset(serialized, 0, size);
336 i2d_SSL_SESSION(sess, &pserialized);
338 Handle<Value> argv[2] = {
339 Buffer::New(reinterpret_cast<char*>(sess->session_id),
340 sess->session_id_length)->handle_,
341 Buffer::New(serialized, size, SessionDataFree, NULL)->handle_
344 if (onnewsession_sym.IsEmpty()) {
345 onnewsession_sym = NODE_PSYMBOL("onnewsession");
347 MakeCallback(p->handle_, onnewsession_sym, ARRAY_SIZE(argv), argv);
353 // Takes a string or buffer and loads it into a BIO.
354 // Caller responsible for BIO_free-ing the returned object.
355 static BIO* LoadBIO (Handle<Value> v) {
356 BIO *bio = BIO_new(BIO_s_mem());
357 if (!bio) return NULL;
364 String::Utf8Value s(v);
365 r = BIO_write(bio, *s, s.length());
366 } else if (Buffer::HasInstance(v)) {
367 char* buffer_data = Buffer::Data(v);
368 size_t buffer_length = Buffer::Length(v);
369 r = BIO_write(bio, buffer_data, buffer_length);
381 // Takes a string or buffer and loads it into an X509
382 // Caller responsible for X509_free-ing the returned object.
383 static X509* LoadX509 (Handle<Value> v) {
384 HandleScope scope; // necessary?
386 BIO *bio = LoadBIO(v);
387 if (!bio) return NULL;
389 X509 * x509 = PEM_read_bio_X509(bio, NULL, NULL, NULL);
400 Handle<Value> SecureContext::SetKey(const Arguments& args) {
403 SecureContext *sc = ObjectWrap::Unwrap<SecureContext>(args.Holder());
405 unsigned int len = args.Length();
406 if (len != 1 && len != 2) {
407 return ThrowException(Exception::TypeError(String::New("Bad parameter")));
409 if (len == 2 && !args[1]->IsString()) {
410 return ThrowException(Exception::TypeError(String::New("Bad parameter")));
413 BIO *bio = LoadBIO(args[0]);
414 if (!bio) return False();
416 String::Utf8Value passphrase(args[1]);
418 EVP_PKEY* key = PEM_read_bio_PrivateKey(bio, NULL, NULL,
419 len == 1 ? NULL : *passphrase);
423 unsigned long err = ERR_get_error();
425 return ThrowException(Exception::Error(
426 String::New("PEM_read_bio_PrivateKey")));
428 return ThrowCryptoError(err);
431 SSL_CTX_use_PrivateKey(sc->ctx_, key);
439 // Read a file that contains our certificate in "PEM" format,
440 // possibly followed by a sequence of CA certificates that should be
441 // sent to the peer in the Certificate message.
443 // Taken from OpenSSL - editted for style.
444 int SSL_CTX_use_certificate_chain(SSL_CTX *ctx, BIO *in) {
448 x = PEM_read_bio_X509_AUX(in, NULL, NULL, NULL);
451 SSLerr(SSL_F_SSL_CTX_USE_CERTIFICATE_CHAIN_FILE, ERR_R_PEM_LIB);
455 ret = SSL_CTX_use_certificate(ctx, x);
457 if (ERR_peek_error() != 0) {
458 // Key/certificate mismatch doesn't imply ret==0 ...
463 // If we could set up our certificate, now proceed to
464 // the CA certificates.
469 if (ctx->extra_certs != NULL) {
470 sk_X509_pop_free(ctx->extra_certs, X509_free);
471 ctx->extra_certs = NULL;
474 while ((ca = PEM_read_bio_X509(in, NULL, NULL, NULL))) {
475 r = SSL_CTX_add_extra_chain_cert(ctx, ca);
482 // Note that we must not free r if it was successfully
483 // added to the chain (while we must free the main
484 // certificate, since its reference count is increased
485 // by SSL_CTX_use_certificate).
488 // When the while loop ends, it's usually just EOF.
489 err = ERR_peek_last_error();
490 if (ERR_GET_LIB(err) == ERR_LIB_PEM &&
491 ERR_GET_REASON(err) == PEM_R_NO_START_LINE) {
500 if (x != NULL) X509_free(x);
505 Handle<Value> SecureContext::SetCert(const Arguments& args) {
508 SecureContext *sc = ObjectWrap::Unwrap<SecureContext>(args.Holder());
510 if (args.Length() != 1) {
511 return ThrowException(Exception::TypeError(
512 String::New("Bad parameter")));
515 BIO* bio = LoadBIO(args[0]);
516 if (!bio) return False();
518 int rv = SSL_CTX_use_certificate_chain(sc->ctx_, bio);
523 unsigned long err = ERR_get_error();
525 return ThrowException(Exception::Error(
526 String::New("SSL_CTX_use_certificate_chain")));
528 return ThrowCryptoError(err);
535 Handle<Value> SecureContext::AddCACert(const Arguments& args) {
536 bool newCAStore = false;
539 SecureContext *sc = ObjectWrap::Unwrap<SecureContext>(args.Holder());
541 if (args.Length() != 1) {
542 return ThrowException(Exception::TypeError(String::New("Bad parameter")));
545 if (!sc->ca_store_) {
546 sc->ca_store_ = X509_STORE_new();
550 X509* x509 = LoadX509(args[0]);
551 if (!x509) return False();
553 X509_STORE_add_cert(sc->ca_store_, x509);
554 SSL_CTX_add_client_CA(sc->ctx_, x509);
559 SSL_CTX_set_cert_store(sc->ctx_, sc->ca_store_);
566 Handle<Value> SecureContext::AddCRL(const Arguments& args) {
569 SecureContext *sc = ObjectWrap::Unwrap<SecureContext>(args.Holder());
571 if (args.Length() != 1) {
572 return ThrowException(Exception::TypeError(String::New("Bad parameter")));
575 BIO *bio = LoadBIO(args[0]);
576 if (!bio) return False();
578 X509_CRL *x509 = PEM_read_bio_X509_CRL(bio, NULL, NULL, NULL);
585 X509_STORE_add_crl(sc->ca_store_, x509);
587 X509_STORE_set_flags(sc->ca_store_, X509_V_FLAG_CRL_CHECK |
588 X509_V_FLAG_CRL_CHECK_ALL);
598 Handle<Value> SecureContext::AddRootCerts(const Arguments& args) {
601 SecureContext *sc = ObjectWrap::Unwrap<SecureContext>(args.Holder());
603 assert(sc->ca_store_ == NULL);
605 if (!root_cert_store) {
606 root_cert_store = X509_STORE_new();
608 for (int i = 0; root_certs[i]; i++) {
609 BIO *bp = BIO_new(BIO_s_mem());
611 if (!BIO_write(bp, root_certs[i], strlen(root_certs[i]))) {
616 X509 *x509 = PEM_read_bio_X509(bp, NULL, NULL, NULL);
623 X509_STORE_add_cert(root_cert_store, x509);
630 sc->ca_store_ = root_cert_store;
631 SSL_CTX_set_cert_store(sc->ctx_, sc->ca_store_);
637 Handle<Value> SecureContext::SetCiphers(const Arguments& args) {
640 SecureContext *sc = ObjectWrap::Unwrap<SecureContext>(args.Holder());
642 if (args.Length() != 1 || !args[0]->IsString()) {
643 return ThrowException(Exception::TypeError(String::New("Bad parameter")));
646 String::Utf8Value ciphers(args[0]);
647 SSL_CTX_set_cipher_list(sc->ctx_, *ciphers);
652 Handle<Value> SecureContext::SetOptions(const Arguments& args) {
655 SecureContext *sc = ObjectWrap::Unwrap<SecureContext>(args.Holder());
657 if (args.Length() != 1 || !args[0]->IntegerValue()) {
658 return ThrowException(Exception::TypeError(String::New("Bad parameter")));
661 SSL_CTX_set_options(sc->ctx_, args[0]->IntegerValue());
666 Handle<Value> SecureContext::SetSessionIdContext(const Arguments& args) {
669 SecureContext *sc = ObjectWrap::Unwrap<SecureContext>(args.Holder());
671 if (args.Length() != 1 || !args[0]->IsString()) {
672 return ThrowException(Exception::TypeError(String::New("Bad parameter")));
675 String::Utf8Value sessionIdContext(args[0]);
676 const unsigned char* sid_ctx = (const unsigned char*) *sessionIdContext;
677 unsigned int sid_ctx_len = sessionIdContext.length();
679 int r = SSL_CTX_set_session_id_context(sc->ctx_, sid_ctx, sid_ctx_len);
681 Local<String> message;
684 if ((bio = BIO_new(BIO_s_mem()))) {
685 ERR_print_errors(bio);
686 BIO_get_mem_ptr(bio, &mem);
687 message = String::New(mem->data, mem->length);
690 message = String::New("SSL_CTX_set_session_id_context error");
692 return ThrowException(Exception::TypeError(message));
698 Handle<Value> SecureContext::Close(const Arguments& args) {
700 SecureContext *sc = ObjectWrap::Unwrap<SecureContext>(args.Holder());
705 //Takes .pfx or .p12 and password in string or buffer format
706 Handle<Value> SecureContext::LoadPKCS12(const Arguments& args) {
711 EVP_PKEY* pkey = NULL;
713 STACK_OF(X509)* extraCerts = NULL;
717 SecureContext *sc = ObjectWrap::Unwrap<SecureContext>(args.Holder());
719 if (args.Length() < 1) {
720 return ThrowException(Exception::TypeError(
721 String::New("Bad parameter")));
724 in = LoadBIO(args[0]);
726 return ThrowException(Exception::Error(
727 String::New("Unable to load BIO")));
730 if (args.Length() >= 2) {
731 ASSERT_IS_BUFFER(args[1]);
733 int passlen = Buffer::Length(args[1]);
736 return ThrowException(Exception::TypeError(
737 String::New("Bad password")));
739 pass = new char[passlen + 1];
740 int pass_written = DecodeWrite(pass, passlen, args[1], BINARY);
742 assert(pass_written == passlen);
743 pass[passlen] = '\0';
746 if (d2i_PKCS12_bio(in, &p12) &&
747 PKCS12_parse(p12, pass, &pkey, &cert, &extraCerts) &&
748 SSL_CTX_use_certificate(sc->ctx_, cert) &&
749 SSL_CTX_use_PrivateKey(sc->ctx_, pkey))
752 while (X509* x509 = sk_X509_pop(extraCerts)) {
753 if (!sc->ca_store_) {
754 sc->ca_store_ = X509_STORE_new();
755 SSL_CTX_set_cert_store(sc->ctx_, sc->ca_store_);
758 X509_STORE_add_cert(sc->ca_store_, x509);
759 SSL_CTX_add_client_CA(sc->ctx_, x509);
765 sk_X509_free(extraCerts);
775 unsigned long err = ERR_get_error();
776 const char* str = ERR_reason_error_string(err);
777 return ThrowException(Exception::Error(String::New(str)));
784 size_t ClientHelloParser::Write(const uint8_t* data, size_t len) {
787 // Just accumulate data, everything will be pushed to BIO later
788 if (state_ == kPaused) return 0;
790 // Copy incoming data to the internal buffer
791 // (which has a size of the biggest possible TLS frame)
792 size_t available = sizeof(data_) - offset_;
793 size_t copied = len < available ? len : available;
794 memcpy(data_ + offset_, data, copied);
797 // Vars for parsing hello
798 bool is_clienthello = false;
799 uint8_t session_size = -1;
800 uint8_t* session_id = NULL;
802 Handle<Value> argv[1];
806 // >= 5 bytes for header parsing
807 if (offset_ < 5) break;
809 if (data_[0] == kChangeCipherSpec || data_[0] == kAlert ||
810 data_[0] == kHandshake || data_[0] == kApplicationData) {
811 frame_len_ = (data_[3] << 8) + data_[4];
815 frame_len_ = (data_[0] << 8) + data_[1];
818 // header with padding
826 // Sanity check (too big frame, or too small)
827 if (frame_len_ >= sizeof(data_)) {
828 // Let OpenSSL handle it
834 // >= 5 + frame size bytes for frame parsing
835 if (offset_ < body_offset_ + frame_len_) break;
837 // Skip unsupported frames and gather some data from frame
839 // TODO: Check protocol version
840 if (data_[body_offset_] == kClientHello) {
841 is_clienthello = true;
843 size_t session_offset;
845 if (state_ == kTLSHeader) {
846 // Skip frame header, hello header, protocol version and random data
847 session_offset = body_offset_ + 4 + 2 + 32;
849 if (session_offset + 1 < offset_) {
850 body = data_ + session_offset;
851 session_size = *body;
852 session_id = body + 1;
854 } else if (state_ == kSSLHeader) {
855 // Skip header, version
856 session_offset = body_offset_ + 3;
858 if (session_offset + 4 < offset_) {
859 body = data_ + session_offset;
861 int ciphers_size = (body[0] << 8) + body[1];
863 if (body + 4 + ciphers_size < data_ + offset_) {
864 session_size = (body[2] << 8) + body[3];
865 session_id = body + 4 + ciphers_size;
869 // Whoa? How did we get here?
873 // Check if we overflowed (do not reply with any private data)
874 if (session_id == NULL ||
876 session_id + session_size > data_ + offset_) {
881 // TODO: Parse other things?
884 // Not client hello - let OpenSSL handle it
885 if (!is_clienthello) {
890 // Parse frame, call javascript handler and
891 // move parser into the paused state
892 if (onclienthello_sym.IsEmpty()) {
893 onclienthello_sym = NODE_PSYMBOL("onclienthello");
895 if (sessionid_sym.IsEmpty()) {
896 sessionid_sym = NODE_PSYMBOL("sessionId");
900 hello = Object::New();
901 hello->Set(sessionid_sym,
902 Buffer::New(reinterpret_cast<char*>(session_id),
903 session_size)->handle_);
906 MakeCallback(conn_->handle_, onclienthello_sym, 1, argv);
917 void ClientHelloParser::Finish() {
918 assert(state_ != kEnded);
921 // Write all accumulated data
922 int r = BIO_write(conn_->bio_read_, reinterpret_cast<char*>(data_), offset_);
923 conn_->HandleBIOError(conn_->bio_read_, "BIO_write", r);
924 conn_->SetShutdownFlags();
928 #ifdef SSL_PRINT_DEBUG
929 # define DEBUG_PRINT(...) fprintf (stderr, __VA_ARGS__)
931 # define DEBUG_PRINT(...)
935 int Connection::HandleBIOError(BIO *bio, const char* func, int rv) {
936 if (rv >= 0) return rv;
938 int retry = BIO_should_retry(bio);
939 (void) retry; // unused if !defined(SSL_PRINT_DEBUG)
941 if (BIO_should_write(bio)) {
942 DEBUG_PRINT("[%p] BIO: %s want write. should retry %d\n", ssl_, func, retry);
945 } else if (BIO_should_read(bio)) {
946 DEBUG_PRINT("[%p] BIO: %s want read. should retry %d\n", ssl_, func, retry);
950 static char ssl_error_buf[512];
951 ERR_error_string_n(rv, ssl_error_buf, sizeof(ssl_error_buf));
954 Local<Value> e = Exception::Error(String::New(ssl_error_buf));
955 handle_->Set(String::New("error"), e);
957 DEBUG_PRINT("[%p] BIO: %s failed: (%d) %s\n", ssl_, func, rv, ssl_error_buf);
966 int Connection::HandleSSLError(const char* func,
970 ClearErrorOnReturn clear_error_on_return;
971 (void) &clear_error_on_return; // Silence unused variable warning.
973 if (rv > 0) return rv;
974 if ((rv == 0) && (zs == kZeroIsNotAnError)) return rv;
976 int err = SSL_get_error(ssl_, rv);
978 if (err == SSL_ERROR_NONE) {
981 } else if (err == SSL_ERROR_WANT_WRITE) {
982 DEBUG_PRINT("[%p] SSL: %s want write\n", ssl_, func);
985 } else if (err == SSL_ERROR_WANT_READ) {
986 DEBUG_PRINT("[%p] SSL: %s want read\n", ssl_, func);
989 } else if (err == SSL_ERROR_ZERO_RETURN) {
990 handle_->Set(String::New("error"),
991 Exception::Error(String::New("ZERO_RETURN")));
994 } else if ((err == SSL_ERROR_SYSCALL) && (ss == kIgnoreSyscall)) {
1002 assert(err == SSL_ERROR_SSL || err == SSL_ERROR_SYSCALL);
1004 // XXX We need to drain the error queue for this thread or else OpenSSL
1005 // has the possibility of blocking connections? This problem is not well
1006 // understood. And we should be somehow propagating these errors up
1007 // into JavaScript. There is no test which demonstrates this problem.
1008 // https://github.com/joyent/node/issues/1719
1009 if ((bio = BIO_new(BIO_s_mem()))) {
1010 ERR_print_errors(bio);
1011 BIO_get_mem_ptr(bio, &mem);
1012 Local<Value> e = Exception::Error(String::New(mem->data, mem->length));
1013 handle_->Set(String::New("error"), e);
1024 void Connection::ClearError() {
1028 // We should clear the error in JS-land
1029 assert(handle_->Get(String::New("error"))->BooleanValue() == false);
1034 void Connection::SetShutdownFlags() {
1037 int flags = SSL_get_shutdown(ssl_);
1039 if (flags & SSL_SENT_SHUTDOWN) {
1040 handle_->Set(String::New("sentShutdown"), True());
1043 if (flags & SSL_RECEIVED_SHUTDOWN) {
1044 handle_->Set(String::New("receivedShutdown"), True());
1049 void Connection::Initialize(Handle<Object> target) {
1052 Local<FunctionTemplate> t = FunctionTemplate::New(Connection::New);
1053 t->InstanceTemplate()->SetInternalFieldCount(1);
1054 t->SetClassName(String::NewSymbol("Connection"));
1056 NODE_SET_PROTOTYPE_METHOD(t, "encIn", Connection::EncIn);
1057 NODE_SET_PROTOTYPE_METHOD(t, "clearOut", Connection::ClearOut);
1058 NODE_SET_PROTOTYPE_METHOD(t, "clearIn", Connection::ClearIn);
1059 NODE_SET_PROTOTYPE_METHOD(t, "encOut", Connection::EncOut);
1060 NODE_SET_PROTOTYPE_METHOD(t, "clearPending", Connection::ClearPending);
1061 NODE_SET_PROTOTYPE_METHOD(t, "encPending", Connection::EncPending);
1062 NODE_SET_PROTOTYPE_METHOD(t, "getPeerCertificate", Connection::GetPeerCertificate);
1063 NODE_SET_PROTOTYPE_METHOD(t, "getSession", Connection::GetSession);
1064 NODE_SET_PROTOTYPE_METHOD(t, "setSession", Connection::SetSession);
1065 NODE_SET_PROTOTYPE_METHOD(t, "loadSession", Connection::LoadSession);
1066 NODE_SET_PROTOTYPE_METHOD(t, "isSessionReused", Connection::IsSessionReused);
1067 NODE_SET_PROTOTYPE_METHOD(t, "isInitFinished", Connection::IsInitFinished);
1068 NODE_SET_PROTOTYPE_METHOD(t, "verifyError", Connection::VerifyError);
1069 NODE_SET_PROTOTYPE_METHOD(t, "getCurrentCipher", Connection::GetCurrentCipher);
1070 NODE_SET_PROTOTYPE_METHOD(t, "start", Connection::Start);
1071 NODE_SET_PROTOTYPE_METHOD(t, "shutdown", Connection::Shutdown);
1072 NODE_SET_PROTOTYPE_METHOD(t, "close", Connection::Close);
1074 #ifdef OPENSSL_NPN_NEGOTIATED
1075 NODE_SET_PROTOTYPE_METHOD(t, "getNegotiatedProtocol", Connection::GetNegotiatedProto);
1076 NODE_SET_PROTOTYPE_METHOD(t, "setNPNProtocols", Connection::SetNPNProtocols);
1080 #ifdef SSL_CTRL_SET_TLSEXT_SERVERNAME_CB
1081 NODE_SET_PROTOTYPE_METHOD(t, "getServername", Connection::GetServername);
1082 NODE_SET_PROTOTYPE_METHOD(t, "setSNICallback", Connection::SetSNICallback);
1085 target->Set(String::NewSymbol("Connection"), t->GetFunction());
1089 static int VerifyCallback(int preverify_ok, X509_STORE_CTX *ctx) {
1090 // Quoting SSL_set_verify(3ssl):
1092 // The VerifyCallback function is used to control the behaviour when
1093 // the SSL_VERIFY_PEER flag is set. It must be supplied by the
1094 // application and receives two arguments: preverify_ok indicates,
1095 // whether the verification of the certificate in question was passed
1096 // (preverify_ok=1) or not (preverify_ok=0). x509_ctx is a pointer to
1097 // the complete context used for the certificate chain verification.
1099 // The certificate chain is checked starting with the deepest nesting
1100 // level (the root CA certificate) and worked upward to the peer's
1101 // certificate. At each level signatures and issuer attributes are
1102 // checked. Whenever a verification error is found, the error number is
1103 // stored in x509_ctx and VerifyCallback is called with preverify_ok=0.
1104 // By applying X509_CTX_store_* functions VerifyCallback can locate the
1105 // certificate in question and perform additional steps (see EXAMPLES).
1106 // If no error is found for a certificate, VerifyCallback is called
1107 // with preverify_ok=1 before advancing to the next level.
1109 // The return value of VerifyCallback controls the strategy of the
1110 // further verification process. If VerifyCallback returns 0, the
1111 // verification process is immediately stopped with "verification
1112 // failed" state. If SSL_VERIFY_PEER is set, a verification failure
1113 // alert is sent to the peer and the TLS/SSL handshake is terminated. If
1114 // VerifyCallback returns 1, the verification process is continued. If
1115 // VerifyCallback always returns 1, the TLS/SSL handshake will not be
1116 // terminated with respect to verification failures and the connection
1117 // will be established. The calling process can however retrieve the
1118 // error code of the last verification error using
1119 // SSL_get_verify_result(3) or by maintaining its own error storage
1120 // managed by VerifyCallback.
1122 // If no VerifyCallback is specified, the default callback will be
1123 // used. Its return value is identical to preverify_ok, so that any
1124 // verification failure will lead to a termination of the TLS/SSL
1125 // handshake with an alert message, if SSL_VERIFY_PEER is set.
1127 // Since we cannot perform I/O quickly enough in this callback, we ignore
1128 // all preverify_ok errors and let the handshake continue. It is
1129 // imparative that the user use Connection::VerifyError after the
1130 // 'secure' callback has been made.
1134 #ifdef OPENSSL_NPN_NEGOTIATED
1136 int Connection::AdvertiseNextProtoCallback_(SSL *s,
1137 const unsigned char** data,
1141 Connection *p = static_cast<Connection*>(SSL_get_app_data(s));
1143 if (p->npnProtos_.IsEmpty()) {
1144 // No initialization - no NPN protocols
1145 *data = reinterpret_cast<const unsigned char*>("");
1148 *data = reinterpret_cast<const unsigned char*>(Buffer::Data(p->npnProtos_));
1149 *len = Buffer::Length(p->npnProtos_);
1152 return SSL_TLSEXT_ERR_OK;
1155 int Connection::SelectNextProtoCallback_(SSL *s,
1156 unsigned char** out, unsigned char* outlen,
1157 const unsigned char* in,
1158 unsigned int inlen, void *arg) {
1159 Connection *p = static_cast<Connection*> SSL_get_app_data(s);
1161 // Release old protocol handler if present
1162 if (!p->selectedNPNProto_.IsEmpty()) {
1163 p->selectedNPNProto_.Dispose();
1166 if (p->npnProtos_.IsEmpty()) {
1167 // We should at least select one protocol
1168 // If server is using NPN
1169 *out = reinterpret_cast<unsigned char*>(const_cast<char*>("http/1.1"));
1172 // set status unsupported
1173 p->selectedNPNProto_ = Persistent<Value>::New(False());
1175 return SSL_TLSEXT_ERR_OK;
1178 const unsigned char* npnProtos =
1179 reinterpret_cast<const unsigned char*>(Buffer::Data(p->npnProtos_));
1181 int status = SSL_select_next_proto(out, outlen, in, inlen, npnProtos,
1182 Buffer::Length(p->npnProtos_));
1185 case OPENSSL_NPN_UNSUPPORTED:
1186 p->selectedNPNProto_ = Persistent<Value>::New(Null());
1188 case OPENSSL_NPN_NEGOTIATED:
1189 p->selectedNPNProto_ = Persistent<Value>::New(String::New(
1190 reinterpret_cast<const char*>(*out), *outlen
1193 case OPENSSL_NPN_NO_OVERLAP:
1194 p->selectedNPNProto_ = Persistent<Value>::New(False());
1200 return SSL_TLSEXT_ERR_OK;
1204 #ifdef SSL_CTRL_SET_TLSEXT_SERVERNAME_CB
1205 int Connection::SelectSNIContextCallback_(SSL *s, int *ad, void* arg) {
1208 Connection *p = static_cast<Connection*> SSL_get_app_data(s);
1210 const char* servername = SSL_get_servername(s, TLSEXT_NAMETYPE_host_name);
1213 if (!p->servername_.IsEmpty()) {
1214 p->servername_.Dispose();
1216 p->servername_ = Persistent<String>::New(String::New(servername));
1218 // Call the SNI callback and use its return value as context
1219 if (!p->sniObject_.IsEmpty()) {
1220 if (!p->sniContext_.IsEmpty()) {
1221 p->sniContext_.Dispose();
1224 // Get callback init args
1225 Local<Value> argv[1] = {*p->servername_};
1228 Local<Value> ret = Local<Value>::New(MakeCallback(p->sniObject_,
1233 // If ret is SecureContext
1234 if (secure_context_constructor->HasInstance(ret)) {
1235 p->sniContext_ = Persistent<Value>::New(ret);
1236 SecureContext *sc = ObjectWrap::Unwrap<SecureContext>(
1237 Local<Object>::Cast(ret));
1238 p->InitNPN(sc, true);
1239 SSL_set_SSL_CTX(s, sc->ctx_);
1241 return SSL_TLSEXT_ERR_NOACK;
1246 return SSL_TLSEXT_ERR_OK;
1250 Handle<Value> Connection::New(const Arguments& args) {
1253 Connection *p = new Connection();
1254 p->Wrap(args.Holder());
1256 if (args.Length() < 1 || !args[0]->IsObject()) {
1257 return ThrowException(Exception::Error(String::New(
1258 "First argument must be a crypto module Credentials")));
1261 SecureContext *sc = ObjectWrap::Unwrap<SecureContext>(args[0]->ToObject());
1263 bool is_server = args[1]->BooleanValue();
1265 p->ssl_ = SSL_new(sc->ctx_);
1266 p->bio_read_ = BIO_new(BIO_s_mem());
1267 p->bio_write_ = BIO_new(BIO_s_mem());
1269 SSL_set_app_data(p->ssl_, p);
1271 if (is_server) SSL_set_info_callback(p->ssl_, SSLInfoCallback);
1273 p->InitNPN(sc, is_server);
1275 #ifdef SSL_CTRL_SET_TLSEXT_SERVERNAME_CB
1277 SSL_CTX_set_tlsext_servername_callback(sc->ctx_, SelectSNIContextCallback_);
1279 String::Utf8Value servername(args[2]);
1280 SSL_set_tlsext_host_name(p->ssl_, *servername);
1284 SSL_set_bio(p->ssl_, p->bio_read_, p->bio_write_);
1286 #ifdef SSL_MODE_RELEASE_BUFFERS
1287 long mode = SSL_get_mode(p->ssl_);
1288 SSL_set_mode(p->ssl_, mode | SSL_MODE_RELEASE_BUFFERS);
1294 bool request_cert = args[2]->BooleanValue();
1295 if (!request_cert) {
1296 // Note reject_unauthorized ignored.
1297 verify_mode = SSL_VERIFY_NONE;
1299 bool reject_unauthorized = args[3]->BooleanValue();
1300 verify_mode = SSL_VERIFY_PEER;
1301 if (reject_unauthorized) verify_mode |= SSL_VERIFY_FAIL_IF_NO_PEER_CERT;
1304 // Note request_cert and reject_unauthorized are ignored for clients.
1305 verify_mode = SSL_VERIFY_NONE;
1309 // Always allow a connection. We'll reject in javascript.
1310 SSL_set_verify(p->ssl_, verify_mode, VerifyCallback);
1312 if ((p->is_server_ = is_server)) {
1313 SSL_set_accept_state(p->ssl_);
1315 SSL_set_connect_state(p->ssl_);
1322 void Connection::SSLInfoCallback(const SSL *ssl_, int where, int ret) {
1323 // Be compatible with older versions of OpenSSL. SSL_get_app_data() wants
1324 // a non-const SSL* in OpenSSL <= 0.9.7e.
1325 SSL* ssl = const_cast<SSL*>(ssl_);
1326 if (where & SSL_CB_HANDSHAKE_START) {
1328 Connection* c = static_cast<Connection*>(SSL_get_app_data(ssl));
1329 if (onhandshakestart_sym.IsEmpty()) {
1330 onhandshakestart_sym = NODE_PSYMBOL("onhandshakestart");
1332 MakeCallback(c->handle_, onhandshakestart_sym, 0, NULL);
1334 if (where & SSL_CB_HANDSHAKE_DONE) {
1336 Connection* c = static_cast<Connection*>(SSL_get_app_data(ssl));
1337 if (onhandshakedone_sym.IsEmpty()) {
1338 onhandshakedone_sym = NODE_PSYMBOL("onhandshakedone");
1340 MakeCallback(c->handle_, onhandshakedone_sym, 0, NULL);
1345 Handle<Value> Connection::EncIn(const Arguments& args) {
1348 Connection *ss = Connection::Unwrap(args);
1350 if (args.Length() < 3) {
1351 return ThrowException(Exception::TypeError(
1352 String::New("Takes 3 parameters")));
1355 if (!Buffer::HasInstance(args[0])) {
1356 return ThrowException(Exception::TypeError(
1357 String::New("Second argument should be a buffer")));
1360 char* buffer_data = Buffer::Data(args[0]);
1361 size_t buffer_length = Buffer::Length(args[0]);
1363 size_t off = args[1]->Int32Value();
1364 size_t len = args[2]->Int32Value();
1365 if (!Buffer::IsWithinBounds(off, len, buffer_length)) {
1366 return ThrowException(Exception::Error(
1367 String::New("off + len > buffer.length")));
1371 char* data = buffer_data + off;
1373 if (ss->is_server_ && !ss->hello_parser_.ended()) {
1374 bytes_written = ss->hello_parser_.Write(reinterpret_cast<uint8_t*>(data),
1377 bytes_written = BIO_write(ss->bio_read_, data, len);
1378 ss->HandleBIOError(ss->bio_read_, "BIO_write", bytes_written);
1379 ss->SetShutdownFlags();
1382 return scope.Close(Integer::New(bytes_written));
1386 Handle<Value> Connection::ClearOut(const Arguments& args) {
1389 Connection *ss = Connection::Unwrap(args);
1391 if (args.Length() < 3) {
1392 return ThrowException(Exception::TypeError(
1393 String::New("Takes 3 parameters")));
1396 if (!Buffer::HasInstance(args[0])) {
1397 return ThrowException(Exception::TypeError(
1398 String::New("Second argument should be a buffer")));
1401 char* buffer_data = Buffer::Data(args[0]);
1402 size_t buffer_length = Buffer::Length(args[0]);
1404 size_t off = args[1]->Int32Value();
1405 size_t len = args[2]->Int32Value();
1406 if (!Buffer::IsWithinBounds(off, len, buffer_length)) {
1407 return ThrowException(Exception::Error(
1408 String::New("off + len > buffer.length")));
1411 if (!SSL_is_init_finished(ss->ssl_)) {
1414 if (ss->is_server_) {
1415 rv = SSL_accept(ss->ssl_);
1416 ss->HandleSSLError("SSL_accept:ClearOut",
1421 rv = SSL_connect(ss->ssl_);
1422 ss->HandleSSLError("SSL_connect:ClearOut",
1428 if (rv < 0) return scope.Close(Integer::New(rv));
1431 int bytes_read = SSL_read(ss->ssl_, buffer_data + off, len);
1432 ss->HandleSSLError("SSL_read:ClearOut",
1436 ss->SetShutdownFlags();
1438 return scope.Close(Integer::New(bytes_read));
1442 Handle<Value> Connection::ClearPending(const Arguments& args) {
1445 Connection *ss = Connection::Unwrap(args);
1447 int bytes_pending = BIO_pending(ss->bio_read_);
1448 return scope.Close(Integer::New(bytes_pending));
1452 Handle<Value> Connection::EncPending(const Arguments& args) {
1455 Connection *ss = Connection::Unwrap(args);
1457 int bytes_pending = BIO_pending(ss->bio_write_);
1458 return scope.Close(Integer::New(bytes_pending));
1462 Handle<Value> Connection::EncOut(const Arguments& args) {
1465 Connection *ss = Connection::Unwrap(args);
1467 if (args.Length() < 3) {
1468 return ThrowException(Exception::TypeError(
1469 String::New("Takes 3 parameters")));
1472 if (!Buffer::HasInstance(args[0])) {
1473 return ThrowException(Exception::TypeError(
1474 String::New("Second argument should be a buffer")));
1477 char* buffer_data = Buffer::Data(args[0]);
1478 size_t buffer_length = Buffer::Length(args[0]);
1480 size_t off = args[1]->Int32Value();
1481 size_t len = args[2]->Int32Value();
1482 if (!Buffer::IsWithinBounds(off, len, buffer_length)) {
1483 return ThrowException(Exception::Error(
1484 String::New("off + len > buffer.length")));
1487 int bytes_read = BIO_read(ss->bio_write_, buffer_data + off, len);
1489 ss->HandleBIOError(ss->bio_write_, "BIO_read:EncOut", bytes_read);
1490 ss->SetShutdownFlags();
1492 return scope.Close(Integer::New(bytes_read));
1496 Handle<Value> Connection::ClearIn(const Arguments& args) {
1499 Connection *ss = Connection::Unwrap(args);
1501 if (args.Length() < 3) {
1502 return ThrowException(Exception::TypeError(
1503 String::New("Takes 3 parameters")));
1506 if (!Buffer::HasInstance(args[0])) {
1507 return ThrowException(Exception::TypeError(
1508 String::New("Second argument should be a buffer")));
1511 char* buffer_data = Buffer::Data(args[0]);
1512 size_t buffer_length = Buffer::Length(args[0]);
1514 size_t off = args[1]->Int32Value();
1515 size_t len = args[2]->Int32Value();
1516 if (!Buffer::IsWithinBounds(off, len, buffer_length)) {
1517 return ThrowException(Exception::Error(
1518 String::New("off + len > buffer.length")));
1521 if (!SSL_is_init_finished(ss->ssl_)) {
1523 if (ss->is_server_) {
1524 rv = SSL_accept(ss->ssl_);
1525 ss->HandleSSLError("SSL_accept:ClearIn",
1530 rv = SSL_connect(ss->ssl_);
1531 ss->HandleSSLError("SSL_connect:ClearIn",
1537 if (rv < 0) return scope.Close(Integer::New(rv));
1540 int bytes_written = SSL_write(ss->ssl_, buffer_data + off, len);
1542 ss->HandleSSLError("SSL_write:ClearIn",
1544 len == 0 ? kZeroIsNotAnError : kZeroIsAnError,
1546 ss->SetShutdownFlags();
1548 return scope.Close(Integer::New(bytes_written));
1552 Handle<Value> Connection::GetPeerCertificate(const Arguments& args) {
1555 Connection *ss = Connection::Unwrap(args);
1557 if (ss->ssl_ == NULL) return Undefined();
1558 Local<Object> info = Object::New();
1559 X509* peer_cert = SSL_get_peer_certificate(ss->ssl_);
1560 if (peer_cert != NULL) {
1561 BIO* bio = BIO_new(BIO_s_mem());
1563 if (X509_NAME_print_ex(bio, X509_get_subject_name(peer_cert), 0,
1564 X509_NAME_FLAGS) > 0) {
1565 BIO_get_mem_ptr(bio, &mem);
1566 info->Set(subject_symbol, String::New(mem->data, mem->length));
1568 (void) BIO_reset(bio);
1570 if (X509_NAME_print_ex(bio, X509_get_issuer_name(peer_cert), 0,
1571 X509_NAME_FLAGS) > 0) {
1572 BIO_get_mem_ptr(bio, &mem);
1573 info->Set(issuer_symbol, String::New(mem->data, mem->length));
1575 (void) BIO_reset(bio);
1577 int index = X509_get_ext_by_NID(peer_cert, NID_subject_alt_name, -1);
1579 X509_EXTENSION* ext;
1582 ext = X509_get_ext(peer_cert, index);
1583 assert(ext != NULL);
1585 rv = X509V3_EXT_print(bio, ext, 0, 0);
1588 BIO_get_mem_ptr(bio, &mem);
1589 info->Set(subjectaltname_symbol, String::New(mem->data, mem->length));
1591 (void) BIO_reset(bio);
1594 EVP_PKEY *pkey = NULL;
1596 if( NULL != (pkey = X509_get_pubkey(peer_cert))
1597 && NULL != (rsa = EVP_PKEY_get1_RSA(pkey)) ) {
1598 BN_print(bio, rsa->n);
1599 BIO_get_mem_ptr(bio, &mem);
1600 info->Set(modulus_symbol, String::New(mem->data, mem->length) );
1601 (void) BIO_reset(bio);
1603 BN_print(bio, rsa->e);
1604 BIO_get_mem_ptr(bio, &mem);
1605 info->Set(exponent_symbol, String::New(mem->data, mem->length) );
1606 (void) BIO_reset(bio);
1610 EVP_PKEY_free(pkey);
1618 ASN1_TIME_print(bio, X509_get_notBefore(peer_cert));
1619 BIO_get_mem_ptr(bio, &mem);
1620 info->Set(valid_from_symbol, String::New(mem->data, mem->length));
1621 (void) BIO_reset(bio);
1623 ASN1_TIME_print(bio, X509_get_notAfter(peer_cert));
1624 BIO_get_mem_ptr(bio, &mem);
1625 info->Set(valid_to_symbol, String::New(mem->data, mem->length));
1628 unsigned int md_size, i;
1629 unsigned char md[EVP_MAX_MD_SIZE];
1630 if (X509_digest(peer_cert, EVP_sha1(), md, &md_size)) {
1631 const char hex[] = "0123456789ABCDEF";
1632 char fingerprint[EVP_MAX_MD_SIZE * 3];
1634 for (i = 0; i<md_size; i++) {
1635 fingerprint[3*i] = hex[(md[i] & 0xf0) >> 4];
1636 fingerprint[(3*i)+1] = hex[(md[i] & 0x0f)];
1637 fingerprint[(3*i)+2] = ':';
1641 fingerprint[(3*(md_size-1))+2] = '\0';
1644 fingerprint[0] = '\0';
1647 info->Set(fingerprint_symbol, String::New(fingerprint));
1650 STACK_OF(ASN1_OBJECT) *eku = (STACK_OF(ASN1_OBJECT) *)X509_get_ext_d2i(
1651 peer_cert, NID_ext_key_usage, NULL, NULL);
1653 Local<Array> ext_key_usage = Array::New();
1656 for (int i = 0; i < sk_ASN1_OBJECT_num(eku); i++) {
1657 memset(buf, 0, sizeof(buf));
1658 OBJ_obj2txt(buf, sizeof(buf) - 1, sk_ASN1_OBJECT_value(eku, i), 1);
1659 ext_key_usage->Set(Integer::New(i), String::New(buf));
1662 sk_ASN1_OBJECT_pop_free(eku, ASN1_OBJECT_free);
1663 info->Set(ext_key_usage_symbol, ext_key_usage);
1666 X509_free(peer_cert);
1668 return scope.Close(info);
1671 Handle<Value> Connection::GetSession(const Arguments& args) {
1674 Connection *ss = Connection::Unwrap(args);
1676 if (ss->ssl_ == NULL) return Undefined();
1678 SSL_SESSION* sess = SSL_get_session(ss->ssl_);
1679 if (!sess) return Undefined();
1681 int slen = i2d_SSL_SESSION(sess, NULL);
1685 unsigned char* sbuf = new unsigned char[slen];
1686 unsigned char* p = sbuf;
1687 i2d_SSL_SESSION(sess, &p);
1688 Local<Value> s = Encode(sbuf, slen, BINARY);
1690 return scope.Close(s);
1696 Handle<Value> Connection::SetSession(const Arguments& args) {
1699 Connection *ss = Connection::Unwrap(args);
1701 if (args.Length() < 1 ||
1702 (!args[0]->IsString() && !Buffer::HasInstance(args[0]))) {
1703 Local<Value> exception = Exception::TypeError(String::New("Bad argument"));
1704 return ThrowException(exception);
1707 ASSERT_IS_BUFFER(args[0]);
1708 ssize_t slen = Buffer::Length(args[0]);
1711 Local<Value> exception = Exception::TypeError(String::New("Bad argument"));
1712 return ThrowException(exception);
1715 char* sbuf = new char[slen];
1717 ssize_t wlen = DecodeWrite(sbuf, slen, args[0], BINARY);
1718 assert(wlen == slen);
1720 const unsigned char* p = reinterpret_cast<const unsigned char*>(sbuf);
1721 SSL_SESSION* sess = d2i_SSL_SESSION(NULL, &p, wlen);
1728 int r = SSL_set_session(ss->ssl_, sess);
1729 SSL_SESSION_free(sess);
1732 Local<String> eStr = String::New("SSL_set_session error");
1733 return ThrowException(Exception::Error(eStr));
1739 Handle<Value> Connection::LoadSession(const Arguments& args) {
1742 Connection *ss = Connection::Unwrap(args);
1744 if (args.Length() >= 1 && Buffer::HasInstance(args[0])) {
1745 ssize_t slen = Buffer::Length(args[0].As<Object>());
1746 char* sbuf = Buffer::Data(args[0].As<Object>());
1748 const unsigned char* p = reinterpret_cast<unsigned char*>(sbuf);
1749 SSL_SESSION* sess = d2i_SSL_SESSION(NULL, &p, slen);
1751 // Setup next session and move hello to the BIO buffer
1752 if (ss->next_sess_ != NULL) {
1753 SSL_SESSION_free(ss->next_sess_);
1755 ss->next_sess_ = sess;
1758 ss->hello_parser_.Finish();
1763 Handle<Value> Connection::IsSessionReused(const Arguments& args) {
1766 Connection *ss = Connection::Unwrap(args);
1768 if (ss->ssl_ == NULL || SSL_session_reused(ss->ssl_) == false) {
1776 Handle<Value> Connection::Start(const Arguments& args) {
1779 Connection *ss = Connection::Unwrap(args);
1781 if (!SSL_is_init_finished(ss->ssl_)) {
1783 if (ss->is_server_) {
1784 rv = SSL_accept(ss->ssl_);
1785 ss->HandleSSLError("SSL_accept:Start", rv, kZeroIsAnError, kSyscallError);
1787 rv = SSL_connect(ss->ssl_);
1788 ss->HandleSSLError("SSL_connect:Start",
1794 return scope.Close(Integer::New(rv));
1797 return scope.Close(Integer::New(0));
1801 Handle<Value> Connection::Shutdown(const Arguments& args) {
1804 Connection *ss = Connection::Unwrap(args);
1806 if (ss->ssl_ == NULL) return False();
1807 int rv = SSL_shutdown(ss->ssl_);
1808 ss->HandleSSLError("SSL_shutdown", rv, kZeroIsNotAnError, kIgnoreSyscall);
1809 ss->SetShutdownFlags();
1811 return scope.Close(Integer::New(rv));
1815 Handle<Value> Connection::IsInitFinished(const Arguments& args) {
1818 Connection *ss = Connection::Unwrap(args);
1820 if (ss->ssl_ == NULL || SSL_is_init_finished(ss->ssl_) == false) {
1828 Handle<Value> Connection::VerifyError(const Arguments& args) {
1831 Connection *ss = Connection::Unwrap(args);
1833 if (ss->ssl_ == NULL) return Null();
1836 // XXX Do this check in JS land?
1837 X509* peer_cert = SSL_get_peer_certificate(ss->ssl_);
1838 if (peer_cert == NULL) {
1839 // We requested a certificate and they did not send us one.
1840 // Definitely an error.
1841 // XXX is this the right error message?
1842 return scope.Close(Exception::Error(
1843 String::New("UNABLE_TO_GET_ISSUER_CERT")));
1845 X509_free(peer_cert);
1848 long x509_verify_error = SSL_get_verify_result(ss->ssl_);
1852 switch (x509_verify_error) {
1856 case X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT:
1857 s = String::New("UNABLE_TO_GET_ISSUER_CERT");
1860 case X509_V_ERR_UNABLE_TO_GET_CRL:
1861 s = String::New("UNABLE_TO_GET_CRL");
1864 case X509_V_ERR_UNABLE_TO_DECRYPT_CERT_SIGNATURE:
1865 s = String::New("UNABLE_TO_DECRYPT_CERT_SIGNATURE");
1868 case X509_V_ERR_UNABLE_TO_DECRYPT_CRL_SIGNATURE:
1869 s = String::New("UNABLE_TO_DECRYPT_CRL_SIGNATURE");
1872 case X509_V_ERR_UNABLE_TO_DECODE_ISSUER_PUBLIC_KEY:
1873 s = String::New("UNABLE_TO_DECODE_ISSUER_PUBLIC_KEY");
1876 case X509_V_ERR_CERT_SIGNATURE_FAILURE:
1877 s = String::New("CERT_SIGNATURE_FAILURE");
1880 case X509_V_ERR_CRL_SIGNATURE_FAILURE:
1881 s = String::New("CRL_SIGNATURE_FAILURE");
1884 case X509_V_ERR_CERT_NOT_YET_VALID:
1885 s = String::New("CERT_NOT_YET_VALID");
1888 case X509_V_ERR_CERT_HAS_EXPIRED:
1889 s = String::New("CERT_HAS_EXPIRED");
1892 case X509_V_ERR_CRL_NOT_YET_VALID:
1893 s = String::New("CRL_NOT_YET_VALID");
1896 case X509_V_ERR_CRL_HAS_EXPIRED:
1897 s = String::New("CRL_HAS_EXPIRED");
1900 case X509_V_ERR_ERROR_IN_CERT_NOT_BEFORE_FIELD:
1901 s = String::New("ERROR_IN_CERT_NOT_BEFORE_FIELD");
1904 case X509_V_ERR_ERROR_IN_CERT_NOT_AFTER_FIELD:
1905 s = String::New("ERROR_IN_CERT_NOT_AFTER_FIELD");
1908 case X509_V_ERR_ERROR_IN_CRL_LAST_UPDATE_FIELD:
1909 s = String::New("ERROR_IN_CRL_LAST_UPDATE_FIELD");
1912 case X509_V_ERR_ERROR_IN_CRL_NEXT_UPDATE_FIELD:
1913 s = String::New("ERROR_IN_CRL_NEXT_UPDATE_FIELD");
1916 case X509_V_ERR_OUT_OF_MEM:
1917 s = String::New("OUT_OF_MEM");
1920 case X509_V_ERR_DEPTH_ZERO_SELF_SIGNED_CERT:
1921 s = String::New("DEPTH_ZERO_SELF_SIGNED_CERT");
1924 case X509_V_ERR_SELF_SIGNED_CERT_IN_CHAIN:
1925 s = String::New("SELF_SIGNED_CERT_IN_CHAIN");
1928 case X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT_LOCALLY:
1929 s = String::New("UNABLE_TO_GET_ISSUER_CERT_LOCALLY");
1932 case X509_V_ERR_UNABLE_TO_VERIFY_LEAF_SIGNATURE:
1933 s = String::New("UNABLE_TO_VERIFY_LEAF_SIGNATURE");
1936 case X509_V_ERR_CERT_CHAIN_TOO_LONG:
1937 s = String::New("CERT_CHAIN_TOO_LONG");
1940 case X509_V_ERR_CERT_REVOKED:
1941 s = String::New("CERT_REVOKED");
1944 case X509_V_ERR_INVALID_CA:
1945 s = String::New("INVALID_CA");
1948 case X509_V_ERR_PATH_LENGTH_EXCEEDED:
1949 s = String::New("PATH_LENGTH_EXCEEDED");
1952 case X509_V_ERR_INVALID_PURPOSE:
1953 s = String::New("INVALID_PURPOSE");
1956 case X509_V_ERR_CERT_UNTRUSTED:
1957 s = String::New("CERT_UNTRUSTED");
1960 case X509_V_ERR_CERT_REJECTED:
1961 s = String::New("CERT_REJECTED");
1965 s = String::New(X509_verify_cert_error_string(x509_verify_error));
1969 return scope.Close(Exception::Error(s));
1973 Handle<Value> Connection::GetCurrentCipher(const Arguments& args) {
1976 Connection *ss = Connection::Unwrap(args);
1978 OPENSSL_CONST SSL_CIPHER *c;
1980 if ( ss->ssl_ == NULL ) return Undefined();
1981 c = SSL_get_current_cipher(ss->ssl_);
1982 if ( c == NULL ) return Undefined();
1983 Local<Object> info = Object::New();
1984 const char* cipher_name = SSL_CIPHER_get_name(c);
1985 info->Set(name_symbol, String::New(cipher_name));
1986 const char* cipher_version = SSL_CIPHER_get_version(c);
1987 info->Set(version_symbol, String::New(cipher_version));
1988 return scope.Close(info);
1991 Handle<Value> Connection::Close(const Arguments& args) {
1994 Connection *ss = Connection::Unwrap(args);
1996 if (ss->ssl_ != NULL) {
2004 void Connection::InitNPN(SecureContext* sc, bool is_server) {
2005 #ifdef OPENSSL_NPN_NEGOTIATED
2007 // Server should advertise NPN protocols
2008 SSL_CTX_set_next_protos_advertised_cb(sc->ctx_,
2009 AdvertiseNextProtoCallback_,
2012 // Client should select protocol from advertised
2013 // If server supports NPN
2014 SSL_CTX_set_next_proto_select_cb(sc->ctx_,
2015 SelectNextProtoCallback_,
2021 #ifdef OPENSSL_NPN_NEGOTIATED
2022 Handle<Value> Connection::GetNegotiatedProto(const Arguments& args) {
2025 Connection *ss = Connection::Unwrap(args);
2027 if (ss->is_server_) {
2028 const unsigned char* npn_proto;
2029 unsigned int npn_proto_len;
2031 SSL_get0_next_proto_negotiated(ss->ssl_, &npn_proto, &npn_proto_len);
2037 return scope.Close(String::New(reinterpret_cast<const char*>(npn_proto),
2040 return ss->selectedNPNProto_;
2044 Handle<Value> Connection::SetNPNProtocols(const Arguments& args) {
2047 Connection *ss = Connection::Unwrap(args);
2049 if (args.Length() < 1 || !Buffer::HasInstance(args[0])) {
2050 return ThrowException(Exception::Error(String::New(
2051 "Must give a Buffer as first argument")));
2054 // Release old handle
2055 if (!ss->npnProtos_.IsEmpty()) {
2056 ss->npnProtos_.Dispose();
2058 ss->npnProtos_ = Persistent<Object>::New(args[0]->ToObject());
2064 #ifdef SSL_CTRL_SET_TLSEXT_SERVERNAME_CB
2065 Handle<Value> Connection::GetServername(const Arguments& args) {
2068 Connection *ss = Connection::Unwrap(args);
2070 if (ss->is_server_ && !ss->servername_.IsEmpty()) {
2071 return ss->servername_;
2077 Handle<Value> Connection::SetSNICallback(const Arguments& args) {
2080 Connection *ss = Connection::Unwrap(args);
2082 if (args.Length() < 1 || !args[0]->IsFunction()) {
2083 return ThrowException(Exception::Error(String::New(
2084 "Must give a Function as first argument")));
2087 // Release old handle
2088 if (!ss->sniObject_.IsEmpty()) {
2089 ss->sniObject_.Dispose();
2091 ss->sniObject_ = Persistent<Object>::New(Object::New());
2092 ss->sniObject_->Set(String::New("onselect"), args[0]);
2099 class Cipher : public ObjectWrap {
2101 static void Initialize (v8::Handle<v8::Object> target) {
2104 Local<FunctionTemplate> t = FunctionTemplate::New(New);
2106 t->InstanceTemplate()->SetInternalFieldCount(1);
2108 NODE_SET_PROTOTYPE_METHOD(t, "init", CipherInit);
2109 NODE_SET_PROTOTYPE_METHOD(t, "initiv", CipherInitIv);
2110 NODE_SET_PROTOTYPE_METHOD(t, "update", CipherUpdate);
2111 NODE_SET_PROTOTYPE_METHOD(t, "setAutoPadding", SetAutoPadding);
2112 NODE_SET_PROTOTYPE_METHOD(t, "final", CipherFinal);
2114 target->Set(String::NewSymbol("Cipher"), t->GetFunction());
2118 bool CipherInit(char* cipherType, char* key_buf, int key_buf_len) {
2119 cipher = EVP_get_cipherbyname(cipherType);
2121 fprintf(stderr, "node-crypto : Unknown cipher %s\n", cipherType);
2125 unsigned char key[EVP_MAX_KEY_LENGTH],iv[EVP_MAX_IV_LENGTH];
2126 int key_len = EVP_BytesToKey(cipher, EVP_md5(), NULL,
2127 (unsigned char*) key_buf, key_buf_len, 1, key, iv);
2129 EVP_CIPHER_CTX_init(&ctx);
2130 EVP_CipherInit_ex(&ctx, cipher, NULL, NULL, NULL, true);
2131 if (!EVP_CIPHER_CTX_set_key_length(&ctx, key_len)) {
2132 fprintf(stderr, "node-crypto : Invalid key length %d\n", key_len);
2133 EVP_CIPHER_CTX_cleanup(&ctx);
2136 EVP_CipherInit_ex(&ctx, NULL, NULL,
2137 (unsigned char*)key,
2138 (unsigned char*)iv, true);
2139 initialised_ = true;
2144 bool CipherInitIv(char* cipherType,
2149 cipher = EVP_get_cipherbyname(cipherType);
2151 fprintf(stderr, "node-crypto : Unknown cipher %s\n", cipherType);
2154 /* OpenSSL versions up to 0.9.8l failed to return the correct
2155 iv_length (0) for ECB ciphers */
2156 if (EVP_CIPHER_iv_length(cipher) != iv_len &&
2157 !(EVP_CIPHER_mode(cipher) == EVP_CIPH_ECB_MODE && iv_len == 0)) {
2158 fprintf(stderr, "node-crypto : Invalid IV length %d\n", iv_len);
2161 EVP_CIPHER_CTX_init(&ctx);
2162 EVP_CipherInit_ex(&ctx, cipher, NULL, NULL, NULL, true);
2163 if (!EVP_CIPHER_CTX_set_key_length(&ctx, key_len)) {
2164 fprintf(stderr, "node-crypto : Invalid key length %d\n", key_len);
2165 EVP_CIPHER_CTX_cleanup(&ctx);
2168 EVP_CipherInit_ex(&ctx, NULL, NULL,
2169 (unsigned char*)key,
2170 (unsigned char*)iv, true);
2171 initialised_ = true;
2175 int CipherUpdate(char* data, int len, unsigned char** out, int* out_len) {
2176 if (!initialised_) return 0;
2177 *out_len = len+EVP_CIPHER_CTX_block_size(&ctx);
2178 *out = new unsigned char[*out_len];
2179 return EVP_CipherUpdate(&ctx, *out, out_len, (unsigned char*)data, len);
2182 int SetAutoPadding(bool auto_padding) {
2183 if (!initialised_) return 0;
2184 return EVP_CIPHER_CTX_set_padding(&ctx, auto_padding ? 1 : 0);
2187 int CipherFinal(unsigned char** out, int *out_len) {
2188 if (!initialised_) return 0;
2189 *out = new unsigned char[EVP_CIPHER_CTX_block_size(&ctx)];
2190 int r = EVP_CipherFinal_ex(&ctx,*out, out_len);
2191 EVP_CIPHER_CTX_cleanup(&ctx);
2192 initialised_ = false;
2199 static Handle<Value> New(const Arguments& args) {
2202 Cipher *cipher = new Cipher();
2203 cipher->Wrap(args.This());
2207 static Handle<Value> CipherInit(const Arguments& args) {
2210 Cipher *cipher = ObjectWrap::Unwrap<Cipher>(args.This());
2212 if (args.Length() <= 1
2213 || !args[0]->IsString()
2214 || !(args[1]->IsString() || Buffer::HasInstance(args[1])))
2216 return ThrowException(Exception::Error(String::New(
2217 "Must give cipher-type, key")));
2220 ASSERT_IS_BUFFER(args[1]);
2221 ssize_t key_buf_len = Buffer::Length(args[1]);
2223 if (key_buf_len < 0) {
2224 Local<Value> exception = Exception::TypeError(String::New("Bad argument"));
2225 return ThrowException(exception);
2228 char* key_buf = new char[key_buf_len];
2229 ssize_t key_written = DecodeWrite(key_buf, key_buf_len, args[1], BINARY);
2230 assert(key_written == key_buf_len);
2232 String::Utf8Value cipherType(args[0]);
2234 bool r = cipher->CipherInit(*cipherType, key_buf, key_buf_len);
2238 if (!r) return ThrowCryptoError(ERR_get_error());
2244 static Handle<Value> CipherInitIv(const Arguments& args) {
2245 Cipher *cipher = ObjectWrap::Unwrap<Cipher>(args.This());
2250 if (args.Length() <= 2
2251 || !args[0]->IsString()
2252 || !(args[1]->IsString() || Buffer::HasInstance(args[1]))
2253 || !(args[2]->IsString() || Buffer::HasInstance(args[2])))
2255 return ThrowException(Exception::Error(String::New(
2256 "Must give cipher-type, key, and iv as argument")));
2259 ASSERT_IS_BUFFER(args[1]);
2260 ssize_t key_len = Buffer::Length(args[1]);
2263 Local<Value> exception = Exception::TypeError(String::New("Bad argument"));
2264 return ThrowException(exception);
2267 ASSERT_IS_BUFFER(args[2]);
2268 ssize_t iv_len = Buffer::Length(args[2]);
2271 Local<Value> exception = Exception::TypeError(String::New("Bad argument"));
2272 return ThrowException(exception);
2275 char* key_buf = new char[key_len];
2276 ssize_t key_written = DecodeWrite(key_buf, key_len, args[1], BINARY);
2277 assert(key_written == key_len);
2279 char* iv_buf = new char[iv_len];
2280 ssize_t iv_written = DecodeWrite(iv_buf, iv_len, args[2], BINARY);
2281 assert(iv_written == iv_len);
2283 String::Utf8Value cipherType(args[0]);
2285 bool r = cipher->CipherInitIv(*cipherType, key_buf,key_len,iv_buf,iv_len);
2290 if (!r) return ThrowCryptoError(ERR_get_error());
2295 static Handle<Value> CipherUpdate(const Arguments& args) {
2296 Cipher *cipher = ObjectWrap::Unwrap<Cipher>(args.This());
2300 ASSERT_IS_STRING_OR_BUFFER(args[0]);
2302 // Only copy the data if we have to, because it's a string
2303 unsigned char* out = 0;
2305 if (args[0]->IsString()) {
2306 Local<String> string = args[0].As<String>();
2307 enum encoding encoding = ParseEncoding(args[1], BINARY);
2308 if (!StringBytes::IsValidString(string, encoding))
2309 return ThrowTypeError("Bad input string");
2310 size_t buflen = StringBytes::StorageSize(string, encoding);
2311 char* buf = new char[buflen];
2312 size_t written = StringBytes::Write(buf, buflen, string, encoding);
2313 r = cipher->CipherUpdate(buf, written, &out, &out_len);
2316 char* buf = Buffer::Data(args[0]);
2317 size_t buflen = Buffer::Length(args[0]);
2318 r = cipher->CipherUpdate(buf, buflen, &out, &out_len);
2323 return ThrowCryptoTypeError(ERR_get_error());
2326 Local<Value> outString;
2327 outString = Encode(out, out_len, BUFFER);
2329 if (out) delete[] out;
2331 return scope.Close(outString);
2334 static Handle<Value> SetAutoPadding(const Arguments& args) {
2336 Cipher *cipher = ObjectWrap::Unwrap<Cipher>(args.This());
2338 cipher->SetAutoPadding(args.Length() < 1 || args[0]->BooleanValue());
2343 static Handle<Value> CipherFinal(const Arguments& args) {
2344 Cipher *cipher = ObjectWrap::Unwrap<Cipher>(args.This());
2348 unsigned char* out_value = NULL;
2350 Local<Value> outString ;
2352 int r = cipher->CipherFinal(&out_value, &out_len);
2354 if (out_len <= 0 || r == 0) {
2357 if (r == 0) return ThrowCryptoTypeError(ERR_get_error());
2360 outString = Encode(out_value, out_len, BUFFER);
2362 delete [] out_value;
2363 return scope.Close(outString);
2366 Cipher () : ObjectWrap ()
2368 initialised_ = false;
2373 EVP_CIPHER_CTX_cleanup(&ctx);
2379 EVP_CIPHER_CTX ctx; /* coverity[member_decl] */
2380 const EVP_CIPHER *cipher; /* coverity[member_decl] */
2386 class Decipher : public ObjectWrap {
2389 Initialize (v8::Handle<v8::Object> target)
2393 Local<FunctionTemplate> t = FunctionTemplate::New(New);
2395 t->InstanceTemplate()->SetInternalFieldCount(1);
2397 NODE_SET_PROTOTYPE_METHOD(t, "init", DecipherInit);
2398 NODE_SET_PROTOTYPE_METHOD(t, "initiv", DecipherInitIv);
2399 NODE_SET_PROTOTYPE_METHOD(t, "update", DecipherUpdate);
2400 NODE_SET_PROTOTYPE_METHOD(t, "final", DecipherFinal);
2401 NODE_SET_PROTOTYPE_METHOD(t, "finaltol", DecipherFinal); // remove someday
2402 NODE_SET_PROTOTYPE_METHOD(t, "setAutoPadding", SetAutoPadding);
2404 target->Set(String::NewSymbol("Decipher"), t->GetFunction());
2407 bool DecipherInit(char* cipherType, char* key_buf, int key_buf_len) {
2408 cipher_ = EVP_get_cipherbyname(cipherType);
2411 fprintf(stderr, "node-crypto : Unknown cipher %s\n", cipherType);
2415 unsigned char key[EVP_MAX_KEY_LENGTH],iv[EVP_MAX_IV_LENGTH];
2416 int key_len = EVP_BytesToKey(cipher_,
2419 (unsigned char*)(key_buf),
2425 EVP_CIPHER_CTX_init(&ctx);
2426 EVP_CipherInit_ex(&ctx, cipher_, NULL, NULL, NULL, false);
2427 if (!EVP_CIPHER_CTX_set_key_length(&ctx, key_len)) {
2428 fprintf(stderr, "node-crypto : Invalid key length %d\n", key_len);
2429 EVP_CIPHER_CTX_cleanup(&ctx);
2432 EVP_CipherInit_ex(&ctx, NULL, NULL,
2433 (unsigned char*)key,
2434 (unsigned char*)iv, false);
2435 initialised_ = true;
2440 bool DecipherInitIv(char* cipherType,
2445 cipher_ = EVP_get_cipherbyname(cipherType);
2447 fprintf(stderr, "node-crypto : Unknown cipher %s\n", cipherType);
2450 /* OpenSSL versions up to 0.9.8l failed to return the correct
2451 iv_length (0) for ECB ciphers */
2452 if (EVP_CIPHER_iv_length(cipher_) != iv_len &&
2453 !(EVP_CIPHER_mode(cipher_) == EVP_CIPH_ECB_MODE && iv_len == 0)) {
2454 fprintf(stderr, "node-crypto : Invalid IV length %d\n", iv_len);
2457 EVP_CIPHER_CTX_init(&ctx);
2458 EVP_CipherInit_ex(&ctx, cipher_, NULL, NULL, NULL, false);
2459 if (!EVP_CIPHER_CTX_set_key_length(&ctx, key_len)) {
2460 fprintf(stderr, "node-crypto : Invalid key length %d\n", key_len);
2461 EVP_CIPHER_CTX_cleanup(&ctx);
2464 EVP_CipherInit_ex(&ctx, NULL, NULL,
2465 (unsigned char*)key,
2466 (unsigned char*)iv, false);
2467 initialised_ = true;
2471 int DecipherUpdate(char* data, int len, unsigned char** out, int* out_len) {
2472 if (!initialised_) {
2478 *out_len = len+EVP_CIPHER_CTX_block_size(&ctx);
2479 *out = new unsigned char[*out_len];
2481 return EVP_CipherUpdate(&ctx, *out, out_len, (unsigned char*)data, len);
2484 int SetAutoPadding(bool auto_padding) {
2485 if (!initialised_) return 0;
2486 return EVP_CIPHER_CTX_set_padding(&ctx, auto_padding ? 1 : 0);
2489 // coverity[alloc_arg]
2490 int DecipherFinal(unsigned char** out, int *out_len) {
2493 if (!initialised_) {
2499 *out = new unsigned char[EVP_CIPHER_CTX_block_size(&ctx)];
2500 r = EVP_CipherFinal_ex(&ctx,*out,out_len);
2501 EVP_CIPHER_CTX_cleanup(&ctx);
2502 initialised_ = false;
2509 static Handle<Value> New (const Arguments& args) {
2512 Decipher *cipher = new Decipher();
2513 cipher->Wrap(args.This());
2517 static Handle<Value> DecipherInit(const Arguments& args) {
2518 Decipher *cipher = ObjectWrap::Unwrap<Decipher>(args.This());
2522 if (args.Length() <= 1
2523 || !args[0]->IsString()
2524 || !(args[1]->IsString() || Buffer::HasInstance(args[1])))
2526 return ThrowException(Exception::Error(String::New(
2527 "Must give cipher-type, key as argument")));
2530 ASSERT_IS_BUFFER(args[1]);
2531 ssize_t key_len = Buffer::Length(args[1]);
2534 Local<Value> exception = Exception::TypeError(String::New("Bad argument"));
2535 return ThrowException(exception);
2538 char* key_buf = new char[key_len];
2539 ssize_t key_written = DecodeWrite(key_buf, key_len, args[1], BINARY);
2540 assert(key_written == key_len);
2542 String::Utf8Value cipherType(args[0]);
2544 bool r = cipher->DecipherInit(*cipherType, key_buf,key_len);
2549 return ThrowException(Exception::Error(String::New("DecipherInit error")));
2555 static Handle<Value> DecipherInitIv(const Arguments& args) {
2556 Decipher *cipher = ObjectWrap::Unwrap<Decipher>(args.This());
2560 if (args.Length() <= 2
2561 || !args[0]->IsString()
2562 || !(args[1]->IsString() || Buffer::HasInstance(args[1]))
2563 || !(args[2]->IsString() || Buffer::HasInstance(args[2])))
2565 return ThrowException(Exception::Error(String::New(
2566 "Must give cipher-type, key, and iv as argument")));
2569 ASSERT_IS_BUFFER(args[1]);
2570 ssize_t key_len = Buffer::Length(args[1]);
2573 Local<Value> exception = Exception::TypeError(String::New("Bad argument"));
2574 return ThrowException(exception);
2577 ASSERT_IS_BUFFER(args[2]);
2578 ssize_t iv_len = Buffer::Length(args[2]);
2581 Local<Value> exception = Exception::TypeError(String::New("Bad argument"));
2582 return ThrowException(exception);
2585 char* key_buf = new char[key_len];
2586 ssize_t key_written = DecodeWrite(key_buf, key_len, args[1], BINARY);
2587 assert(key_written == key_len);
2589 char* iv_buf = new char[iv_len];
2590 ssize_t iv_written = DecodeWrite(iv_buf, iv_len, args[2], BINARY);
2591 assert(iv_written == iv_len);
2593 String::Utf8Value cipherType(args[0]);
2595 bool r = cipher->DecipherInitIv(*cipherType, key_buf,key_len,iv_buf,iv_len);
2601 return ThrowException(Exception::Error(String::New("DecipherInitIv error")));
2607 static Handle<Value> DecipherUpdate(const Arguments& args) {
2610 Decipher *cipher = ObjectWrap::Unwrap<Decipher>(args.This());
2612 ASSERT_IS_STRING_OR_BUFFER(args[0]);
2614 // Only copy the data if we have to, because it's a string
2615 unsigned char* out = 0;
2617 if (args[0]->IsString()) {
2618 Local<String> string = args[0].As<String>();
2619 enum encoding encoding = ParseEncoding(args[1], BINARY);
2620 if (!StringBytes::IsValidString(string, encoding))
2621 return ThrowTypeError("Bad input string");
2622 size_t buflen = StringBytes::StorageSize(string, encoding);
2623 char* buf = new char[buflen];
2624 size_t written = StringBytes::Write(buf, buflen, string, encoding);
2625 r = cipher->DecipherUpdate(buf, written, &out, &out_len);
2628 char* buf = Buffer::Data(args[0]);
2629 size_t buflen = Buffer::Length(args[0]);
2630 r = cipher->DecipherUpdate(buf, buflen, &out, &out_len);
2635 return ThrowCryptoTypeError(ERR_get_error());
2638 Local<Value> outString;
2639 outString = Encode(out, out_len, BUFFER);
2641 if (out) delete [] out;
2643 return scope.Close(outString);
2646 static Handle<Value> SetAutoPadding(const Arguments& args) {
2648 Decipher *cipher = ObjectWrap::Unwrap<Decipher>(args.This());
2650 cipher->SetAutoPadding(args.Length() < 1 || args[0]->BooleanValue());
2655 static Handle<Value> DecipherFinal(const Arguments& args) {
2658 Decipher *cipher = ObjectWrap::Unwrap<Decipher>(args.This());
2660 unsigned char* out_value = NULL;
2662 Local<Value> outString;
2664 int r = cipher->DecipherFinal(&out_value, &out_len);
2666 if (out_len <= 0 || r == 0) {
2667 delete [] out_value; // allocated even if out_len == 0
2669 if (r == 0) return ThrowCryptoTypeError(ERR_get_error());
2672 outString = Encode(out_value, out_len, BUFFER);
2673 delete [] out_value;
2674 return scope.Close(outString);
2677 Decipher () : ObjectWrap () {
2678 initialised_ = false;
2683 EVP_CIPHER_CTX_cleanup(&ctx);
2690 const EVP_CIPHER *cipher_;
2697 class Hmac : public ObjectWrap {
2699 static void Initialize (v8::Handle<v8::Object> target) {
2702 Local<FunctionTemplate> t = FunctionTemplate::New(New);
2704 t->InstanceTemplate()->SetInternalFieldCount(1);
2706 NODE_SET_PROTOTYPE_METHOD(t, "init", HmacInit);
2707 NODE_SET_PROTOTYPE_METHOD(t, "update", HmacUpdate);
2708 NODE_SET_PROTOTYPE_METHOD(t, "digest", HmacDigest);
2710 target->Set(String::NewSymbol("Hmac"), t->GetFunction());
2713 bool HmacInit(char* hashType, char* key, int key_len) {
2714 md = EVP_get_digestbyname(hashType);
2716 fprintf(stderr, "node-crypto : Unknown message digest %s\n", hashType);
2719 HMAC_CTX_init(&ctx);
2721 HMAC_Init(&ctx, "", 0, md);
2723 HMAC_Init(&ctx, key, key_len, md);
2725 initialised_ = true;
2730 int HmacUpdate(char* data, int len) {
2731 if (!initialised_) return 0;
2732 HMAC_Update(&ctx, (unsigned char*)data, len);
2736 int HmacDigest(unsigned char** md_value, unsigned int *md_len) {
2737 if (!initialised_) return 0;
2738 *md_value = new unsigned char[EVP_MAX_MD_SIZE];
2739 HMAC_Final(&ctx, *md_value, md_len);
2740 HMAC_CTX_cleanup(&ctx);
2741 initialised_ = false;
2748 static Handle<Value> New (const Arguments& args) {
2751 Hmac *hmac = new Hmac();
2752 hmac->Wrap(args.This());
2756 static Handle<Value> HmacInit(const Arguments& args) {
2757 Hmac *hmac = ObjectWrap::Unwrap<Hmac>(args.This());
2761 if (args.Length() == 0 || !args[0]->IsString()) {
2762 return ThrowException(Exception::Error(String::New(
2763 "Must give hashtype string as argument")));
2766 ASSERT_IS_BUFFER(args[1]);
2767 ssize_t len = Buffer::Length(args[1]);
2770 Local<Value> exception = Exception::TypeError(String::New("Bad argument"));
2771 return ThrowException(exception);
2774 String::Utf8Value hashType(args[0]);
2778 if( Buffer::HasInstance(args[1])) {
2779 char* buffer_data = Buffer::Data(args[1]);
2780 size_t buffer_length = Buffer::Length(args[1]);
2782 r = hmac->HmacInit(*hashType, buffer_data, buffer_length);
2784 char* buf = new char[len];
2785 ssize_t written = DecodeWrite(buf, len, args[1], BINARY);
2786 assert(written == len);
2788 r = hmac->HmacInit(*hashType, buf, len);
2794 return ThrowException(Exception::Error(String::New("hmac error")));
2800 static Handle<Value> HmacUpdate(const Arguments& args) {
2801 Hmac *hmac = ObjectWrap::Unwrap<Hmac>(args.This());
2805 ASSERT_IS_STRING_OR_BUFFER(args[0]);
2807 // Only copy the data if we have to, because it's a string
2809 if (args[0]->IsString()) {
2810 Local<String> string = args[0].As<String>();
2811 enum encoding encoding = ParseEncoding(args[1], BINARY);
2812 if (!StringBytes::IsValidString(string, encoding))
2813 return ThrowTypeError("Bad input string");
2814 size_t buflen = StringBytes::StorageSize(string, encoding);
2815 char* buf = new char[buflen];
2816 size_t written = StringBytes::Write(buf, buflen, string, encoding);
2817 r = hmac->HmacUpdate(buf, written);
2820 char* buf = Buffer::Data(args[0]);
2821 size_t buflen = Buffer::Length(args[0]);
2822 r = hmac->HmacUpdate(buf, buflen);
2826 Local<Value> exception = Exception::TypeError(String::New("HmacUpdate fail"));
2827 return ThrowException(exception);
2833 static Handle<Value> HmacDigest(const Arguments& args) {
2834 Hmac *hmac = ObjectWrap::Unwrap<Hmac>(args.This());
2838 enum encoding encoding = BUFFER;
2839 if (args.Length() >= 1) {
2840 encoding = ParseEncoding(args[0]->ToString(), BUFFER);
2843 unsigned char* md_value = NULL;
2844 unsigned int md_len = 0;
2845 Local<Value> outString;
2847 int r = hmac->HmacDigest(&md_value, &md_len);
2853 outString = StringBytes::Encode(
2854 reinterpret_cast<const char*>(md_value), md_len, encoding);
2857 return scope.Close(outString);
2860 Hmac () : ObjectWrap () {
2861 initialised_ = false;
2866 HMAC_CTX_cleanup(&ctx);
2872 HMAC_CTX ctx; /* coverity[member_decl] */
2873 const EVP_MD *md; /* coverity[member_decl] */
2878 class Hash : public ObjectWrap {
2880 static void Initialize (v8::Handle<v8::Object> target) {
2883 Local<FunctionTemplate> t = FunctionTemplate::New(New);
2885 t->InstanceTemplate()->SetInternalFieldCount(1);
2887 NODE_SET_PROTOTYPE_METHOD(t, "update", HashUpdate);
2888 NODE_SET_PROTOTYPE_METHOD(t, "digest", HashDigest);
2890 target->Set(String::NewSymbol("Hash"), t->GetFunction());
2893 bool HashInit (const char* hashType) {
2894 md = EVP_get_digestbyname(hashType);
2895 if(!md) return false;
2896 EVP_MD_CTX_init(&mdctx);
2897 EVP_DigestInit_ex(&mdctx, md, NULL);
2898 initialised_ = true;
2902 int HashUpdate(char* data, int len) {
2903 if (!initialised_) return 0;
2904 EVP_DigestUpdate(&mdctx, data, len);
2911 static Handle<Value> New (const Arguments& args) {
2914 if (args.Length() == 0 || !args[0]->IsString()) {
2915 return ThrowException(Exception::Error(String::New(
2916 "Must give hashtype string as argument")));
2919 String::Utf8Value hashType(args[0]);
2921 Hash *hash = new Hash();
2922 if (!hash->HashInit(*hashType)) {
2924 return ThrowException(Exception::Error(String::New(
2925 "Digest method not supported")));
2928 hash->Wrap(args.This());
2932 static Handle<Value> HashUpdate(const Arguments& args) {
2935 Hash *hash = ObjectWrap::Unwrap<Hash>(args.This());
2937 ASSERT_IS_STRING_OR_BUFFER(args[0]);
2939 // Only copy the data if we have to, because it's a string
2941 if (args[0]->IsString()) {
2942 Local<String> string = args[0].As<String>();
2943 enum encoding encoding = ParseEncoding(args[1], BINARY);
2944 if (!StringBytes::IsValidString(string, encoding))
2945 return ThrowTypeError("Bad input string");
2946 size_t buflen = StringBytes::StorageSize(string, encoding);
2947 char* buf = new char[buflen];
2948 size_t written = StringBytes::Write(buf, buflen, string, encoding);
2949 r = hash->HashUpdate(buf, written);
2952 char* buf = Buffer::Data(args[0]);
2953 size_t buflen = Buffer::Length(args[0]);
2954 r = hash->HashUpdate(buf, buflen);
2958 Local<Value> exception = Exception::TypeError(String::New("HashUpdate fail"));
2959 return ThrowException(exception);
2965 static Handle<Value> HashDigest(const Arguments& args) {
2968 Hash *hash = ObjectWrap::Unwrap<Hash>(args.This());
2970 if (!hash->initialised_) {
2971 return ThrowException(Exception::Error(String::New("Not initialized")));
2974 enum encoding encoding = BUFFER;
2975 if (args.Length() >= 1) {
2976 encoding = ParseEncoding(args[0]->ToString(), BUFFER);
2979 unsigned char md_value[EVP_MAX_MD_SIZE];
2980 unsigned int md_len;
2982 EVP_DigestFinal_ex(&hash->mdctx, md_value, &md_len);
2983 EVP_MD_CTX_cleanup(&hash->mdctx);
2984 hash->initialised_ = false;
2986 return scope.Close(StringBytes::Encode(
2987 reinterpret_cast<const char*>(md_value), md_len, encoding));
2990 Hash () : ObjectWrap () {
2991 initialised_ = false;
2996 EVP_MD_CTX_cleanup(&mdctx);
3002 EVP_MD_CTX mdctx; /* coverity[member_decl] */
3003 const EVP_MD *md; /* coverity[member_decl] */
3007 class Sign : public ObjectWrap {
3010 Initialize (v8::Handle<v8::Object> target) {
3013 Local<FunctionTemplate> t = FunctionTemplate::New(New);
3015 t->InstanceTemplate()->SetInternalFieldCount(1);
3017 NODE_SET_PROTOTYPE_METHOD(t, "init", SignInit);
3018 NODE_SET_PROTOTYPE_METHOD(t, "update", SignUpdate);
3019 NODE_SET_PROTOTYPE_METHOD(t, "sign", SignFinal);
3021 target->Set(String::NewSymbol("Sign"), t->GetFunction());
3024 bool SignInit (const char* signType) {
3025 md = EVP_get_digestbyname(signType);
3027 printf("Unknown message digest %s\n", signType);
3030 EVP_MD_CTX_init(&mdctx);
3031 EVP_SignInit_ex(&mdctx, md, NULL);
3032 initialised_ = true;
3037 int SignUpdate(char* data, int len) {
3038 if (!initialised_) return 0;
3039 EVP_SignUpdate(&mdctx, data, len);
3043 int SignFinal(unsigned char** md_value,
3044 unsigned int *md_len,
3047 if (!initialised_) return 0;
3051 bp = BIO_new(BIO_s_mem());
3052 if(!BIO_write(bp, key_pem, key_pemLen)) return 0;
3054 pkey = PEM_read_bio_PrivateKey( bp, NULL, NULL, NULL );
3056 ERR_print_errors_fp(stderr);
3060 if (!EVP_SignFinal(&mdctx, *md_value, md_len, pkey)) {
3061 ERR_print_errors_fp(stderr);
3064 EVP_MD_CTX_cleanup(&mdctx);
3065 initialised_ = false;
3066 EVP_PKEY_free(pkey);
3074 static Handle<Value> New (const Arguments& args) {
3077 Sign *sign = new Sign();
3078 sign->Wrap(args.This());
3083 static Handle<Value> SignInit(const Arguments& args) {
3086 Sign *sign = ObjectWrap::Unwrap<Sign>(args.This());
3088 if (args.Length() == 0 || !args[0]->IsString()) {
3089 return ThrowException(Exception::Error(String::New(
3090 "Must give signtype string as argument")));
3093 String::Utf8Value signType(args[0]);
3095 bool r = sign->SignInit(*signType);
3098 return ThrowException(Exception::Error(String::New("SignInit error")));
3104 static Handle<Value> SignUpdate(const Arguments& args) {
3105 Sign *sign = ObjectWrap::Unwrap<Sign>(args.This());
3109 ASSERT_IS_STRING_OR_BUFFER(args[0]);
3111 // Only copy the data if we have to, because it's a string
3113 if (args[0]->IsString()) {
3114 Local<String> string = args[0].As<String>();
3115 enum encoding encoding = ParseEncoding(args[1], BINARY);
3116 if (!StringBytes::IsValidString(string, encoding))
3117 return ThrowTypeError("Bad input string");
3118 size_t buflen = StringBytes::StorageSize(string, encoding);
3119 char* buf = new char[buflen];
3120 size_t written = StringBytes::Write(buf, buflen, string, encoding);
3121 r = sign->SignUpdate(buf, written);
3124 char* buf = Buffer::Data(args[0]);
3125 size_t buflen = Buffer::Length(args[0]);
3126 r = sign->SignUpdate(buf, buflen);
3130 Local<Value> exception = Exception::TypeError(String::New("SignUpdate fail"));
3131 return ThrowException(exception);
3137 static Handle<Value> SignFinal(const Arguments& args) {
3138 Sign *sign = ObjectWrap::Unwrap<Sign>(args.This());
3142 unsigned char* md_value;
3143 unsigned int md_len;
3144 Local<Value> outString;
3146 ASSERT_IS_BUFFER(args[0]);
3147 ssize_t len = Buffer::Length(args[0]);
3149 enum encoding encoding = BUFFER;
3150 if (args.Length() >= 2) {
3151 encoding = ParseEncoding(args[1]->ToString(), BUFFER);
3154 char* buf = new char[len];
3155 ssize_t written = DecodeWrite(buf, len, args[0], BUFFER);
3156 assert(written == len);
3158 md_len = 8192; // Maximum key size is 8192 bits
3159 md_value = new unsigned char[md_len];
3161 int r = sign->SignFinal(&md_value, &md_len, buf, len);
3167 return ThrowException(Exception::Error(String::New("SignFinal error")));
3172 outString = StringBytes::Encode(
3173 reinterpret_cast<const char*>(md_value), md_len, encoding);
3176 return scope.Close(outString);
3179 Sign () : ObjectWrap () {
3180 initialised_ = false;
3185 EVP_MD_CTX_cleanup(&mdctx);
3191 EVP_MD_CTX mdctx; /* coverity[member_decl] */
3192 const EVP_MD *md; /* coverity[member_decl] */
3196 class Verify : public ObjectWrap {
3198 static void Initialize (v8::Handle<v8::Object> target) {
3201 Local<FunctionTemplate> t = FunctionTemplate::New(New);
3203 t->InstanceTemplate()->SetInternalFieldCount(1);
3205 NODE_SET_PROTOTYPE_METHOD(t, "init", VerifyInit);
3206 NODE_SET_PROTOTYPE_METHOD(t, "update", VerifyUpdate);
3207 NODE_SET_PROTOTYPE_METHOD(t, "verify", VerifyFinal);
3209 target->Set(String::NewSymbol("Verify"), t->GetFunction());
3213 bool VerifyInit (const char* verifyType) {
3214 md = EVP_get_digestbyname(verifyType);
3216 fprintf(stderr, "node-crypto : Unknown message digest %s\n", verifyType);
3219 EVP_MD_CTX_init(&mdctx);
3220 EVP_VerifyInit_ex(&mdctx, md, NULL);
3221 initialised_ = true;
3226 int VerifyUpdate(char* data, int len) {
3227 if (!initialised_) return 0;
3228 EVP_VerifyUpdate(&mdctx, data, len);
3233 int VerifyFinal(char* key_pem, int key_pemLen, unsigned char* sig, int siglen) {
3234 if (!initialised_) return 0;
3236 ClearErrorOnReturn clear_error_on_return;
3237 (void) &clear_error_on_return; // Silence compiler warning.
3239 EVP_PKEY* pkey = NULL;
3244 bp = BIO_new(BIO_s_mem());
3246 ERR_print_errors_fp(stderr);
3249 if(!BIO_write(bp, key_pem, key_pemLen)) {
3250 ERR_print_errors_fp(stderr);
3254 // Check if this is a PKCS#8 or RSA public key before trying as X.509.
3255 // Split this out into a separate function once we have more than one
3256 // consumer of public keys.
3257 if (strncmp(key_pem, PUBLIC_KEY_PFX, PUBLIC_KEY_PFX_LEN) == 0) {
3258 pkey = PEM_read_bio_PUBKEY(bp, NULL, NULL, NULL);
3260 ERR_print_errors_fp(stderr);
3263 } else if (strncmp(key_pem, PUBRSA_KEY_PFX, PUBRSA_KEY_PFX_LEN) == 0) {
3264 RSA* rsa = PEM_read_bio_RSAPublicKey(bp, NULL, NULL, NULL);
3266 pkey = EVP_PKEY_new();
3267 if (pkey) EVP_PKEY_set1_RSA(pkey, rsa);
3271 ERR_print_errors_fp(stderr);
3276 x509 = PEM_read_bio_X509(bp, NULL, NULL, NULL);
3278 ERR_print_errors_fp(stderr);
3282 pkey = X509_get_pubkey(x509);
3284 ERR_print_errors_fp(stderr);
3289 r = EVP_VerifyFinal(&mdctx, sig, siglen, pkey);
3292 EVP_PKEY_free (pkey);
3297 EVP_MD_CTX_cleanup(&mdctx);
3298 initialised_ = false;
3306 static Handle<Value> New (const Arguments& args) {
3309 Verify *verify = new Verify();
3310 verify->Wrap(args.This());
3316 static Handle<Value> VerifyInit(const Arguments& args) {
3317 Verify *verify = ObjectWrap::Unwrap<Verify>(args.This());
3321 if (args.Length() == 0 || !args[0]->IsString()) {
3322 return ThrowException(Exception::Error(String::New(
3323 "Must give verifytype string as argument")));
3326 String::Utf8Value verifyType(args[0]);
3328 bool r = verify->VerifyInit(*verifyType);
3331 return ThrowException(Exception::Error(String::New("VerifyInit error")));
3338 static Handle<Value> VerifyUpdate(const Arguments& args) {
3341 Verify *verify = ObjectWrap::Unwrap<Verify>(args.This());
3343 ASSERT_IS_STRING_OR_BUFFER(args[0]);
3345 // Only copy the data if we have to, because it's a string
3347 if (args[0]->IsString()) {
3348 Local<String> string = args[0].As<String>();
3349 enum encoding encoding = ParseEncoding(args[1], BINARY);
3350 if (!StringBytes::IsValidString(string, encoding))
3351 return ThrowTypeError("Bad input string");
3352 size_t buflen = StringBytes::StorageSize(string, encoding);
3353 char* buf = new char[buflen];
3354 size_t written = StringBytes::Write(buf, buflen, string, encoding);
3355 r = verify->VerifyUpdate(buf, written);
3358 char* buf = Buffer::Data(args[0]);
3359 size_t buflen = Buffer::Length(args[0]);
3360 r = verify->VerifyUpdate(buf, buflen);
3364 Local<Value> exception = Exception::TypeError(String::New("VerifyUpdate fail"));
3365 return ThrowException(exception);
3372 static Handle<Value> VerifyFinal(const Arguments& args) {
3375 Verify *verify = ObjectWrap::Unwrap<Verify>(args.This());
3377 ASSERT_IS_BUFFER(args[0]);
3378 ssize_t klen = Buffer::Length(args[0]);
3381 Local<Value> exception = Exception::TypeError(String::New("Bad argument"));
3382 return ThrowException(exception);
3385 char* kbuf = new char[klen];
3386 ssize_t kwritten = DecodeWrite(kbuf, klen, args[0], BINARY);
3387 assert(kwritten == klen);
3389 ASSERT_IS_STRING_OR_BUFFER(args[1]);
3391 // BINARY works for both buffers and binary strings.
3392 enum encoding encoding = BINARY;
3393 if (args.Length() >= 3) {
3394 encoding = ParseEncoding(args[2]->ToString(), BINARY);
3397 ssize_t hlen = StringBytes::Size(args[1], encoding);
3401 Local<Value> exception = Exception::TypeError(String::New("Bad argument"));
3402 return ThrowException(exception);
3405 unsigned char* hbuf = new unsigned char[hlen];
3406 ssize_t hwritten = StringBytes::Write(
3407 reinterpret_cast<char*>(hbuf), hlen, args[1], encoding);
3408 assert(hwritten == hlen);
3411 r = verify->VerifyFinal(kbuf, klen, hbuf, hlen);
3416 return Boolean::New(r && r != -1);
3419 Verify () : ObjectWrap () {
3420 initialised_ = false;
3425 EVP_MD_CTX_cleanup(&mdctx);
3431 EVP_MD_CTX mdctx; /* coverity[member_decl] */
3432 const EVP_MD *md; /* coverity[member_decl] */
3437 class DiffieHellman : public ObjectWrap {
3439 static void Initialize(v8::Handle<v8::Object> target) {
3442 Local<FunctionTemplate> t = FunctionTemplate::New(New);
3444 t->InstanceTemplate()->SetInternalFieldCount(1);
3446 NODE_SET_PROTOTYPE_METHOD(t, "generateKeys", GenerateKeys);
3447 NODE_SET_PROTOTYPE_METHOD(t, "computeSecret", ComputeSecret);
3448 NODE_SET_PROTOTYPE_METHOD(t, "getPrime", GetPrime);
3449 NODE_SET_PROTOTYPE_METHOD(t, "getGenerator", GetGenerator);
3450 NODE_SET_PROTOTYPE_METHOD(t, "getPublicKey", GetPublicKey);
3451 NODE_SET_PROTOTYPE_METHOD(t, "getPrivateKey", GetPrivateKey);
3452 NODE_SET_PROTOTYPE_METHOD(t, "setPublicKey", SetPublicKey);
3453 NODE_SET_PROTOTYPE_METHOD(t, "setPrivateKey", SetPrivateKey);
3455 target->Set(String::NewSymbol("DiffieHellman"), t->GetFunction());
3457 Local<FunctionTemplate> t2 = FunctionTemplate::New(DiffieHellmanGroup);
3458 t2->InstanceTemplate()->SetInternalFieldCount(1);
3460 NODE_SET_PROTOTYPE_METHOD(t2, "generateKeys", GenerateKeys);
3461 NODE_SET_PROTOTYPE_METHOD(t2, "computeSecret", ComputeSecret);
3462 NODE_SET_PROTOTYPE_METHOD(t2, "getPrime", GetPrime);
3463 NODE_SET_PROTOTYPE_METHOD(t2, "getGenerator", GetGenerator);
3464 NODE_SET_PROTOTYPE_METHOD(t2, "getPublicKey", GetPublicKey);
3465 NODE_SET_PROTOTYPE_METHOD(t2, "getPrivateKey", GetPrivateKey);
3467 target->Set(String::NewSymbol("DiffieHellmanGroup"), t2->GetFunction());
3470 bool Init(int primeLength) {
3472 DH_generate_parameters_ex(dh, primeLength, DH_GENERATOR_2, 0);
3473 bool result = VerifyContext();
3474 if (!result) return false;
3475 initialised_ = true;
3479 bool Init(unsigned char* p, int p_len) {
3481 dh->p = BN_bin2bn(p, p_len, 0);
3483 if (!BN_set_word(dh->g, 2)) return false;
3484 bool result = VerifyContext();
3485 if (!result) return false;
3486 initialised_ = true;
3490 bool Init(unsigned char* p, int p_len, unsigned char* g, int g_len) {
3492 dh->p = BN_bin2bn(p, p_len, 0);
3493 dh->g = BN_bin2bn(g, g_len, 0);
3494 initialised_ = true;
3499 static Handle<Value> DiffieHellmanGroup(const Arguments& args) {
3502 DiffieHellman* diffieHellman = new DiffieHellman();
3504 if (args.Length() != 1 || !args[0]->IsString()) {
3505 return ThrowException(Exception::Error(
3506 String::New("No group name given")));
3509 String::Utf8Value group_name(args[0]);
3511 modp_group* it = modp_groups;
3513 while(it->name != NULL) {
3514 if (!strcasecmp(*group_name, it->name))
3519 if (it->name != NULL) {
3520 diffieHellman->Init(it->prime, it->prime_size,
3521 it->gen, it->gen_size);
3523 return ThrowException(Exception::Error(
3524 String::New("Unknown group")));
3527 diffieHellman->Wrap(args.This());
3532 static Handle<Value> New(const Arguments& args) {
3535 DiffieHellman* diffieHellman = new DiffieHellman();
3536 bool initialized = false;
3538 if (args.Length() > 0) {
3539 if (args[0]->IsInt32()) {
3540 initialized = diffieHellman->Init(args[0]->Int32Value());
3542 initialized = diffieHellman->Init(
3543 reinterpret_cast<unsigned char*>(Buffer::Data(args[0])),
3544 Buffer::Length(args[0]));
3549 return ThrowException(Exception::Error(
3550 String::New("Initialization failed")));
3553 diffieHellman->Wrap(args.This());
3558 static Handle<Value> GenerateKeys(const Arguments& args) {
3559 DiffieHellman* diffieHellman =
3560 ObjectWrap::Unwrap<DiffieHellman>(args.This());
3564 if (!diffieHellman->initialised_) {
3565 return ThrowException(Exception::Error(
3566 String::New("Not initialized")));
3569 if (!DH_generate_key(diffieHellman->dh)) {
3570 return ThrowException(Exception::Error(
3571 String::New("Key generation failed")));
3574 Local<Value> outString;
3576 int dataSize = BN_num_bytes(diffieHellman->dh->pub_key);
3577 char* data = new char[dataSize];
3578 BN_bn2bin(diffieHellman->dh->pub_key,
3579 reinterpret_cast<unsigned char*>(data));
3581 outString = Encode(data, dataSize, BUFFER);
3584 return scope.Close(outString);
3587 static Handle<Value> GetPrime(const Arguments& args) {
3588 DiffieHellman* diffieHellman =
3589 ObjectWrap::Unwrap<DiffieHellman>(args.This());
3593 if (!diffieHellman->initialised_) {
3594 return ThrowException(Exception::Error(String::New("Not initialized")));
3597 int dataSize = BN_num_bytes(diffieHellman->dh->p);
3598 char* data = new char[dataSize];
3599 BN_bn2bin(diffieHellman->dh->p, reinterpret_cast<unsigned char*>(data));
3601 Local<Value> outString;
3603 outString = Encode(data, dataSize, BUFFER);
3607 return scope.Close(outString);
3610 static Handle<Value> GetGenerator(const Arguments& args) {
3611 DiffieHellman* diffieHellman =
3612 ObjectWrap::Unwrap<DiffieHellman>(args.This());
3616 if (!diffieHellman->initialised_) {
3617 return ThrowException(Exception::Error(String::New("Not initialized")));
3620 int dataSize = BN_num_bytes(diffieHellman->dh->g);
3621 char* data = new char[dataSize];
3622 BN_bn2bin(diffieHellman->dh->g, reinterpret_cast<unsigned char*>(data));
3624 Local<Value> outString;
3626 outString = Encode(data, dataSize, BUFFER);
3630 return scope.Close(outString);
3633 static Handle<Value> GetPublicKey(const Arguments& args) {
3634 DiffieHellman* diffieHellman =
3635 ObjectWrap::Unwrap<DiffieHellman>(args.This());
3639 if (!diffieHellman->initialised_) {
3640 return ThrowException(Exception::Error(String::New("Not initialized")));
3643 if (diffieHellman->dh->pub_key == NULL) {
3644 return ThrowException(Exception::Error(
3645 String::New("No public key - did you forget to generate one?")));
3648 int dataSize = BN_num_bytes(diffieHellman->dh->pub_key);
3649 char* data = new char[dataSize];
3650 BN_bn2bin(diffieHellman->dh->pub_key,
3651 reinterpret_cast<unsigned char*>(data));
3653 Local<Value> outString;
3655 outString = Encode(data, dataSize, BUFFER);
3659 return scope.Close(outString);
3662 static Handle<Value> GetPrivateKey(const Arguments& args) {
3663 DiffieHellman* diffieHellman =
3664 ObjectWrap::Unwrap<DiffieHellman>(args.This());
3668 if (!diffieHellman->initialised_) {
3669 return ThrowException(Exception::Error(String::New("Not initialized")));
3672 if (diffieHellman->dh->priv_key == NULL) {
3673 return ThrowException(Exception::Error(
3674 String::New("No private key - did you forget to generate one?")));
3677 int dataSize = BN_num_bytes(diffieHellman->dh->priv_key);
3678 char* data = new char[dataSize];
3679 BN_bn2bin(diffieHellman->dh->priv_key,
3680 reinterpret_cast<unsigned char*>(data));
3682 Local<Value> outString;
3684 outString = Encode(data, dataSize, BUFFER);
3688 return scope.Close(outString);
3691 static Handle<Value> ComputeSecret(const Arguments& args) {
3694 DiffieHellman* diffieHellman =
3695 ObjectWrap::Unwrap<DiffieHellman>(args.This());
3697 if (!diffieHellman->initialised_) {
3698 return ThrowException(Exception::Error(String::New("Not initialized")));
3701 ClearErrorOnReturn clear_error_on_return;
3702 (void) &clear_error_on_return; // Silence compiler warning.
3705 if (args.Length() == 0) {
3706 return ThrowException(Exception::Error(
3707 String::New("First argument must be other party's public key")));
3709 ASSERT_IS_BUFFER(args[0]);
3711 reinterpret_cast<unsigned char*>(Buffer::Data(args[0])),
3712 Buffer::Length(args[0]), 0);
3715 int dataSize = DH_size(diffieHellman->dh);
3716 char* data = new char[dataSize];
3718 int size = DH_compute_key(reinterpret_cast<unsigned char*>(data),
3719 key, diffieHellman->dh);
3725 checked = DH_check_pub_key(diffieHellman->dh, key, &checkResult);
3730 return ThrowException(Exception::Error(String::New("Invalid key")));
3731 } else if (checkResult) {
3732 if (checkResult & DH_CHECK_PUBKEY_TOO_SMALL) {
3733 return ThrowException(Exception::Error(
3734 String::New("Supplied key is too small")));
3735 } else if (checkResult & DH_CHECK_PUBKEY_TOO_LARGE) {
3736 return ThrowException(Exception::Error(
3737 String::New("Supplied key is too large")));
3739 return ThrowException(Exception::Error(String::New("Invalid key")));
3742 return ThrowException(Exception::Error(String::New("Invalid key")));
3749 // DH_size returns number of bytes in a prime number
3750 // DH_compute_key returns number of bytes in a remainder of exponent, which
3751 // may have less bytes than a prime number. Therefore add 0-padding to the
3752 // allocated buffer.
3753 if (size != dataSize) {
3754 assert(dataSize > size);
3755 memmove(data + dataSize - size, data, size);
3756 memset(data, 0, dataSize - size);
3759 Local<Value> outString;
3761 outString = Encode(data, dataSize, BUFFER);
3764 return scope.Close(outString);
3767 static Handle<Value> SetPublicKey(const Arguments& args) {
3770 DiffieHellman* diffieHellman =
3771 ObjectWrap::Unwrap<DiffieHellman>(args.This());
3773 if (!diffieHellman->initialised_) {
3774 return ThrowException(Exception::Error(String::New("Not initialized")));
3777 if (args.Length() == 0) {
3778 return ThrowException(Exception::Error(
3779 String::New("First argument must be public key")));
3781 ASSERT_IS_BUFFER(args[0]);
3782 diffieHellman->dh->pub_key =
3784 reinterpret_cast<unsigned char*>(Buffer::Data(args[0])),
3785 Buffer::Length(args[0]), 0);
3791 static Handle<Value> SetPrivateKey(const Arguments& args) {
3794 DiffieHellman* diffieHellman =
3795 ObjectWrap::Unwrap<DiffieHellman>(args.This());
3797 if (!diffieHellman->initialised_) {
3798 return ThrowException(Exception::Error(
3799 String::New("Not initialized")));
3802 if (args.Length() == 0) {
3803 return ThrowException(Exception::Error(
3804 String::New("First argument must be private key")));
3806 ASSERT_IS_BUFFER(args[0]);
3807 diffieHellman->dh->priv_key =
3809 reinterpret_cast<unsigned char*>(Buffer::Data(args[0])),
3810 Buffer::Length(args[0]), 0);
3816 DiffieHellman() : ObjectWrap() {
3817 initialised_ = false;
3828 bool VerifyContext() {
3830 if (!DH_check(dh, &codes)) return false;
3831 if (codes & DH_CHECK_P_NOT_SAFE_PRIME) return false;
3832 if (codes & DH_CHECK_P_NOT_PRIME) return false;
3833 if (codes & DH_UNABLE_TO_CHECK_GENERATOR) return false;
3834 if (codes & DH_NOT_SUITABLE_GENERATOR) return false;
3853 Persistent<Object> obj;
3857 void EIO_PBKDF2(pbkdf2_req* req) {
3858 req->err = PKCS5_PBKDF2_HMAC_SHA1(
3861 (unsigned char*)req->salt,
3865 (unsigned char*)req->key);
3866 memset(req->pass, 0, req->passlen);
3867 memset(req->salt, 0, req->saltlen);
3871 void EIO_PBKDF2(uv_work_t* work_req) {
3872 pbkdf2_req* req = container_of(work_req, pbkdf2_req, work_req);
3877 void EIO_PBKDF2After(pbkdf2_req* req, Local<Value> argv[2]) {
3879 argv[0] = Local<Value>::New(Undefined());
3880 argv[1] = Encode(req->key, req->keylen, BUFFER);
3881 memset(req->key, 0, req->keylen);
3883 argv[0] = Exception::Error(String::New("PBKDF2 error"));
3884 argv[1] = Local<Value>::New(Undefined());
3894 void EIO_PBKDF2After(uv_work_t* work_req, int status) {
3895 assert(status == 0);
3896 pbkdf2_req* req = container_of(work_req, pbkdf2_req, work_req);
3898 Local<Value> argv[2];
3899 Persistent<Object> obj = req->obj;
3900 EIO_PBKDF2After(req, argv);
3901 MakeCallback(obj, "ondone", ARRAY_SIZE(argv), argv);
3906 Handle<Value> PBKDF2(const Arguments& args) {
3909 const char* type_error = NULL;
3912 ssize_t passlen = -1;
3913 ssize_t saltlen = -1;
3914 ssize_t keylen = -1;
3915 ssize_t pass_written = -1;
3916 ssize_t salt_written = -1;
3918 pbkdf2_req* req = NULL;
3920 if (args.Length() != 4 && args.Length() != 5) {
3921 type_error = "Bad parameter";
3925 ASSERT_IS_BUFFER(args[0]);
3926 passlen = Buffer::Length(args[0]);
3928 type_error = "Bad password";
3932 pass = new char[passlen];
3933 pass_written = DecodeWrite(pass, passlen, args[0], BINARY);
3934 assert(pass_written == passlen);
3936 ASSERT_IS_BUFFER(args[1]);
3937 saltlen = Buffer::Length(args[1]);
3939 type_error = "Bad salt";
3943 salt = new char[saltlen];
3944 salt_written = DecodeWrite(salt, saltlen, args[1], BINARY);
3945 assert(salt_written == saltlen);
3947 if (!args[2]->IsNumber()) {
3948 type_error = "Iterations not a number";
3952 iter = args[2]->Int32Value();
3954 type_error = "Bad iterations";
3958 if (!args[3]->IsNumber()) {
3959 type_error = "Key length not a number";
3963 keylen = args[3]->Int32Value();
3965 type_error = "Bad key length";
3969 req = new pbkdf2_req;
3972 req->passlen = passlen;
3974 req->saltlen = saltlen;
3976 req->key = new char[keylen];
3977 req->keylen = keylen;
3979 if (args[4]->IsFunction()) {
3980 req->obj = Persistent<Object>::New(Object::New());
3981 req->obj->Set(String::New("ondone"), args[4]);
3982 uv_queue_work(uv_default_loop(),
3988 Local<Value> argv[2];
3990 EIO_PBKDF2After(req, argv);
3991 if (argv[0]->IsObject()) return ThrowException(argv[0]);
3992 return scope.Close(argv[1]);
3998 return ThrowException(Exception::TypeError(String::New(type_error)));
4002 struct RandomBytesRequest {
4003 ~RandomBytesRequest();
4004 Persistent<Object> obj_;
4005 unsigned long error_; // openssl error code or zero
4006 uv_work_t work_req_;
4012 RandomBytesRequest::~RandomBytesRequest() {
4013 if (obj_.IsEmpty()) return;
4019 void RandomBytesFree(char* data, void* hint) {
4024 template <bool pseudoRandom>
4025 void RandomBytesWork(uv_work_t* work_req) {
4026 RandomBytesRequest* req = container_of(work_req,
4031 // Ensure that OpenSSL's PRNG is properly seeded.
4034 if (pseudoRandom == true) {
4035 r = RAND_pseudo_bytes(reinterpret_cast<unsigned char*>(req->data_),
4038 r = RAND_bytes(reinterpret_cast<unsigned char*>(req->data_), req->size_);
4041 // RAND_bytes() returns 0 on error. RAND_pseudo_bytes() returns 0 when the
4042 // result is not cryptographically strong - but that's not an error.
4043 if (r == 0 && pseudoRandom == false) {
4044 req->error_ = ERR_get_error();
4045 } else if (r == -1) {
4046 req->error_ = static_cast<unsigned long>(-1);
4051 // don't call this function without a valid HandleScope
4052 void RandomBytesCheck(RandomBytesRequest* req, Local<Value> argv[2]) {
4054 char errmsg[256] = "Operation not supported";
4056 if (req->error_ != (unsigned long) -1)
4057 ERR_error_string_n(req->error_, errmsg, sizeof errmsg);
4059 argv[0] = Exception::Error(String::New(errmsg));
4060 argv[1] = Local<Value>::New(Null());
4063 // avoids the malloc + memcpy
4064 Buffer* buffer = Buffer::New(req->data_, req->size_, RandomBytesFree, NULL);
4065 argv[0] = Local<Value>::New(Null());
4066 argv[1] = Local<Object>::New(buffer->handle_);
4073 void RandomBytesAfter(uv_work_t* work_req, int status) {
4074 assert(status == 0);
4075 RandomBytesRequest* req = container_of(work_req,
4079 Local<Value> argv[2];
4080 RandomBytesCheck(req, argv);
4081 MakeCallback(req->obj_, "ondone", ARRAY_SIZE(argv), argv);
4086 template <bool pseudoRandom>
4087 Handle<Value> RandomBytes(const Arguments& args) {
4090 // maybe allow a buffer to write to? cuts down on object creation
4091 // when generating random data in a loop
4092 if (!args[0]->IsUint32()) {
4093 return ThrowTypeError("Argument #1 must be number > 0");
4096 const uint32_t size = args[0]->Uint32Value();
4097 if (size > Buffer::kMaxLength) {
4098 return ThrowTypeError("size > Buffer::kMaxLength");
4101 RandomBytesRequest* req = new RandomBytesRequest();
4103 req->data_ = new char[size];
4106 if (args[1]->IsFunction()) {
4107 req->obj_ = Persistent<Object>::New(Object::New());
4108 req->obj_->Set(String::New("ondone"), args[1]);
4110 uv_queue_work(uv_default_loop(),
4112 RandomBytesWork<pseudoRandom>,
4118 Local<Value> argv[2];
4119 RandomBytesWork<pseudoRandom>(&req->work_req_);
4120 RandomBytesCheck(req, argv);
4123 if (!argv[0]->IsNull())
4124 return ThrowException(argv[0]);
4131 Handle<Value> GetSSLCiphers(const Arguments& args) {
4134 SSL_CTX* ctx = SSL_CTX_new(TLSv1_server_method());
4136 return ThrowError("SSL_CTX_new() failed.");
4139 SSL* ssl = SSL_new(ctx);
4142 return ThrowError("SSL_new() failed.");
4145 Local<Array> arr = Array::New();
4146 STACK_OF(SSL_CIPHER)* ciphers = SSL_get_ciphers(ssl);
4148 for (int i = 0; i < sk_SSL_CIPHER_num(ciphers); ++i) {
4149 SSL_CIPHER* cipher = sk_SSL_CIPHER_value(ciphers, i);
4150 arr->Set(i, String::New(SSL_CIPHER_get_name(cipher)));
4156 return scope.Close(arr);
4160 template <class TypeName>
4161 static void array_push_back(const TypeName* md,
4165 Local<Array>& arr = *static_cast<Local<Array>*>(arg);
4166 arr->Set(arr->Length(), String::New(from));
4170 Handle<Value> GetCiphers(const Arguments& args) {
4172 Local<Array> arr = Array::New();
4173 EVP_CIPHER_do_all_sorted(array_push_back<EVP_CIPHER>, &arr);
4174 return scope.Close(arr);
4178 Handle<Value> GetHashes(const Arguments& args) {
4180 Local<Array> arr = Array::New();
4181 EVP_MD_do_all_sorted(array_push_back<EVP_MD>, &arr);
4182 return scope.Close(arr);
4186 void InitCrypto(Handle<Object> target) {
4190 OpenSSL_add_all_algorithms();
4191 OpenSSL_add_all_digests();
4192 SSL_load_error_strings();
4193 ERR_load_crypto_strings();
4196 CRYPTO_set_locking_callback(crypto_lock_cb);
4197 CRYPTO_THREADID_set_callback(crypto_threadid_cb);
4199 // Turn off compression. Saves memory - do it in userland.
4200 #if !defined(OPENSSL_NO_COMP)
4201 STACK_OF(SSL_COMP)* comp_methods =
4202 #if OPENSSL_VERSION_NUMBER < 0x00908000L
4203 SSL_COMP_get_compression_method()
4205 SSL_COMP_get_compression_methods()
4208 sk_SSL_COMP_zero(comp_methods);
4209 assert(sk_SSL_COMP_num(comp_methods) == 0);
4212 SecureContext::Initialize(target);
4213 Connection::Initialize(target);
4214 Cipher::Initialize(target);
4215 Decipher::Initialize(target);
4216 DiffieHellman::Initialize(target);
4217 Hmac::Initialize(target);
4218 Hash::Initialize(target);
4219 Sign::Initialize(target);
4220 Verify::Initialize(target);
4222 NODE_SET_METHOD(target, "PBKDF2", PBKDF2);
4223 NODE_SET_METHOD(target, "randomBytes", RandomBytes<false>);
4224 NODE_SET_METHOD(target, "pseudoRandomBytes", RandomBytes<true>);
4225 NODE_SET_METHOD(target, "getSSLCiphers", GetSSLCiphers);
4226 NODE_SET_METHOD(target, "getCiphers", GetCiphers);
4227 NODE_SET_METHOD(target, "getHashes", GetHashes);
4229 subject_symbol = NODE_PSYMBOL("subject");
4230 issuer_symbol = NODE_PSYMBOL("issuer");
4231 valid_from_symbol = NODE_PSYMBOL("valid_from");
4232 valid_to_symbol = NODE_PSYMBOL("valid_to");
4233 subjectaltname_symbol = NODE_PSYMBOL("subjectaltname");
4234 modulus_symbol = NODE_PSYMBOL("modulus");
4235 exponent_symbol = NODE_PSYMBOL("exponent");
4236 fingerprint_symbol = NODE_PSYMBOL("fingerprint");
4237 name_symbol = NODE_PSYMBOL("name");
4238 version_symbol = NODE_PSYMBOL("version");
4239 ext_key_usage_symbol = NODE_PSYMBOL("ext_key_usage");
4242 } // namespace crypto
4245 NODE_MODULE(node_crypto, node::crypto::InitCrypto)