1 /* 2 * Copyright (C) 2007-2008 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 /** 18 * Native glue for Java class org.apache.harmony.xnet.provider.jsse.NativeCrypto 19 */ 20 21 #define LOG_TAG "NativeCrypto" 22 23 #include <algorithm> 24 #include <fcntl.h> 25 #include <sys/socket.h> 26 #include <unistd.h> 27 28 #include <jni.h> 29 30 #include <openssl/dsa.h> 31 #include <openssl/engine.h> 32 #include <openssl/err.h> 33 #include <openssl/evp.h> 34 #include <openssl/rand.h> 35 #include <openssl/rsa.h> 36 #include <openssl/ssl.h> 37 38 #include "AsynchronousSocketCloseMonitor.h" 39 #include "JNIHelp.h" 40 #include "JniConstants.h" 41 #include "JniException.h" 42 #include "NetFd.h" 43 #include "NetworkUtilities.h" 44 #include "ScopedLocalRef.h" 45 #include "ScopedPrimitiveArray.h" 46 #include "ScopedUtfChars.h" 47 #include "UniquePtr.h" 48 49 #undef WITH_JNI_TRACE 50 #undef WITH_JNI_TRACE_DATA 51 52 #ifdef WITH_JNI_TRACE 53 #define JNI_TRACE(...) \ 54 ((void)ALOG(LOG_INFO, LOG_TAG "-jni", __VA_ARGS__)); \ 55 /* 56 ((void)printf("I/" LOG_TAG "-jni:")); \ 57 ((void)printf(__VA_ARGS__)); \ 58 ((void)printf("\n")) 59 */ 60 #else 61 #define JNI_TRACE(...) ((void)0) 62 #endif 63 // don't overwhelm logcat 64 #define WITH_JNI_TRACE_DATA_CHUNK_SIZE 512 65 66 struct BIO_Delete { 67 void operator()(BIO* p) const { 68 BIO_free(p); 69 } 70 }; 71 typedef UniquePtr<BIO, BIO_Delete> Unique_BIO; 72 73 struct BIGNUM_Delete { 74 void operator()(BIGNUM* p) const { 75 BN_free(p); 76 } 77 }; 78 typedef UniquePtr<BIGNUM, BIGNUM_Delete> Unique_BIGNUM; 79 80 struct DH_Delete { 81 void operator()(DH* p) const { 82 DH_free(p); 83 } 84 }; 85 typedef UniquePtr<DH, DH_Delete> Unique_DH; 86 87 struct DSA_Delete { 88 void operator()(DSA* p) const { 89 DSA_free(p); 90 } 91 }; 92 typedef UniquePtr<DSA, DSA_Delete> Unique_DSA; 93 94 struct EC_KEY_Delete { 95 void operator()(EC_KEY* p) const { 96 EC_KEY_free(p); 97 } 98 }; 99 typedef UniquePtr<EC_KEY, EC_KEY_Delete> Unique_EC_KEY; 100 101 struct EVP_MD_CTX_Delete { 102 void operator()(EVP_MD_CTX* p) const { 103 EVP_MD_CTX_destroy(p); 104 } 105 }; 106 typedef UniquePtr<EVP_MD_CTX, EVP_MD_CTX_Delete> Unique_EVP_MD_CTX; 107 108 struct EVP_CIPHER_CTX_Delete { 109 void operator()(EVP_CIPHER_CTX* p) const { 110 EVP_CIPHER_CTX_cleanup(p); 111 } 112 }; 113 typedef UniquePtr<EVP_CIPHER_CTX, EVP_CIPHER_CTX_Delete> Unique_EVP_CIPHER_CTX; 114 115 struct EVP_PKEY_Delete { 116 void operator()(EVP_PKEY* p) const { 117 EVP_PKEY_free(p); 118 } 119 }; 120 typedef UniquePtr<EVP_PKEY, EVP_PKEY_Delete> Unique_EVP_PKEY; 121 122 struct PKCS8_PRIV_KEY_INFO_Delete { 123 void operator()(PKCS8_PRIV_KEY_INFO* p) const { 124 PKCS8_PRIV_KEY_INFO_free(p); 125 } 126 }; 127 typedef UniquePtr<PKCS8_PRIV_KEY_INFO, PKCS8_PRIV_KEY_INFO_Delete> Unique_PKCS8_PRIV_KEY_INFO; 128 129 struct RSA_Delete { 130 void operator()(RSA* p) const { 131 RSA_free(p); 132 } 133 }; 134 typedef UniquePtr<RSA, RSA_Delete> Unique_RSA; 135 136 struct SSL_Delete { 137 void operator()(SSL* p) const { 138 SSL_free(p); 139 } 140 }; 141 typedef UniquePtr<SSL, SSL_Delete> Unique_SSL; 142 143 struct SSL_CTX_Delete { 144 void operator()(SSL_CTX* p) const { 145 SSL_CTX_free(p); 146 } 147 }; 148 typedef UniquePtr<SSL_CTX, SSL_CTX_Delete> Unique_SSL_CTX; 149 150 struct X509_Delete { 151 void operator()(X509* p) const { 152 X509_free(p); 153 } 154 }; 155 typedef UniquePtr<X509, X509_Delete> Unique_X509; 156 157 struct X509_NAME_Delete { 158 void operator()(X509_NAME* p) const { 159 X509_NAME_free(p); 160 } 161 }; 162 typedef UniquePtr<X509_NAME, X509_NAME_Delete> Unique_X509_NAME; 163 164 struct sk_SSL_CIPHER_Delete { 165 void operator()(STACK_OF(SSL_CIPHER)* p) const { 166 sk_SSL_CIPHER_free(p); 167 } 168 }; 169 typedef UniquePtr<STACK_OF(SSL_CIPHER), sk_SSL_CIPHER_Delete> Unique_sk_SSL_CIPHER; 170 171 struct sk_X509_Delete { 172 void operator()(STACK_OF(X509)* p) const { 173 sk_X509_free(p); 174 } 175 }; 176 typedef UniquePtr<STACK_OF(X509), sk_X509_Delete> Unique_sk_X509; 177 178 struct sk_X509_NAME_Delete { 179 void operator()(STACK_OF(X509_NAME)* p) const { 180 sk_X509_NAME_free(p); 181 } 182 }; 183 typedef UniquePtr<STACK_OF(X509_NAME), sk_X509_NAME_Delete> Unique_sk_X509_NAME; 184 185 /** 186 * Many OpenSSL APIs take ownership of an argument on success but don't free the argument 187 * on failure. This means we need to tell our scoped pointers when we've transferred ownership, 188 * without triggering a warning by not using the result of release(). 189 */ 190 #define OWNERSHIP_TRANSFERRED(obj) \ 191 typeof (obj.release()) _dummy __attribute__((unused)) = obj.release() 192 193 /** 194 * Frees the SSL error state. 195 * 196 * OpenSSL keeps an "error stack" per thread, and given that this code 197 * can be called from arbitrary threads that we don't keep track of, 198 * we err on the side of freeing the error state promptly (instead of, 199 * say, at thread death). 200 */ 201 static void freeOpenSslErrorState(void) { 202 ERR_clear_error(); 203 ERR_remove_state(0); 204 } 205 206 /* 207 * Checks this thread's OpenSSL error queue and throws a RuntimeException if 208 * necessary. 209 * 210 * @return true if an exception was thrown, false if not. 211 */ 212 static bool throwExceptionIfNecessary(JNIEnv* env, const char* location __attribute__ ((unused))) { 213 int error = ERR_get_error(); 214 int result = false; 215 216 if (error != 0) { 217 char message[256]; 218 ERR_error_string_n(error, message, sizeof(message)); 219 JNI_TRACE("OpenSSL error in %s %d: %s", location, error, message); 220 jniThrowRuntimeException(env, message); 221 result = true; 222 } 223 224 freeOpenSslErrorState(); 225 return result; 226 } 227 228 /** 229 * Throws an SocketTimeoutException with the given string as a message. 230 */ 231 static void throwSocketTimeoutException(JNIEnv* env, const char* message) { 232 JNI_TRACE("throwSocketTimeoutException %s", message); 233 jniThrowException(env, "java/net/SocketTimeoutException", message); 234 } 235 236 /** 237 * Throws a javax.net.ssl.SSLException with the given string as a message. 238 */ 239 static void throwSSLExceptionStr(JNIEnv* env, const char* message) { 240 JNI_TRACE("throwSSLExceptionStr %s", message); 241 jniThrowException(env, "javax/net/ssl/SSLException", message); 242 } 243 244 /** 245 * Throws a javax.net.ssl.SSLProcotolException with the given string as a message. 246 */ 247 static void throwSSLProtocolExceptionStr(JNIEnv* env, const char* message) { 248 JNI_TRACE("throwSSLProtocolExceptionStr %s", message); 249 jniThrowException(env, "javax/net/ssl/SSLProtocolException", message); 250 } 251 252 /** 253 * Throws an SSLException with a message constructed from the current 254 * SSL errors. This will also log the errors. 255 * 256 * @param env the JNI environment 257 * @param ssl the possibly NULL SSL 258 * @param sslErrorCode error code returned from SSL_get_error() or 259 * SSL_ERROR_NONE to probe with ERR_get_error 260 * @param message null-ok; general error message 261 */ 262 static void throwSSLExceptionWithSslErrors( 263 JNIEnv* env, SSL* ssl, int sslErrorCode, const char* message) { 264 265 if (message == NULL) { 266 message = "SSL error"; 267 } 268 269 // First consult the SSL error code for the general message. 270 const char* sslErrorStr = NULL; 271 switch (sslErrorCode) { 272 case SSL_ERROR_NONE: 273 if (ERR_peek_error() == 0) { 274 sslErrorStr = "OK"; 275 } else { 276 sslErrorStr = ""; 277 } 278 break; 279 case SSL_ERROR_SSL: 280 sslErrorStr = "Failure in SSL library, usually a protocol error"; 281 break; 282 case SSL_ERROR_WANT_READ: 283 sslErrorStr = "SSL_ERROR_WANT_READ occurred. You should never see this."; 284 break; 285 case SSL_ERROR_WANT_WRITE: 286 sslErrorStr = "SSL_ERROR_WANT_WRITE occurred. You should never see this."; 287 break; 288 case SSL_ERROR_WANT_X509_LOOKUP: 289 sslErrorStr = "SSL_ERROR_WANT_X509_LOOKUP occurred. You should never see this."; 290 break; 291 case SSL_ERROR_SYSCALL: 292 sslErrorStr = "I/O error during system call"; 293 break; 294 case SSL_ERROR_ZERO_RETURN: 295 sslErrorStr = "SSL_ERROR_ZERO_RETURN occurred. You should never see this."; 296 break; 297 case SSL_ERROR_WANT_CONNECT: 298 sslErrorStr = "SSL_ERROR_WANT_CONNECT occurred. You should never see this."; 299 break; 300 case SSL_ERROR_WANT_ACCEPT: 301 sslErrorStr = "SSL_ERROR_WANT_ACCEPT occurred. You should never see this."; 302 break; 303 default: 304 sslErrorStr = "Unknown SSL error"; 305 } 306 307 // Prepend either our explicit message or a default one. 308 char* str; 309 if (asprintf(&str, "%s: ssl=%p: %s", message, ssl, sslErrorStr) <= 0) { 310 // problem with asprintf, just throw argument message, log everything 311 throwSSLExceptionStr(env, message); 312 ALOGV("%s: ssl=%p: %s", message, ssl, sslErrorStr); 313 freeOpenSslErrorState(); 314 return; 315 } 316 317 char* allocStr = str; 318 319 // For protocol errors, SSL might have more information. 320 if (sslErrorCode == SSL_ERROR_NONE || sslErrorCode == SSL_ERROR_SSL) { 321 // Append each error as an additional line to the message. 322 for (;;) { 323 char errStr[256]; 324 const char* file; 325 int line; 326 const char* data; 327 int flags; 328 unsigned long err = ERR_get_error_line_data(&file, &line, &data, &flags); 329 if (err == 0) { 330 break; 331 } 332 333 ERR_error_string_n(err, errStr, sizeof(errStr)); 334 335 int ret = asprintf(&str, "%s\n%s (%s:%d %p:0x%08x)", 336 (allocStr == NULL) ? "" : allocStr, 337 errStr, 338 file, 339 line, 340 (flags & ERR_TXT_STRING) ? data : "(no data)", 341 flags); 342 343 if (ret < 0) { 344 break; 345 } 346 347 free(allocStr); 348 allocStr = str; 349 } 350 // For errors during system calls, errno might be our friend. 351 } else if (sslErrorCode == SSL_ERROR_SYSCALL) { 352 if (asprintf(&str, "%s, %s", allocStr, strerror(errno)) >= 0) { 353 free(allocStr); 354 allocStr = str; 355 } 356 // If the error code is invalid, print it. 357 } else if (sslErrorCode > SSL_ERROR_WANT_ACCEPT) { 358 if (asprintf(&str, ", error code is %d", sslErrorCode) >= 0) { 359 free(allocStr); 360 allocStr = str; 361 } 362 } 363 364 if (sslErrorCode == SSL_ERROR_SSL) { 365 throwSSLProtocolExceptionStr(env, allocStr); 366 } else { 367 throwSSLExceptionStr(env, allocStr); 368 } 369 370 ALOGV("%s", allocStr); 371 free(allocStr); 372 freeOpenSslErrorState(); 373 } 374 375 /** 376 * Helper function that grabs the casts an ssl pointer and then checks for nullness. 377 * If this function returns NULL and <code>throwIfNull</code> is 378 * passed as <code>true</code>, then this function will call 379 * <code>throwSSLExceptionStr</code> before returning, so in this case of 380 * NULL, a caller of this function should simply return and allow JNI 381 * to do its thing. 382 * 383 * @param env the JNI environment 384 * @param ssl_address; the ssl_address pointer as an integer 385 * @param throwIfNull whether to throw if the SSL pointer is NULL 386 * @returns the pointer, which may be NULL 387 */ 388 static SSL_CTX* to_SSL_CTX(JNIEnv* env, int ssl_ctx_address, bool throwIfNull) { 389 SSL_CTX* ssl_ctx = reinterpret_cast<SSL_CTX*>(static_cast<uintptr_t>(ssl_ctx_address)); 390 if ((ssl_ctx == NULL) && throwIfNull) { 391 JNI_TRACE("ssl_ctx == null"); 392 jniThrowNullPointerException(env, "ssl_ctx == null"); 393 } 394 return ssl_ctx; 395 } 396 397 static SSL* to_SSL(JNIEnv* env, int ssl_address, bool throwIfNull) { 398 SSL* ssl = reinterpret_cast<SSL*>(static_cast<uintptr_t>(ssl_address)); 399 if ((ssl == NULL) && throwIfNull) { 400 JNI_TRACE("ssl == null"); 401 jniThrowNullPointerException(env, "ssl == null"); 402 } 403 return ssl; 404 } 405 406 static SSL_SESSION* to_SSL_SESSION(JNIEnv* env, int ssl_session_address, bool throwIfNull) { 407 SSL_SESSION* ssl_session 408 = reinterpret_cast<SSL_SESSION*>(static_cast<uintptr_t>(ssl_session_address)); 409 if ((ssl_session == NULL) && throwIfNull) { 410 JNI_TRACE("ssl_session == null"); 411 jniThrowNullPointerException(env, "ssl_session == null"); 412 } 413 return ssl_session; 414 } 415 416 /** 417 * Converts a Java byte[] to an OpenSSL BIGNUM, allocating the BIGNUM on the 418 * fly. Returns true on success. If the return value is false, there is a 419 * pending exception. 420 */ 421 static bool arrayToBignum(JNIEnv* env, jbyteArray source, BIGNUM** dest) { 422 JNI_TRACE("arrayToBignum(%p, %p)", source, *dest); 423 424 ScopedByteArrayRO sourceBytes(env, source); 425 if (sourceBytes.get() == NULL) { 426 JNI_TRACE("arrayToBignum(%p) => NULL", source); 427 return false; 428 } 429 *dest = BN_bin2bn(reinterpret_cast<const unsigned char*>(sourceBytes.get()), 430 sourceBytes.size(), 431 NULL); 432 if (*dest == NULL) { 433 jniThrowRuntimeException(env, "Conversion to BIGNUM failed"); 434 JNI_TRACE("arrayToBignum(%p) => threw exception", source); 435 return false; 436 } 437 438 JNI_TRACE("arrayToBignum(%p) => %p", source, *dest); 439 return true; 440 } 441 442 /** 443 * Converts an OpenSSL BIGNUM to a Java byte[] array. 444 */ 445 static jbyteArray bignumToArray(JNIEnv* env, BIGNUM* source) { 446 JNI_TRACE("bignumToArray(%p)", source); 447 448 if (source == NULL) { 449 jniThrowNullPointerException(env, NULL); 450 return NULL; 451 } 452 453 int len = BN_num_bytes(source) + 1; 454 jbyteArray javaBytes = env->NewByteArray(len); 455 ScopedByteArrayRW bytes(env, javaBytes); 456 if (bytes.get() == NULL) { 457 JNI_TRACE("bignumToArray(%p) => NULL", source); 458 return NULL; 459 } 460 461 unsigned char* tmp = reinterpret_cast<unsigned char*>(bytes.get()); 462 463 // Set the sign for the Java code. 464 if (BN_is_negative(source)) { 465 *tmp = 0xFF; 466 } else { 467 *tmp = 0x00; 468 } 469 470 if (BN_bn2bin(source, tmp + 1) <= 0) { 471 throwExceptionIfNecessary(env, "bignumToArray"); 472 return NULL; 473 } 474 475 JNI_TRACE("bignumToArray(%p) => %p", source, javaBytes); 476 return javaBytes; 477 } 478 479 /** 480 * OpenSSL locking support. Taken from the O'Reilly book by Viega et al., but I 481 * suppose there are not many other ways to do this on a Linux system (modulo 482 * isomorphism). 483 */ 484 #define MUTEX_TYPE pthread_mutex_t 485 #define MUTEX_SETUP(x) pthread_mutex_init(&(x), NULL) 486 #define MUTEX_CLEANUP(x) pthread_mutex_destroy(&(x)) 487 #define MUTEX_LOCK(x) pthread_mutex_lock(&(x)) 488 #define MUTEX_UNLOCK(x) pthread_mutex_unlock(&(x)) 489 #define THREAD_ID pthread_self() 490 #define THROW_SSLEXCEPTION (-2) 491 #define THROW_SOCKETTIMEOUTEXCEPTION (-3) 492 #define THROWN_EXCEPTION (-4) 493 494 static MUTEX_TYPE* mutex_buf = NULL; 495 496 static void locking_function(int mode, int n, const char*, int) { 497 if (mode & CRYPTO_LOCK) { 498 MUTEX_LOCK(mutex_buf[n]); 499 } else { 500 MUTEX_UNLOCK(mutex_buf[n]); 501 } 502 } 503 504 static unsigned long id_function(void) { 505 return ((unsigned long)THREAD_ID); 506 } 507 508 int THREAD_setup(void) { 509 mutex_buf = new MUTEX_TYPE[CRYPTO_num_locks()]; 510 if (!mutex_buf) { 511 return 0; 512 } 513 514 for (int i = 0; i < CRYPTO_num_locks(); ++i) { 515 MUTEX_SETUP(mutex_buf[i]); 516 } 517 518 CRYPTO_set_id_callback(id_function); 519 CRYPTO_set_locking_callback(locking_function); 520 521 return 1; 522 } 523 524 int THREAD_cleanup(void) { 525 if (!mutex_buf) { 526 return 0; 527 } 528 529 CRYPTO_set_id_callback(NULL); 530 CRYPTO_set_locking_callback(NULL); 531 532 for (int i = 0; i < CRYPTO_num_locks( ); i++) { 533 MUTEX_CLEANUP(mutex_buf[i]); 534 } 535 536 free(mutex_buf); 537 mutex_buf = NULL; 538 539 return 1; 540 } 541 542 /** 543 * Initialization phase for every OpenSSL job: Loads the Error strings, the 544 * crypto algorithms and reset the OpenSSL library 545 */ 546 static void NativeCrypto_clinit(JNIEnv*, jclass) 547 { 548 SSL_load_error_strings(); 549 ERR_load_crypto_strings(); 550 SSL_library_init(); 551 OpenSSL_add_all_algorithms(); 552 THREAD_setup(); 553 } 554 555 static void NativeCrypto_ENGINE_load_dynamic(JNIEnv*, jclass) { 556 JNI_TRACE("ENGINE_load_dynamic()"); 557 558 ENGINE_load_dynamic(); 559 } 560 561 static jint NativeCrypto_ENGINE_by_id(JNIEnv* env, jclass, jstring idJava) { 562 JNI_TRACE("ENGINE_by_id(%p)", idJava); 563 564 ScopedUtfChars id(env, idJava); 565 if (id.c_str() == NULL) { 566 jniThrowException(env, "java/lang/IllegalArgumentException", "id == NULL"); 567 return 0; 568 } 569 570 ENGINE* e = ENGINE_by_id(id.c_str()); 571 if (e == NULL) { 572 throwExceptionIfNecessary(env, "ENGINE_by_id"); 573 return 0; 574 } 575 576 JNI_TRACE("ENGINE_by_id(%p) => %p", idJava, e); 577 return static_cast<jint>(reinterpret_cast<uintptr_t>(e)); 578 } 579 580 static jint NativeCrypto_ENGINE_init(JNIEnv* env, jclass, jint engineRef) { 581 ENGINE* e = reinterpret_cast<ENGINE*>(static_cast<uintptr_t>(engineRef)); 582 JNI_TRACE("ENGINE_init(%p)", e); 583 584 if (e == NULL) { 585 jniThrowException(env, "java/lang/IllegalArgumentException", "engineRef == 0"); 586 return 0; 587 } 588 589 int ret = ENGINE_init(e); 590 JNI_TRACE("ENGINE_init(%p) => %d", e, ret); 591 return ret; 592 } 593 594 static jint NativeCrypto_ENGINE_finish(JNIEnv* env, jclass, jint engineRef) { 595 ENGINE* e = reinterpret_cast<ENGINE*>(static_cast<uintptr_t>(engineRef)); 596 JNI_TRACE("ENGINE_finish(%p)", e); 597 598 if (e == NULL) { 599 jniThrowException(env, "java/lang/IllegalArgumentException", "engineRef == 0"); 600 return 0; 601 } 602 603 int ret = ENGINE_finish(e); 604 JNI_TRACE("ENGINE_finish(%p) => %d", e, ret); 605 return ret; 606 } 607 608 static jint NativeCrypto_ENGINE_free(JNIEnv* env, jclass, jint engineRef) { 609 ENGINE* e = reinterpret_cast<ENGINE*>(static_cast<uintptr_t>(engineRef)); 610 JNI_TRACE("ENGINE_free(%p)", e); 611 612 if (e == NULL) { 613 jniThrowException(env, "java/lang/IllegalArgumentException", "engineRef == 0"); 614 return 0; 615 } 616 617 int ret = ENGINE_free(e); 618 JNI_TRACE("ENGINE_free(%p) => %d", e, ret); 619 return ret; 620 } 621 622 static jint NativeCrypto_ENGINE_load_private_key(JNIEnv* env, jclass, jint engineRef, 623 jstring idJava) { 624 ENGINE* e = reinterpret_cast<ENGINE*>(static_cast<uintptr_t>(engineRef)); 625 JNI_TRACE("ENGINE_load_private_key(%p, %p)", e, idJava); 626 627 ScopedUtfChars id(env, idJava); 628 if (id.c_str() == NULL) { 629 jniThrowException(env, "java/lang/IllegalArgumentException", "id == NULL"); 630 return 0; 631 } 632 633 Unique_EVP_PKEY pkey(ENGINE_load_private_key(e, id.c_str(), NULL, NULL)); 634 if (pkey.get() == NULL) { 635 throwExceptionIfNecessary(env, "ENGINE_load_private_key"); 636 return 0; 637 } 638 639 JNI_TRACE("ENGINE_load_private_key(%p, %p) => %p", e, idJava, pkey.get()); 640 return static_cast<jint>(reinterpret_cast<uintptr_t>(pkey.release())); 641 } 642 643 /** 644 * public static native int EVP_PKEY_new_DSA(byte[] p, byte[] q, byte[] g, 645 * byte[] pub_key, byte[] priv_key); 646 */ 647 static EVP_PKEY* NativeCrypto_EVP_PKEY_new_DSA(JNIEnv* env, jclass, 648 jbyteArray p, jbyteArray q, jbyteArray g, 649 jbyteArray pub_key, jbyteArray priv_key) { 650 JNI_TRACE("EVP_PKEY_new_DSA(p=%p, q=%p, g=%p, pub_key=%p, priv_key=%p)", 651 p, q, g, pub_key, priv_key); 652 653 Unique_DSA dsa(DSA_new()); 654 if (dsa.get() == NULL) { 655 jniThrowRuntimeException(env, "DSA_new failed"); 656 return NULL; 657 } 658 659 if (!arrayToBignum(env, p, &dsa->p)) { 660 return NULL; 661 } 662 663 if (!arrayToBignum(env, q, &dsa->q)) { 664 return NULL; 665 } 666 667 if (!arrayToBignum(env, g, &dsa->g)) { 668 return NULL; 669 } 670 671 if (pub_key != NULL && !arrayToBignum(env, pub_key, &dsa->pub_key)) { 672 return NULL; 673 } 674 675 if (priv_key != NULL && !arrayToBignum(env, priv_key, &dsa->priv_key)) { 676 return NULL; 677 } 678 679 if (dsa->p == NULL || dsa->q == NULL || dsa->g == NULL 680 || (dsa->pub_key == NULL && dsa->priv_key == NULL)) { 681 jniThrowRuntimeException(env, "Unable to convert BigInteger to BIGNUM"); 682 return NULL; 683 } 684 685 Unique_EVP_PKEY pkey(EVP_PKEY_new()); 686 if (pkey.get() == NULL) { 687 jniThrowRuntimeException(env, "EVP_PKEY_new failed"); 688 return NULL; 689 } 690 if (EVP_PKEY_assign_DSA(pkey.get(), dsa.get()) != 1) { 691 jniThrowRuntimeException(env, "EVP_PKEY_assign_DSA failed"); 692 return NULL; 693 } 694 OWNERSHIP_TRANSFERRED(dsa); 695 JNI_TRACE("EVP_PKEY_new_DSA(p=%p, q=%p, g=%p, pub_key=%p, priv_key=%p) => %p", 696 p, q, g, pub_key, priv_key, pkey.get()); 697 return pkey.release(); 698 } 699 700 /** 701 * private static native int EVP_PKEY_new_RSA(byte[] n, byte[] e, byte[] d, byte[] p, byte[] q); 702 */ 703 static jint NativeCrypto_EVP_PKEY_new_RSA(JNIEnv* env, jclass, 704 jbyteArray n, jbyteArray e, jbyteArray d, 705 jbyteArray p, jbyteArray q, 706 jbyteArray dmp1, jbyteArray dmq1, 707 jbyteArray iqmp) { 708 JNI_TRACE("EVP_PKEY_new_RSA(n=%p, e=%p, d=%p, p=%p, q=%p, dmp1=%p, dmq1=%p, iqmp=%p)", 709 n, e, d, p, q, dmp1, dmq1, iqmp); 710 711 Unique_RSA rsa(RSA_new()); 712 if (rsa.get() == NULL) { 713 jniThrowRuntimeException(env, "RSA_new failed"); 714 return 0; 715 } 716 717 if (e == NULL && d == NULL) { 718 jniThrowException(env, "java/lang/IllegalArgumentException", "e == NULL && d == NULL"); 719 JNI_TRACE("NativeCrypto_EVP_PKEY_new_RSA => e == NULL && d == NULL"); 720 return 0; 721 } 722 723 if (!arrayToBignum(env, n, &rsa->n)) { 724 return 0; 725 } 726 727 if (e != NULL && !arrayToBignum(env, e, &rsa->e)) { 728 return 0; 729 } 730 731 if (d != NULL && !arrayToBignum(env, d, &rsa->d)) { 732 return 0; 733 } 734 735 if (p != NULL && !arrayToBignum(env, p, &rsa->p)) { 736 return 0; 737 } 738 739 if (q != NULL && !arrayToBignum(env, q, &rsa->q)) { 740 return 0; 741 } 742 743 if (dmp1 != NULL && !arrayToBignum(env, dmp1, &rsa->dmp1)) { 744 return 0; 745 } 746 747 if (dmq1 != NULL && !arrayToBignum(env, dmq1, &rsa->dmq1)) { 748 return 0; 749 } 750 751 if (iqmp != NULL && !arrayToBignum(env, iqmp, &rsa->iqmp)) { 752 return 0; 753 } 754 755 #ifdef WITH_JNI_TRACE 756 if (p != NULL && q != NULL) { 757 int check = RSA_check_key(rsa.get()); 758 JNI_TRACE("EVP_PKEY_new_RSA(...) RSA_check_key returns %d", check); 759 } 760 #endif 761 762 if (rsa->n == NULL || (rsa->e == NULL && rsa->d == NULL)) { 763 jniThrowRuntimeException(env, "Unable to convert BigInteger to BIGNUM"); 764 return 0; 765 } 766 767 /* 768 * If the private exponent is available, there is the potential to do signing 769 * operations. If the public exponent is also available, OpenSSL will do RSA 770 * blinding. Enable it if possible. 771 */ 772 if (rsa->d != NULL) { 773 if (rsa->e != NULL) { 774 JNI_TRACE("EVP_PKEY_new_RSA(...) enabling RSA blinding => %p", rsa.get()); 775 RSA_blinding_on(rsa.get(), NULL); 776 } else { 777 JNI_TRACE("EVP_PKEY_new_RSA(...) disabling RSA blinding => %p", rsa.get()); 778 RSA_blinding_off(rsa.get()); 779 } 780 } 781 782 Unique_EVP_PKEY pkey(EVP_PKEY_new()); 783 if (pkey.get() == NULL) { 784 jniThrowRuntimeException(env, "EVP_PKEY_new failed"); 785 return 0; 786 } 787 if (EVP_PKEY_assign_RSA(pkey.get(), rsa.get()) != 1) { 788 jniThrowRuntimeException(env, "EVP_PKEY_new failed"); 789 return 0; 790 } 791 OWNERSHIP_TRANSFERRED(rsa); 792 JNI_TRACE("EVP_PKEY_new_RSA(n=%p, e=%p, d=%p, p=%p, q=%p dmp1=%p, dmq1=%p, iqmp=%p) => %p", 793 n, e, d, p, q, dmp1, dmq1, iqmp, pkey.get()); 794 return static_cast<jint>(reinterpret_cast<uintptr_t>(pkey.release())); 795 } 796 797 /** 798 * private static native int EVP_PKEY_size(int pkey); 799 */ 800 static int NativeCrypto_EVP_PKEY_type(JNIEnv* env, jclass, jint pkeyRef) { 801 EVP_PKEY* pkey = reinterpret_cast<EVP_PKEY*>(pkeyRef); 802 JNI_TRACE("EVP_PKEY_type(%p)", pkey); 803 804 if (pkey == NULL) { 805 jniThrowNullPointerException(env, NULL); 806 return -1; 807 } 808 809 int result = EVP_PKEY_type(pkey->type); 810 JNI_TRACE("EVP_PKEY_type(%p) => %d", pkey, result); 811 return result; 812 } 813 814 /** 815 * private static native int EVP_PKEY_size(int pkey); 816 */ 817 static int NativeCrypto_EVP_PKEY_size(JNIEnv* env, jclass, jint pkeyRef) { 818 EVP_PKEY* pkey = reinterpret_cast<EVP_PKEY*>(pkeyRef); 819 JNI_TRACE("EVP_PKEY_size(%p)", pkey); 820 821 if (pkey == NULL) { 822 jniThrowNullPointerException(env, NULL); 823 return -1; 824 } 825 826 int result = EVP_PKEY_size(pkey); 827 JNI_TRACE("EVP_PKEY_size(%p) => %d", pkey, result); 828 return result; 829 } 830 831 /** 832 * private static native void EVP_PKEY_free(int pkey); 833 */ 834 static void NativeCrypto_EVP_PKEY_free(JNIEnv*, jclass, EVP_PKEY* pkey) { 835 JNI_TRACE("EVP_PKEY_free(%p)", pkey); 836 837 if (pkey != NULL) { 838 EVP_PKEY_free(pkey); 839 } 840 } 841 842 /* 843 * static native byte[] i2d_PKCS8_PRIV_KEY_INFO(int, byte[]) 844 */ 845 static jbyteArray NativeCrypto_i2d_PKCS8_PRIV_KEY_INFO(JNIEnv* env, jclass, jint pkeyRef) { 846 EVP_PKEY* pkey = reinterpret_cast<EVP_PKEY*>(pkeyRef); 847 JNI_TRACE("i2d_PKCS8_PRIV_KEY_INFO(%p)", pkey); 848 849 if (pkey == NULL) { 850 jniThrowNullPointerException(env, NULL); 851 return NULL; 852 } 853 854 Unique_PKCS8_PRIV_KEY_INFO pkcs8(EVP_PKEY2PKCS8(pkey)); 855 if (pkcs8.get() == NULL) { 856 throwExceptionIfNecessary(env, "NativeCrypto_i2d_PKCS8_PRIV_KEY_INFO"); 857 JNI_TRACE("key=%p i2d_PKCS8_PRIV_KEY_INFO => error from key to PKCS8", pkey); 858 return NULL; 859 } 860 861 int len = i2d_PKCS8_PRIV_KEY_INFO(pkcs8.get(), NULL); 862 if (len < 0) { 863 throwExceptionIfNecessary(env, "i2d_PKCS8_PRIV_KEY_INFO"); 864 return NULL; 865 } 866 867 jbyteArray javaBytes = env->NewByteArray(len); 868 ScopedByteArrayRW bytes(env, javaBytes); 869 if (bytes.get() == NULL) { 870 return NULL; 871 } 872 873 unsigned char* tmp = reinterpret_cast<unsigned char*>(bytes.get()); 874 if (i2d_PKCS8_PRIV_KEY_INFO(pkcs8.get(), &tmp) < 0) { 875 throwExceptionIfNecessary(env, "i2d_PKCS8_PRIV_KEY_INFO"); 876 return NULL; 877 } 878 879 JNI_TRACE("pkey=%p i2d_PKCS8_PRIV_KEY_INFO => size=%d", pkey, len); 880 return javaBytes; 881 } 882 883 /* 884 * static native int d2i_PKCS8_PRIV_KEY_INFO(byte[]) 885 */ 886 static jint NativeCrypto_d2i_PKCS8_PRIV_KEY_INFO(JNIEnv* env, jclass, jbyteArray keyJavaBytes) { 887 JNI_TRACE("d2i_PKCS8_PRIV_KEY_INFO(%p)", keyJavaBytes); 888 889 ScopedByteArrayRO bytes(env, keyJavaBytes); 890 if (bytes.get() == NULL) { 891 JNI_TRACE("bytes=%p d2i_PKCS8_PRIV_KEY_INFO => threw exception", keyJavaBytes); 892 return 0; 893 } 894 895 const unsigned char* tmp = reinterpret_cast<const unsigned char*>(bytes.get()); 896 Unique_PKCS8_PRIV_KEY_INFO pkcs8(d2i_PKCS8_PRIV_KEY_INFO(NULL, &tmp, bytes.size())); 897 if (pkcs8.get() == NULL) { 898 throwExceptionIfNecessary(env, "d2i_PKCS8_PRIV_KEY_INFO"); 899 JNI_TRACE("ssl=%p d2i_PKCS8_PRIV_KEY_INFO => error from DER to PKCS8", keyJavaBytes); 900 return 0; 901 } 902 903 Unique_EVP_PKEY pkey(EVP_PKCS82PKEY(pkcs8.get())); 904 if (pkey.get() == NULL) { 905 throwExceptionIfNecessary(env, "d2i_PKCS8_PRIV_KEY_INFO"); 906 JNI_TRACE("ssl=%p d2i_PKCS8_PRIV_KEY_INFO => error from PKCS8 to key", keyJavaBytes); 907 return 0; 908 } 909 910 JNI_TRACE("bytes=%p d2i_PKCS8_PRIV_KEY_INFO => %p", keyJavaBytes, pkey.get()); 911 return static_cast<jint>(reinterpret_cast<uintptr_t>(pkey.release())); 912 } 913 914 /* 915 * static native byte[] i2d_PUBKEY(int) 916 */ 917 static jbyteArray NativeCrypto_i2d_PUBKEY(JNIEnv* env, jclass, jint pkeyRef) { 918 EVP_PKEY* pkey = reinterpret_cast<EVP_PKEY*>(pkeyRef); 919 JNI_TRACE("i2d_PUBKEY(%p)", pkey); 920 921 if (pkey == NULL) { 922 jniThrowNullPointerException(env, NULL); 923 return NULL; 924 } 925 926 int len = i2d_PUBKEY(pkey, NULL); 927 if (len < 0) { 928 throwExceptionIfNecessary(env, "i2d_PUBKEY"); 929 JNI_TRACE("i2d_PUBKEY(%p) => threw error measuring key", pkey); 930 return NULL; 931 } 932 933 jbyteArray javaBytes = env->NewByteArray(len); 934 ScopedByteArrayRW bytes(env, javaBytes); 935 if (bytes.get() == NULL) { 936 return NULL; 937 } 938 939 unsigned char* tmp = reinterpret_cast<unsigned char*>(bytes.get()); 940 if (i2d_PUBKEY(pkey, &tmp) < 0) { 941 throwExceptionIfNecessary(env, "i2d_PUBKEY"); 942 JNI_TRACE("i2d_PUBKEY(%p) => threw error converting key", pkey); 943 return NULL; 944 } 945 946 JNI_TRACE("pkey=%p i2d_PUBKEY => size=%d", pkey, len); 947 return javaBytes; 948 } 949 950 /* 951 * static native int d2i_PUBKEY(byte[]) 952 */ 953 static jint NativeCrypto_d2i_PUBKEY(JNIEnv* env, jclass, jbyteArray javaBytes) { 954 JNI_TRACE("d2i_PUBKEY(%p)", javaBytes); 955 956 ScopedByteArrayRO bytes(env, javaBytes); 957 if (bytes.get() == NULL) { 958 JNI_TRACE("d2i_PUBKEY(%p) => threw error", javaBytes); 959 return 0; 960 } 961 962 const unsigned char* tmp = reinterpret_cast<const unsigned char*>(bytes.get()); 963 Unique_EVP_PKEY pkey(d2i_PUBKEY(NULL, &tmp, bytes.size())); 964 if (pkey.get() == NULL) { 965 JNI_TRACE("bytes=%p d2i_PUBKEY => threw exception", javaBytes); 966 throwExceptionIfNecessary(env, "d2i_PUBKEY"); 967 return 0; 968 } 969 970 return static_cast<jint>(reinterpret_cast<uintptr_t>(pkey.release())); 971 } 972 973 /* 974 * public static native int RSA_generate_key(int modulusBits, byte[] publicExponent); 975 */ 976 static jint NativeCrypto_RSA_generate_key_ex(JNIEnv* env, jclass, jint modulusBits, 977 jbyteArray publicExponent) { 978 JNI_TRACE("RSA_generate_key_ex(%d, %p)", modulusBits, publicExponent); 979 980 BIGNUM* eRef; 981 if (!arrayToBignum(env, publicExponent, &eRef)) { 982 return 0; 983 } 984 Unique_BIGNUM e(eRef); 985 986 Unique_RSA rsa(RSA_new()); 987 if (rsa.get() == NULL) { 988 jniThrowOutOfMemoryError(env, "Unable to allocate RSA key"); 989 return 0; 990 } 991 992 if (RSA_generate_key_ex(rsa.get(), modulusBits, e.get(), NULL) < 0) { 993 throwExceptionIfNecessary(env, "RSA_generate_key_ex"); 994 return 0; 995 } 996 997 Unique_EVP_PKEY pkey(EVP_PKEY_new()); 998 if (pkey.get() == NULL) { 999 jniThrowRuntimeException(env, "RSA_generate_key_ex failed"); 1000 return 0; 1001 } 1002 1003 if (EVP_PKEY_assign_RSA(pkey.get(), rsa.get()) != 1) { 1004 jniThrowRuntimeException(env, "RSA_generate_key_ex failed"); 1005 return 0; 1006 } 1007 1008 OWNERSHIP_TRANSFERRED(rsa); 1009 JNI_TRACE("RSA_generate_key_ex(n=%d, e=%p) => %p", modulusBits, publicExponent, pkey.get()); 1010 return static_cast<jint>(reinterpret_cast<uintptr_t>(pkey.release())); 1011 } 1012 1013 /* 1014 * public static native byte[][] get_RSA_public_params(int); 1015 */ 1016 static jobjectArray NativeCrypto_get_RSA_public_params(JNIEnv* env, jclass, jint pkeyRef) { 1017 EVP_PKEY* pkey = reinterpret_cast<EVP_PKEY*>(pkeyRef); 1018 JNI_TRACE("get_RSA_public_params(%p)", pkey); 1019 1020 Unique_RSA rsa(EVP_PKEY_get1_RSA(pkey)); 1021 if (rsa.get() == NULL) { 1022 jniThrowRuntimeException(env, "get_RSA_public_params failed"); 1023 return 0; 1024 } 1025 1026 jobjectArray joa = env->NewObjectArray(2, JniConstants::byteArrayClass, NULL); 1027 if (joa == NULL) { 1028 return NULL; 1029 } 1030 1031 jbyteArray n = bignumToArray(env, rsa->n); 1032 if (env->ExceptionCheck()) { 1033 return NULL; 1034 } 1035 env->SetObjectArrayElement(joa, 0, n); 1036 1037 jbyteArray e = bignumToArray(env, rsa->e); 1038 if (env->ExceptionCheck()) { 1039 return NULL; 1040 } 1041 env->SetObjectArrayElement(joa, 1, e); 1042 1043 return joa; 1044 } 1045 1046 /* 1047 * public static native byte[][] get_RSA_private_params(int); 1048 */ 1049 static jobjectArray NativeCrypto_get_RSA_private_params(JNIEnv* env, jclass, jint pkeyRef) { 1050 EVP_PKEY* pkey = reinterpret_cast<EVP_PKEY*>(pkeyRef); 1051 JNI_TRACE("get_RSA_public_params(%p)", pkey); 1052 1053 Unique_RSA rsa(EVP_PKEY_get1_RSA(pkey)); 1054 if (rsa.get() == NULL) { 1055 jniThrowRuntimeException(env, "get_RSA_public_params failed"); 1056 return 0; 1057 } 1058 1059 jobjectArray joa = env->NewObjectArray(8, JniConstants::byteArrayClass, NULL); 1060 if (joa == NULL) { 1061 return NULL; 1062 } 1063 1064 jbyteArray n = bignumToArray(env, rsa->n); 1065 if (env->ExceptionCheck()) { 1066 return NULL; 1067 } 1068 env->SetObjectArrayElement(joa, 0, n); 1069 1070 if (rsa->e != NULL) { 1071 jbyteArray e = bignumToArray(env, rsa->e); 1072 if (env->ExceptionCheck()) { 1073 return NULL; 1074 } 1075 env->SetObjectArrayElement(joa, 1, e); 1076 } 1077 1078 if (rsa->d != NULL) { 1079 jbyteArray d = bignumToArray(env, rsa->d); 1080 if (env->ExceptionCheck()) { 1081 return NULL; 1082 } 1083 env->SetObjectArrayElement(joa, 2, d); 1084 } 1085 1086 if (rsa->p != NULL) { 1087 jbyteArray p = bignumToArray(env, rsa->p); 1088 if (env->ExceptionCheck()) { 1089 return NULL; 1090 } 1091 env->SetObjectArrayElement(joa, 3, p); 1092 } 1093 1094 if (rsa->q != NULL) { 1095 jbyteArray q = bignumToArray(env, rsa->q); 1096 if (env->ExceptionCheck()) { 1097 return NULL; 1098 } 1099 env->SetObjectArrayElement(joa, 4, q); 1100 } 1101 1102 if (rsa->dmp1 != NULL) { 1103 jbyteArray dmp1 = bignumToArray(env, rsa->dmp1); 1104 if (env->ExceptionCheck()) { 1105 return NULL; 1106 } 1107 env->SetObjectArrayElement(joa, 5, dmp1); 1108 } 1109 1110 if (rsa->dmq1 != NULL) { 1111 jbyteArray dmq1 = bignumToArray(env, rsa->dmq1); 1112 if (env->ExceptionCheck()) { 1113 return NULL; 1114 } 1115 env->SetObjectArrayElement(joa, 6, dmq1); 1116 } 1117 1118 if (rsa->iqmp != NULL) { 1119 jbyteArray iqmp = bignumToArray(env, rsa->iqmp); 1120 if (env->ExceptionCheck()) { 1121 return NULL; 1122 } 1123 env->SetObjectArrayElement(joa, 7, iqmp); 1124 } 1125 1126 return joa; 1127 } 1128 1129 /* 1130 * public static native int DSA_generate_key(int, byte[]); 1131 */ 1132 static jint NativeCrypto_DSA_generate_key(JNIEnv* env, jclass, jint primeBits, 1133 jbyteArray seedJavaBytes, jbyteArray gBytes, jbyteArray pBytes, jbyteArray qBytes) { 1134 JNI_TRACE("DSA_generate_key(%d, %p, %p, %p, %p)", primeBits, seedJavaBytes, 1135 gBytes, pBytes, qBytes); 1136 1137 UniquePtr<unsigned char[]> seedPtr; 1138 unsigned long seedSize = 0; 1139 if (seedJavaBytes != NULL) { 1140 ScopedByteArrayRO seed(env, seedJavaBytes); 1141 if (seed.get() == NULL) { 1142 return 0; 1143 } 1144 1145 seedSize = seed.size(); 1146 seedPtr.reset(new unsigned char[seedSize]); 1147 1148 memcpy(seedPtr.get(), seed.get(), seedSize); 1149 } 1150 1151 Unique_DSA dsa(DSA_new()); 1152 if (dsa.get() == NULL) { 1153 JNI_TRACE("DSA_generate_key failed"); 1154 jniThrowOutOfMemoryError(env, "Unable to allocate DSA key"); 1155 return 0; 1156 } 1157 1158 if (gBytes != NULL && pBytes != NULL && qBytes != NULL) { 1159 JNI_TRACE("DSA_generate_key parameters specified"); 1160 1161 if (!arrayToBignum(env, gBytes, &dsa->g)) { 1162 return 0; 1163 } 1164 1165 if (!arrayToBignum(env, pBytes, &dsa->p)) { 1166 return 0; 1167 } 1168 1169 if (!arrayToBignum(env, qBytes, &dsa->q)) { 1170 return 0; 1171 } 1172 } else { 1173 JNI_TRACE("DSA_generate_key generating parameters"); 1174 1175 if (!DSA_generate_parameters_ex(dsa.get(), primeBits, seedPtr.get(), seedSize, NULL, NULL, NULL)) { 1176 JNI_TRACE("DSA_generate_key => param generation failed"); 1177 throwExceptionIfNecessary(env, "NativeCrypto_DSA_generate_parameters_ex failed"); 1178 return 0; 1179 } 1180 } 1181 1182 if (!DSA_generate_key(dsa.get())) { 1183 JNI_TRACE("DSA_generate_key failed"); 1184 throwExceptionIfNecessary(env, "NativeCrypto_DSA_generate_key failed"); 1185 return 0; 1186 } 1187 1188 Unique_EVP_PKEY pkey(EVP_PKEY_new()); 1189 if (pkey.get() == NULL) { 1190 JNI_TRACE("DSA_generate_key failed"); 1191 jniThrowRuntimeException(env, "NativeCrypto_DSA_generate_key failed"); 1192 return 0; 1193 } 1194 1195 if (EVP_PKEY_assign_DSA(pkey.get(), dsa.get()) != 1) { 1196 JNI_TRACE("DSA_generate_key failed"); 1197 jniThrowRuntimeException(env, "NativeCrypto_DSA_generate_key failed"); 1198 return 0; 1199 } 1200 1201 OWNERSHIP_TRANSFERRED(dsa); 1202 JNI_TRACE("DSA_generate_key(n=%d, e=%p) => %p", primeBits, seedPtr.get(), pkey.get()); 1203 return static_cast<jint>(reinterpret_cast<uintptr_t>(pkey.release())); 1204 } 1205 1206 /* 1207 * public static native byte[][] get_DSA_params(int); 1208 */ 1209 static jobjectArray NativeCrypto_get_DSA_params(JNIEnv* env, jclass, jint pkeyRef) { 1210 EVP_PKEY* pkey = reinterpret_cast<EVP_PKEY*>(pkeyRef); 1211 JNI_TRACE("get_DSA_params(%p)", pkey); 1212 1213 Unique_DSA dsa(EVP_PKEY_get1_DSA(pkey)); 1214 if (dsa.get() == NULL) { 1215 jniThrowRuntimeException(env, "get_DSA_params failed"); 1216 return 0; 1217 } 1218 1219 jobjectArray joa = env->NewObjectArray(5, JniConstants::byteArrayClass, NULL); 1220 if (joa == NULL) { 1221 return NULL; 1222 } 1223 1224 jbyteArray g = bignumToArray(env, dsa->g); 1225 if (env->ExceptionCheck()) { 1226 return NULL; 1227 } 1228 env->SetObjectArrayElement(joa, 0, g); 1229 1230 jbyteArray p = bignumToArray(env, dsa->p); 1231 if (env->ExceptionCheck()) { 1232 return NULL; 1233 } 1234 env->SetObjectArrayElement(joa, 1, p); 1235 1236 jbyteArray q = bignumToArray(env, dsa->q); 1237 if (env->ExceptionCheck()) { 1238 return NULL; 1239 } 1240 env->SetObjectArrayElement(joa, 2, q); 1241 1242 if (dsa->pub_key != NULL) { 1243 jbyteArray pub_key = bignumToArray(env, dsa->pub_key); 1244 if (env->ExceptionCheck()) { 1245 return NULL; 1246 } 1247 env->SetObjectArrayElement(joa, 3, pub_key); 1248 } 1249 1250 if (dsa->priv_key != NULL) { 1251 jbyteArray priv_key = bignumToArray(env, dsa->priv_key); 1252 if (env->ExceptionCheck()) { 1253 return NULL; 1254 } 1255 env->SetObjectArrayElement(joa, 4, priv_key); 1256 } 1257 1258 return joa; 1259 } 1260 1261 /* 1262 * public static native void EVP_MD_CTX_destroy(int) 1263 */ 1264 static void NativeCrypto_EVP_MD_CTX_destroy(JNIEnv*, jclass, EVP_MD_CTX* ctx) { 1265 JNI_TRACE("NativeCrypto_EVP_MD_CTX_destroy(%p)", ctx); 1266 1267 if (ctx != NULL) { 1268 EVP_MD_CTX_destroy(ctx); 1269 } 1270 } 1271 1272 /* 1273 * public static native int EVP_MD_CTX_copy(int) 1274 */ 1275 static jint NativeCrypto_EVP_MD_CTX_copy(JNIEnv* env, jclass, EVP_MD_CTX* ctx) { 1276 JNI_TRACE("NativeCrypto_EVP_MD_CTX_copy(%p)", ctx); 1277 1278 if (ctx == NULL) { 1279 jniThrowNullPointerException(env, NULL); 1280 return 0; 1281 } 1282 1283 EVP_MD_CTX* copy = EVP_MD_CTX_create(); 1284 if (copy == NULL) { 1285 jniThrowOutOfMemoryError(env, "Unable to allocate copy of EVP_MD_CTX"); 1286 return 0; 1287 } 1288 1289 EVP_MD_CTX_init(copy); 1290 int result = EVP_MD_CTX_copy_ex(copy, ctx); 1291 if (result == 0) { 1292 EVP_MD_CTX_destroy(copy); 1293 jniThrowRuntimeException(env, "Unable to copy EVP_MD_CTX"); 1294 return 0; 1295 } 1296 1297 JNI_TRACE("NativeCrypto_EVP_MD_CTX_copy(%p) => %p", ctx, copy); 1298 return static_cast<jint>(reinterpret_cast<uintptr_t>(copy)); 1299 } 1300 1301 /* 1302 * public static native int EVP_DigestFinal(int, byte[], int) 1303 */ 1304 static jint NativeCrypto_EVP_DigestFinal(JNIEnv* env, jclass, jint ctxRef, 1305 jbyteArray hash, jint offset) { 1306 EVP_MD_CTX* ctx = reinterpret_cast<EVP_MD_CTX*>(ctxRef); 1307 JNI_TRACE("NativeCrypto_EVP_DigestFinal(%p, %p, %d)", ctx, hash, offset); 1308 1309 if (ctx == NULL || hash == NULL) { 1310 jniThrowNullPointerException(env, NULL); 1311 return -1; 1312 } 1313 1314 ScopedByteArrayRW hashBytes(env, hash); 1315 if (hashBytes.get() == NULL) { 1316 return -1; 1317 } 1318 unsigned int bytesWritten = -1; 1319 int ok = EVP_DigestFinal(ctx, 1320 reinterpret_cast<unsigned char*>(hashBytes.get() + offset), 1321 &bytesWritten); 1322 if (ok == 0) { 1323 throwExceptionIfNecessary(env, "NativeCrypto_EVP_DigestFinal"); 1324 } 1325 EVP_MD_CTX_destroy(ctx); 1326 1327 JNI_TRACE("NativeCrypto_EVP_DigestFinal(%p, %p, %d) => %d", ctx, hash, offset, bytesWritten); 1328 return bytesWritten; 1329 } 1330 1331 /* 1332 * public static native int EVP_DigestInit(int) 1333 */ 1334 static jint NativeCrypto_EVP_DigestInit(JNIEnv* env, jclass, jint evpMdRef) { 1335 EVP_MD* evp_md = reinterpret_cast<EVP_MD*>(evpMdRef); 1336 JNI_TRACE("NativeCrypto_EVP_DigestInit(%p)", evp_md); 1337 1338 if (evp_md == NULL) { 1339 jniThrowNullPointerException(env, NULL); 1340 return 0; 1341 } 1342 1343 Unique_EVP_MD_CTX ctx(EVP_MD_CTX_create()); 1344 if (ctx.get() == NULL) { 1345 jniThrowOutOfMemoryError(env, "Unable to allocate EVP_MD_CTX"); 1346 return 0; 1347 } 1348 JNI_TRACE("NativeCrypto_EVP_DigestInit ctx=%p", ctx.get()); 1349 1350 int ok = EVP_DigestInit(ctx.get(), evp_md); 1351 if (ok == 0) { 1352 bool exception = throwExceptionIfNecessary(env, "NativeCrypto_EVP_DigestInit"); 1353 if (exception) { 1354 return 0; 1355 } 1356 } 1357 return static_cast<jint>(reinterpret_cast<uintptr_t>(ctx.release())); 1358 } 1359 1360 /* 1361 * public static native int EVP_get_digestbyname(java.lang.String) 1362 */ 1363 static jint NativeCrypto_EVP_get_digestbyname(JNIEnv* env, jclass, jstring algorithm) { 1364 JNI_TRACE("NativeCrypto_EVP_get_digestbyname(%p)", algorithm); 1365 1366 if (algorithm == NULL) { 1367 jniThrowNullPointerException(env, NULL); 1368 return -1; 1369 } 1370 1371 ScopedUtfChars algorithmChars(env, algorithm); 1372 if (algorithmChars.c_str() == NULL) { 1373 return 0; 1374 } 1375 JNI_TRACE("NativeCrypto_EVP_get_digestbyname(%s)", algorithmChars.c_str()); 1376 1377 const EVP_MD* evp_md = EVP_get_digestbyname(algorithmChars.c_str()); 1378 if (evp_md == NULL) { 1379 jniThrowRuntimeException(env, "Hash algorithm not found"); 1380 return 0; 1381 } 1382 1383 JNI_TRACE("NativeCrypto_EVP_get_digestbyname(%s) => %p", algorithmChars.c_str(), evp_md); 1384 return static_cast<jint>(reinterpret_cast<uintptr_t>(evp_md)); 1385 } 1386 1387 /* 1388 * public static native int EVP_MD_size(int) 1389 */ 1390 static jint NativeCrypto_EVP_MD_size(JNIEnv* env, jclass, EVP_MD* evp_md) { 1391 JNI_TRACE("NativeCrypto_EVP_MD_size(%p)", evp_md); 1392 1393 if (evp_md == NULL) { 1394 jniThrowNullPointerException(env, NULL); 1395 return -1; 1396 } 1397 1398 int result = EVP_MD_size(evp_md); 1399 JNI_TRACE("NativeCrypto_EVP_MD_size(%p) => %d", evp_md, result); 1400 return result; 1401 } 1402 1403 /* 1404 * public static int void EVP_MD_block_size(int) 1405 */ 1406 static jint NativeCrypto_EVP_MD_block_size(JNIEnv* env, jclass, EVP_MD* evp_md) { 1407 JNI_TRACE("NativeCrypto_EVP_MD_block_size(%p)", evp_md); 1408 1409 if (evp_md == NULL) { 1410 jniThrowNullPointerException(env, NULL); 1411 return -1; 1412 } 1413 1414 int result = EVP_MD_block_size(evp_md); 1415 JNI_TRACE("NativeCrypto_EVP_MD_block_size(%p) => %d", evp_md, result); 1416 return result; 1417 } 1418 1419 /* 1420 * public static native void EVP_DigestUpdate(int, byte[], int, int) 1421 */ 1422 static void NativeCrypto_EVP_DigestUpdate(JNIEnv* env, jclass, jint ctxRef, 1423 jbyteArray buffer, jint offset, jint length) { 1424 EVP_MD_CTX* ctx = reinterpret_cast<EVP_MD_CTX*>(ctxRef); 1425 JNI_TRACE("NativeCrypto_EVP_DigestUpdate(%p, %p, %d, %d)", ctx, buffer, offset, length); 1426 1427 if (offset < 0 || length < 0) { 1428 jniThrowException(env, "java/lang/IndexOutOfBoundsException", NULL); 1429 return; 1430 } 1431 1432 if (ctx == NULL || buffer == NULL) { 1433 jniThrowNullPointerException(env, NULL); 1434 return; 1435 } 1436 1437 ScopedByteArrayRO bufferBytes(env, buffer); 1438 if (bufferBytes.get() == NULL) { 1439 return; 1440 } 1441 int ok = EVP_DigestUpdate(ctx, 1442 reinterpret_cast<const unsigned char*>(bufferBytes.get() + offset), 1443 length); 1444 if (ok == 0) { 1445 throwExceptionIfNecessary(env, "NativeCrypto_EVP_DigestUpdate"); 1446 } 1447 } 1448 1449 /* 1450 * public static native int EVP_SignInit(java.lang.String) 1451 */ 1452 static jint NativeCrypto_EVP_SignInit(JNIEnv* env, jclass, jstring algorithm) { 1453 JNI_TRACE("NativeCrypto_EVP_SignInit(%p)", algorithm); 1454 1455 if (algorithm == NULL) { 1456 jniThrowNullPointerException(env, NULL); 1457 return 0; 1458 } 1459 1460 Unique_EVP_MD_CTX ctx(EVP_MD_CTX_create()); 1461 if (ctx.get() == NULL) { 1462 jniThrowOutOfMemoryError(env, "Unable to allocate EVP_MD_CTX"); 1463 return 0; 1464 } 1465 JNI_TRACE("NativeCrypto_EVP_SignInit ctx=%p", ctx.get()); 1466 1467 ScopedUtfChars algorithmChars(env, algorithm); 1468 if (algorithmChars.c_str() == NULL) { 1469 return 0; 1470 } 1471 JNI_TRACE("NativeCrypto_EVP_SignInit algorithmChars=%s", algorithmChars.c_str()); 1472 1473 const EVP_MD* digest = EVP_get_digestbynid(OBJ_txt2nid(algorithmChars.c_str())); 1474 if (digest == NULL) { 1475 jniThrowRuntimeException(env, "Hash algorithm not found"); 1476 return 0; 1477 } 1478 1479 int ok = EVP_SignInit(ctx.get(), digest); 1480 if (ok == 0) { 1481 bool exception = throwExceptionIfNecessary(env, "NativeCrypto_EVP_SignInit"); 1482 if (exception) { 1483 return 0; 1484 } 1485 } 1486 return static_cast<jint>(reinterpret_cast<uintptr_t>(ctx.release())); 1487 } 1488 1489 /* 1490 * public static native void EVP_SignUpdate(int, byte[], int, int) 1491 */ 1492 static void NativeCrypto_EVP_SignUpdate(JNIEnv* env, jclass, jint ctxRef, 1493 jbyteArray buffer, jint offset, jint length) { 1494 EVP_MD_CTX* ctx = reinterpret_cast<EVP_MD_CTX*>(ctxRef); 1495 JNI_TRACE("NativeCrypto_EVP_SignUpdate(%p, %p, %d, %d)", ctx, buffer, offset, length); 1496 1497 if (ctx == NULL || buffer == NULL) { 1498 jniThrowNullPointerException(env, NULL); 1499 return; 1500 } 1501 1502 ScopedByteArrayRO bufferBytes(env, buffer); 1503 if (bufferBytes.get() == NULL) { 1504 return; 1505 } 1506 int ok = EVP_SignUpdate(ctx, 1507 reinterpret_cast<const unsigned char*>(bufferBytes.get() + offset), 1508 length); 1509 if (ok == 0) { 1510 throwExceptionIfNecessary(env, "NativeCrypto_EVP_SignUpdate"); 1511 } 1512 } 1513 1514 /* 1515 * public static native int EVP_SignFinal(int, byte[], int, int) 1516 */ 1517 static jint NativeCrypto_EVP_SignFinal(JNIEnv* env, jclass, jint ctxRef, jbyteArray signature, 1518 jint offset, jint pkeyRef) { 1519 EVP_MD_CTX* ctx = reinterpret_cast<EVP_MD_CTX*>(ctxRef); 1520 EVP_PKEY* pkey = reinterpret_cast<EVP_PKEY*>(pkeyRef); 1521 JNI_TRACE("NativeCrypto_EVP_SignFinal(%p, %p, %d, %p)", ctx, signature, offset, pkey); 1522 1523 if (ctx == NULL || pkey == NULL) { 1524 jniThrowNullPointerException(env, NULL); 1525 return -1; 1526 } 1527 1528 ScopedByteArrayRW signatureBytes(env, signature); 1529 if (signatureBytes.get() == NULL) { 1530 return -1; 1531 } 1532 unsigned int bytesWritten = -1; 1533 int ok = EVP_SignFinal(ctx, 1534 reinterpret_cast<unsigned char*>(signatureBytes.get() + offset), 1535 &bytesWritten, 1536 pkey); 1537 if (ok == 0) { 1538 throwExceptionIfNecessary(env, "NativeCrypto_EVP_SignFinal"); 1539 } 1540 JNI_TRACE("NativeCrypto_EVP_SignFinal(%p, %p, %d, %p) => %u", 1541 ctx, signature, offset, pkey, bytesWritten); 1542 1543 return bytesWritten; 1544 } 1545 1546 /* 1547 * public static native int EVP_VerifyInit(java.lang.String) 1548 */ 1549 static jint NativeCrypto_EVP_VerifyInit(JNIEnv* env, jclass, jstring algorithm) { 1550 JNI_TRACE("NativeCrypto_EVP_VerifyInit(%p)", algorithm); 1551 1552 if (algorithm == NULL) { 1553 jniThrowNullPointerException(env, NULL); 1554 return 0; 1555 } 1556 1557 Unique_EVP_MD_CTX ctx(EVP_MD_CTX_create()); 1558 if (ctx.get() == NULL) { 1559 jniThrowOutOfMemoryError(env, "Unable to allocate EVP_MD_CTX"); 1560 return 0; 1561 } 1562 JNI_TRACE("NativeCrypto_EVP_VerifyInit ctx=%p", ctx.get()); 1563 1564 ScopedUtfChars algorithmChars(env, algorithm); 1565 if (algorithmChars.c_str() == NULL) { 1566 return 0; 1567 } 1568 JNI_TRACE("NativeCrypto_EVP_VerifyInit algorithmChars=%s", algorithmChars.c_str()); 1569 1570 const EVP_MD* digest = EVP_get_digestbynid(OBJ_txt2nid(algorithmChars.c_str())); 1571 if (digest == NULL) { 1572 jniThrowRuntimeException(env, "Hash algorithm not found"); 1573 return 0; 1574 } 1575 1576 int ok = EVP_VerifyInit(ctx.get(), digest); 1577 if (ok == 0) { 1578 bool exception = throwExceptionIfNecessary(env, "NativeCrypto_EVP_VerifyInit"); 1579 if (exception) { 1580 return 0; 1581 } 1582 } 1583 return static_cast<jint>(reinterpret_cast<uintptr_t>(ctx.release())); 1584 } 1585 1586 /* 1587 * public static native void EVP_VerifyUpdate(int, byte[], int, int) 1588 */ 1589 static void NativeCrypto_EVP_VerifyUpdate(JNIEnv* env, jclass, jint ctxRef, 1590 jbyteArray buffer, jint offset, jint length) { 1591 EVP_MD_CTX* ctx = reinterpret_cast<EVP_MD_CTX*>(ctxRef); 1592 JNI_TRACE("NativeCrypto_EVP_VerifyUpdate(%p, %p, %d, %d)", ctx, buffer, offset, length); 1593 1594 if (ctx == NULL || buffer == NULL) { 1595 jniThrowNullPointerException(env, NULL); 1596 return; 1597 } 1598 1599 ScopedByteArrayRO bufferBytes(env, buffer); 1600 if (bufferBytes.get() == NULL) { 1601 return; 1602 } 1603 int ok = EVP_VerifyUpdate(ctx, 1604 reinterpret_cast<const unsigned char*>(bufferBytes.get() + offset), 1605 length); 1606 if (ok == 0) { 1607 throwExceptionIfNecessary(env, "NativeCrypto_EVP_VerifyUpdate"); 1608 } 1609 } 1610 1611 /* 1612 * public static native int EVP_VerifyFinal(int, byte[], int, int, int) 1613 */ 1614 static jint NativeCrypto_EVP_VerifyFinal(JNIEnv* env, jclass, jint ctxRef, jbyteArray buffer, 1615 jint offset, jint length, jint pkeyRef) { 1616 EVP_MD_CTX* ctx = reinterpret_cast<EVP_MD_CTX*>(ctxRef); 1617 EVP_PKEY* pkey = reinterpret_cast<EVP_PKEY*>(pkeyRef); 1618 JNI_TRACE("NativeCrypto_EVP_VerifyFinal(%p, %p, %d, %d, %p)", 1619 ctx, buffer, offset, length, pkey); 1620 1621 if (ctx == NULL || buffer == NULL || pkey == NULL) { 1622 jniThrowNullPointerException(env, NULL); 1623 return -1; 1624 } 1625 1626 ScopedByteArrayRO bufferBytes(env, buffer); 1627 if (bufferBytes.get() == NULL) { 1628 return -1; 1629 } 1630 int ok = EVP_VerifyFinal(ctx, 1631 reinterpret_cast<const unsigned char*>(bufferBytes.get() + offset), 1632 length, 1633 pkey); 1634 if (ok < 0) { 1635 throwExceptionIfNecessary(env, "NativeCrypto_EVP_VerifyFinal"); 1636 } 1637 JNI_TRACE("NativeCrypto_EVP_VerifyFinal(%p, %p, %d, %d, %p) => %d", 1638 ctx, buffer, offset, length, pkey, ok); 1639 1640 return ok; 1641 } 1642 1643 /* 1644 * public static native int EVP_get_cipherbyname(java.lang.String) 1645 */ 1646 static jint NativeCrypto_EVP_get_cipherbyname(JNIEnv* env, jclass, jstring algorithm) { 1647 JNI_TRACE("EVP_get_cipherbyname(%p)", algorithm); 1648 if (algorithm == NULL) { 1649 JNI_TRACE("EVP_get_cipherbyname(%p) => threw exception algorithm == null", algorithm); 1650 jniThrowNullPointerException(env, NULL); 1651 return -1; 1652 } 1653 1654 ScopedUtfChars algorithmChars(env, algorithm); 1655 if (algorithmChars.c_str() == NULL) { 1656 return 0; 1657 } 1658 JNI_TRACE("EVP_get_cipherbyname(%p) => algorithm = %s", algorithm, algorithmChars.c_str()); 1659 1660 const EVP_CIPHER* evp_cipher = EVP_get_cipherbyname(algorithmChars.c_str()); 1661 if (evp_cipher == NULL) { 1662 jniThrowRuntimeException(env, "Cipher algorithm not found"); 1663 return 0; 1664 } 1665 1666 JNI_TRACE("EVP_get_cipherbyname(%s) => %p", algorithmChars.c_str(), evp_cipher); 1667 return static_cast<jint>(reinterpret_cast<uintptr_t>(evp_cipher)); 1668 } 1669 1670 /* 1671 * public static native int EVP_CipherInit_ex(int cipherNid, byte[] key, byte[] iv, 1672 * boolean encrypting); 1673 */ 1674 static jint NativeCrypto_EVP_CipherInit_ex(JNIEnv* env, jclass, jint cipherRef, jbyteArray keyArray, 1675 jbyteArray ivArray, jboolean encrypting) { 1676 const EVP_CIPHER* evp_cipher = reinterpret_cast<const EVP_CIPHER*>(cipherRef); 1677 JNI_TRACE("EVP_CipherInit_ex(%p, %p, %p, %d)", evp_cipher, keyArray, ivArray, encrypting ? 1 : 0); 1678 1679 ScopedByteArrayRO keyBytes(env, keyArray); 1680 if (keyBytes.get() == NULL) { 1681 return 0; 1682 } 1683 1684 // The IV can be null if we're using ECB. 1685 UniquePtr<unsigned char[]> ivPtr; 1686 if (ivArray != NULL) { 1687 ScopedByteArrayRO ivBytes(env, ivArray); 1688 if (ivBytes.get() == NULL) { 1689 return 0; 1690 } 1691 1692 ivPtr.reset(new unsigned char[ivBytes.size()]); 1693 memcpy(ivPtr.get(), ivBytes.get(), ivBytes.size()); 1694 } 1695 1696 Unique_EVP_CIPHER_CTX ctx(EVP_CIPHER_CTX_new()); 1697 if (ctx.get() == NULL) { 1698 jniThrowOutOfMemoryError(env, "Unable to allocate cipher context"); 1699 JNI_TRACE("ctx=%p EVP_CipherInit_ex => context allocation error", evp_cipher); 1700 return 0; 1701 } 1702 1703 const unsigned char* key = reinterpret_cast<const unsigned char*>(keyBytes.get()); 1704 if (!EVP_CipherInit_ex(ctx.get(), evp_cipher, NULL, key, ivPtr.get(), encrypting ? 1 : 0)) { 1705 throwExceptionIfNecessary(env, "EVP_CipherInit_ex"); 1706 JNI_TRACE("EVP_CipherInit_ex => error initializing cipher"); 1707 return 0; 1708 } 1709 1710 JNI_TRACE("EVP_CipherInit_ex(%p, %p, %p, %d) => %p", evp_cipher, keyArray, ivArray, 1711 encrypting ? 1 : 0, ctx.get()); 1712 return static_cast<jint>(reinterpret_cast<uintptr_t>(ctx.release())); 1713 } 1714 1715 /* 1716 * public static native int EVP_CipherUpdate(int ctx, byte[] out, int outOffset, byte[] in, 1717 * int inOffset); 1718 */ 1719 static jint NativeCrypto_EVP_CipherUpdate(JNIEnv* env, jclass, jint ctxRef, jbyteArray outArray, 1720 jint outOffset, jbyteArray inArray, jint inOffset) { 1721 EVP_CIPHER_CTX* ctx = reinterpret_cast<EVP_CIPHER_CTX*>(ctxRef); 1722 JNI_TRACE("EVP_CipherUpdate(%p, %p, %d, %p, %d)", ctx, outArray, outOffset, inArray, inOffset); 1723 1724 if (ctx == NULL) { 1725 jniThrowNullPointerException(env, "ctx == null"); 1726 JNI_TRACE("ctx=%p EVP_CipherUpdate => ctx == null", ctx); 1727 return 0; 1728 } 1729 1730 ScopedByteArrayRO inBytes(env, inArray); 1731 if (inBytes.get() == NULL) { 1732 return 0; 1733 } 1734 const size_t inSize = inBytes.size(); 1735 if (size_t(inOffset + EVP_CIPHER_CTX_block_size(ctx)) > inSize) { 1736 jniThrowException(env, "java/lang/IndexOutOfBoundsException", NULL); 1737 return 0; 1738 } 1739 1740 ScopedByteArrayRW outBytes(env, outArray); 1741 if (outBytes.get() == NULL) { 1742 return 0; 1743 } 1744 const size_t outSize = outBytes.size(); 1745 if (size_t(outOffset + EVP_CIPHER_CTX_block_size(ctx)) > outSize) { 1746 jniThrowException(env, "java/lang/IndexOutOfBoundsException", NULL); 1747 return 0; 1748 } 1749 1750 unsigned char* out = reinterpret_cast<unsigned char*>(outBytes.get()); 1751 const unsigned char* in = reinterpret_cast<const unsigned char*>(inBytes.get()); 1752 1753 int outl; 1754 if (!EVP_CipherUpdate(ctx, out + outOffset, &outl, in+inOffset, inSize - inOffset)) { 1755 throwExceptionIfNecessary(env, "EVP_CipherInit_ex"); 1756 JNI_TRACE("ctx=%p EVP_CipherUpdate => threw error", ctx); 1757 return 0; 1758 } 1759 1760 JNI_TRACE("EVP_CipherUpdate(%p, %p, %d, %p, %d) => %d", ctx, outArray, outOffset, inArray, 1761 inOffset, outl); 1762 return outl; 1763 } 1764 1765 /* 1766 * public static native int EVP_CipherFinal(int ctx, byte[] out, int outOffset); 1767 */ 1768 static jint NativeCrypto_EVP_CipherFinal_ex(JNIEnv* env, jclass, jint ctxRef, jbyteArray outArray, 1769 jint outOffset) { 1770 EVP_CIPHER_CTX* ctx = reinterpret_cast<EVP_CIPHER_CTX*>(ctxRef); 1771 JNI_TRACE("EVP_CipherFinal_ex(%p, %p, %d)", ctx, outArray, outOffset); 1772 1773 if (ctx == NULL) { 1774 jniThrowNullPointerException(env, "ctx == null"); 1775 JNI_TRACE("ctx=%p EVP_CipherFinal_ex => ctx == null", ctx); 1776 return 0; 1777 } 1778 1779 ScopedByteArrayRW outBytes(env, outArray); 1780 if (outBytes.get() == NULL) { 1781 return 0; 1782 } 1783 1784 unsigned char* out = reinterpret_cast<unsigned char*>(outBytes.get()); 1785 1786 int outl; 1787 if (!EVP_CipherFinal_ex(ctx, out + outOffset, &outl)) { 1788 throwExceptionIfNecessary(env, "EVP_CipherInit_ex"); 1789 JNI_TRACE("ctx=%p EVP_CipherUpdate => threw error", ctx); 1790 return 0; 1791 } 1792 1793 JNI_TRACE("EVP_CipherFinal(%p, %p, %d) => %d", ctx, outArray, outOffset, outl); 1794 return outl; 1795 } 1796 1797 /* 1798 * public static native void EVP_CIPHER_CTX_cleanup(int ctx); 1799 */ 1800 static void NativeCrypto_EVP_CIPHER_CTX_cleanup(JNIEnv*, jclass, jint ctxRef) { 1801 EVP_CIPHER_CTX* ctx = reinterpret_cast<EVP_CIPHER_CTX*>(ctxRef); 1802 1803 if (ctx != NULL) { 1804 EVP_CIPHER_CTX_cleanup(ctx); 1805 } 1806 } 1807 1808 /** 1809 * public static native void RAND_seed(byte[]); 1810 */ 1811 static void NativeCrypto_RAND_seed(JNIEnv* env, jclass, jbyteArray seed) { 1812 JNI_TRACE("NativeCrypto_RAND_seed seed=%p", seed); 1813 ScopedByteArrayRO randseed(env, seed); 1814 if (randseed.get() == NULL) { 1815 return; 1816 } 1817 RAND_seed(randseed.get(), randseed.size()); 1818 } 1819 1820 static jint NativeCrypto_RAND_load_file(JNIEnv* env, jclass, jstring filename, jlong max_bytes) { 1821 JNI_TRACE("NativeCrypto_RAND_load_file filename=%p max_bytes=%lld", filename, max_bytes); 1822 ScopedUtfChars file(env, filename); 1823 if (file.c_str() == NULL) { 1824 return -1; 1825 } 1826 int result = RAND_load_file(file.c_str(), max_bytes); 1827 JNI_TRACE("NativeCrypto_RAND_load_file file=%s => %d", file.c_str(), result); 1828 return result; 1829 } 1830 1831 #ifdef WITH_JNI_TRACE 1832 /** 1833 * Based on example logging call back from SSL_CTX_set_info_callback man page 1834 */ 1835 static void info_callback_LOG(const SSL* s __attribute__ ((unused)), int where, int ret) 1836 { 1837 int w = where & ~SSL_ST_MASK; 1838 const char* str; 1839 if (w & SSL_ST_CONNECT) { 1840 str = "SSL_connect"; 1841 } else if (w & SSL_ST_ACCEPT) { 1842 str = "SSL_accept"; 1843 } else { 1844 str = "undefined"; 1845 } 1846 1847 if (where & SSL_CB_LOOP) { 1848 JNI_TRACE("ssl=%p %s:%s %s", s, str, SSL_state_string(s), SSL_state_string_long(s)); 1849 } else if (where & SSL_CB_ALERT) { 1850 str = (where & SSL_CB_READ) ? "read" : "write"; 1851 JNI_TRACE("ssl=%p SSL3 alert %s:%s:%s %s %s", 1852 s, 1853 str, 1854 SSL_alert_type_string(ret), 1855 SSL_alert_desc_string(ret), 1856 SSL_alert_type_string_long(ret), 1857 SSL_alert_desc_string_long(ret)); 1858 } else if (where & SSL_CB_EXIT) { 1859 if (ret == 0) { 1860 JNI_TRACE("ssl=%p %s:failed exit in %s %s", 1861 s, str, SSL_state_string(s), SSL_state_string_long(s)); 1862 } else if (ret < 0) { 1863 JNI_TRACE("ssl=%p %s:error exit in %s %s", 1864 s, str, SSL_state_string(s), SSL_state_string_long(s)); 1865 } else if (ret == 1) { 1866 JNI_TRACE("ssl=%p %s:ok exit in %s %s", 1867 s, str, SSL_state_string(s), SSL_state_string_long(s)); 1868 } else { 1869 JNI_TRACE("ssl=%p %s:unknown exit %d in %s %s", 1870 s, str, ret, SSL_state_string(s), SSL_state_string_long(s)); 1871 } 1872 } else if (where & SSL_CB_HANDSHAKE_START) { 1873 JNI_TRACE("ssl=%p handshake start in %s %s", 1874 s, SSL_state_string(s), SSL_state_string_long(s)); 1875 } else if (where & SSL_CB_HANDSHAKE_DONE) { 1876 JNI_TRACE("ssl=%p handshake done in %s %s", 1877 s, SSL_state_string(s), SSL_state_string_long(s)); 1878 } else { 1879 JNI_TRACE("ssl=%p %s:unknown where %d in %s %s", 1880 s, str, where, SSL_state_string(s), SSL_state_string_long(s)); 1881 } 1882 } 1883 #endif 1884 1885 /** 1886 * Returns an array containing all the X509 certificate's bytes. 1887 */ 1888 static jobjectArray getCertificateBytes(JNIEnv* env, const STACK_OF(X509)* chain) 1889 { 1890 if (chain == NULL) { 1891 // Chain can be NULL if the associated cipher doesn't do certs. 1892 return NULL; 1893 } 1894 1895 int count = sk_X509_num(chain); 1896 if (count <= 0) { 1897 return NULL; 1898 } 1899 1900 jobjectArray joa = env->NewObjectArray(count, JniConstants::byteArrayClass, NULL); 1901 if (joa == NULL) { 1902 return NULL; 1903 } 1904 1905 for (int i = 0; i < count; i++) { 1906 X509* cert = sk_X509_value(chain, i); 1907 1908 int len = i2d_X509(cert, NULL); 1909 if (len < 0) { 1910 return NULL; 1911 } 1912 ScopedLocalRef<jbyteArray> byteArray(env, env->NewByteArray(len)); 1913 if (byteArray.get() == NULL) { 1914 return NULL; 1915 } 1916 ScopedByteArrayRW bytes(env, byteArray.get()); 1917 if (bytes.get() == NULL) { 1918 return NULL; 1919 } 1920 unsigned char* p = reinterpret_cast<unsigned char*>(bytes.get()); 1921 int n = i2d_X509(cert, &p); 1922 if (n < 0) { 1923 return NULL; 1924 } 1925 env->SetObjectArrayElement(joa, i, byteArray.get()); 1926 } 1927 1928 return joa; 1929 } 1930 1931 /** 1932 * Returns an array containing all the X500 principal's bytes. 1933 */ 1934 static jobjectArray getPrincipalBytes(JNIEnv* env, const STACK_OF(X509_NAME)* names) 1935 { 1936 if (names == NULL) { 1937 return NULL; 1938 } 1939 1940 int count = sk_X509_NAME_num(names); 1941 if (count <= 0) { 1942 return NULL; 1943 } 1944 1945 jobjectArray joa = env->NewObjectArray(count, JniConstants::byteArrayClass, NULL); 1946 if (joa == NULL) { 1947 return NULL; 1948 } 1949 1950 for (int i = 0; i < count; i++) { 1951 X509_NAME* principal = sk_X509_NAME_value(names, i); 1952 1953 int len = i2d_X509_NAME(principal, NULL); 1954 if (len < 0) { 1955 return NULL; 1956 } 1957 ScopedLocalRef<jbyteArray> byteArray(env, env->NewByteArray(len)); 1958 if (byteArray.get() == NULL) { 1959 return NULL; 1960 } 1961 ScopedByteArrayRW bytes(env, byteArray.get()); 1962 if (bytes.get() == NULL) { 1963 return NULL; 1964 } 1965 unsigned char* p = reinterpret_cast<unsigned char*>(bytes.get()); 1966 int n = i2d_X509_NAME(principal, &p); 1967 if (n < 0) { 1968 return NULL; 1969 } 1970 env->SetObjectArrayElement(joa, i, byteArray.get()); 1971 } 1972 1973 return joa; 1974 } 1975 1976 /** 1977 * Our additional application data needed for getting synchronization right. 1978 * This maybe warrants a bit of lengthy prose: 1979 * 1980 * (1) We use a flag to reflect whether we consider the SSL connection alive. 1981 * Any read or write attempt loops will be cancelled once this flag becomes 0. 1982 * 1983 * (2) We use an int to count the number of threads that are blocked by the 1984 * underlying socket. This may be at most two (one reader and one writer), since 1985 * the Java layer ensures that no more threads will enter the native code at the 1986 * same time. 1987 * 1988 * (3) The pipe is used primarily as a means of cancelling a blocking select() 1989 * when we want to close the connection (aka "emergency button"). It is also 1990 * necessary for dealing with a possible race condition situation: There might 1991 * be cases where both threads see an SSL_ERROR_WANT_READ or 1992 * SSL_ERROR_WANT_WRITE. Both will enter a select() with the proper argument. 1993 * If one leaves the select() successfully before the other enters it, the 1994 * "success" event is already consumed and the second thread will be blocked, 1995 * possibly forever (depending on network conditions). 1996 * 1997 * The idea for solving the problem looks like this: Whenever a thread is 1998 * successful in moving around data on the network, and it knows there is 1999 * another thread stuck in a select(), it will write a byte to the pipe, waking 2000 * up the other thread. A thread that returned from select(), on the other hand, 2001 * knows whether it's been woken up by the pipe. If so, it will consume the 2002 * byte, and the original state of affairs has been restored. 2003 * 2004 * The pipe may seem like a bit of overhead, but it fits in nicely with the 2005 * other file descriptors of the select(), so there's only one condition to wait 2006 * for. 2007 * 2008 * (4) Finally, a mutex is needed to make sure that at most one thread is in 2009 * either SSL_read() or SSL_write() at any given time. This is an OpenSSL 2010 * requirement. We use the same mutex to guard the field for counting the 2011 * waiting threads. 2012 * 2013 * Note: The current implementation assumes that we don't have to deal with 2014 * problems induced by multiple cores or processors and their respective 2015 * memory caches. One possible problem is that of inconsistent views on the 2016 * "aliveAndKicking" field. This could be worked around by also enclosing all 2017 * accesses to that field inside a lock/unlock sequence of our mutex, but 2018 * currently this seems a bit like overkill. Marking volatile at the very least. 2019 * 2020 * During handshaking, additional fields are used to up-call into 2021 * Java to perform certificate verification and handshake 2022 * completion. These are also used in any renegotiation. 2023 * 2024 * (5) the JNIEnv so we can invoke the Java callback 2025 * 2026 * (6) a NativeCrypto.SSLHandshakeCallbacks instance for callbacks from native to Java 2027 * 2028 * (7) a java.io.FileDescriptor wrapper to check for socket close 2029 * 2030 * We store the NPN protocols list so we can either send it (from the server) or 2031 * select a protocol (on the client). We eagerly acquire a pointer to the array 2032 * data so the callback doesn't need to acquire resources that it cannot 2033 * release. 2034 * 2035 * Because renegotiation can be requested by the peer at any time, 2036 * care should be taken to maintain an appropriate JNIEnv on any 2037 * downcall to openssl since it could result in an upcall to Java. The 2038 * current code does try to cover these cases by conditionally setting 2039 * the JNIEnv on calls that can read and write to the SSL such as 2040 * SSL_do_handshake, SSL_read, SSL_write, and SSL_shutdown. 2041 * 2042 * Finally, we have two emphemeral keys setup by OpenSSL callbacks: 2043 * 2044 * (8) a set of ephemeral RSA keys that is lazily generated if a peer 2045 * wants to use an exportable RSA cipher suite. 2046 * 2047 * (9) a set of ephemeral EC keys that is lazily generated if a peer 2048 * wants to use an TLS_ECDHE_* cipher suite. 2049 * 2050 */ 2051 class AppData { 2052 public: 2053 volatile int aliveAndKicking; 2054 int waitingThreads; 2055 int fdsEmergency[2]; 2056 MUTEX_TYPE mutex; 2057 JNIEnv* env; 2058 jobject sslHandshakeCallbacks; 2059 jobject fileDescriptor; 2060 jbyteArray npnProtocolsArray; 2061 jbyte* npnProtocolsData; 2062 size_t npnProtocolsLength; 2063 Unique_RSA ephemeralRsa; 2064 Unique_EC_KEY ephemeralEc; 2065 2066 /** 2067 * Creates the application data context for the SSL*. 2068 */ 2069 public: 2070 static AppData* create() { 2071 UniquePtr<AppData> appData(new AppData()); 2072 if (pipe(appData.get()->fdsEmergency) == -1) { 2073 return NULL; 2074 } 2075 if (!setBlocking(appData.get()->fdsEmergency[0], false)) { 2076 return NULL; 2077 } 2078 if (MUTEX_SETUP(appData.get()->mutex) == -1) { 2079 return NULL; 2080 } 2081 return appData.release(); 2082 } 2083 2084 ~AppData() { 2085 aliveAndKicking = 0; 2086 if (fdsEmergency[0] != -1) { 2087 close(fdsEmergency[0]); 2088 } 2089 if (fdsEmergency[1] != -1) { 2090 close(fdsEmergency[1]); 2091 } 2092 MUTEX_CLEANUP(mutex); 2093 } 2094 2095 private: 2096 AppData() : 2097 aliveAndKicking(1), 2098 waitingThreads(0), 2099 env(NULL), 2100 sslHandshakeCallbacks(NULL), 2101 npnProtocolsArray(NULL), 2102 npnProtocolsData(NULL), 2103 npnProtocolsLength(-1), 2104 ephemeralRsa(NULL), 2105 ephemeralEc(NULL) { 2106 fdsEmergency[0] = -1; 2107 fdsEmergency[1] = -1; 2108 } 2109 2110 public: 2111 /** 2112 * Used to set the SSL-to-Java callback state before each SSL_* 2113 * call that may result in a callback. It should be cleared after 2114 * the operation returns with clearCallbackState. 2115 * 2116 * @param env The JNIEnv 2117 * @param shc The SSLHandshakeCallbacks 2118 * @param fd The FileDescriptor 2119 * @param npnProtocols NPN protocols so that they may be advertised (by the 2120 * server) or selected (by the client). Has no effect 2121 * unless NPN is enabled. 2122 */ 2123 bool setCallbackState(JNIEnv* e, jobject shc, jobject fd, jbyteArray npnProtocols) { 2124 NetFd netFd(e, fd); 2125 if (netFd.isClosed()) { 2126 return false; 2127 } 2128 env = e; 2129 sslHandshakeCallbacks = shc; 2130 fileDescriptor = fd; 2131 if (npnProtocols != NULL) { 2132 npnProtocolsArray = npnProtocols; 2133 npnProtocolsLength = e->GetArrayLength(npnProtocols); 2134 npnProtocolsData = e->GetByteArrayElements(npnProtocols, NULL); 2135 if (npnProtocolsData == NULL) { 2136 return false; 2137 } 2138 } 2139 return true; 2140 } 2141 2142 void clearCallbackState() { 2143 sslHandshakeCallbacks = NULL; 2144 fileDescriptor = NULL; 2145 if (npnProtocolsArray != NULL) { 2146 env->ReleaseByteArrayElements(npnProtocolsArray, npnProtocolsData, JNI_ABORT); 2147 npnProtocolsArray = NULL; 2148 npnProtocolsData = NULL; 2149 npnProtocolsLength = -1; 2150 } 2151 env = NULL; 2152 } 2153 2154 }; 2155 2156 /** 2157 * Dark magic helper function that checks, for a given SSL session, whether it 2158 * can SSL_read() or SSL_write() without blocking. Takes into account any 2159 * concurrent attempts to close the SSLSocket from the Java side. This is 2160 * needed to get rid of the hangs that occur when thread #1 closes the SSLSocket 2161 * while thread #2 is sitting in a blocking read or write. The type argument 2162 * specifies whether we are waiting for readability or writability. It expects 2163 * to be passed either SSL_ERROR_WANT_READ or SSL_ERROR_WANT_WRITE, since we 2164 * only need to wait in case one of these problems occurs. 2165 * 2166 * @param env 2167 * @param type Either SSL_ERROR_WANT_READ or SSL_ERROR_WANT_WRITE 2168 * @param fdObject The FileDescriptor, since appData->fileDescriptor should be NULL 2169 * @param appData The application data structure with mutex info etc. 2170 * @param timeout_millis The timeout value for select call, with the special value 2171 * 0 meaning no timeout at all (wait indefinitely). Note: This is 2172 * the Java semantics of the timeout value, not the usual 2173 * select() semantics. 2174 * @return The result of the inner select() call, 2175 * THROW_SOCKETEXCEPTION if a SocketException was thrown, -1 on 2176 * additional errors 2177 */ 2178 static int sslSelect(JNIEnv* env, int type, jobject fdObject, AppData* appData, int timeout_millis) { 2179 // This loop is an expanded version of the NET_FAILURE_RETRY 2180 // macro. It cannot simply be used in this case because select 2181 // cannot be restarted without recreating the fd_sets and timeout 2182 // structure. 2183 int result; 2184 fd_set rfds; 2185 fd_set wfds; 2186 do { 2187 NetFd fd(env, fdObject); 2188 if (fd.isClosed()) { 2189 result = THROWN_EXCEPTION; 2190 break; 2191 } 2192 int intFd = fd.get(); 2193 JNI_TRACE("sslSelect type=%s fd=%d appData=%p timeout_millis=%d", 2194 (type == SSL_ERROR_WANT_READ) ? "READ" : "WRITE", intFd, appData, timeout_millis); 2195 2196 FD_ZERO(&rfds); 2197 FD_ZERO(&wfds); 2198 2199 if (type == SSL_ERROR_WANT_READ) { 2200 FD_SET(intFd, &rfds); 2201 } else { 2202 FD_SET(intFd, &wfds); 2203 } 2204 2205 FD_SET(appData->fdsEmergency[0], &rfds); 2206 2207 int maxFd = (intFd > appData->fdsEmergency[0]) ? intFd : appData->fdsEmergency[0]; 2208 2209 // Build a struct for the timeout data if we actually want a timeout. 2210 timeval tv; 2211 timeval* ptv; 2212 if (timeout_millis > 0) { 2213 tv.tv_sec = timeout_millis / 1000; 2214 tv.tv_usec = (timeout_millis % 1000) * 1000; 2215 ptv = &tv; 2216 } else { 2217 ptv = NULL; 2218 } 2219 2220 AsynchronousSocketCloseMonitor monitor(intFd); 2221 result = select(maxFd + 1, &rfds, &wfds, NULL, ptv); 2222 JNI_TRACE("sslSelect %s fd=%d appData=%p timeout_millis=%d => %d", 2223 (type == SSL_ERROR_WANT_READ) ? "READ" : "WRITE", 2224 fd.get(), appData, timeout_millis, result); 2225 if (result == -1) { 2226 if (fd.isClosed()) { 2227 result = THROWN_EXCEPTION; 2228 break; 2229 } 2230 if (errno != EINTR) { 2231 break; 2232 } 2233 } 2234 } while (result == -1); 2235 2236 if (MUTEX_LOCK(appData->mutex) == -1) { 2237 return -1; 2238 } 2239 2240 if (result > 0) { 2241 // We have been woken up by a token in the emergency pipe. We 2242 // can't be sure the token is still in the pipe at this point 2243 // because it could have already been read by the thread that 2244 // originally wrote it if it entered sslSelect and acquired 2245 // the mutex before we did. Thus we cannot safely read from 2246 // the pipe in a blocking way (so we make the pipe 2247 // non-blocking at creation). 2248 if (FD_ISSET(appData->fdsEmergency[0], &rfds)) { 2249 char token; 2250 do { 2251 read(appData->fdsEmergency[0], &token, 1); 2252 } while (errno == EINTR); 2253 } 2254 } 2255 2256 // Tell the world that there is now one thread less waiting for the 2257 // underlying network. 2258 appData->waitingThreads--; 2259 2260 MUTEX_UNLOCK(appData->mutex); 2261 2262 return result; 2263 } 2264 2265 /** 2266 * Helper function that wakes up a thread blocked in select(), in case there is 2267 * one. Is being called by sslRead() and sslWrite() as well as by JNI glue 2268 * before closing the connection. 2269 * 2270 * @param data The application data structure with mutex info etc. 2271 */ 2272 static void sslNotify(AppData* appData) { 2273 // Write a byte to the emergency pipe, so a concurrent select() can return. 2274 // Note we have to restore the errno of the original system call, since the 2275 // caller relies on it for generating error messages. 2276 int errnoBackup = errno; 2277 char token = '*'; 2278 do { 2279 errno = 0; 2280 write(appData->fdsEmergency[1], &token, 1); 2281 } while (errno == EINTR); 2282 errno = errnoBackup; 2283 } 2284 2285 static AppData* toAppData(const SSL* ssl) { 2286 return reinterpret_cast<AppData*>(SSL_get_app_data(ssl)); 2287 } 2288 2289 /** 2290 * Verify the X509 certificate via SSL_CTX_set_cert_verify_callback 2291 */ 2292 static int cert_verify_callback(X509_STORE_CTX* x509_store_ctx, void* arg __attribute__ ((unused))) 2293 { 2294 /* Get the correct index to the SSLobject stored into X509_STORE_CTX. */ 2295 SSL* ssl = reinterpret_cast<SSL*>(X509_STORE_CTX_get_ex_data(x509_store_ctx, 2296 SSL_get_ex_data_X509_STORE_CTX_idx())); 2297 JNI_TRACE("ssl=%p cert_verify_callback x509_store_ctx=%p arg=%p", ssl, x509_store_ctx, arg); 2298 2299 AppData* appData = toAppData(ssl); 2300 JNIEnv* env = appData->env; 2301 if (env == NULL) { 2302 ALOGE("AppData->env missing in cert_verify_callback"); 2303 JNI_TRACE("ssl=%p cert_verify_callback => 0", ssl); 2304 return 0; 2305 } 2306 jobject sslHandshakeCallbacks = appData->sslHandshakeCallbacks; 2307 2308 jclass cls = env->GetObjectClass(sslHandshakeCallbacks); 2309 jmethodID methodID 2310 = env->GetMethodID(cls, "verifyCertificateChain", "([[BLjava/lang/String;)V"); 2311 2312 jobjectArray objectArray = getCertificateBytes(env, x509_store_ctx->untrusted); 2313 2314 const char* authMethod = SSL_authentication_method(ssl); 2315 JNI_TRACE("ssl=%p cert_verify_callback calling verifyCertificateChain authMethod=%s", 2316 ssl, authMethod); 2317 jstring authMethodString = env->NewStringUTF(authMethod); 2318 env->CallVoidMethod(sslHandshakeCallbacks, methodID, objectArray, authMethodString); 2319 2320 int result = (env->ExceptionCheck()) ? 0 : 1; 2321 JNI_TRACE("ssl=%p cert_verify_callback => %d", ssl, result); 2322 return result; 2323 } 2324 2325 /** 2326 * Call back to watch for handshake to be completed. This is necessary 2327 * for SSL_MODE_HANDSHAKE_CUTTHROUGH support, since SSL_do_handshake 2328 * returns before the handshake is completed in this case. 2329 */ 2330 static void info_callback(const SSL* ssl, int where, int ret __attribute__ ((unused))) { 2331 JNI_TRACE("ssl=%p info_callback where=0x%x ret=%d", ssl, where, ret); 2332 #ifdef WITH_JNI_TRACE 2333 info_callback_LOG(ssl, where, ret); 2334 #endif 2335 if (!(where & SSL_CB_HANDSHAKE_DONE)) { 2336 JNI_TRACE("ssl=%p info_callback ignored", ssl); 2337 return; 2338 } 2339 2340 AppData* appData = toAppData(ssl); 2341 JNIEnv* env = appData->env; 2342 if (env == NULL) { 2343 ALOGE("AppData->env missing in info_callback"); 2344 JNI_TRACE("ssl=%p info_callback env error", ssl); 2345 return; 2346 } 2347 if (env->ExceptionCheck()) { 2348 JNI_TRACE("ssl=%p info_callback already pending exception", ssl); 2349 return; 2350 } 2351 2352 jobject sslHandshakeCallbacks = appData->sslHandshakeCallbacks; 2353 2354 jclass cls = env->GetObjectClass(sslHandshakeCallbacks); 2355 jmethodID methodID = env->GetMethodID(cls, "handshakeCompleted", "()V"); 2356 2357 JNI_TRACE("ssl=%p info_callback calling handshakeCompleted", ssl); 2358 env->CallVoidMethod(sslHandshakeCallbacks, methodID); 2359 2360 if (env->ExceptionCheck()) { 2361 JNI_TRACE("ssl=%p info_callback exception", ssl); 2362 } 2363 JNI_TRACE("ssl=%p info_callback completed", ssl); 2364 } 2365 2366 /** 2367 * Call back to ask for a client certificate 2368 */ 2369 static int client_cert_cb(SSL* ssl, X509** x509Out, EVP_PKEY** pkeyOut) { 2370 JNI_TRACE("ssl=%p client_cert_cb x509Out=%p pkeyOut=%p", ssl, x509Out, pkeyOut); 2371 2372 AppData* appData = toAppData(ssl); 2373 JNIEnv* env = appData->env; 2374 if (env == NULL) { 2375 ALOGE("AppData->env missing in client_cert_cb"); 2376 JNI_TRACE("ssl=%p client_cert_cb env error => 0", ssl); 2377 return 0; 2378 } 2379 if (env->ExceptionCheck()) { 2380 JNI_TRACE("ssl=%p client_cert_cb already pending exception => 0", ssl); 2381 return 0; 2382 } 2383 jobject sslHandshakeCallbacks = appData->sslHandshakeCallbacks; 2384 2385 jclass cls = env->GetObjectClass(sslHandshakeCallbacks); 2386 jmethodID methodID 2387 = env->GetMethodID(cls, "clientCertificateRequested", "([B[[B)V"); 2388 2389 // Call Java callback which can use SSL_use_certificate and SSL_use_PrivateKey to set values 2390 char ssl2_ctype = SSL3_CT_RSA_SIGN; 2391 const char* ctype = NULL; 2392 int ctype_num = 0; 2393 jobjectArray issuers = NULL; 2394 switch (ssl->version) { 2395 case SSL2_VERSION: 2396 ctype = &ssl2_ctype; 2397 ctype_num = 1; 2398 break; 2399 case SSL3_VERSION: 2400 case TLS1_VERSION: 2401 case TLS1_1_VERSION: 2402 case TLS1_2_VERSION: 2403 case DTLS1_VERSION: 2404 ctype = ssl->s3->tmp.ctype; 2405 ctype_num = ssl->s3->tmp.ctype_num; 2406 issuers = getPrincipalBytes(env, ssl->s3->tmp.ca_names); 2407 break; 2408 } 2409 #ifdef WITH_JNI_TRACE 2410 for (int i = 0; i < ctype_num; i++) { 2411 JNI_TRACE("ssl=%p clientCertificateRequested keyTypes[%d]=%d", ssl, i, ctype[i]); 2412 } 2413 #endif 2414 2415 jbyteArray keyTypes = env->NewByteArray(ctype_num); 2416 if (keyTypes == NULL) { 2417 JNI_TRACE("ssl=%p client_cert_cb bytes == null => 0", ssl); 2418 return 0; 2419 } 2420 env->SetByteArrayRegion(keyTypes, 0, ctype_num, reinterpret_cast<const jbyte*>(ctype)); 2421 2422 JNI_TRACE("ssl=%p clientCertificateRequested calling clientCertificateRequested " 2423 "keyTypes=%p issuers=%p", ssl, keyTypes, issuers); 2424 env->CallVoidMethod(sslHandshakeCallbacks, methodID, keyTypes, issuers); 2425 2426 if (env->ExceptionCheck()) { 2427 JNI_TRACE("ssl=%p client_cert_cb exception => 0", ssl); 2428 return 0; 2429 } 2430 2431 // Check for values set from Java 2432 X509* certificate = SSL_get_certificate(ssl); 2433 EVP_PKEY* privatekey = SSL_get_privatekey(ssl); 2434 int result; 2435 if (certificate != NULL && privatekey != NULL) { 2436 *x509Out = certificate; 2437 *pkeyOut = privatekey; 2438 result = 1; 2439 } else { 2440 *x509Out = NULL; 2441 *pkeyOut = NULL; 2442 result = 0; 2443 } 2444 JNI_TRACE("ssl=%p client_cert_cb => *x509=%p *pkey=%p %d", ssl, *x509Out, *pkeyOut, result); 2445 return result; 2446 } 2447 2448 static RSA* rsaGenerateKey(int keylength) { 2449 Unique_BIGNUM bn(BN_new()); 2450 if (bn.get() == NULL) { 2451 return NULL; 2452 } 2453 int setWordResult = BN_set_word(bn.get(), RSA_F4); 2454 if (setWordResult != 1) { 2455 return NULL; 2456 } 2457 Unique_RSA rsa(RSA_new()); 2458 if (rsa.get() == NULL) { 2459 return NULL; 2460 } 2461 int generateResult = RSA_generate_key_ex(rsa.get(), keylength, bn.get(), NULL); 2462 if (generateResult != 1) { 2463 return NULL; 2464 } 2465 return rsa.release(); 2466 } 2467 2468 /** 2469 * Call back to ask for an ephemeral RSA key for SSL_RSA_EXPORT_WITH_RC4_40_MD5 (aka EXP-RC4-MD5) 2470 */ 2471 static RSA* tmp_rsa_callback(SSL* ssl __attribute__ ((unused)), 2472 int is_export __attribute__ ((unused)), 2473 int keylength) { 2474 JNI_TRACE("ssl=%p tmp_rsa_callback is_export=%d keylength=%d", ssl, is_export, keylength); 2475 2476 AppData* appData = toAppData(ssl); 2477 if (appData->ephemeralRsa.get() == NULL) { 2478 JNI_TRACE("ssl=%p tmp_rsa_callback generating ephemeral RSA key", ssl); 2479 appData->ephemeralRsa.reset(rsaGenerateKey(keylength)); 2480 } 2481 JNI_TRACE("ssl=%p tmp_rsa_callback => %p", ssl, appData->ephemeralRsa.get()); 2482 return appData->ephemeralRsa.get(); 2483 } 2484 2485 static DH* dhGenerateParameters(int keylength) { 2486 2487 /* 2488 * The SSL_CTX_set_tmp_dh_callback(3SSL) man page discusses two 2489 * different options for generating DH keys. One is generating the 2490 * keys using a single set of DH parameters. However, generating 2491 * DH parameters is slow enough (minutes) that they suggest doing 2492 * it once at install time. The other is to generate DH keys from 2493 * DSA parameters. Generating DSA parameters is faster than DH 2494 * parameters, but to prevent small subgroup attacks, they needed 2495 * to be regenerated for each set of DH keys. Setting the 2496 * SSL_OP_SINGLE_DH_USE option make sure OpenSSL will call back 2497 * for new DH parameters every type it needs to generate DH keys. 2498 */ 2499 #if 0 2500 // Slow path that takes minutes but could be cached 2501 Unique_DH dh(DH_new()); 2502 if (!DH_generate_parameters_ex(dh.get(), keylength, 2, NULL)) { 2503 return NULL; 2504 } 2505 return dh.release(); 2506 #else 2507 // Faster path but must have SSL_OP_SINGLE_DH_USE set 2508 Unique_DSA dsa(DSA_new()); 2509 if (!DSA_generate_parameters_ex(dsa.get(), keylength, NULL, 0, NULL, NULL, NULL)) { 2510 return NULL; 2511 } 2512 DH* dh = DSA_dup_DH(dsa.get()); 2513 return dh; 2514 #endif 2515 } 2516 2517 /** 2518 * Call back to ask for Diffie-Hellman parameters 2519 */ 2520 static DH* tmp_dh_callback(SSL* ssl __attribute__ ((unused)), 2521 int is_export __attribute__ ((unused)), 2522 int keylength) { 2523 JNI_TRACE("ssl=%p tmp_dh_callback is_export=%d keylength=%d", ssl, is_export, keylength); 2524 DH* tmp_dh = dhGenerateParameters(keylength); 2525 JNI_TRACE("ssl=%p tmp_dh_callback => %p", ssl, tmp_dh); 2526 return tmp_dh; 2527 } 2528 2529 static EC_KEY* ecGenerateKey(int keylength __attribute__ ((unused))) { 2530 // TODO selected curve based on keylength 2531 Unique_EC_KEY ec(EC_KEY_new_by_curve_name(NID_X9_62_prime256v1)); 2532 if (ec.get() == NULL) { 2533 return NULL; 2534 } 2535 return ec.release(); 2536 } 2537 2538 /** 2539 * Call back to ask for an ephemeral EC key for TLS_ECDHE_* cipher suites 2540 */ 2541 static EC_KEY* tmp_ecdh_callback(SSL* ssl __attribute__ ((unused)), 2542 int is_export __attribute__ ((unused)), 2543 int keylength) { 2544 JNI_TRACE("ssl=%p tmp_ecdh_callback is_export=%d keylength=%d", ssl, is_export, keylength); 2545 AppData* appData = toAppData(ssl); 2546 if (appData->ephemeralEc.get() == NULL) { 2547 JNI_TRACE("ssl=%p tmp_ecdh_callback generating ephemeral EC key", ssl); 2548 appData->ephemeralEc.reset(ecGenerateKey(keylength)); 2549 } 2550 JNI_TRACE("ssl=%p tmp_ecdh_callback => %p", ssl, appData->ephemeralEc.get()); 2551 return appData->ephemeralEc.get(); 2552 } 2553 2554 /* 2555 * public static native int SSL_CTX_new(); 2556 */ 2557 static int NativeCrypto_SSL_CTX_new(JNIEnv* env, jclass) { 2558 Unique_SSL_CTX sslCtx(SSL_CTX_new(SSLv23_method())); 2559 if (sslCtx.get() == NULL) { 2560 jniThrowRuntimeException(env, "SSL_CTX_new"); 2561 return 0; 2562 } 2563 SSL_CTX_set_options(sslCtx.get(), 2564 SSL_OP_ALL 2565 // Note: We explicitly do not allow SSLv2 to be used. 2566 | SSL_OP_NO_SSLv2 2567 // We also disable session tickets for better compatibility b/2682876 2568 | SSL_OP_NO_TICKET 2569 // We also disable compression for better compatibility b/2710492 b/2710497 2570 | SSL_OP_NO_COMPRESSION 2571 // Because dhGenerateParameters uses DSA_generate_parameters_ex 2572 | SSL_OP_SINGLE_DH_USE 2573 // Because ecGenerateParameters uses a fixed named curve 2574 | SSL_OP_SINGLE_ECDH_USE); 2575 2576 int mode = SSL_CTX_get_mode(sslCtx.get()); 2577 /* 2578 * Turn on "partial write" mode. This means that SSL_write() will 2579 * behave like Posix write() and possibly return after only 2580 * writing a partial buffer. Note: The alternative, perhaps 2581 * surprisingly, is not that SSL_write() always does full writes 2582 * but that it will force you to retry write calls having 2583 * preserved the full state of the original call. (This is icky 2584 * and undesirable.) 2585 */ 2586 mode |= SSL_MODE_ENABLE_PARTIAL_WRITE; 2587 #if defined(SSL_MODE_SMALL_BUFFERS) /* not all SSL versions have this */ 2588 mode |= SSL_MODE_SMALL_BUFFERS; /* lazily allocate record buffers; usually saves 2589 * 44k over the default */ 2590 #endif 2591 SSL_CTX_set_mode(sslCtx.get(), mode); 2592 2593 SSL_CTX_set_cert_verify_callback(sslCtx.get(), cert_verify_callback, NULL); 2594 SSL_CTX_set_info_callback(sslCtx.get(), info_callback); 2595 SSL_CTX_set_client_cert_cb(sslCtx.get(), client_cert_cb); 2596 SSL_CTX_set_tmp_rsa_callback(sslCtx.get(), tmp_rsa_callback); 2597 SSL_CTX_set_tmp_dh_callback(sslCtx.get(), tmp_dh_callback); 2598 SSL_CTX_set_tmp_ecdh_callback(sslCtx.get(), tmp_ecdh_callback); 2599 2600 JNI_TRACE("NativeCrypto_SSL_CTX_new => %p", sslCtx.get()); 2601 return (jint) sslCtx.release(); 2602 } 2603 2604 /** 2605 * public static native void SSL_CTX_free(int ssl_ctx) 2606 */ 2607 static void NativeCrypto_SSL_CTX_free(JNIEnv* env, 2608 jclass, jint ssl_ctx_address) 2609 { 2610 SSL_CTX* ssl_ctx = to_SSL_CTX(env, ssl_ctx_address, true); 2611 JNI_TRACE("ssl_ctx=%p NativeCrypto_SSL_CTX_free", ssl_ctx); 2612 if (ssl_ctx == NULL) { 2613 return; 2614 } 2615 SSL_CTX_free(ssl_ctx); 2616 } 2617 2618 static void NativeCrypto_SSL_CTX_set_session_id_context(JNIEnv* env, jclass, 2619 jint ssl_ctx_address, jbyteArray sid_ctx) 2620 { 2621 SSL_CTX* ssl_ctx = to_SSL_CTX(env, ssl_ctx_address, true); 2622 JNI_TRACE("ssl_ctx=%p NativeCrypto_SSL_CTX_set_session_id_context sid_ctx=%p", ssl_ctx, sid_ctx); 2623 if (ssl_ctx == NULL) { 2624 return; 2625 } 2626 2627 ScopedByteArrayRO buf(env, sid_ctx); 2628 if (buf.get() == NULL) { 2629 JNI_TRACE("ssl_ctx=%p NativeCrypto_SSL_CTX_set_session_id_context => threw exception", ssl_ctx); 2630 return; 2631 } 2632 2633 unsigned int length = buf.size(); 2634 if (length > SSL_MAX_SSL_SESSION_ID_LENGTH) { 2635 jniThrowException(env, "java/lang/IllegalArgumentException", 2636 "length > SSL_MAX_SSL_SESSION_ID_LENGTH"); 2637 JNI_TRACE("NativeCrypto_SSL_CTX_set_session_id_context => length = %d", length); 2638 return; 2639 } 2640 const unsigned char* bytes = reinterpret_cast<const unsigned char*>(buf.get()); 2641 int result = SSL_CTX_set_session_id_context(ssl_ctx, bytes, length); 2642 if (result == 0) { 2643 throwExceptionIfNecessary(env, "NativeCrypto_SSL_CTX_set_session_id_context"); 2644 return; 2645 } 2646 JNI_TRACE("ssl_ctx=%p NativeCrypto_SSL_CTX_set_session_id_context => ok", ssl_ctx); 2647 } 2648 2649 /** 2650 * public static native int SSL_new(int ssl_ctx) throws SSLException; 2651 */ 2652 static jint NativeCrypto_SSL_new(JNIEnv* env, jclass, jint ssl_ctx_address) 2653 { 2654 SSL_CTX* ssl_ctx = to_SSL_CTX(env, ssl_ctx_address, true); 2655 JNI_TRACE("ssl_ctx=%p NativeCrypto_SSL_new", ssl_ctx); 2656 if (ssl_ctx == NULL) { 2657 return 0; 2658 } 2659 Unique_SSL ssl(SSL_new(ssl_ctx)); 2660 if (ssl.get() == NULL) { 2661 throwSSLExceptionWithSslErrors(env, NULL, SSL_ERROR_NONE, 2662 "Unable to create SSL structure"); 2663 JNI_TRACE("ssl_ctx=%p NativeCrypto_SSL_new => NULL", ssl_ctx); 2664 return 0; 2665 } 2666 2667 /* Java code in class OpenSSLSocketImpl does the verification. Meaning of 2668 * SSL_VERIFY_NONE flag in client mode: if not using an anonymous cipher 2669 * (by default disabled), the server will send a certificate which will 2670 * be checked. The result of the certificate verification process can be 2671 * checked after the TLS/SSL handshake using the SSL_get_verify_result(3) 2672 * function. The handshake will be continued regardless of the 2673 * verification result. 2674 */ 2675 SSL_set_verify(ssl.get(), SSL_VERIFY_NONE, NULL); 2676 2677 JNI_TRACE("ssl_ctx=%p NativeCrypto_SSL_new => ssl=%p", ssl_ctx, ssl.get()); 2678 return (jint) ssl.release(); 2679 } 2680 2681 static void NativeCrypto_SSL_use_OpenSSL_PrivateKey(JNIEnv* env, jclass, jint ssl_address, jint pkeyRef) { 2682 SSL* ssl = to_SSL(env, ssl_address, true); 2683 EVP_PKEY* pkey = reinterpret_cast<EVP_PKEY*>(pkeyRef); 2684 JNI_TRACE("ssl=%p SSL_use_OpenSSL_PrivateKey privatekey=%p", ssl, pkey); 2685 if (ssl == NULL) { 2686 return; 2687 } 2688 2689 if (pkey == NULL) { 2690 return; 2691 } 2692 2693 int ret = SSL_use_PrivateKey(ssl, pkey); 2694 if (ret != 1) { 2695 ALOGE("%s", ERR_error_string(ERR_peek_error(), NULL)); 2696 throwSSLExceptionWithSslErrors(env, ssl, SSL_ERROR_NONE, "Error setting private key"); 2697 SSL_clear(ssl); 2698 JNI_TRACE("ssl=%p SSL_use_OpenSSL_PrivateKey => error", ssl); 2699 return; 2700 } 2701 // SSL_use_PrivateKey expects to take ownership of the EVP_PKEY, 2702 // but we have an external reference from the caller such as an 2703 // OpenSSLKey, so we manually increment the reference count here. 2704 CRYPTO_add(&pkey->references,+1,CRYPTO_LOCK_EVP_PKEY); 2705 2706 JNI_TRACE("ssl=%p SSL_use_OpenSSL_PrivateKey => ok", ssl); 2707 } 2708 2709 static void NativeCrypto_SSL_use_PrivateKey(JNIEnv* env, jclass, 2710 jint ssl_address, jbyteArray privatekey) 2711 { 2712 SSL* ssl = to_SSL(env, ssl_address, true); 2713 JNI_TRACE("ssl=%p NativeCrypto_SSL_use_PrivateKey privatekey=%p", ssl, privatekey); 2714 if (ssl == NULL) { 2715 return; 2716 } 2717 2718 ScopedByteArrayRO buf(env, privatekey); 2719 if (buf.get() == NULL) { 2720 JNI_TRACE("ssl=%p NativeCrypto_SSL_use_PrivateKey => threw exception", ssl); 2721 return; 2722 } 2723 const unsigned char* tmp = reinterpret_cast<const unsigned char*>(buf.get()); 2724 Unique_PKCS8_PRIV_KEY_INFO pkcs8(d2i_PKCS8_PRIV_KEY_INFO(NULL, &tmp, buf.size())); 2725 if (pkcs8.get() == NULL) { 2726 ALOGE("%s", ERR_error_string(ERR_peek_error(), NULL)); 2727 throwSSLExceptionWithSslErrors(env, ssl, SSL_ERROR_NONE, 2728 "Error parsing private key from DER to PKCS8"); 2729 SSL_clear(ssl); 2730 JNI_TRACE("ssl=%p NativeCrypto_SSL_use_PrivateKey => error from DER to PKCS8", ssl); 2731 return; 2732 } 2733 2734 Unique_EVP_PKEY privatekeyevp(EVP_PKCS82PKEY(pkcs8.get())); 2735 if (privatekeyevp.get() == NULL) { 2736 ALOGE("%s", ERR_error_string(ERR_peek_error(), NULL)); 2737 throwSSLExceptionWithSslErrors(env, ssl, SSL_ERROR_NONE, 2738 "Error creating private key from PKCS8"); 2739 SSL_clear(ssl); 2740 JNI_TRACE("ssl=%p NativeCrypto_SSL_use_PrivateKey => error from PKCS8 to key", ssl); 2741 return; 2742 } 2743 2744 JNI_TRACE("ssl=%p NativeCrypto_SSL_use_PrivateKey EVP_PKEY_type=%d", 2745 ssl, EVP_PKEY_type(privatekeyevp.get()->type)); 2746 int ret = SSL_use_PrivateKey(ssl, privatekeyevp.get()); 2747 if (ret == 1) { 2748 OWNERSHIP_TRANSFERRED(privatekeyevp); 2749 } else { 2750 ALOGE("%s", ERR_error_string(ERR_peek_error(), NULL)); 2751 throwSSLExceptionWithSslErrors(env, ssl, SSL_ERROR_NONE, "Error setting private key"); 2752 SSL_clear(ssl); 2753 JNI_TRACE("ssl=%p NativeCrypto_SSL_use_PrivateKey => error", ssl); 2754 return; 2755 } 2756 2757 JNI_TRACE("ssl=%p NativeCrypto_SSL_use_PrivateKey => ok", ssl); 2758 } 2759 2760 static void NativeCrypto_SSL_use_certificate(JNIEnv* env, jclass, 2761 jint ssl_address, jobjectArray certificates) 2762 { 2763 SSL* ssl = to_SSL(env, ssl_address, true); 2764 JNI_TRACE("ssl=%p NativeCrypto_SSL_use_certificate certificates=%p", ssl, certificates); 2765 if (ssl == NULL) { 2766 return; 2767 } 2768 2769 if (certificates == NULL) { 2770 jniThrowNullPointerException(env, "certificates == null"); 2771 JNI_TRACE("ssl=%p NativeCrypto_SSL_use_certificate => certificates == null", ssl); 2772 return; 2773 } 2774 2775 int length = env->GetArrayLength(certificates); 2776 if (length == 0) { 2777 jniThrowException(env, "java/lang/IllegalArgumentException", "certificates.length == 0"); 2778 JNI_TRACE("ssl=%p NativeCrypto_SSL_use_certificate => certificates.length == 0", ssl); 2779 return; 2780 } 2781 2782 Unique_X509 certificatesX509[length]; 2783 for (int i = 0; i < length; i++) { 2784 ScopedLocalRef<jbyteArray> certificate(env, 2785 reinterpret_cast<jbyteArray>(env->GetObjectArrayElement(certificates, i))); 2786 if (certificate.get() == NULL) { 2787 jniThrowNullPointerException(env, "certificates element == null"); 2788 JNI_TRACE("ssl=%p NativeCrypto_SSL_use_certificate => certificates element null", ssl); 2789 return; 2790 } 2791 2792 ScopedByteArrayRO buf(env, certificate.get()); 2793 if (buf.get() == NULL) { 2794 JNI_TRACE("ssl=%p NativeCrypto_SSL_use_certificate => threw exception", ssl); 2795 return; 2796 } 2797 const unsigned char* tmp = reinterpret_cast<const unsigned char*>(buf.get()); 2798 certificatesX509[i].reset(d2i_X509(NULL, &tmp, buf.size())); 2799 2800 if (certificatesX509[i].get() == NULL) { 2801 ALOGE("%s", ERR_error_string(ERR_peek_error(), NULL)); 2802 throwSSLExceptionWithSslErrors(env, ssl, SSL_ERROR_NONE, "Error parsing certificate"); 2803 SSL_clear(ssl); 2804 JNI_TRACE("ssl=%p NativeCrypto_SSL_use_certificate => certificates parsing error", ssl); 2805 return; 2806 } 2807 } 2808 2809 int ret = SSL_use_certificate(ssl, certificatesX509[0].get()); 2810 if (ret == 1) { 2811 OWNERSHIP_TRANSFERRED(certificatesX509[0]); 2812 } else { 2813 ALOGE("%s", ERR_error_string(ERR_peek_error(), NULL)); 2814 throwSSLExceptionWithSslErrors(env, ssl, SSL_ERROR_NONE, "Error setting certificate"); 2815 SSL_clear(ssl); 2816 JNI_TRACE("ssl=%p NativeCrypto_SSL_use_certificate => SSL_use_certificate error", ssl); 2817 return; 2818 } 2819 2820 Unique_sk_X509 chain(sk_X509_new_null()); 2821 if (chain.get() == NULL) { 2822 jniThrowOutOfMemoryError(env, "Unable to allocate local certificate chain"); 2823 JNI_TRACE("ssl=%p NativeCrypto_SSL_use_certificate => chain allocation error", ssl); 2824 return; 2825 } 2826 for (int i = 1; i < length; i++) { 2827 if (!sk_X509_push(chain.get(), certificatesX509[i].release())) { 2828 jniThrowOutOfMemoryError(env, "Unable to push certificate"); 2829 JNI_TRACE("ssl=%p NativeCrypto_SSL_use_certificate => certificate push error", ssl); 2830 return; 2831 } 2832 } 2833 int chainResult = SSL_use_certificate_chain(ssl, chain.get()); 2834 if (chainResult == 0) { 2835 throwSSLExceptionWithSslErrors(env, ssl, SSL_ERROR_NONE, "Error setting certificate chain"); 2836 JNI_TRACE("ssl=%p NativeCrypto_SSL_use_certificate => SSL_use_certificate_chain error", 2837 ssl); 2838 return; 2839 } else { 2840 OWNERSHIP_TRANSFERRED(chain); 2841 } 2842 2843 JNI_TRACE("ssl=%p NativeCrypto_SSL_use_certificate => ok", ssl); 2844 } 2845 2846 static void NativeCrypto_SSL_check_private_key(JNIEnv* env, jclass, jint ssl_address) 2847 { 2848 SSL* ssl = to_SSL(env, ssl_address, true); 2849 JNI_TRACE("ssl=%p NativeCrypto_SSL_check_private_key", ssl); 2850 if (ssl == NULL) { 2851 return; 2852 } 2853 int ret = SSL_check_private_key(ssl); 2854 if (ret != 1) { 2855 throwSSLExceptionWithSslErrors(env, ssl, SSL_ERROR_NONE, "Error checking private key"); 2856 SSL_clear(ssl); 2857 JNI_TRACE("ssl=%p NativeCrypto_SSL_check_private_key => error", ssl); 2858 return; 2859 } 2860 JNI_TRACE("ssl=%p NativeCrypto_SSL_check_private_key => ok", ssl); 2861 } 2862 2863 static void NativeCrypto_SSL_set_client_CA_list(JNIEnv* env, jclass, 2864 jint ssl_address, jobjectArray principals) 2865 { 2866 SSL* ssl = to_SSL(env, ssl_address, true); 2867 JNI_TRACE("ssl=%p NativeCrypto_SSL_set_client_CA_list principals=%p", ssl, principals); 2868 if (ssl == NULL) { 2869 return; 2870 } 2871 2872 if (principals == NULL) { 2873 jniThrowNullPointerException(env, "principals == null"); 2874 JNI_TRACE("ssl=%p NativeCrypto_SSL_set_client_CA_list => principals == null", ssl); 2875 return; 2876 } 2877 2878 int length = env->GetArrayLength(principals); 2879 if (length == 0) { 2880 jniThrowException(env, "java/lang/IllegalArgumentException", "principals.length == 0"); 2881 JNI_TRACE("ssl=%p NativeCrypto_SSL_set_client_CA_list => principals.length == 0", ssl); 2882 return; 2883 } 2884 2885 Unique_sk_X509_NAME principalsStack(sk_X509_NAME_new_null()); 2886 if (principalsStack.get() == NULL) { 2887 jniThrowOutOfMemoryError(env, "Unable to allocate principal stack"); 2888 JNI_TRACE("ssl=%p NativeCrypto_SSL_set_client_CA_list => stack allocation error", ssl); 2889 return; 2890 } 2891 for (int i = 0; i < length; i++) { 2892 ScopedLocalRef<jbyteArray> principal(env, 2893 reinterpret_cast<jbyteArray>(env->GetObjectArrayElement(principals, i))); 2894 if (principal.get() == NULL) { 2895 jniThrowNullPointerException(env, "principals element == null"); 2896 JNI_TRACE("ssl=%p NativeCrypto_SSL_set_client_CA_list => principals element null", ssl); 2897 return; 2898 } 2899 2900 ScopedByteArrayRO buf(env, principal.get()); 2901 if (buf.get() == NULL) { 2902 JNI_TRACE("ssl=%p NativeCrypto_SSL_set_client_CA_list => threw exception", ssl); 2903 return; 2904 } 2905 const unsigned char* tmp = reinterpret_cast<const unsigned char*>(buf.get()); 2906 Unique_X509_NAME principalX509Name(d2i_X509_NAME(NULL, &tmp, buf.size())); 2907 2908 if (principalX509Name.get() == NULL) { 2909 ALOGE("%s", ERR_error_string(ERR_peek_error(), NULL)); 2910 throwSSLExceptionWithSslErrors(env, ssl, SSL_ERROR_NONE, "Error parsing principal"); 2911 SSL_clear(ssl); 2912 JNI_TRACE("ssl=%p NativeCrypto_SSL_set_client_CA_list => principals parsing error", 2913 ssl); 2914 return; 2915 } 2916 2917 if (!sk_X509_NAME_push(principalsStack.get(), principalX509Name.release())) { 2918 jniThrowOutOfMemoryError(env, "Unable to push principal"); 2919 JNI_TRACE("ssl=%p NativeCrypto_SSL_set_client_CA_list => principal push error", ssl); 2920 return; 2921 } 2922 } 2923 2924 SSL_set_client_CA_list(ssl, principalsStack.release()); 2925 JNI_TRACE("ssl=%p NativeCrypto_SSL_set_client_CA_list => ok", ssl); 2926 } 2927 2928 /** 2929 * public static native long SSL_get_mode(int ssl); 2930 */ 2931 static jlong NativeCrypto_SSL_get_mode(JNIEnv* env, jclass, jint ssl_address) { 2932 SSL* ssl = to_SSL(env, ssl_address, true); 2933 JNI_TRACE("ssl=%p NativeCrypto_SSL_get_mode", ssl); 2934 if (ssl == NULL) { 2935 return 0; 2936 } 2937 long mode = SSL_get_mode(ssl); 2938 JNI_TRACE("ssl=%p NativeCrypto_SSL_get_mode => 0x%lx", ssl, mode); 2939 return mode; 2940 } 2941 2942 /** 2943 * public static native long SSL_set_mode(int ssl, long mode); 2944 */ 2945 static jlong NativeCrypto_SSL_set_mode(JNIEnv* env, jclass, 2946 jint ssl_address, jlong mode) { 2947 SSL* ssl = to_SSL(env, ssl_address, true); 2948 JNI_TRACE("ssl=%p NativeCrypto_SSL_set_mode mode=0x%llx", ssl, mode); 2949 if (ssl == NULL) { 2950 return 0; 2951 } 2952 long result = SSL_set_mode(ssl, mode); 2953 JNI_TRACE("ssl=%p NativeCrypto_SSL_set_mode => 0x%lx", ssl, result); 2954 return result; 2955 } 2956 2957 /** 2958 * public static native long SSL_clear_mode(int ssl, long mode); 2959 */ 2960 static jlong NativeCrypto_SSL_clear_mode(JNIEnv* env, jclass, 2961 jint ssl_address, jlong mode) { 2962 SSL* ssl = to_SSL(env, ssl_address, true); 2963 JNI_TRACE("ssl=%p NativeCrypto_SSL_clear_mode mode=0x%llx", ssl, mode); 2964 if (ssl == NULL) { 2965 return 0; 2966 } 2967 long result = SSL_clear_mode(ssl, mode); 2968 JNI_TRACE("ssl=%p NativeCrypto_SSL_clear_mode => 0x%lx", ssl, result); 2969 return result; 2970 } 2971 2972 /** 2973 * public static native long SSL_get_options(int ssl); 2974 */ 2975 static jlong NativeCrypto_SSL_get_options(JNIEnv* env, jclass, 2976 jint ssl_address) { 2977 SSL* ssl = to_SSL(env, ssl_address, true); 2978 JNI_TRACE("ssl=%p NativeCrypto_SSL_get_options", ssl); 2979 if (ssl == NULL) { 2980 return 0; 2981 } 2982 long options = SSL_get_options(ssl); 2983 JNI_TRACE("ssl=%p NativeCrypto_SSL_get_options => 0x%lx", ssl, options); 2984 return options; 2985 } 2986 2987 /** 2988 * public static native long SSL_set_options(int ssl, long options); 2989 */ 2990 static jlong NativeCrypto_SSL_set_options(JNIEnv* env, jclass, 2991 jint ssl_address, jlong options) { 2992 SSL* ssl = to_SSL(env, ssl_address, true); 2993 JNI_TRACE("ssl=%p NativeCrypto_SSL_set_options options=0x%llx", ssl, options); 2994 if (ssl == NULL) { 2995 return 0; 2996 } 2997 long result = SSL_set_options(ssl, options); 2998 JNI_TRACE("ssl=%p NativeCrypto_SSL_set_options => 0x%lx", ssl, result); 2999 return result; 3000 } 3001 3002 /** 3003 * public static native long SSL_clear_options(int ssl, long options); 3004 */ 3005 static jlong NativeCrypto_SSL_clear_options(JNIEnv* env, jclass, 3006 jint ssl_address, jlong options) { 3007 SSL* ssl = to_SSL(env, ssl_address, true); 3008 JNI_TRACE("ssl=%p NativeCrypto_SSL_clear_options options=0x%llx", ssl, options); 3009 if (ssl == NULL) { 3010 return 0; 3011 } 3012 long result = SSL_clear_options(ssl, options); 3013 JNI_TRACE("ssl=%p NativeCrypto_SSL_clear_options => 0x%lx", ssl, result); 3014 return result; 3015 } 3016 3017 /** 3018 * Sets the ciphers suites that are enabled in the SSL 3019 */ 3020 static void NativeCrypto_SSL_set_cipher_lists(JNIEnv* env, jclass, 3021 jint ssl_address, jobjectArray cipherSuites) 3022 { 3023 SSL* ssl = to_SSL(env, ssl_address, true); 3024 JNI_TRACE("ssl=%p NativeCrypto_SSL_set_cipher_lists cipherSuites=%p", ssl, cipherSuites); 3025 if (ssl == NULL) { 3026 return; 3027 } 3028 if (cipherSuites == NULL) { 3029 jniThrowNullPointerException(env, "cipherSuites == null"); 3030 return; 3031 } 3032 3033 Unique_sk_SSL_CIPHER cipherstack(sk_SSL_CIPHER_new_null()); 3034 if (cipherstack.get() == NULL) { 3035 jniThrowRuntimeException(env, "sk_SSL_CIPHER_new_null failed"); 3036 return; 3037 } 3038 3039 const SSL_METHOD* ssl_method = ssl->method; 3040 int num_ciphers = ssl_method->num_ciphers(); 3041 3042 int length = env->GetArrayLength(cipherSuites); 3043 JNI_TRACE("ssl=%p NativeCrypto_SSL_set_cipher_lists length=%d", ssl, length); 3044 for (int i = 0; i < length; i++) { 3045 ScopedLocalRef<jstring> cipherSuite(env, 3046 reinterpret_cast<jstring>(env->GetObjectArrayElement(cipherSuites, i))); 3047 ScopedUtfChars c(env, cipherSuite.get()); 3048 if (c.c_str() == NULL) { 3049 return; 3050 } 3051 JNI_TRACE("ssl=%p NativeCrypto_SSL_set_cipher_lists cipherSuite=%s", ssl, c.c_str()); 3052 bool found = false; 3053 for (int j = 0; j < num_ciphers; j++) { 3054 const SSL_CIPHER* cipher = ssl_method->get_cipher(j); 3055 if ((strcmp(c.c_str(), cipher->name) == 0) 3056 && (strcmp(SSL_CIPHER_get_version(cipher), "SSLv2"))) { 3057 if (!sk_SSL_CIPHER_push(cipherstack.get(), cipher)) { 3058 jniThrowOutOfMemoryError(env, "Unable to push cipher"); 3059 JNI_TRACE("ssl=%p NativeCrypto_SSL_set_cipher_lists => cipher push error", ssl); 3060 return; 3061 } 3062 found = true; 3063 } 3064 } 3065 if (!found) { 3066 jniThrowException(env, "java/lang/IllegalArgumentException", 3067 "Could not find cipher suite."); 3068 return; 3069 } 3070 } 3071 3072 int rc = SSL_set_cipher_lists(ssl, cipherstack.get()); 3073 if (rc == 0) { 3074 freeOpenSslErrorState(); 3075 jniThrowException(env, "java/lang/IllegalArgumentException", 3076 "Illegal cipher suite strings."); 3077 } else { 3078 OWNERSHIP_TRANSFERRED(cipherstack); 3079 } 3080 } 3081 3082 /** 3083 * Sets certificate expectations, especially for server to request client auth 3084 */ 3085 static void NativeCrypto_SSL_set_verify(JNIEnv* env, 3086 jclass, jint ssl_address, jint mode) 3087 { 3088 SSL* ssl = to_SSL(env, ssl_address, true); 3089 JNI_TRACE("ssl=%p NativeCrypto_SSL_set_verify mode=%x", ssl, mode); 3090 if (ssl == NULL) { 3091 return; 3092 } 3093 SSL_set_verify(ssl, (int)mode, NULL); 3094 } 3095 3096 /** 3097 * Sets the ciphers suites that are enabled in the SSL 3098 */ 3099 static void NativeCrypto_SSL_set_session(JNIEnv* env, jclass, 3100 jint ssl_address, jint ssl_session_address) 3101 { 3102 SSL* ssl = to_SSL(env, ssl_address, true); 3103 SSL_SESSION* ssl_session = to_SSL_SESSION(env, ssl_session_address, false); 3104 JNI_TRACE("ssl=%p NativeCrypto_SSL_set_session ssl_session=%p", ssl, ssl_session); 3105 if (ssl == NULL) { 3106 return; 3107 } 3108 3109 int ret = SSL_set_session(ssl, ssl_session); 3110 if (ret != 1) { 3111 /* 3112 * Translate the error, and throw if it turns out to be a real 3113 * problem. 3114 */ 3115 int sslErrorCode = SSL_get_error(ssl, ret); 3116 if (sslErrorCode != SSL_ERROR_ZERO_RETURN) { 3117 throwSSLExceptionWithSslErrors(env, ssl, sslErrorCode, "SSL session set"); 3118 SSL_clear(ssl); 3119 } 3120 } 3121 } 3122 3123 /** 3124 * Sets the ciphers suites that are enabled in the SSL 3125 */ 3126 static void NativeCrypto_SSL_set_session_creation_enabled(JNIEnv* env, jclass, 3127 jint ssl_address, jboolean creation_enabled) 3128 { 3129 SSL* ssl = to_SSL(env, ssl_address, true); 3130 JNI_TRACE("ssl=%p NativeCrypto_SSL_set_session_creation_enabled creation_enabled=%d", 3131 ssl, creation_enabled); 3132 if (ssl == NULL) { 3133 return; 3134 } 3135 SSL_set_session_creation_enabled(ssl, creation_enabled); 3136 } 3137 3138 static void NativeCrypto_SSL_set_tlsext_host_name(JNIEnv* env, jclass, 3139 jint ssl_address, jstring hostname) 3140 { 3141 SSL* ssl = to_SSL(env, ssl_address, true); 3142 JNI_TRACE("ssl=%p NativeCrypto_SSL_set_tlsext_host_name hostname=%p", 3143 ssl, hostname); 3144 if (ssl == NULL) { 3145 return; 3146 } 3147 3148 ScopedUtfChars hostnameChars(env, hostname); 3149 if (hostnameChars.c_str() == NULL) { 3150 return; 3151 } 3152 JNI_TRACE("ssl=%p NativeCrypto_SSL_set_tlsext_host_name hostnameChars=%s", 3153 ssl, hostnameChars.c_str()); 3154 3155 int ret = SSL_set_tlsext_host_name(ssl, hostnameChars.c_str()); 3156 if (ret != 1) { 3157 throwSSLExceptionWithSslErrors(env, ssl, SSL_ERROR_NONE, "Error setting host name"); 3158 SSL_clear(ssl); 3159 JNI_TRACE("ssl=%p NativeCrypto_SSL_set_tlsext_host_name => error", ssl); 3160 return; 3161 } 3162 JNI_TRACE("ssl=%p NativeCrypto_SSL_set_tlsext_host_name => ok", ssl); 3163 } 3164 3165 static jstring NativeCrypto_SSL_get_servername(JNIEnv* env, jclass, jint ssl_address) { 3166 SSL* ssl = to_SSL(env, ssl_address, true); 3167 JNI_TRACE("ssl=%p NativeCrypto_SSL_get_servername", ssl); 3168 if (ssl == NULL) { 3169 return NULL; 3170 } 3171 const char* servername = SSL_get_servername(ssl, TLSEXT_NAMETYPE_host_name); 3172 JNI_TRACE("ssl=%p NativeCrypto_SSL_get_servername => %s", ssl, servername); 3173 return env->NewStringUTF(servername); 3174 } 3175 3176 /** 3177 * Callback for the client to select a protocol. 3178 */ 3179 static int next_proto_select_callback(SSL* ssl, unsigned char **out, unsigned char *outlen, 3180 const unsigned char *in, unsigned int inlen, void *) 3181 { 3182 JNI_TRACE("ssl=%p next_proto_select_callback", ssl); 3183 3184 // Enable False Start on the client if the server understands NPN 3185 // http://www.imperialviolet.org/2012/04/11/falsestart.html 3186 SSL_set_mode(ssl, SSL_MODE_HANDSHAKE_CUTTHROUGH); 3187 3188 AppData* appData = toAppData(ssl); 3189 unsigned char* npnProtocols = reinterpret_cast<unsigned char*>(appData->npnProtocolsData); 3190 size_t npnProtocolsLength = appData->npnProtocolsLength; 3191 3192 int status = SSL_select_next_proto(out, outlen, in, inlen, npnProtocols, npnProtocolsLength); 3193 switch (status) { 3194 case OPENSSL_NPN_NEGOTIATED: 3195 JNI_TRACE("ssl=%p next_proto_select_callback NPN negotiated", ssl); 3196 break; 3197 case OPENSSL_NPN_UNSUPPORTED: 3198 JNI_TRACE("ssl=%p next_proto_select_callback NPN unsupported", ssl); 3199 break; 3200 case OPENSSL_NPN_NO_OVERLAP: 3201 JNI_TRACE("ssl=%p next_proto_select_callback NPN no overlap", ssl); 3202 break; 3203 } 3204 return SSL_TLSEXT_ERR_OK; 3205 } 3206 3207 /** 3208 * Callback for the server to advertise available protocols. 3209 */ 3210 static int next_protos_advertised_callback(SSL* ssl, 3211 const unsigned char **out, unsigned int *outlen, void *) 3212 { 3213 JNI_TRACE("ssl=%p next_protos_advertised_callback", ssl); 3214 AppData* appData = toAppData(ssl); 3215 unsigned char* npnProtocols = reinterpret_cast<unsigned char*>(appData->npnProtocolsData); 3216 if (npnProtocols != NULL) { 3217 *out = npnProtocols; 3218 *outlen = appData->npnProtocolsLength; 3219 } 3220 return SSL_TLSEXT_ERR_OK; 3221 } 3222 3223 static void NativeCrypto_SSL_CTX_enable_npn(JNIEnv* env, jclass, jint ssl_ctx_address) 3224 { 3225 SSL_CTX* ssl_ctx = to_SSL_CTX(env, ssl_ctx_address, true); 3226 if (ssl_ctx == NULL) { 3227 return; 3228 } 3229 SSL_CTX_set_next_proto_select_cb(ssl_ctx, next_proto_select_callback, NULL); // client 3230 SSL_CTX_set_next_protos_advertised_cb(ssl_ctx, next_protos_advertised_callback, NULL); // server 3231 } 3232 3233 static void NativeCrypto_SSL_CTX_disable_npn(JNIEnv* env, jclass, jint ssl_ctx_address) 3234 { 3235 SSL_CTX* ssl_ctx = to_SSL_CTX(env, ssl_ctx_address, true); 3236 if (ssl_ctx == NULL) { 3237 return; 3238 } 3239 SSL_CTX_set_next_proto_select_cb(ssl_ctx, NULL, NULL); // client 3240 SSL_CTX_set_next_protos_advertised_cb(ssl_ctx, NULL, NULL); // server 3241 } 3242 3243 static jbyteArray NativeCrypto_SSL_get_npn_negotiated_protocol(JNIEnv* env, jclass, 3244 jint ssl_address) 3245 { 3246 SSL* ssl = to_SSL(env, ssl_address, true); 3247 JNI_TRACE("ssl=%p NativeCrypto_SSL_get_npn_negotiated_protocol", ssl); 3248 if (ssl == NULL) { 3249 return NULL; 3250 } 3251 const jbyte* npn; 3252 unsigned npnLength; 3253 SSL_get0_next_proto_negotiated(ssl, reinterpret_cast<const unsigned char**>(&npn), &npnLength); 3254 if (npnLength == 0) { 3255 return NULL; 3256 } 3257 jbyteArray result = env->NewByteArray(npnLength); 3258 if (result != NULL) { 3259 env->SetByteArrayRegion(result, 0, npnLength, npn); 3260 } 3261 return result; 3262 } 3263 3264 /** 3265 * Perform SSL handshake 3266 */ 3267 static jint NativeCrypto_SSL_do_handshake(JNIEnv* env, jclass, jint ssl_address, 3268 jobject fdObject, jobject shc, jint timeout_millis, jboolean client_mode, 3269 jbyteArray npnProtocols) 3270 { 3271 SSL* ssl = to_SSL(env, ssl_address, true); 3272 JNI_TRACE("ssl=%p NativeCrypto_SSL_do_handshake fd=%p shc=%p timeout_millis=%d client_mode=%d npn=%p", 3273 ssl, fdObject, shc, timeout_millis, client_mode, npnProtocols); 3274 if (ssl == NULL) { 3275 return 0; 3276 } 3277 if (fdObject == NULL) { 3278 jniThrowNullPointerException(env, "fd == null"); 3279 JNI_TRACE("ssl=%p NativeCrypto_SSL_do_handshake fd == null => 0", ssl); 3280 return 0; 3281 } 3282 if (shc == NULL) { 3283 jniThrowNullPointerException(env, "sslHandshakeCallbacks == null"); 3284 JNI_TRACE("ssl=%p NativeCrypto_SSL_do_handshake sslHandshakeCallbacks == null => 0", ssl); 3285 return 0; 3286 } 3287 3288 NetFd fd(env, fdObject); 3289 if (fd.isClosed()) { 3290 // SocketException thrown by NetFd.isClosed 3291 SSL_clear(ssl); 3292 JNI_TRACE("ssl=%p NativeCrypto_SSL_do_handshake fd.isClosed() => 0", ssl); 3293 return 0; 3294 } 3295 3296 int ret = SSL_set_fd(ssl, fd.get()); 3297 JNI_TRACE("ssl=%p NativeCrypto_SSL_do_handshake s=%d", ssl, fd.get()); 3298 3299 if (ret != 1) { 3300 throwSSLExceptionWithSslErrors(env, ssl, SSL_ERROR_NONE, 3301 "Error setting the file descriptor"); 3302 SSL_clear(ssl); 3303 JNI_TRACE("ssl=%p NativeCrypto_SSL_do_handshake SSL_set_fd => 0", ssl); 3304 return 0; 3305 } 3306 3307 /* 3308 * Make socket non-blocking, so SSL_connect SSL_read() and SSL_write() don't hang 3309 * forever and we can use select() to find out if the socket is ready. 3310 */ 3311 if (!setBlocking(fd.get(), false)) { 3312 throwSSLExceptionStr(env, "Unable to make socket non blocking"); 3313 SSL_clear(ssl); 3314 JNI_TRACE("ssl=%p NativeCrypto_SSL_do_handshake setBlocking => 0", ssl); 3315 return 0; 3316 } 3317 3318 /* 3319 * Create our special application data. 3320 */ 3321 AppData* appData = AppData::create(); 3322 if (appData == NULL) { 3323 throwSSLExceptionStr(env, "Unable to create application data"); 3324 SSL_clear(ssl); 3325 JNI_TRACE("ssl=%p NativeCrypto_SSL_do_handshake appData => 0", ssl); 3326 return 0; 3327 } 3328 3329 SSL_set_app_data(ssl, reinterpret_cast<char*>(appData)); 3330 JNI_TRACE("ssl=%p AppData::create => %p", ssl, appData); 3331 3332 if (client_mode) { 3333 SSL_set_connect_state(ssl); 3334 } else { 3335 SSL_set_accept_state(ssl); 3336 } 3337 3338 ret = 0; 3339 while (appData->aliveAndKicking) { 3340 errno = 0; 3341 3342 if (!appData->setCallbackState(env, shc, fdObject, npnProtocols)) { 3343 // SocketException thrown by NetFd.isClosed 3344 SSL_clear(ssl); 3345 JNI_TRACE("ssl=%p NativeCrypto_SSL_do_handshake setCallbackState => 0", ssl); 3346 return 0; 3347 } 3348 ret = SSL_do_handshake(ssl); 3349 appData->clearCallbackState(); 3350 // cert_verify_callback threw exception 3351 if (env->ExceptionCheck()) { 3352 SSL_clear(ssl); 3353 JNI_TRACE("ssl=%p NativeCrypto_SSL_do_handshake exception => 0", ssl); 3354 return 0; 3355 } 3356 // success case 3357 if (ret == 1) { 3358 break; 3359 } 3360 // retry case 3361 if (errno == EINTR) { 3362 continue; 3363 } 3364 // error case 3365 int sslError = SSL_get_error(ssl, ret); 3366 JNI_TRACE("ssl=%p NativeCrypto_SSL_do_handshake ret=%d errno=%d sslError=%d timeout_millis=%d", 3367 ssl, ret, errno, sslError, timeout_millis); 3368 3369 /* 3370 * If SSL_do_handshake doesn't succeed due to the socket being 3371 * either unreadable or unwritable, we use sslSelect to 3372 * wait for it to become ready. If that doesn't happen 3373 * before the specified timeout or an error occurs, we 3374 * cancel the handshake. Otherwise we try the SSL_connect 3375 * again. 3376 */ 3377 if (sslError == SSL_ERROR_WANT_READ || sslError == SSL_ERROR_WANT_WRITE) { 3378 appData->waitingThreads++; 3379 int selectResult = sslSelect(env, sslError, fdObject, appData, timeout_millis); 3380 3381 if (selectResult == THROWN_EXCEPTION) { 3382 // SocketException thrown by NetFd.isClosed 3383 SSL_clear(ssl); 3384 JNI_TRACE("ssl=%p NativeCrypto_SSL_do_handshake sslSelect => 0", ssl); 3385 return 0; 3386 } 3387 if (selectResult == -1) { 3388 throwSSLExceptionWithSslErrors(env, ssl, SSL_ERROR_SYSCALL, "handshake error"); 3389 SSL_clear(ssl); 3390 JNI_TRACE("ssl=%p NativeCrypto_SSL_do_handshake selectResult == -1 => 0", ssl); 3391 return 0; 3392 } 3393 if (selectResult == 0) { 3394 throwSocketTimeoutException(env, "SSL handshake timed out"); 3395 SSL_clear(ssl); 3396 freeOpenSslErrorState(); 3397 JNI_TRACE("ssl=%p NativeCrypto_SSL_do_handshake selectResult == 0 => 0", ssl); 3398 return 0; 3399 } 3400 } else { 3401 // ALOGE("Unknown error %d during handshake", error); 3402 break; 3403 } 3404 } 3405 3406 // clean error. See SSL_do_handshake(3SSL) man page. 3407 if (ret == 0) { 3408 /* 3409 * The other side closed the socket before the handshake could be 3410 * completed, but everything is within the bounds of the TLS protocol. 3411 * We still might want to find out the real reason of the failure. 3412 */ 3413 int sslError = SSL_get_error(ssl, ret); 3414 if (sslError == SSL_ERROR_NONE || (sslError == SSL_ERROR_SYSCALL && errno == 0)) { 3415 throwSSLExceptionStr(env, "Connection closed by peer"); 3416 } else { 3417 throwSSLExceptionWithSslErrors(env, ssl, sslError, "SSL handshake terminated"); 3418 } 3419 SSL_clear(ssl); 3420 JNI_TRACE("ssl=%p NativeCrypto_SSL_do_handshake clean error => 0", ssl); 3421 return 0; 3422 } 3423 3424 // unclean error. See SSL_do_handshake(3SSL) man page. 3425 if (ret < 0) { 3426 /* 3427 * Translate the error and throw exception. We are sure it is an error 3428 * at this point. 3429 */ 3430 int sslError = SSL_get_error(ssl, ret); 3431 throwSSLExceptionWithSslErrors(env, ssl, sslError, "SSL handshake aborted"); 3432 SSL_clear(ssl); 3433 JNI_TRACE("ssl=%p NativeCrypto_SSL_do_handshake unclean error => 0", ssl); 3434 return 0; 3435 } 3436 SSL_SESSION* ssl_session = SSL_get1_session(ssl); 3437 JNI_TRACE("ssl=%p NativeCrypto_SSL_do_handshake => ssl_session=%p", ssl, ssl_session); 3438 return (jint) ssl_session; 3439 } 3440 3441 /** 3442 * Perform SSL renegotiation 3443 */ 3444 static void NativeCrypto_SSL_renegotiate(JNIEnv* env, jclass, jint ssl_address) 3445 { 3446 SSL* ssl = to_SSL(env, ssl_address, true); 3447 JNI_TRACE("ssl=%p NativeCrypto_SSL_renegotiate", ssl); 3448 if (ssl == NULL) { 3449 return; 3450 } 3451 int result = SSL_renegotiate(ssl); 3452 if (result != 1) { 3453 throwSSLExceptionStr(env, "Problem with SSL_renegotiate"); 3454 return; 3455 } 3456 // first call asks client to perform renegotiation 3457 int ret = SSL_do_handshake(ssl); 3458 if (ret != 1) { 3459 int sslError = SSL_get_error(ssl, ret); 3460 throwSSLExceptionWithSslErrors(env, ssl, sslError, 3461 "Problem with SSL_do_handshake after SSL_renegotiate"); 3462 return; 3463 } 3464 // if client agrees, set ssl state and perform renegotiation 3465 ssl->state = SSL_ST_ACCEPT; 3466 SSL_do_handshake(ssl); 3467 JNI_TRACE("ssl=%p NativeCrypto_SSL_renegotiate =>", ssl); 3468 } 3469 3470 /** 3471 * public static native byte[][] SSL_get_certificate(int ssl); 3472 */ 3473 static jobjectArray NativeCrypto_SSL_get_certificate(JNIEnv* env, jclass, jint ssl_address) 3474 { 3475 SSL* ssl = to_SSL(env, ssl_address, true); 3476 JNI_TRACE("ssl=%p NativeCrypto_SSL_get_certificate", ssl); 3477 if (ssl == NULL) { 3478 return NULL; 3479 } 3480 X509* certificate = SSL_get_certificate(ssl); 3481 if (certificate == NULL) { 3482 JNI_TRACE("ssl=%p NativeCrypto_SSL_get_certificate => NULL", ssl); 3483 return NULL; 3484 } 3485 3486 Unique_sk_X509 chain(sk_X509_new_null()); 3487 if (chain.get() == NULL) { 3488 jniThrowOutOfMemoryError(env, "Unable to allocate local certificate chain"); 3489 JNI_TRACE("ssl=%p NativeCrypto_SSL_get_certificate => threw exception", ssl); 3490 return NULL; 3491 } 3492 if (!sk_X509_push(chain.get(), certificate)) { 3493 jniThrowOutOfMemoryError(env, "Unable to push local certificate"); 3494 JNI_TRACE("ssl=%p NativeCrypto_SSL_get_certificate => NULL", ssl); 3495 return NULL; 3496 } 3497 STACK_OF(X509)* cert_chain = SSL_get_certificate_chain(ssl, certificate); 3498 for (int i=0; i<sk_X509_num(cert_chain); i++) { 3499 if (!sk_X509_push(chain.get(), sk_X509_value(cert_chain, i))) { 3500 jniThrowOutOfMemoryError(env, "Unable to push local certificate chain"); 3501 JNI_TRACE("ssl=%p NativeCrypto_SSL_get_certificate => NULL", ssl); 3502 return NULL; 3503 } 3504 } 3505 3506 jobjectArray objectArray = getCertificateBytes(env, chain.get()); 3507 JNI_TRACE("ssl=%p NativeCrypto_SSL_get_certificate => %p", ssl, objectArray); 3508 return objectArray; 3509 } 3510 3511 // Fills a byte[][] with the peer certificates in the chain. 3512 static jobjectArray NativeCrypto_SSL_get_peer_cert_chain(JNIEnv* env, jclass, jint ssl_address) 3513 { 3514 SSL* ssl = to_SSL(env, ssl_address, true); 3515 JNI_TRACE("ssl=%p NativeCrypto_SSL_get_peer_cert_chain", ssl); 3516 if (ssl == NULL) { 3517 return NULL; 3518 } 3519 STACK_OF(X509)* chain = SSL_get_peer_cert_chain(ssl); 3520 Unique_sk_X509 chain_copy(NULL); 3521 if (ssl->server) { 3522 X509* x509 = SSL_get_peer_certificate(ssl); 3523 if (x509 == NULL) { 3524 JNI_TRACE("ssl=%p NativeCrypto_SSL_get_peer_cert_chain => NULL", ssl); 3525 return NULL; 3526 } 3527 chain_copy.reset(sk_X509_dup(chain)); 3528 if (chain_copy.get() == NULL) { 3529 jniThrowOutOfMemoryError(env, "Unable to allocate peer certificate chain"); 3530 JNI_TRACE("ssl=%p NativeCrypto_SSL_get_peer_cert_chain => certificate dup error", ssl); 3531 return NULL; 3532 } 3533 if (!sk_X509_push(chain_copy.get(), x509)) { 3534 jniThrowOutOfMemoryError(env, "Unable to push server's peer certificate"); 3535 JNI_TRACE("ssl=%p NativeCrypto_SSL_get_peer_cert_chain => certificate push error", ssl); 3536 return NULL; 3537 } 3538 chain = chain_copy.get(); 3539 } 3540 jobjectArray objectArray = getCertificateBytes(env, chain); 3541 JNI_TRACE("ssl=%p NativeCrypto_SSL_get_peer_cert_chain => %p", ssl, objectArray); 3542 return objectArray; 3543 } 3544 3545 /** 3546 * Helper function which does the actual reading. The Java layer guarantees that 3547 * at most one thread will enter this function at any given time. 3548 * 3549 * @param ssl non-null; the SSL context 3550 * @param buf non-null; buffer to read into 3551 * @param len length of the buffer, in bytes 3552 * @param sslReturnCode original SSL return code 3553 * @param sslErrorCode filled in with the SSL error code in case of error 3554 * @return number of bytes read on success, -1 if the connection was 3555 * cleanly shut down, or THROW_SSLEXCEPTION if an exception should be thrown. 3556 */ 3557 static int sslRead(JNIEnv* env, SSL* ssl, jobject fdObject, jobject shc, char* buf, jint len, 3558 int* sslReturnCode, int* sslErrorCode, int timeout_millis) { 3559 JNI_TRACE("ssl=%p sslRead buf=%p len=%d", ssl, buf, len); 3560 3561 if (len == 0) { 3562 // Don't bother doing anything in this case. 3563 return 0; 3564 } 3565 3566 BIO* bio = SSL_get_rbio(ssl); 3567 3568 AppData* appData = toAppData(ssl); 3569 if (appData == NULL) { 3570 return THROW_SSLEXCEPTION; 3571 } 3572 3573 while (appData->aliveAndKicking) { 3574 errno = 0; 3575 3576 if (MUTEX_LOCK(appData->mutex) == -1) { 3577 return -1; 3578 } 3579 3580 unsigned int bytesMoved = BIO_number_read(bio) + BIO_number_written(bio); 3581 3582 if (!appData->setCallbackState(env, shc, fdObject, NULL)) { 3583 MUTEX_UNLOCK(appData->mutex); 3584 return THROWN_EXCEPTION; 3585 } 3586 int result = SSL_read(ssl, buf, len); 3587 appData->clearCallbackState(); 3588 // callbacks can happen if server requests renegotiation 3589 if (env->ExceptionCheck()) { 3590 SSL_clear(ssl); 3591 JNI_TRACE("ssl=%p sslRead => THROWN_EXCEPTION", ssl); 3592 return THROWN_EXCEPTION; 3593 } 3594 int sslError = SSL_ERROR_NONE; 3595 if (result <= 0) { 3596 sslError = SSL_get_error(ssl, result); 3597 freeOpenSslErrorState(); 3598 } 3599 JNI_TRACE("ssl=%p sslRead SSL_read result=%d sslError=%d", ssl, result, sslError); 3600 #ifdef WITH_JNI_TRACE_DATA 3601 for (int i = 0; i < result; i+= WITH_JNI_TRACE_DATA_CHUNK_SIZE) { 3602 int n = std::min(result - i, WITH_JNI_TRACE_DATA_CHUNK_SIZE); 3603 JNI_TRACE("ssl=%p sslRead data: %d:\n%*s", ssl, n, n, buf+i); 3604 } 3605 #endif 3606 3607 // If we have been successful in moving data around, check whether it 3608 // might make sense to wake up other blocked threads, so they can give 3609 // it a try, too. 3610 if (BIO_number_read(bio) + BIO_number_written(bio) != bytesMoved 3611 && appData->waitingThreads > 0) { 3612 sslNotify(appData); 3613 } 3614 3615 // If we are blocked by the underlying socket, tell the world that 3616 // there will be one more waiting thread now. 3617 if (sslError == SSL_ERROR_WANT_READ || sslError == SSL_ERROR_WANT_WRITE) { 3618 appData->waitingThreads++; 3619 } 3620 3621 MUTEX_UNLOCK(appData->mutex); 3622 3623 switch (sslError) { 3624 // Successfully read at least one byte. 3625 case SSL_ERROR_NONE: { 3626 return result; 3627 } 3628 3629 // Read zero bytes. End of stream reached. 3630 case SSL_ERROR_ZERO_RETURN: { 3631 return -1; 3632 } 3633 3634 // Need to wait for availability of underlying layer, then retry. 3635 case SSL_ERROR_WANT_READ: 3636 case SSL_ERROR_WANT_WRITE: { 3637 int selectResult = sslSelect(env, sslError, fdObject, appData, timeout_millis); 3638 if (selectResult == THROWN_EXCEPTION) { 3639 return THROWN_EXCEPTION; 3640 } 3641 if (selectResult == -1) { 3642 *sslReturnCode = -1; 3643 *sslErrorCode = sslError; 3644 return THROW_SSLEXCEPTION; 3645 } 3646 if (selectResult == 0) { 3647 return THROW_SOCKETTIMEOUTEXCEPTION; 3648 } 3649 3650 break; 3651 } 3652 3653 // A problem occurred during a system call, but this is not 3654 // necessarily an error. 3655 case SSL_ERROR_SYSCALL: { 3656 // Connection closed without proper shutdown. Tell caller we 3657 // have reached end-of-stream. 3658 if (result == 0) { 3659 return -1; 3660 } 3661 3662 // System call has been interrupted. Simply retry. 3663 if (errno == EINTR) { 3664 break; 3665 } 3666 3667 // Note that for all other system call errors we fall through 3668 // to the default case, which results in an Exception. 3669 } 3670 3671 // Everything else is basically an error. 3672 default: { 3673 *sslReturnCode = result; 3674 *sslErrorCode = sslError; 3675 return THROW_SSLEXCEPTION; 3676 } 3677 } 3678 } 3679 3680 return -1; 3681 } 3682 3683 /** 3684 * OpenSSL read function (2): read into buffer at offset n chunks. 3685 * Returns 1 (success) or value <= 0 (failure). 3686 */ 3687 static jint NativeCrypto_SSL_read(JNIEnv* env, jclass, jint ssl_address, jobject fdObject, 3688 jobject shc, jbyteArray b, jint offset, jint len, 3689 jint timeout_millis) 3690 { 3691 SSL* ssl = to_SSL(env, ssl_address, true); 3692 JNI_TRACE("ssl=%p NativeCrypto_SSL_read fd=%p shc=%p b=%p offset=%d len=%d timeout_millis=%d", 3693 ssl, fdObject, shc, b, offset, len, timeout_millis); 3694 if (ssl == NULL) { 3695 return 0; 3696 } 3697 if (fdObject == NULL) { 3698 jniThrowNullPointerException(env, "fd == null"); 3699 JNI_TRACE("ssl=%p NativeCrypto_SSL_read => fd == null", ssl); 3700 return 0; 3701 } 3702 if (shc == NULL) { 3703 jniThrowNullPointerException(env, "sslHandshakeCallbacks == null"); 3704 JNI_TRACE("ssl=%p NativeCrypto_SSL_read => sslHandshakeCallbacks == null", ssl); 3705 return 0; 3706 } 3707 3708 ScopedByteArrayRW bytes(env, b); 3709 if (bytes.get() == NULL) { 3710 JNI_TRACE("ssl=%p NativeCrypto_SSL_read => threw exception", ssl); 3711 return 0; 3712 } 3713 int returnCode = 0; 3714 int sslErrorCode = SSL_ERROR_NONE;; 3715 3716 int ret = sslRead(env, ssl, fdObject, shc, reinterpret_cast<char*>(bytes.get() + offset), len, 3717 &returnCode, &sslErrorCode, timeout_millis); 3718 3719 int result; 3720 switch (ret) { 3721 case THROW_SSLEXCEPTION: 3722 // See sslRead() regarding improper failure to handle normal cases. 3723 throwSSLExceptionWithSslErrors(env, ssl, sslErrorCode, "Read error"); 3724 result = -1; 3725 break; 3726 case THROW_SOCKETTIMEOUTEXCEPTION: 3727 throwSocketTimeoutException(env, "Read timed out"); 3728 result = -1; 3729 break; 3730 case THROWN_EXCEPTION: 3731 // SocketException thrown by NetFd.isClosed 3732 // or RuntimeException thrown by callback 3733 result = -1; 3734 break; 3735 default: 3736 result = ret; 3737 break; 3738 } 3739 3740 JNI_TRACE("ssl=%p NativeCrypto_SSL_read => %d", ssl, result); 3741 return result; 3742 } 3743 3744 /** 3745 * Helper function which does the actual writing. The Java layer guarantees that 3746 * at most one thread will enter this function at any given time. 3747 * 3748 * @param ssl non-null; the SSL context 3749 * @param buf non-null; buffer to write 3750 * @param len length of the buffer, in bytes 3751 * @param sslReturnCode original SSL return code 3752 * @param sslErrorCode filled in with the SSL error code in case of error 3753 * @return number of bytes read on success, -1 if the connection was 3754 * cleanly shut down, or THROW_SSLEXCEPTION if an exception should be thrown. 3755 */ 3756 static int sslWrite(JNIEnv* env, SSL* ssl, jobject fdObject, jobject shc, const char* buf, jint len, 3757 int* sslReturnCode, int* sslErrorCode) { 3758 JNI_TRACE("ssl=%p sslWrite buf=%p len=%d", ssl, buf, len); 3759 3760 if (len == 0) { 3761 // Don't bother doing anything in this case. 3762 return 0; 3763 } 3764 3765 BIO* bio = SSL_get_wbio(ssl); 3766 3767 AppData* appData = toAppData(ssl); 3768 if (appData == NULL) { 3769 return THROW_SSLEXCEPTION; 3770 } 3771 3772 int count = len; 3773 3774 while (appData->aliveAndKicking && len > 0) { 3775 errno = 0; 3776 3777 if (MUTEX_LOCK(appData->mutex) == -1) { 3778 return -1; 3779 } 3780 3781 unsigned int bytesMoved = BIO_number_read(bio) + BIO_number_written(bio); 3782 3783 // ALOGD("Doing SSL_write() with %d bytes to go", len); 3784 if (!appData->setCallbackState(env, shc, fdObject, NULL)) { 3785 MUTEX_UNLOCK(appData->mutex); 3786 return THROWN_EXCEPTION; 3787 } 3788 int result = SSL_write(ssl, buf, len); 3789 appData->clearCallbackState(); 3790 // callbacks can happen if server requests renegotiation 3791 if (env->ExceptionCheck()) { 3792 SSL_clear(ssl); 3793 JNI_TRACE("ssl=%p sslWrite exception => THROWN_EXCEPTION", ssl); 3794 return THROWN_EXCEPTION; 3795 } 3796 int sslError = SSL_ERROR_NONE; 3797 if (result <= 0) { 3798 sslError = SSL_get_error(ssl, result); 3799 freeOpenSslErrorState(); 3800 } 3801 JNI_TRACE("ssl=%p sslWrite SSL_write result=%d sslError=%d", ssl, result, sslError); 3802 #ifdef WITH_JNI_TRACE_DATA 3803 for (int i = 0; i < result; i+= WITH_JNI_TRACE_DATA_CHUNK_SIZE) { 3804 int n = std::min(result - i, WITH_JNI_TRACE_DATA_CHUNK_SIZE); 3805 JNI_TRACE("ssl=%p sslWrite data: %d:\n%*s", ssl, n, n, buf+i); 3806 } 3807 #endif 3808 3809 // If we have been successful in moving data around, check whether it 3810 // might make sense to wake up other blocked threads, so they can give 3811 // it a try, too. 3812 if (BIO_number_read(bio) + BIO_number_written(bio) != bytesMoved 3813 && appData->waitingThreads > 0) { 3814 sslNotify(appData); 3815 } 3816 3817 // If we are blocked by the underlying socket, tell the world that 3818 // there will be one more waiting thread now. 3819 if (sslError == SSL_ERROR_WANT_READ || sslError == SSL_ERROR_WANT_WRITE) { 3820 appData->waitingThreads++; 3821 } 3822 3823 MUTEX_UNLOCK(appData->mutex); 3824 3825 switch (sslError) { 3826 // Successfully wrote at least one byte. 3827 case SSL_ERROR_NONE: { 3828 buf += result; 3829 len -= result; 3830 break; 3831 } 3832 3833 // Wrote zero bytes. End of stream reached. 3834 case SSL_ERROR_ZERO_RETURN: { 3835 return -1; 3836 } 3837 3838 // Need to wait for availability of underlying layer, then retry. 3839 // The concept of a write timeout doesn't really make sense, and 3840 // it's also not standard Java behavior, so we wait forever here. 3841 case SSL_ERROR_WANT_READ: 3842 case SSL_ERROR_WANT_WRITE: { 3843 int selectResult = sslSelect(env, sslError, fdObject, appData, 0); 3844 if (selectResult == THROWN_EXCEPTION) { 3845 return THROWN_EXCEPTION; 3846 } 3847 if (selectResult == -1) { 3848 *sslReturnCode = -1; 3849 *sslErrorCode = sslError; 3850 return THROW_SSLEXCEPTION; 3851 } 3852 if (selectResult == 0) { 3853 return THROW_SOCKETTIMEOUTEXCEPTION; 3854 } 3855 3856 break; 3857 } 3858 3859 // A problem occurred during a system call, but this is not 3860 // necessarily an error. 3861 case SSL_ERROR_SYSCALL: { 3862 // Connection closed without proper shutdown. Tell caller we 3863 // have reached end-of-stream. 3864 if (result == 0) { 3865 return -1; 3866 } 3867 3868 // System call has been interrupted. Simply retry. 3869 if (errno == EINTR) { 3870 break; 3871 } 3872 3873 // Note that for all other system call errors we fall through 3874 // to the default case, which results in an Exception. 3875 } 3876 3877 // Everything else is basically an error. 3878 default: { 3879 *sslReturnCode = result; 3880 *sslErrorCode = sslError; 3881 return THROW_SSLEXCEPTION; 3882 } 3883 } 3884 } 3885 JNI_TRACE("ssl=%p sslWrite => count=%d", ssl, count); 3886 3887 return count; 3888 } 3889 3890 /** 3891 * OpenSSL write function (2): write into buffer at offset n chunks. 3892 */ 3893 static void NativeCrypto_SSL_write(JNIEnv* env, jclass, jint ssl_address, jobject fdObject, 3894 jobject shc, jbyteArray b, jint offset, jint len) 3895 { 3896 SSL* ssl = to_SSL(env, ssl_address, true); 3897 JNI_TRACE("ssl=%p NativeCrypto_SSL_write fd=%p shc=%p b=%p offset=%d len=%d", 3898 ssl, fdObject, shc, b, offset, len); 3899 if (ssl == NULL) { 3900 return; 3901 } 3902 if (fdObject == NULL) { 3903 jniThrowNullPointerException(env, "fd == null"); 3904 JNI_TRACE("ssl=%p NativeCrypto_SSL_write => fd == null", ssl); 3905 return; 3906 } 3907 if (shc == NULL) { 3908 jniThrowNullPointerException(env, "sslHandshakeCallbacks == null"); 3909 JNI_TRACE("ssl=%p NativeCrypto_SSL_write => sslHandshakeCallbacks == null", ssl); 3910 return; 3911 } 3912 3913 ScopedByteArrayRO bytes(env, b); 3914 if (bytes.get() == NULL) { 3915 JNI_TRACE("ssl=%p NativeCrypto_SSL_write => threw exception", ssl); 3916 return; 3917 } 3918 int returnCode = 0; 3919 int sslErrorCode = SSL_ERROR_NONE; 3920 int ret = sslWrite(env, ssl, fdObject, shc, reinterpret_cast<const char*>(bytes.get() + offset), 3921 len, &returnCode, &sslErrorCode); 3922 3923 switch (ret) { 3924 case THROW_SSLEXCEPTION: 3925 // See sslWrite() regarding improper failure to handle normal cases. 3926 throwSSLExceptionWithSslErrors(env, ssl, sslErrorCode, "Write error"); 3927 break; 3928 case THROW_SOCKETTIMEOUTEXCEPTION: 3929 throwSocketTimeoutException(env, "Write timed out"); 3930 break; 3931 case THROWN_EXCEPTION: 3932 // SocketException thrown by NetFd.isClosed 3933 break; 3934 default: 3935 break; 3936 } 3937 } 3938 3939 /** 3940 * Interrupt any pending IO before closing the socket. 3941 */ 3942 static void NativeCrypto_SSL_interrupt( 3943 JNIEnv* env, jclass, jint ssl_address) { 3944 SSL* ssl = to_SSL(env, ssl_address, false); 3945 JNI_TRACE("ssl=%p NativeCrypto_SSL_interrupt", ssl); 3946 if (ssl == NULL) { 3947 return; 3948 } 3949 3950 /* 3951 * Mark the connection as quasi-dead, then send something to the emergency 3952 * file descriptor, so any blocking select() calls are woken up. 3953 */ 3954 AppData* appData = toAppData(ssl); 3955 if (appData != NULL) { 3956 appData->aliveAndKicking = 0; 3957 3958 // At most two threads can be waiting. 3959 sslNotify(appData); 3960 sslNotify(appData); 3961 } 3962 } 3963 3964 /** 3965 * OpenSSL close SSL socket function. 3966 */ 3967 static void NativeCrypto_SSL_shutdown(JNIEnv* env, jclass, jint ssl_address, 3968 jobject fdObject, jobject shc) { 3969 SSL* ssl = to_SSL(env, ssl_address, false); 3970 JNI_TRACE("ssl=%p NativeCrypto_SSL_shutdown fd=%p shc=%p", ssl, fdObject, shc); 3971 if (ssl == NULL) { 3972 return; 3973 } 3974 if (fdObject == NULL) { 3975 jniThrowNullPointerException(env, "fd == null"); 3976 JNI_TRACE("ssl=%p NativeCrypto_SSL_shutdown => fd == null", ssl); 3977 return; 3978 } 3979 if (shc == NULL) { 3980 jniThrowNullPointerException(env, "sslHandshakeCallbacks == null"); 3981 JNI_TRACE("ssl=%p NativeCrypto_SSL_shutdown => sslHandshakeCallbacks == null", ssl); 3982 return; 3983 } 3984 3985 AppData* appData = toAppData(ssl); 3986 if (appData != NULL) { 3987 if (!appData->setCallbackState(env, shc, fdObject, NULL)) { 3988 // SocketException thrown by NetFd.isClosed 3989 SSL_clear(ssl); 3990 freeOpenSslErrorState(); 3991 return; 3992 } 3993 3994 /* 3995 * Try to make socket blocking again. OpenSSL literature recommends this. 3996 */ 3997 int fd = SSL_get_fd(ssl); 3998 JNI_TRACE("ssl=%p NativeCrypto_SSL_shutdown s=%d", ssl, fd); 3999 if (fd != -1) { 4000 setBlocking(fd, true); 4001 } 4002 4003 int ret = SSL_shutdown(ssl); 4004 appData->clearCallbackState(); 4005 // callbacks can happen if server requests renegotiation 4006 if (env->ExceptionCheck()) { 4007 SSL_clear(ssl); 4008 JNI_TRACE("ssl=%p NativeCrypto_SSL_shutdown => exception", ssl); 4009 return; 4010 } 4011 switch (ret) { 4012 case 0: 4013 /* 4014 * Shutdown was not successful (yet), but there also 4015 * is no error. Since we can't know whether the remote 4016 * server is actually still there, and we don't want to 4017 * get stuck forever in a second SSL_shutdown() call, we 4018 * simply return. This is not security a problem as long 4019 * as we close the underlying socket, which we actually 4020 * do, because that's where we are just coming from. 4021 */ 4022 break; 4023 case 1: 4024 /* 4025 * Shutdown was successful. We can safely return. Hooray! 4026 */ 4027 break; 4028 default: 4029 /* 4030 * Everything else is a real error condition. We should 4031 * let the Java layer know about this by throwing an 4032 * exception. 4033 */ 4034 int sslError = SSL_get_error(ssl, ret); 4035 throwSSLExceptionWithSslErrors(env, ssl, sslError, "SSL shutdown failed"); 4036 break; 4037 } 4038 } 4039 4040 SSL_clear(ssl); 4041 freeOpenSslErrorState(); 4042 } 4043 4044 /** 4045 * public static native void SSL_free(int ssl); 4046 */ 4047 static void NativeCrypto_SSL_free(JNIEnv* env, jclass, jint ssl_address) 4048 { 4049 SSL* ssl = to_SSL(env, ssl_address, true); 4050 JNI_TRACE("ssl=%p NativeCrypto_SSL_free", ssl); 4051 if (ssl == NULL) { 4052 return; 4053 } 4054 4055 AppData* appData = toAppData(ssl); 4056 SSL_set_app_data(ssl, NULL); 4057 delete appData; 4058 SSL_free(ssl); 4059 } 4060 4061 /** 4062 * Gets and returns in a byte array the ID of the actual SSL session. 4063 */ 4064 static jbyteArray NativeCrypto_SSL_SESSION_session_id(JNIEnv* env, jclass, 4065 jint ssl_session_address) { 4066 SSL_SESSION* ssl_session = to_SSL_SESSION(env, ssl_session_address, true); 4067 JNI_TRACE("ssl_session=%p NativeCrypto_SSL_SESSION_session_id", ssl_session); 4068 if (ssl_session == NULL) { 4069 return NULL; 4070 } 4071 jbyteArray result = env->NewByteArray(ssl_session->session_id_length); 4072 if (result != NULL) { 4073 jbyte* src = reinterpret_cast<jbyte*>(ssl_session->session_id); 4074 env->SetByteArrayRegion(result, 0, ssl_session->session_id_length, src); 4075 } 4076 JNI_TRACE("ssl_session=%p NativeCrypto_SSL_SESSION_session_id => %p session_id_length=%d", 4077 ssl_session, result, ssl_session->session_id_length); 4078 return result; 4079 } 4080 4081 /** 4082 * Gets and returns in a long integer the creation's time of the 4083 * actual SSL session. 4084 */ 4085 static jlong NativeCrypto_SSL_SESSION_get_time(JNIEnv* env, jclass, jint ssl_session_address) { 4086 SSL_SESSION* ssl_session = to_SSL_SESSION(env, ssl_session_address, true); 4087 JNI_TRACE("ssl_session=%p NativeCrypto_SSL_SESSION_get_time", ssl_session); 4088 if (ssl_session == NULL) { 4089 return 0; 4090 } 4091 // result must be jlong, not long or *1000 will overflow 4092 jlong result = SSL_SESSION_get_time(ssl_session); 4093 result *= 1000; // OpenSSL uses seconds, Java uses milliseconds. 4094 JNI_TRACE("ssl_session=%p NativeCrypto_SSL_SESSION_get_time => %lld", ssl_session, result); 4095 return result; 4096 } 4097 4098 /** 4099 * Gets and returns in a string the version of the SSL protocol. If it 4100 * returns the string "unknown" it means that no connection is established. 4101 */ 4102 static jstring NativeCrypto_SSL_SESSION_get_version(JNIEnv* env, jclass, jint ssl_session_address) { 4103 SSL_SESSION* ssl_session = to_SSL_SESSION(env, ssl_session_address, true); 4104 JNI_TRACE("ssl_session=%p NativeCrypto_SSL_SESSION_get_version", ssl_session); 4105 if (ssl_session == NULL) { 4106 return NULL; 4107 } 4108 const char* protocol = SSL_SESSION_get_version(ssl_session); 4109 JNI_TRACE("ssl_session=%p NativeCrypto_SSL_SESSION_get_version => %s", ssl_session, protocol); 4110 return env->NewStringUTF(protocol); 4111 } 4112 4113 /** 4114 * Gets and returns in a string the cipher negotiated for the SSL session. 4115 */ 4116 static jstring NativeCrypto_SSL_SESSION_cipher(JNIEnv* env, jclass, jint ssl_session_address) { 4117 SSL_SESSION* ssl_session = to_SSL_SESSION(env, ssl_session_address, true); 4118 JNI_TRACE("ssl_session=%p NativeCrypto_SSL_SESSION_cipher", ssl_session); 4119 if (ssl_session == NULL) { 4120 return NULL; 4121 } 4122 const SSL_CIPHER* cipher = ssl_session->cipher; 4123 const char* name = SSL_CIPHER_get_name(cipher); 4124 JNI_TRACE("ssl_session=%p NativeCrypto_SSL_SESSION_cipher => %s", ssl_session, name); 4125 return env->NewStringUTF(name); 4126 } 4127 4128 /** 4129 * Gets and returns in a string the compression method negotiated for the SSL session. 4130 */ 4131 static jstring NativeCrypto_SSL_SESSION_compress_meth(JNIEnv* env, jclass, 4132 jint ssl_ctx_address, 4133 jint ssl_session_address) { 4134 SSL_CTX* ssl_ctx = to_SSL_CTX(env, ssl_ctx_address, true); 4135 SSL_SESSION* ssl_session = to_SSL_SESSION(env, ssl_session_address, true); 4136 JNI_TRACE("ssl_session=%p NativeCrypto_SSL_SESSION_compress_meth ssl_ctx=%p", 4137 ssl_session, ssl_ctx); 4138 if (ssl_ctx == NULL || ssl_session == NULL) { 4139 return NULL; 4140 } 4141 4142 int compress_meth = ssl_session->compress_meth; 4143 if (compress_meth == 0) { 4144 const char* name = "NULL"; 4145 JNI_TRACE("ssl_session=%p NativeCrypto_SSL_SESSION_compress_meth => %s", ssl_session, name); 4146 return env->NewStringUTF(name); 4147 } 4148 4149 int num_comp_methods = sk_SSL_COMP_num(ssl_ctx->comp_methods); 4150 for (int i = 0; i < num_comp_methods; i++) { 4151 SSL_COMP* comp = sk_SSL_COMP_value(ssl_ctx->comp_methods, i); 4152 if (comp->id != compress_meth) { 4153 continue; 4154 } 4155 const char* name = ((comp->method && comp->method->type == NID_zlib_compression) 4156 ? SN_zlib_compression 4157 : (comp->name ? comp->name : "UNKNOWN")); 4158 JNI_TRACE("ssl_session=%p NativeCrypto_SSL_SESSION_compress_meth => %s", ssl_session, name); 4159 return env->NewStringUTF(name); 4160 } 4161 throwSSLExceptionStr(env, "Unknown compression method"); 4162 return NULL; 4163 } 4164 4165 /** 4166 * Frees the SSL session. 4167 */ 4168 static void NativeCrypto_SSL_SESSION_free(JNIEnv* env, jclass, jint ssl_session_address) { 4169 SSL_SESSION* ssl_session = to_SSL_SESSION(env, ssl_session_address, true); 4170 JNI_TRACE("ssl_session=%p NativeCrypto_SSL_SESSION_free", ssl_session); 4171 if (ssl_session == NULL) { 4172 return; 4173 } 4174 SSL_SESSION_free(ssl_session); 4175 } 4176 4177 4178 /** 4179 * Serializes the native state of the session (ID, cipher, and keys but 4180 * not certificates). Returns a byte[] containing the DER-encoded state. 4181 * See apache mod_ssl. 4182 */ 4183 static jbyteArray NativeCrypto_i2d_SSL_SESSION(JNIEnv* env, jclass, jint ssl_session_address) { 4184 SSL_SESSION* ssl_session = to_SSL_SESSION(env, ssl_session_address, true); 4185 JNI_TRACE("ssl_session=%p NativeCrypto_i2d_SSL_SESSION", ssl_session); 4186 if (ssl_session == NULL) { 4187 return NULL; 4188 } 4189 4190 // Compute the size of the DER data 4191 int size = i2d_SSL_SESSION(ssl_session, NULL); 4192 if (size == 0) { 4193 JNI_TRACE("ssl_session=%p NativeCrypto_i2d_SSL_SESSION => NULL", ssl_session); 4194 return NULL; 4195 } 4196 4197 jbyteArray javaBytes = env->NewByteArray(size); 4198 if (javaBytes != NULL) { 4199 ScopedByteArrayRW bytes(env, javaBytes); 4200 if (bytes.get() == NULL) { 4201 JNI_TRACE("ssl_session=%p NativeCrypto_i2d_SSL_SESSION => threw exception", 4202 ssl_session); 4203 return NULL; 4204 } 4205 unsigned char* ucp = reinterpret_cast<unsigned char*>(bytes.get()); 4206 i2d_SSL_SESSION(ssl_session, &ucp); 4207 } 4208 4209 JNI_TRACE("ssl_session=%p NativeCrypto_i2d_SSL_SESSION => size=%d", ssl_session, size); 4210 return javaBytes; 4211 } 4212 4213 /** 4214 * Deserialize the session. 4215 */ 4216 static jint NativeCrypto_d2i_SSL_SESSION(JNIEnv* env, jclass, jbyteArray javaBytes) { 4217 JNI_TRACE("NativeCrypto_d2i_SSL_SESSION bytes=%p", javaBytes); 4218 4219 ScopedByteArrayRO bytes(env, javaBytes); 4220 if (bytes.get() == NULL) { 4221 JNI_TRACE("NativeCrypto_d2i_SSL_SESSION => threw exception"); 4222 return 0; 4223 } 4224 const unsigned char* ucp = reinterpret_cast<const unsigned char*>(bytes.get()); 4225 SSL_SESSION* ssl_session = d2i_SSL_SESSION(NULL, &ucp, bytes.size()); 4226 4227 JNI_TRACE("NativeCrypto_d2i_SSL_SESSION => %p", ssl_session); 4228 return static_cast<jint>(reinterpret_cast<uintptr_t>(ssl_session)); 4229 } 4230 4231 #define FILE_DESCRIPTOR "Ljava/io/FileDescriptor;" 4232 #define SSL_CALLBACKS "Lorg/apache/harmony/xnet/provider/jsse/NativeCrypto$SSLHandshakeCallbacks;" 4233 static JNINativeMethod sNativeCryptoMethods[] = { 4234 NATIVE_METHOD(NativeCrypto, clinit, "()V"), 4235 NATIVE_METHOD(NativeCrypto, ENGINE_load_dynamic, "()V"), 4236 NATIVE_METHOD(NativeCrypto, ENGINE_by_id, "(Ljava/lang/String;)I"), 4237 NATIVE_METHOD(NativeCrypto, ENGINE_init, "(I)I"), 4238 NATIVE_METHOD(NativeCrypto, ENGINE_finish, "(I)I"), 4239 NATIVE_METHOD(NativeCrypto, ENGINE_free, "(I)I"), 4240 NATIVE_METHOD(NativeCrypto, ENGINE_load_private_key, "(ILjava/lang/String;)I"), 4241 NATIVE_METHOD(NativeCrypto, EVP_PKEY_new_DSA, "([B[B[B[B[B)I"), 4242 NATIVE_METHOD(NativeCrypto, EVP_PKEY_new_RSA, "([B[B[B[B[B[B[B[B)I"), 4243 NATIVE_METHOD(NativeCrypto, EVP_PKEY_type, "(I)I"), 4244 NATIVE_METHOD(NativeCrypto, EVP_PKEY_size, "(I)I"), 4245 NATIVE_METHOD(NativeCrypto, EVP_PKEY_free, "(I)V"), 4246 NATIVE_METHOD(NativeCrypto, i2d_PKCS8_PRIV_KEY_INFO, "(I)[B"), 4247 NATIVE_METHOD(NativeCrypto, d2i_PKCS8_PRIV_KEY_INFO, "([B)I"), 4248 NATIVE_METHOD(NativeCrypto, i2d_PUBKEY, "(I)[B"), 4249 NATIVE_METHOD(NativeCrypto, d2i_PUBKEY, "([B)I"), 4250 NATIVE_METHOD(NativeCrypto, RSA_generate_key_ex, "(I[B)I"), 4251 NATIVE_METHOD(NativeCrypto, get_RSA_private_params, "(I)[[B"), 4252 NATIVE_METHOD(NativeCrypto, get_RSA_public_params, "(I)[[B"), 4253 NATIVE_METHOD(NativeCrypto, DSA_generate_key, "(I[B[B[B[B)I"), 4254 NATIVE_METHOD(NativeCrypto, get_DSA_params, "(I)[[B"), 4255 NATIVE_METHOD(NativeCrypto, EVP_MD_CTX_destroy, "(I)V"), 4256 NATIVE_METHOD(NativeCrypto, EVP_MD_CTX_copy, "(I)I"), 4257 NATIVE_METHOD(NativeCrypto, EVP_DigestFinal, "(I[BI)I"), 4258 NATIVE_METHOD(NativeCrypto, EVP_DigestInit, "(I)I"), 4259 NATIVE_METHOD(NativeCrypto, EVP_get_digestbyname, "(Ljava/lang/String;)I"), 4260 NATIVE_METHOD(NativeCrypto, EVP_MD_block_size, "(I)I"), 4261 NATIVE_METHOD(NativeCrypto, EVP_MD_size, "(I)I"), 4262 NATIVE_METHOD(NativeCrypto, EVP_DigestUpdate, "(I[BII)V"), 4263 NATIVE_METHOD(NativeCrypto, EVP_SignInit, "(Ljava/lang/String;)I"), 4264 NATIVE_METHOD(NativeCrypto, EVP_SignUpdate, "(I[BII)V"), 4265 NATIVE_METHOD(NativeCrypto, EVP_SignFinal, "(I[BII)I"), 4266 NATIVE_METHOD(NativeCrypto, EVP_VerifyInit, "(Ljava/lang/String;)I"), 4267 NATIVE_METHOD(NativeCrypto, EVP_VerifyUpdate, "(I[BII)V"), 4268 NATIVE_METHOD(NativeCrypto, EVP_VerifyFinal, "(I[BIII)I"), 4269 NATIVE_METHOD(NativeCrypto, EVP_get_cipherbyname, "(Ljava/lang/String;)I"), 4270 NATIVE_METHOD(NativeCrypto, EVP_CipherInit_ex, "(I[B[BZ)I"), 4271 NATIVE_METHOD(NativeCrypto, EVP_CipherUpdate, "(I[BI[BI)I"), 4272 NATIVE_METHOD(NativeCrypto, EVP_CipherFinal_ex, "(I[BI)I"), 4273 NATIVE_METHOD(NativeCrypto, EVP_CIPHER_CTX_cleanup, "(I)V"), 4274 NATIVE_METHOD(NativeCrypto, RAND_seed, "([B)V"), 4275 NATIVE_METHOD(NativeCrypto, RAND_load_file, "(Ljava/lang/String;J)I"), 4276 NATIVE_METHOD(NativeCrypto, SSL_CTX_new, "()I"), 4277 NATIVE_METHOD(NativeCrypto, SSL_CTX_free, "(I)V"), 4278 NATIVE_METHOD(NativeCrypto, SSL_CTX_set_session_id_context, "(I[B)V"), 4279 NATIVE_METHOD(NativeCrypto, SSL_new, "(I)I"), 4280 NATIVE_METHOD(NativeCrypto, SSL_use_OpenSSL_PrivateKey, "(II)V"), 4281 NATIVE_METHOD(NativeCrypto, SSL_use_PrivateKey, "(I[B)V"), 4282 NATIVE_METHOD(NativeCrypto, SSL_use_certificate, "(I[[B)V"), 4283 NATIVE_METHOD(NativeCrypto, SSL_check_private_key, "(I)V"), 4284 NATIVE_METHOD(NativeCrypto, SSL_set_client_CA_list, "(I[[B)V"), 4285 NATIVE_METHOD(NativeCrypto, SSL_get_mode, "(I)J"), 4286 NATIVE_METHOD(NativeCrypto, SSL_set_mode, "(IJ)J"), 4287 NATIVE_METHOD(NativeCrypto, SSL_clear_mode, "(IJ)J"), 4288 NATIVE_METHOD(NativeCrypto, SSL_get_options, "(I)J"), 4289 NATIVE_METHOD(NativeCrypto, SSL_set_options, "(IJ)J"), 4290 NATIVE_METHOD(NativeCrypto, SSL_clear_options, "(IJ)J"), 4291 NATIVE_METHOD(NativeCrypto, SSL_set_cipher_lists, "(I[Ljava/lang/String;)V"), 4292 NATIVE_METHOD(NativeCrypto, SSL_set_verify, "(II)V"), 4293 NATIVE_METHOD(NativeCrypto, SSL_set_session, "(II)V"), 4294 NATIVE_METHOD(NativeCrypto, SSL_set_session_creation_enabled, "(IZ)V"), 4295 NATIVE_METHOD(NativeCrypto, SSL_set_tlsext_host_name, "(ILjava/lang/String;)V"), 4296 NATIVE_METHOD(NativeCrypto, SSL_get_servername, "(I)Ljava/lang/String;"), 4297 NATIVE_METHOD(NativeCrypto, SSL_do_handshake, "(I" FILE_DESCRIPTOR SSL_CALLBACKS "IZ[B)I"), 4298 NATIVE_METHOD(NativeCrypto, SSL_renegotiate, "(I)V"), 4299 NATIVE_METHOD(NativeCrypto, SSL_get_certificate, "(I)[[B"), 4300 NATIVE_METHOD(NativeCrypto, SSL_get_peer_cert_chain, "(I)[[B"), 4301 NATIVE_METHOD(NativeCrypto, SSL_read, "(I" FILE_DESCRIPTOR SSL_CALLBACKS "[BIII)I"), 4302 NATIVE_METHOD(NativeCrypto, SSL_write, "(I" FILE_DESCRIPTOR SSL_CALLBACKS "[BII)V"), 4303 NATIVE_METHOD(NativeCrypto, SSL_interrupt, "(I)V"), 4304 NATIVE_METHOD(NativeCrypto, SSL_shutdown, "(I" FILE_DESCRIPTOR SSL_CALLBACKS ")V"), 4305 NATIVE_METHOD(NativeCrypto, SSL_free, "(I)V"), 4306 NATIVE_METHOD(NativeCrypto, SSL_SESSION_session_id, "(I)[B"), 4307 NATIVE_METHOD(NativeCrypto, SSL_SESSION_get_time, "(I)J"), 4308 NATIVE_METHOD(NativeCrypto, SSL_SESSION_get_version, "(I)Ljava/lang/String;"), 4309 NATIVE_METHOD(NativeCrypto, SSL_SESSION_cipher, "(I)Ljava/lang/String;"), 4310 NATIVE_METHOD(NativeCrypto, SSL_SESSION_compress_meth, "(II)Ljava/lang/String;"), 4311 NATIVE_METHOD(NativeCrypto, SSL_SESSION_free, "(I)V"), 4312 NATIVE_METHOD(NativeCrypto, i2d_SSL_SESSION, "(I)[B"), 4313 NATIVE_METHOD(NativeCrypto, d2i_SSL_SESSION, "([B)I"), 4314 NATIVE_METHOD(NativeCrypto, SSL_CTX_enable_npn, "(I)V"), 4315 NATIVE_METHOD(NativeCrypto, SSL_CTX_disable_npn, "(I)V"), 4316 NATIVE_METHOD(NativeCrypto, SSL_get_npn_negotiated_protocol, "(I)[B"), 4317 }; 4318 4319 void register_org_apache_harmony_xnet_provider_jsse_NativeCrypto(JNIEnv* env) { 4320 JNI_TRACE("register_org_apache_harmony_xnet_provider_jsse_NativeCrypto"); 4321 // Register org.apache.harmony.xnet.provider.jsse.NativeCrypto methods 4322 jniRegisterNativeMethods(env, "org/apache/harmony/xnet/provider/jsse/NativeCrypto", sNativeCryptoMethods, NELEM(sNativeCryptoMethods)); 4323 } 4324