Skip to content

Commit db9afe5

Browse files
author
Annnekkk
committed
Handshake Fix for httpx-tls
1 parent 75e6f07 commit db9afe5

File tree

11 files changed

+305
-21
lines changed

11 files changed

+305
-21
lines changed

README.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
tlslite-ng version 0.9.0b1 (2025-09-25)
1+
tlslite-ng version 0.9.0b2 (2025-09-26)
22

33
[![GitHub CI](https://github.com/tlsfuzzer/tlslite-ng/actions/workflows/ci.yml/badge.svg)](https://github.com/tlsfuzzer/tlslite-ng/actions/workflows/ci.yml)
44
[![Read the Docs](https://img.shields.io/readthedocs/tlslite-ng)](https://tlslite-ng.readthedocs.io/en/latest/)
@@ -622,7 +622,7 @@ Similarly, while delegated credentials have a valid time option, it is not enfor
622622
12 History
623623
===========
624624
625-
0.9.0b1 - 2025-09-25
625+
0.9.0b2 - 2025-09-26
626626
* support for Delegated Credentials (Ganna Starovoytova)
627627
* (Experimental) support for ML-DSA certificates in TLS
628628

docs/conf.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -34,7 +34,7 @@
3434
# The short X.Y version.
3535
version = u'0.9'
3636
# The full version, including alpha/beta/rc tags.
37-
release = u'0.9.0b1'
37+
release = u'0.9.0b2'
3838

3939

4040
# -- General configuration ---------------------------------------------------

setup.py

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@
1111
README = f.read()
1212

1313
setup(name="tlslite-ng",
14-
version="0.9.0b1",
14+
version="0.9.0b2",
1515
author="Alicja Kario",
1616
author_email="[email protected]",
1717
url="https://github.com/tlsfuzzer/tlslite-ng",
@@ -24,7 +24,7 @@
2424
'package1': ['LICENSE', 'README.md']},
2525
install_requires=['ecdsa>=0.18.0b1'],
2626
obsoletes=["tlslite"],
27-
python_requires=">=2.6, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, !=3.4.*, !=3.5.*, !=3.6.*",
27+
python_requires=">=2.6, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, !=3.4.*, !=3.5.*",
2828
classifiers=[
2929
'Development Status :: 5 - Production/Stable',
3030
'Intended Audience :: Developers',
@@ -35,6 +35,7 @@
3535
'Programming Language :: Python :: 2.6',
3636
'Programming Language :: Python :: 2.7',
3737
'Programming Language :: Python :: 3',
38+
'Programming Language :: Python :: 3.6',
3839
'Programming Language :: Python :: 3.7',
3940
'Programming Language :: Python :: 3.8',
4041
'Programming Language :: Python :: 3.9',

tlslite/api.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44
#
55
# See the LICENSE file for legal information regarding use of this file.
66

7-
__version__ = "0.9.0b1"
7+
__version__ = "0.9.0b2"
88
# the whole module is about importing most commonly used methods, for use
99
# by other applications
1010
# pylint: disable=unused-import

tlslite/handshakesettings.py

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -478,7 +478,7 @@ def _init_misc_extensions(self):
478478
self.dc_sig_algs = []
479479
self.dc_valid_time = DC_VALID_TIME
480480

481-
def __init__(self):
481+
def __init__(self, **kwargs):
482482
"""Initialise default values for settings."""
483483
self._init_key_settings()
484484
self._init_misc_extensions()
@@ -490,6 +490,11 @@ def __init__(self):
490490
self.keyExchangeNames = list(KEY_EXCHANGE_NAMES)
491491
self.cipherImplementations = list(CIPHER_IMPLEMENTATIONS)
492492

493+
# Custom attributes for exact JA3 control (added for httpx-tls compatibility)
494+
self.cipher_order = kwargs.get("cipher_order", None)
495+
self.extension_order = kwargs.get("extension_order", None)
496+
self.groups_order = kwargs.get("groups_order", None)
497+
493498
@staticmethod
494499
def _sanityCheckKeySizes(other):
495500
"""Check if key size limits are sane"""
@@ -869,6 +874,11 @@ def validate(self):
869874
other.pskConfigs = self.pskConfigs
870875
other.psk_modes = self.psk_modes
871876

877+
# Copy custom JA3 control attributes (added for httpx-tls compatibility)
878+
other.cipher_order = getattr(self, 'cipher_order', None)
879+
other.extension_order = getattr(self, 'extension_order', None)
880+
other.groups_order = getattr(self, 'groups_order', None)
881+
872882
if not other.certificateTypes:
873883
raise ValueError("No supported certificate types")
874884

tlslite/tlsconnection.py

Lines changed: 20 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -712,21 +712,27 @@ def _clientSendClientHello(self, settings, session, srpUsername,
712712
srpParams, certParams, anonParams,
713713
serverName, nextProtos, reqTack, alpn):
714714
# Initialize acceptable ciphersuites
715-
cipherSuites = [CipherSuite.TLS_EMPTY_RENEGOTIATION_INFO_SCSV]
716-
if srpParams:
717-
cipherSuites += CipherSuite.getSrpAllSuites(settings)
718-
elif certParams:
719-
cipherSuites += CipherSuite.getTLS13Suites(settings)
720-
cipherSuites += CipherSuite.getEcdsaSuites(settings)
721-
cipherSuites += CipherSuite.getEcdheCertSuites(settings)
722-
cipherSuites += CipherSuite.getDheCertSuites(settings)
723-
cipherSuites += CipherSuite.getCertSuites(settings)
724-
cipherSuites += CipherSuite.getDheDsaSuites(settings)
725-
elif anonParams:
726-
cipherSuites += CipherSuite.getEcdhAnonSuites(settings)
727-
cipherSuites += CipherSuite.getAnonSuites(settings)
715+
# Check if exact cipher order is specified (for JA3 fingerprint control)
716+
if hasattr(settings, 'cipher_order') and settings.cipher_order is not None:
717+
# Use exact cipher order specified by httpx-tls for precise JA3 control
718+
cipherSuites = list(settings.cipher_order)
728719
else:
729-
assert False
720+
# Default behavior: add renegotiation info and standard cipher suites
721+
cipherSuites = [CipherSuite.TLS_EMPTY_RENEGOTIATION_INFO_SCSV]
722+
if srpParams:
723+
cipherSuites += CipherSuite.getSrpAllSuites(settings)
724+
elif certParams:
725+
cipherSuites += CipherSuite.getTLS13Suites(settings)
726+
cipherSuites += CipherSuite.getEcdsaSuites(settings)
727+
cipherSuites += CipherSuite.getEcdheCertSuites(settings)
728+
cipherSuites += CipherSuite.getDheCertSuites(settings)
729+
cipherSuites += CipherSuite.getCertSuites(settings)
730+
cipherSuites += CipherSuite.getDheDsaSuites(settings)
731+
elif anonParams:
732+
cipherSuites += CipherSuite.getEcdhAnonSuites(settings)
733+
cipherSuites += CipherSuite.getAnonSuites(settings)
734+
else:
735+
assert False
730736

731737
# Add any SCSVs. These are not real cipher suites, but signaling
732738
# values which reuse the cipher suite field in the ClientHello.

tlslite_ng.egg-info/PKG-INFO

Lines changed: 95 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,95 @@
1+
Metadata-Version: 2.4
2+
Name: tlslite-ng
3+
Version: 0.9.0b1
4+
Summary: Pure python implementation of SSL and TLS.
5+
Home-page: https://github.com/tlsfuzzer/tlslite-ng
6+
Author: Alicja Kario
7+
Author-email: [email protected]
8+
License: LGPLv2
9+
Keywords: ssl,tls,pure-python
10+
Classifier: Development Status :: 5 - Production/Stable
11+
Classifier: Intended Audience :: Developers
12+
Classifier: License :: OSI Approved :: GNU Lesser General Public License v2 (LGPLv2)
13+
Classifier: Operating System :: OS Independent
14+
Classifier: Programming Language :: Python
15+
Classifier: Programming Language :: Python :: 2
16+
Classifier: Programming Language :: Python :: 2.6
17+
Classifier: Programming Language :: Python :: 2.7
18+
Classifier: Programming Language :: Python :: 3
19+
Classifier: Programming Language :: Python :: 3.7
20+
Classifier: Programming Language :: Python :: 3.8
21+
Classifier: Programming Language :: Python :: 3.9
22+
Classifier: Programming Language :: Python :: 3.10
23+
Classifier: Programming Language :: Python :: 3.11
24+
Classifier: Programming Language :: Python :: 3.12
25+
Classifier: Programming Language :: Python :: 3.13
26+
Classifier: Topic :: Security :: Cryptography
27+
Classifier: Topic :: Software Development :: Libraries :: Python Modules
28+
Classifier: Topic :: System :: Networking
29+
Obsoletes: tlslite
30+
Requires-Python: >=2.6, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, !=3.4.*, !=3.5.*, !=3.6.*
31+
License-File: LICENSE
32+
Requires-Dist: ecdsa>=0.18.0b1
33+
Dynamic: author
34+
Dynamic: author-email
35+
Dynamic: classifier
36+
Dynamic: description
37+
Dynamic: home-page
38+
Dynamic: keywords
39+
Dynamic: license
40+
Dynamic: license-file
41+
Dynamic: obsoletes
42+
Dynamic: requires-dist
43+
Dynamic: requires-python
44+
Dynamic: summary
45+
46+
tlslite-ng is a pure python implementation of SSLv3.0, TLS 1.0, TLS 1.1,
47+
TLS 1.2 and TLS 1.3 protocols.
48+
49+
It can use pycrypto, m2crypto and gmp for acceleration of cryptographic
50+
operations but is not dependant upon them.
51+
52+
Functionality implemented include:
53+
- all above mentioned protocols, including support for client certificates
54+
(RFC 6101, RFC 2246, RFC 4346, RFC 5246, RFC 8446 - not complete)
55+
- RSA, RSA-PSS, DSA, and ECDSA certificates
56+
- RC4, 3DES-CBC, AES-CBC, AES-GCM, AES-CCM, AES-CCM_8 and ChaCha20 ciphers
57+
(RFC 5246, RFC 6347, RFC 4492, RFC 5288, RFC 5289, RFC 7539, RFC 7905,
58+
RFC 6655, RFC 7251)
59+
- MD5, SHA1, SHA256 and SHA384 HMACs as well as AEAD mode of operation with
60+
GCM or Poly1305 authenticator
61+
- RSA, DHE_RSA, DHE_DSS, ECDHE_RSA, ECDHE_ECDSA key exchange
62+
- full set of signature hashes (md5, sha1, sha224, sha256, sha384, sha512,
63+
rsa_pss_rsae_sha256, rsa_pss_rsae_sha384 and rsa_pss_rsae_sha512) for
64+
ServerKeyExchange and CertfificateVerify
65+
- secp256r1, secp384r1, secp521r1, secp256k1, secp224r1 and secp192r1 curves
66+
for ECDHE key exchange (support for last two depends on the version of ecdsa
67+
library used)
68+
- x25519 and x448 curves for ECDHE key exchage (RFC 7748. RFC 4492bis)
69+
- anonymous DHE key exchange
70+
- anonymous ECDH key exchange
71+
- PSK and PSK-DH key exchange in TLS 1.3
72+
- session ticket based resumption (RFC 5077) and in TLS 1.3
73+
- post-handshake client authentication in TLS 1.3
74+
- NULL encryption ciphersuites
75+
- FALLBACK_SCSV (RFC 7507)
76+
- encrypt-then-MAC mode of operation for CBC ciphersuites (RFC 7366)
77+
- TACK certificate pinning
78+
- SRP_SHA_RSA and SRP_SHA ciphersuites (RFC 5054)
79+
- Extended Master Secret calculation for TLS connections (RFC 7627)
80+
- padding extension (RFC 7685)
81+
- Keying material exporter (RFC 5705)
82+
- Next Protocol Negotiation
83+
- Application-Layer Protocol Negotiation Extension (RFC 7301)
84+
- FFDHE prime/group negotiation (RFC 7919)
85+
- Heartbeat Extension (RFC 6520)
86+
- Record Size Limit (RFC 8449)
87+
- TLS Certificate Compression (RFC 8879)
88+
- Hybrid ML-KEM key exchage groups (draft-kwiatkowski-tls-ecdhe-mlkem-02)
89+
- support for Brainpool curves in TLS 1.2 and TLS 1.3
90+
- Delegated Credentials (RFC 9345)
91+
- ML-DSA certificates suppport (draft-ietf-tls-mldsa-00)
92+
93+
94+
tlslite-ng aims to be a drop-in replacement for tlslite while providing more
95+
comprehensive set of features and more secure defaults.

0 commit comments

Comments
 (0)