While Linux systems have long supported IPv4 address configuration through kernel boot parameters using the ip=
syntax, the equivalent functionality for IPv6 remains conspicuously absent from standard kernel documentation. This gap becomes particularly problematic in scenarios like:
# Example of IPv4 boot configuration we're trying to match for IPv6
ip=192.0.2.1::192.0.2.62:255.255.255.192::eth0:none
For systems requiring early IPv6 connectivity (particularly in pre-boot environments), we have several suboptimal alternatives:
# Option 1: Static configuration in initramfs
ip -6 addr add 2001:db8::1/64 dev eth0
ip -6 route add default via 2001:db8::fffe
The fundamental issue is that none of these solutions integrate with the kernel's early boot parameter system as cleanly as the IPv4 ip=
parameter does.
After examining kernel source (particularly net/ipv6/addrconf.c
and drivers/net/netconsole.c
), I found no built-in equivalent to ip=
for IPv6. However, we can implement this through:
# Option 2: Custom kernel patch
diff --git a/net/ipv6/addrconf.c b/net/ipv6/addrconf.c
index 1a2b3c4..5d6e7f9 100644
--- a/net/ipv6/addrconf.c
+++ b/net/ipv6/addrconf.c
@@ -4641,6 +4641,33 @@ static int __init addrconf_init(void)
{
int err;
+ /* Check for ip6= boot parameter */
+ {
+ char *ip6_param, *ifname, *addr, *next;
+ ip6_param = strstr(boot_command_line, "ip6=");
+ if (ip6_param) {
+ ip6_param += 4; // Skip "ip6="
+ ifname = strsep(&ip6_param, ":");
+ addr = strsep(&ip6_param, ":");
+ if (ifname && addr) {
+ struct in6_addr in6;
+ if (in6_pton(addr, -1, (u8 *)&in6, '\0', NULL) > 0) {
+ struct net_device *dev;
+ dev = dev_get_by_name(&init_net, ifname);
+ if (dev) {
+ struct inet6_ifaddr *ifp;
+ ifp = ipv6_add_addr(dev, &in6, 0,
+ IFA_F_PERMANENT);
+ if (!IS_ERR(ifp))
+ printk(KERN_INFO "IPv6 boot address %pI6 configured on %s\n",
+ &ifp->addr, ifname);
+ dev_put(dev);
+ }
+ }
+ }
+ }
+ }
+
err = addrconf_init_net(&init_net);
if (err < 0)
goto out;
For users who can't modify their kernel, consider these approaches:
# Option 3: Early userspace script in initramfs
#!/bin/sh
PREREQ="network"
prereqs() {
echo "$PREREQ"
}
case $1 in
prereqs)
prereqs
exit 0
;;
esac
ip link set eth0 up
ip -6 addr add 2001:db8::1/64 dev eth0
ip -6 route add default via 2001:db8::fffe
For systems using dropbear in initramfs, ensure your init script includes:
# Example for Debian/Ubuntu initramfs-tools
local_ip=2001:db8::1
remote_ip=2001:db8::fffe
ip -6 addr add $local_ip/64 dev eth0
ip -6 route add default via $remote_ip
The Linux kernel's ip=
boot parameter follows this syntax for IPv4 configuration:
ip=client_ip:server_ip:gw_ip:netmask:hostname:interface:none
Example configuration that sets static IPv4 on eth0:
ip=192.0.2.1::192.0.2.62:255.255.255.192::eth0:none
Unlike IPv4, there's no direct kernel boot parameter equivalent for IPv6. The need arises in scenarios like:
- Pre-boot environments (e.g., Dropbear SSH for encrypted root unlock)
- Network segments without DHCPv6 or RA
- Hosting provider networks where network configuration cannot be modified
Method 1: Using initramfs scripts
Add this to your initramfs scripts (e.g., /etc/initramfs-tools/scripts/init-premount/static_ipv6
):
#!/bin/sh
PREREQ=""
prereqs()
{
echo "$PREREQ"
}
case $1 in
prereqs)
prereqs
exit 0
;;
esac
ip -6 addr add 2001:db8::1/64 dev eth0
ip -6 route add default via 2001:db8::ffff
Then update initramfs:
chmod +x /etc/initramfs-tools/scripts/init-premount/static_ipv6
update-initramfs -u
Method 2: GRUB network configuration
For systems using GRUB with network boot:
menuentry 'Linux with IPv6' {
linux /boot/vmlinuz root=/dev/sda1 ipv6.disable=0
initrd /boot/initrd.img
# GRUB network commands (limited IPv6 support)
net_add_addr enp0s3 2001:db8::1/64
net_add_route default 2001:db8::ffff
}
Method 3: Kernel command-line extension
Create a custom kernel parameter handler by modifying the kernel source (advanced):
// In drivers/net/netconsole.c or similar
static int __init ipv6_setup(char *str)
{
char *ip_str, *dev_str;
ip_str = strsep(&str, ":");
dev_str = str;
if (ip_str && dev_str) {
printk(KERN_INFO "Configuring IPv6 %s on %s\n", ip_str, dev_str);
// Actual implementation would call netdevice APIs
}
return 1;
}
__setup("ipv6=", ipv6_setup);
When kernel-level configuration isn't possible:
- Early userspace scripts: Systemd units with
Before=network.target
- Network manager hooks: Use
nmcli
in startup scripts - Cloud-init: For cloud environments with metadata service
The inability to configure IPv6 at boot creates challenges for:
- Headless servers in remote locations
- Secure boot environments requiring early network access
- Network bootstrap systems without DHCP infrastructure
Current Linux distributions typically handle this through userspace networking daemons, but for special cases, the above solutions provide viable alternatives.