๐งช Beginner KVM Networking Lab with Alpine Linux (Step-by-Step)
In this tutorial, we will:
- Download Alpine Linux ISO
- Create
alpine1VM - Install Alpine to disk
- Verify NAT networking
- Clone and create
alpine2 - Test VM-to-VM communication
All using KVM + libvirt on Ubuntu.
We use:
Alpine Linux
because it is extremely lightweight and perfect for networking labs.
๐งฑ Lab Architecture
We will use the default libvirt NAT network:
Host (Ubuntu)
โโโ virbr0 (192.168.121.1/24)
โโโ alpine1
โโโ alpine2
- VMs can talk to each other
- VMs can access internet via NAT
- VMs are not reachable from outside
๐ฅ Step 1 โ Download Alpine ISO
Download Alpine (virt edition recommended for KVM):
wget https://dl-cdn.alpinelinux.org/alpine/v3.19/releases/x86_64/alpine-virt-3.19.1-x86_64.iso
Move it to libvirt image directory:
sudo mv alpine-virt-3.19.1-x86_64.iso /var/lib/libvirt/images/
Verify:
ls -lh /var/lib/libvirt/images/
๐ฅ Step 2 โ Create alpine1 VM
Create a 4GB disk and attach ISO:
sudo virt-install \
--name alpine1 \
--memory 256 \
--vcpus 1 \
--disk path=/var/lib/libvirt/images/alpine1.qcow2,size=4,format=qcow2 \
--cdrom /var/lib/libvirt/images/alpine-virt-3.19.1-x86_64.iso \
--os-variant generic \
--network network=default \
--graphics none \
--console pty,target_type=serial
Explanation:
| Option | Purpose |
|---|---|
--memory 256 |
Lightweight VM |
--disk size=4 |
Create 4GB disk |
--network default |
Attach to NAT bridge |
--graphics none |
CLI only |
--console |
Serial console access |
๐ฅ Step 3 โ Install Alpine Inside VM
Inside VM:
setup-alpine
Important answers:
- Hostname โ
alpine1 - Network โ
eth0 - IP โ
dhcp - Proxy โ
none - SSH server โ
openssh - Disk โ
sda - Install mode โ
sys - Confirm erase โ
y
After installation:
reboot
๐งน Step 4 โ Verify ISO Removed
On host:
sudo virsh domblklist alpine1
You should see:
Target Source
---------------------------------
hda /var/lib/libvirt/images/alpine1.qcow2
No ISO attached = good.
๐ Step 5 โ Verify Networking
Connect to console:
sudo virsh console alpine1
Inside VM:
ip a
ip route
You should see something like:
inet 192.168.121.100/24
default via 192.168.121.1
Test internet:
ping 8.8.8.8
If it works โ NAT is working ๐
๐ Step 6 โ Inspect Networking From Host
Check bridge:
ip a | grep virbr0
You should see:
virbr0: 192.168.121.1/24
Check bridge members:
brctl show
You should see:
virbr0 vnetX
Check NAT rules:
sudo iptables -t nat -L -n
Look for:
MASQUERADE 192.168.121.0/24
This rule allows VM internet access.
๐ฅ Step 7 โ Clone alpine1 to Create alpine2
Do NOT manually copy disk.
Use virt-clone:
sudo virt-clone \
--original alpine1 \
--name alpine2 \
--file /var/lib/libvirt/images/alpine2.qcow2
This:
- Copies disk safely
- Generates new MAC address
- Prevents network conflict
๐ฅ Step 8 โ Start alpine2
sudo virsh start alpine2
sudo virsh console alpine2
Inside alpine2:
ip a
It should get a different IP:
alpine1 โ 192.168.121.100
alpine2 โ 192.168.121.101
๐งช Step 9 โ Test VM-to-VM Communication
From alpine1:
ping <alpine2-ip>
Example:
ping 192.168.121.101
This traffic:
- Does NOT go through NAT
- Stays inside virbr0 bridge
- Pure Layer 2 switching
๐ Observe Host Again
brctl show
Now you will see:
virbr0
โโโ vnet10 (alpine1)
โโโ vnet11 (alpine2)
Each VM gets its own tap device.
๐ฆ What You Built
You now have:
โ 2 lightweight VMs (256MB each)
โ DHCP working
โ NAT outbound internet
โ VM-to-VM communication
โ Real bridge networking
โ Understanding of packet flow
๐ง Packet Flow Explained
VM โ Internet
VM โ vnetX โ virbr0 โ host โ iptables MASQUERADE โ Internet
VM โ VM
VM1 โ vnetX โ virbr0 โ vnetY โ VM2
No NAT involved.
๐ Resource Usage
Each Alpine VM:
- 256MB RAM
- 4GB disk
- ~60MB ISO
- Very fast boot
You can easily run 6โ8 VMs on a normal 8GB machine.
๐ Next Phase (Preview)
In the next phase, we will:
- Create isolated network (no NAT)
- Create internal bridge
- Make one VM act as router
- Add static routes
- Simulate multi-subnet enterprise network

Top comments (0)