Jump to content
Not connected, Your IP: 216.73.217.175
Fragmented Sentinel

Independent AirVPN/WireGuard verification: DNS, IPv4/IPv6, kill switch testing and trust boundaries

Recommended Posts

I recently watched NetworkChuck’s video discussing what a VPN actually hides and, in particular, the idea that using a VPN shifts trust from the ISP to the VPN provider.
I use AirVPN, so rather than treating that as a theoretical discussion, I decided to test my own setup and document what I could actually verify.
The result turned into a fairly extensive lab exercise and eventually a short technical paper.
My test environment was an Ubuntu VM using a manually configured AirVPN WireGuard connection rather than Eddie. I inspected Linux policy routing, captured traffic on both the physical and WireGuard interfaces, tested DNS behaviour, deliberately attempted IPv4 and IPv6 bypasses, forced applications to use the physical interface, tested hard-coded external DNS, stopped the VPN to test failure behaviour, and finally rebooted the VM to verify firewall ordering and persistence.
One of the most useful findings actually had nothing to do with an AirVPN failure.
My own custom nftables kill switch was broken.
I had created a persistent nftables ruleset, but it used interface references that required the airvpn interface to exist when the firewall loaded. At boot, nftables started before WireGuard created that interface, so the firewall service failed. When I stopped WireGuard during testing, the VM silently fell back to its normal VMware NAT route and regained direct Internet access.
That was a good reminder that having a security configuration present is not the same as demonstrating that it is operating.
I corrected the ruleset to allow it to load before the WireGuard interface exists and then repeated the testing.
After the repair, I tested:
- IPv4 and IPv6 default routing through AirVPN
- DNS visibility inside and outside the WireGuard tunnel
- direct queries to the VMware/local DNS resolver
- hard-coded DNS to 1.1.1.1
- applications explicitly binding to the physical interface
- forced IPv4 and IPv6 escape attempts
- WireGuard-down behaviour
- reboot persistence
- nftables/WireGuard boot ordering
The hardened configuration failed closed as intended.
The packet captures were particularly interesting.
On the AirVPN interface I could plainly see normal DNS queries going to AirVPN’s internal resolver. On the VM’s physical interface, the same activity appeared only as encrypted UDP traffic to the AirVPN WireGuard endpoint. I could not see the individual DNS queries or direct connections to the websites being accessed.
A hard-coded query to 1.1.1.1 also behaved as expected: it bypassed AirVPN’s DNS resolver, but did not bypass AirVPN itself. The DNS request still travelled through the WireGuard tunnel.
I also queried the AirVPN resolver using CHAOS-class DNS records. version.bind returned "AirVPN DNS" and id.server identified the resolver as:
unurgunite.airservers.org
The server/network data pointed to the New York Unurgunite infrastructure on tzulo / AS11878.
Using Akamai’s whoami.ds.akahelp.net resolver diagnostic, the recursive DNS egress appeared from the same IPv6 /64 as the VPN’s public IPv6 egress, although it was a different address. The response did not include an EDNS Client Subnet value.
I also confirmed that the IPv4 WireGuard entry address and the public IPv4 exit address were different.
The conclusion I came away with is slightly more precise than simply saying a VPN “hides metadata.”
From the local/ISP side, AirVPN successfully hid substantial destination-related metadata. The ISP-side observer could still see the AirVPN endpoint, packet timing, sizes, traffic direction, volume and session duration, but could not directly see the individual DNS queries and destination connections carried inside WireGuard.
That brings the investigation back to the trust question.
Once traffic reaches the VPN endpoint, AirVPN is necessarily in a privileged network position. HTTPS still protects the application content end-to-end, but the VPN infrastructure is technically positioned to observe destination IPs, AirVPN DNS queries, timing and traffic volume.
AirVPN states that it does not retain identifying traffic logs or inspect customer traffic, and a number of the architectural behaviours I could observe were consistent with a privacy-focused design. What I cannot verify externally is the production server-side logging configuration itself.
That is the largest remaining evidence gap I identified: I could not find a published independent no-logs/infrastructure audit comparable to those some other VPN providers have commissioned.
I would be particularly interested in clarification from AirVPN staff or anyone familiar with the infrastructure on a few points:
1. Does the resolver identified as unurgunite.airservers.org run directly on the same physical VPN host, or is the 10.128.0.1 service presented locally while recursion is handled elsewhere?
2. For the current tzulo New York servers, is the bare-metal hardware AirVPN-owned/colocated, rented dedicated hardware, or another arrangement?
3. Is an independent infrastructure/no-logging audit something AirVPN has considered or plans to pursue?
4. Is my interpretation of the separate entry/exit addressing and DNS architecture accurate, or is there anything important I have misunderstood?
I’ve published the complete methodology, evidence, limitations and conclusions here:
Paper / DOI:
https://doi.org/10.5281/zenodo.22986653
GitHub:
https://github.com/Fragmented-Sentinel/what-a-vpn-actually-hides
The work is independent and is not affiliated with or sponsored by AirVPN, NetworkChuck, tzulo, or any other organization mentioned in the paper.
I’d genuinely welcome technical corrections. The purpose of the exercise was not to prove that AirVPN is “good” or “bad,” but to separate what I could actually verify from what still depends on provider claims and trust.

Share this post


Link to post
@Fragmented Sentinel

Hello!

Thank you for publishing your investigation and explaining the limits of what client-side testing can establish. We agree with the distinction between observing traffic on the client and verifying what happens to data on a provider's servers. Having reviewed version 1.0, we would like to suggest a few clarifications to help readers understand exactly what was tested and what the results establish.

1. Identify the firewall that failed
The setup uses wg-quick with a separate persistent nftables ruleset. The reported boot failure concerns that local ruleset; the experiment does not demonstrate a failure of Eddie or Network Lock.
Section 10 makes this distinction, but it would help to state it in the abstract and Section 3 as well. For example: "The test VM's custom persistent nftables firewall failed to load at boot." If the origin of those rules is known, please identify it. The comparison with RTINGS should specify the client version, operating system and startup conditions involved. A result from this custom Linux configuration can't confirm or refute the behavior of a different client setup.

2. Separate IPv6 connectivity from IPv6 firewall enforcement
The successful IPv6 request through the tunnel demonstrates IPv6 connectivity through AirVPN in the tested configuration. However, "Network unreachable" on the direct-interface test could also mean that the VM had no usable non-VPN IPv6 route. Without a baseline demonstrating a working alternative IPv6 path, the supported conclusion is that no IPv6 escape was observed in this environment. Establishing that the firewall blocked an otherwise viable connection requires that additional control. The VMware NAT configuration is relevant here and should be documented.

3. Distinguish reboot persistence from protection throughout startup
Finding the expected rules and service state after reboot supports persistence. It does not, by itself, establish that no traffic escaped during shutdown or startup. The systemd directives also need to be considered together with the complete unit dependencies. network-pre.target is passive and must be pulled into the transaction; the network-management service must participate in the ordering. Ordering alone does not make successful firewall loading a prerequisite for networking.
https://systemd.io/NETWORK_ONLINE/
A capture from outside the rebooting VM, covering the whole transition, would provide stronger evidence. This is a limitation of the published evidence, not a finding that the repaired configuration leaks.

4. Identify how DNS settings were applied
WireGuard itself does not negotiate or push DNS settings. In a wg-quick setup, those settings are applied locally through the profile and through supporting tools or hooks. Please specify the mechanism that configured systemd-resolved, including the ~. routing domain.
https://git.zx2c4.com/wireguard-tools/tree/src/man/wg-quick.8
The ~. domain is also not an unconditional guarantee of exclusive DNS routing through one link: the complete resolver configuration matters. This does not invalidate the capture results for the queries you tested. Ordinary DNS carried inside the encrypted tunnel is not, merely because it is ordinary DNS, a DNS leak.

5. Make the experiment reproducible
The reviewed deposit provides the paper and representative commands, but not the underlying artifacts. Sanitized original and repaired firewall rules, the WireGuard profile, software versions, routing and resolver state, service dependencies, and capture records would make independent checking much easier. Capture duration and dropped-packet statistics are useful too. For the infrastructure identification, please include the relevant public-address lookup records. Address registration, BGP origin and a DNS identity string are different kinds of evidence; none alone establishes physical placement.

6. Keep the no-logging conclusion within its evidential scope
We agree that these tests cannot establish server-side non-retention, and that the absence of a published audit does not demonstrate logging. Provider statements, published source code, historical reports and operational audits should be assessed separately. Source availability does not prove what is deployed. Historical claims need supporting records. An audit has a defined scope and period rather than establishing a permanent guarantee.

The central observation remains useful: after the local firewall was repaired, the reported tests found that the examined configuration carried the tested traffic through the VPN. These clarifications would make the attribution more precise and help others reproduce and extend your work.

Kind regards
 

Share this post


Link to post

Thank you for taking the time to review the paper in this much detail. This is exactly the kind of technical criticism I was hoping the publication would generate, and I agree that several parts of v1.0 need to be either narrowed, clarified, or supported with stronger evidence.
On the firewall point, you are correct. The failure I observed was in my own persistent nftables configuration used alongside wg-quick; it was not a failure of Eddie or Network Lock. I did clarify that later in the paper, but I agree that it should have been made explicit much earlier, including in the abstract and in the section describing the initial failure. I will correct that in the next revision and make the distinction much more prominent.
I also agree with the IPv6 criticism. The successful IPv6 request through airvpn demonstrated working IPv6 connectivity through the VPN, but the direct-interface result of Network is unreachable does not prove that nftables blocked an otherwise viable IPv6 path. The correct conclusion from the existing evidence is that no IPv6 escape was observed in that VMware environment. I plan to add a proper control with a known-working non-VPN IPv6 path so that firewall enforcement can be tested independently of IPv6 availability.
The reboot/startup point is also well taken. What I demonstrated was that the expected firewall and WireGuard state existed after reboot and that nftables was ordered before network-pre.target. That is evidence of persistence and service ordering, but not proof that no traffic escaped during the entire shutdown/startup transition. I plan to repeat this with a packet capture taken outside the VM, covering the full reboot, so that any traffic leaving the guest before the VPN becomes available can be observed directly.
On DNS, I agree that my wording needs to be more precise. WireGuard itself is not negotiating DNS settings. In this configuration the DNS values are present in the wg-quick profile and are applied locally through the resolver integration. I already have evidence in the boot logs showing wg-quick invoking resolvconf, and I will document exactly how that results in the AirVPN resolver addresses and the ~. route-only domain being associated with the tunnel. I will also make it clear that ~. is part of the resolver-selection logic rather than an unconditional guarantee on its own. The packet captures remain the stronger evidence for the individual DNS queries that were tested.
I strongly agree with the reproducibility point. Version 1.0 describes the experiment and includes representative commands, but it does not provide enough underlying material for someone else to independently inspect or reproduce the work. I plan to add a sanitized artifact set to the GitHub repository containing the original and repaired nftables configurations, a sanitized WireGuard profile, software versions, routing tables, resolver state, relevant systemd dependency information, infrastructure lookups, and packet captures where practical. I will also separate ARIN registration, BGP origin, reverse DNS, geolocation, and the AirVPN DNS identity more carefully rather than treating them as interchangeable evidence of infrastructure or physical placement.
I also agree with the point about the no-logging conclusion. The absence of a published independent audit should be described as an evidence gap, not as evidence that logging occurs. Likewise, published source code, provider statements, historical reports, and audits all provide different kinds of evidence and should not be treated as equivalent. An audit would itself only establish findings within its defined scope and period, not provide a permanent guarantee.
I intend to leave v1.0 intact as the original published record and incorporate these corrections, additional controls, and reproducibility artifacts into a v1.1 release. That way the revision history remains transparent rather than silently changing the original publication.
Thank you again for the detailed review. The central goal of the project was to separate what I could directly observe from what I was assuming, and your feedback has identified several places where that distinction can be made substantially stronger.

Share this post


Link to post

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Loading...
  • Security Check
    Play CAPTCHA Audio
    Refresh Image

×
×
  • Create New...