// Copyright 2017 The Fuchsia Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

// +build !build_with_native_toolchain

package routes_test

import (
	"fmt"
	"net"
	"testing"

	"go.fuchsia.dev/fuchsia/src/connectivity/network/netstack/routes"

	"gvisor.dev/gvisor/pkg/tcpip"
	"gvisor.dev/gvisor/pkg/tcpip/stack"
)

var testRouteTable = routes.ExtendedRouteTable{
	// nic, subnet, gateway, metric, tracksInterface, dynamic, enabled
	createExtendedRoute(1, "127.0.0.1/32", "", 100, true, false, true),                 // loopback
	createExtendedRoute(1, "::1/128", "", 100, true, false, true),                      // loopback
	createExtendedRoute(4, "192.168.1.0/24", "", 100, true, true, true),                // DHCP IP (eth)
	createExtendedRoute(2, "192.168.100.0/24", "", 200, true, true, true),              // DHCP IP (wlan)
	createExtendedRoute(3, "10.1.2.0/23", "", 100, true, false, true),                  // static IP
	createExtendedRoute(2, "110.34.0.0/16", "192.168.100.10", 500, false, false, true), // static route
	// static route (eth)
	createExtendedRoute(4, "2610:1:22:123:34:faed::/96", "fe80::250:a8ff:9:79", 100, false, false, true),
	createExtendedRoute(4, "2622:0:2200:10::/64", "", 100, true, true, true),           // RA (eth)
	createExtendedRoute(4, "0.0.0.0/0", "192.168.1.1", 100, true, true, true),          // default (eth)
	createExtendedRoute(2, "0.0.0.0/0", "192.168.100.10", 200, true, true, true),       // default (wlan)
	createExtendedRoute(4, "::/0", "fe80::210:6e00:fe11:3265", 100, true, false, true), // default (eth)
}

func createRoute(nicid tcpip.NICID, subnet string, gateway string) tcpip.Route {
	_, s, err := net.ParseCIDR(subnet)
	if err != nil {
		panic(err)
	}
	sn, err := tcpip.NewSubnet(tcpip.Address(s.IP), tcpip.AddressMask(s.Mask))
	if err != nil {
		panic(err)
	}
	return tcpip.Route{
		Destination: sn,
		Gateway:     ipStringToAddress(gateway),
		NIC:         nicid,
	}
}

func createExtendedRoute(nicid tcpip.NICID, subnet string, gateway string, metric routes.Metric, tracksInterface bool, dynamic bool, enabled bool) routes.ExtendedRoute {
	return routes.ExtendedRoute{
		Route:                 createRoute(nicid, subnet, gateway),
		Metric:                metric,
		MetricTracksInterface: tracksInterface,
		Dynamic:               dynamic,
		Enabled:               enabled,
	}
}

func ipStringToAddress(ipStr string) tcpip.Address {
	return ipToAddress(net.ParseIP(ipStr))
}

func ipToAddress(ip net.IP) tcpip.Address {
	if v4 := ip.To4(); v4 != nil {
		return tcpip.Address(v4)
	}
	return tcpip.Address(ip)
}

func TestExtendedRouteMatch(t *testing.T) {
	for _, tc := range []struct {
		subnet string
		addr   string
		want   bool
	}{
		{"192.168.10.0/24", "192.168.10.0", true},
		{"192.168.10.0/24", "192.168.10.1", true},
		{"192.168.10.0/24", "192.168.10.10", true},
		{"192.168.10.0/24", "192.168.10.255", true},
		{"192.168.10.0/24", "192.168.11.1", false},
		{"192.168.10.0/24", "192.168.0.1", false},
		{"192.168.10.0/24", "192.167.10.1", false},
		{"192.168.10.0/24", "193.168.10.1", false},
		{"192.168.10.0/24", "0.0.0.0", false},

		{"123.220.0.0/14", "123.220.11.22", true},
		{"123.220.0.0/14", "123.221.11.22", true},
		{"123.220.0.0/14", "123.222.11.22", true},
		{"123.220.0.0/14", "123.223.11.22", true},
		{"123.220.0.0/14", "123.224.11.22", false},

		{"0.0.0.0/0", "0.0.0.0", true},
		{"0.0.0.0/0", "1.1.1.1", true},
		{"0.0.0.0/0", "255.255.255.255", true},

		{"2402:f000:5:8401::/64", "2402:f000:5:8401::", true},
		{"2402:f000:5:8401::/64", "2402:f000:5:8401::1", true},
		{"2402:f000:5:8401::/64", "2402:f000:5:8401:1:12:123::", true},
		{"2402:f000:5:8401::/64", "2402:f000:5:8402::", false},
		{"2402:f000:5:8401::/64", "2402:f000:15:8401::", false},
		{"2402:f000:5:8401::/64", "2402::5:8401::", false},
		{"2402:f000:5:8401::/64", "2400:f000:5:8401::", false},

		{"::/0", "::", true},
		{"::/0", "1:1:1:1:1:1:1:1", true},
		{"::/0", "ffff:ffff:ffff:ffff:ffff:ffff:ffff:ffff", true},
	} {
		t.Run("RouteMatch", func(t *testing.T) {
			er := createExtendedRoute(1, tc.subnet, "", 100, true, true, true)
			addr := ipStringToAddress(tc.addr)
			if got := er.Match(addr); got != tc.want {
				t.Errorf("got match addr %s in subnet %s = %t, want = %t", tc.addr, tc.subnet, got, tc.want)
			}
		})
	}
}

func TestSortingLess(t *testing.T) {
	for _, tc := range []struct {
		subnet1 string
		metric1 routes.Metric
		nic1    tcpip.NICID

		subnet2 string
		metric2 routes.Metric
		nic2    tcpip.NICID

		want bool
	}{
		// non-default before default
		{"100.99.24.12/32", 100, 1, "0.0.0.0/0", 100, 1, true},
		{"10.144.0.0/12", 100, 1, "0.0.0.0/0", 100, 2, true},
		{"127.0.0.1/24", 100, 1, "0.0.0.0/0", 100, 1, true},
		{"2511:5f32:4:6:124::2:1/128", 100, 1, "::/0", 100, 1, true},
		{"fe80:ffff:0:1234:5:6::/96", 100, 2, "::/0", 100, 1, true},
		{"::1/128", 100, 2, "::/0", 100, 2, true},
		// IPv4 before IPv6
		{"100.99.24.12/32", 100, 1, "2511:5f32:4:6:124::2/120", 100, 1, true},
		{"100.99.24.12/32", 100, 2, "2605:32::12/128", 100, 1, true},
		{"127.0.0.1/24", 100, 1, "::1/128", 100, 1, true},
		{"0.0.0.0/0", 100, 1, "::/0", 100, 3, true},
		// longer prefix wins
		{"100.99.24.12/32", 100, 2, "100.99.24.12/31", 100, 1, true},
		{"100.99.24.12/32", 100, 1, "10.144.0.0/12", 100, 1, true},
		{"100.99.24.128/25", 100, 5, "128.0.0.1/24", 100, 3, true},
		{"2511:5f32:4:6:124::2:12/128", 100, 1, "2511:5f32:4:6:124::2:12/126", 100, 1, true},
		{"2511:5f32:4:6:124::2:12/128", 100, 1, "2605:32::12/127", 100, 1, true},
		{"fe80:ffff:0:1234:5:6::/96", 100, 2, "2511:5f32:4:6:124::/90", 100, 1, true},
		{"2511:5f32:4:6:124::2:1/128", 100, 1, "::1/120", 100, 2, true},
		// lower metric
		{"100.99.24.12/32", 100, 1, "10.1.21.31/32", 101, 1, true},
		{"100.99.24.12/32", 101, 1, "10.1.21.31/32", 100, 2, false},
		{"100.99.2.0/23", 100, 3, "10.1.22.0/23", 101, 1, true},
		{"100.99.2.0/23", 101, 1, "10.1.22.0/23", 100, 1, false},
		{"2511:5f32:4:6:124::2:1/128", 100, 1, "2605:32::12/128", 101, 1, true},
		{"2511:5f32:4:6:124::2:1/128", 101, 3, "2605:32::12/128", 100, 2, false},
		{"2511:5f32:4:6:124::2:1/96", 100, 1, "fe80:ffff:0:1234:5:6::/96", 101, 4, true},
		{"2511:5f32:4:6:124::2:1/96", 101, 1, "fe80:ffff:0:1234:5:6::/96", 100, 4, false},
		// tie-breaker: destination IPs
		{"10.1.21.31/32", 100, 2, "100.99.24.12/32", 100, 1, true},
		{"100.99.24.12/32", 100, 1, "10.1.21.31/32", 100, 3, false},
		{"2511:5f32:4:6:124::2:1/128", 100, 1, "2605:32::12/128", 100, 1, true},
		{"2605:32::12/128", 100, 1, "2511:5f32:4:6:124::2:1/128", 100, 1, false},
		// tie-breaker: NIC
		{"10.1.21.31/32", 100, 1, "10.1.21.31/32", 100, 2, true},
		{"10.1.21.31/32", 100, 2, "10.1.21.31/32", 100, 1, false},
		{"2511:5f32:4:6:124::2:1/128", 100, 1, "2511:5f32:4:6:124::2:1/128", 100, 2, true},
		{"2511:5f32:4:6:124::2:1/128", 100, 2, "2511:5f32:4:6:124::2:1/128", 100, 1, false},
	} {
		name := fmt.Sprintf("Test-%s@nic%d[m:%d]_<_%s@nic%d[m:%d]", tc.subnet1, tc.nic1, tc.metric1, tc.subnet2, tc.nic2, tc.metric2)
		t.Run(name, func(t *testing.T) {
			e1 := createExtendedRoute(tc.nic1, tc.subnet1, "", tc.metric1, true, true, true)
			e2 := createExtendedRoute(tc.nic2, tc.subnet2, "", tc.metric2, true, true, true)
			if got := routes.Less(&e1, &e2); got != tc.want {
				t.Errorf("got Less(%s, %s) = %t, want = %t", &e1, &e2, got, tc.want)
			}
			// reverse test
			reverseWant := !tc.want
			if got := routes.Less(&e2, &e1); got != reverseWant {
				t.Errorf("got Less(%s, %s) = %t, want = %t", &e2, &e1, got, reverseWant)
			}
		})
	}
}

func isSameRouteTableImpl(rt1, rt2 []routes.ExtendedRoute, checkAttributes bool) bool {
	if len(rt1) != len(rt2) {
		return false
	}
	for i, r1 := range rt1 {
		r2 := rt2[i]
		if r1.Route != r2.Route {
			return false
		}
		if checkAttributes && (r1.Metric != r2.Metric || r1.MetricTracksInterface != r2.MetricTracksInterface || r1.Dynamic != r2.Dynamic || r1.Enabled != r2.Enabled) {
			return false
		}
	}
	return true
}

func isSameRouteTable(rt1, rt2 []routes.ExtendedRoute) bool {
	return isSameRouteTableImpl(rt1, rt2, true /* checkAttributes */)
}

func isSameRouteTableSkippingAttributes(rt1, rt2 []routes.ExtendedRoute) bool {
	return isSameRouteTableImpl(rt1, rt2, false /* checkAttributes */)
}

func TestAddRoute(t *testing.T) {
	for _, tc := range []struct {
		name  string
		order []int
	}{
		// different orders
		{"Add1", []int{0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10}},
		{"Add2", []int{10, 9, 8, 7, 6, 5, 4, 3, 2, 1, 0}},
		{"Add3", []int{5, 3, 9, 2, 6, 0, 7, 10, 1, 4, 8}},
		{"Add4", []int{6, 5, 7, 4, 8, 3, 9, 2, 10, 1, 0}},

		// different orders and duplicates
		{"Add5", []int{0, 0, 1, 2, 3, 4, 2, 5, 6, 7, 1, 8, 9, 10, 0}},
		{"Add6", []int{10, 9, 8, 4, 7, 6, 5, 2, 4, 3, 2, 1, 0, 5, 5}},
		{"Add7", []int{5, 3, 9, 2, 6, 0, 7, 10, 10, 1, 3, 4, 8}},
		{"Add8", []int{6, 6, 6, 5, 7, 4, 8, 3, 9, 9, 2, 7, 10, 1, 0}},
	} {
		t.Run(tc.name, func(t *testing.T) {
			// Create route table by adding all routes in the given order.
			tb := routes.RouteTable{}
			for _, j := range tc.order {
				r := testRouteTable[j]
				tb.AddRoute(r.Route, r.Metric, r.MetricTracksInterface, r.Dynamic, r.Enabled)
			}
			tableWanted := testRouteTable
			tableGot := tb.GetExtendedRouteTable()
			if len(tableGot) != len(tableWanted) {
				t.Fatalf("got len(table) = %d, want len(table) = %d", len(tableGot), len(tableWanted))
			}
			if !isSameRouteTable(tableGot, tableWanted) {
				t.Errorf("got\n%s, want\n%s", tableGot, tableWanted)
			}
		})
	}

	// Adding a route that already exists but with different dynamic/enabled
	// attributes will just overwrite the entry with the new attributes. The
	// position in the table stays the same.
	t.Run("Changing dynamic/enabled", func(t *testing.T) {
		tb := routes.RouteTable{}
		tb.Set(testRouteTable)
		for i, r := range testRouteTable {
			r.Dynamic = !r.Dynamic
			tb.AddRoute(r.Route, r.Metric, r.MetricTracksInterface, r.Dynamic, r.Enabled)
			tableWanted := testRouteTable
			tableGot := tb.GetExtendedRouteTable()
			if tableGot[i].Dynamic != r.Dynamic {
				t.Errorf("got tableGot[%d].Dynamic = %t, want %t", i, tableGot[i].Dynamic, r.Dynamic)
			}
			if !isSameRouteTableSkippingAttributes(tableGot, tableWanted) {
				t.Errorf("got\n%s, want\n%s", tableGot, tableWanted)
			}

			r.Enabled = !r.Enabled
			tb.AddRoute(r.Route, r.Metric, r.MetricTracksInterface, r.Dynamic, r.Enabled)
			tableGot = tb.GetExtendedRouteTable()
			if tableGot[i].Enabled != r.Enabled {
				t.Errorf("got tableGot[%d].Enabled = %t, want %t", i, tableGot[i].Enabled, r.Enabled)
			}
			if !isSameRouteTableSkippingAttributes(tableGot, tableWanted) {
				t.Errorf("got\n%s, want\n%s", tableGot, tableWanted)
			}
		}
	})

	// The metric is used as a tie-breaker when routes have the same prefix length
	t.Run("Changing metric", func(t *testing.T) {
		r0 := createRoute(1, "0.0.0.0/0", "192.168.1.1")
		r1 := createRoute(2, "0.0.0.0/0", "192.168.100.10")

		// 1.test - r0 gets lower metric.
		{
			var tb routes.RouteTable
			tb.AddRoute(r0, 100, true, true, true)
			tb.AddRoute(r1, 200, true, true, true)
			tableGot := tb.GetExtendedRouteTable()
			if got, want := tableGot[0].Route, r0; got != want {
				t.Errorf("got = %s, want = %s", got, want)
			}
			if got, want := tableGot[1].Route, r1; got != want {
				t.Errorf("got = %s, want = %s", got, want)
			}
		}

		// 2.test - r1 gets lower metric.
		{
			var tb routes.RouteTable
			tb.AddRoute(r0, 200, true, true, true)
			tb.AddRoute(r1, 100, true, true, true)
			tableGot := tb.GetExtendedRouteTable()
			if got, want := tableGot[0].Route, r1; got != want {
				t.Errorf("got = %s, want = %s", got, want)
			}
			if got, want := tableGot[1].Route, r0; got != want {
				t.Errorf("got = %s, want = %s", got, want)
			}
		}
	})
}

func TestDelRoute(t *testing.T) {
	for _, tc := range []struct {
		name  string
		order []int
	}{
		{"Del1", []int{0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10}},
		{"Del2", []int{10, 9, 8, 7, 6, 5, 4, 3, 2, 1, 0}},
		{"Del3", []int{6, 5, 7, 4, 8, 3, 9, 2, 10, 1, 0}},
		{"Del4", []int{0}},
		{"Del5", []int{1}},
		{"Del6", []int{9}},
		{"Del7", []int{0, 0, 1, 1, 5, 5, 9, 9, 10, 10}},
		{"Del8", []int{5, 8, 5, 0, 1, 9, 1, 5}},
	} {
		t.Run(tc.name, func(t *testing.T) {
			tb := routes.RouteTable{}
			tb.Set(testRouteTable)
			validRoutes := make([]bool, len(testRouteTable))
			for i := range validRoutes {
				validRoutes[i] = true
			}
			for _, d := range tc.order {
				toDel := testRouteTable[d]
				tb.DelRoute(toDel.Route)
				validRoutes[d] = false
			}
			tableGot := tb.GetExtendedRouteTable()
			tableWant := routes.ExtendedRouteTable{}
			for i, valid := range validRoutes {
				if valid {
					tableWant = append(tableWant, testRouteTable[i])
				}
			}
			if !isSameRouteTable(tableGot, tableWant) {
				t.Errorf("got\n%s, want\n%s", tableGot, tableWant)
			}
		})
	}
}

func TestUpdateMetricByInterface(t *testing.T) {
	// Updating the metric for the an interface updates the metric for all routes
	// that track that interface.
	for nicid := tcpip.NICID(1); nicid <= 4; nicid++ {
		t.Run(fmt.Sprintf("Change-NIC-%d-metric-updates-route-metric", nicid), func(t *testing.T) {
			tb := routes.RouteTable{}
			tb.Set(testRouteTable)
			newMetric := routes.Metric(1000 + nicid)
			// Verify existing table does not use the new metric yet.
			tableGot := tb.GetExtendedRouteTable()
			for _, r := range tableGot {
				if r.Metric == newMetric {
					t.Fatalf("Error: r.Metric said to invalid value before test start")
				}
			}

			tb.UpdateMetricByInterface(nicid, newMetric)

			tableGot = tb.GetExtendedRouteTable()
			for _, r := range tableGot {
				if r.Route.NIC != nicid {
					continue
				}
				if !r.MetricTracksInterface && r.Metric == newMetric {
					t.Errorf("got MetricTracksInterface==false && Metric=%d, want metric!=%d", r.Metric, newMetric)
				}
				if r.MetricTracksInterface && r.Metric != newMetric {
					t.Errorf("got MetricTracksInterface==true && Metric=%d, want metric=%d", r.Metric, newMetric)
				}
			}
		})
	}

	// A metric change should trigger a re-sort of the routing table.
	t.Run(fmt.Sprint("Change-metric-resorts-table"), func(t *testing.T) {
		r0 := createRoute(0, "0.0.0.0/0", "192.168.1.1")
		r1 := createRoute(1, "0.0.0.0/0", "192.168.100.10")

		// Initially r0 has lower metric and is ahead in the table.
		tb := routes.RouteTable{}
		tb.AddRoute(r0, 100, true, true, true)
		tb.AddRoute(r1, 200, true, true, true)
		{
			tableGot := tb.GetExtendedRouteTable()
			if got, want := tableGot[0].Route, r0; got != want {
				t.Errorf("got = %s, want = %s", got, want)
			}
			if got, want := tableGot[1].Route, r1; got != want {
				t.Errorf("got = %s, want = %s", got, want)
			}
		}

		// Lowering nic1's metric should be reflected in r1's metric and promote it
		// in the route table.
		tb.UpdateMetricByInterface(1, 50)
		{
			tableGot := tb.GetExtendedRouteTable()
			if got, want := tableGot[0].Route, r1; got != want {
				t.Errorf("got = %s, want = %s", got, want)
			}
			if got, want := tableGot[1].Route, r0; got != want {
				t.Errorf("got = %s, want = %s", got, want)
			}
		}
	})
}

func TestUpdateRoutesByInterface(t *testing.T) {
	for nicid := tcpip.NICID(1); nicid <= 4; nicid++ {
		// Test the normal case where on DOWN netstack removes dynamic routes and
		// disables static ones (ActionDeleteDynamicDisableStatic), and on up
		// it re-enables static routes (ActionEnableStatic).
		t.Run(fmt.Sprintf("Down-Up_NIC-%d", nicid), func(t *testing.T) {
			tb := routes.RouteTable{}
			tb.Set(testRouteTable)
			tableGot := tb.GetExtendedRouteTable()
			for _, r := range tableGot {
				if got, want := r.Enabled, true; got != want {
					t.Errorf("got Enabled = %t, want = %t, route = %s", got, want, &r)
				}
			}

			// Down -> 1.Remove dynamic routes.
			tb.UpdateRoutesByInterface(nicid, routes.ActionDeleteDynamic)

			// Verify all dynamic routes to this NIC are gone, and static ones are
			// still enabled.
			tableGot = tb.GetExtendedRouteTable()
			for _, r := range tableGot {
				if r.Route.NIC != nicid {
					continue
				}
				if got, want := r.Enabled, true; got != want {
					t.Errorf("got Enabled = %t, want = %t, route = %s", got, want, &r)
				}
				if got, want := r.Dynamic, false; got != want {
					t.Errorf("got Dynamic = %t, want = %t, route = %s", got, want, &r)
				}
			}

			// Down -> 2.Disable static ones.
			tb.UpdateRoutesByInterface(nicid, routes.ActionDisableStatic)
			// Verify all dynamic routes to this NIC are gone, and static ones are
			// disabled.
			tableGot = tb.GetExtendedRouteTable()
			for _, r := range tableGot {
				if r.Route.NIC != nicid {
					continue
				}
				if got, want := r.Enabled, false; got != want {
					t.Errorf("got Enabled = %t, want = %t, route = %s", got, want, &r)
				}
				if got, want := r.Dynamic, false; got != want {
					t.Errorf("got Dynamic = %t, want = %t, route = %s", got, want, &r)
				}
			}

			// Up -> Re-enable static routes.
			tb.UpdateRoutesByInterface(nicid, routes.ActionEnableStatic)

			// Verify dynamic routes to this NIC are still gone, and static ones are
			// enabled.
			tableGot = tb.GetExtendedRouteTable()
			for _, r := range tableGot {
				if r.Route.NIC != nicid {
					continue
				}
				if got, want := r.Enabled, true; got != want {
					t.Errorf("got Enabled = %t, want = %t, route = %s", got, want, &r)
				}
				if got, want := r.Dynamic, false; got != want {
					t.Errorf("got Dynamic = %t, want = %t, route = %s", got, want, &r)
				}
			}
		})

		// Test the special case where the interface is removed and in response all
		// routes to this interface are removed (ActionDeleteAll).
		t.Run(fmt.Sprintf("Remove_NIC-%d", nicid), func(t *testing.T) {
			tb := routes.RouteTable{}
			tb.Set(testRouteTable)
			tableGot := tb.GetExtendedRouteTable()
			for _, r := range tableGot {
				if got, want := r.Enabled, true; got != want {
					t.Errorf("got Enabled = %t, want = %t, route = %s", got, want, &r)
				}
			}

			// Remove all routes to nicid.
			tb.UpdateRoutesByInterface(nicid, routes.ActionDeleteAll)

			// Verify all routes to this NIC are gone.
			tableGot = tb.GetExtendedRouteTable()
			for _, r := range tableGot {
				if r.Route.NIC == nicid {
					t.Errorf("got route pointing to NIC-%d, want none, route = %s", nicid, &r)
				}
			}
		})
	}
}

func TestGetNetstackTable(t *testing.T) {
	for _, tc := range []struct {
		name     string
		disabled []int
	}{
		{"GetNsTable1", []int{}},
		{"GetNsTable2", []int{0}},
		{"GetNsTable3", []int{10}},
		{"GetNsTable4", []int{1}},
		{"GetNsTable5", []int{9}},
		{"GetNsTable6", []int{3, 5, 8}},
		{"GetNsTable7", []int{0, 1, 5, 6, 8, 9, 10}},
		{"GetNsTable8", []int{0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10}},
	} {
		t.Run(tc.name, func(t *testing.T) {
			// We have no way to directly disable routes in the route table, but we
			// can use the Set() command to set a table with pre-disabled routes.
			testRouteTable := append([]routes.ExtendedRoute(nil), testRouteTable...)
			// Disable a few routes.
			for _, i := range tc.disabled {
				testRouteTable[i].Enabled = false
			}
			var tb routes.RouteTable
			tb.Set(testRouteTable)

			var dummyStack stack.Stack
			tb.UpdateStack(&dummyStack)
			tableGot := dummyStack.GetRouteTable()

			// Verify no disabled routes are in the Netstack table we got.
			i := 0
			for _, r := range testRouteTable {
				if r.Enabled {
					if got, want := tableGot[i], r.Route; got != want {
						t.Errorf("got = %s, want = %s", got, want)
					}
					i++
				}
			}
		})
	}
}

func TestFindNIC(t *testing.T) {
	for _, tc := range []struct {
		name      string
		addr      string
		nicWanted tcpip.NICID // 0 means not found
	}{
		{"FindNic1", "127.0.0.1", 1},
		{"FindNic2", "127.0.0.0", 0},
		{"FindNic3", "192.168.1.234", 4},
		{"FindNic4", "192.168.1.1", 4},
		{"FindNic5", "192.168.2.1", 0},
		{"FindNic6", "192.168.100.1", 2},
		{"FindNic7", "192.168.100.10", 2},
		{"FindNic8", "192.168.101.10", 0},
		{"FindNic9", "10.1.2.1", 3},
		{"FindNic10", "10.1.3.1", 3},
		{"FindNic11", "10.1.4.1", 0},
	} {
		t.Run(tc.name, func(t *testing.T) {
			tb := routes.RouteTable{}
			tb.Set(testRouteTable)

			nicGot, err := tb.FindNIC(ipStringToAddress(tc.addr))
			if err != nil && tc.nicWanted > 0 {
				t.Errorf("got nic = <unknown>, want = %d", tc.nicWanted)
			} else if err == nil && tc.nicWanted != nicGot {
				t.Errorf("got nic = %d, want = %d", nicGot, tc.nicWanted)
			}
		})
	}
}
