[HN Gopher] Reverse-engineering the UniFi inform protocol
___________________________________________________________________
Reverse-engineering the UniFi inform protocol
Author : baconomatic
Score : 133 points
Date : 2026-03-09 12:38 UTC (10 hours ago)
(HTM) web link (tamarack.cloud)
(TXT) w3m dump (tamarack.cloud)
| devmor wrote:
| > ("TNBU" is "UNBT" backwards, presumably UniFi Broadcast
| Technology.)
|
| This seems like an odd misunderstanding, especially because the
| correct inversion "UBNT" is the default login name for most UniFi
| web UIs.
|
| You might have a bit of dyslexia, OP!
| dwood_dev wrote:
| ubnt has been the ubiquiti default login at least back to 2010
| when I started using their products, before UniFi was a brand.
| I always assumed it was short for Ubiquiti Networks.
| hrimfaxi wrote:
| Sure, but the parent was saying this part was odd:
|
| > "TNBU" is "UNBT" backwards
|
| TNBU is clearly NOT uNbt backwards.
| idorosen wrote:
| Using the network byte ordering (big endian) of UBNT as the
| magic number in the protocol is a nice touch.
| EvanAnderson wrote:
| I believe they used MIPS processors in their early gear,
| so that makes sense.
| mikepurvis wrote:
| A lot of companies in that space did then. I was at a
| robotics company at the time and we experimented with
| mikrotik routerboards + the various long-range Ubiquiti
| wifi modules, some of which are even still listed on the
| website: https://techspecs.ui.com/uisp/accessory-tech/xr
| (though not the 900 MHz XR9, which was arguably one of
| the most interesting for long range comms)
| baconomatic wrote:
| You might be onto something there! But yes, good catch, I'll
| get that updated.
| voidUpdate wrote:
| Is it just me that pretty much cannot read most of the text in
| the "Reading the MAC" code block? I don't know if it's because I
| use dark mode, but some of the text is #24292E on top of #141A16,
| which for me at least is practically invisible
| baconomatic wrote:
| Sorry about that, I typically use light mode, fixed and
| deployed!
| voidUpdate wrote:
| A million times better, thanks =)
| baconomatic wrote:
| Thanks for calling it out!
| scottlamb wrote:
| Bit of a thread-jack, but has anyone reverse-engineered the UniFi
| camera adoption protocol? I was surprised to discover that,
| unlike the APs, the cameras can't be adopted through the Unifi
| Software Controller that you can just throw into a Docker
| container. You're supposed to do that through their NVR appliance
| (Unifi Protect). I was hoping to just use them with my open-
| source NVR. They seem to be about the only option for a
| reasonably priced, larger image sensor camera that is not made by
| a company participating in the Uyghur genocide (Hikvision, Dahua,
| Univision, Huawei).
|
| I found https://community.home-assistant.io/t/unifi-cameras-
| without-... in which someone sshed in, edited some config files
| by hand, and got streaming to work for the current boot. One
| could probably take that a bit further and, you know, save the
| config to flash. But it'd be nice to just do it the way their
| controller does and know it's going to work for future firmware
| updates and such.
|
| They also stream by connecting _to_ your NVR with modified
| version of flv, rather than you connecting to them with RTSP,
| which is annoying but can be worked around.
| ImPostingOnHN wrote:
| If you want to bypass Unifi Protect, what sort of "adoption"
| are you thinking of? AFAIK, "adoption" is a Unifi Protect
| thing. Otherwise it's just a device on your network that you
| can configure Frigate etc. to connect to and pull streams.
| scottlamb wrote:
| Changing the credentials for web access (firmware upgrade,
| janky jpeg-based live stream, etc.) and ssh access from the
| default ubnt:ubnt. Surprisingly, I don't see a page for this
| in the web UI, and the `password` command in the CLI is
| ineffective. I haven't looked around the filesystem.
|
| Setting where it sends the video stream.
|
| Configuring video settings, zone detections, etc. I found a
| video going through them here:
| <https://youtu.be/URam5XSFzuM?si=8WK4Yghh9kidZe6c&t=279> Just
| about any other camera lets you change this stuff through the
| camera's built-in web interface and/or ONVIF. Ubiquitis
| apparently don't.
|
| > Otherwise it's just a device on your network that you can
| configure Frigate etc. to connect to and pull streams.
|
| No, it connects to you!
| ImPostingOnHN wrote:
| You want to change the credentials of the camera, so
| Frigate can log into it while it is connected to your Unifi
| network?
|
| I did that for 5 different cameras yesterday, you're saying
| Unifi's cameras doesn't allow user management? That sucks!
|
| _> No, it connects to you!_
|
| I thought frigate connects to the camera's RTSP stream
| (maybe with ONVIF in the mix)?
| scottlamb wrote:
| > I thought frigate connects to the camera's RTSP stream
| (maybe with ONVIF in the mix)?
|
| Right, that's the expectation of Frigate, my own Moonfire
| NVR, and basically every other NVR out there. Ubiquiti
| decided to think different.
| ImPostingOnHN wrote:
| Well thanks for the heads-up to avoid their cameras.
| scottlamb wrote:
| I hear you, but on the other hand, I'd take a bit of
| interop pain over supporting genocide any day. It looks
| like with the hints from moonlighter and from
| https://github.com/keshavdv/unifi-cam-proxy I'll be able
| to get this to work.
|
| Honestly it might be less work than some other cameras
| that (allegedly) speak RTSP. You'd be shocked how low-
| quality these implementations are. Never advancing
| timestamps, setting the RTP MARK bit arbitrarily, writing
| uninitialized memory framed as audio packets (on cameras
| that don't have microphones), closing file descriptors
| then writing data to them anyway (and so having it show
| up on the next accepted connection to be assigned that fd
| even pre-auth), etc.
| ImPostingOnHN wrote:
| FWIW, there are multiple other camera brands who don't
| manufacture in Xinjiang (or China for that matter), like
| Axis or Vivotek.
| moonlighter wrote:
| Unifi cams don't stream RTSP, they stream FLV v1
| (FlashVideo) on 3 streams over plain TCP on port 7550,
| one per quality channel. And yes, they stream that TO the
| NVR who adopted them only... then the NVR recodes and
| sends RTSP (configurable).
|
| For the adoption stage, UniFi cameras broadcast on UDP
| port 10001 using a proprietary TLV (Type-Length-Value)
| protocol. The Protect console listens on this port and
| picks up new cameras immediately. 4 bytes
| `\x01\x00\x00\x00` sent as UDP broadcast to
| `255.255.255.255:10001`
|
| The response then contains these fields:
| | Hex Code | Field | Data |
| |----------|-------|------| | `0x01` | MAC Address
| | 6-byte hardware address | | `0x02` | MAC + IP |
| Combined MAC and IPv4 address | | `0x03` | Firmware
| Version | String | | `0x0B` | Hostname | String |
| | `0x0C` | Platform (Short Model) | String | |
| `0x0A` | Uptime | 64-bit integer | | `0x13` |
| Serial | String | | `0x14` | Model (Full) | String
| | | `0x17` | Is Default | Boolean (adopted vs
| unmanaged) |
|
| After discovery, the Protect console: 1. Connects to the
| camera via SSH (default credentials) 2. Configures the
| Inform URL (TCP 8080) 3. Camera registers with the
| controller
|
| So conceivably at step 2 you could use your own modified
| URL to point to your own NVR and then grab the FLV
| streams from there.
| scottlamb wrote:
| Thanks!
|
| > 1. Connects to the camera via SSH (default credentials)
| 2. Configures the Inform URL (TCP 8080)
|
| Not what I expected but okay. Looks like there's a `set-
| inform` command. It looks like it opens a TLS connection,
| doesn't check the certificate, and tries to opens a
| websocket: GET /camera/1.0/ws HTTP/1.1
| Pragma: no-cache Cache-Control: no-cache
| Host: ... Origin:
| http://ws_camera_proto_secure_transfer Upgrade:
| websocket Connection: close, Upgrade Sec-
| WebSocket-Key: ... Sec-WebSocket-Protocol:
| secure_transfer Sec-WebSocket-Version: 13
| Camera-MAC: ... Camera-IP: ... Camera-
| Model: 0xa601 Camera-Firmware: 5.0.83
| Device-ID: ... Adopted: false x-guid:
| be9d8e45-62a8-ae84-8b23-71723c7decaf
|
| I might try accepting the websocket but I have a feeling
| I'll get stuck about there without knowing what the
| server is supposed to send over it. I'm debating if I'm
| willing to buy a Unifi Protect device or not.
|
| ...then again I did a search for a couple strings and ran
| across https://github.com/keshavdv/unifi-cam-proxy . It's
| the opposite direction of what I want (makes a standard
| camera work with Unifi Protect) but maybe contains the
| protocol details I'm looking for...
| scottlamb wrote:
| > ...then again I did a search for a couple strings and
| ran across https://github.com/keshavdv/unifi-cam-proxy .
| It's the opposite direction of what I want (makes a
| standard camera work with Unifi Protect) but maybe
| contains the protocol details I'm looking for...
|
| Actually, yes. I got lazy and just asked Claude Code to
| write a server, using that as a reference...and it
| worked. It was able to change the password and have it
| start streaming flv video. Not exactly a production-
| quality implementation but as a proof-of-concept it's
| quite successful.
| ThePowerOfFuet wrote:
| Here's that YouTube link without the creepy Google tracking
| component:
|
| https://youtu.be/URam5XSFzuM?t=279
| glottis wrote:
| Im using a g3 flex with frigate without use of unifi
| protect, works fine.
|
| I think newer models like g4 flex dont support this thou.
| mrweasel wrote:
| It seems like a pretty tall order, but I really want an open
| source access point controller daemon that knows how to provision
| and manage a wide variety of APs from different manufacturers.
|
| So you'd have one services that can provision Ubiquity, MikroTik,
| TPLink and other APs and manage the clients.
| baconomatic wrote:
| Now that would be interesting! Multi-vendor support is on the
| radar, but haven't started looking into it much yet.
| myself248 wrote:
| Alternately, run OpenWRT on the APs themselves, and then you
| just need one provisioning protocol.
| blacklion wrote:
| Does it support seamless roaming of clients between group of
| APs?
|
| Last time I've tried, it was not supported by any open source
| solution.
| BenjiWiebe wrote:
| Well AFAIK the core seamless roaming in Unifi is using
| hostapd, which is the same AP software you use on OpenWrt.
| See 802.11r Fast Transition.
|
| I _think_ it should even be possible to get seamless
| roaming between Unifi and OpenWrt with correct
| configuration of hostapd.
| ctippett wrote:
| Nice trick. Just a heads up that I had to whitelist your domain
| as NextDNS blocked it for being newly registered.
|
| Given this thread will probably attract other Unifi users... has
| anyone had success migrating from MongoDB to something like
| FerretDB?
|
| I played around with getting this to work a few weeks ago and
| found that day-to-day it works without issue, but restoring a
| backup will error since it relies on some unsupported Mongo
| semantics (renaming collections iirc).
| paulddraper wrote:
| What does an admin do about NextDNS blocks?
| bastawhiz wrote:
| If you subscribe to the mindset of "new domains are likely to
| be bad" you just deal with a steady stream of allowlist
| requests from your users until the end of time. There will be
| new domains until the end of time, and site owners shouldn't
| be doing _anything_ extra (imo) to justify their existence to
| admins. If you use a firewall voluntarily and that firewall
| blocks sites that are legitimate, that 's on you, not the
| site owner.
|
| We get this a lot at my job, where many customers' admins
| block s3 buckets by default. We give our customers a list of
| hostnames to allowlist and if they can't figure it out,
| that's on them.
| ThePowerOfFuet wrote:
| >If you subscribe to the mindset of "new domains are likely
| to be bad" you just deal with a steady stream of allowlist
| requests from your users until the end of time.
|
| Newly-registered domains are not generally an issue with
| enterprise users. However, they are overrepresented in
| malicious traffic due to domain-generation algorithms
| (DGAs).
| Terretta wrote:
| > _Newly-registered domains are not generally an issue
| with enterprise users._
|
| I take it this means enterprise users are not generally
| needing to do anything legit-for-work on a newly
| registered domain.
|
| Enterprise clicks on newly registered domains tend to be
| (a) being phished or smished or cryptomined or whatever,
| or (b) someone reading X or Bsky or HN or ProductHunt's
| vibe code of the date -- things the enterprise would
| _also_ like to have blocked.
|
| Consider the CloudFlare/Proofpoint/NextDNS/etc. domain
| block on new domains much like updating one's HN home
| page to https://news.ycombinator.com/classic ...
| slacka wrote:
| Sounds like a massive waste of your time for NextDNS admins
| and a poor UX for end users. If your security relies on
| trusting old domains, then you need to rethink your
| security. Also, I bet it's just as easy for you to
| accidentally whitelist a bad actors as to blacklist a good
| one. What am I missing here?
| bastawhiz wrote:
| I don't disagree. The idea seems to be that newly
| registered domains are far more likely to be malicious
| (and not present on domain blocklists yet).
| adobrawy wrote:
| How are you performing backup of FerratDB? Are you using
| MongoDB tools, or are you using PostgreSQL-specific tools?
| CptKriechstrom wrote:
| Do I miss something? How do you adopt the device in the first
| place? If you have to SSH into the device and set the inform URL
| manually could't you just route the request based on the request
| hostname?
| baconomatic wrote:
| Yep, once you set-inform the host header handles the routing.
| This in particular is most useful for things like DHCP Option
| 43, where devices only get an IP.
| CptKriechstrom wrote:
| But if you only got that IP and a MAC-Address - how do you
| know which tenant is supposed to adopt the device?
| baconomatic wrote:
| We support two approaches, you can either pre-register MAC-
| Addresses or you can add source IP's to assist with that
| mapping. There is more information in our docs about this:
| https://tamarack.cloud/docs/migration
| Szpadel wrote:
| that's the key information to understand the whole thing.
|
| it would be great if that could be in the article in the
| first place. (I'm assuming you are the author)
| baconomatic wrote:
| Good call, I should have made that more clear. Article
| updated!
| opengrass wrote:
| Controller uses way to much RAM compared to OpenWISP and good
| luck if a device is EOL. Lots of $10 USG-3P's out there.
| devilbunny wrote:
| FWIW, the USG-3P is listed as supported by OpenWRT.
| bxbdbehdbdb wrote:
| I don't quite get the reason for sniffing the packets. Wouldn't
| it be simpler to just run multiple VMs on one host to be multi
| tenant?
| baconomatic wrote:
| It would definitely be simpler, however the routing issue still
| stands. You would need to have a public IP for every VM, which
| is getting less practical. The MAC-based proxy makes it so we
| only need one IP and we can worry about the routing within our
| platform instead.
| roywashere wrote:
| but it is http! why can't you do virtual hosting on a reverse
| proxy?
| baconomatic wrote:
| You definitely can once the device has a hostname set in
| set-inform. The MAC proxy is just for initial adoption
| where a device may only know the IP. Such as when you use
| DHCP Option 43.
| gh02t wrote:
| You can after the initial discovery step, the article
| mentions this. The MAC routing is for the first step where
| the device is reaching out to try and find a controller and
| signal it's available for adoption, which uses an IP
| address at least in the scheme that is relevant for hosted
| operators. After that initial channel is established, the
| controller uses it to tell the device what its hostname is,
| and you can switch to more normal HTTP proxy routing
| thereafter.
| baconomatic wrote:
| Yep, that's exactly right!
| cheriot wrote:
| This is very cool.
|
| I wonder if there's a way to control routing client side and
| remove the list of mac addresses. Eg manage DNS for customers
| (upsell ad blocking!) and CNAME the unifi entry to a customer
| specific vhost.
| baconomatic wrote:
| Thank you! DNS-based adoption works well for this. You point
| the unifi hostname at the tenant's subdomain and the Host
| header handles routing from there. We also have a DHCP Option
| 43 generator for setups where DNS isn't practical.
| andrewaylett wrote:
| I'm glad the payload was usable and the author has fixed their
| problem, it's an interesting challenge.
|
| However, there are other approaches. A public IP per client isn't
| going to be nearly as expensive as a VM per client, and lets you
| route your clients by target. Or you could route by source IP:
| either by having the client register their IPs, or with some
| combination with seeing where folk log in from.
|
| Neither is necessary, though, given inspection does appear to
| work.
| burgreblast wrote:
| I don't get this comment. Inspection does work but the
| suggested alternatives don't.
|
| Having the client register their IPs isn't tenable for most
| folks. What's my IP at the shop? (No idea) Will it change?
| (Yes) now it's broken.
|
| Seeing where folks log in from isn't nearly the same as where
| their UniFi networks are located. (Store vs home.) Broken.
|
| So neither of the those are robust approaches whereas the
| author's solution is bulletproof and simply works in all cases.
|
| No offense, but why suggest "other approaches" that have such
| major holes? Why not just cheer on the solution that works all
| the time?
| andrewaylett wrote:
| The author framed his issue as a choice between separate VMs
| (with high cost) per user or decoding the messages. As he,
| you, and I all say: what he's got does work. I'm absolutely
| not saying that now he's solved the problem he should do
| something else. But the choice wasn't between only those two
| extremes.
|
| This protocol was amenable to inspection, the next might not
| be.
|
| I use NextDNS, one of the features it provides is letting you
| register a source IP so requests from your network "just
| work". It might not be a mainstream consumer feature, but
| neither NextDNS nor managed Unifi controllers are mainstream
| consumer products.
| stereo wrote:
| Nice hack! Would hosting controllers on individual IPv6 addresses
| on the same VM solve this too?
| baconomatic wrote:
| Yeah IPv6 would solve this because we wouldn't have to go
| through the proxy at all, since each VM could get their own.
| Unfortunately IPv6 isn't quite as supported as we'd like.
___________________________________________________________________
(page generated 2026-03-09 23:00 UTC)