Commit Graph

689 Commits

Author SHA1 Message Date
Brian Cunnie
078a69f75e 3.2.2: Join the Public Suffix List 3.2.2 2024-10-08 18:53:08 -07:00
Brian Cunnie
dea655a990 TXT record attests ownership for the Public Suffix List
We want to place sslip.io on the Public Suffix List so we don't need to
pester Let's Encrypt for rate limit increases.

According to https://publicsuffix.org/submit/:

> owners of privately-registered domains who themselves issue subdomains
to mutually-untrusting parties may wish to be added to the PRIVATE
section of the list.

References:

- https://publicsuffix.org/
- https://github.com/publicsuffix/list/pull/2206

[Fixes #57]
2024-10-08 18:08:59 -07:00
Brian Cunnie
39d876079c Update SOA to 10/8
Lucy's birthday.
2024-10-08 09:09:24 -07:00
Brian Cunnie
705c50b70e Bump dependencies go get -u -t; go mod tidy 2024-10-08 09:06:54 -07:00
Brian Cunnie
8eb5d82e83 Who is querying us the most? 2024-09-23 07:20:21 -07:00
Brian Cunnie
d0c3927415 3.2.1: Return NS records in random order 3.2.1 2024-09-17 06:34:32 -07:00
Brian Cunnie
63a2be439e Return NS records randomly
Previously when the NS records were returned, ns-aws was always returned
first. Coincidentally, 64% of the queries were directed to ns-aws. And
once I exceeded AWS's 10 TB bandwidth limit, AWS began gouging me for
bandwidth charges, and $12.66/month rapidly climbed to $62.30

I'm hoping that by randomly rotating the order of nameservers, the
traffic will balance across the nameservers.

Current snapshot (already ns-ovh is helping):

ns-aws.sslip.io
"Queries: 237744377 (1800.6/s)"
"Answered Queries: 63040894 (477.5/s)"

ns-azure.sslip.io
"Queries: 42610823 (323.4/s)"
"Answered Queries: 14660603 (111.3/s)"

ns-gce.sslip.io
"Queries: 59734371 (454.1/s)"
"Answered Queries: 17636444 (134.1/s)"

ns-ovh.sslip.io
"Queries: 135897332 (1034.4/s)"
"Answered Queries: 36010164 (274.1/s)"
2024-09-17 06:27:53 -07:00
Brian Cunnie
c4310ebb86 3.2.0: Introduce new nameserver, ns-ovh.sslip.io 3.2.0 2024-09-15 17:45:01 -07:00
Brian Cunnie
6855598f0f Introduce new name server, ns-ovh.sslip.io
- located in Warsaw, Poland
- IPv4: 51.75.53.19
- IPv6: 2001:41d0:602:2313::1

The crux of this is to take the load off ns-aws, which jumped from
$12.66 → $20.63 → $38.51 → $62.30 in the last four months due to
bandwidth charges exceeding 10 TB.

The real fix is to randomize the order in which the nameservers are
returned.
2024-09-15 17:21:16 -07:00
Brian Cunnie
afe851a867 Dismantle DNS-backed key-value store, k-v.io
I'm no longer engaged on setting up k-v.io; I thought it'd be cool to
have a DNS-backed etcd implementation, but now I don't care anymore.

There were technical challenges, too: Specifically, updating values did
not play well with DNS caching — you'd get the old value after updating.

If the service became popular, I'd quickly run out of disk space on my
tiny cloud VMs.

The service would most likely be used by people doing data exfiltration
via DNS. I already have enough problems with sslip.io scammers — the
last thing I want is to sign up for dealing with k-v.io scammers.

This commit removes the etcd configuration, certificates, and pipelines.
2024-09-15 07:30:57 -07:00
Brian Cunnie
450fc67a57 Prune unused default.json
I had big plans for feeding in the configuration of the DNS server with
a JSON file, but since then I've come to consider command-line flags
good enough, so there's no reason to leave this useless file lingering —
it'll only server to confuse.
2024-09-15 06:54:43 -07:00
Brian Cunnie
4111f7c1ba Update SOA to 9/15
In preparation of adding a new nameserver, ns-ovh.sslip.io
2024-09-15 06:48:45 -07:00
Brian Cunnie
76d27df591 Bump dependencies go get -u -t; go mod tidy 2024-09-15 06:44:49 -07:00
Brian Cunnie
ba85d1aacf 🐞 Remove incorrect -delegates warning
fixes, when server is started with `-delegates` unset:

```
-delegates: arguments should be in the format "delegatedDomain=nameserver", not ""
```
2024-07-04 05:47:45 -07:00
Brian Cunnie
74a5c2edfd Bump Ruby 3.1 → 3.3 (for rspec) 2024-06-17 06:22:42 -07:00
Brian Cunnie
1ec255123f A first-class page about blocked sites
We warn people that they're scammers.
2024-06-16 11:55:00 -07:00
Brian Cunnie
48dd9269f9 Placate the linter
- `ip.String()` → `ip` might be nil

Drive-bys:

- better documentation for NameToA() and NameToAAAA()
- better naming: public → allowPublicIPs
2024-06-15 20:23:16 -07:00
Brian Cunnie
093fc5dadf Appease/placate/mollify the linter
- Unnecessarily handle the error in the `defer`
- Do a better comparison of the address-in-use error
2024-06-15 18:49:18 -07:00
Brian Cunnie
8a08e49034 Flag -delegates for delegated domains
Meant for obtaining wildcard certs from Let's Encrypt using the DNS-01
challenge.

- introduce a variant of `blocklist.txt` to be used for testing
  (`blocklist-test.txt`) because the blocklist has grown so large it
  clutters the test output
- more rigorous about lowercasing hostnames when matching against
  customized records. This needs to be extendend when we parse _any_
  arguments

TODOs:

- remove the wildcard DNS servers
- update instructions
2024-06-08 19:40:09 -07:00
Brian Cunnie
d52d97f478 Bump dependencies go get -u -t; go mod tidy 2024-06-08 16:16:40 -07:00
Brian Cunnie
1a42b85926 Warn developers to not index their sites
The sslip.io service has been abused by scammers and phishers who create
sites that masquerade as legitimate sites. For example,
<https://nf-43-134-66-67.sslip.io/sg> masqueraded as Netflix.

To combat this, we've undertaken to block all sites that masquerade as a
legitimate sites, but this had the unfortunate consequence of ensnaring
a legitimate staging site (th-ab.de).

This commit assists developers by updating the documentation to warn
developers not to index their staging site.

[#53]
2024-05-29 08:27:28 -07:00
Brian Cunnie
bce9e3971b 🐞 Fix broken paths caused by moving code
When we promoted the Golang code to the root of the repo, we neglected
to update the paths in the documentation, helper scripts, and pipelines.

This commit addresses that oversight by updating the paths.
2024-05-11 10:54:54 -07:00
Brian Cunnie
2fe81195d7 The BOSH Release is dead
The last BOSH Release was cut over two years ago (Feb 26, 2022), and I
don't think we're ever gonna cut another one, so I'm clearing out the
BOSH-related files.

I deployed to BOSH until I decided k8s was the way to go, and then later
decided to deploy to standalone VMs
2024-05-11 10:20:56 -07:00
Brian Cunnie
1bdd03fd39 Promote Golang code to the root of the repo
- That's where the code is expected to be
- The only reason the code was buried two directories down was because
  it was originally a BOSH release
- There hasn't been a BOSH release in over two years; last one was Feb
  26, 2022
- Other than a slight adjustment to the relative location of
  `blocklist.txt` file in the integration tests, there were no other
  changes
2024-05-11 10:14:23 -07:00
Brian Cunnie
9a238f4165 Bump dependencies 2024-05-11 06:24:56 -07:00
Brian Cunnie
758006e66b Update SOA to the Cinquo de Mayo (5/5)
Also, the date of the celebrated "Five Coves of Death" swim.
2024-05-07 06:29:51 -07:00
Brian Cunnie
fc4ecd6018 -public flag controls resolution of public IPs
Companies who run their own sslip.io DNS nameservers may want to restrict
the resolution of public IPs to mitigiate bad actors from impersonating
them. For example, the corporation Pivotal, which owns the domain
pivotal.io, may want to set `-public=false` when they delegate the
domain `xip.pivotal.io` to their internal instances of sslip.io
nameservers, which enables their developers to use their internal IPs
(e.g. 10-9-9-31.xip.pivotal.io) while preventing a bad actor from using
a public IP (e.g. 52-0-56-137.xip.pivotal.io) to trick users.

- `-public` defaults to `true`
- `-public=true` enables resolution of all hostnames with embedded IP
  addresses
- `-public=false` restricts resolution to hostnames with private IP
  addresses

The following ranges are not considered public and always resolve:

- 10/8, 172.16/12, 192.168/16 — RFC 1918
- fc/7                        — RFC 4193
- 100.64/10                   — CG-NAT
- 127/8, ::1                  — loopback
- 169.254/16                  — IPv4 link local
- fe80/10                     — IPv6 link local
- 64:ff9b:1/48                — IPv4/IPv6 translation private internet
- 2001:20/28                  — ORCHIDv2
- 2001:db8/32                 — Documentation
2024-05-07 06:29:17 -07:00
Brian Cunnie
75ba5b62f4 ns-gce has an IPv6 address
- This IPv6 address is "ephemeral" in the sense that if a `terraform
  destroy` and `terraform apply` are run I'll get a different address
  (not `2600:1900:4000:4d12::`)
- I don't plan on updating the WHOIS information because the address is
  somewhat ephemeral
2024-03-09 10:39:48 -08:00
Brian Cunnie
a442a7d368 Release Procedure: Include GCP
Previously the GCP NS was a k8s container, but now it's a standalone VM
(for, believe it or not, cost reasons: it was cheaper to assign a static
IP to a VM than to a load balancer).

The instructions now include the procedure to update the GCP VM.

Also, we double-checked that all servers had the same version number
twice, and now we only do it once. And we incorporate it with another
step, so there are two fewer steps to follow.
2024-03-09 08:15:00 -08:00
Brian Cunnie
27d7f4bcd6 3.1.0: Shorten TTL for publicly-accessible A & AAAA records 3.1.0 2024-03-09 07:20:50 -08:00
Brian Cunnie
66c7fbc72c Bump serial 2023093000 → 2024022900
...because I love Leap Day!
2024-03-09 07:03:00 -08:00
Brian Cunnie
44efa97c58 Bump dependencies go get -u -t; go mod tidy 2024-03-09 06:58:36 -08:00
Brian Cunnie
e664144b32 Lena M. doesn't want her name 2024-02-23 04:07:15 -08:00
Brian Cunnie
2d78f14989 Thank you, Lena of JetBrains 2024-02-22 05:02:25 -08:00
Brian Cunnie
1ed944f1e5 sslip.io is hosted on GCP, not GKE
I don't need this k8s configuration for sslip.io (DNS, NTP) because I'm
no longer hosting on GKE now that it has an ephemeral IP instead of a
reserved IP because otherwise I'd have to pay $360 extra per year for a
premium-tier load balancer.
2024-01-10 11:27:50 -08:00
Brian Cunnie
9e8a2985b8 Don't use GKE cluster as an sslip.io example
The GKE's cluster's IP address is now an ephemeral IP because otherwise
I'd have to pay $360 extra per year from a premium-tier load balancer.

I don't want my website to point to an ephemeral address that quickly
becomes stale, so I'm pointing from what previously was the GKE
cluster's address to the AWS's NS server's address.
2024-01-10 10:36:16 -08:00
Brian Cunnie
e13f14535b Fix random test failures by choosing ports better
My integration tests would randomly fail 5% of the time (based on a sample size
of 59 tests), and the reason was that my algorithm for choosing a random
port was flawed. I was very proud of that algorithm, so accepting that
it was flawed was a bitter pill.

One of the problems was that it had unnecessarily limited the range of
available ports to pick from to 1,000. This change expands that
selection to 64,511.

I changed to a less-clever-but-more-reliable algorithm, and the results
are stunning order-of-magnitude increase in reliability: 0.5% failure
rate (based on 210 tests).

Fixes, when running `ginkgo -r -p -until-it-fails .`

```
Got stuck at:
    ...
    2023/11/19 21:52:15 I couldn't bind via UDP to any IPs on port 1941, so I'm exiting
Waiting for:
    Ready to answer queries
```
2023-11-29 15:10:53 -08:00
Brian Cunnie
91c23a3a48 Elaborate on why to use certain flags
e.g. `-quiet` can save $30 / month. Or set `-nameservers` and
`-addresses` if you're running your own sslip.io nameservers.
2023-11-29 14:59:04 -08:00
Brian Cunnie
f0b5ed0e63 Classless Inter-Domain Routing: "CIDR" not "CDIR"
This is a cosmetic change, but one that's important to me.

I also updated the comment to reflect the purpose of `BlockListCIDRs`.
2023-11-29 12:45:56 -08:00
Brian Cunnie
bcbf75a25b Shorten TTL for publicly-accessible A & AAAA records
If we have IPs that we need to block, I want them to time-out within the
hour.

TTL: 604800 → 3600 (1 week → 1 hour)
2023-11-19 13:50:28 -08:00
Brian Cunnie
aacd566ab4 3.0.0: enable TCP binding in addition to UDP 3.0.0 2023-10-04 08:07:03 -07:00
Brian Cunnie
85991a0793 Document the "TCP/UDP" metrics
Also, the README points out that we now bind to both UDP & TCP;
previously it said that we only bound to UDP.
2023-10-04 07:52:52 -07:00
Brian Cunnie
2df94a4352 🐞 Make integration tests more robust
I'd assert that the server had exited with a 1 (error condition) when it
couldn't bind via UDP to any addresses; however, I wrote the expectation
wrong, and sometimes the server hadn't exited by the time I made the
assertion, resulting in an exit code of -1 (not yet exited) instead of
1.

Using an async assertion `Eventually()`, with a switch `ExitCode()` →
`Exit()`, fixes that problem.

Fixes, during `ginkgo -r -p`:
```
  [FAILED] Expected
      <int>: -1
  to equal
      <int>: 1
  In [It] at: /home/cunnie/workspace/sslip.io/src/sslip.io-dns-server/integration_test.go:400 @ 10/02/23 03:58:15.824
```
2023-10-02 04:51:55 -07:00
Brian Cunnie
ce94dfc20b Metrics: track the use of TCP vs. UDP
Why implement a feature w/out measuring how much it gets used?

I want to know who, if anyone, is using TCP queries.

TODO: update the documentation.
2023-10-01 18:35:49 -07:00
Brian Cunnie
358d85bb04 Test TCP binding failure modes
- If it can't bind to all addresses via TCP, log the ones it could &
  couldn't bind to & keep running
- If it can't bind to any address via TCP, keep running (unlike UDP
  which must fail)

The big challenge in writing these tests is that the binding behavior is
different for macOS (Ventura 13.6 (22G120)) than for Linux.
Specifically, to "squat" on an address, macOS must listen on ALL TCP
addresses (INADDR_ANY) plus the specific address. Linux only needs to
listen to the specific address.

I have no idea what the behavior on Windows is.

I also removed listenPort as a top-level variable; it didn't need to be
top level.
2023-10-01 14:18:03 -07:00
Brian Cunnie
2eab823fc1 Less verbose testing
I was printing out the throughput (queries/second) in the middle of the
ginkgo tests, and it was unseemly and didn't belong.

I changed the test to make sure that the throughput was > 1,000 queries
per second. No unnecessary output.
2023-10-01 13:59:53 -07:00
Brian Cunnie
7bf617996d Bump serial 2023031500 → 2023093000 2023-09-30 12:56:25 -07:00
Brian Cunnie
9873f4f3f2 Bump dependencies 2023-09-30 12:49:49 -07:00
Brian Cunnie
81f9f6c9a3 Listen on TCP, not solely UDP
I've wanted sslip.io to bind to both UDP & TCP, mostly because TCP is
more secure (at least with regards to DNS cache poisoning).

In general, the process to receive a packet, whether TCP or UDP, is
similar.

- UDP uses `net.UDPConn`, TCP uses `net.TCPListener`
- Once bound, UDP uses `ReadFromUDP()` to get the data; TCP first
  requires an `AcceptTCP()` followed by a `Read()`
- Technically you can ask several queries over a single TCP socket, but
  I close the connection after the first query.
- DNS TCP packet has a two-byte length field that has no counterpart in
  the DNS UDP packet.
- The TCP integration tests are lacking.
2023-09-30 09:14:20 -07:00
Brian Cunnie
b09bccdd86 🐞 Make integration tests IPv4/IPv6 stack-agnostic
The integration test which worked fine on my dual-stack laptop failed on
my IPv4-only Concourse.

Fixes, when running `ginkgo -r -p .` on an IPv4-only machine:
```
sslip.io-dns-server When it can't bind to a port on loopback [BeforeEach] prints an informative message and continues
  [BeforeEach] /tmp/build/b4e0c68a/sslip.io/src/sslip.io-dns-server/integration_test.go:399
  [It] /tmp/build/b4e0c68a/sslip.io/src/sslip.io-dns-server/integration_test.go:409
  [FAILED] Unexpected error:
      <*net.OpError | 0xc000310d20>:
      listen udp [::1]:1918: socket: address family not supported by protocol
```
2023-09-30 09:01:01 -07:00