Compatibility
What we have actually tested.
Three tiers, and the difference between them is evidence, not confidence. Tier one is hardware we have driven with a capture to show for it. Tier two is an identity the node presents that no point-of-sale system has ever accepted in front of us. Tier three is what this firmware does not implement at all.
How to read this
Every row cites what produced it.
A device moves up a tier when a new artefact says it can — a byte capture, a dated bench session, a trace of a POS accepting it. Nothing else promotes a row.
The one sentence that covers most buyers: a generic 80 mm USB ESC/POS printer works, and a POS that prints to an address you type in on port 9100 works. The complications start when your POS wants to pick a printer from a certified list instead — that is tier two, and tier two is not proven.
ESC/POS is the only print language this firmware implements. Everything in tier three is a refusal, not a driver.
Tier one
Tested on our bench.
Physically attached to a node, driven, and captured. Each row names the device ID and the date.
DYMO M25 25 lb USB scale
Drives it. Weight reads, and the limits are stated.
221 bytes read off the device itself and checked into the firmware as a test fixture, plus three live frames from its interrupt pipe in the same session. What that captures is narrower than "scale support": the ounce unit and status codes 2, 4 and 5 are the ones this device actually produced — every other unit and status in the codec is inferred from the HID specification and has never been seen. It also goes to sleep after about three minutes of no weight change, which reads downstream as a mute scale rather than a fault.
Source: 0922:8009 · captured 2026-08-07 · firmware test fixture fixture_dymo_m25.h
Generic 80 mm thermal receipt printer
Drives it, reads its sensors, and takes a job over raw :9100.
The bench printer reports its manufacturer string as "POS-X". Paper, cover and drawer state all read back over DLE EOT — real readings, not assumptions, and the driver says so by marking them known. Cut clearance needed eight feed lines before the cutter to stop it cutting through the last line, and its 64-byte endpoint drives the wrapping the node does for it. A 137-byte ESC/POS job arrived over port 9100 and came out of the printer.
Source: 0416:5011 · :9100 job accepted 2026-09-05 · bench-bringup.md §printer bring-up
USB keyboard-wedge barcode scanner (Netum family)
Drives it — but read the caveat, because it is the honest part.
The reference unit binds as a single-interface HID boot keyboard, accepts SET_PROTOCOL and SET_IDLE rather than stalling them, and delivers reads to the API. Here is the thing worth knowing: a wedge scanner and an ordinary keyboard are byte-identical to the node. It cannot tell them apart, and it does not try — binding is policy ("on a scanner-declaring node, any boot keyboard is the scanner"), not detection. So the real claim is not "this brand works": it is that HID boot keyboards work, and every wedge scanner in that mode is one. The upside is that any USB keyboard is a test scanner — type a code, press Enter, watch it arrive on the event stream.
Source: 9901:0301 · Class_03 SubClass_01 Prot_01 · bench-bringup.md §the scanner
Unbranded RJ12 cash drawer
Opens it, and reports its state correctly — including inverted.
The kick pulse fires and the drawer opens, measured at 0.15 s from API call to pulse. The state reading is the more interesting result: this drawer answers DLE EOT 1 with 0x16 when shut and 0x12 when open — the inverse of the Epson convention. That is why the node has a drawerOpenLevel setting instead of a hardcoded assumption, and it is a good example of what a real device teaches that a datasheet does not.
Source: Hardware conformance on node pn-d938, 2026-08-23: 118 passed, 0 failed
Tier two
Emulated identity, unverified against a POS.
The node can present itself as one of these printers. That the advertisement is well-formed is proven; that a point-of-sale system will accept it is not.
The firmware's own profile table carries the words UNVERIFIED AGAINST A REAL POS in its source comments. This page says the same thing in public, because a claim that is qualified in the code and unqualified on the website is just a lie with a footnote.
Epson TM-m30
Identity advertised. Never accepted by a POS in our presence.
The mDNS advertisement is proven on real silicon: the node announces itself as this model and the announcement is well-formed on the wire. That is the entire claim. No Epson TM-m30 has ever been attached to a node, and no point-of-sale system has ever completed an add-a-printer flow against this identity while we were watching.
Source: mDNS identity confirmed on hardware 2026-09-05 · firmware pn_profile.c
Epson TM-T88V
Identity strings only.
The discovery records name the manufacturer and model as Epson writes them, which is safe to state. The model-query bytes a POS might ask for are deliberately incomplete rather than copied from the TM-m30 entry — inventing them would make the node fail the one check that distinguishes a real printer from something imitating one, and fail it silently.
Source: firmware pn_profile.c — the source comment reads UNVERIFIED AGAINST A REAL POS
Star TSP143 / TSP100
Identity strings only, and weaker than the Epson entries.
The discovery keys follow the general print-discovery convention rather than a documented Star advertisement, so treat the whole entry as a starting point for a capture. The node deliberately answers no ESC/POS model queries under this profile: Star's native language is not ESC/POS, and a genuine TSP100 would not answer them either. Answering would look like success in a trace that was actually a lie.
Source: firmware pn_profile.c — self-labelled UNVERIFIED AGAINST A REAL POS
Tier three
Not supported.
Named so you can rule the product out in thirty seconds rather than after a delivery.
- StarPRNT
- Not driven. A printer that declares it is refused by name — the node tells you it found a command set it cannot speak, rather than feeding a roll of garbage. Some Star models offer an ESC/POS emulation mode; in that mode they are an ESC/POS printer and tier one applies.
- ZPL
- Label printers. Not implemented.
- TSPL
- Label printers. Not implemented.
- EPL2
- Label printers. Not implemented.
- CPCL
- Mobile label printers. Not implemented.
- ePOS-XML
- In development. A POST to the usual path is captured so we can see what a POS actually asks for, and answered honestly rather than pretended at.
- CloudPRNT
- Not implemented, and not a direction we are taking — it is a polling design.
Two caveats
Where our evidence is weaker than it looks.
Both of these could be left out and nobody would notice. They are here because noticing them yourself, later, would be worse.
Our capture traces are self-captures.
The node records inbound traffic and can replay it, and those traces are genuine. But every inbound peer in them is an operator's laptop on our own bench network — not a point-of-sale terminal. They prove the capture and replay machinery works. They do not prove any POS has talked to a node, because none has.
The nightly hardware job has never run.
A scheduled workflow exists that would exercise real hardware on every change. It has never executed once, because there is no machine attached to run it. Everything on this page therefore comes from a person at a bench on a named date — which is why every row carries a date instead of a green tick.
Something on your counter that is not on this list? Tell us what it is on the support page, or try it against the free simulator before spending anything. The hardware itself is the Station Hub.