This artifact contains a slimmed-down version of the large-scale scanning setup for detecting session ticket confusion attacks in the wild.
It has been modified to work with a local dummy server setup to demonstrate the functionality.
The original setup was heavily customized for our own infrastructure, so functionality was removed to make it easier to run on a local machine (e.g. running zmap
against Docker containers doesn't work well).
All changes are marked with comments # AE Version
in the code.
Note that this repository relies on a custom fork of zgrab2
and zcrypto
to support the required functionality, which are built using the build_dependencies.sh
script.
The artifact itself consists of a series of (Python) scripts and Docker containers. The instructions here are designed for Ubuntu 25.04, but should be easily adaptable to other Linux distributions.
Make sure that you have cloned the submodules, either by using the --recurse-submodules
flag when cloning or by running:
git submodule init
git submodule update
Nothing, see below.
- Python 3.12+
- Docker
- Docker Compose
- pip
- golang 1.20+
For Ubuntu 25.04, the following commands installs all required dependencies.
If you are using a different distribution, you may need to adapt the package names, as not all versions package the same versions of the dependencies (e.g. Ubuntu 24 does not offer python3.13
).
apt install python3.13-dev python3.13-full python3.13-venv docker.io cmake jq libjudy-dev libgmp-dev libpcap-dev flex byacc libjson-c-dev gengetopt libunistring-dev golang-go curl git
systemctl start docker.service
sudo curl -L "https://github.com/docker/compose/releases/download/v2.35.1/docker-compose-$(uname -s)-$(uname -m)" -o /usr/local/bin/docker-compose
sudo chmod +x /usr/local/bin/docker-compose
- Build required dependencies (our custom fork of
zgrab2
and appropiate versions ofzmap
andzdns
)
sudo ./build_dependencies.sh
sudo
is required to give zmap
access to the network interface.
Check if the build was successful by running the binaries.
./zdns/zdns --help
./zmap/src/zmap --help
./zmapv6/src/zmap --help
./zgrab2_tls13/cmd/zgrab2/zgrab2 --help
Also check that the dummy server and corresponding DNS resolution are working:
sudo ./setup.sh
dig @127.0.0.1 -p 8053 a.com
which should yield two 172.x.0.x
local Docker IP addresses.
- Set up the local dummy servers and DNS
sudo ./setup.sh
- Run the all-in-one script
sudo ./0_all_in_one.sh
- Examine the
analysisdump
folder for the results of the scans. The folder contains a list of all potentially successful resumptions across hosts, grouped by AS. Within, each path./<target IP>/<source IP>/
contains a separate scan result. I.e. the folder./172.19.0.5/172.19.0.3/
contains the different resulting HTML documents when resuming at .5 with a ticket from .3:0_initial.html
is the original page at .3, without a ticket.1_resumed.html
contains the page received by .5 after resumption.2_*_supposed_origin.html
contains the closest HTML match, for1_resumed.html
, based on different metrics._meta.md
summarizes these findings, including which domain we believe to have encountered.
- Observe the effects of different countermeasures by modifying the file
ae-dummy-servers/docker-compose.yml
and re-running steps 1-3. You can activate a countermeasure by uncommenting the corresponding lines in the environment section.
# - "NO_FALLBACK_CERT=1" # fail the handshake if the SNI is unknown
# - "NO_FALLBACK_CONTENT=1" # serve an HTTP error if the SNI is unknown; NB our implementation does not look at the host header at all
# - "NO_FALLBACK_STEK=1" # do not set a STEK if the SNI is unknown
# - "BIND_CERT=1" # bind the certificate to the ticket
# - "BIND_SNI=1" # bind the SNI to the ticket
If you get something like
May 08 17:06:29.447 [FATAL] recv: could not open device wlan0: wlan0: You don't have permission to perform this capture on that device (socket: Operation not permitted)
from zmap
, you need to give zmap
the required permissions (manually) to access the network interface. You can do this by running:
sudo setcap cap_net_raw=eip zmapv6/src/zmap
sudo setcap cap_net_raw=eip zmap/src/zmap
Make sure that your host /etc/hosts
does not contain any entries for {a,b,c,d}.com
, as this may interfere with the DNS setup.
We had to learn this the hard way.
The sleep
for spawning Neo4J may not be sufficient to actually start. Try to increase the sleep delay.
As explained above, this artifact is a slimmed-down version of the original experiments. If you are interested in re-running the original experiments, beware of the resource requirements.
Our setup:
uname -a
: Linux syssec-scanner6 6.1.0-37-amd64 #1 SMP PREEMPT_DYNAMIC Debian 6.1.140-1 (2025-05-22) x86_64 GNU/Linux
64 cores, Intel(R) Xeon(R) Platinum 8462Y+
64 GB RAM
2 TB Storage (our results are about 900 GB)