Мы не являемся экспертами и пытаемся - пока безуспешно - обновить настройки нашего веб-сервера (JBoss-5.1.0.GA) в соответствии со стандартами Диффи-Хеллмана. После запуска теста на https://weakdh.org/sysadmin.htmlнам говорят, что нам нужно «сгенерировать новые 2048-битные параметры Диффи-Хеллмана». В прошлом мы генерировали ключи с помощью Java keytool, но нам не удалось найти никакой информации о создании нового, 2048-битного параметра Диффи-Хеллмана с помощью Java keytool. Кто-нибудь знает, как это сделать, или может указать нам правильное направление? Спасибо!
Вы не можете сделать это с помощью keytool. Первый, keytool
вообще не поддерживает DH. Во-вторых, keytool
не генерирует параметры отдельно для какого-либо алгоритма, только пара секретный ключ / ключ. В-третьих, когда keytool
генерирует пару ключей, он также генерирует самозаверяющий сертификат (который иногда впоследствии заменяется «настоящим» сертификатом, выданным CA), и невозможно создать самоподписанный сертификат для DH, потому что DH не подписывает. Вы мог напишите очень простую (около 10 строк) программу на Java для генерации параметров DH. Но, вероятно, вам это не поможет, потому что:
В любом случае Java не принимает здесь параметры DHE. JbossWS (веб-сервер Jboss, позже Wildfly) является ответвлением Tomcat и обычно использует Java-реализацию SSL / TLS, JSSE. Вплоть до Java 7 JSSE использует свои собственные параметры DHE, которые являются 768-битными, что недопустимо слабо. (За исключением пакетов EXPORT, в которых JSSE подчиняется требованиям RFC для DH-512, которые полностью нарушены, но тогда пакеты EXPORT в любом случае полностью нарушены по конструкции и отключены по умолчанию в Java 7 и более поздних версиях.) Java 8 JSSE позволяет вам контролировать размер параметров DHE, но не фактическое значение.
Используйте Java 8. JSSE в Java 8, но не ранее, по умолчанию использует для DHE 1024 бита, что большинство специалистов считает достаточно сильным, хотя weakdh.org этого не делает, и позволяет указать больше, см. https://docs.oracle.com/javase/8/docs/technotes/guides/security/jsse/JSSERefGuide.html#customizing_dh_keys и для фона https://stackoverflow.com/questions/30352105/how-to-set-custom-dh-group-in-java-sslengine-to-prevent-logjam-attack . Обратите внимание: если у вас есть Java клиенты до Java 8 они будут потерпеть поражение если сервер использует DHE более 1024 бит. Я не знаю других клиентов, у которых есть эта проблема, но проверьте свой, прежде чем вносить изменения.
Включите ECDHE. JSSE в Java 7 и более поздних версиях реализует ECDHE, который не подлежит предварительному вычислению, как DHE, (обычно) с использованием P-256, что более чем достаточно. (Хотя некоторые люди не верят любой кривых NIST ECC, потому что NIST в целом находится под влиянием NSA, хотя ни один из известных мне открытых исходных кодов не выявил проблем именно с кривыми ECC.) В Java 6 фактически есть часть JSSE для ECDHE, но она включена только в том случае, если JVM имеет криптографический «провайдер» для примитивов ECC, чего нет в Java 6. bcprov - * - jdk15on из http://www.bouncycastle.org/ является поставщиком JCE для ряда крипто-примитивов Java, включая ECC, поэтому, если вы добавите банку в свой JRE/lib/ext
и добавить org.bouncycastle.jce.provider.BouncyCastleProvider
к списку в JRE/lib/security/java.security
(или сделать подходящий Security.add/insertProvider()
где-то в начале вашего кода) Java 6 может выполнять ECDHE. Конечно, стоит ли использовать Java 6 - вопрос сам по себе.
Несколько лет назад поддержка ECDHE в браузерах и других клиентах была ненадежной, но сегодня AFAIK все современные браузеры поддерживают ее и предпочитаю это в DHE - то есть в браузере hello перечисляются наборы ECDHE перед наборами DHE, поэтому, если сервер реализует оба, он должен выбрать ECDHE. Клиенты без браузера, возможно, и нет; проверить, чтобы быть уверенным.
Отключите DHE. Вы можете настроить список шифров в атрибуте Connector для исключения шифров DHE; пока вы в нем, также исключите staticDH и staticECDH, которые бесполезны, и (одиночный) DES и (все) "EXPORT", если они есть (Java 6). Это означает, что браузеры и клиенты, которые не поддерживают ECHDE, будут зависать с простым RSA и без прямой секретности, но, по крайней мере, у них есть «текущая» секретность. Я не помню точно, но я думаю, что конфигурация 5.1 Connector все еще была где-то вроде $server/deploy/jbossweb/server.xml
.
Попробуйте родной. Tomcat, с которого, как я уже сказал, начал JbossWS, имеет возможность реализовать HTTPS (SSL / TLS) с использованием «родного», известного как «APR», который на самом деле является OpenSSL внутри, а не JSSE. У меня были переменные успехи в том, чтобы заставить эту опцию работать на JbossWS, и я не помню про 5.1. Если ваш JbossWS имеет работоспособную опцию TC-native и если он может обрабатывать настройку параметров DH, затем использовать openssl для генерации параметров DH и собственных инструкций JbossWS для их настройки.
Фактически вы можете указать собственные параметры DHE с последними версиями Java 8. Это не зависит от приложения (если оно использует реализацию JSSE TLS).
Сначала вам нужно указать размер используемого ключа DHE (-Djdk.tls.ephemeralDHKeySize=1024
или -Djdk.tls.ephemeralDHKeySize=2048
). На сервере будет использоваться предварительно определенная комбинация генератор / первичный преобразователь для DHE. С Java 8 можно использовать только 1024 или 2048, JDK 9 будет поддерживать большие размеры.
Если вы хотите предоставить другую комбинацию, вы можете указать их в jre / lib / security / Java.security с помощью jdk.tls.server.defaultDHEParameters
охранное имущество (с 8у51). Он принимает список параметров (по одному для каждого используемого размера ключа), и он должен содержать штрих и генератор (обычно 2 или 5) в шестнадцатеричном формате.
Если вы использовали openssl dhparam -out dhparam2048.pem 2048
для создания новой пары вы можете использовать openssl dhparam -noout -text -check -in dhparam2048.pem
для чтения и печати этого файла в текстовом режиме. Вам нужно будет скопировать и вставить текст в свойства безопасности Java (используя tr -d ':'
убрать :
между шестнадцатеричным представлением openssl)
Вот пример (только 1024 бис):
>openssl dhparam -in p -check -text -noout | tr -d ':'
PKCS#3 DH Parameters: (1024 bit)
prime:
00f7a63b59edcc43a43df12077f0e9
14129c20a73cef95f919896e608ebc
8722776c948765bbbf61542e118329
6c6ea74ecbded3a93aff77a062aba4
fcf04fc01030e65077f5a802605058
65b836368dd5ea389d77691fac0f2c
f7a161c51c8e97ddecb3cf7f872b0c
cfaf54373d5203edcabc575e871bb1
107ec2f30c78ebf403
generator: 2 (0x2)
DH parameters appear to be ok.
И это приводит к
jdk.tls.server.defaultDHEParameters= \
{ \
00f7a63b59edcc43a43df12077f0e9 \
14129c20a73cef95f919896e608ebc \
8722776c948765bbbf61542e118329 \
6c6ea74ecbded3a93aff77a062aba4 \
fcf04fc01030e65077f5a802605058 \
65b836368dd5ea389d77691fac0f2c \
f7a161c51c8e97ddecb3cf7f872b0c \
cfaf54373d5203edcabc575e871bb1 \
107ec2f30c78ebf403, 2 }
Вам следует перезапустить Сервер и убедиться, что он действительно использует это простое число (а не стандартные), поскольку процесс не прямолинейный, поэтому многое может пойти не так. Значение по умолчанию определено в источнике, для 2048 бита штрих взят из проекта TLS FFDHE.
Например, при запуске openssl s_client я вижу 1024-битное простое число (ffffff ffffffffffc90f ... 5381ffffffffffffffff) при подключении к серверу Java 8 JSSE:
>openssl s_client -msg -cipher DHE-RSA-AES128-SHA256 -connect localhost:1234
...
<<< TLS 1.2 Handshake [length 018f], ServerKeyExchange
0c 00 01 8b 00 80 ff ff ff ff ff ff ff ff c9 0f
da a2 21 68 c2 34 c4 c6 62 8b 80 dc 1c d1 29 02
4e 08 8a 67 cc 74 02 0b be a6 3b 13 9b 22 51 4a
08 79 8e 34 04 dd ef 95 19 b3 cd 3a 43 1b 30 2b
0a 6d f2 5f 14 37 4f e1 35 6d 6d 51 c2 45 e4 85
b5 76 62 5e 7e c6 f4 4c 42 e9 a6 37 ed 6b 0b ff
5c b6 f4 06 b7 ed ee 38 6b fb 5a 89 9f a5 ae 9f
24 11 7c 4b 1f e6 49 28 66 51 ec e6 53 81 ff ff
ff ff ff ff ff ff 00 01 02 ...
Вместо этого вы должны видеть свои настраиваемые параметры при установке.
Параметры по умолчанию для Java 7 (768 бит) будут "e9e642 ... 7a3daf" с длинным генератором "30470ad..529252" как определено в ParameterCache.
У меня была такая же проблема, но от Glassfish.
Во-первых, я бы рекомендовал (если можете) поставить какой-то обратный прокси перед вашим сервером JBoss, поскольку он удалит связь между безопасностью шифра / сертификата и версией Java, которую вы используете.
Чтобы получить длину эфемерного ключа DH, превышающую 768 бит, вам необходимо использовать Java 8. 1024 является новым значением по умолчанию, и вы можете увеличить его до 2048, используя jdk.tls.ephemeralDHKeySize
(подробности: настройка ключей DH). Из того, что я смог найти, в Java нет концепции отдельной регенерации ключевых параметров.