<?xml version="1.0" encoding="utf-8"?>
<feed xmlns="http://www.w3.org/2005/Atom"><title>Peakhour.IO - JA3</title><link href="https://www.peakhour.io/" rel="alternate"></link><link href="https://www.peakhour.io/feeds/tag/ja3.atom.xml" rel="self"></link><id>https://www.peakhour.io/</id><updated>2026-08-30T09:00:00+10:00</updated><entry><title>Public Fingerprint Databases Are Not Ground Truth</title><link href="https://www.peakhour.io/blog/public-fingerprint-databases-are-not-ground-truth/" rel="alternate"></link><published>2026-08-30T09:00:00+10:00</published><updated>2026-08-30T09:00:00+10:00</updated><author><name>AC</name></author><id>tag:www.peakhour.io,2026-08-30:/blog/public-fingerprint-databases-are-not-ground-truth/</id><summary type="html">&lt;p&gt;We reviewed the main public fingerprint resources. The formats are open, but current application labels and auditable ground truth remain scarce.&lt;/p&gt;</summary><content type="html">&lt;p&gt;Network fingerprint formats are public. Reliable labels are not.&lt;/p&gt;
&lt;p&gt;We reviewed the main public JA3, JA4, TLS, TCP, HTTP, SSH, JARM, DHCP, operating-system and service-fingerprint resources. The result was not one large ecosystem of interchangeable databases. It was a set of much narrower things: small mapping samples, old signature lists, active-probe rules, malware feeds, account services and a large observatory whose TLS records are almost entirely unlabelled.&lt;/p&gt;
&lt;p&gt;That is not a criticism of the maintainers. It is a warning about what happens after a fingerprint field reaches a dashboard. A precise-looking value invites a precise-looking name. The evidence behind that name may be a controlled capture, a best guess from 2018, a community submission or a malware sandbox observation that was never compared with benign traffic.&lt;/p&gt;
&lt;p&gt;Those labels should not produce the same decision.&lt;/p&gt;
&lt;h2&gt;The largest public TLS database has almost no TLS labels&lt;/h2&gt;
&lt;p&gt;The relaunched &lt;a href="https://tlsfingerprint.io/"&gt;TLS Fingerprint Observatory&lt;/a&gt; is an unusually valuable public resource. It exposes more than a million distinct TLS fingerprints and billions of passive observations from the University of Colorado Boulder and Merit Network. Records can include first and last seen, counts by source, cipher suites, extensions, groups, signature algorithms, ALPN and other parsed fields.&lt;/p&gt;
&lt;p&gt;At the time of our review, essentially none of the TLS fingerprints had implementation labels.&lt;/p&gt;
&lt;p&gt;That fact makes the observatory more credible, not less. The collection can answer prevalence and protocol-evolution questions without pretending it knows which application created every handshake. Its smaller QUIC corpus has several hundred controlled labels, often tied to generated capture files.&lt;/p&gt;
&lt;p&gt;The limitation is equally clear. A prevalence database cannot become a browser or malware classifier merely because its records are detailed. The labels require another source of truth.&lt;/p&gt;
&lt;h2&gt;The public JA4 database is a sample, not JA4DB&lt;/h2&gt;
&lt;p&gt;FoxIO maintains &lt;a href="https://ja4db.foxio.io/"&gt;JA4DB&lt;/a&gt;, a hosted service covering several JA4-family methods, applications and detection guidance. It is the closest current service to a multi-surface mapping database.&lt;/p&gt;
&lt;p&gt;The public file most people can inspect is different. FoxIO's &lt;a href="https://github.com/FoxIO-LLC/ja4/blob/main/ja4plus-mapping.csv"&gt;&lt;code&gt;ja4plus-mapping.csv&lt;/code&gt;&lt;/a&gt; contains 66 data rows. Only 35 carry a core JA4 value; the other JA4+ columns are sparser.&lt;/p&gt;
&lt;p&gt;That file is useful documentation. It shows how an application, library, device, operating system and several network observations can sit in one row. It is not broad enough to serve as a general browser, bot or malware catalogue.&lt;/p&gt;
&lt;p&gt;The hosted service is now account-oriented. Its bulk-data licence and per-record provenance are not publicly clear enough to call it an open database. Core JA4's BSD licence does not automatically cover the hosted labels, and it does not cover all other JA4+ methods under the same terms.&lt;/p&gt;
&lt;h2&gt;The open JA3 mappings are mostly historical&lt;/h2&gt;
&lt;p&gt;Salesforce's archived &lt;a href="https://github.com/salesforce/ja3/tree/master/lists"&gt;JA3 lists&lt;/a&gt; contain roughly 159 application mappings for macOS and Linux. The repository describes them as example or best-guess material. They have no per-row capture date, client version, source PCAP or confidence.&lt;/p&gt;
&lt;p&gt;Trisul's &lt;a href="https://github.com/trisulnsm/ja3prints"&gt;ja3prints&lt;/a&gt; is larger: 626 JSONL mappings assembled from Salesforce examples, malware-traffic-analysis captures, FingerprinTLS and browser additions. Its last update was in 2018, and the combined dataset does not have a clear repository-wide licence.&lt;/p&gt;
&lt;p&gt;The historical &lt;a href="https://github.com/LeeBrotherston/tls-fingerprinting"&gt;FingerprinTLS&lt;/a&gt; database preserves richer ClientHello fields than JA3, which makes it valuable for research. It is now archived, and many records lack consistent capture dates, operating-system evidence and confidence.&lt;/p&gt;
&lt;p&gt;These sources still matter. They document the lineage and can help with an older incident. They should not silently become current application ground truth.&lt;/p&gt;
&lt;h2&gt;Rules are not observations&lt;/h2&gt;
&lt;p&gt;Some of the strongest public databases are actually matcher corpora.&lt;/p&gt;
&lt;p&gt;&lt;a href="https://github.com/nmap/nmap/blob/master/nmap-os-db"&gt;Nmap's OS database&lt;/a&gt; contains actively maintained probe-response signatures. &lt;a href="https://github.com/nmap/nmap/blob/master/nmap-service-probes"&gt;Nmap service probes&lt;/a&gt; combine test payloads with regular expressions that extract products and versions. &lt;a href="https://github.com/rapid7/recog"&gt;Rapid7 Recog&lt;/a&gt; maintains XML signatures for SSH, HTTP, SNMP, favicons, JARM and other surfaces. p0f's &lt;code&gt;p0f.fp&lt;/code&gt; contains passive TCP and HTTP traits, although its upstream corpus is now dated.&lt;/p&gt;
&lt;p&gt;These resources can be excellent at their stated job. A rule match means that a response satisfied the signature. It does not establish population prevalence, exclusivity or a particular process behind the connection.&lt;/p&gt;
&lt;p&gt;Flattening a matcher result into the same table as an observed application mapping discards that distinction.&lt;/p&gt;
&lt;h2&gt;Malware observation is not malware identity&lt;/h2&gt;
&lt;p&gt;SSLBL publishes a &lt;a href="https://sslbl.abuse.ch/blacklist/"&gt;JA3 blacklist&lt;/a&gt; under CC0. It records fingerprints observed while analysing more than 25 million malware PCAPs and offers both CSV and Suricata rules.&lt;/p&gt;
&lt;p&gt;SSLBL also says the values were not tested against known-good traffic and may cause substantial false positives.&lt;/p&gt;
&lt;p&gt;That warning is part of the data. A row supports this statement:&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;malware samples assigned this family label produced this JA3
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

&lt;p&gt;It does not support this statement:&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;every connection with this JA3 is that malware
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

&lt;p&gt;Shared libraries make the second statement unsafe. Cisco's &lt;a href="https://arxiv.org/abs/2009.01939"&gt;destination-context research&lt;/a&gt; examined public malware JA3 indicators and found that many were more strongly associated with benign processes in its enterprise observations.&lt;/p&gt;
&lt;p&gt;VirusTotal's behavioural pivots have the same boundary. Files sharing a JA4 may be related malware, come from one developer or merely use the same TLS library. The pivot begins an investigation; it does not finish one.&lt;/p&gt;
&lt;h2&gt;Mercury publishes the schema, not the labels&lt;/h2&gt;
&lt;p&gt;Cisco Mercury offers one of the clearest public designs for a fingerprint knowledge base. Its &lt;a href="https://github.com/cisco/mercury/blob/main/doc/resources.md"&gt;resource documentation&lt;/a&gt; describes mappings from fingerprints to candidate processes, process counts, operating-system observations and destinations. The classifier can use destination address, port and server name to rank those candidates.&lt;/p&gt;
&lt;p&gt;The current Cisco-labelled resource database is not in the public repository.&lt;/p&gt;
&lt;p&gt;This is an honest architectural boundary. The NPF format, collector and database contract are inspectable. The production labels depend on continuously collected endpoint, network and malware-analysis data that Cisco does not publish as an open corpus.&lt;/p&gt;
&lt;h2&gt;What is actually missing&lt;/h2&gt;
&lt;p&gt;The public ecosystem does not mainly need another hash list. It needs evidence attached to each mapping:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;the raw or reversible fingerprint;&lt;/li&gt;
&lt;li&gt;the method and implementation version;&lt;/li&gt;
&lt;li&gt;an independent label source;&lt;/li&gt;
&lt;li&gt;capture position and environment;&lt;/li&gt;
&lt;li&gt;first and last seen;&lt;/li&gt;
&lt;li&gt;observation count;&lt;/li&gt;
&lt;li&gt;competing labels;&lt;/li&gt;
&lt;li&gt;confidence and review state;&lt;/li&gt;
&lt;li&gt;a usable dataset licence.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Almost none of the public resources supplies all of these. Some optimise for scale, some for current labels, some for inspectability and some for rules that can run in an existing scanner.&lt;/p&gt;
&lt;p&gt;The practical response is to preserve those categories. Use an observatory for prevalence, a matcher corpus for response signatures, a threat feed for malware observations, and a mapping database for candidate labels. Then validate the result against local evidence before it reaches enforcement.&lt;/p&gt;
&lt;p&gt;The full directory is in &lt;a href="/learning/fingerprinting/public-network-fingerprint-databases/"&gt;Public Network Fingerprint Databases and What They Cover&lt;/a&gt;. The evaluation checklist is in &lt;a href="/learning/fingerprinting/how-to-evaluate-a-fingerprint-database/"&gt;How to Evaluate a Network Fingerprint Database&lt;/a&gt;.&lt;/p&gt;</content><category term="Security"></category><category term="Network Fingerprinting"></category><category term="TLS Fingerprinting"></category><category term="JA3"></category><category term="JA4"></category><category term="Threat Intelligence"></category></entry><entry><title>A Network Fingerprint Is a Cohort, Not a Client</title><link href="https://www.peakhour.io/blog/fingerprint-is-a-cohort-not-a-client/" rel="alternate"></link><published>2026-08-09T09:00:00+10:00</published><updated>2026-08-09T09:00:00+10:00</updated><author><name>AC</name></author><id>tag:www.peakhour.io,2026-08-09:/blog/fingerprint-is-a-cohort-not-a-client/</id><summary type="html">&lt;p&gt;TLS fingerprints group similar protocol implementations. They do not prove which application, device or person made a request.&lt;/p&gt;</summary><content type="html">&lt;p&gt;A TLS fingerprint usually tells you that two connections look alike under a particular set of rules. That is useful. It is not the same as showing that they came from the same client.&lt;/p&gt;
&lt;p&gt;The distinction becomes obvious when a common TLS library sits underneath many programs. Those programs can offer the same protocol version, cipher suites, extensions and signature algorithms. A fingerprint built from those fields groups them together even though their purpose, owner and risk are different.&lt;/p&gt;
&lt;p&gt;The reverse also happens. One application can generate several fingerprints after a browser update, operating-system change, feature rollout or configuration difference. A fixed application name does not imply a fixed ClientHello.&lt;/p&gt;
&lt;p&gt;The safest mental model is a cohort: traffic that looks the same after a fingerprint method has selected and normalised its inputs.&lt;/p&gt;
&lt;h2&gt;The method defines the cohort&lt;/h2&gt;
&lt;p&gt;JA3 preserves the order of its selected ClientHello feature lists. Change the order and the MD5 value changes. JA4 sorts selected identifiers before calculating two of its components, so permutations that split a JA3 cohort may remain grouped under JA4.&lt;/p&gt;
&lt;p&gt;Cisco Mercury can preserve more packet-derived structure in its full Network Protocol Fingerprint. Different Mercury rule versions also make different normalisation choices. A &lt;code&gt;tls/2&lt;/code&gt; value is therefore not just a longer spelling of JA4. It is the result of another feature-selection contract.&lt;/p&gt;
&lt;p&gt;This means there is no format-independent "real fingerprint" hiding underneath the tools. Each method answers its own equivalence question: which differences count, and which should be ignored?&lt;/p&gt;
&lt;p&gt;Our &lt;a href="/blog/one-clienthello-ja3-ja4-mercury-lab/"&gt;same-PCAP lab&lt;/a&gt; demonstrates that point without relying on a hypothetical browser. The three tools inspect the same ClientHello and produce representations with different retained detail.&lt;/p&gt;
&lt;h2&gt;Common does not mean safe&lt;/h2&gt;
&lt;p&gt;A popular browser fingerprint will naturally appear in a great deal of legitimate traffic. An attacker can also use a browser, drive one through automation, or imitate its TLS stack. Matching a common browser value therefore says little about intent by itself.&lt;/p&gt;
&lt;p&gt;The opposite shortcut is just as risky. An uncommon fingerprint is not proof of malware. Internal tools, older mobile applications, embedded devices, accessibility software and regional client variants can all be rare in one dataset.&lt;/p&gt;
&lt;p&gt;Rarity is relative to the observation point. A fingerprint that is common across a public content site may be unusual on an administrative API. A value common in one country, network or month may be rare in another.&lt;/p&gt;
&lt;h2&gt;Capture point changes what you see&lt;/h2&gt;
&lt;p&gt;TLS fingerprinting only works where the relevant handshake is visible. At an origin behind a CDN or reverse proxy, the TLS connection may have been terminated and replaced upstream. The origin can then observe the proxy's connection rather than the end user's ClientHello unless the edge explicitly forwards a derived fingerprint.&lt;/p&gt;
&lt;p&gt;That forwarded value also needs provenance. Operators should know which implementation and format version produced it, whether it came from the client-facing connection, and whether middleware transformed or sampled the traffic.&lt;/p&gt;
&lt;p&gt;Without that information, two values that look compatible may have been generated under different rules. Fastly has documented how implementation differences can undermine the portability promised by a shared hash in &lt;a href="https://www.fastly.com/blog/the-state-of-tls-fingerprinting-whats-working-what-isnt-and-whats-next"&gt;The State of TLS Fingerprinting&lt;/a&gt;.&lt;/p&gt;
&lt;h2&gt;Context can improve an inference&lt;/h2&gt;
&lt;p&gt;Cisco's Mercury research is helpful because it does not hide the ambiguity. The 2020 destination-context paper reports that one TLS fingerprint often maps to tens or hundreds of process names. Its classifier adds destination IP address, port and server name, backed by a labelled knowledge base, to rank the possible processes.&lt;/p&gt;
&lt;p&gt;That is stronger than treating a bare fingerprint as an application name. It is still conditional. Change the environment, the age of the knowledge base, the available destination fields or the software population and the probabilities can change. The paper's reported accuracy belongs to its datasets and experimental design, not to every network that runs Mercury.&lt;/p&gt;
&lt;p&gt;JA4 deployments often add context too. A security platform might combine the JA4 value with request rate, geography, path, account state or observations from other customers. Those extra fields are not secretly part of JA4. They are features in the surrounding detection system.&lt;/p&gt;
&lt;h2&gt;Use fingerprints where grouping helps&lt;/h2&gt;
&lt;p&gt;Fingerprints earn their place when grouping similar connections improves an investigation or control. Examples include:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;counting login failures across rotating IP addresses;&lt;/li&gt;
&lt;li&gt;finding a TLS stack that appeared at the start of an incident;&lt;/li&gt;
&lt;li&gt;comparing a claimed browser with HTTP and browser-side evidence;&lt;/li&gt;
&lt;li&gt;monitoring drift after a client or library release;&lt;/li&gt;
&lt;li&gt;selecting traffic for review before writing a narrower rule.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;For the decision and enforcement consequences, see &lt;a href="/blog/fingerprints-are-evidence-not-identity/"&gt;Fingerprints are evidence, not identity&lt;/a&gt;. The protocol-specific conclusion here is narrower: a matching TLS fingerprint places connections in a cohort defined by one method. It cannot tell you, on its own, who is on the other end.&lt;/p&gt;
&lt;p&gt;The practitioner follow-up, &lt;a href="/blog/using-network-fingerprints-in-bot-and-rate-limit-decisions/"&gt;Using network fingerprints in bot and rate-limit decisions&lt;/a&gt;, turns that boundary into a route-scoped policy and rollback model.&lt;/p&gt;</content><category term="Security"></category><category term="TLS Fingerprinting"></category><category term="JA3"></category><category term="JA4"></category><category term="Cisco Mercury"></category><category term="Network Fingerprinting"></category><category term="Bot Management"></category></entry><entry><title>Two Lineages of TLS Fingerprinting: JA3, JA4 and Cisco Mercury</title><link href="https://www.peakhour.io/blog/two-lineages-tls-fingerprinting/" rel="alternate"></link><published>2026-07-26T09:00:00+10:00</published><updated>2026-07-26T09:00:00+10:00</updated><author><name>AC</name></author><id>tag:www.peakhour.io,2026-07-26:/blog/two-lineages-tls-fingerprinting/</id><summary type="html">&lt;p&gt;JA4 did not descend from Cisco Mercury. The two projects come from different strands of TLS fingerprinting research and solve different operational problems.&lt;/p&gt;</summary><content type="html">&lt;p&gt;It is tempting to draw the history of TLS fingerprinting as a single line: JA3, then JA4, with Cisco Mercury somewhere nearby. That version is tidy. It is also wrong.&lt;/p&gt;
&lt;p&gt;Two strands of work developed around the same observation: a TLS ClientHello exposes enough information to say something useful about the software that created it. One strand concentrated on portable identifiers that could be logged and exchanged. The other concentrated on retaining protocol structure and combining it with evidence that could improve classification.&lt;/p&gt;
&lt;p&gt;JA3 and JA4 belong mainly to the first strand. Cisco Mercury belongs mainly to the second. For the technical work that preceded JA3, see &lt;a href="/blog/before-ja3-tls-fingerprinting-history/"&gt;how TLS handshakes became fingerprints&lt;/a&gt;.&lt;/p&gt;
&lt;h2&gt;Before JA3&lt;/h2&gt;
&lt;p&gt;Passive fingerprinting predates TLS. Tools such as p0f identified operating-system characteristics from TCP/IP behaviour without sending probes to the target. Researchers later applied the same instinct to fields exposed during SSL and TLS negotiation.&lt;/p&gt;
&lt;p&gt;In 2009, Ivan Ristić published an &lt;a href="https://blog.ivanristic.com/2009/06/http-client-fingerprinting-using-ssl-handshake-analysis.html"&gt;SSL handshake fingerprinting experiment&lt;/a&gt; that compared ClientHello messages from web clients. Marek Majkowski followed with a &lt;a href="https://idea.popcount.org/2012-06-17-ssl-fingerprinting-for-p0f/"&gt;TLS fingerprinting patch for p0f&lt;/a&gt; in 2012. Lee Brotherston's &lt;a href="https://github.com/LeeBrotherston/tls-fingerprinting"&gt;FingerprinTLS&lt;/a&gt; later provided tools and a database for creating and matching TLS fingerprints.&lt;/p&gt;
&lt;p&gt;Salesforce's JA3 project drew directly on that work. JA3 serialised five ordered ClientHello feature groups, removed GREASE values and calculated an MD5 digest. The result was compact enough to put in a log, share in threat intelligence or match in a rule. The &lt;a href="https://github.com/salesforce/ja3"&gt;archived JA3 repository&lt;/a&gt; documents both the format and its debt to FingerprinTLS.&lt;/p&gt;
&lt;p&gt;JA3's compactness came with a cost. A digest does not explain why two clients differ. Ordered inputs also meant that harmless permutation could produce a different value. Most importantly, a matching digest did not prove that the traffic came from one application. Programs built on a shared TLS library could produce the same ClientHello.&lt;/p&gt;
&lt;h2&gt;The JA4 branch&lt;/h2&gt;
&lt;p&gt;FoxIO introduced JA4 in 2023 after Chrome began permuting TLS extension order. Peakhour saw the practical effect of that change in our &lt;a href="/blog/tls-extension-randomisation/"&gt;Chrome extension-randomisation analysis&lt;/a&gt;: a representation that preserved extension order split one common browser family into a large number of values.&lt;/p&gt;
&lt;p&gt;JA4 canonicalises selected ClientHello features before hashing them. Its &lt;code&gt;a_b_c&lt;/code&gt; structure keeps a readable summary in the first section, a digest of sorted cipher identifiers in the second, and a digest derived from extensions and signature algorithms in the third. This makes the components useful independently. An analyst can group on part of a JA4 value without pretending every field is identical.&lt;/p&gt;
&lt;p&gt;That is deliberate lossy compression. JA4 is useful because it throws away distinctions its designers judged unstable or unhelpful for this job. It is not a reversible rendering of the ClientHello, and its truncated SHA-256 sections do not provide a measure of semantic distance. The exact format is set out in the &lt;a href="https://github.com/FoxIO-LLC/ja4/blob/main/technical_details/JA4.md"&gt;FoxIO JA4 technical specification&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;JA4 is one method. JA4+ is the name used for a wider family that includes server, HTTP, TCP, SSH, certificate and other fingerprints. Those methods do not all share JA4's licence, which matters if the fingerprints will be built into a commercial service.&lt;/p&gt;
&lt;h2&gt;The Cisco research branch&lt;/h2&gt;
&lt;p&gt;Cisco's work took a different route. In 2016, Blake Anderson, Subharthi Paul and David McGrew studied how observable TLS features could help distinguish malware from enterprise traffic without decrypting it. Their paper, &lt;a href="https://arxiv.org/abs/1607.01639"&gt;Deciphering Malware's Use of TLS&lt;/a&gt;, also dealt with an awkward issue that still matters: malware-sandbox data can bias a classifier.&lt;/p&gt;
&lt;p&gt;Anderson and McGrew's 2017 &lt;a href="https://arxiv.org/abs/1706.08003"&gt;operating-system fingerprinting research&lt;/a&gt; combined evidence from TCP/IP, TLS and HTTP across multiple sessions. The point was not to mint a universally portable hash. It was to ask whether several kinds of passive evidence, accumulated over time, reduced uncertainty about the endpoint.&lt;/p&gt;
&lt;p&gt;The same multi-protocol approach appears in Cisco's Joy and Mercury projects. Mercury's Network Protocol Fingerprinting format represents selected protocol features as a tree of hexadecimal byte strings. The full form retains structure. Its naming can state the protocol and fingerprint rule version. An optional compact hash can be used where a fixed-length value is more practical. Cisco's current &lt;a href="https://github.com/cisco/mercury/blob/main/doc/npf.md"&gt;draft NPF specification&lt;/a&gt; defines fingerprints for TLS, QUIC, TCP, HTTP, SSH and other protocols.&lt;/p&gt;
&lt;p&gt;Mercury also keeps fingerprint generation separate from process classification. That distinction is easy to miss.&lt;/p&gt;
&lt;h2&gt;A fingerprint and a label are different things&lt;/h2&gt;
&lt;p&gt;In Cisco's 2020 paper, &lt;a href="https://arxiv.org/abs/2009.01939"&gt;Accurate TLS Fingerprinting Using Destination Context and Knowledge Bases&lt;/a&gt;, the authors found that common TLS fingerprints mapped to many processes. For the 100 most prevalent fingerprints in their May 2020 data, the median was 24.5 process names per fingerprint.&lt;/p&gt;
&lt;p&gt;Their response was not a longer hash. They combined the fingerprint with destination address, port and server name, then used a weighted naïve Bayes classifier backed by a continually updated knowledge base.&lt;/p&gt;
&lt;p&gt;That produces an inference, not a property embedded in the fingerprint string. The result depends on labelled observations, their age, the monitored environment and the destination evidence available for the connection. The open Mercury repository can generate fingerprints without possessing Cisco's production knowledge base.&lt;/p&gt;
&lt;p&gt;This is the clearest difference between the two lineages:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;JA3 and JA4 define portable representations for selected TLS observations.&lt;/li&gt;
&lt;li&gt;Mercury NPF retains a richer, versioned representation that can be fed into a separate analysis system.&lt;/li&gt;
&lt;li&gt;Mercury's destination-context classifier is another layer again.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;None of these layers proves who made a request.&lt;/p&gt;
&lt;h2&gt;Where the lineages meet&lt;/h2&gt;
&lt;p&gt;The projects respond to many of the same protocol changes. Both JA4 and recent Mercury formats sort selected TLS fields to reduce instability caused by permutation. Both deal explicitly with GREASE. Both recognise that operators need compact values for logs as well as enough detail to investigate differences.&lt;/p&gt;
&lt;p&gt;They make different trade-offs. JA4 is convenient for grouping and interchange. Mercury's full NPF form is better suited to inspection and to analysis that benefits from retained structure. JA4's wider family adds fingerprints for other observations, while Mercury is also a packet metadata collector and protocol-analysis library. Comparing only the length of their hashes misses most of the design.&lt;/p&gt;
&lt;p&gt;The lab article makes that concrete. In &lt;a href="/blog/one-clienthello-ja3-ja4-mercury-lab/"&gt;one ClientHello, three fingerprints&lt;/a&gt;, we run JA3, JA4 and Mercury against the same packet capture, record the exact tool versions and compare what each output preserves.&lt;/p&gt;</content><category term="Security"></category><category term="TLS Fingerprinting"></category><category term="JA3"></category><category term="JA4"></category><category term="Cisco Mercury"></category><category term="Network Fingerprinting"></category><category term="Threat Detection"></category></entry><entry><title>Before JA3: How TLS Handshakes Became Fingerprints</title><link href="https://www.peakhour.io/blog/before-ja3-tls-fingerprinting-history/" rel="alternate"></link><published>2026-07-19T09:00:00+10:00</published><updated>2026-07-19T09:00:00+10:00</updated><author><name>AC</name></author><id>tag:www.peakhour.io,2026-07-19:/blog/before-ja3-tls-fingerprinting-history/</id><summary type="html">&lt;p&gt;JA3 made TLS fingerprints easy to log and share, but the technical ideas behind it had already been tested in SSL Labs experiments, a p0f patch and FingerprinTLS.&lt;/p&gt;</summary><content type="html">&lt;p&gt;JA3 is often treated as the beginning of TLS fingerprinting. It was not. Its real contribution was narrower and, operationally, just as important: JA3 took a set of ideas that had been explored for years and turned them into a small identifier that ordinary security tools could carry.&lt;/p&gt;
&lt;p&gt;The path to that format runs through an SSL Labs experiment in 2009, an experimental p0f extension in 2012 and Lee Brotherston's FingerprinTLS work in 2015. Each step answered a different question. What can the cleartext handshake reveal? Which details survive often enough to identify a client? How do you turn those details into something an analyst can match? And, finally, how do you make the result portable?&lt;/p&gt;
&lt;p&gt;This is a documented lineage where the authors themselves cite the earlier work. The claim that JA3's decisive move was simplification is our interpretation of those sources, not a claim that every project shared one design plan.&lt;/p&gt;
&lt;h2&gt;2009: the cipher list as a client signature&lt;/h2&gt;
&lt;p&gt;In June 2009, Ivan Ristić described an experiment in &lt;a href="https://blog.ivanristic.com/2009/06/http-client-fingerprinting-using-ssl-handshake-analysis.html"&gt;HTTP client fingerprinting using SSL handshake analysis&lt;/a&gt;. He was working on SSL Labs and noticed a useful property of the initial handshake: clients sent different lists of supported cipher suites, and those lists were visible before encryption began.&lt;/p&gt;
&lt;p&gt;The important observation was not that any one cipher identified a browser. It was the combination of ciphers a client offered. Ristić recorded the entire list as a signature and compared it with the HTTP User-Agent seen after the connection was established. He then published &lt;a href="https://blog.ivanristic.com/2009/07/examples-of-the-information-collected-from-ssl-handshakes.html"&gt;examples collected from real SSL handshakes&lt;/a&gt;, showing that the approach could separate a range of browsers, command-line clients and crawlers.&lt;/p&gt;
&lt;p&gt;This early method was deliberately modest. It concentrated on the cipher-suite list. It did not define a general-purpose fingerprint containing every useful ClientHello feature, and it did not claim that a signature proved the identity of a process.&lt;/p&gt;
&lt;p&gt;Even so, the core technical idea was in place:&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;unencrypted ClientHello
  -&amp;gt; implementation-dependent choices
  -&amp;gt; repeatable signature
  -&amp;gt; comparison with previously observed clients
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

&lt;p&gt;The handshake was no longer just cryptographic setup. It was passive metadata about the software constructing it.&lt;/p&gt;
&lt;h2&gt;2012: p0f adds order, extensions and matching rules&lt;/h2&gt;
&lt;p&gt;Marek Majkowski pushed the idea further in his 2012 &lt;a href="https://idea.popcount.org/2012-06-17-ssl-fingerprinting-for-p0f/"&gt;SSL fingerprinting patch for p0f&lt;/a&gt;. p0f was already known for passive operating-system fingerprinting at lower layers. Majkowski applied a similar signature-and-database model to SSL and TLS ClientHello messages.&lt;/p&gt;
&lt;p&gt;His post explicitly credits Ristić's 2009 work, then points to two details he believed deserved more attention: ordering and TLS extensions. The patch represented a fingerprint as four fields:&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;requested version : ordered ciphers : ordered extensions : flags
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

&lt;p&gt;That is a meaningful technical step. Cipher suites are normally sent in preference order, and extension order can differ between implementations. Retaining those sequences gives the signature more discriminatory power than an unordered inventory. The flags recorded other behaviours, such as compression support or an unusual relationship between record and handshake versions.&lt;/p&gt;
&lt;p&gt;The implementation did more than print a string. It matched the result against a database of signatures that could contain wildcards and return a browser family, possible versions and sometimes a platform. The &lt;a href="https://gist.github.com/majek/2721464"&gt;original p0f patch and notes&lt;/a&gt; are still useful because they expose the boundary between observation and label: one part generates the raw signature; another compares it with knowledge gathered elsewhere.&lt;/p&gt;
&lt;p&gt;Majkowski also wrote with appropriate caution. His notes say that a ClientHello can sometimes identify the underlying SSL library and, for software with a custom build or distinctive feature set, may narrow the application version. "Sometimes" matters. Two applications using the same TLS stack can look alike, while one application can change its handshake when its library, configuration or build changes.&lt;/p&gt;
&lt;p&gt;The p0f work did not become the universal exchange format for TLS fingerprints. It did, however, demonstrate most of the ingredients that later systems would reuse: selected fields, preserved order, a serialised signature and a separate matching database.&lt;/p&gt;
&lt;h2&gt;2015: FingerprinTLS turns a method into a toolset&lt;/h2&gt;
&lt;p&gt;Lee Brotherston's 2015 work expanded the practical surface again. His DerbyCon and SecTor presentation, &lt;a href="https://archives.sector.ca/presentations15/BrotherstonTLS%20Fingerprinting%20SecTor.pdf"&gt;Stealthier Attacks and Smarter Defending with TLS Fingerprinting&lt;/a&gt;, examined TLS fingerprinting from both sides: defenders could recognise unexpected software, while an operator could alter a client's handshake to blend in or evade a simplistic rule.&lt;/p&gt;
&lt;p&gt;The associated &lt;a href="https://github.com/LeeBrotherston/tls-fingerprinting"&gt;FingerprinTLS repository&lt;/a&gt; packaged the approach into several working parts:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;FingerprinTLS&lt;/code&gt; detected TLS sessions on a live interface or in a PCAP, created fingerprints and matched them;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;fingerprints.json&lt;/code&gt; stored the known fingerprint database;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;Fingerprintout&lt;/code&gt; exported observations into other forms, including Snort and Suricata rules.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;This was broader than calculating a digest. It was a workflow for capturing a handshake, retaining many of its characteristics, associating that observation with known software and moving the result into operational tools.&lt;/p&gt;
&lt;p&gt;The project also made an awkward truth visible: rich fingerprints are not especially convenient interchange formats. FingerprinTLS could inspect more detail, but exporting that detail into a rule language could lose accuracy. Its README warned that Snort and Suricata exports might require tuning because their rule syntax could not express the full matching logic.&lt;/p&gt;
&lt;p&gt;That trade-off set the stage for JA3. A detailed signature helps an analyst explain why two handshakes differ. A compact value is easier to add to a connection log, compare across sensors and share with another team. It is difficult to optimise one representation for both jobs.&lt;/p&gt;
&lt;h2&gt;2017: JA3 chooses portability&lt;/h2&gt;
&lt;p&gt;Salesforce open-sourced JA3 in 2017. John Althouse's original &lt;a href="https://engineering.salesforce.com/open-sourcing-ja3-92c9e53c3c41/"&gt;JA3 announcement&lt;/a&gt; directly cites Ristić's 2009 post and Brotherston's 2015 research. It also states the team's design requirement plainly: the result had to work with existing monitoring systems and load balancers, be independent of the destination, and be easy for other tools to consume.&lt;/p&gt;
&lt;p&gt;JA3 selected five ordered ClientHello feature groups:&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;TLS version,
cipher suites,
extension types,
supported groups,
elliptic-curve point formats
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

&lt;p&gt;It rendered their numeric values into a comma-separated string, removed GREASE values, then calculated an MD5 digest. A long handshake description became a 32-character identifier.&lt;/p&gt;
&lt;p&gt;MD5 was not being used here to protect a password or prove integrity. It was a compact naming function. The security weakness of MD5 still means a JA3 value should not be treated as proof, but changing to a stronger digest would not solve the more common identification problem: unrelated software can naturally produce the same selected features, and software can deliberately copy another client's ClientHello.&lt;/p&gt;
&lt;p&gt;The simplification was substantial. Compared with FingerprinTLS, JA3 retained fewer fields and discarded the explanatory structure once the string was hashed. Compared with the p0f patch, it did not carry matching wildcards or classification rules in the fingerprint. What it gained was a common unit that could fit almost anywhere an operator could put a string.&lt;/p&gt;
&lt;p&gt;That was why JA3 travelled. A sensor could calculate the value, a SIEM could index it, an intelligence report could publish it and a rule could match it without every participant adopting the same fingerprint database or packet parser.&lt;/p&gt;
&lt;h2&gt;What JA3 inherited, and what it left behind&lt;/h2&gt;
&lt;p&gt;The documented history supports a few specific claims:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Ristić showed in 2009 that an unencrypted SSL handshake, particularly its cipher list, could distinguish HTTP clients.&lt;/li&gt;
&lt;li&gt;Majkowski's 2012 p0f work explicitly built on that experiment and added ordered extensions, behavioural flags and database matching.&lt;/li&gt;
&lt;li&gt;Brotherston's 2015 research and FingerprinTLS made detailed capture, matching, creation and export available as a standalone toolset.&lt;/li&gt;
&lt;li&gt;Salesforce cited the earlier work when it released JA3 and designed a smaller representation for existing operational systems.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;It does not support treating a fingerprint as an application identity. Every stage depended on a set of observed features and, when a software name was returned, knowledge collected outside the handshake itself. The label could be useful without being certain.&lt;/p&gt;
&lt;p&gt;That distinction is easier to see when the formats are run side by side. Our reproducible lab feeds &lt;a href="/blog/one-clienthello-ja3-ja4-mercury-lab/"&gt;one ClientHello to JA3, JA4 and Cisco Mercury&lt;/a&gt; and records both the compact outputs and the detail each format preserves.&lt;/p&gt;
&lt;p&gt;JA3 was not the final step either. JA4 later changed the normalisation and output structure to cope with modern sources of instability, while Cisco's research followed a more structured, context-aware path. Those are separate branches, not one straight succession. We trace them in &lt;a href="/blog/two-lineages-tls-fingerprinting/"&gt;Two Lineages of TLS Fingerprinting&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;The useful lesson from the early history is not who coined the first fingerprint. It is that the representation determines the work you can do with it. Rich detail helps investigation. Compact identifiers help distribution. Neither turns a handshake into an identity document.&lt;/p&gt;</content><category term="Security"></category><category term="TLS Fingerprinting"></category><category term="JA3"></category><category term="FingerprinTLS"></category><category term="p0f"></category><category term="Network Fingerprinting"></category><category term="Security Research"></category></entry><entry><title>One ClientHello, Three Fingerprints: JA3, JA4 and Mercury</title><link href="https://www.peakhour.io/blog/one-clienthello-ja3-ja4-mercury-lab/" rel="alternate"></link><published>2026-07-12T09:00:00+10:00</published><updated>2026-07-12T09:00:00+10:00</updated><author><name>AC</name></author><id>tag:www.peakhour.io,2026-07-12:/blog/one-clienthello-ja3-ja4-mercury-lab/</id><summary type="html">&lt;p&gt;A reproducible lab runs JA3, JA4 and Cisco Mercury against the same TLS ClientHello and compares what each fingerprint preserves.&lt;/p&gt;</summary><content type="html">&lt;p&gt;The easiest way to misunderstand network fingerprints is to compare example strings taken from different clients. We wanted a cleaner test: one packet capture, one TLS ClientHello and three fingerprint formats.&lt;/p&gt;
&lt;p&gt;The complete lab is checked into this site's source under &lt;code&gt;labs/network-fingerprinting/&lt;/code&gt;, and the &lt;a href="/static/downloads/network-fingerprinting-lab.tar.gz"&gt;publication bundle is available here&lt;/a&gt;. It pins the tool revisions, reconstructs the fixture, verifies its checksum, runs the tools and checks that their outputs refer to the same connection. Nothing in the comparison depends on a vendor database or an application label.&lt;/p&gt;
&lt;h2&gt;The input&lt;/h2&gt;
&lt;p&gt;The fixture is a 329-byte Peakhour-generated capture containing a local OpenSSL 3.5.6 ClientHello wrapped in one synthetic Ethernet/IPv4/TCP packet:&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;10.1.1.1:40000 -&amp;gt; 10.2.2.2:443
SNI: lab.peakhour.test
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

&lt;p&gt;The lab stores the small fixture as base64 under an adjacent BSD 3-Clause licence and verifies the decoded PCAP with SHA-256 before using it. The reserved SNI and private addresses did not cross a network. We select packet 1 and TCP stream 0. That selection matters: saying that several tools read the same PCAP is weaker than proving that their output describes the same flow and ClientHello.&lt;/p&gt;
&lt;p&gt;The pinned revisions for this run are:&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;Cisco Mercury  3172786645f70e1a8347d8cf020b736e185651e5
FoxIO JA4      0e54bc8371de34df94a35f2442c05bda2e8b2034
Salesforce JA3 502cc6395811c54743b0561419d61900a6df3ff7
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

&lt;p&gt;These pins are part of the result. Fingerprint implementations and specifications change. A value without its method and version is harder to reproduce than it first appears.&lt;/p&gt;
&lt;h2&gt;Running the lab&lt;/h2&gt;
&lt;p&gt;From the repository root:&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;./labs/network-fingerprinting/run.sh
python&lt;span class="w"&gt; &lt;/span&gt;labs/network-fingerprinting/verify.py
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

&lt;p&gt;The runner fetches the pinned source archives, builds or invokes the implementations in a temporary work directory, and writes evidence to &lt;code&gt;labs/network-fingerprinting/results/&lt;/code&gt;. The verifier checks the fixture and output checksums, connection tuple, SNI and output shape. The pinned source URLs are enforced by the runner rather than inferred by the verifier.&lt;/p&gt;
&lt;p&gt;This is a fingerprint-format lab, not a speed test. Build time, runtime and memory use depend heavily on language, wrapper and capture path, so we do not compare them here.&lt;/p&gt;
&lt;h2&gt;JA3: a portable exact-match digest&lt;/h2&gt;
&lt;p&gt;For this ClientHello, the canonical JA3 feature string is:&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;771,49196-49200-159-52393-52392-52394-49195-49199-158-49188-49192-107-49187-49191-103-49162-49172-57-49161-49171-51-157-156-61-60-53-47,65281-0-11-10-35-16-22-23-13,29-23-30-24-25,0-1-2
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

&lt;p&gt;Its MD5 digest is:&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;e1934f32e97b0bd52227953ca7d30118
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

&lt;p&gt;The digest is convenient for logs and exact lookup. On its own it does not show which cipher, extension or group changed. The pre-hash string retains enough information to investigate that difference, which is why throwing it away too early can make later analysis harder.&lt;/p&gt;
&lt;p&gt;JA3 removes GREASE values but otherwise retains the order of its selected lists. A client that permutes extension order can therefore generate a new JA3 digest without changing its effective TLS capabilities. The &lt;a href="https://github.com/salesforce/ja3"&gt;archived Salesforce JA3 repository&lt;/a&gt; defines the input fields and GREASE handling.&lt;/p&gt;
&lt;h2&gt;JA4: canonicalised components&lt;/h2&gt;
&lt;p&gt;The same ClientHello produces this JA4:&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;t12d2709h2_a2460661a67a_36cef8aed422
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

&lt;p&gt;Its first section is readable:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;t&lt;/code&gt; means TLS over TCP;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;12&lt;/code&gt; is the highest supported TLS version after ignoring GREASE;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;d&lt;/code&gt; says a domain was present in SNI;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;27&lt;/code&gt; and &lt;code&gt;09&lt;/code&gt; are the cipher and extension counts after the format's exclusions;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;h2&lt;/code&gt; summarises the first ALPN value.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;The second section is the first 12 hexadecimal characters of SHA-256 over sorted cipher identifiers. The third is a truncated SHA-256 value derived from sorted extension identifiers and the signature algorithms in their original order. The canonical &lt;a href="https://github.com/FoxIO-LLC/ja4/blob/main/technical_details/JA4.md"&gt;JA4 technical specification&lt;/a&gt; defines the exact exclusions and encodings.&lt;/p&gt;
&lt;p&gt;The lab also records &lt;code&gt;JA4_r&lt;/code&gt;, the raw form used by the FoxIO tooling:&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;t12d2709h2_002f,0033,0035,0039,003c,003d,0067,006b,009c,009d,009e,009f,c009,c00a,c013,c014,c023,c024,c027,c028,c02b,c02c,c02f,c030,cca8,cca9,ccaa_000a,000b,000d,0016,0017,0023,ff01_0403,0503,0603,0807,0808,0809,080a,080b,0804,0805,0806,0401,0501,0601,0303,0301,0302,0402,0502,0602
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

&lt;p&gt;That makes the normalisation visible. It also shows why JA4 is not fuzzy hashing: sorting makes selected permutations equivalent, while the hashes still support equality matching rather than semantic distance.&lt;/p&gt;
&lt;h2&gt;Mercury NPF: a retained protocol tree&lt;/h2&gt;
&lt;p&gt;Cisco Mercury 2.18 emits this &lt;code&gt;tls/2&lt;/code&gt; fingerprint for the same ClientHello:&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;tls/2/(0303)(c02cc030009fcca9cca8ccaac02bc02f009ec024c028006bc023c0270067c00ac0140039c009c0130033009d009c003d003c0035002f)[(0000)(000a000c000a001d0017001e00180019)(000b000403000102)(000d002a0028040305030603080708080809080a080b080408050806040105010601030303010302040205020602)(0010000e000c02683208687474702f312e31)(0016)(0017)(ff01)]
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

&lt;p&gt;The value is longer because it is doing another job. Parentheses and square brackets describe an ordered tree of selected byte strings. In the draft NPF notation, square brackets mark a lexicographically sorted list. The &lt;code&gt;tls/2&lt;/code&gt; prefix names the protocol and fingerprint rule version.&lt;/p&gt;
&lt;p&gt;An analyst can inspect the retained values rather than relying only on a digest. Mercury also defines a compact hash nickname when a fixed-length index is needed, but that nickname loses the structure used for inspection, prefix comparison or approximate matching. Cisco's &lt;a href="https://github.com/cisco/mercury/blob/main/doc/npf.md"&gt;draft NPF specification&lt;/a&gt; documents both representations.&lt;/p&gt;
&lt;p&gt;The Mercury JSON includes the same source and destination tuple and the same SNI as the JA3 and JA4 records. It does not identify the client application in this lab because we did not run a labelled fingerprint knowledge base or the destination-context classifier. A packet-derived NPF value and a process assessment are separate outputs.&lt;/p&gt;
&lt;h2&gt;What the comparison establishes&lt;/h2&gt;
&lt;p&gt;All three methods observe the same ClientHello, but they define similarity differently.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Question&lt;/th&gt;
&lt;th&gt;JA3&lt;/th&gt;
&lt;th&gt;JA4&lt;/th&gt;
&lt;th&gt;Mercury NPF &lt;code&gt;tls/2&lt;/code&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Compact default&lt;/td&gt;
&lt;td&gt;Yes&lt;/td&gt;
&lt;td&gt;Yes&lt;/td&gt;
&lt;td&gt;No; optional hash available&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Inspectable selected inputs&lt;/td&gt;
&lt;td&gt;Only if the pre-hash string is retained&lt;/td&gt;
&lt;td&gt;Partly in &lt;code&gt;a&lt;/code&gt;; fully in the recorded raw form&lt;/td&gt;
&lt;td&gt;Yes in the full tree&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Selected list sorting&lt;/td&gt;
&lt;td&gt;No, after GREASE removal&lt;/td&gt;
&lt;td&gt;Ciphers and most extensions&lt;/td&gt;
&lt;td&gt;Rule-specific selected extensions&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Explicit format version in value&lt;/td&gt;
&lt;td&gt;No&lt;/td&gt;
&lt;td&gt;Encoded field semantics, but no separate rule number&lt;/td&gt;
&lt;td&gt;Yes&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Semantic or approximate comparison&lt;/td&gt;
&lt;td&gt;Not from the digest&lt;/td&gt;
&lt;td&gt;Component grouping, not hash distance&lt;/td&gt;
&lt;td&gt;Full structure can support richer matching&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Application attribution in the format&lt;/td&gt;
&lt;td&gt;No&lt;/td&gt;
&lt;td&gt;No&lt;/td&gt;
&lt;td&gt;No&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;The table does not produce a universal winner. JA3 remains useful where historical compatibility matters. JA4 is compact and handles selected permutations cleanly. Mercury retains more material for inspection and for analysis systems that need structured features.&lt;/p&gt;
&lt;p&gt;It also shows what none of the values can establish. The capture does not prove which person, device or application created the connection. Shared libraries, browser impersonation and software updates all complicate that inference. See &lt;a href="/blog/fingerprint-is-a-cohort-not-a-client/"&gt;A network fingerprint is a cohort, not a client&lt;/a&gt; for the operational consequences.&lt;/p&gt;
&lt;p&gt;For the history behind these design choices, read &lt;a href="/blog/two-lineages-tls-fingerprinting/"&gt;Two lineages of TLS fingerprinting&lt;/a&gt;. The durable format comparison is in &lt;a href="/learning/fingerprinting/mercury-vs-ja4-vs-ja3/"&gt;Mercury vs JA4 vs JA3&lt;/a&gt;.&lt;/p&gt;</content><category term="Security"></category><category term="TLS Fingerprinting"></category><category term="JA3"></category><category term="JA4"></category><category term="Cisco Mercury"></category><category term="Network Fingerprinting"></category><category term="Security Research"></category></entry></feed>