Расписание ключей TLS не работает через Server_Handshake_traffic_secretJAVA

Программисты JAVA общаются здесь
Anonymous
Расписание ключей TLS не работает через Server_Handshake_traffic_secret

Сообщение Anonymous »

Я создаю минимальный сервер TLS 1.3/HTTPS на Java, используя только сокеты.
Я уже создал анализатор ClientHello и ServerHello. При тестировании с OpenSSL ServerHello принимается, но когда приходит время зашифрованного расширения, он терпит неудачу. После отладки с флагом -keylogfile я пришел к выводу, что «Server_Handshake_Traffic_Secret» не один и тот же на сервере (я) и клиенте (OpenSSL).
Я прошел через каждую часть, связанную с расписанием ключей, Transcipt_Hash, Shared_Secret, функциями HKDF (расширение и извлечение), HkdfLabel, контекстом, длиной, солью и IKM и AAD (для AES/GCM). Я все трижды проверил 100 раз.
HkdfLabel.

Код: Выделить всё

public static byte[] expandLabel(byte[] secret, String label, byte[] context, int length)
throws NoSuchAlgorithmException, InvalidKeyException {

// Prefix the label with "tls13 " as per TLS 1.3 spec
String fullLabel = "tls13 " + label;
byte[] labelBytes = fullLabel.getBytes(StandardCharsets.UTF_8);
byte[] contextBytes = (context != null) ? context : new byte[0];

// Total length of the label structure
int hkdfLabelLength = 2 + 1 + labelBytes.length + 1 + contextBytes.length;

if (labelBytes.length < 7 || labelBytes.length > 255) {
throw new IllegalArgumentException("Label length must be between 7 and 255 bytes");
}
if (contextBytes.length > 255) {
throw new IllegalArgumentException("Context length must be between 0 and 255 bytes");
}

ByteBuffer buffer = ByteBuffer.allocate(hkdfLabelLength);

// Set byte order to BIG_ENDIAN for TLS 1.3 spec compliance
// buffer.order(ByteOrder.BIG_ENDIAN);

// Write the output length (uint16)
buffer.putShort((short) length);

// Write the label length (uint8) and the label bytes
buffer.put((byte) labelBytes.length);
buffer.put(labelBytes);

// Write the context length (uint8) and the context bytes
buffer.put((byte) contextBytes.length);
buffer.put(contextBytes);

byte[] hkdfLabel = buffer.array();
return expand(secret, hkdfLabel, length);
}
ECDH/SharedSecret.

Код: Выделить всё

NamedParameterSpec paramSpec = new NamedParameterSpec("X25519");
ECGenParameterSpec ecSpec = new ECGenParameterSpec("X25519");

KeyFactory kf = KeyFactory.getInstance("X25519");
XECPublicKeySpec clientPublicKeySpec = new XECPublicKeySpec(paramSpec,
new BigInteger(1, clientPubKey));
XECPublicKey clientPublicKey = (XECPublicKey) kf.generatePublic(clientPublicKeySpec);

XECPrivateKey secretKey = (XECPrivateKey) key.getPrivate();

KeyAgreement ka = KeyAgreement.getInstance("X25519");
ka.init(secretKey);
ka.doPhase(clientPublicKey, true);
byte[] sharedSecret = ka.generateSecret();
Расписание клавиш.

Код: Выделить всё

KeySchedule ks = new KeySchedule();

ks.early_secret = HKDF.extract(HKDF.zeros, HKDF.zeros);
System.out.println("early_serect: " + Hex.toHexString(ks.early_secret) + " zeros length "+ HKDF.zeros.length);
ks.derived_secret = HKDF.expandLabel(ks.early_secret, "derived", null, 32);

ks.handshake_secret = HKDF.extract(ks.derived_secret, sharedSecret);
// ks.handshake_secret = HKDF.extract(sharedSecret, ks.derived_secret);

ks.server_handshake_traffic_secret = HKDF.expandLabel(ks.handshake_secret, "s hs traffic",trascriptHash, 32);//  255) {
throw new IllegalArgumentException("Cannot expand to more than 255 blocks");
}

byte[] okm = new byte[outputLength];
byte[] previousT = new byte[0];
Mac mac = Mac.getInstance(HMAC_ALGORITHM);
mac.init(new SecretKeySpec(prk, HMAC_ALGORITHM));

int offset = 0;
for (int i = 1; i

Вернуться в «JAVA»