Мы используем SSL для трафика нашей базы данных (12c). При подключении к базе данных с использованием клиента JDBC (Java 1.8.0_65, ojdbc7) мы получаем ошибку рукопожатия. Наш сервер базы данных использует SSL_RSA_WITH_AES_128_CBC_SHA256 шифр.

java.sql.SQLRecoverableException: IO Error: Received fatal alert: handshake_failure
        at oracle.jdbc.driver.T4CConnection.logon(T4CConnection.java:752) ~[ojdbc7.jar:12.1.0.2.0]
        at oracle.jdbc.driver.PhysicalConnection.connect(PhysicalConnection.java:666) ~[ojdbc7.jar:12.1.0.2.0]
        at oracle.jdbc.driver.T4CDriverExtension.getConnection(T4CDriverExtension.java:32) ~[ojdbc7.jar:12.1.0.2.0]
        at oracle.jdbc.driver.OracleDriver.connect(OracleDriver.java:566) ~[ojdbc7.jar:12.1.0.2.0]
        at java.sql.DriverManager.getConnection(DriverManager.java:664) ~[?:1.8.0_65]
        at java.sql.DriverManager.getConnection(DriverManager.java:247) ~[?:1.8.0_65]
Caused by: javax.net.ssl.SSLHandshakeException: Received fatal alert: handshake_failure
        at sun.security.ssl.Alerts.getSSLException(Alerts.java:192) ~[?:1.8.0_65]
        at sun.security.ssl.Alerts.getSSLException(Alerts.java:154) ~[?:1.8.0_65]
        at sun.security.ssl.SSLSocketImpl.recvAlert(SSLSocketImpl.java:2023) ~[?:1.8.0_65]
        at sun.security.ssl.SSLSocketImpl.readRecord(SSLSocketImpl.java:1125) ~[?:1.8.0_65]
        at sun.security.ssl.SSLSocketImpl.performInitialHandshake(SSLSocketImpl.java:1375) ~[?:1.8.0_65]
        at sun.security.ssl.SSLSocketImpl.writeRecord(SSLSocketImpl.java:747) ~[?:1.8.0_65]
        at sun.security.ssl.AppOutputStream.write(AppOutputStream.java:123) ~[?:1.8.0_65]
        at oracle.net.ns.Packet.send(Packet.java:419) ~[ojdbc7.jar:12.1.0.2.0]
        at oracle.net.ns.ConnectPacket.send(ConnectPacket.java:241) ~[ojdbc7.jar:12.1.0.2.0]
        at oracle.net.ns.NSProtocolStream.negotiateConnection(NSProtocolStream.java:157) ~[ojdbc7.jar:12.1.0.2.0]
        at oracle.net.ns.NSProtocol.connect(NSProtocol.java:264) ~[ojdbc7.jar:12.1.0.2.0]
        at oracle.jdbc.driver.T4CConnection.connect(T4CConnection.java:1452) ~[ojdbc7.jar:12.1.0.2.0]
        at oracle.jdbc.driver.T4CConnection.logon(T4CConnection.java:496) ~[ojdbc7.jar:12.1.0.2.0]

Для анализа мы включили отладку ssl и обнаружили следующее:

 *** ClientHello, TLSv1
RandomCookie:  GMT: 1491604703 bytes = { 8, 77, 210, 159, 243, 108, 135, 13, 187, 223, 121, 238, 236, 46, 76, 255, 76, 12, 130, 135, 233, 99, 154, 136, 70, 38, 132, 176 }
Session ID:  {223, 118, 94, 151, 92, 90, 47, 206, 76, 197, 24, 27, 241, 230, 236, 184, 87, 216, 9, 178, 99, 207, 38, 169, 193, 168, 99, 17, 211, 45, 239, 31}
Cipher Suites: [TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA, TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA, TLS_RSA_WITH_AES_256_CBC_SHA, TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA, TLS_ECDH_RSA_WITH_AES_256_CBC_SHA, TLS_DHE_RSA_WITH_AES_256_CBC_SHA, TLS_DHE_DSS_WITH_AES_256_CBC_SHA, TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA, TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA, TLS_RSA_WITH_AES_128_CBC_SHA, TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA, TLS_ECDH_RSA_WITH_AES_128_CBC_SHA, TLS_DHE_RSA_WITH_AES_128_CBC_SHA, TLS_DHE_DSS_WITH_AES_128_CBC_SHA, TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA, TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA, SSL_RSA_WITH_3DES_EDE_CBC_SHA, TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA, TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA, SSL_DHE_RSA_WITH_3DES_EDE_CBC_SHA, SSL_DHE_DSS_WITH_3DES_EDE_CBC_SHA, TLS_EMPTY_RENEGOTIATION_INFO_SCSV]
Compression Methods:  { 0 }
Extension elliptic_curves, curve names: {secp256r1, sect163k1, sect163r2, secp192r1, secp224r1, sect233k1, sect233r1, sect283k1, sect283r1, secp384r1, sect409k1, sect409r1, secp521r1, sect571k1, sect571r1, secp160k1, secp160r1, secp160r2, sect163r1, secp192k1, sect193r1, sect193r2, secp224k1, sect239k1, secp256k1}
Extension ec_point_formats, formats: [uncompressed]
***
main, WRITE: TLSv1 Handshake, length = 183
main, READ: TLSv1 Handshake, length = 81

Мы могли видеть, что клиент Java не поддерживает SSL_RSA_WITH_AES_128_CBC_SHA256 шифр. Итак, мы установили банки JDK8 Unlimited Strength. Даже после этого Java-клиент также не поддерживает шифр SSL_RSA_WITH_AES_128_CBC_SHA256.

Мои запросы:

  1. Поскольку шифр использует 256-битный алгоритм, после того как я предоставил баночки Unlimited Strength, почему Java-клиент все еще не поддерживает вышеупомянутый шифр.

  2. Как я мог видеть из документов Oracle, здесь сказано, что указанный выше шифр поддерживается по умолчанию в JDK 1.8. Тогда также, почему клиент Java не показывает, что он игнорирует вышеупомянутый шифр.

Я не понимаю, чего мне здесь не хватает. Любое руководство по этому вопросу высоко ценится.

< Сильный > ИЗМЕНИТЬ

Как предложено в комментарии, использование ojdbc1.8 решило проблему. Тем не менее, я получил еще пару вопросов по этому вопросу:

  1. Я вижу, что рукопожатие теперь происходит с TLSv1.2, ранее это происходило с TLSv1. Что я понял из этой ссылки это JDK 1.8 по умолчанию поддерживает TLSv1.2. Почему он не использовал то же самое ранее.

  2. Относительно Cipher Suite, теперь с ojdbc8, передаются дополнительные шифры, которые также включают SSL_RSA_WITH_AES_128_CBC_SHA256 шифр, которого раньше не было с jar ojdbc7. Эта Oracle ссылка по умолчанию говорит о JDK 1.8 поддерживает этот шифр. Но изначально он не поддерживается с ojdbc7. Я также не понимал, как создание ojdbc8 имеет значение.

0
Somnath Musib 19 Окт 2017 в 08:45

3 ответа

Лучший ответ

Вышеуказанная ошибка связана с Oracle ошибка 19030178. Эта SO link подробно объясняет эти шаги ,

В банке ojdbc7 мы применили патч для bug 19030178 и добавили необходимые параметры -D. С этими изменениями все заработало правильно.

0
musibs 20 Окт 2017 в 04:12

Исправленный файл ojdbc7.jar для ошибки 19030178 находится в OTN. Вы можете скачать это, а также, используя драйвер 12.2 также будет работать.

Кроме того, обратитесь к этой записи "Подключение к базе данных через TLSv1. 2 с использованием JDBC thin и JKS "

1
Nirmala 24 Окт 2017 в 17:44

Изменение используемой библиотеки на ojdbc8 решило проблему.

1
Cyphrags 20 Окт 2017 в 00:27