Previously on VyOS for Home Use

VyOS for Home Use: Part 1 – Initial Setup
VyOS for Home Use: Part 2 – Internet Access

Part 2 Recap

In Part 2, we configured our router to have an IP from our provider, as well as secured it with a firewall configuration. Our router is now ready to have LAN connections added so our users can start using it.

Identifying our LAN interface(s)

Just like when we were setting up our WAN interface, we need to know what interface to configure. If you labeled your interfaces (or if you only have 2 interfaces), then you probably already know what interface you’re using. If you’re not sure, just connect something to an interface and see what comes up. After connecting an interface, I can see that “eth2” has a status of “u/u” in the “S/L” column. So that is what I’ll be using as my LAN interface.

admin@GK41:~$ show interfaces 
Codes: S - State, L - Link, u - Up, D - Down, A - Admin Down
Interface IP Address MAC VRF MTU S/L Description
----------- -------------- ----------------- ------- ----- ----- -------------
eth1 xx.x.95.244/24 84:47:09:2d:a9:80 default 1500 u/u Internet
eth2 - 84:47:09:2d:a9:82 default 1500 u/u
lo 127.0.0.1/8 00:00:00:00:00:00 default 65536 u/u
::1/128

To VLAN or not to VLAN

If your switch supports VLANs, it can be a good idea to start using VLANs from the start. You can have your Wireless clients use a different subnet than your wired clients. This allows you to have different security postures for each network. Throughout this whole series, I am assuming that the user has a simple network and can’t use VLANs, but I will show how to configure an interface with VLANs.

Configuring an interface with VLANs.

We will configure the interface similar to what we did for our WAN interface, but we need to apply our IP config under a virtual interface

set interfaces ethernet eth2 vif 10 address 10.0.10.1/24
set interfaces ethernet eth2 vif 20 address 10.0.20.1/24

Remember, to enter Conf Mode, type “configure”


And of course, don’t forget to give your interfaces useful descriptions.

set interfaces ethernet eth2 description 'LAN connection to Switch port 1'
set interfaces ethernet eth2 vif 10 description 'Wired Clients'
set interfaces ethernet eth2 vif 20 description 'Wireless Clients'


Our full config would look something like this. We would commit if everything looked correct.

admin@GK41# compare commands 

set interfaces ethernet eth2 description 'LAN connection to Switch port 1'
set interfaces ethernet eth2 vif 10 address '10.0.10.1/24'
set interfaces ethernet eth2 vif 10 description 'Wired Clients'
set interfaces ethernet eth2 vif 20 address '10.0.20.1/24'
set interfaces ethernet eth2 vif 20 description 'Wireless Clients'

commit


We could verify our interfaces with the “show interfaces” Op command.

admin@GK41# run show interfaces 
Codes: S - State, L - Link, u - Up, D - Down, A - Admin Down
Interface IP Address MAC VRF MTU S/L Description
----------- -------------- ----------------- ------- ----- ----- -------------------------------
eth1 xx.x.95.244/24 84:47:09:2d:a9:80 default 1500 u/u Internet
eth2 - 84:47:09:2d:a9:82 default 1500 u/u LAN connection to Switch port 1
eth2.10 10.0.10.1/24 84:47:09:2d:a9:82 default 1496 u/u Wired Clients
eth2.20 10.0.20.1/24 84:47:09:2d:a9:82 default 1496 u/u Wireless Clients

lo 127.0.0.1/8 00:00:00:00:00:00 default 65536 u/u
::1/128

Configuring the LAN interface without VLANs

I’m going to assume this will be the more common deployment for users that want VyOS as a home router, so going forward all configurations will show the LAN interface without VLANs.


We need to add an IP, as well as a useful description to our interface.

set interfaces ethernet eth2 address '10.0.10.1/24'
set interfaces ethernet eth2 description 'LAN connection to Switch port 1'

commit


We can see the interface configured

admin@GK41# run show interfaces
Codes: S - State, L - Link, u - Up, D - Down, A - Admin Down
Interface IP Address MAC VRF MTU S/L Description
----------- -------------- ----------------- ------- ----- ----- -------------------------------
eth1 xx.x.95.244/24 84:47:09:2d:a9:80 default 1500 u/u
eth2 10.0.10.1/24 84:47:09:2d:a9:82 default 1500 u/u LAN connection to Switch port 1
lo 127.0.0.1/8 00:00:00:00:00:00 default 65536 u/u
::1/128

Updating the Firewall

Since this interface is from the trusted side of our network, we need to update some of our firewall rules. We will update the input and forward chains to explicitly allow traffic from the LAN interface. I like to put the rule out of the way, that’s why I use rule ‘1000’.

set firewall ipv4 forward filter rule 1000 action 'accept'
set firewall ipv4 forward filter rule 1000 description 'Allow all traffic from LAN interface'
set firewall ipv4 forward filter rule 1000 inbound-interface name 'eth2'

set firewall ipv4 input filter rule 1000 action 'accept'
set firewall ipv4 input filter rule 1000 description 'Allow all traffic from LAN interface'
set firewall ipv4 input filter rule 1000 inbound-interface name 'eth2'


We also need to add the LAN interface to our flow table.

set firewall flowtable FT1 interface eth2


Let’s check our config before we commit.

admin@GK41# compare commands

set firewall flowtable FT1 interface 'eth2'
set firewall ipv4 forward filter rule 1000 action 'accept'
set firewall ipv4 forward filter rule 1000 description 'Allow all traffic from LAN interface'
set firewall ipv4 forward filter rule 1000 inbound-interface name 'eth2'
set firewall ipv4 input filter rule 1000 action 'accept'
set firewall ipv4 input filter rule 1000 description 'Allow all traffic from LAN interface'
set firewall ipv4 input filter rule 1000 inbound-interface name 'eth2'


If everything looks good, we can commit.

admin@GK41# save
Warning: you have uncommitted changes that will not be saved.

commit commit-confirm
admin@GK41# commit-confirm 5

commit-confirm will automatically reboot in 5 minutes unless changes
are confirmed.

Proceed ? [Y/n] y
Initialized commit-confirm; 5 minutes to confirm before reboot


And if you haven’t lost access, you can confirm and save your config.

admin@GK41# confirm
Reboot timer stopped

admin@GK41# save

NOTE: When you’re using the console (either KVM or serial), you are not really in danger of losing access, but if you are using SSH to manage the router, you could. If you’re using SSH, and make a firewall change, it is smart to log in with another session to make sure you can get in with new sessions.

Adding a DHCP Pool

Before our hosts can use our router, we need them to be able to pull an IP address from our router. We will create a DHCP pool for our LAN connections.

NOTE: If you’re using separate LAN subnets using VLANs, you need a DHCP Pool per subnet.


I already created my LAN interface in the 10.0.10.0/24 subnet, so that is the pool I need to create. I need to create a subnet-id for this pool. It can be anything from 1-4294967295

set service dhcp-server shared-network-name Users subnet 10.0.10.0/24 subnet-id 1


Then we need to designate what the gateway should be for our clients. The gateway for this will be our LAN interface (10.0.10.1).

set service dhcp-server shared-network-name Users subnet 10.0.10.0/24 option default-router '10.0.10.1'


Next we need to define the range of IPs that can be issued by DHCP. You may want to put the full range of IPs in here, but it’s wise to leave room for static IPs for devices like printers.

set service dhcp-server shared-network-name Users subnet 10.0.10.0/24 range 0 start '10.0.10.10'
set service dhcp-server shared-network-name Users subnet 10.0.10.0/24 range 0 stop '10.0.10.250'


We also need to tell the clients what to use as a DNS server. I generally recommend pinging different DNS servers to see which one has the lowest latency from you. I find that ‘9.9.9.9’ is the best server for me.

set service dhcp-server shared-network-name Users subnet 10.0.10.0/24 option name-server '9.9.9.9'

NOTE: There are some minor syntactical differences between 1.4 and 1.5. If you’re using 1.4, you may have to modify this slightly (mostly just don’t put stuff like ‘default-router’ and ‘name-server’ under ‘option’, and you don’t need the ‘subnet-id’).


If everything looks good, we can commit our config.

admin@GK41# compare commands

set service dhcp-server shared-network-name Users subnet 10.0.10.0/24 option default-router '10.0.10.1'
set service dhcp-server shared-network-name Users subnet 10.0.10.0/24 option name-server '9.9.9.9'
set service dhcp-server shared-network-name Users subnet 10.0.10.0/24 range 0 start '10.0.10.10'
set service dhcp-server shared-network-name Users subnet 10.0.10.0/24 range 0 stop '10.0.10.250'

commit


Once we connect a host to the interface (or in my case, a switch connected to the LAN interface), we should pull an IP for the host (provided the host is configured to pull an IP via DHCP). We can verify this with the following Op command.

admin@GK41# run show dhcp server leases
IP Address MAC address State Lease start Lease expiration Remaining Pool Hostname Origin
------------ ----------------- ------- ------------------- ------------------- ----------- ------ ---------------- --------
10.0.10.10 70:85:c2:a8:8d:3e active 2024/06/16 20:45:18 2024/06/17 20:45:18 23:57:25 Users desktop-37rabmr. local


Let’s try to ping the internet.

C:\WINDOWS\system32>ping 4.2.2.2

Pinging 4.2.2.2 with 32 bytes of data:
Request timed out.
Request timed out.
Request timed out.
Request timed out.

Ping statistics for 4.2.2.2:
Packets: Sent = 4, Received = 0, Lost = 4 (100% loss),


It’s not working! Let’s do a tcpdump on the WAN interface of the router and see what’s happening.

admin@GK41# sudo tcpdump -ni eth1 icmp
tcpdump: verbose output suppressed, use -v[v]... for full protocol decode
listening on eth1, link-type EN10MB (Ethernet), snapshot length 262144 bytes
20:53:20.264325 IP 10.0.10.10 > 4.2.2.2: ICMP echo request, id 7, seq 63244, length 40


We can see that our source IP is the hosts IP, but hosts on the internet have no idea how to get back to that.

Network Address Translation

To solve this, we need to configure Network Address Translation (NAT) so that we can replace our source IP address with the address of our externally facing interface. This is why this specific NAT is called “Source NAT”, or SNAT.


We start by defining what our external interface is, which in my case is “eth1”. This says I want you to NAT traffic that leaves out of this interface.

set nat source rule 10 outbound-interface name eth1


Next we will say what IP we want to replace the source address with. We’re going to use something called ‘masquerade’, which is just replacing the source address with the IP of the interface it leaves out of (“eth1” in my case).

set nat source rule 10 translation address masquerade


And always, make sure you give it a useful description.

set nat source rule 10 description "NAT source address for all traffic leaving eth1"


If everything looks good, we can commit our configuration.

admin@GK41# compare commands

set nat source rule 10 description 'NAT source address for all traffic leaving eth1'
set nat source rule 10 outbound-interface name 'eth1'
set nat source rule 10 translation address 'masquerade'

commit


Let’s try our ping again.

C:\WINDOWS\system32>ping 4.2.2.2

Pinging 4.2.2.2 with 32 bytes of data:
Reply from 4.2.2.2: bytes=32 time=5ms TTL=57
Reply from 4.2.2.2: bytes=32 time=5ms TTL=57
Reply from 4.2.2.2: bytes=32 time=4ms TTL=57
Reply from 4.2.2.2: bytes=32 time=5ms TTL=57

Ping statistics for 4.2.2.2:
Packets: Sent = 4, Received = 4, Lost = 0 (0% loss),
Approximate round trip times in milli-seconds:
Minimum = 4ms, Maximum = 5ms, Average = 4ms


And we can also see in our tcpdump, that the IP has been replaced.

admin@GK41# sudo tcpdump -ni eth1 icmp
tcpdump: verbose output suppressed, use -v[v]... for full protocol decode
listening on eth1, link-type EN10MB (Ethernet), snapshot length 262144 bytes
21:04:22.288931 IP xx.x.95.244 > 4.2.2.2: ICMP echo request, id 7, seq 63291, length 40
21:04:22.292529 IP 4.2.2.2 > xx.x.95.244: ICMP echo reply, id 7, seq 63291, length 40

Allowing SSH

The last thing we want to do before doing further testing is enable SSH on our device. This will make it easier to manage our router, since we won’t always have to connect it to a monitor and keyboard.


We need to enable the SSH service, and scope it to a specific IP to limit what can be accessed. I like to create a dummy interface for this.

set interfaces dummy dum0 address 10.0.0.1/32


Next we need to limit SSH to only that IP.

set service ssh listen-address '10.0.0.1'


If everything looks good, we can commit our configuration and try to SSH to 10.0.0.1.

admin@GK41# compare commands

set interfaces dummy dum0 address '10.0.0.1/32'
set service ssh listen-address '10.0.0.1'



We now have a fully functional VyOS router for home use.


Let’s see a speed test result.


I was doing other things with my internet at that time, so that was the max throughput available for the speed test at the time.

Performance

With normal internet usage, here is the resource utilization of this $100USD mini PC.


And here is the utilization when maxing out a 1Gbps internet connection during the speed test.

Conclusion

You can see that VyOS is incredibly optimized. Not only can we max out a 1Gbps internet connection, we have plenty of headroom for more traffic….or additional services.


In part 4 of this series, we’ll do exactly that by adding network level DNS filtering using AdGuard.

6 responses to “VyOS for Home Use: Part 3 – LAN Connections”

  1. I’m curious, why do you put SSH on a dummy interface?

    1. It’s an always up interface, so you can have redundant paths on the LAN side and it’ll always be reachable on the same IP no matter which link(s) are up at that time.

  2. What about the idea to combine AdGuard function of DHCP, I mean to make AdGuard as dhcp server, this way you can track all dns request from LAN clients. (not sure if it is supported in container AdGuard version)

    1. You can definitely do that, but the limitation of using AdGuard for DHCP is it only supports a single pool. If you’ll only ever have 1 pool, then that’s fine. But if you wanted different networks for wired and wireless, or users and guests, you wouldn’t be able to have multiple pools.

      I’ve always wished AdGuard and PiHole supported multiple pools, but I don’t believe either have added that capability.

  3. Not sure I understand the mtu 1496 for when you use vlan option in vyos. If you use vif (vlan) and you connect your vyos lan interface to a switch that understands 802.1q tagging, you would want to keep the mtu as 1500…else all your lan devices would need to change to 1496 to match your vyos router (or risk devices sending packets too large towards vyos lan interface to process). Appreciate your content and videos, interesting topics!

    1. Without setting the MTU, it will be set to 1500, which is also the default of the physical interface. That makes the actual MTU of the VIF interface 1496, whether you set it as 1496 or not.

      If a client has an MTU of 1500, then the packet as received on the VyOS interface would be 1504 (1518 with Ethernet header), accounting for the dot1q tag from the switch, which would cause fragmentation against the 1500B MTU. Setting the MTU on the VIF interface to 1496 at least gives Path MTU Discovery (PMTUD) a chance to avoid fragmentation (assuming the client supports it, which clients on a home network often do).

      VyOS does support MSS Clamping, but I was trying to keep things simple in this series.

Leave a Reply

Trending

Discover more from Level Zero Networking

Subscribe now to keep reading and get access to the full archive.

Continue reading