|
|
@@ -45,14 +45,14 @@ Iface Destination Gateway Flags RefCnt Use Metric Mask
|
|
|
ens18 00000000 0100000A 0003 0 0 0 00000000 0 0 0
|
|
|
ens18 0000000A 00000000 0001 0 0 0 0000FFFF 0 0 0
|
|
|
*/
|
|
|
-func likelyHomeRouterIPLinux() (ret netip.Addr, ok bool) {
|
|
|
+func likelyHomeRouterIPLinux() (ret netip.Addr, myIP netip.Addr, ok bool) {
|
|
|
if procNetRouteErr.Load() {
|
|
|
// If we failed to read /proc/net/route previously, don't keep trying.
|
|
|
// But if we're on Android, go into the Android path.
|
|
|
if runtime.GOOS == "android" {
|
|
|
return likelyHomeRouterIPAndroid()
|
|
|
}
|
|
|
- return ret, false
|
|
|
+ return ret, myIP, false
|
|
|
}
|
|
|
lineNum := 0
|
|
|
var f []mem.RO
|
|
|
@@ -99,7 +99,27 @@ func likelyHomeRouterIPLinux() (ret netip.Addr, ok bool) {
|
|
|
log.Printf("interfaces: failed to read /proc/net/route: %v", err)
|
|
|
}
|
|
|
if ret.IsValid() {
|
|
|
- return ret, true
|
|
|
+ // Try to get the local IP of the interface associated with
|
|
|
+ // this route to short-circuit finding the IP associated with
|
|
|
+ // this gateway. This isn't fatal if it fails.
|
|
|
+ if len(f) > 0 && !disableLikelyHomeRouterIPSelf() {
|
|
|
+ ForeachInterface(func(ni Interface, pfxs []netip.Prefix) {
|
|
|
+ // Ensure this is the same interface
|
|
|
+ if !f[0].EqualString(ni.Name) {
|
|
|
+ return
|
|
|
+ }
|
|
|
+
|
|
|
+ // Find the first IPv4 address and use it.
|
|
|
+ for _, pfx := range pfxs {
|
|
|
+ if addr := pfx.Addr(); addr.Is4() {
|
|
|
+ myIP = addr
|
|
|
+ break
|
|
|
+ }
|
|
|
+ }
|
|
|
+ })
|
|
|
+ }
|
|
|
+
|
|
|
+ return ret, myIP, true
|
|
|
}
|
|
|
if lineNum >= maxProcNetRouteRead {
|
|
|
// If we went over our line limit without finding an answer, assume
|
|
|
@@ -113,12 +133,12 @@ func likelyHomeRouterIPLinux() (ret netip.Addr, ok bool) {
|
|
|
// find one in the future.
|
|
|
procNetRouteErr.Store(true)
|
|
|
}
|
|
|
- return netip.Addr{}, false
|
|
|
+ return netip.Addr{}, netip.Addr{}, false
|
|
|
}
|
|
|
|
|
|
// Android apps don't have permission to read /proc/net/route, at
|
|
|
// least on Google devices and the Android emulator.
|
|
|
-func likelyHomeRouterIPAndroid() (ret netip.Addr, ok bool) {
|
|
|
+func likelyHomeRouterIPAndroid() (ret netip.Addr, _ netip.Addr, ok bool) {
|
|
|
cmd := exec.Command("/system/bin/ip", "route", "show", "table", "0")
|
|
|
out, err := cmd.StdoutPipe()
|
|
|
if err != nil {
|
|
|
@@ -148,7 +168,7 @@ func likelyHomeRouterIPAndroid() (ret netip.Addr, ok bool) {
|
|
|
})
|
|
|
cmd.Process.Kill()
|
|
|
cmd.Wait()
|
|
|
- return ret, ret.IsValid()
|
|
|
+ return ret, netip.Addr{}, ret.IsValid()
|
|
|
}
|
|
|
|
|
|
func defaultRoute() (d DefaultRouteDetails, err error) {
|