[1.90.0] - 2026-11-07
- FIXED: AI apps on the newest MCP protocol, such as Antigravity CLI, lost the connection to b4 before its tools appeared - such an app sends some notifications without the protocol version, and b4 refused them. The app then closed the connection. Cancelling a running tool from such an app did not stop the tool in b4 either.
- FIXED: Behind nginx, an AI app on the newest MCP protocol could wait a minute before b4's tools appeared - the app first opens a stream for updates from b4 and waits for b4's first message on it. nginx could hold that message until its read timeout, 60 seconds by default, and then closed the stream.
- FIXED: Many errors in the web interface showed only a bare status, such as 409 Conflict - b4 sent the reason as plain text, and the web interface dropped it while reading the reply. This hit starting Discovery or the DPI Detector, editing the Watchdog domain list and clearing DPI Detector history. Adding a domain to a set from the Traffic page or the Dashboard showed a parse error instead of the reason.
- FIXED: In TUN mode, a device could keep waiting after b4 had cut its connection or answered its DNS query - when another connection already leaves the router for the same server from the same port, the router moves the new one to another port. b4 sent its reset, refusal or DNS answer for that connection to the new port, which the device does not use. This hit IP Block Detection, sets that block a site, refused UDP connections and DNS answers from a set.
- FIXED: With IP Block Detection and Cache Blocked IPs on, a set that sends RST or FIN fakes did not check a silent server - the fakes of TCP Desync Attack and Post-ClientHello RST closed the kernel's record of the connection while the device kept waiting. b4 took the connection for a finished one. It neither checked the address for a ban nor reset the connection.
- CHANGED: A set routed into an AmneziaWG interface leaves its packets alone, as a set routed into WireGuard does - while the interface is up, the set's strategy, its ban resets and its QUIC refusal for banned addresses do not apply. Its connections end with routed->awg0 on the Logs page.
- FIXED: A set using Combo with an Overlap Length could break connections soon after they opened - b4 added the overlap to later packets of a connection, not just to its first one. A second request sent before the answer to the first is one example. Its fake bytes covered earlier data that could still be on its way. The site could read them as real data and close the connection.
- FIXED: On a busy network, connections could hang after b4 started, while b4 showed as running - packets that arrived during the start could make b4 fail to open one of its packet queues. b4 then tried again without asking for the owner of each packet, so that queue could no longer tell the router's own packets from the others. When the second try failed as well, nothing read the queue and connections through it hung.
- FIXED: With IP Block Detection on, a connection could be cut at its first request when a device reused a port - a device that opened a new connection to the same server from the same port within two minutes inherited the old connection's state. b4 took the new request for a repeat of the old one. It reset the connection and checked the server for a block.
- ADDED: A set that lists a provider's own servers, such as its Google Global Cache nodes, can keep the connections to them - with IP priority on, a connection to one of the set's addresses stays with the set even when a set lower in the list matches its domain. The switch is under Targets, Bypass IPs in the set editor and is off by default. It is meant for servers that carry only this set's sites, not for shared CDN ranges.
- CHANGED: ASN targets moved to Targets, Bypass IPs in the set editor - the separate ASN tab is gone. The Networks (ASN) panel sits next to Manual Bypass IPs and Bypass GeoIP Categories.
- FIXED: Tab did not leave an empty entry field in the set editor - in fields such as Add Bypass Domain and Add Bypass IP/CIDR, Tab tried to add an entry even when the field was empty. Keyboard focus stayed in the field.
- FIXED: Manual Bypass IPs took text that is not an address, such as an AS number - the set saved such an entry, but it matched no traffic. The entry still counted as a target. A routing set with nothing else showed no warning that it routes nothing.
- FIXED: A duplicated set appeared below its source, then jumped to the top of the list once the list reloaded - b4 saved the copy as the first set in the list. Ahead of its source, the copy took the connections to the sites both sets list.
- FIXED: Without a login set for the web interface, any website opened on a device in the network could watch b4's live log and the sites each device visits - b4 sent the live data of the Logs, Traffic, Dashboard and Discovery pages to a page of any site. Browsers do not keep other sites away from this data on their own.
- FIXED: Escalation did not keep a site's address from being banned - after a set moved a site to its backup set, it kept checking the site's earlier connections. When their server stayed silent, the set banned the address.
- FIXED: A backup set could give up on a site as soon as Escalation moved the site to it - the connection that triggered the switch arrived with the first set's unanswered attempts already counted. A backup set with IP Block Detection reset it, and with Cache Blocked IPs on, connections to that address were then reset for several minutes. A backup set with its own Escalation passed the site on to the next set without trying it.
- FIXED: Escalation and IP Block Detection missed a stuck connection when the site's name was in the second packet of its first request - a browser often sends that request as two packets, and the name can land in either one. With no answer, the device resends only the first packet, and b4 did not count a packet without a name. The connection waited until the browser gave up.
- FIXED: A set with IP Block Detection or Escalation and a delay in its strategy, such as Combo, could cut off a working site that asked the browser to repeat its first request - some servers ask for this as the connection opens. b4 counted the repeated request as an unanswered resend, although the server had answered. The set then reset the connection or moved the site to its backup set. With Cache Blocked IPs on, later connections to that address were reset too.
- CHANGED: Without a login set for the web interface, b4's live data reaches only pages at the same address and port as b4 - a dashboard on another site, such as a Home Assistant panel, needs a login set for the web interface and must pass its token. A reverse proxy in front of b4 must pass the original Host header and X-Forwarded-Proto, or the Logs and Traffic pages stay empty.
- ADDED: Discovery offers the other blocked hosts a site's page needs for its styles, scripts and images - a last step, Page hosts, tests the hosts the page names, first without b4 and then with the strategy found. Hosts that load only with the strategy get checkboxes on the result card, and Apply as a set adds the ticked ones. History keeps them for a later Apply, and b4_find_bypass_strategy names them to AI apps.
- CHANGED: Reloading or reopening the Discovery page within 30 minutes of a run's end shows its results again - this holds for a run started from that page. New search clears them in the browser where it is clicked.
- CHANGED: During a Discovery run, a site's row shows a strategy it found as Fastest so far instead of Found - the result card offers the strategy that loaded the most sites, which can be another one. Among strategies from earlier runs, the card prefers the one that worked most often, so cached-2 goes before cached-10. The card and the history list the same other strategies, up to twelve, fastest first.
- FIXED: Discovery gave sets a DNS redirect that the site did not need - it took the provider's DNS answer for a forged one when a public resolver gave other addresses and no address opened the site without a bypass. Blocked sites that send each region to its own servers got such a redirect. The apply dialog then could not add the site to a set with the same strategy.
- FIXED: A strategy remembered from an earlier Discovery run could pass every try, then fail as a set - when its fake was a captured ClientHello, the run tested it with the built-in fake. The set made from it sent the capture. The DNS and Page hosts results came from the same wrong test. Community sets with a captured fake had the same problem.
- FIXED: Applying a saved Discovery result could give a set another fake than the one it was tested with - when the strategy's captured payload had been deleted since the run, the set sent the built-in fake, with no warning.
- CHANGED: Deleting a payload that a set uses asks first - on the Payloads tab, Delete and Clear all captures name those sets and what their fakes fall back to. A payload no set uses is deleted at once, as before.
- FIXED: A missing TCP fake payload also took away a set's UDP fake payload - when b4 could not read the captured payload of a set's TCP fakes, it skipped the set's UDP payload too. UDP fakes went out as zeros, even with their own payload file intact or a QUIC preset chosen.
- FIXED: An AI app could report one Discovery strategy and apply another - b4_find_bypass_strategy named each site's fastest strategy, while applying installed the one the result card offers. When the AI app applied a saved result, the Discovery history marked the fastest strategy as tried.
- FIXED: AI apps connected to b4 could misread a setting or miss what it does - a search of b4's notes on settings in plain words, such as "logging level", found nothing. The notes named a set's fake payload in words, while b4 reports it as a number, and left out STUN. They also did not say that a routing set with Match any IP address on takes the router's own connections too.
- CHANGED: The diagnose_domain prompt for AI apps checks whether the site's traffic reaches b4 - it reads b4's error log, has the user open the site again and then reads the recent connections. It names the installed version and, with Allow active probes on, offers a test fetch of the site. It reads the firewall rules only when the status shows a problem or no other step finds the cause.
- FIXED: Discovery could report that a set with the Random fake works while the set itself failed - Discovery never sent random bytes. It tested that fake with the built-in fake, so the watchdog gave up on the failing set. A site tested with the built-in fake could also be offered a set with Random, as if both carried the same strategy.
- FIXED: A captured ClientHello picked in Discovery's options could go out as the same site's QUIC capture - this needed a TLS and a QUIC capture saved for one site. Which of the two a run used could change from run to run. The set made from the result named the QUIC file.
- FIXED: Discovery's result card and History could show the confirmation of another strategy - the card can offer a strategy other than a site's fastest, and both read the fastest one's result. After Stop now, a strategy that was never re-checked could read confirmed 3 of 3. A strategy that passed 3 of 3 read not confirmed when the fastest one had failed.
- FIXED: On a narrow screen, the history headers on the Discovery and DPI Detector pages could be unreadable - the buttons next to the title kept their full width. The text under the title was squeezed into a narrow column and ran under the buttons.
What's Changed
- IP bans after #481: escalation keeps its precedence; docs, UI text, AI topics and changelog by @DanielLavrushin in #483
- fix(http): refuse cross-site WebSocket connections when no web login is set by @DanielLavrushin in #486
- Implement learned address management and testing framework by @DanielLavrushin in #485
- fix: update .gitignore to exclude CLAUDE.local.md and add CLAUDE.md by @DanielLavrushin in #494
- fix(nfq): hold segment 1 of a split ClientHello until segment 2 names the site (#430) by @DanielLavrushin in #484
- fix(nfq): forget the old connection's silence watch and hello count on a reused tuple by @DanielLavrushin in #489
- feat(discovery): settle the DNS verdict through the found strategy, keep finished runs, align History with the card by @DanielLavrushin in #490
- feat(discovery): offer the other blocked hosts a site's page needs (page hosts) by @DanielLavrushin in #491
- feat: merge ASN into IPS ui by @DanielLavrushin in #496
- fix(discovery): show a page host another set handles the same on the card and in the dialog by @DanielLavrushin in #507
- fix(discovery): test cached and community presets with the fake they name by @DanielLavrushin in #508
- fix(discovery): send a set's Random fake in tests and resolve a picked payload to its TLS capture by @DanielLavrushin in #514
- fix(nfq): count resends of a split ClientHello with the name in a later segment (#505) by @DanielLavrushin in #509
- fix(discovery): refuse to apply a result whose captured fake is gone by @DanielLavrushin in #515
- fix(discovery): take the card's and History's confirmation from the offered strategy by @DanielLavrushin in #516
- fix(nfq): stop combo's overlap corrupting data and fail a queue that never binds by @DanielLavrushin in #520
- fix(hub): name the chat id that would work when Telegram refuses a notification by @DanielLavrushin in #519
- fix(nfq): check silent servers behind b4's closing fakes, hand AmneziaWG sets off by @DanielLavrushin in #517
- fix(nfq): send TUN resets and rejects to the device's own port (#482) by @DanielLavrushin in #522
- fix(nfq): send TUN DNS answers to the device's own port by @DanielLavrushin in #524
- fix(ui): keep the reason of plain-text error replies by @DanielLavrushin in #532
- fix(mcp): keep 2026-07-28 clients connected, cancel on stream close, ask nginx not to buffer by @DanielLavrushin in #535
- fix(nfq): give combo's overlap only to a connection's first data packet by @DanielLavrushin in #525
- fix(mcp): search topics by word, name fake payloads, flag the router's own traffic, rework diagnose_domain by @DanielLavrushin in #541
- docs: guide to the b4 skills for AI assistants, cloud apps in the MCP requirements by @DanielLavrushin in #543
Full Changelog: v1.89.1...v1.90.0