txthinking/brook · error
no ipv4 from nic
Error message
no ipv4 from nic
What it means
In the same IP method, when v46 == "4" the code looks for a globally-unicast, PRIVATE IPv4 address (IsPrivate() && To4() != nil) to use as the source. Error [73] means the interface's address list contained no matching private IPv4 address — the host has no private IPv4 address on the selected NIC. The library intentionally wants an RFC1918-style source address and refuses to continue without one.
Source
Thrown at plugins/dialwithnic/dialwithnic.go:62
for _, v := range addrs {
if v.(*net.IPNet).IP.IsGlobalUnicast() && v.(*net.IPNet).IP.To4() == nil {
return v.(*net.IPNet).IP, nil
}
}
return nil, errors.New("no ipv6 from nic")
}
if v46 == "4" {
for _, v := range addrs {
if v.(*net.IPNet).IP.IsGlobalUnicast() && !v.(*net.IPNet).IP.IsPrivate() && v.(*net.IPNet).IP.To4() != nil {
return v.(*net.IPNet).IP, nil
}
}
for _, v := range addrs {
if v.(*net.IPNet).IP.IsGlobalUnicast() && v.(*net.IPNet).IP.IsPrivate() && v.(*net.IPNet).IP.To4() != nil {
return v.(*net.IPNet).IP, nil
}
}
return nil, errors.New("no ipv4 from nic")
}
return nil, errors.New("black hole")
}
func (p *DialWithNIC) TouchBrook() {
brook.DialTCP = func(network string, laddr, raddr string) (net.Conn, error) {
var la, ra *net.TCPAddr
if laddr != "" {
var err error
la, err = net.ResolveTCPAddr(network, laddr)
if err != nil {
return nil, err
}
}
a, err := brook.Resolve(network, raddr)
if err != nil {
return nil, err
}View on GitHub (pinned to 5cd13ef3b1)
Solutions
- Verify the NIC actually has a private IPv4 address (`ip -4 addr`); if not, add/configure one or pick a different interface whose addr list is passed to IP().
- Check the addr-selection/filtering upstream of this loop — if the library lets you choose the NIC, select one with an RFC1918 address.
- If a public IPv4 is the only option and fits your use case, bypass the NIC-source constraint and use the default dialer instead of DialWithNIC.
- Handle the error as 'no private IPv4 available' and fall back to IPv6 or the default dial path.
Example fix
// before
ip, err := plugin.IP("4") // NIC has only a public IPv4
// after
ip, err := plugin.IP("4")
if err != nil {
// use default dialer without binding to a private source IP
conn, err := net.Dial("tcp", addr)
} Defensive patterns
Strategy: fallback
Validate before calling
func hasPrivateIPv4() bool {
for _, a := range interfaceAddrs() {
if ipnet, ok := a.(*net.IPNet); ok && ipnet.IP.IsGlobalUnicast() && ipnet.IP.IsPrivate() && ipnet.IP.To4() != nil {
return true
}
}
return false
}
// only call plugin.IP("4") if hasPrivateIPv4() Type guard
func isPrivateIPv4(ip net.IP) bool {
return ip.To4() != nil && ip.IsGlobalUnicast() && ip.IsPrivate()
} Try / catch
ip, err := plugin.IP("4")
if err != nil && err.Error() == "no ipv4 from nic" {
log.Println("no private IPv4 on NIC, using default dialer")
conn, err = net.Dial("tcp", addr)
} Prevention
- Check `ip -4 addr` / net.InterfaceAddrs() for an RFC1918 address before using DialWithNIC.
- Remember the library wants a PRIVATE IPv4 source; a public-only interface will fail — pick a NIC with an internal address.
- Avoid relying on this plugin in IPv6-only or public-IP-only environments.
- Provide a fallback dial path in callers when source-NIC binding is unavailable.
When it happens
Trigger: Calling IP(v46="4") when the enumerated addrs contain no global-unicast private IPv4 address — e.g. the NIC only has IPv6, only a public IPv4 address, or only loopback (127.0.0.1 fails IsGlobalUnicast for the intended use).
Common situations: Running in environments where the NIC has only a public IP (some cloud VMs with public IPs directly on the interface); IPv6-only containers; misconfigured interface selection passing the wrong interface's addr list; hosts where the only IPv4 address is loopback.
Understand the failure class
Background: 'Could not be found', 'does not exist', 'not found in database': the resource-not-found family when an ID, slug, key, or URI lookup comes back empty — this error's family across 20 libraries.
Related errors
- Invalid dial with IP
- no ipv6 from nic
- black hole
- socks5 server requires a clear IP for UDP, only port is not
- Looks like you want create socks5 from a socks5, you may wan
AI-assisted analysis of txthinking/brook@5cd13ef3b1 (2026-09-06).
Data as JSON: /api/errors/db23da24a599194c.
Report an issue: GitHub.