diff --git a/.github/CODEOWNERS b/.github/CODEOWNERS index 93d40f8b043..df375ba3436 100644 --- a/.github/CODEOWNERS +++ b/.github/CODEOWNERS @@ -1,16 +1,36 @@ # https://docs.github.com/en/repositories/managing-your-repositorys-settings-and-features/customizing-your-repository/about-code-owners # Each line is a file pattern followed by one or more owners. +# Order is important; the last matching pattern takes the most +# precedence. # These owners will be the default owners for everything in # the repo. Unless a later match takes precedence, # @openconfig/featureprofiles-maintainers will be requested for # review when someone opens a pull request. -* @openconfig/featureprofiles-maintainers @openconfig/featureprofiles-quattro-tl +* @openconfig/featureprofiles-maintainers -# Tests which are ported from ate_tests to otg_tests may be reviewed by this team. -**/otg_tests/** @openconfig/featureprofiles-maintainers-otg @openconfig/featureprofiles-maintainers @openconfig/featureprofiles-quattro-tl -/internal/otgutils/ @openconfig/featureprofiles-maintainers-otg @openconfig/featureprofiles-maintainers @openconfig/featureprofiles-quattro-tl +# /feature folders each have owners who are auto requested for review and may merge PR's +/feature/acl/ @alokmtri-g +/feature/aft/ @sudhinj +/feature/bgp/ @dplore +/feature/dhcp/ @alokmtri-g +/feature/ethernet/ @ram-mac +/feature/interface/ @ram-mac +/feature/isis/ @rohit-rp +/feature/lldp/ @alokmtri-g +/feature/mpls/ @swetha-haridasula +/feature/mtu/ @swetha-haridasula +/feature/networkinstance/ @swetha-haridasula +/feature/platform/ @amrindrr +/feature/qos @sezhang2 +/feature/routing_policy/ @swetha-haridasula +/feature/sampling/ @sudhinj +/feature/security @mihirpitale-googler +/feature/staticroute/ @swetha-haridasula +/feature/stp/ @alokmtri-g +/feature/system @swetha-haridasula +/feature/vrrp @amrindrr -# Order is important; the last matching pattern takes the most -# precedence. +# Common OTG utilities +/internal/otgutils/ @openconfig/featureprofiles-maintainers-otg diff --git a/.github/workflows/readme_oc_path_and_rpc.yml b/.github/workflows/readme_oc_path_and_rpc.yml index b757f475a66..73e78f5be8d 100644 --- a/.github/workflows/readme_oc_path_and_rpc.yml +++ b/.github/workflows/readme_oc_path_and_rpc.yml @@ -37,7 +37,7 @@ jobs: exemption_flags=( --non-test-readme feature/security/gnsi/certz/test_data/README.md - --non-test-readme feature/experimental/p4rt/README.md + --non-test-readme feature/p4rt/README.md --non-test-readme feature/security/gnsi/acctz/README.md ) diff --git a/.gitignore b/.gitignore index 93acb89f3cb..07ebd5a939c 100644 --- a/.gitignore +++ b/.gitignore @@ -1,6 +1,7 @@ *~ topologies/kne/testbed.kne.yml .vscode/ +.idea/ # used by `make validate_paths` openconfig_public/ # used by `make proto/...` diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 5875bebd432..2290141cb5a 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -62,10 +62,6 @@ The directory tree is organized as follows: * `cloudbuild/` contains google cloud build scripts for running virtual routers in containers on [KNE](https://github.com/openconfig/kne) * `feature/` contains definition and tests of feature profiles. -* `feature/experimental` contains tests which have automation which is - not confirmed to pass on any hardware platform or software release. - When the test automation is passing against at least one DUT, - it is moved to the `feature/` directory. * `internal/` contains packages used by feature profile tests. * `proto/` contains protobuf files for feature profiles. * `tools/` contains code used for CI checks. diff --git a/feature/bgp/addpath/otg_tests/route_propagation_test/README.md b/feature/bgp/addpath/otg_tests/route_propagation_test/README.md index 502d71ee974..6c790232e3b 100644 --- a/feature/bgp/addpath/otg_tests/route_propagation_test/README.md +++ b/feature/bgp/addpath/otg_tests/route_propagation_test/README.md @@ -4,49 +4,91 @@ BGP Route Propagation +## Testbed type + +* [`featureprofiles/topologies/atedut_2.testbed`](https://github.com/openconfig/featureprofiles/blob/main/topologies/atedut_2.testbed) + ## Procedure Establish eBGP sessions between: * ATE port-1 and DUT port-1 * ATE port-2 and DUT port-2 -* Configure Route-policy under BGP peer-group address-family - -For IPv4 and IPv6: - -* Advertise prefixes from ATE port-1, observe received prefixes at ATE port-2. -* TODO: Specify default accept for received prefixes on DUT. -* TODO: Specify table based neighbor configuration to cover - validating the - supported capabilities from the DUT. - * TODO: MRAI (minimum route advertisement interval), ensuring routes are - advertised within specified time. - * IPv4 routes with an IPv6 next-hop when negotiating RFC5549 - validating - that routes are accepted and advertised with the specified values. - * TODO: With ADD-PATH enabled, ensure that multiple routes are accepted - from a neighbor when advertised with individual path IDs, and that these - routes are advertised to ATE port-2. - -## Config Parameter Coverage - -For prefix: -/network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor - -Parameters: - -* afi-safis/afi-safi/add-paths/config/receive -* afi-safis/afi-safi/add-paths/config/send -* afi-safis/afi-safi/add-paths/config/send-max - -## Telemetry Parameter Coverage - -/network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/state/supported-capabilities - -## Protocol/RPC Parameter Coverage -BGP -* OPEN - * Capabilities (Extended nexthop encoding capability (5), ADD-PATH (69)) -* UPDATE - * Extended NLRI Encodings (RFC7911) - * Nexthop AFI (RFC5549) +### RT-1.3.1: MRAI: [TODO: https://github.com/openconfig/featureprofiles/issues/3035] +* DUT: Configure the Minimum Route Advertisement Interval (MRAI) for desired behavior. +* ATE Port 2: Verify received routes adhere to the MRAI timing. + +### RT-1.3.2: RFC5549 +* DUT: Enable RFC5549 support: + * Update the BGP peer group configuration to enable extended next hop encoding using `/network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/afi-safis/afi-safi/ipv4-unicast/config/extended-next-hop-encoding` +* ATE Port 1: Advertise IPv4 routes with IPv6 next-hops. +* ATE Port 2: Validate correct acceptance and propagation of routes with IPv6 next-hops. + +### RT-1.3.3: Add-Path (Initial State): [TODO: https://github.com/openconfig/featureprofiles/issues/3037] +* ATE Port 1: Advertise multiple routes with distinct path IDs for the same prefix. +* ATE Port 2: Confirm that all advertised routes are accepted and propagated by the DUT due to the initially enabled Add-Path. +* Verification (Telemetry): Verify that the DUT's telemetry output reflects the enabled Add-Path capabilities. + +### RT-1.3.4: Disabling Add-Path Send: [TODO: https://github.com/openconfig/featureprofiles/issues/3037] +* DUT: Disable Add-Path send for the neighbor connected to ATE Port 2 for both IPv4 and IPv6. +* Verification (Telemetry): Confirm that the DUT's telemetry reflects the disabled Add-Path send status. +* ATE Port 1: Readvertise multiple paths. +* ATE Port 2: Verify that only a single best path is received by ATE Port 2 due to disabled Add-Path send on the DUT. + +### RT-1.3.5: Disabling Add-Path Receive: [TODO: https://github.com/openconfig/featureprofiles/issues/3037] +* DUT: Disable Add-Path receive for the neighbor connected to ATE Port 1 for both IPv4 and IPv6. +* Verification (Telemetry): Confirm the disabled Add-Path receive status in telemetry. +* ATE Port 1: Advertise BGP routes to the DUT via Port 1. +* ATE Port 2: Verify that the DUT has received and propagated only one single path. + +## OpenConfig Path and RPC Coverage + +The below yaml defines the OC paths intended to be covered by this test. + +```yaml +paths: + ## Config paths + /network-instances/network-instance/protocols/protocol/bgp/global/afi-safis/afi-safi/add-paths/config/receive: + /network-instances/network-instance/protocols/protocol/bgp/global/afi-safis/afi-safi/add-paths/config/send: + /network-instances/network-instance/protocols/protocol/bgp/global/afi-safis/afi-safi/add-paths/config/send-max: + /network-instances/network-instance/protocols/protocol/bgp/global/afi-safis/afi-safi/ipv4-unicast/config/extended-next-hop-encoding: + /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/afi-safis/afi-safi/add-paths/config/receive: + /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/afi-safis/afi-safi/add-paths/config/send: + /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/afi-safis/afi-safi/add-paths/config/send-max: + /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/timers/config/minimum-advertisement-interval: + /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/afi-safis/afi-safi/ipv4-unicast/config/extended-next-hop-encoding: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/afi-safis/afi-safi/add-paths/config/receive: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/afi-safis/afi-safi/add-paths/config/send: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/afi-safis/afi-safi/add-paths/config/send-max: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/timers/config/minimum-advertisement-interval: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/afi-safis/afi-safi/ipv4-unicast/config/extended-next-hop-encoding: + + ## State paths + /network-instances/network-instance/protocols/protocol/bgp/global/afi-safis/afi-safi/add-paths/state/receive: + /network-instances/network-instance/protocols/protocol/bgp/global/afi-safis/afi-safi/add-paths/state/send: + /network-instances/network-instance/protocols/protocol/bgp/global/afi-safis/afi-safi/add-paths/state/send-max: + /network-instances/network-instance/protocols/protocol/bgp/global/afi-safis/afi-safi/ipv4-unicast/state/extended-next-hop-encoding: + /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/afi-safis/afi-safi/add-paths/state/receive: + /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/afi-safis/afi-safi/add-paths/state/send: + /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/afi-safis/afi-safi/add-paths/state/send-max: + /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/timers/state/minimum-advertisement-interval: + /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/afi-safis/afi-safi/ipv4-unicast/state/extended-next-hop-encoding: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/afi-safis/afi-safi/add-paths/state/receive: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/afi-safis/afi-safi/add-paths/state/send: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/afi-safis/afi-safi/add-paths/state/send-max: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/timers/state/minimum-advertisement-interval: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/afi-safis/afi-safi/ipv4-unicast/state/extended-next-hop-encoding: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/state/supported-capabilities: + +rpcs: + gnmi: + gNMI.Set: + gNMI.Subscribe: +``` + +## Minimum DUT platform requirement + +* MFF - A modular form factor device containing LINECARDs, FABRIC and redundant CONTROLLER_CARD components +* FFF - fixed form factor diff --git a/feature/experimental/bgp/ate_tests/bgp_long_lived_graceful_restart/README.md b/feature/bgp/ate_tests/bgp_long_lived_graceful_restart/README.md similarity index 100% rename from feature/experimental/bgp/ate_tests/bgp_long_lived_graceful_restart/README.md rename to feature/bgp/ate_tests/bgp_long_lived_graceful_restart/README.md diff --git a/feature/experimental/bgp/ate_tests/bgp_long_lived_graceful_restart/bgp_long_lived_graceful_restart_test.go b/feature/bgp/ate_tests/bgp_long_lived_graceful_restart/bgp_long_lived_graceful_restart_test.go similarity index 100% rename from feature/experimental/bgp/ate_tests/bgp_long_lived_graceful_restart/bgp_long_lived_graceful_restart_test.go rename to feature/bgp/ate_tests/bgp_long_lived_graceful_restart/bgp_long_lived_graceful_restart_test.go diff --git a/feature/experimental/bgp/ate_tests/bgp_long_lived_graceful_restart/metadata.textproto b/feature/bgp/ate_tests/bgp_long_lived_graceful_restart/metadata.textproto similarity index 100% rename from feature/experimental/bgp/ate_tests/bgp_long_lived_graceful_restart/metadata.textproto rename to feature/bgp/ate_tests/bgp_long_lived_graceful_restart/metadata.textproto diff --git a/feature/bgp/bgp_session_mode_configuration_test/README.md b/feature/bgp/bgp_session_mode/otg_tests/bgp_session_mode_configuration_test/README.md similarity index 100% rename from feature/bgp/bgp_session_mode_configuration_test/README.md rename to feature/bgp/bgp_session_mode/otg_tests/bgp_session_mode_configuration_test/README.md diff --git a/feature/bgp/bgp_session_mode/otg_tests/bgp_session_mode_configuration_test/bgp_session_mode_configuration_test.go b/feature/bgp/bgp_session_mode/otg_tests/bgp_session_mode_configuration_test/bgp_session_mode_configuration_test.go new file mode 100644 index 00000000000..80fc518aee2 --- /dev/null +++ b/feature/bgp/bgp_session_mode/otg_tests/bgp_session_mode_configuration_test/bgp_session_mode_configuration_test.go @@ -0,0 +1,326 @@ +// Copyright 2024 Google LLC +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +package bgp_session_mode_configuration_test + +import ( + "testing" + "time" + + "github.com/open-traffic-generator/snappi/gosnappi" + "github.com/openconfig/featureprofiles/internal/attrs" + "github.com/openconfig/featureprofiles/internal/deviations" + "github.com/openconfig/featureprofiles/internal/fptest" + "github.com/openconfig/ondatra" + "github.com/openconfig/ondatra/gnmi" + "github.com/openconfig/ondatra/gnmi/oc" + "github.com/openconfig/ondatra/otg" + "github.com/openconfig/ygnmi/ygnmi" + "github.com/openconfig/ygot/ygot" +) + +// The testbed consists of ate:port1 -> dut:port1. +func TestMain(m *testing.M) { + fptest.RunTests(m) +} + +// List of variables. +var ( + dutAttrs = attrs.Attributes{ + Desc: "To ATE", + IPv4: "192.0.2.1", + IPv4Len: 30, + } + ateAttrs = attrs.Attributes{ + Desc: "To DUT", + Name: "ateSrc", + MAC: "02:00:01:01:01:01", + IPv4: "192.0.2.2", + IPv4Len: 30, + } +) + +// Constants. +const ( + dutAS = 65540 + ateAS = 65550 + peerGrpName = "eBGP-PEER-GROUP" + peerLvlPassive = "PeerGrpLevelPassive" + peerLvlActive = "PeerGrpLevelActive" + nbrLvlPassive = "nbrLevelPassive" + nbrLvlActive = "nbrLevelActive" +) + +// configureDUT is used to configure interfaces on the DUT. +func configureDUT(t *testing.T, dut *ondatra.DUTDevice) { + dc := gnmi.OC() + i1 := dutAttrs.NewOCInterface(dut.Port(t, "port1").Name(), dut) + gnmi.Replace(t, dut, dc.Interface(i1.GetName()).Config(), i1) + + if deviations.ExplicitPortSpeed(dut) { + fptest.SetPortSpeed(t, dut.Port(t, "port1")) + } + if deviations.ExplicitInterfaceInDefaultVRF(dut) { + fptest.AssignToNetworkInstance(t, dut, i1.GetName(), deviations.DefaultNetworkInstance(dut), 0) + } +} + +// verifyPortsUp asserts that each port on the device is operating. +func verifyPortsUp(t *testing.T, dev *ondatra.Device) { + t.Helper() + for _, p := range dev.Ports() { + status := gnmi.Get(t, dev, gnmi.OC().Interface(p.Name()).OperStatus().State()) + if want := oc.Interface_OperStatus_UP; status != want { + t.Errorf("%s Status: got %v, want %v", p, status, want) + } + } +} + +// Struct is to pass bgp session parameters. +type bgpTestParams struct { + localAS, peerAS, nbrLocalAS uint32 + peerIP string + transportMode string +} + +// bgpCreateNbr creates a BGP object with neighbors pointing to ate and returns bgp object. +func bgpCreateNbr(bgpParams *bgpTestParams, dut *ondatra.DUTDevice) *oc.NetworkInstance_Protocol { + d := &oc.Root{} + ni1 := d.GetOrCreateNetworkInstance(deviations.DefaultNetworkInstance(dut)) + niProto := ni1.GetOrCreateProtocol(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, "BGP") + + bgp := niProto.GetOrCreateBgp() + + global := bgp.GetOrCreateGlobal() + global.As = ygot.Uint32(bgpParams.localAS) + global.RouterId = ygot.String(dutAttrs.IPv4) + + // Note: we have to define the peer group even if we aren't setting any policy because it's + // invalid OC for the neighbor to be part of a peer group that doesn't exist. + pg := bgp.GetOrCreatePeerGroup(peerGrpName) + pg.PeerAs = ygot.Uint32(dutAS) + pg.PeerGroupName = ygot.String(peerGrpName) + + nv4 := bgp.GetOrCreateNeighbor(ateAttrs.IPv4) + nv4.PeerGroup = ygot.String(peerGrpName) + nv4.PeerAs = ygot.Uint32(ateAS) + nv4.Enabled = ygot.Bool(true) + + nv4.GetOrCreateAfiSafi(oc.BgpTypes_AFI_SAFI_TYPE_IPV4_UNICAST).Enabled = ygot.Bool(true) + + switch bgpParams.transportMode { + case nbrLvlPassive: + nv4.GetOrCreateTransport().SetPassiveMode(true) + case nbrLvlActive: + nv4.GetOrCreateTransport().SetPassiveMode(false) + case peerLvlPassive: + pg.GetOrCreateTransport().SetPassiveMode(true) + case peerLvlActive: + pg.GetOrCreateTransport().SetPassiveMode(false) + } + + return niProto +} + +// bgpClearConfig removes all BGP configuration from the DUT. +func bgpClearConfig(t *testing.T, dut *ondatra.DUTDevice) { + resetBatch := &gnmi.SetBatch{} + gnmi.BatchDelete(resetBatch, gnmi.OC().NetworkInstance(deviations.DefaultNetworkInstance(dut)).Protocol(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, "BGP").Config()) + + if deviations.NetworkInstanceTableDeletionRequired(dut) { + tablePath := gnmi.OC().NetworkInstance(deviations.DefaultNetworkInstance(dut)).TableAny() + for _, table := range gnmi.LookupAll[*oc.NetworkInstance_Table](t, dut, tablePath.Config()) { + if val, ok := table.Val(); ok { + if val.GetProtocol() == oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP { + gnmi.BatchDelete(resetBatch, gnmi.OC().NetworkInstance(deviations.DefaultNetworkInstance(dut)).Table(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, val.GetAddressFamily()).Config()) + } + } + } + } + resetBatch.Set(t, dut) +} + +// verifyBgpTelemetry checks that the dut has an established BGP session with reasonable settings. +func verifyBgpTelemetry(t *testing.T, dut *ondatra.DUTDevice, wantState oc.E_Bgp_Neighbor_SessionState, transMode string) { + statePath := gnmi.OC().NetworkInstance(deviations.DefaultNetworkInstance(dut)).Protocol(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, "BGP").Bgp() + nbrPath := statePath.Neighbor(ateAttrs.IPv4) + + // Get BGP adjacency state + t.Log("Checking BGP neighbor to state...") + _, ok := gnmi.Watch(t, dut, nbrPath.SessionState().State(), time.Minute, func(val *ygnmi.Value[oc.E_Bgp_Neighbor_SessionState]) bool { + state, present := val.Val() + return present && state == wantState + }).Await(t) + if !ok { + fptest.LogQuery(t, "BGP reported state", nbrPath.State(), gnmi.Get(t, dut, nbrPath.State())) + t.Errorf("BGP Session state is not as expected.") + } + status := gnmi.Get(t, dut, nbrPath.SessionState().State()) + t.Logf("BGP adjacency for %s: %s", ateAttrs.IPv4, status) + if status != wantState { + t.Errorf("BGP peer %s status got %d, want %d", ateAttrs.IPv4, status, wantState) + } + + nbrTransMode := gnmi.Get(t, dut, nbrPath.Transport().State()) + pgTransMode := gnmi.Get(t, dut, statePath.PeerGroup(peerGrpName).Transport().State()) + // Check transport mode telemetry. + switch transMode { + case nbrLvlPassive: + if nbrTransMode.GetPassiveMode() != true { + t.Errorf("Neighbor level passive mode is not set to true on DUT. want true, got %v", nbrTransMode.GetPassiveMode()) + } + t.Logf("Neighbor level passive mode is set to %v on DUT", nbrTransMode.GetPassiveMode()) + case nbrLvlActive: + if nbrTransMode.GetPassiveMode() != false { + t.Errorf("Neighbor level passive mode is not set to false on DUT. want false, got %v", nbrTransMode.GetPassiveMode()) + } + t.Logf("Neighbor level passive mode is set to %v on DUT", nbrTransMode.GetPassiveMode()) + case peerLvlPassive: + if pgTransMode.GetPassiveMode() != true { + t.Errorf("Peer group level passive mode is not set to true on DUT. want true, got %v", pgTransMode.GetPassiveMode()) + } + t.Logf("Peer group level passive mode is set to %v on DUT", pgTransMode.GetPassiveMode()) + case peerLvlActive: + if pgTransMode.GetPassiveMode() != false { + t.Errorf("Peer group level passive mode is not set to false on DUT. want false, got %v", pgTransMode.GetPassiveMode()) + } + t.Logf("Peer group level passive mode is set to %v on DUT", pgTransMode.GetPassiveMode()) + } +} + +// Function to configure ATE configs based on args and returns ate topology handle. +func configureATE(t *testing.T, ateParams *bgpTestParams) gosnappi.Config { + t.Helper() + ate := ondatra.ATE(t, "ate") + port1 := ate.Port(t, "port1") + topo := gosnappi.NewConfig() + + topo.Ports().Add().SetName(port1.ID()) + dev := topo.Devices().Add().SetName(ateAttrs.Name) + eth := dev.Ethernets().Add().SetName(ateAttrs.Name + ".Eth") + eth.Connection().SetPortName(port1.ID()) + eth.SetMac(ateAttrs.MAC) + + ip := eth.Ipv4Addresses().Add().SetName(dev.Name() + ".IPv4") + ip.SetAddress(ateAttrs.IPv4).SetGateway(dutAttrs.IPv4).SetPrefix(uint32(ateAttrs.IPv4Len)) + + bgp := dev.Bgp().SetRouterId(ateAttrs.IPv4) + peerBGP := bgp.Ipv4Interfaces().Add().SetIpv4Name(ip.Name()).Peers().Add() + peerBGP.SetName(ateAttrs.Name + ".BGP4.peer") + peerBGP.SetPeerAddress(ip.Gateway()).SetAsNumber(uint32(ateParams.localAS)) + peerBGP.SetAsType(gosnappi.BgpV4PeerAsType.EBGP) + + switch ateParams.transportMode { + case nbrLvlPassive: + case peerLvlPassive: + peerBGP.Advanced().SetPassiveMode(true) + case peerLvlActive: + case nbrLvlActive: + peerBGP.Advanced().SetPassiveMode(false) + } + + return topo +} + +func verifyOTGBGPTelemetry(t *testing.T, otg *otg.OTG, c gosnappi.Config) { + //nbrPath := gnmi.OTG().BgpPeer("ateSrc.BGP4.peer") + t.Log("OTG telemetry does not support checking transport mode.") +} + +// TestBgpSessionModeConfiguration is to verify when transport mode is set +// active/passive at both neighbor level and peer group level. +func TestBgpSessionModeConfiguration(t *testing.T) { + dutIP := dutAttrs.IPv4 + dut := ondatra.DUT(t, "dut") + ate := ondatra.ATE(t, "ate") + + // Configure interface on the DUT + t.Log("Start DUT interface Config") + configureDUT(t, dut) + + // Configure Network instance type on DUT + t.Log("Configure Network Instance") + fptest.ConfigureDefaultNetworkInstance(t, dut) + + // Verify Port Status + t.Log("Verifying port status") + verifyPortsUp(t, dut.Device) + + dutConfPath := gnmi.OC().NetworkInstance(deviations.DefaultNetworkInstance(dut)).Protocol(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, "BGP") + + cases := []struct { + name string + dutConf *oc.NetworkInstance_Protocol + ateConf gosnappi.Config + wantBGPState oc.E_Bgp_Neighbor_SessionState + dutTransportMode string + otgTransportMode string + }{ + { + name: "Test transport mode passive at neighbor level on both DUT and ATE ", + dutConf: bgpCreateNbr(&bgpTestParams{localAS: dutAS, peerAS: ateAS, transportMode: nbrLvlPassive}, dut), + ateConf: configureATE(t, &bgpTestParams{localAS: ateAS, peerIP: dutIP, transportMode: nbrLvlPassive}), + wantBGPState: oc.Bgp_Neighbor_SessionState_ACTIVE, + dutTransportMode: nbrLvlPassive, + otgTransportMode: nbrLvlPassive, + }, + { + name: "Test transport mode active on ATE and passive on DUT at neighbor level", + dutConf: bgpCreateNbr(&bgpTestParams{localAS: dutAS, peerAS: ateAS, nbrLocalAS: dutAS, transportMode: nbrLvlPassive}, dut), + ateConf: configureATE(t, &bgpTestParams{localAS: ateAS, peerIP: dutIP, transportMode: nbrLvlActive}), + wantBGPState: oc.Bgp_Neighbor_SessionState_ESTABLISHED, + dutTransportMode: nbrLvlPassive, + otgTransportMode: nbrLvlActive, + }, + { + name: "Test transport passive mode at Peer group level on both DUT and ATE.", + dutConf: bgpCreateNbr(&bgpTestParams{localAS: dutAS, peerAS: ateAS, transportMode: peerLvlPassive}, dut), + ateConf: configureATE(t, &bgpTestParams{localAS: ateAS, peerIP: dutIP, transportMode: peerLvlPassive}), + wantBGPState: oc.Bgp_Neighbor_SessionState_ACTIVE, + dutTransportMode: peerLvlPassive, + otgTransportMode: peerLvlPassive, + }, + { + name: "Test transport mode active on ATE and passive on DUT at peer group level", + dutConf: bgpCreateNbr(&bgpTestParams{localAS: dutAS, peerAS: ateAS, nbrLocalAS: dutAS, transportMode: peerLvlPassive}, dut), + ateConf: configureATE(t, &bgpTestParams{localAS: ateAS, peerIP: dutIP, transportMode: peerLvlActive}), + wantBGPState: oc.Bgp_Neighbor_SessionState_ESTABLISHED, + dutTransportMode: peerLvlPassive, + otgTransportMode: peerLvlActive, + }, + } + for _, tc := range cases { + t.Run(tc.name, func(t *testing.T) { + t.Log("Clear BGP configuration") + bgpClearConfig(t, dut) + + t.Log("Configure BGP Configs on DUT") + gnmi.Replace(t, dut, dutConfPath.Config(), tc.dutConf) + fptest.LogQuery(t, "DUT BGP Config ", dutConfPath.Config(), gnmi.Get(t, dut, dutConfPath.Config())) + + t.Log("Configure BGP on ATE") + ate.OTG().PushConfig(t, tc.ateConf) + ate.OTG().StartProtocols(t) + + t.Logf("Verify BGP telemetry") + verifyBgpTelemetry(t, dut, tc.wantBGPState, tc.dutTransportMode) + + t.Logf("Verify BGP telemetry on otg") + verifyOTGBGPTelemetry(t, ate.OTG(), tc.ateConf) + + t.Log("Clear BGP Configs on ATE") + ate.OTG().StopProtocols(t) + }) + } +} diff --git a/feature/bgp/bgp_session_mode/otg_tests/bgp_session_mode_configuration_test/metadata.textproto b/feature/bgp/bgp_session_mode/otg_tests/bgp_session_mode_configuration_test/metadata.textproto new file mode 100644 index 00000000000..2b5a539450e --- /dev/null +++ b/feature/bgp/bgp_session_mode/otg_tests/bgp_session_mode_configuration_test/metadata.textproto @@ -0,0 +1,41 @@ +# proto-file: github.com/openconfig/featureprofiles/proto/metadata.proto +# proto-message: Metadata + +uuid: "7e2082f6-4fbc-4e2b-a8a8-c83af2574ec4" +plan_id: "RT-1.55" +description: "BGP session mode (active/passive)" +testbed: TESTBED_DUT_ATE_2LINKS +platform_exceptions: { + platform: { + vendor: CISCO + } + deviations: { + ipv4_missing_enabled: true + connect_retry: true + } +} +platform_exceptions: { + platform: { + vendor: NOKIA + } + deviations: { + explicit_port_speed: true + explicit_interface_in_default_vrf: true + missing_value_for_defaults: true + interface_enabled: true + } +} +platform_exceptions: { + platform: { + vendor: ARISTA + } + deviations: { + connect_retry: true + omit_l2_mtu: true + network_instance_table_deletion_required: true + bgp_md5_requires_reset: true + missing_value_for_defaults: true + interface_enabled: true + default_network_instance: "default" + } +} diff --git a/feature/bgp/multipath/otg_tests/bgp_multipath_ecmp_test/bgp_multipath_ecmp_test.go b/feature/bgp/multipath/otg_tests/bgp_multipath_ecmp_test/bgp_multipath_ecmp_test.go index 2354ccc83ac..6991c940414 100644 --- a/feature/bgp/multipath/otg_tests/bgp_multipath_ecmp_test/bgp_multipath_ecmp_test.go +++ b/feature/bgp/multipath/otg_tests/bgp_multipath_ecmp_test/bgp_multipath_ecmp_test.go @@ -15,6 +15,7 @@ package bgp_multipath_ecmp_test import ( + "slices" "sort" "strconv" "testing" @@ -40,6 +41,7 @@ const ( pathID = 1 maxPaths = 2 trafficPps = 100000 + kneTrafficPps = 1000 totalPackets = 12000000 lossTolerancePct = 0 lbToleranceFms = 20 @@ -49,6 +51,10 @@ func TestMain(m *testing.M) { fptest.RunTests(m) } +var ( + kneDeviceModelList = []string{"ncptx"} +) + func configureOTG(t *testing.T, bs *cfgplugins.BGPSession) { devices := bs.ATETop.Devices().Items() byName := func(i, j int) bool { return devices[i].Name() < devices[j].Name() } @@ -104,6 +110,10 @@ func configureFlow(t *testing.T, bs *cfgplugins.BGPSession) { flow.Size().SetFixed(1500) flow.Rate().SetPps(trafficPps) + if slices.Contains(kneDeviceModelList, bs.DUT.Model()) { + flow.Rate().SetPps(kneTrafficPps) + } + e := flow.Packet().Add().Ethernet() e.Src().SetValue(bs.ATEPorts[0].MAC) v4 := flow.Packet().Add().Ipv4() diff --git a/feature/experimental/bgp/otg_tests/base_bgp_session_parameters/README.md b/feature/bgp/otg_tests/base_bgp_session_parameters/README.md similarity index 61% rename from feature/experimental/bgp/otg_tests/base_bgp_session_parameters/README.md rename to feature/bgp/otg_tests/base_bgp_session_parameters/README.md index dc3416dbd47..8bdeb896e1a 100644 --- a/feature/experimental/bgp/otg_tests/base_bgp_session_parameters/README.md +++ b/feature/bgp/otg_tests/base_bgp_session_parameters/README.md @@ -48,48 +48,21 @@ Test the normal session establishment and termination: * Explicit holdtime interval and keepalive interval. * Explicit connect retry interval. -## Config Parameter coverage - -* For prefix: - - * /network-instances/network-instance/protocols/protocol/bgp/global - -* For Parameters: - - * config/as - * config/router-id - * config/peer-as - * config/local-as - * config/description - * timers/config/hold-time - * timers/config/keepalive-interval - * timers/config/minimum-route-advertisement-interval - -* For prefixes: - - * /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group - * /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor - -## Telemetry Parameter coverage - -* For prefix: - - * /network-instances/network-instance/protocols/protocol/bgp/ - -* For Parameters: - - * state/last-established - * state/messages/received/NOTIFICATION - * state/negotiated-hold-time - * state/supported-capabilities - -## Protocol/RPC Parameter coverage - -* BGP - - * OPEN - - * Version - * My Autonomous System - * BGP Identifier - * Hold Time +## OpenConfig Path and RPC Coverage +```yaml +paths: + ## Config Parameter Coverage + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/timers/config/hold-time: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/timers/config/keepalive-interval: + + ## Telemetry Parameter Coverage + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/state/last-established: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/state/messages/received/NOTIFICATION: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/timers/state/negotiated-hold-time: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/state/supported-capabilities: + +rpcs: + gnmi: + gNMI.Subscribe: + gNMI.Set: +``` diff --git a/feature/experimental/bgp/otg_tests/base_bgp_session_parameters/base_bgp_session_parameters_test.go b/feature/bgp/otg_tests/base_bgp_session_parameters/base_bgp_session_parameters_test.go similarity index 100% rename from feature/experimental/bgp/otg_tests/base_bgp_session_parameters/base_bgp_session_parameters_test.go rename to feature/bgp/otg_tests/base_bgp_session_parameters/base_bgp_session_parameters_test.go diff --git a/feature/experimental/bgp/otg_tests/base_bgp_session_parameters/metadata.textproto b/feature/bgp/otg_tests/base_bgp_session_parameters/metadata.textproto similarity index 100% rename from feature/experimental/bgp/otg_tests/base_bgp_session_parameters/metadata.textproto rename to feature/bgp/otg_tests/base_bgp_session_parameters/metadata.textproto diff --git a/feature/experimental/bgp/otg_tests/bgp_2byte_4byte_asn/README.md b/feature/bgp/otg_tests/bgp_2byte_4byte_asn/README.md similarity index 100% rename from feature/experimental/bgp/otg_tests/bgp_2byte_4byte_asn/README.md rename to feature/bgp/otg_tests/bgp_2byte_4byte_asn/README.md diff --git a/feature/experimental/bgp/otg_tests/bgp_2byte_4byte_asn/bgp_2byte_4byte_asn_test.go b/feature/bgp/otg_tests/bgp_2byte_4byte_asn/bgp_2byte_4byte_asn_test.go similarity index 100% rename from feature/experimental/bgp/otg_tests/bgp_2byte_4byte_asn/bgp_2byte_4byte_asn_test.go rename to feature/bgp/otg_tests/bgp_2byte_4byte_asn/bgp_2byte_4byte_asn_test.go diff --git a/feature/experimental/bgp/otg_tests/bgp_2byte_4byte_asn/metadata.textproto b/feature/bgp/otg_tests/bgp_2byte_4byte_asn/metadata.textproto similarity index 100% rename from feature/experimental/bgp/otg_tests/bgp_2byte_4byte_asn/metadata.textproto rename to feature/bgp/otg_tests/bgp_2byte_4byte_asn/metadata.textproto diff --git a/feature/experimental/bgp/otg_tests/bgp_2byte_4byte_asn_policy_test/README.md b/feature/bgp/otg_tests/bgp_2byte_4byte_asn_policy_test/README.md similarity index 100% rename from feature/experimental/bgp/otg_tests/bgp_2byte_4byte_asn_policy_test/README.md rename to feature/bgp/otg_tests/bgp_2byte_4byte_asn_policy_test/README.md diff --git a/feature/experimental/bgp/otg_tests/bgp_2byte_4byte_asn_policy_test/bgp_2byte_4byte_asn_policy_test.go b/feature/bgp/otg_tests/bgp_2byte_4byte_asn_policy_test/bgp_2byte_4byte_asn_policy_test.go similarity index 100% rename from feature/experimental/bgp/otg_tests/bgp_2byte_4byte_asn_policy_test/bgp_2byte_4byte_asn_policy_test.go rename to feature/bgp/otg_tests/bgp_2byte_4byte_asn_policy_test/bgp_2byte_4byte_asn_policy_test.go diff --git a/feature/experimental/bgp/otg_tests/bgp_2byte_4byte_asn_policy_test/metadata.textproto b/feature/bgp/otg_tests/bgp_2byte_4byte_asn_policy_test/metadata.textproto similarity index 100% rename from feature/experimental/bgp/otg_tests/bgp_2byte_4byte_asn_policy_test/metadata.textproto rename to feature/bgp/otg_tests/bgp_2byte_4byte_asn_policy_test/metadata.textproto diff --git a/feature/experimental/bgp/otg_tests/bgp_afi_safi_defaults/README.md b/feature/bgp/otg_tests/bgp_afi_safi_defaults/README.md similarity index 62% rename from feature/experimental/bgp/otg_tests/bgp_afi_safi_defaults/README.md rename to feature/bgp/otg_tests/bgp_afi_safi_defaults/README.md index a1fa3a84b8b..68fe918d23c 100644 --- a/feature/experimental/bgp/otg_tests/bgp_afi_safi_defaults/README.md +++ b/feature/bgp/otg_tests/bgp_afi_safi_defaults/README.md @@ -75,47 +75,43 @@ BGP AFI SAFI OC DEFAULTS TEST * For IPv6 neighbor ensure that the IPv6 neighborship is not ESTABLISHED and IPv6-unicast capabilities are set to FALSE. -## Config Parameter coverage - -* /network-instances/network-instance/protocols/protocol/bgp/global/config/as -* /network-instances/network-instance/protocols/protocol/bgp/global/config/router-id -* /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/config/auth-password -* /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/config/ - neighbor-address -* /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/config/peer-as -* /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/neighbor-address -* /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/afi-safis/afi-safi/ - config/enabled -* /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/config/ - auth-password -* /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/config/ - neighbor-address -* /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/config/peer-as -* /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/config/peer-group/ - peer-group-name -* /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/afi-safis/ - afi-safi/config/enabled -* /network-instances/network-instance/protocols/protocol/bgp/global/afi-safis/afi-safi/config/enabled - - -## Telemetry Parameter coverage - -* /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/state/session-state -* /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/state/ - supported-capabilities -* /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/state/peer-type -* /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/state/peer-as -* /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/state/ - supported-capabilities -* /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/state/peer-type -* /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/state/peer-as -* /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/state/local-as -* /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/state/peer-group - -## Protocol/RPC Parameter coverage - -N/A - -## Minimum DUT platform requirement - -N/A + +## OpenConfig Path and RPC Coverage + +The below yaml defines the OC paths intended to be covered by this test. OC paths used for test setup are not listed here. + +```yaml +paths: + ## Config Parameter coverage + + /network-instances/network-instance/protocols/protocol/bgp/global/config/as: + /network-instances/network-instance/protocols/protocol/bgp/global/config/router-id: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/config/auth-password: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/config/neighbor-address: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/config/peer-as: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/neighbor-address: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/afi-safis/afi-safi/config/enabled: + /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/config/auth-password: + /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/config/peer-as: + /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/afi-safis/afi-safi/config/enabled: + /network-instances/network-instance/protocols/protocol/bgp/global/afi-safis/afi-safi/config/enabled: + + ## Telemetry Parameter coverage + + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/state/session-state: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/state/supported-capabilities: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/state/peer-type: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/state/peer-as: + /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/state/peer-type: + /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/state/peer-as: + /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/state/local-as: + +rpcs: + gnmi: + gNMI.Set: + gNMI.Get: + gNMI.Subscribe: +``` +## Minimum DUT Required + +vRX - Virtual Router Device \ No newline at end of file diff --git a/feature/experimental/bgp/otg_tests/bgp_afi_safi_defaults/bgp_afi_safi_defaults_test.go b/feature/bgp/otg_tests/bgp_afi_safi_defaults/bgp_afi_safi_defaults_test.go similarity index 99% rename from feature/experimental/bgp/otg_tests/bgp_afi_safi_defaults/bgp_afi_safi_defaults_test.go rename to feature/bgp/otg_tests/bgp_afi_safi_defaults/bgp_afi_safi_defaults_test.go index d5405862c93..568d9060182 100644 --- a/feature/experimental/bgp/otg_tests/bgp_afi_safi_defaults/bgp_afi_safi_defaults_test.go +++ b/feature/bgp/otg_tests/bgp_afi_safi_defaults/bgp_afi_safi_defaults_test.go @@ -286,7 +286,7 @@ func configureOTG(t *testing.T, otg *otg.OTG, otgPeerList []string) gosnappi.Con case otgPort1V6Peer: iDut1Bgp6Peer := iDut1Bgp.Ipv6Interfaces().Add().SetIpv6Name(iDut1Ipv6.Name()).Peers().Add().SetName(otgPort1V6Peer) iDut1Bgp6Peer.SetPeerAddress(iDut1Ipv6.Gateway()).SetAsNumber(ateAS).SetAsType(gosnappi.BgpV6PeerAsType.EBGP) - iDut1Bgp6Peer.Capability().SetIpv4UnicastAddPath(true).SetIpv6UnicastAddPath(true) + iDut1Bgp6Peer.Capability().SetIpv4UnicastAddPath(true).SetIpv6UnicastAddPath(true).SetExtendedNextHopEncoding(true) iDut1Bgp6Peer.LearnedInformationFilter().SetUnicastIpv4Prefix(true).SetUnicastIpv6Prefix(true) case otgPort2V4Peer: iDut2Bgp4Peer := iDut2Bgp.Ipv4Interfaces().Add().SetIpv4Name(iDut2Ipv4.Name()).Peers().Add().SetName(otgPort2V4Peer) @@ -296,7 +296,7 @@ func configureOTG(t *testing.T, otg *otg.OTG, otgPeerList []string) gosnappi.Con case otgPort2V6Peer: iDut2Bgp6Peer := iDut2Bgp.Ipv6Interfaces().Add().SetIpv6Name(iDut2Ipv6.Name()).Peers().Add().SetName(otgPort2V6Peer) iDut2Bgp6Peer.SetPeerAddress(iDut2Ipv6.Gateway()).SetAsNumber(dutAS).SetAsType(gosnappi.BgpV6PeerAsType.IBGP) - iDut2Bgp6Peer.Capability().SetIpv4UnicastAddPath(true).SetIpv6UnicastAddPath(true) + iDut2Bgp6Peer.Capability().SetIpv4UnicastAddPath(true).SetIpv6UnicastAddPath(true).SetExtendedNextHopEncoding(true) iDut2Bgp6Peer.LearnedInformationFilter().SetUnicastIpv4Prefix(true).SetUnicastIpv6Prefix(true) } } diff --git a/feature/experimental/bgp/otg_tests/bgp_afi_safi_defaults/metadata.textproto b/feature/bgp/otg_tests/bgp_afi_safi_defaults/metadata.textproto similarity index 100% rename from feature/experimental/bgp/otg_tests/bgp_afi_safi_defaults/metadata.textproto rename to feature/bgp/otg_tests/bgp_afi_safi_defaults/metadata.textproto diff --git a/feature/experimental/bgp/otg_tests/bgp_always_compare_med/README.md b/feature/bgp/otg_tests/bgp_always_compare_med/README.md similarity index 57% rename from feature/experimental/bgp/otg_tests/bgp_always_compare_med/README.md rename to feature/bgp/otg_tests/bgp_always_compare_med/README.md index 91fdcdad95e..d239bc302e9 100644 --- a/feature/experimental/bgp/otg_tests/bgp_always_compare_med/README.md +++ b/feature/bgp/otg_tests/bgp_always_compare_med/README.md @@ -18,20 +18,22 @@ BGP always compare MED * Validate the change of traffic flow because of the change (OTG Port2). * Validate session state and capabilities received on DUT using telemetry. -## Config Parameter coverage - -* /route-selection-options/config/always-compare-med -* /global/afi-safis/afi-safi/route-selection-options/config/always-compare-med -* /global/route-selection-options/config/always-compare-med - -## Telemetry Parameter coverage - -* /global/afi-safis/afi-safi/route-selection-options/state/always-compare-med -* /global/route-selection-options/state/always-compare-med - -## Protocol/RPC Parameter coverage - -N/A +## OpenConfig Path and RPC Coverage +```yaml +paths: + ## Config Parameter Coverage + /network-instances/network-instance/protocols/protocol/bgp/global/route-selection-options/config/always-compare-med: + /network-instances/network-instance/protocols/protocol/bgp/global/afi-safis/afi-safi/route-selection-options/config/always-compare-med: + + ## Telemetry Parameter Coverage + /network-instances/network-instance/protocols/protocol/bgp/global/route-selection-options/state/always-compare-med: + /network-instances/network-instance/protocols/protocol/bgp/global/afi-safis/afi-safi/route-selection-options/state/always-compare-med: + +rpcs: + gnmi: + gNMI.Subscribe: + gNMI.Set: +``` ## Minimum DUT platform requirement diff --git a/feature/experimental/bgp/otg_tests/bgp_always_compare_med/bgp_always_compare_med_test.go b/feature/bgp/otg_tests/bgp_always_compare_med/bgp_always_compare_med_test.go similarity index 100% rename from feature/experimental/bgp/otg_tests/bgp_always_compare_med/bgp_always_compare_med_test.go rename to feature/bgp/otg_tests/bgp_always_compare_med/bgp_always_compare_med_test.go diff --git a/feature/experimental/bgp/otg_tests/bgp_always_compare_med/metadata.textproto b/feature/bgp/otg_tests/bgp_always_compare_med/metadata.textproto similarity index 100% rename from feature/experimental/bgp/otg_tests/bgp_always_compare_med/metadata.textproto rename to feature/bgp/otg_tests/bgp_always_compare_med/metadata.textproto diff --git a/feature/experimental/bgp/otg_tests/bgp_override_as_path_split_horizon_test/README.md b/feature/bgp/otg_tests/bgp_override_as_path_split_horizon_test/README.md similarity index 100% rename from feature/experimental/bgp/otg_tests/bgp_override_as_path_split_horizon_test/README.md rename to feature/bgp/otg_tests/bgp_override_as_path_split_horizon_test/README.md diff --git a/feature/experimental/bgp/otg_tests/bgp_remove_private_as/README.md b/feature/bgp/otg_tests/bgp_remove_private_as/README.md similarity index 60% rename from feature/experimental/bgp/otg_tests/bgp_remove_private_as/README.md rename to feature/bgp/otg_tests/bgp_remove_private_as/README.md index 6a5ce3e8a52..7da3a2fc346 100644 --- a/feature/experimental/bgp/otg_tests/bgp_remove_private_as/README.md +++ b/feature/bgp/otg_tests/bgp_remove_private_as/README.md @@ -18,17 +18,20 @@ BGP remove private AS * PRIV_AS1 AS1 * AS1 PRIV_AS1 AS2 -## Config Parameter coverage - -* /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/config/remove-private-as - -## Telemetry Parameter coverage - -* /network-instances/network-instance/protocols/protocol/bgp/rib/attr-sets/attr-set/as4-path/as4-segment/state - -## Protocol/RPC Parameter coverage - -N/A +## OpenConfig Path and RPC Coverage +```yaml +paths: + ## Config Parameter Coverage + /network-instances/network-instance/protocols/protocol/bgp/peer-groups/peer-group/config/remove-private-as: + + ## Telemetry Parameter Coverage + /network-instances/network-instance/protocols/protocol/bgp/rib/attr-sets/attr-set/as4-path/as4-segment/state/index: + +rpcs: + gnmi: + gNMI.Subscribe: + gNMI.Set: +``` ## Minimum DUT platform requirement diff --git a/feature/experimental/bgp/otg_tests/bgp_remove_private_as/bgp_remove_private_as_test.go b/feature/bgp/otg_tests/bgp_remove_private_as/bgp_remove_private_as_test.go similarity index 100% rename from feature/experimental/bgp/otg_tests/bgp_remove_private_as/bgp_remove_private_as_test.go rename to feature/bgp/otg_tests/bgp_remove_private_as/bgp_remove_private_as_test.go diff --git a/feature/experimental/bgp/otg_tests/bgp_remove_private_as/metadata.textproto b/feature/bgp/otg_tests/bgp_remove_private_as/metadata.textproto similarity index 100% rename from feature/experimental/bgp/otg_tests/bgp_remove_private_as/metadata.textproto rename to feature/bgp/otg_tests/bgp_remove_private_as/metadata.textproto diff --git a/feature/experimental/bgp/otg_tests/bgp_tcp_mss_path_mtu/README.md b/feature/bgp/otg_tests/bgp_tcp_mss_path_mtu/README.md similarity index 67% rename from feature/experimental/bgp/otg_tests/bgp_tcp_mss_path_mtu/README.md rename to feature/bgp/otg_tests/bgp_tcp_mss_path_mtu/README.md index 45457c0b801..8c21d568b0e 100644 --- a/feature/experimental/bgp/otg_tests/bgp_tcp_mss_path_mtu/README.md +++ b/feature/bgp/otg_tests/bgp_tcp_mss_path_mtu/README.md @@ -25,19 +25,22 @@ * Re-establish the IBGP sessions by tcp reset. * Validate that the min MSS value has been adjusted to be below 1500 bytes on the tcp session. -## Config Parameter coverage - -* /neighbors/neighbor/transport/config/tcp-mss -* /neighbors/neighbor/transport/config/mtu-discovery - -## Telemetry Parameter coverage - -* /neighbors/neighbor/transport/state/tcp-mss -* /neighbors/neighbor/transport/state/mtu-discovery - -## Protocol/RPC Parameter coverage - -N/A +## OpenConfig Path and RPC Coverage +```yaml +paths: + ## Config Parameter Coverage + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/transport/config/tcp-mss: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/transport/config/mtu-discovery: + + ## Telemetry Parameter Coverage + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/transport/state/tcp-mss: + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/transport/state/mtu-discovery: + +rpcs: + gnmi: + gNMI.Subscribe: + gNMI.Set: +``` ## Minimum DUT platform requirement diff --git a/feature/experimental/bgp/otg_tests/bgp_tcp_mss_path_mtu/bgp_tcp_mss_path_mtu_test.go b/feature/bgp/otg_tests/bgp_tcp_mss_path_mtu/bgp_tcp_mss_path_mtu_test.go similarity index 100% rename from feature/experimental/bgp/otg_tests/bgp_tcp_mss_path_mtu/bgp_tcp_mss_path_mtu_test.go rename to feature/bgp/otg_tests/bgp_tcp_mss_path_mtu/bgp_tcp_mss_path_mtu_test.go diff --git a/feature/experimental/bgp/otg_tests/bgp_tcp_mss_path_mtu/metadata.textproto b/feature/bgp/otg_tests/bgp_tcp_mss_path_mtu/metadata.textproto similarity index 100% rename from feature/experimental/bgp/otg_tests/bgp_tcp_mss_path_mtu/metadata.textproto rename to feature/bgp/otg_tests/bgp_tcp_mss_path_mtu/metadata.textproto diff --git a/feature/experimental/bgp/otg_tests/link_bandwidth_test/README.md b/feature/bgp/otg_tests/link_bandwidth_test/README.md similarity index 100% rename from feature/experimental/bgp/otg_tests/link_bandwidth_test/README.md rename to feature/bgp/otg_tests/link_bandwidth_test/README.md diff --git a/feature/experimental/bgp/otg_tests/link_bandwidth_test/link_bandwidth_test.go b/feature/bgp/otg_tests/link_bandwidth_test/link_bandwidth_test.go similarity index 100% rename from feature/experimental/bgp/otg_tests/link_bandwidth_test/link_bandwidth_test.go rename to feature/bgp/otg_tests/link_bandwidth_test/link_bandwidth_test.go diff --git a/feature/experimental/bgp/otg_tests/link_bandwidth_test/metadata.textproto b/feature/bgp/otg_tests/link_bandwidth_test/metadata.textproto similarity index 100% rename from feature/experimental/bgp/otg_tests/link_bandwidth_test/metadata.textproto rename to feature/bgp/otg_tests/link_bandwidth_test/metadata.textproto diff --git a/feature/bgp/policybase/otg_tests/community_test/README.md b/feature/bgp/policybase/otg_tests/community_test/README.md index a068367488f..f1911b3c359 100644 --- a/feature/bgp/policybase/otg_tests/community_test/README.md +++ b/feature/bgp/policybase/otg_tests/community_test/README.md @@ -54,6 +54,27 @@ BGP policy configuration for Community Sets * Verify traffic is received on ATE port 1 for accepted prefixes. * Verify traffic is not received on ATE port 1 for rejected prefixes. +* RT-7.2.3 - Update community set and validate + 1. Configure a community-set named `update_comm_set` with "100:1" as member. + + 2. Create a `policy-definition` named 'community-match' with the following `statements` + * statement[name='accept_update_comm_set']/ + * conditions/bgp-conditions/match-community-set/config/community-set = 'update_comm_set' + * conditions/bgp-conditions/match-community-set/config/match-set-options = INVERT + * actions/config/policy-result = ACCEPT_ROUTE + + 3. Send traffic from ATE port-2 to all prefix-sets. + * Verify traffic is received on ATE port 1 for accepted prefixes for all community set except "100:1". + * Verify traffic is not received on ATE port 1 for rejected prefixes for community set "100:1". + + 4. Update the community-set named `update_comm_set` with "200:2" as member. + + 5. Send traffic from ATE port-2 to all prefix-sets. + * Verify traffic is received on ATE port 1 for accepted prefixes for all community set except "200:1". + * Verify traffic is not received on ATE port 1 for rejected prefixes for community set "200:1". + + + ### Expected community matches | prefix-set | any_my_3_comms | all_3_comms | no_3_comms | any_my_regex_comms | @@ -155,4 +176,4 @@ rpcs: gnmi: gNMI.Set: gNMI.Subscribe: -``` \ No newline at end of file +``` diff --git a/feature/bgp/policybase/otg_tests/community_test/community_test.go b/feature/bgp/policybase/otg_tests/community_test/community_test.go index f37293a40c3..c5164592725 100644 --- a/feature/bgp/policybase/otg_tests/community_test/community_test.go +++ b/feature/bgp/policybase/otg_tests/community_test/community_test.go @@ -94,7 +94,9 @@ func configureImportBGPPolicy(t *testing.T, dut *ondatra.DUTDevice, ipv4 string, if deviations.BGPConditionsMatchCommunitySetUnsupported(dut) { stmt1.GetOrCreateConditions().GetOrCreateBgpConditions().SetCommunitySet(communitySetName) } else { - stmt1.GetOrCreateConditions().GetOrCreateBgpConditions().GetOrCreateMatchCommunitySet().SetCommunitySet(communitySetName) + communitySet := stmt1.GetOrCreateConditions().GetOrCreateBgpConditions().GetOrCreateMatchCommunitySet() + communitySet.SetCommunitySet(communitySetName) + communitySet.SetMatchSetOptions(oc.E_RoutingPolicy_MatchSetOptionsType(matchSetOptions)) } if deviations.CommunityMemberRegexUnsupported(dut) && communitySetName == comunitySetNameRegex { @@ -223,32 +225,7 @@ type testCase struct { } func TestCommunitySet(t *testing.T) { - bs := cfgplugins.NewBGPSession(t, cfgplugins.PortCount2, nil) - bs.WithEBGP(t, []oc.E_BgpTypes_AFI_SAFI_TYPE{oc.BgpTypes_AFI_SAFI_TYPE_IPV4_UNICAST, oc.BgpTypes_AFI_SAFI_TYPE_IPV6_UNICAST}, []string{"port2"}, true, true) - - var communityMembers = [][][]int{ - { - {100, 1}, {200, 2}, {300, 3}, - }, - { - {100, 1}, {101, 1}, {200, 2}, - }, - { - {107, 1}, {108, 1}, {109, 1}, - }, - { - {400, 1}, {500, 1}, {600, 1}, - }, - } - - configureOTG(t, bs, prefixesV4, prefixesV6, communityMembers) - bs.PushAndStart(t) - - t.Log("Verify DUT BGP sessions up") - cfgplugins.VerifyDUTBGPEstablished(t, bs.DUT) - t.Log("Verify OTG BGP sessions up") - cfgplugins.VerifyOTGBGPEstablished(t, bs.ATE) - + bs := testSetup(t) ipv4 := bs.ATETop.Devices().Items()[1].Ethernets().Items()[0].Ipv4Addresses().Items()[0].Address() ipv6 := bs.ATETop.Devices().Items()[1].Ethernets().Items()[0].Ipv6Addresses().Items()[0].Address() @@ -285,6 +262,10 @@ func TestCommunitySet(t *testing.T) { for _, tc := range testCases { t.Run(tc.desc, func(t *testing.T) { + if tc.desc == "Testing with no_3_comms" && deviations.CommunityInvertAnyUnsupported(bs.DUT) { + t.Skip("Skipping community match invert testcase") + } + configureImportBGPPolicy(t, bs.DUT, ipv4, ipv6, tc.communitySetName, tc.communityMatch, tc.matchSetOptions) sleepTime := time.Duration(totalPackets/trafficPps) + 2 @@ -313,3 +294,79 @@ func TestCommunitySet(t *testing.T) { }) } } + +func testSetup(t *testing.T) *cfgplugins.BGPSession { + t.Helper() + + bs := cfgplugins.NewBGPSession(t, cfgplugins.PortCount2, nil) + bs.WithEBGP(t, []oc.E_BgpTypes_AFI_SAFI_TYPE{oc.BgpTypes_AFI_SAFI_TYPE_IPV4_UNICAST, oc.BgpTypes_AFI_SAFI_TYPE_IPV6_UNICAST}, []string{"port2"}, true, true) + + var communityMembers = [][][]int{ + { + {100, 1}, {200, 2}, {300, 3}, + }, + { + {100, 1}, {101, 1}, {200, 2}, + }, + { + {107, 1}, {108, 1}, {109, 1}, + }, + { + {400, 1}, {500, 1}, {600, 1}, + }, + } + + configureOTG(t, bs, prefixesV4, prefixesV6, communityMembers) + bs.PushAndStart(t) + + t.Log("Verify DUT BGP sessions up") + cfgplugins.VerifyDUTBGPEstablished(t, bs.DUT) + t.Log("Verify OTG BGP sessions up") + cfgplugins.VerifyOTGBGPEstablished(t, bs.ATE) + + return bs +} + +func TestCommunitySetUpdate(t *testing.T) { + bs := testSetup(t) + ipv4 := bs.ATETop.Devices().Items()[1].Ethernets().Items()[0].Ipv4Addresses().Items()[0].Address() + ipv6 := bs.ATETop.Devices().Items()[1].Ethernets().Items()[0].Ipv6Addresses().Items()[0].Address() + + commMatch := [3]string{"100:1"} + configureImportBGPPolicy(t, bs.DUT, ipv4, ipv6, "update_comm_set", commMatch, oc.BgpPolicy_MatchSetOptionsType_INVERT) + validateCommunitySetUpdateTraffic(t, bs) + + // change community match set + commMatch = [3]string{"200:2"} + configureImportBGPPolicy(t, bs.DUT, ipv4, ipv6, "update_comm_set", commMatch, oc.BgpPolicy_MatchSetOptionsType_INVERT) + validateCommunitySetUpdateTraffic(t, bs) +} + +func validateCommunitySetUpdateTraffic(t *testing.T, bs *cfgplugins.BGPSession) { + t.Helper() + + sleepTime := time.Duration(totalPackets/trafficPps) + 2 + bs.ATETop.Flows().Clear() + for index, prefixPairV4 := range prefixesV4 { + configureFlow(t, bs, prefixPairV4, "ipv4", index) + configureFlow(t, bs, prefixesV6[index], "ipv6", index) + } + bs.PushAndStartATE(t) + + // Verify BGP session after its reset with OTG push config & start + cfgplugins.VerifyDUTBGPEstablished(t, bs.DUT) + + t.Logf("Starting traffic for IPv4 and v6") + bs.ATE.OTG().StartTraffic(t) + time.Sleep(sleepTime * time.Second) + bs.ATE.OTG().StopTraffic(t) + otgutils.LogFlowMetrics(t, bs.ATE.OTG(), bs.ATETop) + + testResults := [4]bool{false, false, true, true} + for index, prefixPairV4 := range prefixesV4 { + t.Logf("Validating traffic test for IPv4 prefixes: [%s, %s]. Expected Result: [%t]", prefixPairV4[0], prefixPairV4[1], testResults[index]) + verifyTraffic(t, bs.ATE, "ipv4", testResults[index], index) + t.Logf("Validating traffic test for IPv6 prefixes: [%s, %s]. Expected Result: [%t]", prefixesV6[index][0], prefixesV6[index][1], testResults[index]) + verifyTraffic(t, bs.ATE, "ipv6", testResults[index], index) + } +} diff --git a/feature/bgp/policybase/otg_tests/community_test/metadata.textproto b/feature/bgp/policybase/otg_tests/community_test/metadata.textproto index e30e35b5e7a..4c6b8f1496e 100644 --- a/feature/bgp/policybase/otg_tests/community_test/metadata.textproto +++ b/feature/bgp/policybase/otg_tests/community_test/metadata.textproto @@ -40,4 +40,12 @@ platform_exceptions: { bgp_conditions_match_community_set_unsupported: true } } +platform_exceptions: { + platform: { + vendor: JUNIPER + } + deviations: { + community_invert_any_unsupported: true + } +} diff --git a/feature/container/containerz/tests/container_lifecycle/containerz_test.go b/feature/container/containerz/tests/container_lifecycle/containerz_test.go index 4d14062b228..696c9a9c0fa 100644 --- a/feature/container/containerz/tests/container_lifecycle/containerz_test.go +++ b/feature/container/containerz/tests/container_lifecycle/containerz_test.go @@ -9,6 +9,7 @@ import ( "github.com/openconfig/containerz/client" cpb "github.com/openconfig/featureprofiles/internal/cntrsrv/proto/cntr" "google.golang.org/grpc" + "google.golang.org/grpc/connectivity" "google.golang.org/grpc/credentials" ) @@ -53,7 +54,9 @@ func TestDeployAndStartContainer(t *testing.T) { tlsc := credentials.NewTLS(&tls.Config{ InsecureSkipVerify: true, // NOLINT }) - conn, err := grpc.DialContext(ctx, "localhost:60061", grpc.WithTransportCredentials(tlsc), grpc.WithBlock()) + conntectionState := connectivity.Ready + conn, err := grpc.NewClient("localhost:60061", grpc.WithTransportCredentials(tlsc)) + conn.WaitForStateChange(ctx, conntectionState) if err != nil { t.Fatalf("Failed to dial cntrsrv, %v", err) } diff --git a/feature/container/networking/tests/container_connectivity/README.md b/feature/container/networking/tests/container_connectivity/README.md index 41cb94a38ce..0c5156b571b 100644 --- a/feature/container/networking/tests/container_connectivity/README.md +++ b/feature/container/networking/tests/container_connectivity/README.md @@ -50,3 +50,11 @@ service on `tcp/[::]60062`. * Instruct C2 to make a gRPC dial call to C2's listen port with a specified timeout, ensure that an RPC response is received. +## OpenConfig Path and RPC Coverage +```yaml +rpcs: + gnmi: + gNMI.Get: + gNMI.Set: + gNMI.Subscribe: +``` diff --git a/feature/container/networking/tests/container_connectivity/cntr_test.go b/feature/container/networking/tests/container_connectivity/cntr_test.go index b81cbec889a..e1d57a59c3a 100644 --- a/feature/container/networking/tests/container_connectivity/cntr_test.go +++ b/feature/container/networking/tests/container_connectivity/cntr_test.go @@ -34,6 +34,7 @@ import ( "github.com/openconfig/ondatra/gnmi/oc" "github.com/openconfig/ygot/ygot" "google.golang.org/grpc" + "google.golang.org/grpc/connectivity" "google.golang.org/grpc/credentials" "google.golang.org/protobuf/encoding/prototext" @@ -57,7 +58,8 @@ func DialService(ctx context.Context, t *testing.T, name string, dut *ondatra.DU tlsc := credentials.NewTLS(&tls.Config{ InsecureSkipVerify: true, // NOLINT }) - conn, err := dialer.DialGRPC(ctx, name, grpc.WithTransportCredentials(tlsc), grpc.WithBlock()) + conn, err := dialer.DialGRPC(ctx, name, grpc.WithTransportCredentials(tlsc)) + conn.WaitForStateChange(ctx, connectivity.Ready) if err != nil { t.Fatalf("Failed to dial %s, %v", name, err) } diff --git a/feature/experimental/basic_entries_installed_in_gribi/gribi_ip4_entry/feature.textproto b/feature/experimental/basic_entries_installed_in_gribi/gribi_ip4_entry/feature.textproto deleted file mode 100644 index 14e9565fdd7..00000000000 --- a/feature/experimental/basic_entries_installed_in_gribi/gribi_ip4_entry/feature.textproto +++ /dev/null @@ -1,70 +0,0 @@ -# Copyright 2022 Google LLC -# -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at -# -# https://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. -# -# proto-file: github.com/openconfig/featureprofiles/proto/feature.proto -# proto-message: FeatureProfile - -id { - name: "experimental_basic_entries_installed_in_gribi_gribi_ip4_entry" - version: 1 -} - -telemetry_path { - path: "/network-instances/network-instance/afts/ipv4-unicast/ipv4-entry/state/next-hop-group" -} -telemetry_path { - path: "/network-instances/network-instance/afts/ipv4-unicast/ipv4-entry/state/origin-protocol" -} -telemetry_path { - path: "/network-instances/network-instance/afts/ipv4-unicast/ipv4-entry/state/prefix" -} -telemetry_path { - path: "/network-instances/network-instance/afts/next-hop-groups/next-hop-group/id" -} -telemetry_path { - path: "/network-instances/network-instance/afts/next-hop-groups/next-hop-group/next-hops/next-hop/index" -} -telemetry_path { - path: "/network-instances/network-instance/afts/next-hop-groups/next-hop-group/next-hops/next-hop/state/index" -} -telemetry_path { - path: "/network-instances/network-instance/afts/next-hop-groups/next-hop-group/state/id" -} -telemetry_path { - path: "/network-instances/network-instance/afts/next-hops/next-hop/index" -} -telemetry_path { - path: "/network-instances/network-instance/afts/next-hops/next-hop/interface-ref/state/interface" -} -telemetry_path { - path: "/network-instances/network-instance/afts/next-hops/next-hop/interface-ref/state/subinterface" -} -telemetry_path { - path: "/network-instances/network-instance/afts/next-hops/next-hop/state/index" -} -telemetry_path { - path: "/network-instances/network-instance/afts/next-hops/next-hop/state/ip-address" -} -telemetry_path { - path: "/network-instances/network-instance/afts/next-hops/next-hop/state/mac-address" -} -telemetry_path { - path: "/network-instances/network-instance/afts/ipv4-unicast/ipv4-entry/state/decapsulate-header" -} -telemetry_path { - path: "/network-instances/network-instance/afts/ipv4-unicast/ipv4-entry/state/counters/octets-forwarded" -} -telemetry_path { - path: "/network-instances/network-instance/afts/ipv4-unicast/ipv4-entry/state/counters/packets-forwarded" -} diff --git a/feature/experimental/gnmi_service/benchmarking_drained_configuration_convergence_time/feature.textproto b/feature/experimental/gnmi_service/benchmarking_drained_configuration_convergence_time/feature.textproto deleted file mode 100644 index fc6bb224159..00000000000 --- a/feature/experimental/gnmi_service/benchmarking_drained_configuration_convergence_time/feature.textproto +++ /dev/null @@ -1,31 +0,0 @@ -# Copyright 2022 Google LLC -# -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at -# -# https://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. -# -# proto-file: github.com/openconfig/featureprofiles/proto/feature.proto -# proto-message: FeatureProfile - -id { - name: "experimental_gnmi_service_benchmarking_drained_configuration_convergence_time" - version: 1 -} - -config_path { - path: "/routing-policy/policy-definitions/policy-definition/statements/statement/actions/bgp-actions/config/set-med" -} -config_path { - path: "/routing-policy/policy-definitions/policy-definition/statements/statement/actions/bgp-actions/set-as-path-prepend/config/repeat-n" -} -config_path { - path: "/routing-policy/policy-definitions/policy-definition/statements/statement/actions/bgp-actions/set-as-path-prepend/config/asn" -} diff --git a/feature/experimental/gnmi_service/telemetry_port_speed/feature.textproto b/feature/experimental/gnmi_service/telemetry_port_speed/feature.textproto deleted file mode 100644 index f7a6d7df109..00000000000 --- a/feature/experimental/gnmi_service/telemetry_port_speed/feature.textproto +++ /dev/null @@ -1,31 +0,0 @@ -# Copyright 2022 Google LLC -# -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at -# -# https://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. -# -# proto-file: github.com/openconfig/featureprofiles/proto/feature.proto -# proto-message: FeatureProfile - -id { - name: "experimental_gnmi_service_telemetry_port_speed" - version: 1 -} - -telemetry_path { - path: "/interfaces/interface/state/oper-status" -} -telemetry_path { - path: "/interfaces/interface/ethernet/state/port-speed" -} -telemetry_path { - path: "/interfaces/interface/aggregation/state/lag-speed" -} diff --git a/feature/experimental/hierarchical_gribi_entries/base_hierarchical_route_installation/feature.textproto b/feature/experimental/hierarchical_gribi_entries/base_hierarchical_route_installation/feature.textproto deleted file mode 100644 index f4d10b21f31..00000000000 --- a/feature/experimental/hierarchical_gribi_entries/base_hierarchical_route_installation/feature.textproto +++ /dev/null @@ -1,73 +0,0 @@ -# Copyright 2022 Google LLC -# -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at -# -# https://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. -# -# proto-file: github.com/openconfig/featureprofiles/proto/feature.proto -# proto-message: FeatureProfile - -id { - name: "experimental_hierarchical_gribi_entries_base_hierarchical_route_installation" - version: 1 -} - -telemetry_path { - path: "/network-instances/network-instance/afts/ipv4-unicast/ipv4-entry/state/next-hop-group" -} -telemetry_path { - path: "/network-instances/network-instance/afts/ipv4-unicast/ipv4-entry/state/origin-protocol" -} -telemetry_path { - path: "/network-instances/network-instance/afts/ipv4-unicast/ipv4-entry/state/prefix" -} -telemetry_path { - path: "/network-instances/network-instance/afts/next-hop-groups/next-hop-group/id" -} -telemetry_path { - path: "/network-instances/network-instance/afts/next-hop-groups/next-hop-group/next-hops/next-hop/index" -} -telemetry_path { - path: "/network-instances/network-instance/afts/next-hop-groups/next-hop-group/next-hops/next-hop/state/index" -} -telemetry_path { - path: "/network-instances/network-instance/afts/next-hop-groups/next-hop-group/state/id" -} -telemetry_path { - path: "/network-instances/network-instance/afts/next-hops/next-hop/index" -} -telemetry_path { - path: "/network-instances/network-instance/afts/next-hops/next-hop/interface-ref/state/interface" -} -telemetry_path { - path: "/network-instances/network-instance/afts/next-hops/next-hop/interface-ref/state/subinterface" -} -telemetry_path { - path: "/network-instances/network-instance/afts/next-hops/next-hop/state/index" -} -telemetry_path { - path: "/network-instances/network-instance/afts/next-hops/next-hop/state/ip-address" -} -telemetry_path { - path: "/network-instances/network-instance/afts/next-hops/next-hop/state/mac-address" -} -telemetry_path { - path: "/network-instances/network-instance/afts/next-hop-groups/next-hop-group/state/backup-next-hop-group" -} -telemetry_path { - path: "/network-instances/network-instance/afts/next-hop-groups/next-hop-group/state/color" -} -telemetry_path { - path: "/network-instances/network-instance/afts/next-hops/next-hop/state/origin-protocol" -} -telemetry_path { - path: "/network-instances/network-instance/afts/next-hops/next-hop/state/pushed-mpls-label-stack" -} diff --git a/feature/experimental/hierarchical_gribi_entries/traffic_balancing_according_to_weights/feature.textproto b/feature/experimental/hierarchical_gribi_entries/traffic_balancing_according_to_weights/feature.textproto deleted file mode 100644 index 2f8a1e24a06..00000000000 --- a/feature/experimental/hierarchical_gribi_entries/traffic_balancing_according_to_weights/feature.textproto +++ /dev/null @@ -1,25 +0,0 @@ -# Copyright 2022 Google LLC -# -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at -# -# https://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. -# -# proto-file: github.com/openconfig/featureprofiles/proto/feature.proto -# proto-message: FeatureProfile - -id { - name: "experimental_hierarchical_gribi_entries_traffic_balancing_according_to_weights" - version: 1 -} - -telemetry_path { - path: "/network-instances/network-instance/afts/next-hop-groups/next-hop-group/next-hops/next-hop/state/weight" -} diff --git a/feature/experimental/isis/ate_tests/internal/session/attrs.go b/feature/experimental/isis/ate_tests/internal/session/attrs.go deleted file mode 100644 index 06dfae73b5b..00000000000 --- a/feature/experimental/isis/ate_tests/internal/session/attrs.go +++ /dev/null @@ -1,124 +0,0 @@ -// Copyright 2022 Google LLC -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. - -package session - -// This is identical to the internal/attrs library except it points to ygnmi -import ( - "fmt" - - "github.com/openconfig/featureprofiles/internal/deviations" - "github.com/openconfig/ondatra" - "github.com/openconfig/ondatra/gnmi/oc" - "github.com/openconfig/ygot/ygot" -) - -// Attributes bundles some common attributes for devices and/or interfaces. -// It provides helpers to generate appropriate configuration for OpenConfig -// and for an ATETopology. All fields are optional; only those that are -// non-empty will be set when configuring an interface. -type Attributes struct { - IPv4 string - IPv6 string - MAC string - Name string // Interface name, only applied to ATE ports. - Desc string // Description, only applied to DUT interfaces. - IPv4Len uint8 // Prefix length for IPv4. - IPv6Len uint8 // Prefix length for IPv6. - MTU uint16 -} - -// IPv4CIDR constructs the IPv4 CIDR notation with the given prefix -// length, e.g. "192.0.2.1/30". -func (a *Attributes) IPv4CIDR() string { - return fmt.Sprintf("%s/%d", a.IPv4, a.IPv4Len) -} - -// IPv6CIDR constructs the IPv6 CIDR notation with the given prefix -// length, e.g. "2001:db8::1/126". -func (a *Attributes) IPv6CIDR() string { - return fmt.Sprintf("%s/%d", a.IPv6, a.IPv6Len) -} - -// ConfigInterface configures an OpenConfig interface with these attributes. -func (a *Attributes) ConfigInterface(intf *oc.Interface, dut *ondatra.DUTDevice) *oc.Interface { - if a.Desc != "" { - intf.Description = ygot.String(a.Desc) - } - intf.Type = oc.IETFInterfaces_InterfaceType_ethernetCsmacd - if deviations.InterfaceEnabled(dut) { - intf.Enabled = ygot.Bool(true) - } - if a.MTU > 0 && !deviations.OmitL2MTU(dut) { - intf.Mtu = ygot.Uint16(a.MTU + 14) - } - e := intf.GetOrCreateEthernet() - if a.MAC != "" { - e.MacAddress = ygot.String(a.MAC) - } - - s := intf.GetOrCreateSubinterface(0) - if a.IPv4 != "" { - s4 := s.GetOrCreateIpv4() - if deviations.InterfaceEnabled(dut) && !deviations.IPv4MissingEnabled(dut) { - s4.Enabled = ygot.Bool(true) - } - if a.MTU > 0 { - s4.Mtu = ygot.Uint16(a.MTU) - } - a4 := s4.GetOrCreateAddress(a.IPv4) - if a.IPv4Len > 0 { - a4.PrefixLength = ygot.Uint8(a.IPv4Len) - } - } - - if a.IPv6 != "" { - s6 := s.GetOrCreateIpv6() - if a.MTU > 0 { - s6.Mtu = ygot.Uint32(uint32(a.MTU)) - } - if deviations.InterfaceEnabled(dut) { - s6.Enabled = ygot.Bool(true) - } - a6 := s6.GetOrCreateAddress(a.IPv6) - if a.IPv6Len > 0 { - a6.PrefixLength = ygot.Uint8(a.IPv6Len) - } - } - return intf -} - -// NewOCInterface returns a new *oc.Interface configured with these attributes -func (a *Attributes) NewOCInterface(name string, dut *ondatra.DUTDevice) *oc.Interface { - return a.ConfigInterface(&oc.Interface{Name: ygot.String(name)}, dut) -} - -// AddToATE adds a new interface to an ATETopology with these attributes. -func (a *Attributes) AddToATE(top *ondatra.ATETopology, ap *ondatra.Port, peer *Attributes) *ondatra.Interface { - i := top.AddInterface(a.Name).WithPort(ap) - if a.MTU > 0 { - i.Ethernet().WithMTU(a.MTU) - } - if a.IPv4 != "" { - i.IPv4(). - WithAddress(a.IPv4CIDR()). - WithDefaultGateway(peer.IPv4) - } - if a.IPv6 != "" { - i.IPv6(). - WithAddress(a.IPv6CIDR()). - WithDefaultGateway(peer.IPv6) - } - return i -} diff --git a/feature/experimental/isis/ate_tests/internal/session/session.go b/feature/experimental/isis/ate_tests/internal/session/session.go deleted file mode 100644 index 6fbc5caa12c..00000000000 --- a/feature/experimental/isis/ate_tests/internal/session/session.go +++ /dev/null @@ -1,338 +0,0 @@ -// Copyright 2022 Google LLC -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. - -// Package session is deprecated and scoped only to be used with -// feature/experimental/isis/ate_tests/*. Do not use elsewhere. -package session - -import ( - "context" - "fmt" - "testing" - "time" - - "github.com/openconfig/featureprofiles/internal/deviations" - "github.com/openconfig/featureprofiles/internal/fptest" - "github.com/openconfig/ondatra" - "github.com/openconfig/ondatra/gnmi/oc" - "github.com/openconfig/ondatra/gnmi/oc/netinstisis" - "github.com/openconfig/ondatra/gnmi/oc/networkinstance" - "github.com/openconfig/ondatra/gnmi/oc/ocpath" - "github.com/openconfig/ondatra/ixnet" - "github.com/openconfig/ygnmi/ygnmi" - "github.com/openconfig/ygot/ygot" -) - -// PTISIS is shorthand for the long oc protocol type constant -const PTISIS = oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_ISIS - -// The testbed consists of a dut and an ate with two connections, labeled ISISIntf and Intf2. -// ISISIntf links dut:port1 and ate:port1, which are assigned 192.0.2.1/30 and 192.0.2.2/30 -// respectively. Intf2 connects dut:port2 to ate:port2, which are 192.0.2.5/30 and 192.0.2.6/30. -// We establish an IS-IS adjacency over ISISIntf. For traffic testing, we configure the ATE end -// of the IS-IS adjacency to advertise 198.51.100.0/24, then generate traffic through ate:port2 with -// IPv4 headers indicating that it should go to a random address in that range; the dut should -// route this traffic to the IS-IS link, where the ATE should log it arriving on ate:port1. -const ( - DUTAreaAddress = "49.0001" - ATEAreaAddress = "49.0002" - DUTSysID = "1920.0000.2001" - ISISName = "DEFAULT" - pLen4 = 30 - pLen6 = 126 -) - -var ( - // DUTNET is the Network Entity Title for the DUT - DUTNET = fmt.Sprintf("%v.%v.00", DUTAreaAddress, DUTSysID) - // DUTISISAttrs has attributes for the DUT ISIS connection on port1 - DUTISISAttrs = &Attributes{ - Desc: "DUT to ATE with IS-IS", - IPv4: "192.0.2.1", - IPv6: "2001:db8::1", - IPv4Len: pLen4, - IPv6Len: pLen6, - } - // ATEISISAttrs has attributes for the ATE ISIS connection on port1 - ATEISISAttrs = &Attributes{ - Name: "port1", - Desc: "ATE to DUT with IS-IS", - IPv4: "192.0.2.2", - IPv6: "2001:db8::2", - IPv4Len: pLen4, - IPv6Len: pLen6, - } - // DUTTrafficAttrs has attributes for the DUT end of the traffic connection (port2) - DUTTrafficAttrs = &Attributes{ - Desc: "DUT to ATE secondary link", - IPv4: "192.0.2.5", - IPv6: "2001:db8::5", - IPv4Len: pLen4, - IPv6Len: pLen6, - } - // ATETrafficAttrs has attributes for the ATE end of the traffic connection (port2) - ATETrafficAttrs = &Attributes{ - Name: "port2", - Desc: "ATE to DUT secondary link", - IPv4: "192.0.2.6", - IPv6: "2001:db8::6", - IPv4Len: pLen4, - IPv6Len: pLen6, - } -) - -// ISISPath is shorthand for ProtocolPath().Isis(). -func ISISPath(dut *ondatra.DUTDevice) *netinstisis.NetworkInstance_Protocol_IsisPath { - return ProtocolPath(dut).Isis() -} - -// ProtocolPath returns the path to the IS-IS protocol named ISISName on the -// default network instance. -func ProtocolPath(dut *ondatra.DUTDevice) *networkinstance.NetworkInstance_ProtocolPath { - return ocpath.Root().NetworkInstance(deviations.DefaultNetworkInstance(dut)).Protocol(PTISIS, ISISName) -} - -// addISISOC configures basic IS-IS on a device. -func addISISOC(dev *oc.Root, areaAddress, sysID, ifaceName string, dut *ondatra.DUTDevice) { - inst := dev.GetOrCreateNetworkInstance(deviations.DefaultNetworkInstance(dut)) - prot := inst.GetOrCreateProtocol(PTISIS, ISISName) - prot.Enabled = ygot.Bool(true) - isis := prot.GetOrCreateIsis() - glob := isis.GetOrCreateGlobal() - if deviations.ISISInstanceEnabledRequired(dut) { - glob.Instance = ygot.String(ISISName) - } - glob.Net = []string{fmt.Sprintf("%v.%v.00", areaAddress, sysID)} - glob.GetOrCreateAf(oc.IsisTypes_AFI_TYPE_IPV4, oc.IsisTypes_SAFI_TYPE_UNICAST).Enabled = ygot.Bool(true) - glob.GetOrCreateAf(oc.IsisTypes_AFI_TYPE_IPV6, oc.IsisTypes_SAFI_TYPE_UNICAST).Enabled = ygot.Bool(true) - level := isis.GetOrCreateLevel(2) - level.MetricStyle = oc.Isis_MetricStyle_WIDE_METRIC - intf := isis.GetOrCreateInterface(ifaceName) - intf.CircuitType = oc.Isis_CircuitType_POINT_TO_POINT - intf.Enabled = ygot.Bool(true) - // Configure ISIS level at global mode if true else at interface mode - if deviations.ISISInterfaceLevel1DisableRequired(dut) { - intf.GetOrCreateLevel(1).Enabled = ygot.Bool(false) - } else { - intf.GetOrCreateLevel(2).Enabled = ygot.Bool(true) - } - glob.LevelCapability = oc.Isis_LevelType_LEVEL_2 - // Configure ISIS enable flag at interface level - intf.GetOrCreateAf(oc.IsisTypes_AFI_TYPE_IPV4, oc.IsisTypes_SAFI_TYPE_UNICAST).Enabled = ygot.Bool(true) - intf.GetOrCreateAf(oc.IsisTypes_AFI_TYPE_IPV6, oc.IsisTypes_SAFI_TYPE_UNICAST).Enabled = ygot.Bool(true) - if deviations.ISISInterfaceAfiUnsupported(dut) { - intf.Af = nil - } - -} - -// addISISTopo configures basic IS-IS on an ATETopology interface. -func addISISTopo(iface *ondatra.Interface, areaAddress, sysID string) { - isis := iface.ISIS() - isis. - WithAreaID(areaAddress). - WithTERouterID(sysID). - WithNetworkTypePointToPoint(). - WithWideMetricEnabled(true). - WithLevelL2().WithMetric(10) -} - -// TestSession is a convenience wrapper around the dut, ate, ports, and -// topology we're using. -type TestSession struct { - DUT *ondatra.DUTDevice - DUTClient *ygnmi.Client - ATE *ondatra.ATEDevice - // Rather than looking these up all the time, we fetch all the relevant ports - // and interfaces at setup time. - DUTPort1, DUTPort2, ATEPort1, ATEPort2 *ondatra.Port - ATEIntf1, ATEIntf2 *ondatra.Interface - // DUTConf and ATETop can be modified by tests; calling .Push() will apply - // them to the dut and ate. - DUTConf *oc.Root - ATETop *ondatra.ATETopology -} - -// New creates a new TestSession using the default global config, and -// configures the interfaces on the dut and the ate. -func New(t testing.TB) (*TestSession, error) { - t.Helper() - s := &TestSession{} - s.DUT = ondatra.DUT(t, "dut") - var err error - s.DUTClient, err = ygnmi.NewClient(s.DUT.RawAPIs().GNMI(t), ygnmi.WithTarget(s.DUT.ID())) - if err != nil { - return nil, fmt.Errorf("unable to connect to gNMI on %v: %w", s.DUT, err) - } - s.DUTPort1 = s.DUT.Port(t, "port1") - s.DUTPort2 = s.DUT.Port(t, "port2") - s.DUTConf = &oc.Root{} - // configure dut ports - DUTISISAttrs.ConfigInterface(s.DUTConf.GetOrCreateInterface(s.DUTPort1.Name()), s.DUT) - DUTTrafficAttrs.ConfigInterface(s.DUTConf.GetOrCreateInterface(s.DUTPort2.Name()), s.DUT) - - // If there is no ate, any operation that requires the ATE will call - // t.Fatal() instead. This is helpful for debugging the parts of the test - // that don't use an ATE. - if ate, ok := ondatra.ATEs(t)["ate"]; ok { - s.ATE = ate - s.ATEPort1 = s.ATE.Port(t, "port1") - s.ATEPort2 = s.ATE.Port(t, "port2") - s.ATETop = s.ATE.Topology().New() - s.ATEIntf1 = ATEISISAttrs.AddToATE(s.ATETop, s.ATEPort1, DUTISISAttrs) - s.ATEIntf2 = ATETrafficAttrs.AddToATE(s.ATETop, s.ATEPort2, DUTTrafficAttrs) - } - return s, nil -} - -// MustNew creates a new TestSession or Fatal()s if anything goes wrong. -func MustNew(t testing.TB) *TestSession { - t.Helper() - v, err := New(t) - if err != nil { - t.Fatalf("Unable to initialize topology: %v", err) - } - return v -} - -// WithISIS adds ISIS to a test session. -func (s *TestSession) WithISIS() *TestSession { - if deviations.ExplicitInterfaceInDefaultVRF(s.DUT) { - addISISOC(s.DUTConf, DUTAreaAddress, DUTSysID, s.DUTPort1.Name()+".0", s.DUT) - } else { - addISISOC(s.DUTConf, DUTAreaAddress, DUTSysID, s.DUTPort1.Name(), s.DUT) - } - if s.ATE != nil { - addISISTopo(s.ATEIntf1, ATEAreaAddress, "*") - } - return s -} - -// ConfigISIS takes two functions, one that operates on an OC IS-IS block and -// one that operates on an ondatra ATE IS-IS block. The first will be applied -// to the IS-IS block of ts.DUTConfig, and the second will be applied to the -// IS-IS configuration of ts.ATETop -func (s *TestSession) ConfigISIS(ocFn func(*oc.NetworkInstance_Protocol_Isis), ateFn func(*ixnet.ISIS)) { - ocFn(s.DUTConf.GetOrCreateNetworkInstance(deviations.DefaultNetworkInstance(s.DUT)).GetOrCreateProtocol(PTISIS, ISISName).GetOrCreateIsis()) - if s.ATE != nil { - ateFn(s.ATEIntf1.ISIS()) - } -} - -// PushAndStart calls PushDUT and PushAndStartATE to send config to both -// devices. -func (s *TestSession) PushAndStart(t testing.TB) error { - t.Helper() - if err := s.PushDUT(context.Background(), t); err != nil { - return err - } - s.PushAndStartATE(t) - return nil -} - -// PushDUT replaces DUT config with s.dutConf. Only interfaces and the ISIS -// protocol are written. -func (s *TestSession) PushDUT(ctx context.Context, t testing.TB) error { - // Push the interfaces - for name, conf := range s.DUTConf.Interface { - _, err := ygnmi.Replace(ctx, s.DUTClient, ocpath.Root().Interface(name).Config(), conf) - if err != nil { - return fmt.Errorf("configuring interface %s: %w", name, err) - } - } - if deviations.ExplicitInterfaceInDefaultVRF(s.DUT) { - fptest.AssignToNetworkInstance(t, s.DUT, s.DUTPort1.Name(), deviations.DefaultNetworkInstance(s.DUT), 0) - fptest.AssignToNetworkInstance(t, s.DUT, s.DUTPort2.Name(), deviations.DefaultNetworkInstance(s.DUT), 0) - } - if deviations.ExplicitPortSpeed(s.DUT) { - fptest.SetPortSpeed(t, s.DUTPort1) - fptest.SetPortSpeed(t, s.DUTPort2) - } - - // Push the ISIS protocol - if _, err := ygnmi.Update(ctx, s.DUTClient, ocpath.Root().NetworkInstance(deviations.DefaultNetworkInstance(s.DUT)).Config(), &oc.NetworkInstance{ - Name: ygot.String(deviations.DefaultNetworkInstance(s.DUT)), - Type: oc.NetworkInstanceTypes_NETWORK_INSTANCE_TYPE_DEFAULT_INSTANCE, - }); err != nil { - return fmt.Errorf("configuring network instance: %w", err) - } - dutConf := s.DUTConf.GetOrCreateNetworkInstance(deviations.DefaultNetworkInstance(s.DUT)).GetOrCreateProtocol(PTISIS, ISISName) - _, err := ygnmi.Replace(ctx, s.DUTClient, ProtocolPath(s.DUT).Config(), dutConf) - if err != nil { - return fmt.Errorf("configuring ISIS: %w", err) - } - return nil -} - -// PushAndStartATE pushes the ATETop to the ATE and starts protocols on it. -func (s *TestSession) PushAndStartATE(t testing.TB) { - t.Helper() - if s.ATE == nil { - t.Fatal("Cannot run test without ATE") - } - s.ATETop.Push(t).StartProtocols(t) -} - -// AwaitAdjacency waits up to a minute for the dut to report that the ISISIntf -// link has formed any IS-IS adjacency, returning the adjacency ID or an error -// if one doesn't form. -func (s *TestSession) AwaitAdjacency() (string, error) { - intf := ISISPath(s.DUT).Interface(s.DUTPort1.Name()) - if deviations.ExplicitInterfaceInDefaultVRF(s.DUT) { - intf = ISISPath(s.DUT).Interface(s.DUTPort1.Name() + ".0") - } - query := intf.LevelAny().AdjacencyAny().AdjacencyState().State() - ctx, cancel := context.WithTimeout(context.Background(), time.Minute) - defer cancel() - watcher := ygnmi.WatchAll(ctx, s.DUTClient, query, func(val *ygnmi.Value[oc.E_Isis_IsisInterfaceAdjState]) error { - if val == nil || !val.IsPresent() { - return ygnmi.Continue - } - v, _ := val.Val() - if v == oc.Isis_IsisInterfaceAdjState_UP { - return nil - } - return ygnmi.Continue - }) - - got, err := watcher.Await() - if err != nil { - return "", err - } - return got.Path.GetElem()[10].GetKey()["system-id"], nil -} - -// MustAdjacency waits up to a minute for an IS-IS adjacency to form between -// the DUT and the ATE; it returns the adjacency ID or calls t.Fatal no -// adjacency forms. -func (s *TestSession) MustAdjacency(t testing.TB) string { - adjID, err := s.AwaitAdjacency() - if err != nil { - t.Fatalf("Waiting for adjacency to form: %v", err) - } - return adjID -} - -// MustATEInterface returns the ATE interface for the portID, or calls t.Fatal -// if this fails. -func (s *TestSession) MustATEInterface(t testing.TB, portID string) *ondatra.Interface { - if s.ATE == nil { - t.Fatal("Cannot run test without ATE") - } - iface, ok := s.ATETop.Interfaces()[portID] - if !ok { - t.Fatalf("No ATE interface with ID %v", portID) - } - return iface -} diff --git a/feature/experimental/isis/otg_tests/base_adjacencies_test/README.md b/feature/experimental/isis/otg_tests/base_adjacencies_test/README.md deleted file mode 100644 index 3448bd66fb8..00000000000 --- a/feature/experimental/isis/otg_tests/base_adjacencies_test/README.md +++ /dev/null @@ -1,167 +0,0 @@ -# RT-2.1: Base IS-IS Process and Adjacencies - -## Summary - -Base IS-IS functionality and adjacency establishment. - -## Procedure - -* Basic fields test - * Configure DUT:port1 for an IS-IS session with ATE:port1. - * Read back the configuration to ensure that all fields are readable and - have been set properly (or correctly have their default value). - * Check that all relevant counters are readable and are 0 since the - adjacency has not yet been established. - * Push ATE configuration for the other end of the adjacency, and wait for - the adjacency to form. - * Check that the various state fields of the adjacency are reported - correctly. - * Check that error counters are still 0 and that packet counters have all - increased. -* Hello padding test - * Configure IS-IS between DUT:port1 and ATE:port1 for each possible value - of hello padding (DISABLED, STRICT, etc.) - * Confirm in each case that that adjacency forms and the correct values - are reported back by the device. -* Authentication test - * Configure IS-IS between DUT:port1 and ATE:port1 With authentication - disabled, then enabled in TEXT mode, then enabled in MD5 mode. - * Confirm in each case that that adjacency forms and the correct values - are reported back by the device. -* Routing test -* With ISIS level authentication enabled and hello authentication enabled: - * Ensure that IPv4 and IPv6 prefixes that are advertised as attached - prefixes within each LSP are correctly installed into the DUT - routing table, by ensuring that packets are received to the attached - prefix when forwarded from ATE port-1. - * Ensure that IPv4 and IPv6 prefixes that are advertised as part of an - (emulated) neighboring system are installed into the DUT routing - table, and validate that packets are sent and received to them. - * With a known LSP content, ensure that the telemetry received from the - device for the LSP matches the expected content. - -## Config Parameter coverage - -* For prefix: - - * /network-instances/network-instance/protocols/protocol/isis/ - -* Parameters: - - * TODO: global/config/authentication-check - * global/config/net - * global/config/level-capability - * global/config/hello-padding - * global/afi-safi/af/config/enabled - * levels/level/config/level-number - * levels/level/config/enabled - * levels/level/authentication/config/enabled - * levels/level/authentication/config/auth-mode - levels/level/authentication/config/auth-password - * levels/level/authentication/config/auth-type - * interfaces/interface/config/interface-id - * interfaces/interface/config/enabled - * interfaces/interface/config/circuit-type - * interfaces/interface/timers/config/csnp-interval - * interfaces/interface/timers/config/lsp-pacing-interval - * interfaces/interface/levels/level/config/level-number - * interfaces/interface/levels/level/timers/config/hello-interval - * interfaces/interface/levels/level/timers/config/hello-multiplier - * interfaces/interface/levels/level/hello-authentication/config/auth-mode - * network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/hello-authentication/config/auth-password - * interfaces/interface/levels/level/hello-authentication/config/auth-type - * interfaces/interface/levels/level/hello-authentication/config/enabled - * interfaces/interface/afi-safi/af/config/afi-name - * interfaces/interface/afi-safi/af/config/safi-name - * interfaces/interface/afi-safi/af/config/metric - * interfaces/interface/afi-safi/af/config/enabled - -## Telemetry Parameter coverage - -* For prefix: - - * /network-instances/network-instance/protocols/protocol/isis/ - -* Parameters: - - * interfaces/interface/levels/level/adjacencies/adjacency/state/adjacency-state - * interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-ipv4-address - * interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-ipv6-address - * interfaces/interface/levels/level/adjacencies/adjacency/state/system-id - * interfaces/interface/levels/level/afi-safi/af/state/afi-name - * interfaces/interface/levels/level/afi-safi/af/state/metric - * interfaces/interface/levels/level/afi-safi/af/state/safi-name - * interfaces/interface/levels/level/afi-safis/afi-safi/state/metric - * interfaces/interface/levels/level/packet-counters/cnsp/dropped - * interfaces/interface/levels/level/packet-counters/cnsp/processed - * interfaces/interface/levels/level/packet-counters/cnsp/received - * interfaces/interface/levels/level/packet-counters/cnsp/sent - * interfaces/interface/levels/level/packet-counters/iih/dropped - * interfaces/interface/levels/level/packet-counters/iih/processed - * interfaces/interface/levels/level/packet-counters/iih/received - * interfaces/interface/levels/level/packet-counters/iih/retransmit - * interfaces/interface/levels/level/packet-counters/iih/sent - * interfaces/interface/levels/level/packet-counters/lsp/dropped - * interfaces/interface/levels/level/packet-counters/lsp/processed - * interfaces/interface/levels/level/packet-counters/lsp/received - * interfaces/interface/levels/level/packet-counters/lsp/retransmit - * interfaces/interface/levels/level/packet-counters/lsp/sent - * interfaces/interface/levels/level/packet-counters/psnp/dropped - * interfaces/interface/levels/level/packet-counters/psnp/processed - * interfaces/interface/levels/level/packet-counters/psnp/received - * interfaces/interface/levels/level/packet-counters/psnp/retransmit - * interfaces/interface/levels/level/packet-counters/psnp/sent - * interfaces/interfaces/circuit-counters/state/adj-changes - * interfaces/interfaces/circuit-counters/state/adj-number - * interfaces/interfaces/circuit-counters/state/auth-fails - * interfaces/interfaces/circuit-counters/state/auth-type-fails - * interfaces/interfaces/circuit-counters/state/id-field-len-mismatches - * interfaces/interfaces/circuit-counters/state/lan-dis-changes - * interfaces/interfaces/circuit-counters/state/max-area-address-mismatch - * interfaces/interfaces/circuit-counters/state/rejected-adj - * interfaces/interfaces/levels/level/adjacencies/adjacency/state/adjacency-state - * interfaces/interfaces/levels/level/adjacencies/adjacency/state/area-address - * interfaces/interfaces/levels/level/adjacencies/adjacency/state/dis-system-id - * interfaces/interfaces/levels/level/adjacencies/adjacency/state/local-extended-system-id - * interfaces/interfaces/levels/level/adjacencies/adjacency/state/multi-topology - * interfaces/interfaces/levels/level/adjacencies/adjacency/state/neighbor-circuit-type - * interfaces/interfaces/levels/level/adjacencies/adjacency/state/neighbor-extended-system-id - * interfaces/interfaces/levels/level/adjacencies/adjacency/state/neighbor-ipv4-address - * interfaces/interfaces/levels/level/adjacencies/adjacency/state/neighbor-ipv6-address - * interfaces/interfaces/levels/level/adjacencies/adjacency/state/neighbor-snpa - * interfaces/interfaces/levels/level/adjacencies/adjacency/state/nlpid - * interfaces/interfaces/levels/level/adjacencies/adjacency/state/priority - * interfaces/interfaces/levels/level/adjacencies/adjacency/state/remaining-hold-time - * interfaces/interfaces/levels/level/adjacencies/adjacency/state/restart-status - * interfaces/interfaces/levels/level/adjacencies/adjacency/state/restart-support - * interfaces/interfaces/levels/level/adjacencies/adjacency/state/restart-suppress - * levels/level/system-level-counters/state/auth-fails - * levels/level/system-level-counters/state/auth-type-fails - * levels/level/system-level-counters/state/corrupted-lsps - * levels/level/system-level-counters/state/database-overloads - * levels/level/system-level-counters/state/exceeded-max-seq-nums - * levels/level/system-level-counters/state/id-len-mismatch - * levels/level/system-level-counters/state/lsp-errors - * levels/level/system-level-counters/state/max-area-address-mismatches - * levels/level/system-level-counters/state/own-lsp-purges - * levels/level/system-level-counters/state/seq-num-skips - * levels/level/system-level-counters/state/spf-runs - -* For LSDB - subpaths of - - * /network-instances/network-instance/protocols/protocol/isis/levels/level/link-state-database/... - -## Protocol/RPC Parameter coverage - -* IS-IS: - * LSP messages - * TLV 1 (Area Addresses) - * TLV 10 (Authentication) - * TLV 22 (Extended IS reach) - * TLV 135 (Extended IP Reachability) - * TLV 137 (Dynamic Name) - * TLV 232 (IPv6 Reachability) - -## Minimum DUT platform requirement - -vRX diff --git a/feature/experimental/isis/otg_tests/isis_interface_hello_padding_enable_test/README.md b/feature/experimental/isis/otg_tests/isis_interface_hello_padding_enable_test/README.md deleted file mode 100644 index 0a0d6fe16b1..00000000000 --- a/feature/experimental/isis/otg_tests/isis_interface_hello_padding_enable_test/README.md +++ /dev/null @@ -1,99 +0,0 @@ -# RT-2.6: IS-IS Hello-Padding enabled at interface level - -## Summary - -* Base IS-IS functionality and adjacency establishment. -* Verifies isis adjacency by changing MTU. - -## Procedure - -* Configure IS-IS for ATE port-1 and DUT port-1. -* Configure DUT with global hello-padding enabled. -* Ensure that adjacencies are established with: - * Interface level hello padding is enabled. - * Verify that IPv4 and IPv6 IS-ISIS adjacency comes up fine. - * Verify the output of ST path displaying the status of ISIS hello padding. - * If we change the MTU on either side, then adjacency should not come up. - * Verify that IPv4 and IPv6 prefixes that are advertised by ATE correctly installed into DUTs route and forwarding table. - * TODO-Verify the Hellos are sent with Padding during adjacency turn-up if the padding is enabled adaptively/sometimes. - * Ensure that IPv4 and IPv6 prefixes that are advertised as part of an (emulated) neighboring system are installed into the DUT routing table, and validate that packets are sent and received to them. - -## Config Parameter coverage - -* For prefix: - - * /network-instances/network-instance/protocols/protocol/isis/ - -* Parameters: - - * global/config/authentication-check - * global/config/net - * global/config/level-capability - * global/config/hello-padding - * global/afi-safi/af/config/enabled - * levels/level/config/level-number - * levels/level/config/enabled - * levels/level/authentication/config/enabled - * levels/level/authentication/config/auth-mode - * levels/level/authentication/config/auth-password - * levels/level/authentication/config/auth-type - * interfaces/interface/config/interface-id - * interfaces/interface/config/enabled - * interfaces/interface/config/circuit-type - * interfaces/interface/timers/config/csnp-interval - * interfaces/interface/timers/config/lsp-pacing-interval - * interfaces/interface/levels/level/config/level-number - * interfaces/interface/levels/level/timers/config/hello-interval - * interfaces/interface/levels/level/timers/config/hello-multiplier - * interfaces/interface/levels/level/hello-authentication/config/auth-mode - * interfaces/interface/levels/level/hello-authentication/config/auth-password - * interfaces/interface/levels/level/hello-authentication/config/auth-type - * interfaces/interface/levels/level/hello-authentication/config/enabled - * interfaces/interface/afi-safi/af/config/afi-name - * interfaces/interface/afi-safi/af/config/safi-name - * interfaces/interface/afi-safi/af/config/metric - * interfaces/interface/afi-safi/af/config/enabled - -## Telemetry Parameter coverage - -* For prefix: - - * /network-instances/network-instance/protocols/protocol/isis/ - -* Parameters: - - * global/state/hello-padding - * interfaces/interface/state/hello-padding - * interfaces/interface/levels/level/adjacencies/adjacency/state/adjacency-state - * interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-ipv4-address - * interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-ipv6-address - * interfaces/interface/levels/level/adjacencies/adjacency/state/system-id - * interfaces/interface/levels/level/adjacencies/adjacency/state/area-address - * interfaces/interface/levels/level/adjacencies/adjacency/state/dis-system-id - * interfaces/interface/levels/level/adjacencies/adjacency/state/local-extended-circuit-id - * interfaces/interface/levels/level/adjacencies/adjacency/state/multi-topology - * interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-circuit-type - * interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-extended-circuit-id - * interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-snpa - * interfaces/interface/levels/level/adjacencies/adjacency/state/nlpid - * interfaces/interface/levels/level/adjacencies/adjacency/state/priority - * interfaces/interface/levels/level/adjacencies/adjacency/state/restart-status - * interfaces/interface/levels/level/adjacencies/adjacency/state/restart-support - * interfaces/interface/levels/level/adjacencies/adjacency/state/restart-suppress - * interfaces/interface/levels/level/afi-safi/af/state/afi-name - * interfaces/interface/levels/level/afi-safi/af/state/metric - * interfaces/interface/levels/level/afi-safi/af/state/safi-name - * interfaces/interface/levels/level/afi-safi/af/state/metric - * levels/level/system-level-counters/state/auth-fails - * levels/level/system-level-counters/state/auth-type-fails - * levels/level/system-level-counters/state/corrupted-lsps - * levels/level/system-level-counters/state/database-overloads - * levels/level/system-level-counters/state/exceed-max-seq-nums - * levels/level/system-level-counters/state/id-len-mismatch - * levels/level/system-level-counters/state/lsp-errors - * levels/level/system-level-counters/state/manual-address-drop-from-area - * levels/level/system-level-counters/state/max-area-address-mismatches - * levels/level/system-level-counters/state/own-lsp-purges - * levels/level/system-level-counters/state/part-changes - * levels/level/system-level-counters/state/seq-num-skips - * levels/level/system-level-counters/state/spf-runs diff --git a/feature/experimental/isis/otg_tests/isis_interface_level_passive_test/README.md b/feature/experimental/isis/otg_tests/isis_interface_level_passive_test/README.md deleted file mode 100644 index 6e80f5f2985..00000000000 --- a/feature/experimental/isis/otg_tests/isis_interface_level_passive_test/README.md +++ /dev/null @@ -1,102 +0,0 @@ -# RT-2.11: IS-IS Passive is enabled at the area level - -## Summary - -* Verify isis adjacency with passive enabled under level. - -## Topology - -* ATE:port1 <-> port1:DUT:port2 <-> ATE:port2 - -## Procedure - -* Configure IS-IS for ATE port-1 and DUT port-1. -* Configure DUT interface with IS-IS passive configured at area level 2. - * Verify that IS-IS adjacency is not coming up in level-2 area for IPv4 and IPV6 address families. -* Undo the IS-IS passive configuration under level 2 - * Verify that IS-IS adjacency for IPv4 and IPV6 address families are coming up in the level-2 area. - * Verify that IPv4 and IPv6 prefixes that are advertised by ATE are correctly installed into DUTs route and forwarding table. - * Ensure that IPv4 and IPv6 prefixes that are advertised as part of an (emulated) neighboring system are installed into the DUT routing table, and validate that packets are sent and received to them. - * TODO-Verify the output of ST path displaying the interface as passive in ISIS database/adj table - -## Config Parameter coverage - -* For prefix: - - * /network-instances/network-instance/protocols/protocol/isis/ - -* Parameters: - - * global/config/authentication-check - * global/config/net - * global/config/level-capability - * global/config/hello-padding - * global/afi-safi/af/config/enabled - * levels/level/config/level-number - * levels/level/config/enabled - * levels/level/authentication/config/enabled - * levels/level/authentication/config/auth-mode - * levels/level/authentication/config/auth-password - * levels/level/authentication/config/auth-type - * interfaces/interface/config/interface-id - * interfaces/interface/config/enabled - * interfaces/interface/config/circuit-type - * interfaces/interface/config/passive - * interfaces/interface/timers/config/csnp-interval - * interfaces/interface/timers/config/lsp-pacing-interval - * interfaces/interface/levels/level/config/level-number - * interfaces/interface/levels/level/config/passive - * interfaces/interface/levels/level/timers/config/hello-interval - * interfaces/interface/levels/level/timers/config/hello-multiplier - * interfaces/interface/levels/level/hello-authentication/config/auth-mode - * interfaces/interface/levels/level/hello-authentication/config/auth-password - * interfaces/interface/levels/level/hello-authentication/config/auth-type - * interfaces/interface/levels/level/hello-authentication/config/enabled - * interfaces/interface/afi-safi/af/config/afi-name - * interfaces/interface/afi-safi/af/config/safi-name - * interfaces/interface/afi-safi/af/config/metric - * interfaces/interface/afi-safi/af/config/enabled - -## Telemetry Parameter coverage - -* For prefix: - - * /network-instances/network-instance/protocols/protocol/isis/ - -* Parameters: - - * interfaces/interface/state/passive - * interfaces/interface/levels/level/state/passive - * interfaces/interface/levels/level/adjacencies/adjacency/state/adjacency-state - * interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-ipv4-address - * interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-ipv6-address - * interfaces/interface/levels/level/adjacencies/adjacency/state/system-id - * interfaces/interface/levels/level/adjacencies/adjacency/state/area-address - * interfaces/interface/levels/level/adjacencies/adjacency/state/dis-system-id - * interfaces/interface/levels/level/adjacencies/adjacency/state/local-extended-circuit-id - * interfaces/interface/levels/level/adjacencies/adjacency/state/multi-topology - * interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-circuit-type - * interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-extended-circuit-id - * interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-snpa - * interfaces/interface/levels/level/adjacencies/adjacency/state/nlpid - * interfaces/interface/levels/level/adjacencies/adjacency/state/priority - * interfaces/interface/levels/level/adjacencies/adjacency/state/restart-status - * interfaces/interface/levels/level/adjacencies/adjacency/state/restart-support - * interfaces/interface/levels/level/adjacencies/adjacency/state/restart-suppress - * interfaces/interface/levels/level/afi-safi/af/state/afi-name - * interfaces/interface/levels/level/afi-safi/af/state/metric - * interfaces/interface/levels/level/afi-safi/af/state/safi-name - * interfaces/interface/levels/level/afi-safi/af/state/metric - * levels/level/system-level-counters/state/auth-fails - * levels/level/system-level-counters/state/auth-type-fails - * levels/level/system-level-counters/state/corrupted-lsps - * levels/level/system-level-counters/state/database-overloads - * levels/level/system-level-counters/state/exceed-max-seq-nums - * levels/level/system-level-counters/state/id-len-mismatch - * levels/level/system-level-counters/state/lsp-errors - * levels/level/system-level-counters/state/manual-address-drop-from-area - * levels/level/system-level-counters/state/max-area-address-mismatches - * levels/level/system-level-counters/state/own-lsp-purges - * levels/level/system-level-counters/state/part-changes - * levels/level/system-level-counters/state/seq-num-skips - * levels/level/system-level-counters/state/spf-runs diff --git a/feature/experimental/isis/otg_tests/isis_metric_style_wide_not_enabled_test/README.md b/feature/experimental/isis/otg_tests/isis_metric_style_wide_not_enabled_test/README.md deleted file mode 100644 index 4347c71375c..00000000000 --- a/feature/experimental/isis/otg_tests/isis_metric_style_wide_not_enabled_test/README.md +++ /dev/null @@ -1,101 +0,0 @@ -# RT-2.8: IS-IS metric style wide not enabled - -## Summary - -* Base IS-IS functionality and adjacency establishment. -* Verifies route metric with wide metric disabled on DUT. - -## Procedure - -* TestISISWideMetricNotEnabled - - * Configure IS-IS for ATE port-1 and DUT port-1. - * Do not configure metric style wide under the area level. - * Enable wide metric style on ATE. - * Advertise ISIS prefixes from ATE with wide metrics (value > 63). - * Verify that IS-IS adjacency for IPv4 and IPV6 address family is coming up. - * Verify that IPv4 and IPv6 prefixes that are advertised by ATE correctly installed into DUTs route and forwarding table. - * TODO-Verify that the metrics of the IPv4 and IPv6 prefixes is 63. - * Ensure that IPv4 and IPv6 prefixes that are advertised as part of an (emulated) neighboring system are installed into the DUT routing table, and validate that packets are sent and received to them. - - -## Config Parameter coverage - -* For prefix: - - * /network-instances/network-instance/protocols/protocol/isis/ - -* Parameters: - - * global/config/authentication-check - * global/config/net - * global/config/level-capability - * global/config/hello-padding - * global/afi-safi/af/config/enabled - * levels/level/config/level-number - * levels/level/config/enabled - * levels/level/config/metric-style - * levels/level/authentication/config/enabled - * levels/level/authentication/config/auth-mode - * levels/level/authentication/config/auth-password - * levels/level/authentication/config/auth-type - * interfaces/interface/config/interface-id - * interfaces/interface/config/enabled - * interfaces/interface/config/circuit-type - * interfaces/interface/config/passive - * interfaces/interface/timers/config/csnp-interval - * interfaces/interface/timers/config/lsp-pacing-interval - * interfaces/interface/levels/level/config/level-number - * interfaces/interface/levels/level/config/passive - * interfaces/interface/levels/level/timers/config/hello-interval - * interfaces/interface/levels/level/timers/config/hello-multiplier - * interfaces/interface/levels/level/hello-authentication/config/auth-mode - * interfaces/interface/levels/level/hello-authentication/config/auth-password - * interfaces/interface/levels/level/hello-authentication/config/auth-type - * interfaces/interface/levels/level/hello-authentication/config/enabled - * interfaces/interface/afi-safi/af/config/afi-name - * interfaces/interface/afi-safi/af/config/safi-name - * interfaces/interface/afi-safi/af/config/enabled - -## Telemetry Parameter coverage - -* For prefix: - - * /network-instances/network-instance/protocols/protocol/isis/ - -* Parameters: - - * levels/level/state/metric-style - * interfaces/interface/levels/level/adjacencies/adjacency/state/adjacency-state - * interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-ipv4-address - * interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-ipv6-address - * interfaces/interface/levels/level/adjacencies/adjacency/state/system-id - * interfaces/interface/levels/level/adjacencies/adjacency/state/area-address - * interfaces/interface/levels/level/adjacencies/adjacency/state/dis-system-id - * interfaces/interface/levels/level/adjacencies/adjacency/state/local-extended-circuit-id - * interfaces/interface/levels/level/adjacencies/adjacency/state/multi-topology - * interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-circuit-type - * interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-extended-circuit-id - * interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-snpa - * interfaces/interface/levels/level/adjacencies/adjacency/state/nlpid - * interfaces/interface/levels/level/adjacencies/adjacency/state/priority - * interfaces/interface/levels/level/adjacencies/adjacency/state/restart-status - * interfaces/interface/levels/level/adjacencies/adjacency/state/restart-support - * interfaces/interface/levels/level/adjacencies/adjacency/state/restart-suppress - * interfaces/interface/levels/level/afi-safi/af/state/afi-name - * interfaces/interface/levels/level/afi-safi/af/state/metric - * interfaces/interface/levels/level/afi-safi/af/state/safi-name - * interfaces/interface/levels/level/afi-safi/af/state/metric - * levels/level/system-level-counters/state/auth-fails - * levels/level/system-level-counters/state/auth-type-fails - * levels/level/system-level-counters/state/corrupted-lsps - * levels/level/system-level-counters/state/database-overloads - * levels/level/system-level-counters/state/exceed-max-seq-nums - * levels/level/system-level-counters/state/id-len-mismatch - * levels/level/system-level-counters/state/lsp-errors - * levels/level/system-level-counters/state/manual-address-drop-from-area - * levels/level/system-level-counters/state/max-area-address-mismatches - * levels/level/system-level-counters/state/own-lsp-purges - * levels/level/system-level-counters/state/part-changes - * levels/level/system-level-counters/state/seq-num-skips - * levels/level/system-level-counters/state/spf-runs diff --git a/feature/experimental/lacp_and_base_interface/aggregate_interfaces/feature.textproto b/feature/experimental/lacp_and_base_interface/aggregate_interfaces/feature.textproto deleted file mode 100644 index b9f58a8ae68..00000000000 --- a/feature/experimental/lacp_and_base_interface/aggregate_interfaces/feature.textproto +++ /dev/null @@ -1,94 +0,0 @@ -# Copyright 2022 Google LLC -# -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at -# -# https://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. -# -# proto-file: github.com/openconfig/featureprofiles/proto/feature.proto -# proto-message: FeatureProfile - -id { - name: "experimental_lacp_and_base_interface_aggregate_interfaces" - version: 1 -} - -config_path { - path: "/interfaces/interface/ethernet/config/mac-address" -} -config_path { - path: "/interfaces/interface/ethernet/config/port-speed" -} -config_path { - path: "/interfaces/interface/ethernet/config/duplex-mode" -} -config_path { - path: "/interfaces/interface/ethernet/config/aggregate-id" -} -config_path { - path: "/interfaces/interface/aggregation/config/lag-type" -} -config_path { - path: "/interfaces/interface/aggregation/config/min-links" -} -config_path { - path: "/lacp/config/system-priority" -} -config_path { - path: "/lacp/interfaces/interface/config/name" -} -config_path { - path: "/lacp/interfaces/interface/config/interval" -} -config_path { - path: "/lacp/interfaces/interface/config/lacp-mode" -} -config_path { - path: "/lacp/interfaces/interface/config/system-id-mac" -} -config_path { - path: "/lacp/interfaces/interface/config/system-priority" -} -telemetry_path { - path: "/lacp/interfaces/interface/members/member/state/counters/lacp-in-pkts" -} -telemetry_path { - path: "/lacp/interfaces/interface/members/member/state/counters/lacp-errors" -} -telemetry_path { - path: "/lacp/interfaces/interface/members/member/state/counters/lacp-timeout-transitions" -} -telemetry_path { - path: "/lacp/interfaces/interface/members/member/state/counters/lacp-tx-errors" -} -telemetry_path { - path: "/lacp/interfaces/interface/members/member/state/counters/lacp-out-pkts" -} -telemetry_path { - path: "/lacp/interfaces/interface/members/member/state/counters/lacp-rx-errors" -} -telemetry_path { - path: "/lacp/interfaces/interface/members/member/state/oper-key" -} -telemetry_path { - path: "/lacp/interfaces/interface/members/member/state/last-change" -} -telemetry_path { - path: "/lacp/interfaces/interface/members/member/state/partner-id" -} -telemetry_path { - path: "/lacp/interfaces/interface/members/member/state/system-id" -} -telemetry_path { - path: "/lacp/interfaces/interface/members/member/state/port-num" -} -telemetry_path { - path: "/lacp/interfaces/interface/state/system-priority" -} diff --git a/feature/experimental/platform/tests/breakout_configuration/README.md b/feature/experimental/platform/tests/breakout_configuration/README.md deleted file mode 100644 index d70c053e362..00000000000 --- a/feature/experimental/platform/tests/breakout_configuration/README.md +++ /dev/null @@ -1,32 +0,0 @@ -# PLT-1.1: Interface breakout Test - -## Summary - -Validate Interface breakout configuration. - -## Procedure - - -* This test is carried out for different breakout types -* Connect DUT with ATE to all interfaces in the breakout port -* Configure each interface with test IP addressing -* Verify correct interface state and speed reported -* Verify that DUT responds to ARP/ICMP on all tested interfaces - -## Config Parameter coverage - -* /components/component/port/breakout-mode/groups/group/index -* /components/component/port/breakout-mode/groups/group/config -* /components/component/port/breakout-mode/groups/group/config/index -* /components/component/port/breakout-mode/groups/group/config/num-breakouts -* /components/component/port/breakout-mode/groups/group/config/breakout-speed -* /components/component/port/breakout-mode/groups/group/config/num-physical-channels - - -## Telemetry Parameter coverage - * interfaces/interface/state - * interfaces/interface/ethernet/stateOutput power thresholds: - -## Minimum DUT Platform Requirement - -* Breakout types - 4x100G, 2x100G and 4x10G \ No newline at end of file diff --git a/feature/experimental/policy/policy_base/feature.textproto b/feature/experimental/policy/policy_base/feature.textproto deleted file mode 100644 index e0799b0980c..00000000000 --- a/feature/experimental/policy/policy_base/feature.textproto +++ /dev/null @@ -1,208 +0,0 @@ -# Copyright 2022 Google LLC -# -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at -# -# https://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. -# -# proto-file: github.com/openconfig/featureprofiles/proto/feature.proto -# proto-message: FeatureProfile - -id { - name: "experimental_policy_policy_base" - version: 1 -} - -# Policy base - -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/config/policy-id" -} -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/config/type" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/state/policy-id" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/state/type" -} - -# Rules base - -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/config/sequence-id" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/state/sequence-id" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/state/matched-pkts" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/state/matched-octets" -} - -# Action base - -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/action/config/discard" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/action/state/discard" -} - -# Interface base - -config_path { - path: "/network-instances/network-instance/policy-forwarding/interfaces/interface/config/interface-id" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/interfaces/interface/state/interface-id" -} - -# L2 rules - -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/l2/config/ethertype" -} -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/l2/config/source-mac" -} -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/l2/config/source-mac-mask" -} -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/l2/config/destination-mac" -} -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/l2/config/destination-mac-mask" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/l2/state/ethertype" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/l2/state/source-mac" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/l2/state/source-mac-mask" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/l2/state/destination-mac" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/l2/state/destination-mac-mask" -} - -# IPv4 rules - -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv4/config/source-address" -} -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv4/config/destination-address" -} -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv4/config/dscp" -} -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv4/config/dscp-set" -} -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv4/config/protocol" -} -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv4/config/hop-limit" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv4/state/source-address" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv4/state/destination-address" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv4/state/dscp" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv4/state/dscp-set" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv4/state/protocol" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv4/state/hop-limit" -} - -# IPv6 rules - -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv6/config/source-address" -} -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv6/config/source-flow-label" -} -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv6/config/destination-address" -} -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv6/config/destination-flow-label" -} -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv6/config/dscp" -} -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv6/config/dscp-set" -} -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv6/config/protocol" -} -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv6/config/hop-limit" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv6/state/source-address" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv6/state/source-flow-label" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv6/state/destination-address" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv6/state/destination-flow-label" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv6/state/dscp" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv6/state/dscp-set" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv6/state/protocol" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv6/state/hop-limit" -} - -# Transport rules - -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/transport/config/source-port" -} -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/transport/config/destination-port" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/transport/state/source-port" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/transport/state/destination-port" -} - diff --git a/feature/experimental/policy/policy_vrf_selection/feature.textproto b/feature/experimental/policy/policy_vrf_selection/feature.textproto deleted file mode 100644 index a5262ef5612..00000000000 --- a/feature/experimental/policy/policy_vrf_selection/feature.textproto +++ /dev/null @@ -1,45 +0,0 @@ -# Copyright 2022 Google LLC -# -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at -# -# https://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. -# -# proto-file: github.com/openconfig/featureprofiles/proto/feature.proto -# proto-message: FeatureProfile - -id { - name: "experimental_policy_policy_vrf_selection" - version: 1 -} - -# Interface - -config_path { - path: "/network-instances/network-instance/policy-forwarding/interfaces/interface/config/apply-vrf-selection-policy" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/interfaces/interface/state/apply-vrf-selection-policy" -} - -# VRF actions - -config_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/action/config/network-instance" -} -telemetry_path { - path: "/network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/action/state/network-instance" -} - - -feature_profile_dependency { - name: "bgp_policybase" - version: 1 -} diff --git a/feature/experimental/replay/tests/presession_test/README.md b/feature/experimental/replay/tests/presession_test/README.md deleted file mode 100644 index 2fcd2fc461d..00000000000 --- a/feature/experimental/replay/tests/presession_test/README.md +++ /dev/null @@ -1,6 +0,0 @@ -# Replay-1.0: Record/replay presession test - -## Summary - -This is an example record/replay test. -At this time, no vendor is expected to run this test. diff --git a/feature/experimental/route_redistribution/feature.textproto b/feature/experimental/route_redistribution/feature.textproto deleted file mode 100644 index fa276b3ca6b..00000000000 --- a/feature/experimental/route_redistribution/feature.textproto +++ /dev/null @@ -1,86 +0,0 @@ -# Copyright 2022 Google LLC -# -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at -# -# https://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. -# -# proto-file: github.com/openconfig/featureprofiles/proto/feature.proto -# proto-message: FeatureProfile - -id { - name: "experimental_route_redistribution" - version: 1 -} - -# https://github.com/openconfig/public/blob/e9e3a82693d1f26c61d7fbf85b3b2d0418d4af9e/doc/network_instance_redistribution.md -# Protocol tables -config_path { - path: "/network-instances/network-instance/tables/table/config/protocol" -} -config_path { - path: "/network-instances/network-instance/tables/table/config/address-family" -} -telemetry_path { - path: "/network-instances/network-instance/tables/table/state/protocol" -} -telemetry_path { - path: "/network-instances/network-instance/tables/table/state/address-family" -} - - -# Table-connections -config_path { - path: "/network-instances/network-instance/table-connections/table-connection/config/src-protocol" -} -config_path { - path: "/network-instances/network-instance/table-connections/table-connection/config/dst-protocol" -} -config_path { - path: "/network-instances/network-instance/table-connections/table-connection/config/address-family" -} -config_path { - path: "/network-instances/network-instance/table-connections/table-connection/config/import-policy" -} -config_path { - path: "/network-instances/network-instance/table-connections/table-connection/config/default-import-policy" -} -telemetry_path { - path: "/network-instances/network-instance/table-connections/table-connection/state/src-protocol" -} -telemetry_path { - path: "/network-instances/network-instance/table-connections/table-connection/state/dst-protocol" -} -telemetry_path { - path: "/network-instances/network-instance/table-connections/table-connection/state/address-family" -} -telemetry_path { - path: "/network-instances/network-instance/table-connections/table-connection/state/import-policy" -} -telemetry_path { - path: "/network-instances/network-instance/table-connections/table-connection/state/default-import-policy" -} - - - -feature_profile_dependency { - name: "bgp" - version: 1 -} - -feature_profile_dependency { - name: "localaggregates" - version: 1 -} - -feature_profile_dependency { - name: "bgp_policybase" - version: 1 -} diff --git a/feature/experimental/telemetry_only/feature.textproto b/feature/experimental/telemetry_only/feature.textproto deleted file mode 100644 index 829203c9478..00000000000 --- a/feature/experimental/telemetry_only/feature.textproto +++ /dev/null @@ -1,459 +0,0 @@ -# Copyright 2022 Google LLC -# -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at -# -# https://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. -# -# proto-file: github.com/openconfig/featureprofiles/proto/feature.proto -# proto-message: FeatureProfile - -id { - name: "experimental_telemetry_only" - version: 1 -} - -# Fan -telemetry_path { - path: "/components/component/fan/state/speed" -} - -# Pipeline-counters lookup block -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/lookup-block/state/nexthop-memory" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/lookup-block/state/nexthop-memory-used" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/lookup-block/state/acl-memory-total-entries" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/lookup-block/state/acl-memory-used-entries" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/lookup-block/state/acl-memory-total-bytes" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/lookup-block/state/acl-memory-used-bytes" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/lookup-block/state/lookup-memory" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/lookup-block/state/lookup-memory-used" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/drop/lookup-block/state/oversubscription" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/drop/lookup-block/state/no-route" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/drop/lookup-block/state/no-label" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/drop/lookup-block/state/no-nexthop" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/drop/lookup-block/state/invalid-packet" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/drop/lookup-block/state/forwarding-policy" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/drop/lookup-block/state/incorrect-software-state" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/drop/lookup-block/state/rate-limit" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/drop/lookup-block/state/fragment-total-drops" -} - -# Pipeline counters queueing block -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/queueing-block/state/in-bytes" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/queueing-block/state/out-bytes" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/queueing-block/state/queue-memory" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/queueing-block/state/queue-memory-used" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/queueing-block/state/loopback-packets" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/queueing-block/state/loopback-bytes" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/drop/queueing-block/state/oversubscription" -} - -# Pipeline counters fabric block -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/fabric-block/state/in-bytes" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/fabric-block/state/out-bytes" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/fabric-block/state/in-packets" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/fabric-block/state/out-packets" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/fabric-block/state/in-low-priority-cells" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/fabric-block/state/out-low-priority-cells" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/fabric-block/state/in-high-priority-packets" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/fabric-block/state/out-high-priority-packets" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/fabric-block/state/in-low-priority-packets" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/fabric-block/state/out-low-priority-packets" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/drop/fabric-block/state/oversubscription" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/drop/fabric-block/state/lost-packets" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/drop/fabric-block/state/out-high-priority" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/drop/fabric-block/state/fabric-aggregate" -} - -# Pipeline counters host interface block -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/host-interface-block/state/out-packets" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/host-interface-block/state/in-bytes" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/host-interface-block/state/out-bytes" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/host-interface-block/state/fragment-punt-pkts" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/host-interface-block/state/in-high-priority-packets" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/host-interface-block/state/out-high-priority-packets" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/host-interface-block/state/in-low-priority-packets" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/packet/host-interface-block/state/out-low-priority-packets" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/drop/host-interface-block/state/oversubscription" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/drop/host-interface-block/state/rate-limit" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/drop/host-interface-block/state/in-high-priority" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/drop/host-interface-block/state/out-high-priority" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/drop/host-interface-block/state/in-low-priority" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/drop/host-interface-block/state/out-low-priority" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/drop/host-interface-block/state/fragment-punt" -} -telemetry_path { - path: "/components/component/integrated-circuit/pipeline-counters/drop/host-interface-block/state/host-aggregate" -} - - -# Port -telemetry_path { - path: "/components/component/port/breakout-mode/groups/group/state/breakout-speed" -} -telemetry_path { - path: "/components/component/port/breakout-mode/groups/group/state/index" -} -telemetry_path { - path: "/components/component/port/breakout-mode/groups/group/state/num-breakouts" -} -telemetry_path { - path: "/components/component/port/breakout-mode/groups/group/state/num-physical-channels" -} -config_path { - path: "/components/component/port/breakout-mode/groups/group/config/breakout-speed" -} -config_path { - path: "/components/component/port/breakout-mode/groups/group/config/index" -} -config_path { - path: "/components/component/port/breakout-mode/groups/group/config/num-breakouts" -} -config_path { - path: "/components/component/port/breakout-mode/groups/group/config/num-physical-channels" -} - -# Power supply -telemetry_path { - path: "/components/component/power-supply/state/input-current" -} -telemetry_path { - path: "/components/component/power-supply/state/output-current" -} -telemetry_path { - path: "/components/component/power-supply/state/output-voltage" -} - -# integrated circuit backplane -telemetry_path { - path: "/components/component/integrated-circuit/backplane-facing-capacity/state/total" -} -telemetry_path { - path: "/components/component/integrated-circuit/backplane-facing-capacity/state/consumed-capacity" -} -telemetry_path { - path: "/components/component/integrated-circuit/backplane-facing-capacity/state/available-pct" -} - -telemetry_path { - path: "/components/component/properties/property/state/value" -} -telemetry_path { - path: "/components/component/subcomponents/subcomponent/state/name" -} -telemetry_path { - path: "/components/component/state/description" -} -telemetry_path { - path: "/components/component/properties/property/state/value" -} -telemetry_path { - path: "/components/component/state/parent" -} -telemetry_path { - path: "/components/component/subcomponents/subcomponent/state/name" -} -telemetry_path { - path: "/components/component/integrated-circuit/state/node-id" -} -telemetry_path { - path: "/components/component/state/empty" -} -telemetry_path { - path: "/components/component/state/firmware-version" -} -telemetry_path { - path: "/components/component/state/hardware-version" -} -telemetry_path { - path: "/components/component/state/mfg-date" -} -telemetry_path { - path: "/components/component/state/mfg-name" -} -telemetry_path { - path: "/components/component/state/name" -} -telemetry_path { - path: "/components/component/state/oper-status" -} -telemetry_path { - path: "/components/component/state/parent" -} -telemetry_path { - path: "/components/component/state/part-no" -} -telemetry_path { - path: "/components/component/state/serial-no" -} -telemetry_path { - path: "/components/component/state/software-version" -} -telemetry_path { - path: "/components/component/state/temperature/instant" -} -telemetry_path { - path: "/components/component/state/type" -} -telemetry_path { - path: "/components/component/transceiver/physical-channels/channel/state/input-power/instant" -} -telemetry_path { - path: "/components/component/transceiver/physical-channels/channel/state/laser-bias-current/instant" -} -telemetry_path { - path: "/components/component/transceiver/physical-channels/channel/state/output-power/instant" -} -telemetry_path { - path: "/components/component/transceiver/state/form-factor" -} -telemetry_path { - path: "/interfaces/interface/aggregation/state/member" -} -telemetry_path { - path: "/interfaces/interface/ethernet/state/counters/in-maxsize-exceeded" -} -telemetry_path { - path: "/interfaces/interface/hold-time/state/down" -} -telemetry_path { - path: "/interfaces/interface/hold-time/state/up" -} -telemetry_path { - path: "/interfaces/interface/state/counters/carrier-transitions" -} -telemetry_path { - path: "/interfaces/interface/state/counters/in-discards" -} -telemetry_path { - path: "/interfaces/interface/state/counters/in-fcs-errors" -} -telemetry_path { - path: "/interfaces/interface/state/counters/in-pkts" -} -telemetry_path { - path: "/interfaces/interface/state/cpu" -} -telemetry_path { - path: "/interfaces/interface/state/hardware-port" -} -telemetry_path { - path: "/interfaces/interface/state/last-change" -} -telemetry_path { - path: "/interfaces/interface/state/management" -} -telemetry_path { - path: "/interfaces/interface/state/physical-channel" -} -telemetry_path { - path: "/interfaces/interface/state/transceiver" -} -telemetry_path { - path: "/interfaces/interface/subinterfaces/subinterface/ipv4/addresses/address/state/ip" -} -telemetry_path { - path: "/interfaces/interface/subinterfaces/subinterface/ipv4/addresses/address/state/prefix-length" -} -telemetry_path { - path: "/interfaces/interface/subinterfaces/subinterface/ipv6/addresses/address/state/ip" -} -telemetry_path { - path: "/interfaces/interface/subinterfaces/subinterface/ipv6/addresses/address/state/prefix-length" -} -telemetry_path { - path: "/interfaces/interface/subinterfaces/subinterface/state/index" -} -telemetry_path { - path: "/lacp/interfaces/interface/members/member/state/activity" -} -telemetry_path { - path: "/lacp/interfaces/interface/members/member/state/collecting" -} -telemetry_path { - path: "/lacp/interfaces/interface/members/member/state/distributing" -} -telemetry_path { - path: "/lacp/interfaces/interface/state/system-id-mac" -} -telemetry_path { - path: "/qos/interfaces/interface/output/queues/queue/state/dropped-pkts" -} -telemetry_path { - path: "/qos/interfaces/interface/output/queues/queue/state/name" -} -telemetry_path { - path: "/qos/interfaces/interface/output/queues/queue/state/transmit-octets" -} -telemetry_path { - path: "/qos/interfaces/interface/output/queues/queue/state/transmit-pkts" -} -telemetry_path { - path: "/qos/interfaces/interface/output/scheduler-policy/state/name" -} -telemetry_path { - path: "/system/alarms/alarm/state/id" -} -telemetry_path { - path: "/system/alarms/alarm/state/resource" -} -telemetry_path { - path: "/system/alarms/alarm/state/severity" -} -telemetry_path { - path: "/system/alarms/alarm/state/text" -} -telemetry_path { - path: "/system/alarms/alarm/state/time-created" -} -telemetry_path { - path: "/system/alarms/alarm/state/type-id" -} -telemetry_path { - path: "/system/cpus/cpu/state/total/avg" -} -telemetry_path { - path: "/system/memory/state/counters/correctable-ecc-errors" -} -telemetry_path { - path: "/system/memory/state/counters/uncorrectable-ecc-errors" -} -telemetry_path { - path: "/system/memory/state/free" -} -telemetry_path { - path: "/system/memory/state/physical" -} -telemetry_path { - path: "/system/memory/state/used" -} -telemetry_path { - path: "/system/processes/process/state/cpu-utilization" -} -telemetry_path { - path: "/system/processes/process/state/memory-usage" -} -telemetry_path { - path: "/system/processes/process/state/name" -} -telemetry_path { - path: "/system/processes/process/state/pid" -} -telemetry_path { - path: "/system/state/hostname" -} -config_path { - path: "/components/component/config/name" -} -config_path { - path: "/components/component/integrated-circuit/config/node-id" -} diff --git a/feature/gnmi/otg_tests/telemetry_interface_packet_counters_test/metadata.textproto b/feature/gnmi/otg_tests/telemetry_interface_packet_counters_test/metadata.textproto index 693fd78a761..7eae9761928 100644 --- a/feature/gnmi/otg_tests/telemetry_interface_packet_counters_test/metadata.textproto +++ b/feature/gnmi/otg_tests/telemetry_interface_packet_counters_test/metadata.textproto @@ -13,6 +13,7 @@ platform_exceptions: { ipv4_missing_enabled: true interface_counters_from_container: true subinterface_packet_counters_missing: true + interface_counters_update_delayed: true } } platform_exceptions: { diff --git a/feature/gnmi/otg_tests/telemetry_interface_packet_counters_test/telemetry_interface_packet_counters_test.go b/feature/gnmi/otg_tests/telemetry_interface_packet_counters_test/telemetry_interface_packet_counters_test.go index cf9310999ee..9cc8591a9ab 100644 --- a/feature/gnmi/otg_tests/telemetry_interface_packet_counters_test/telemetry_interface_packet_counters_test.go +++ b/feature/gnmi/otg_tests/telemetry_interface_packet_counters_test/telemetry_interface_packet_counters_test.go @@ -244,6 +244,31 @@ func fetchInAndOutPkts(t *testing.T, dut *ondatra.DUTDevice, i1, i2 *interfaces. return inPkts, outPkts } +func waitForCountersUpdate(t *testing.T, dut *ondatra.DUTDevice, i1, i2 *interfaces.InterfacePath, + inTarget, outTarget uint64) (map[string]uint64, map[string]uint64) { + inWatcher := gnmi.Watch(t, dut, i1.Counters().InUnicastPkts().State(), time.Second*60, func(v *ygnmi.Value[uint64]) bool { + got, present := v.Val() + return present && got >= inTarget + }) + outWatcher := gnmi.Watch(t, dut, i2.Counters().OutUnicastPkts().State(), + time.Second*60, func(v *ygnmi.Value[uint64]) bool { + got, present := v.Val() + return present && got >= outTarget + }) + + inPktsV, ok := inWatcher.Await(t) + if !ok { + t.Fatalf("InPkts counter did not update in time") + } + outPktsV, ok := outWatcher.Await(t) + if !ok { + t.Fatalf("OutPkts counter did not update in time") + } + inPkts, _ := inPktsV.Val() + outPkts, _ := outPktsV.Val() + return map[string]uint64{"parent": inPkts}, map[string]uint64{"parent": outPkts} +} + func TestIntfCounterUpdate(t *testing.T) { dut := ondatra.DUT(t, "dut") dp1 := dut.Port(t, "port1") @@ -378,7 +403,14 @@ func TestIntfCounterUpdate(t *testing.T) { } } - dutInPktsAfterTraffic, dutOutPktsAfterTraffic := fetchInAndOutPkts(t, dut, i1, i2) + var dutInPktsAfterTraffic, dutOutPktsAfterTraffic map[string]uint64 + if deviations.InterfaceCountersUpdateDelayed(dut) { + dutInPktsAfterTraffic, dutOutPktsAfterTraffic = waitForCountersUpdate(t, dut, i1, i2, + dutInPktsBeforeTraffic["parent"]+ateInPkts["parent"], + dutOutPktsBeforeTraffic["parent"]+ateOutPkts["parent"]) + } else { + dutInPktsAfterTraffic, dutOutPktsAfterTraffic = fetchInAndOutPkts(t, dut, i1, i2) + } t.Logf("inPkts: %v and outPkts: %v after traffic: ", dutInPktsAfterTraffic, dutOutPktsAfterTraffic) for k := range dutInPktsAfterTraffic { diff --git a/feature/gnmi/subscribe/tests/gnmi_subscriptionlist_test/gnmi_subscriptionlist_test.go b/feature/gnmi/subscribe/tests/gnmi_subscriptionlist_test/gnmi_subscriptionlist_test.go new file mode 100644 index 00000000000..35376391d3e --- /dev/null +++ b/feature/gnmi/subscribe/tests/gnmi_subscriptionlist_test/gnmi_subscriptionlist_test.go @@ -0,0 +1,165 @@ +package gnmi_subscriptionlist_test + +import ( + "context" + "testing" + "time" + + "github.com/openconfig/featureprofiles/internal/args" + "github.com/openconfig/featureprofiles/internal/fptest" + gpb "github.com/openconfig/gnmi/proto/gnmi" + "github.com/openconfig/ondatra" + "github.com/openconfig/ondatra/gnmi" + "github.com/openconfig/ygnmi/ygnmi" +) + +const ( + syncResponseWaitTimeOut = 300 * time.Second +) + +var ( + returnChangedMode = map[gpb.SubscriptionMode]gpb.SubscriptionMode{ + gpb.SubscriptionMode_TARGET_DEFINED: gpb.SubscriptionMode_SAMPLE, + gpb.SubscriptionMode_ON_CHANGE: gpb.SubscriptionMode_TARGET_DEFINED, + } + backplaneFacingCapacityPaths = map[gpb.SubscriptionMode][]ygnmi.PathStruct{ + gpb.SubscriptionMode_ON_CHANGE: { + gnmi.OC().ComponentAny().IntegratedCircuit().BackplaneFacingCapacity().TotalOperationalCapacity().State().PathStruct(), + }, + gpb.SubscriptionMode_TARGET_DEFINED: { + gnmi.OC().ComponentAny().IntegratedCircuit().BackplaneFacingCapacity().AvailablePct().State().PathStruct(), + gnmi.OC().ComponentAny().IntegratedCircuit().BackplaneFacingCapacity().ConsumedCapacity().State().PathStruct(), + gnmi.OC().ComponentAny().IntegratedCircuit().BackplaneFacingCapacity().Total().State().PathStruct(), + }, + } + + telemetryPaths = map[gpb.SubscriptionMode][]ygnmi.PathStruct{ + gpb.SubscriptionMode_ON_CHANGE: { + gnmi.OC().InterfaceAny().AdminStatus().State().PathStruct(), + gnmi.OC().Lacp().InterfaceAny().MemberAny().Interface().State().PathStruct(), + gnmi.OC().InterfaceAny().Ethernet().MacAddress().State().PathStruct(), + gnmi.OC().InterfaceAny().HardwarePort().State().PathStruct(), + gnmi.OC().InterfaceAny().Id().State().PathStruct(), + gnmi.OC().InterfaceAny().OperStatus().State().PathStruct(), + gnmi.OC().InterfaceAny().Ethernet().PortSpeed().State().PathStruct(), + gnmi.OC().ComponentAny().IntegratedCircuit().NodeId().State().PathStruct(), + gnmi.OC().ComponentAny().Parent().State().PathStruct(), + gnmi.OC().ComponentAny().OperStatus().State().PathStruct(), + gnmi.OC().InterfaceAny().ForwardingViable().State().PathStruct(), + }, gpb.SubscriptionMode_TARGET_DEFINED: { + gnmi.OC().InterfaceAny().Counters().InUnicastPkts().State().PathStruct(), + gnmi.OC().InterfaceAny().Counters().InBroadcastPkts().State().PathStruct(), + gnmi.OC().InterfaceAny().Counters().InMulticastPkts().State().PathStruct(), + gnmi.OC().InterfaceAny().Counters().OutUnicastPkts().State().PathStruct(), + gnmi.OC().InterfaceAny().Counters().OutBroadcastPkts().State().PathStruct(), + gnmi.OC().InterfaceAny().Counters().OutMulticastPkts().State().PathStruct(), + gnmi.OC().InterfaceAny().Counters().InOctets().State().PathStruct(), + gnmi.OC().InterfaceAny().Counters().OutOctets().State().PathStruct(), + gnmi.OC().InterfaceAny().Counters().InDiscards().State().PathStruct(), + gnmi.OC().InterfaceAny().Counters().OutDiscards().State().PathStruct(), + gnmi.OC().InterfaceAny().Counters().InErrors().State().PathStruct(), + gnmi.OC().InterfaceAny().Counters().OutErrors().State().PathStruct(), + gnmi.OC().InterfaceAny().Counters().InFcsErrors().State().PathStruct(), + gnmi.OC().Qos().InterfaceAny().Output().QueueAny().TransmitOctets().State().PathStruct(), + gnmi.OC().Qos().InterfaceAny().Output().QueueAny().TransmitPkts().State().PathStruct(), + gnmi.OC().Qos().InterfaceAny().Output().QueueAny().DroppedPkts().State().PathStruct(), + }, + } +) + +func TestMain(m *testing.M) { + fptest.RunTests(m) +} + +func updateTelemetryPaths() { + if *args.NumControllerCards > 0 { + for mode, paths := range backplaneFacingCapacityPaths { + telemetryPaths[mode] = append(telemetryPaths[mode], paths...) + } + } +} + +func createSubscriptionList(t *testing.T, telemetryData map[gpb.SubscriptionMode][]ygnmi.PathStruct, changeSubscriptionModes bool) *gpb.SubscriptionList { + subscriptions := make([]*gpb.Subscription, 0) + for mode, paths := range telemetryData { + currMode := mode + if changeSubscriptionModes == true { + currMode = returnChangedMode[mode] + } + for _, path := range paths { + gnmiPath, _, err := ygnmi.ResolvePath(path) + + if err != nil { + t.Errorf("[Error]:Error in resolving gnmi path =%v", path) + } + + gnmiRequest := &gpb.Subscription{ + Path: gnmiPath, + Mode: currMode, + } + if currMode == gpb.SubscriptionMode_SAMPLE { + gnmiRequest.SampleInterval = uint64(time.Second * 10) + } + + subscriptions = append(subscriptions, gnmiRequest) + } + } + + return &gpb.SubscriptionList{ + Subscription: subscriptions, + Mode: gpb.SubscriptionList_STREAM, + } +} + +func TestSingleSubscription(t *testing.T) { + dut := ondatra.DUT(t, "dut") + ctx := context.Background() + updateTelemetryPaths() + testCases := []struct { + desc string + changeMode bool + }{ + {desc: "GNMI-2.1: Verify single subscription request with a Subscriptionlist and different SubscriptionModes", changeMode: false}, + {desc: "GNMI-2.2: Change SubscriptionModes in the subscription list and verify receipt of sync_response:", changeMode: true}, + {desc: "GNMI-2.2: Swithcing Modes, back to previous modes and verifying the receipt of sync_response ", changeMode: false}, + } + + for _, tc := range testCases { + t.Run(tc.desc, func(t *testing.T) { + t.Log(tc.desc) + subscribeList := createSubscriptionList(t, telemetryPaths, tc.changeMode) + subscribeRequest := &gpb.SubscribeRequest{ + Request: &gpb.SubscribeRequest_Subscribe{ + Subscribe: subscribeList, + }, + } + stream, err := dut.RawAPIs().GNMI(t).Subscribe(ctx) + defer stream.CloseSend() + defer ctx.Done() + + if err != nil { + t.Fatalf("[Fail]:Failed to create subscribe stream: %v", err) + } + + if err := stream.Send(subscribeRequest); err != nil { + t.Fatalf("[Fail]:Failed to send subscribe request: %v", err) + } + + startTime := time.Now() + for { + resp, err := stream.Recv() + if resp.GetSyncResponse() == true { + t.Logf("Received sync_response!") + break + } + if err != nil { + t.Errorf("[Error]: While receieving the subcription response %v", err) + } + + if time.Since(startTime).Seconds() > float64(syncResponseWaitTimeOut) { + t.Fatalf("[Fail]:Didn't receive sync_response. Time limit = %v exceeded", syncResponseWaitTimeOut) + } + } + }) + } +} diff --git a/feature/gnmi/subscribe/tests/gnmi_subscriptionlist_test/metadata.textproto b/feature/gnmi/subscribe/tests/gnmi_subscriptionlist_test/metadata.textproto new file mode 100644 index 00000000000..f28d64715ef --- /dev/null +++ b/feature/gnmi/subscribe/tests/gnmi_subscriptionlist_test/metadata.textproto @@ -0,0 +1,7 @@ +# proto-file: github.com/openconfig/featureprofiles/proto/metadata.proto +# proto-message: Metadata + +uuid: "262084aa-ab98-4492-849e-d7ca83105a0e" +plan_id: "GNMI-2" +description: "gnmi_subscriptionlist_test" +testbed: TESTBED_DUT diff --git a/feature/gnoi/system/tests/copying_debug_files_test/copying_debug_files_test.go b/feature/gnoi/system/tests/copying_debug_files_test/copying_debug_files_test.go index 39c752d9f74..7a2bfcfc27a 100644 --- a/feature/gnoi/system/tests/copying_debug_files_test/copying_debug_files_test.go +++ b/feature/gnoi/system/tests/copying_debug_files_test/copying_debug_files_test.go @@ -28,7 +28,7 @@ import ( var ( processName = map[ondatra.Vendor]string{ - ondatra.NOKIA: "sr_bgp_mgr", + ondatra.NOKIA: "sr_qos_mgr", ondatra.ARISTA: "IpRib", ondatra.JUNIPER: "rpd", } diff --git a/feature/gribi/ate_tests/hierarchical_weight_resolution_pbf_test/README.md b/feature/gribi/ate_tests/hierarchical_weight_resolution_pbf_test/README.md deleted file mode 100644 index d2d65948ea1..00000000000 --- a/feature/gribi/ate_tests/hierarchical_weight_resolution_pbf_test/README.md +++ /dev/null @@ -1,143 +0,0 @@ -# TE-3.31: Hierarchical weight resolution with PBF - -## Summary - -Ensures that next-hop weights (for WCMP) are honored hierarchically in gRIBI -recursive resolution and traffic is load-shared according to these weights. - -## Procedure - -Configure ATE and DUT: - -* Connect ATE port-1 to DUT port-1. ATE port-2 to DUT port-2. - -* Create a non-default VRF (VRF-1) that contains no interfaces. - -* On DUT port-2 and ATE port-2 create 18 L3 sub-interfaces each with a /30 - subnet as below: - - * On DUT port-2, create subinterfaces with indices 1 to 18 mapped to VLAN - IDs 1 to 18 and corressponding IPv4 addresses 192.0.2.5, 192.0.2.9, ..., - 192.0.2.73 respectively. - - * On ATE port-2, create subinterfaces with indices 1 to 18 mapped to VLAN - IDs 1 to 18 and corresponding IPv4 addresses 192.0.2.6, 192.0.2.10, ..., - 192.0.2.74 and default gateways as 192.0.2.5, 192.0.2.9, ..., 192.0.2.73 - respectively. - -* On DUT port-1 and ATE port-1 create a single L3 interface. - -* On DUT, create a policy-based forwarding rule to redirect all traffic - received from DUT port-1 into VRF-1 (based on src. IP match criteria). - -* Add an empty decap VRF, `DECAP_TE_VRF`. - -* Add 4 empty encap VRFs, `ENCAP_TE_VRF_A`, `ENCAP_TE_VRF_B`, `ENCAP_TE_VRF_C` - and `ENCAP_TE_VRF_D`. - -* Replace the existing VRF selection policy with `vrf_selection_policy_w` as - in - -Test case for basic hierarchical weight: - -* Establish gRIBI client connection with DUT with PERSISTENCE, make it become - leader and install the following Entries: - - * IPv4Entry 203.0.113.0/32 in VRF-1, pointing to NextHopGroup(NHG#1) in - default VRF, with two NextHops(NH#1, NH#2) in default VRF: - - * NH#1 with weight:1, pointing to 192.0.2.111 - - * NH#2 with weight:3, pointing to 192.0.2.222 - - * IPv4Entry 192.0.2.111/32 in default VRF, pointing to NextHopGroup(NHG#2) - in default VRF, with two NextHops(NH#10, NH#11) in default VRF: - - * NH#10 with weight:1, pointing to 192.0.2.10 - - * NH#11 with weight:3, pointing to 192.0.2.14 - - * IPv4Entry 192.0.2.222/32 in default VRF, pointing to NextHopGroup(NHG#3) - in default VRF, with two NextHops(NH#100, NH#101) in default VRF: - - * NH#100 with weight:3, pointing to 192.0.2.18 - - * NH#101 with weight:5, pointing to 192.0.2.22 - -* Validate with traffic: - - * NH10: (1/4) * (1/4) = 6.25% traffic received by ATE port-2 VLAN 1 - - * NH11: (1/4) * (3/4) = 18.75% traffic received by ATE port-2 VLAN 2 - - * NH100: (3/4) * (3/8) = 28.12% traffic received by ATE port-2 VLAN 3 - - * NH101: (3/4) * (5/8) = 46.87% traffic received by ATE port-2 VLAN 4 - - * A tolerance of 0.2% is allowed for each VLAN for now, since we only test - for 2 mins. - -Test case for hierarchical weight in boundary scenarios, with maximum expected -WCMP width of 16 nexthops: - -* Flush previous gRIBI Entries for all NIs and establish a new connection with - DUT with PERSISTENCE and install the following Entries: - - * IPv4Entry 203.0.113.0/32 in VRF-1, pointing to NextHopGroup(NHG#1) in - default VRF, with two NextHops(NH#1, NH#2) in default VRF: - - * NH#1 with weight:1, pointing to 192.0.2.111 - - * NH#2 with weight:31, pointing to 192.0.2.222 - - * IPv4Entry 192.0.2.111/32 in default VRF, pointing to NextHopGroup(NHG#2) - in default VRF, with two NextHops(NH#10, NH#11) in default VRF: - - * NH#10 with weight:3, pointing to 192.0.2.10 - - * NH#11 with weight:5, pointing to 192.0.2.14 - - * IPv4Entry 192.0.2.222/32 in default VRF, pointing to NextHopGroup(NHG#3) - in default VRF, with 16 NextHops(NH#100, NH#101, ..., NH#115), all with - weight: 16 except NHG#100 is of weight 1, in default VRF: - - * NH#100 with weight:1, pointing to 192.0.2.18 - - * NH#101 with weight:16, pointing to 192.0.2.22 - - * ... - - * NH#115 with weight:16, pointing to 192.0.2.79 - -* Validate with traffic: - - * NH10: (1/32) * (3/8) ~ 1.171% traffic received by ATE port-2 VLAN 1 - - * NH11: (1/32) * (5/8) ~ 1.953% traffic received by ATE port-2 VLAN 2 - - * NH100: (31/32) * (1/241) ~ 0.402% traffic received by ATE port-2 VLAN 3 - - * for each VLAN ID in 4...18: - - * NH: (31/32) * (16/241) ~ 6.432% traffic received by ATE port-2 VLAN - ID - - * A tolerance of 0.2% is allowed for each VLAN for now, since we only test - for 2 mins. - -## OpenConfig Path and RPC Coverage -```yaml -rpcs: - gnmi: - gNMI.Get: - gNMI.Set: - gNMI.Subscribe: - gribi: - gRIBI.Get: - gRIBI.Modify: - gRIBI.Flush: -``` - -## Minimum DUT platform requirement - -vRX diff --git a/feature/gribi/ate_tests/hierarchical_weight_resolution_pbf_test/hierarchical_weight_resolution_pbf_test.go b/feature/gribi/ate_tests/hierarchical_weight_resolution_pbf_test/hierarchical_weight_resolution_pbf_test.go deleted file mode 100644 index 78883a0158c..00000000000 --- a/feature/gribi/ate_tests/hierarchical_weight_resolution_pbf_test/hierarchical_weight_resolution_pbf_test.go +++ /dev/null @@ -1,705 +0,0 @@ -// Copyright 2022 Google LLC -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. - -// Package hierarchical_weight_resolution_test implements TE-3.3 of the Popgate vendor testplan -package hierarchical_weight_resolution_pbf_test - -import ( - "context" - "fmt" - "strconv" - "testing" - "time" - - "github.com/google/go-cmp/cmp" - "github.com/google/go-cmp/cmp/cmpopts" - "github.com/openconfig/featureprofiles/internal/attrs" - "github.com/openconfig/featureprofiles/internal/deviations" - "github.com/openconfig/featureprofiles/internal/fptest" - "github.com/openconfig/featureprofiles/internal/gribi" - "github.com/openconfig/featureprofiles/internal/vrfpolicy" - "github.com/openconfig/gribigo/chk" - "github.com/openconfig/gribigo/constants" - "github.com/openconfig/gribigo/fluent" - "github.com/openconfig/ondatra" - "github.com/openconfig/ondatra/gnmi" - "github.com/openconfig/ondatra/gnmi/oc" - "github.com/openconfig/ygot/ygot" -) - -type attributes struct { - attrs.Attributes - numSubIntf uint32 - ip func(vlan uint8) string - gateway func(vlan uint8) string -} - -type nhInfo struct { - index uint64 - weight uint64 -} - -const ( - ipv4EntryPrefix = "203.0.113.0/32" - ipv4FlowIP = "203.0.113.0" - innerSrcIPv4Start = "198.18.0.0" - innerDstIPv4Start = "198.19.0.0" - ipv4PrefixLen = 30 - ipv4FlowCount = 65000 - nhEntryIP1 = "192.0.2.111" - nhEntryIP2 = "192.0.2.222" - nonDefaultVRF = "TE_VRF_111" - policyName = "redirect-to-VRF1" - ipipProtocol = 4 - decapFlowSrc = "198.51.100.111" - dscpEncapA1 = 10 -) - -var ( - dutPort1 = attributes{ - Attributes: attrs.Attributes{ - Desc: "dutPort1", - Name: "port1", - IPv4: dutPort1IPv4(0), - IPv4Len: ipv4PrefixLen, - }, - numSubIntf: 0, - ip: dutPort1IPv4, - } - - atePort1 = attributes{ - Attributes: attrs.Attributes{ - Name: "port1", - IPv4: atePort1IPv4(0), - IPv4Len: ipv4PrefixLen, - }, - numSubIntf: 0, - ip: atePort1IPv4, - gateway: dutPort1IPv4, - } - - dutPort2 = attributes{ - Attributes: attrs.Attributes{ - Desc: "dutPort2", - Name: "port2", - IPv4: dutPort2IPv4(0), - IPv4Len: ipv4PrefixLen, - }, - numSubIntf: 18, - ip: dutPort2IPv4, - } - - atePort2 = attributes{ - Attributes: attrs.Attributes{ - Name: "port2", - IPv4: atePort2IPv4(0), - IPv4Len: ipv4PrefixLen, - }, - numSubIntf: 18, - ip: atePort2IPv4, - gateway: dutPort2IPv4, - } - - // nhgIPv4EntryMap maps NextHopGroups to the ipv4 entries pointing to that NextHopGroup. - nhgIPv4EntryMap = map[uint64]string{ - 1: ipv4EntryPrefix, - 2: cidr(nhEntryIP1, 32), - 3: cidr(nhEntryIP2, 32), - } - // 'tolerance' is the maximum difference that is allowed between the observed - // traffic distribution and the required traffic distribution. - tolerance = 0.2 -) - -func TestMain(m *testing.M) { - fptest.RunTests(m) -} - -// dutPort1IPv4 returns ip address 192.0.2.1, for every vlanID. -func dutPort1IPv4(uint8) string { - return "192.0.2.1" -} - -// atePort1IPv4 returns ip address 192.0.2.2, for every vlanID -func atePort1IPv4(uint8) string { - return "192.0.2.2" -} - -// dutPort2IPv4 returns ip addresses starting 192.0.2.5, increasing by 4 -// for every vlanID. -func dutPort2IPv4(vlan uint8) string { - return fmt.Sprintf("192.0.2.%d", vlan*4+5) -} - -// atePort2IPv4 returns ip addresses starting 192.0.2.6, increasing by 4 -// for every vlanID. -func atePort2IPv4(vlan uint8) string { - return fmt.Sprintf("192.0.2.%d", vlan*4+6) -} - -// cidr taks as input the IPv4 address and the Mask and returns the IP string in -// CIDR notation. -func cidr(ipv4 string, ones int) string { - return ipv4 + "/" + strconv.Itoa(ones) -} - -// filterPacketReceived uses ATE:EgressTracking bucket counters to create a map -// with bucket-label as the Key and the percentage of packets-received for that -// bucket as the Value. -func filterPacketReceived(t *testing.T, flow string, ate *ondatra.ATEDevice) map[string]float64 { - t.Helper() - - flowPath := gnmi.OC().Flow(flow) - filters := gnmi.GetAll(t, ate, flowPath.EgressTrackingAny().State()) - - inPkts := map[string]uint64{} - for _, f := range filters { - inPkts[f.GetFilter()] = f.GetCounters().GetInPkts() - } - inPct := map[string]float64{} - total := gnmi.Get(t, ate, flowPath.Counters().OutPkts().State()) - for k, v := range inPkts { - inPct[k] = (float64(v) / float64(total)) * 100.0 - } - return inPct -} - -// configureGRIBIClient configures a new GRIBI client with PRESERVE and FIB_ACK. -func configureGRIBIClient(t *testing.T, dut *ondatra.DUTDevice) *fluent.GRIBIClient { - t.Helper() - gribic := dut.RawAPIs().GRIBI(t) - - // Configure the gRIBI client. - c := fluent.NewClient() - c.Connection(). - WithStub(gribic). - WithRedundancyMode(fluent.ElectedPrimaryClient). - WithInitialElectionID(1 /* low */, 0 /* hi */). - WithPersistence(). - WithFIBACK() - - return c -} - -// nextHopEntry configures a fluent.GRIBIEntry for a NextHopEntry. -func nextHopEntry(index uint64, networkInstance string, ipAddr string) fluent.GRIBIEntry { - return fluent.NextHopEntry(). - WithNetworkInstance(networkInstance). - WithIndex(index). - WithIPAddress(ipAddr) -} - -// nextHopGroupEntry configures a fluent.GRIBIEntry for a NextHopGroupEntry. -func nextHopGroupEntry(index uint64, networkInstance string, nhs []nhInfo) fluent.GRIBIEntry { - x := fluent.NextHopGroupEntry(). - WithNetworkInstance(networkInstance). - WithID(index) - for _, nh := range nhs { - x.AddNextHop(nh.index, nh.weight) - } - return x -} - -// ipv4Entry configures a fluent.GRIBIEntry for an IPv4Entry. -func ipv4Entry(prefix string, networkInstance string, nhgIndex uint64, nextHopGroupNetworkInstance string) fluent.GRIBIEntry { - return fluent.IPv4Entry(). - WithPrefix(prefix). - WithNetworkInstance(networkInstance). - WithNextHopGroup(nhgIndex). - WithNextHopGroupNetworkInstance(nextHopGroupNetworkInstance) -} - -// awaitTimeout calls a fluent client Await, adding a timeout to the context. -func awaitTimeout(ctx context.Context, c *fluent.GRIBIClient, t testing.TB, timeout time.Duration) error { - t.Helper() - subctx, cancel := context.WithTimeout(ctx, timeout) - defer cancel() - return c.Await(subctx, t) -} - -// configSubinterfaceDUT configures the Sub Interfaces of an Interfaces, -// starting from Sub Interface 1. Each Subinterface is configured with a -// unique VlanID starting from 1 and an IP address. The starting IP Address -// for Subinterface(1) = dutPort.ip(1) = dutPort.ip + 4. -func (a *attributes) configSubinterfaceDUT(t *testing.T, intf *oc.Interface, dut *ondatra.DUTDevice) { - t.Helper() - if deviations.RequireRoutedSubinterface0(dut) { - s0 := intf.GetOrCreateSubinterface(0).GetOrCreateIpv4() - s0.Enabled = ygot.Bool(true) - } - for i := uint32(1); i <= a.numSubIntf; i++ { - ip := a.ip(uint8(i)) - - s := intf.GetOrCreateSubinterface(i) - if deviations.InterfaceEnabled(dut) { - s.Enabled = ygot.Bool(true) - } - if deviations.DeprecatedVlanID(dut) { - s.GetOrCreateVlan().VlanId = oc.UnionUint16(i) - } else { - s.GetOrCreateVlan().GetOrCreateMatch().GetOrCreateSingleTagged().VlanId = ygot.Uint16(uint16(i)) - } - s4 := s.GetOrCreateIpv4() - if deviations.InterfaceEnabled(dut) && !deviations.IPv4MissingEnabled(dut) { - s4.Enabled = ygot.Bool(true) - } - s4a := s4.GetOrCreateAddress(ip) - s4a.PrefixLength = ygot.Uint8(a.IPv4Len) - t.Logf("Adding DUT Subinterface with ID: %d, Vlan ID: %d and IPv4 address: %s", i, i, ip) - } -} - -// configInterfaceDUT configures the DUT interface with the provided IP Address. -// Sub Interfaces are also configured if numSubIntf > 0. -func (a *attributes) configInterfaceDUT(t *testing.T, d *ondatra.DUTDevice) { - t.Helper() - p := d.Port(t, a.Name) - i := &oc.Interface{Name: ygot.String(p.Name())} - - if a.numSubIntf > 0 { - i.Description = ygot.String(a.Desc) - i.Type = oc.IETFInterfaces_InterfaceType_ethernetCsmacd - if deviations.InterfaceEnabled(d) { - i.Enabled = ygot.Bool(true) - } - } else { - i = a.NewOCInterface(p.Name(), d) - } - - if deviations.ExplicitPortSpeed(d) { - i.GetOrCreateEthernet().PortSpeed = fptest.GetIfSpeed(t, p) - } - - a.configSubinterfaceDUT(t, i, d) - intfPath := gnmi.OC().Interface(p.Name()) - gnmi.Replace(t, d, intfPath.Config(), i) - fptest.LogQuery(t, "DUT", intfPath.Config(), gnmi.Get(t, d, intfPath.Config())) -} - -func configureDUT(t *testing.T, dut *ondatra.DUTDevice) { - // configure NI. - configureNetworkInstance(t, dut) - - // Configure DUT ports. - dutPort1.configInterfaceDUT(t, dut) - dutPort2.configInterfaceDUT(t, dut) - - // assign subinterfaces to DEFAULT network instance if needed (deviation-based). - dutPort1.assignSubifsToDefaultNetworkInstance(t, dut) - dutPort2.assignSubifsToDefaultNetworkInstance(t, dut) - - // apply PBF to src interface. - dp1 := dut.Port(t, dutPort1.Name) - applyForwardingPolicy(t, dp1.Name()) -} - -// configureNetworkInstance creates and configures non-default and default NIs. -func configureNetworkInstance(t *testing.T, d *ondatra.DUTDevice) { - t.Helper() - - // configure non-default VRF - ni := &oc.NetworkInstance{ - Name: ygot.String(nonDefaultVRF), - Type: oc.NetworkInstanceTypes_NETWORK_INSTANCE_TYPE_L3VRF, - } - dni := gnmi.OC().NetworkInstance(nonDefaultVRF) - gnmi.Replace(t, d, dni.Config(), ni) - fptest.LogQuery(t, "NI", dni.Config(), gnmi.Get(t, d, dni.Config())) - - // configure PBF in DEFAULT vrf - defNIPath := gnmi.OC().NetworkInstance(deviations.DefaultNetworkInstance(d)) - fptest.ConfigureDefaultNetworkInstance(t, d) - gnmi.Replace(t, d, defNIPath.PolicyForwarding().Config(), configurePBF(d)) - -} - -// assignSubifsToDefaultNetworkInstance assign subinterfaces to the default network instance when ExplicitInterfaceInDefaultVRF is enabled. -func (a *attributes) assignSubifsToDefaultNetworkInstance(t *testing.T, d *ondatra.DUTDevice) { - p := d.Port(t, a.Name) - if deviations.ExplicitInterfaceInDefaultVRF(d) { - if a.numSubIntf == 0 { - fptest.AssignToNetworkInstance(t, d, p.Name(), deviations.DefaultNetworkInstance(d), 0) - } else { - for i := uint32(1); i <= a.numSubIntf; i++ { - fptest.AssignToNetworkInstance(t, d, p.Name(), deviations.DefaultNetworkInstance(d), i) - } - } - } -} - -// configurePBF returns a fully configured network-instance PF struct. -func configurePBF(dut *ondatra.DUTDevice) *oc.NetworkInstance_PolicyForwarding { - d := &oc.Root{} - ni := d.GetOrCreateNetworkInstance(deviations.DefaultNetworkInstance(dut)) - pf := ni.GetOrCreatePolicyForwarding() - vrfPolicy := pf.GetOrCreatePolicy(policyName) - vrfPolicy.SetType(oc.Policy_Type_VRF_SELECTION_POLICY) - vrfPolicy.GetOrCreateRule(1).GetOrCreateIpv4().Protocol = oc.UnionUint8(ipipProtocol) - vrfPolicy.GetOrCreateRule(1).GetOrCreateAction().NetworkInstance = ygot.String(nonDefaultVRF) - return pf -} - -// applyForwardingPolicy applies the forwarding policy on the interface. -func applyForwardingPolicy(t *testing.T, ingressPort string) { - t.Logf("Applying forwarding policy on interface %v ... ", ingressPort) - d := &oc.Root{} - dut := ondatra.DUT(t, "dut") - interfaceID := ingressPort - if deviations.InterfaceRefInterfaceIDFormat(dut) { - interfaceID = ingressPort + ".0" - } - pfPath := gnmi.OC().NetworkInstance(deviations.DefaultNetworkInstance(dut)).PolicyForwarding().Interface(interfaceID) - pfCfg := d.GetOrCreateNetworkInstance(deviations.DefaultNetworkInstance(dut)).GetOrCreatePolicyForwarding().GetOrCreateInterface(interfaceID) - pfCfg.ApplyVrfSelectionPolicy = ygot.String(policyName) - pfCfg.GetOrCreateInterfaceRef().Interface = ygot.String(ingressPort) - pfCfg.GetOrCreateInterfaceRef().Subinterface = ygot.Uint32(0) - if deviations.InterfaceRefConfigUnsupported(dut) { - pfCfg.InterfaceRef = nil - } - gnmi.Replace(t, dut, pfPath.Config(), pfCfg) -} - -// ConfigureATE configures Ethernet + IPv4 on the ATE. If the number of -// Subinterfaces(numSubIntf) > 0, we then create additional sub-interfaces -// each with a unique VlanID starting from 1. The IPv4 addresses start with -// ATE:Port.IPv4 and then nextIP(ATE:Port.IPv4, 4) for each sub interface. -func (a *attributes) ConfigureATE(t *testing.T, top *ondatra.ATETopology, ate *ondatra.ATEDevice) { - t.Helper() - p := ate.Port(t, a.Name) - // Configure source port on ATE : Port1. - if a.numSubIntf == 0 { - ip := a.ip(0) - gateway := a.gateway(0) - intf := top.AddInterface(ip).WithPort(p) - intf.IPv4().WithAddress(cidr(ip, 30)) - intf.IPv4().WithDefaultGateway(gateway) - t.Logf("Adding ATE Ipv4 address: %s with gateway: %s", cidr(ip, 30), gateway) - } - // Configure destination port on ATE : Port2. - for i := uint32(1); i <= a.numSubIntf; i++ { - ip := a.ip(uint8(i)) - gateway := a.gateway(uint8(i)) - intf := top.AddInterface(ip).WithPort(p) - intf.IPv4().WithAddress(cidr(ip, 30)) - intf.IPv4().WithDefaultGateway(gateway) - intf.Ethernet().WithVLANID(uint16(i)) - t.Logf("Adding ATE Ipv4 address: %s with gateway: %s and VlanID: %d", cidr(ip, 30), gateway, i) - } -} - -// testTraffic creates a traffic flow with ATE source & destination endpoints -// and configures a VlanID filter for output frames. The IPv4 header for the -// flow contains the ATE:Port1 address as source and the configured gRIBI- -// IndirectEntry as the destination. The function also takes as input a map of -// that is wanted and compares it to the actual -// traffic test result. -func testTraffic(t *testing.T, ate *ondatra.ATEDevice, top *ondatra.ATETopology) map[string]float64 { - allIntf := top.Interfaces() - - // ATE source endpoint. - srcEndPoint := allIntf[atePort1.IPv4] - - // ATE destination endpoints. - dstEndPoints := []ondatra.Endpoint{} - for i := uint32(1); i <= atePort2.numSubIntf; i++ { - dstIP := atePort2.ip(uint8(i)) - dstEndPoints = append(dstEndPoints, allIntf[dstIP]) - } - - // Configure Ethernet+IPv4 headers. - ethHeader := ondatra.NewEthernetHeader() - ipv4Header := ondatra.NewIPv4Header() - ipv4Header.WithSrcAddress(decapFlowSrc) - ipv4Header.WithDSCP(dscpEncapA1) - ipv4Header.WithDstAddress(ipv4FlowIP) - innerIpv4Header := ondatra.NewIPv4Header() - innerIpv4Header.SrcAddressRange().WithMin(innerSrcIPv4Start).WithCount(ipv4FlowCount).WithStep("0.0.0.1") - innerIpv4Header.DstAddressRange().WithMin(innerDstIPv4Start).WithCount(ipv4FlowCount).WithStep("0.0.0.1") - - // Ethernet header: - // - Destination MAC (6 octets) - // - Source MAC (6 octets) - // - Optional 802.1q VLAN tag (4 octets) - // - Frame size (2 octets) - flow := ate.Traffic().NewFlow("flow"). - WithSrcEndpoints(srcEndPoint). - WithDstEndpoints(dstEndPoints...). - WithHeaders(ethHeader, ipv4Header, innerIpv4Header) - - // VlanID is the last 12 bits in the 802.1q VLAN tag. - // Offset for VlanID: ((6+6+4) * 8)-12 = 116. - flow.EgressTracking().WithOffset(116).WithWidth(12).WithCount(18) - - // Run traffic for 2 minutes. - ate.Traffic().Start(t, flow) - time.Sleep(2 * time.Minute) - ate.Traffic().Stop(t) - - gnmi.Await(t, ate, gnmi.OC().Flow("flow").LossPct().State(), time.Minute, 0) - - // Compare traffic distribution with the wanted results. - results := filterPacketReceived(t, "flow", ate) - t.Logf("Filters: %v", results) - return results -} - -// aftNextHopWeights queries AFT telemetry using Get() and returns -// the weights. If not-found, an empty list is returned. -func aftNextHopWeights(t *testing.T, dut *ondatra.DUTDevice, nhg uint64, networkInstance string) []uint64 { - aft := gnmi.Get(t, dut, gnmi.OC().NetworkInstance(networkInstance).Afts().State()) - var nhgD *oc.NetworkInstance_Afts_NextHopGroup - for _, nhgData := range aft.NextHopGroup { - if nhgData.GetProgrammedId() == nhg { - nhgD = nhgData - break - } - } - - if nhgD == nil { - return []uint64{} - } - - got := []uint64{} - for _, nhD := range nhgD.NextHop { - got = append(got, nhD.GetWeight()) - } - - return got -} - -// testBasicHierarchicalWeight tests and validates traffic through 4 Vlans. -func testBasicHierarchicalWeight(ctx context.Context, t *testing.T, dut *ondatra.DUTDevice, - ate *ondatra.ATEDevice, top *ondatra.ATETopology, gRIBI *fluent.GRIBIClient) { - defaultVRF := deviations.DefaultNetworkInstance(dut) - - // Set up NH#10, NH#11, NHG#2, IPv4Entry(192.0.2.111). - nh10 := nextHopEntry(10, defaultVRF, atePort2.ip(1)) - nh11 := nextHopEntry(11, defaultVRF, atePort2.ip(2)) - nhg2 := nextHopGroupEntry(2, defaultVRF, []nhInfo{{index: 10, weight: 1}, {index: 11, weight: 3}}) - ipEntry2 := ipv4Entry(nhgIPv4EntryMap[2], defaultVRF, 2, defaultVRF) - - gRIBI.Modify().AddEntry(t, nh10, nh11, nhg2, ipEntry2) - - // Set up NH#100, NH#101, NHG#3, IPv4Entry(192.0.2.222). - nh100 := nextHopEntry(100, defaultVRF, atePort2.ip(3)) - nh101 := nextHopEntry(101, defaultVRF, atePort2.ip(4)) - nhg3 := nextHopGroupEntry(3, defaultVRF, []nhInfo{{index: 100, weight: 3}, {index: 101, weight: 5}}) - ipEntry3 := ipv4Entry(nhgIPv4EntryMap[3], defaultVRF, 3, defaultVRF) - - gRIBI.Modify().AddEntry(t, nh100, nh101, nhg3, ipEntry3) - - // Set up NH#1, NH#2, NHG#1, IPv4Entry(198.18.196.1/22). - nh1 := nextHopEntry(1, defaultVRF, nhEntryIP1) - nh2 := nextHopEntry(2, defaultVRF, nhEntryIP2) - nhg1 := nextHopGroupEntry(1, defaultVRF, []nhInfo{{index: 1, weight: 1}, {index: 2, weight: 3}}) - ipEntry1 := ipv4Entry(nhgIPv4EntryMap[1], nonDefaultVRF, 1, defaultVRF) - - gRIBI.Modify().AddEntry(t, nh1, nh2, nhg1, ipEntry1) - - if err := awaitTimeout(ctx, gRIBI, t, time.Minute); err != nil { - t.Fatalf("Could not program entries via gRIBI, got err: %v", err) - } - - // Validate entries were installed in FIB. - for _, route := range nhgIPv4EntryMap { - chk.HasResult(t, gRIBI.Results(t), - fluent.OperationResult(). - WithIPv4Operation(route). - WithOperationType(constants.Add). - WithProgrammingResult(fluent.InstalledInFIB). - AsResult(), - chk.IgnoreOperationID(), - ) - } - - // Test traffic flows correctly and - wantWeights := map[string]float64{ - "1": 6.25, - "2": 18.75, - "3": 28.12, - "4": 46.87, - } - t.Run("testTraffic", func(t *testing.T) { - got := testTraffic(t, ate, top) - if diff := cmp.Diff(wantWeights, got, cmpopts.EquateApprox(0, tolerance)); diff != "" { - t.Errorf("Packet distribution ratios -want,+got:\n%s", diff) - } - }) - - t.Run("validateAFTWeights", func(t *testing.T) { - for nhg, weights := range map[uint64][]uint64{ - 2: {1, 3}, - 3: {3, 5}, - } { - got := aftNextHopWeights(t, dut, nhg, defaultVRF) - ok := cmp.Equal(weights, got, cmpopts.SortSlices(func(a, b uint64) bool { return a < b })) - if !ok { - t.Errorf("Valid weights not present for NI: %s, NHG: %d, got: %v, want: %v", defaultVRF, nhg, got, weights) - } - } - }) - - // Flush gRIBI routes after test. - if err := gribi.FlushAll(gRIBI); err != nil { - t.Error(err) - } -} - -// testHierarchicalWeightBoundaryScenario tests and validates traffic through all 18 Vlans. -func testHierarchicalWeightBoundaryScenario(ctx context.Context, t *testing.T, dut *ondatra.DUTDevice, - ate *ondatra.ATEDevice, top *ondatra.ATETopology, gRIBI *fluent.GRIBIClient) { - defaultVRF := deviations.DefaultNetworkInstance(dut) - - // Set up NH#10, NH#11, NHG#2, IPv4Entry(192.0.2.111). - nh10 := nextHopEntry(10, defaultVRF, atePort2.ip(1)) - nh11 := nextHopEntry(11, defaultVRF, atePort2.ip(2)) - nhg2 := nextHopGroupEntry(2, defaultVRF, []nhInfo{{index: 10, weight: 3}, {index: 11, weight: 5}}) - ipEntry2 := ipv4Entry(nhgIPv4EntryMap[2], defaultVRF, 2, defaultVRF) - - gRIBI.Modify().AddEntry(t, nh10, nh11, nhg2, ipEntry2) - - // Set up NH#100..NH#116, NHG#3, IPv4Entry(192.0.2.222). - nextHopWeights := []nhInfo{} - nhIdx := uint64(100) - gribiEntries := []fluent.GRIBIEntry{} - for i := 0; i < 16; i++ { - nh := nextHopEntry(nhIdx, defaultVRF, atePort2.ip(uint8(3+i))) - gribiEntries = append(gribiEntries, nh) - if i == 0 { - nextHopWeights = append(nextHopWeights, nhInfo{index: nhIdx, weight: 1}) - } else { - nextHopWeights = append(nextHopWeights, nhInfo{index: nhIdx, weight: 16}) - } - nhIdx++ - } - nhg3 := nextHopGroupEntry(3, defaultVRF, nextHopWeights) - ipEntry3 := ipv4Entry(nhgIPv4EntryMap[3], defaultVRF, 3, defaultVRF) - gribiEntries = append(gribiEntries, nhg3, ipEntry3) - - gRIBI.Modify().AddEntry(t, gribiEntries...) - - // Set up NH#1, NH#2, NHG#1, IPv4Entry(198.18.196.1/22). - nh1 := nextHopEntry(1, defaultVRF, nhEntryIP1) - nh2 := nextHopEntry(2, defaultVRF, nhEntryIP2) - nhg1 := nextHopGroupEntry(1, defaultVRF, []nhInfo{{index: 1, weight: 1}, {index: 2, weight: 31}}) - ipEntry1 := ipv4Entry(nhgIPv4EntryMap[1], nonDefaultVRF, 1, defaultVRF) - - gRIBI.Modify().AddEntry(t, nh1, nh2, nhg1, ipEntry1) - - if err := awaitTimeout(ctx, gRIBI, t, time.Minute); err != nil { - t.Fatalf("Could not program entries via gRIBI, got err: %v", err) - } - - // Validate entries were installed in FIB. - for _, route := range nhgIPv4EntryMap { - chk.HasResult(t, gRIBI.Results(t), - fluent.OperationResult(). - WithIPv4Operation(route). - WithOperationType(constants.Add). - WithProgrammingResult(fluent.InstalledInFIB). - AsResult(), - chk.IgnoreOperationID(), - ) - } - - wantWeights := map[string]float64{ - "1": 1.171, - "2": 1.953, - "3": 0.402, - } - // 6.432 weight for vlans 4 to 18. - for i := 4; i <= 18; i++ { - wantWeights[strconv.Itoa(i)] = 6.432 - } - t.Run("testTraffic", func(t *testing.T) { - got := testTraffic(t, ate, top) - - if deviations.HierarchicalWeightResolutionTolerance(dut) != tolerance { - tolerance = deviations.HierarchicalWeightResolutionTolerance(dut) - } - if diff := cmp.Diff(wantWeights, got, cmpopts.EquateApprox(0, tolerance)); diff != "" { - t.Errorf("Packet distribution ratios -want,+got:\n%s", diff) - } - }) - - t.Run("validateAFTWeights", func(t *testing.T) { - for nhg, weights := range map[uint64][]uint64{ - 2: {3, 5}, - 3: {1, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16}, - } { - got := aftNextHopWeights(t, dut, nhg, defaultVRF) - ok := cmp.Equal(weights, got, cmpopts.SortSlices(func(a, b uint64) bool { return a < b })) - if !ok { - t.Errorf("Valid weights not present for NI: %s, NHG: %d, got: %v, want: %v", defaultVRF, nhg, got, weights) - } - } - }) - - // Flush gRIBI routes after test. - if err := gribi.FlushAll(gRIBI); err != nil { - t.Error(err) - } -} - -func TestHierarchicalWeightResolution(t *testing.T) { - dut := ondatra.DUT(t, "dut") - ate := ondatra.ATE(t, "ate") - ctx := context.Background() - - // configure DUT. - configureDUT(t, dut) - - // Configure ATE ports and start Ethernet+IPv4. - top := ate.Topology().New() - atePort1.ConfigureATE(t, top, ate) - atePort2.ConfigureATE(t, top, ate) - top.Push(t) - top.StartProtocols(t) - - // Configure gRIBI with FIB_ACK. - gRIBI := configureGRIBIClient(t, dut) - - gRIBI.Start(ctx, t) - defer gRIBI.Stop(t) - - defer func() { - // Flush all gRIBI routes after test. - if err := gribi.FlushAll(gRIBI); err != nil { - t.Error(err) - } - }() - - gRIBI.StartSending(ctx, t) - if err := awaitTimeout(ctx, gRIBI, t, time.Minute); err != nil { - t.Fatalf("Await got error during session negotiation for gRIBI: %v", err) - } - gribi.BecomeLeader(t, gRIBI) - - // Flush existing gRIBI routes before test. - if err := gribi.FlushAll(gRIBI); err != nil { - t.Fatal(err) - } - - t.Run("TestBasicHierarchicalWeightWithVrfPolW", func(t *testing.T) { - vrfpolicy.ConfigureVRFSelectionPolicy(t, dut, vrfpolicy.VRFPolicyW) - testBasicHierarchicalWeight(ctx, t, dut, ate, top, gRIBI) - }) - - t.Run("TestHierarchicalWeightBoundaryScenarioWithVrfPolW", func(t *testing.T) { - vrfpolicy.ConfigureVRFSelectionPolicy(t, dut, vrfpolicy.VRFPolicyW) - testHierarchicalWeightBoundaryScenario(ctx, t, dut, ate, top, gRIBI) - }) - - top.StopProtocols(t) -} diff --git a/feature/gribi/ate_tests/hierarchical_weight_resolution_pbf_test/metadata.textproto b/feature/gribi/ate_tests/hierarchical_weight_resolution_pbf_test/metadata.textproto deleted file mode 100644 index 7e578982254..00000000000 --- a/feature/gribi/ate_tests/hierarchical_weight_resolution_pbf_test/metadata.textproto +++ /dev/null @@ -1,50 +0,0 @@ -# proto-file: github.com/openconfig/featureprofiles/proto/metadata.proto -# proto-message: Metadata - -uuid: "bf5df0ee-79b7-460b-8146-3a1351fd56d7" -plan_id: "TE-3.31" -description: "Hierarchical weight resolution with PBF" -testbed: TESTBED_DUT_ATE_2LINKS -platform_exceptions: { - platform: { - vendor: CISCO - } - deviations: { - hierarchical_weight_resolution_tolerance: 1.5 - ipv4_missing_enabled: true - interface_ref_interface_id_format: true - pf_require_match_default_rule: true - pf_require_sequential_order_pbr_rules: true - } -} -platform_exceptions: { - platform: { - vendor: JUNIPER - } - deviations: { - hierarchical_weight_resolution_tolerance: 0.4 - explicit_interface_ref_definition: true - } -} -platform_exceptions: { - platform: { - vendor: NOKIA - } - deviations: { - explicit_port_speed: true - explicit_interface_in_default_vrf: true - interface_enabled: true - } -} -platform_exceptions: { - platform: { - vendor: ARISTA - } - deviations: { - omit_l2_mtu: true - deprecated_vlan_id: true - interface_enabled: true - default_network_instance: "default" - } -} -tags: TAGS_DATACENTER_EDGE diff --git a/feature/gribi/ate_tests/hierarchical_weight_resolution_test/README.md b/feature/gribi/ate_tests/hierarchical_weight_resolution_test/README.md deleted file mode 100644 index 63bfca04b3c..00000000000 --- a/feature/gribi/ate_tests/hierarchical_weight_resolution_test/README.md +++ /dev/null @@ -1,144 +0,0 @@ -# TE-3.3: Hierarchical weight resolution - -## Summary - -Ensures that next-hop weights (for WCMP) are honored hierarchically in gRIBI -recursive resolution and traffic is load-shared according to these weights. - -## Procedure - -Configure ATE and DUT: - -* Connect ATE port-1 to DUT port-1. ATE port-2 to DUT port-2. - -* Create a non-default VRF (VRF-1) that contains no interfaces. - -* On DUT port-2 and ATE port-2 create 18 L3 sub-interfaces each with a /30 - subnet as below: - - * On DUT port-2, create subinterfaces with indices 1 to 18 mapped to VLAN - IDs 1 to 18 and corressponding IPv4 addresses 192.0.2.5, 192.0.2.9, ..., - 192.0.2.73 respectively. - - * On ATE port-2, create subinterfaces with indices 1 to 18 mapped to VLAN - IDs 1 to 18 and corresponding IPv4 addresses 192.0.2.6, 192.0.2.10, ..., - 192.0.2.74 and default gateways as 192.0.2.5, 192.0.2.9, ..., 192.0.2.73 - respectively. - -* On DUT port-1 and ATE port-1 create a single L3 interface. - -* On DUT, create a policy-based forwarding rule to redirect all traffic - received from DUT port-1 into VRF-1 (based on src. IP match criteria). - -Test case for basic hierarchical weight: - -* Establish gRIBI client connection with DUT with PERSISTENCE, make it become - leader and install the following Entries: - - * IPv4Entry 203.0.113.0/32 in VRF-1, pointing to NextHopGroup(NHG#1) in - default VRF, with two NextHops(NH#1, NH#2) in default VRF: - - * NH#1 with weight:1, pointing to 192.0.2.111 - - * NH#2 with weight:3, pointing to 192.0.2.222 - - * IPv4Entry 192.0.2.111/32 in default VRF, pointing to NextHopGroup(NHG#2) - in default VRF, with two NextHops(NH#10, NH#11) in default VRF: - - * NH#10 with weight:1, pointing to 192.0.2.10 - - * NH#11 with weight:3, pointing to 192.0.2.14 - - * IPv4Entry 192.0.2.222/32 in default VRF, pointing to NextHopGroup(NHG#3) - in default VRF, with two NextHops(NH#100, NH#101) in default VRF: - - * NH#100 with weight:3, pointing to 192.0.2.18 - - * NH#101 with weight:5, pointing to 192.0.2.22 - -* Validate with traffic: - - * NH10: (1/4) * (1/4) = 6.25% traffic received by ATE port-2 VLAN 1 - - * NH11: (1/4) * (3/4) = 18.75% traffic received by ATE port-2 VLAN 2 - - * NH100: (3/4) * (3/8) = 28.12% traffic received by ATE port-2 VLAN 3 - - * NH101: (3/4) * (5/8) = 46.87% traffic received by ATE port-2 VLAN 4 - - * A tolerance of 0.2% is allowed for each VLAN for now, since we only test - for 2 mins. - -Test case for hierarchical weight in boundary scenarios, with maximum expected -WCMP width of 16 nexthops: - -* Flush previous gRIBI Entries for all NIs and establish a new connection with - DUT with PERSISTENCE and install the following Entries: - - * IPv4Entry 203.0.113.0/32 in VRF-1, pointing to NextHopGroup(NHG#1) in - default VRF, with two NextHops(NH#1, NH#2) in default VRF: - - * NH#1 with weight:1, pointing to 192.0.2.111 - - * NH#2 with weight:31, pointing to 192.0.2.222 - - * IPv4Entry 192.0.2.111/32 in default VRF, pointing to NextHopGroup(NHG#2) - in default VRF, with two NextHops(NH#10, NH#11) in default VRF: - - * NH#10 with weight:3, pointing to 192.0.2.10 - - * NH#11 with weight:5, pointing to 192.0.2.14 - - * IPv4Entry 192.0.2.222/32 in default VRF, pointing to NextHopGroup(NHG#3) - in default VRF, with 16 NextHops(NH#100, NH#101, ..., NH#115), all with - weight: 16 except NHG#100 is of weight 1, in default VRF: - - * NH#100 with weight:1, pointing to 192.0.2.18 - - * NH#101 with weight:16, pointing to 192.0.2.22 - - * ... - - * NH#115 with weight:16, pointing to 192.0.2.79 - -* Validate with traffic: - - * NH10: (1/32) * (3/8) ~ 1.171% traffic received by ATE port-2 VLAN 1 - - * NH11: (1/32) * (5/8) ~ 1.953% traffic received by ATE port-2 VLAN 2 - - * NH100: (31/32) * (1/241) ~ 0.402% traffic received by ATE port-2 VLAN 3 - - * for each VLAN ID in 4...18: - - * NH: (31/32) * (16/241) ~ 6.432% traffic received by ATE port-2 VLAN - ID - - * A tolerance of 0.2% is allowed for each VLAN for now, since we only test - for 2 mins. - -## Config Parameter Coverage - -N/A - -## OpenConfig Path and RPC Coverage -```yaml -paths: - ## State Paths ## - /network-instances/network-instance/afts/next-hop-groups/next-hop-group/next-hops/next-hop/state/weight: - -rpcs: - gnmi: - gNMI.Get: - gNMI.Set: - gNMI.Subscribe: - gribi: - gRIBI.Get: - gRIBI.Modify: - gRIBI.Flush: -``` - -## Minimum DUT platform requirement - -* vRX - virtual router device - diff --git a/feature/gribi/ate_tests/hierarchical_weight_resolution_test/hierarchical_weight_resolution_test.go b/feature/gribi/ate_tests/hierarchical_weight_resolution_test/hierarchical_weight_resolution_test.go deleted file mode 100644 index 2e18c26622f..00000000000 --- a/feature/gribi/ate_tests/hierarchical_weight_resolution_test/hierarchical_weight_resolution_test.go +++ /dev/null @@ -1,699 +0,0 @@ -// Copyright 2022 Google LLC -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. - -// Package hierarchical_weight_resolution_test implements TE-3.3 of the Popgate vendor testplan -package hierarchical_weight_resolution_test - -import ( - "context" - "fmt" - "strconv" - "testing" - "time" - - "github.com/google/go-cmp/cmp" - "github.com/google/go-cmp/cmp/cmpopts" - "github.com/openconfig/featureprofiles/internal/attrs" - "github.com/openconfig/featureprofiles/internal/deviations" - "github.com/openconfig/featureprofiles/internal/fptest" - "github.com/openconfig/featureprofiles/internal/gribi" - "github.com/openconfig/gribigo/chk" - "github.com/openconfig/gribigo/constants" - "github.com/openconfig/gribigo/fluent" - "github.com/openconfig/ondatra" - "github.com/openconfig/ondatra/gnmi" - "github.com/openconfig/ondatra/gnmi/oc" - "github.com/openconfig/ygot/ygot" -) - -type attributes struct { - attrs.Attributes - numSubIntf uint32 - ip func(vlan uint8) string - gateway func(vlan uint8) string -} - -type nhInfo struct { - index uint64 - weight uint64 -} - -const ( - ipv4EntryPrefix = "203.0.113.0/32" - ipv4FlowIP = "203.0.113.0" - innerSrcIPv4Start = "198.18.0.0" - innerDstIPv4Start = "198.19.0.0" - ipv4PrefixLen = 30 - ipv4FlowCount = 65000 - nhEntryIP1 = "192.0.2.111" - nhEntryIP2 = "192.0.2.222" - nonDefaultVRF = "VRF-1" - policyName = "redirect-to-VRF1" - ipipProtocol = 4 -) - -var ( - dutPort1 = attributes{ - Attributes: attrs.Attributes{ - Desc: "dutPort1", - Name: "port1", - IPv4: dutPort1IPv4(0), - IPv4Len: ipv4PrefixLen, - }, - numSubIntf: 0, - ip: dutPort1IPv4, - } - - atePort1 = attributes{ - Attributes: attrs.Attributes{ - Name: "port1", - IPv4: atePort1IPv4(0), - IPv4Len: ipv4PrefixLen, - }, - numSubIntf: 0, - ip: atePort1IPv4, - gateway: dutPort1IPv4, - } - - dutPort2 = attributes{ - Attributes: attrs.Attributes{ - Desc: "dutPort2", - Name: "port2", - IPv4: dutPort2IPv4(0), - IPv4Len: ipv4PrefixLen, - }, - numSubIntf: 18, - ip: dutPort2IPv4, - } - - atePort2 = attributes{ - Attributes: attrs.Attributes{ - Name: "port2", - IPv4: atePort2IPv4(0), - IPv4Len: ipv4PrefixLen, - }, - numSubIntf: 18, - ip: atePort2IPv4, - gateway: dutPort2IPv4, - } - - // nhgIPv4EntryMap maps NextHopGroups to the ipv4 entries pointing to that NextHopGroup. - nhgIPv4EntryMap = map[uint64]string{ - 1: ipv4EntryPrefix, - 2: cidr(nhEntryIP1, 32), - 3: cidr(nhEntryIP2, 32), - } - // 'tolerance' is the maximum difference that is allowed between the observed - // traffic distribution and the required traffic distribution. - tolerance = 0.2 -) - -func TestMain(m *testing.M) { - fptest.RunTests(m) -} - -// dutPort1IPv4 returns ip address 192.0.2.1, for every vlanID. -func dutPort1IPv4(uint8) string { - return "192.0.2.1" -} - -// atePort1IPv4 returns ip address 192.0.2.2, for every vlanID -func atePort1IPv4(uint8) string { - return "192.0.2.2" -} - -// dutPort2IPv4 returns ip addresses starting 192.0.2.5, increasing by 4 -// for every vlanID. -func dutPort2IPv4(vlan uint8) string { - return fmt.Sprintf("192.0.2.%d", vlan*4+5) -} - -// atePort2IPv4 returns ip addresses starting 192.0.2.6, increasing by 4 -// for every vlanID. -func atePort2IPv4(vlan uint8) string { - return fmt.Sprintf("192.0.2.%d", vlan*4+6) -} - -// cidr taks as input the IPv4 address and the Mask and returns the IP string in -// CIDR notation. -func cidr(ipv4 string, ones int) string { - return ipv4 + "/" + strconv.Itoa(ones) -} - -// filterPacketReceived uses ATE:EgressTracking bucket counters to create a map -// with bucket-label as the Key and the percentage of packets-received for that -// bucket as the Value. -func filterPacketReceived(t *testing.T, flow string, ate *ondatra.ATEDevice) map[string]float64 { - t.Helper() - - flowPath := gnmi.OC().Flow(flow) - filters := gnmi.GetAll(t, ate, flowPath.EgressTrackingAny().State()) - - inPkts := map[string]uint64{} - for _, f := range filters { - inPkts[f.GetFilter()] = f.GetCounters().GetInPkts() - } - inPct := map[string]float64{} - total := gnmi.Get(t, ate, flowPath.Counters().OutPkts().State()) - for k, v := range inPkts { - inPct[k] = (float64(v) / float64(total)) * 100.0 - } - return inPct -} - -// configureGRIBIClient configures a new GRIBI client with PRESERVE and FIB_ACK. -func configureGRIBIClient(t *testing.T, dut *ondatra.DUTDevice) *fluent.GRIBIClient { - t.Helper() - gribic := dut.RawAPIs().GRIBI(t) - - // Configure the gRIBI client. - c := fluent.NewClient() - c.Connection(). - WithStub(gribic). - WithRedundancyMode(fluent.ElectedPrimaryClient). - WithInitialElectionID(1 /* low */, 0 /* hi */). - WithPersistence(). - WithFIBACK() - - return c -} - -// nextHopEntry configures a fluent.GRIBIEntry for a NextHopEntry. -func nextHopEntry(index uint64, networkInstance string, ipAddr string) fluent.GRIBIEntry { - return fluent.NextHopEntry(). - WithNetworkInstance(networkInstance). - WithIndex(index). - WithIPAddress(ipAddr) -} - -// nextHopGroupEntry configures a fluent.GRIBIEntry for a NextHopGroupEntry. -func nextHopGroupEntry(index uint64, networkInstance string, nhs []nhInfo) fluent.GRIBIEntry { - x := fluent.NextHopGroupEntry(). - WithNetworkInstance(networkInstance). - WithID(index) - for _, nh := range nhs { - x.AddNextHop(nh.index, nh.weight) - } - return x -} - -// ipv4Entry configures a fluent.GRIBIEntry for an IPv4Entry. -func ipv4Entry(prefix string, networkInstance string, nhgIndex uint64, nextHopGroupNetworkInstance string) fluent.GRIBIEntry { - return fluent.IPv4Entry(). - WithPrefix(prefix). - WithNetworkInstance(networkInstance). - WithNextHopGroup(nhgIndex). - WithNextHopGroupNetworkInstance(nextHopGroupNetworkInstance) -} - -// awaitTimeout calls a fluent client Await, adding a timeout to the context. -func awaitTimeout(ctx context.Context, c *fluent.GRIBIClient, t testing.TB, timeout time.Duration) error { - t.Helper() - subctx, cancel := context.WithTimeout(ctx, timeout) - defer cancel() - return c.Await(subctx, t) -} - -// configSubinterfaceDUT configures the Sub Interfaces of an Interfaces, -// starting from Sub Interface 1. Each Subinterface is configured with a -// unique VlanID starting from 1 and an IP address. The starting IP Address -// for Subinterface(1) = dutPort.ip(1) = dutPort.ip + 4. -func (a *attributes) configSubinterfaceDUT(t *testing.T, intf *oc.Interface, dut *ondatra.DUTDevice) { - t.Helper() - if deviations.RequireRoutedSubinterface0(dut) { - s0 := intf.GetOrCreateSubinterface(0).GetOrCreateIpv4() - s0.Enabled = ygot.Bool(true) - } - for i := uint32(1); i <= a.numSubIntf; i++ { - ip := a.ip(uint8(i)) - - s := intf.GetOrCreateSubinterface(i) - if deviations.InterfaceEnabled(dut) { - s.Enabled = ygot.Bool(true) - } - if deviations.DeprecatedVlanID(dut) { - s.GetOrCreateVlan().VlanId = oc.UnionUint16(i) - } else { - s.GetOrCreateVlan().GetOrCreateMatch().GetOrCreateSingleTagged().VlanId = ygot.Uint16(uint16(i)) - } - s4 := s.GetOrCreateIpv4() - if deviations.InterfaceEnabled(dut) && !deviations.IPv4MissingEnabled(dut) { - s4.Enabled = ygot.Bool(true) - } - s4a := s4.GetOrCreateAddress(ip) - s4a.PrefixLength = ygot.Uint8(a.IPv4Len) - t.Logf("Adding DUT Subinterface with ID: %d, Vlan ID: %d and IPv4 address: %s", i, i, ip) - } -} - -// configInterfaceDUT configures the DUT interface with the provided IP Address. -// Sub Interfaces are also configured if numSubIntf > 0. -func (a *attributes) configInterfaceDUT(t *testing.T, d *ondatra.DUTDevice) { - t.Helper() - p := d.Port(t, a.Name) - i := &oc.Interface{Name: ygot.String(p.Name())} - - if a.numSubIntf > 0 { - i.Description = ygot.String(a.Desc) - i.Type = oc.IETFInterfaces_InterfaceType_ethernetCsmacd - if deviations.InterfaceEnabled(d) { - i.Enabled = ygot.Bool(true) - } - } else { - i = a.NewOCInterface(p.Name(), d) - } - - if deviations.ExplicitPortSpeed(d) { - i.GetOrCreateEthernet().PortSpeed = fptest.GetIfSpeed(t, p) - } - - a.configSubinterfaceDUT(t, i, d) - intfPath := gnmi.OC().Interface(p.Name()) - gnmi.Replace(t, d, intfPath.Config(), i) - fptest.LogQuery(t, "DUT", intfPath.Config(), gnmi.Get(t, d, intfPath.Config())) -} - -func configureDUT(t *testing.T, dut *ondatra.DUTDevice) { - // configure NI. - configureNetworkInstance(t, dut) - - // Configure DUT ports. - dutPort1.configInterfaceDUT(t, dut) - dutPort2.configInterfaceDUT(t, dut) - - // assign subinterfaces to DEFAULT network instance if needed (deviation-based). - dutPort1.assignSubifsToDefaultNetworkInstance(t, dut) - dutPort2.assignSubifsToDefaultNetworkInstance(t, dut) - - // apply PBF to src interface. - dp1 := dut.Port(t, dutPort1.Name) - applyForwardingPolicy(t, dp1.Name()) -} - -// configureNetworkInstance creates and configures non-default and default NIs. -func configureNetworkInstance(t *testing.T, d *ondatra.DUTDevice) { - t.Helper() - - // configure non-default VRF - ni := &oc.NetworkInstance{ - Name: ygot.String(nonDefaultVRF), - Type: oc.NetworkInstanceTypes_NETWORK_INSTANCE_TYPE_L3VRF, - } - dni := gnmi.OC().NetworkInstance(nonDefaultVRF) - gnmi.Replace(t, d, dni.Config(), ni) - fptest.LogQuery(t, "NI", dni.Config(), gnmi.Get(t, d, dni.Config())) - - // configure PBF in DEFAULT vrf - defNIPath := gnmi.OC().NetworkInstance(deviations.DefaultNetworkInstance(d)) - fptest.ConfigureDefaultNetworkInstance(t, d) - gnmi.Replace(t, d, defNIPath.PolicyForwarding().Config(), configurePBF(d)) - -} - -// assignSubifsToDefaultNetworkInstance assign subinterfaces to the default network instance when ExplicitInterfaceInDefaultVRF is enabled. -func (a *attributes) assignSubifsToDefaultNetworkInstance(t *testing.T, d *ondatra.DUTDevice) { - p := d.Port(t, a.Name) - if deviations.ExplicitInterfaceInDefaultVRF(d) { - if a.numSubIntf == 0 { - fptest.AssignToNetworkInstance(t, d, p.Name(), deviations.DefaultNetworkInstance(d), 0) - } else { - for i := uint32(1); i <= a.numSubIntf; i++ { - fptest.AssignToNetworkInstance(t, d, p.Name(), deviations.DefaultNetworkInstance(d), i) - } - } - } -} - -// configurePBF returns a fully configured network-instance PF struct. -func configurePBF(dut *ondatra.DUTDevice) *oc.NetworkInstance_PolicyForwarding { - d := &oc.Root{} - ni := d.GetOrCreateNetworkInstance(deviations.DefaultNetworkInstance(dut)) - pf := ni.GetOrCreatePolicyForwarding() - vrfPolicy := pf.GetOrCreatePolicy(policyName) - vrfPolicy.SetType(oc.Policy_Type_VRF_SELECTION_POLICY) - vrfPolicy.GetOrCreateRule(1).GetOrCreateIpv4().Protocol = oc.UnionUint8(ipipProtocol) - vrfPolicy.GetOrCreateRule(1).GetOrCreateAction().NetworkInstance = ygot.String(nonDefaultVRF) - return pf -} - -// applyForwardingPolicy applies the forwarding policy on the interface. -func applyForwardingPolicy(t *testing.T, ingressPort string) { - t.Logf("Applying forwarding policy on interface %v ... ", ingressPort) - d := &oc.Root{} - dut := ondatra.DUT(t, "dut") - interfaceID := ingressPort - if deviations.InterfaceRefInterfaceIDFormat(dut) { - interfaceID = ingressPort + ".0" - } - pfPath := gnmi.OC().NetworkInstance(deviations.DefaultNetworkInstance(dut)).PolicyForwarding().Interface(interfaceID) - pfCfg := d.GetOrCreateNetworkInstance(deviations.DefaultNetworkInstance(dut)).GetOrCreatePolicyForwarding().GetOrCreateInterface(interfaceID) - pfCfg.ApplyVrfSelectionPolicy = ygot.String(policyName) - pfCfg.GetOrCreateInterfaceRef().Interface = ygot.String(ingressPort) - pfCfg.GetOrCreateInterfaceRef().Subinterface = ygot.Uint32(0) - if deviations.InterfaceRefConfigUnsupported(dut) { - pfCfg.InterfaceRef = nil - } - gnmi.Replace(t, dut, pfPath.Config(), pfCfg) -} - -// ConfigureATE configures Ethernet + IPv4 on the ATE. If the number of -// Subinterfaces(numSubIntf) > 0, we then create additional sub-interfaces -// each with a unique VlanID starting from 1. The IPv4 addresses start with -// ATE:Port.IPv4 and then nextIP(ATE:Port.IPv4, 4) for each sub interface. -func (a *attributes) ConfigureATE(t *testing.T, top *ondatra.ATETopology, ate *ondatra.ATEDevice) { - t.Helper() - p := ate.Port(t, a.Name) - // Configure source port on ATE : Port1. - if a.numSubIntf == 0 { - ip := a.ip(0) - gateway := a.gateway(0) - intf := top.AddInterface(ip).WithPort(p) - intf.IPv4().WithAddress(cidr(ip, 30)) - intf.IPv4().WithDefaultGateway(gateway) - t.Logf("Adding ATE Ipv4 address: %s with gateway: %s", cidr(ip, 30), gateway) - } - // Configure destination port on ATE : Port2. - for i := uint32(1); i <= a.numSubIntf; i++ { - ip := a.ip(uint8(i)) - gateway := a.gateway(uint8(i)) - intf := top.AddInterface(ip).WithPort(p) - intf.IPv4().WithAddress(cidr(ip, 30)) - intf.IPv4().WithDefaultGateway(gateway) - intf.Ethernet().WithVLANID(uint16(i)) - t.Logf("Adding ATE Ipv4 address: %s with gateway: %s and VlanID: %d", cidr(ip, 30), gateway, i) - } -} - -// testTraffic creates a traffic flow with ATE source & destination endpoints -// and configures a VlanID filter for output frames. The IPv4 header for the -// flow contains the ATE:Port1 address as source and the configured gRIBI- -// IndirectEntry as the destination. The function also takes as input a map of -// that is wanted and compares it to the actual -// traffic test result. -func testTraffic(t *testing.T, ate *ondatra.ATEDevice, top *ondatra.ATETopology) map[string]float64 { - allIntf := top.Interfaces() - - // ATE source endpoint. - srcEndPoint := allIntf[atePort1.IPv4] - - // ATE destination endpoints. - dstEndPoints := []ondatra.Endpoint{} - for i := uint32(1); i <= atePort2.numSubIntf; i++ { - dstIP := atePort2.ip(uint8(i)) - dstEndPoints = append(dstEndPoints, allIntf[dstIP]) - } - - // Configure Ethernet+IPv4 headers. - ethHeader := ondatra.NewEthernetHeader() - ipv4Header := ondatra.NewIPv4Header() - ipv4Header.WithSrcAddress(atePort1.IPv4) - ipv4Header.WithDstAddress(ipv4FlowIP) - innerIpv4Header := ondatra.NewIPv4Header() - innerIpv4Header.SrcAddressRange().WithMin(innerSrcIPv4Start).WithCount(ipv4FlowCount).WithStep("0.0.0.1") - innerIpv4Header.DstAddressRange().WithMin(innerDstIPv4Start).WithCount(ipv4FlowCount).WithStep("0.0.0.1") - - // Ethernet header: - // - Destination MAC (6 octets) - // - Source MAC (6 octets) - // - Optional 802.1q VLAN tag (4 octets) - // - Frame size (2 octets) - flow := ate.Traffic().NewFlow("flow"). - WithSrcEndpoints(srcEndPoint). - WithDstEndpoints(dstEndPoints...). - WithHeaders(ethHeader, ipv4Header, innerIpv4Header) - - // VlanID is the last 12 bits in the 802.1q VLAN tag. - // Offset for VlanID: ((6+6+4) * 8)-12 = 116. - flow.EgressTracking().WithOffset(116).WithWidth(12).WithCount(18) - - // Run traffic for 2 minutes. - ate.Traffic().Start(t, flow) - time.Sleep(2 * time.Minute) - ate.Traffic().Stop(t) - - gnmi.Await(t, ate, gnmi.OC().Flow("flow").LossPct().State(), time.Minute, 0) - - // Compare traffic distribution with the wanted results. - results := filterPacketReceived(t, "flow", ate) - t.Logf("Filters: %v", results) - return results -} - -// aftNextHopWeights queries AFT telemetry using Get() and returns -// the weights. If not-found, an empty list is returned. -func aftNextHopWeights(t *testing.T, dut *ondatra.DUTDevice, nhg uint64, networkInstance string) []uint64 { - aft := gnmi.Get(t, dut, gnmi.OC().NetworkInstance(networkInstance).Afts().State()) - var nhgD *oc.NetworkInstance_Afts_NextHopGroup - for _, nhgData := range aft.NextHopGroup { - if nhgData.GetProgrammedId() == nhg { - nhgD = nhgData - break - } - } - - if nhgD == nil { - return []uint64{} - } - - got := []uint64{} - for _, nhD := range nhgD.NextHop { - got = append(got, nhD.GetWeight()) - } - - return got -} - -// testBasicHierarchicalWeight tests and validates traffic through 4 Vlans. -func testBasicHierarchicalWeight(ctx context.Context, t *testing.T, dut *ondatra.DUTDevice, - ate *ondatra.ATEDevice, top *ondatra.ATETopology, gRIBI *fluent.GRIBIClient) { - defaultVRF := deviations.DefaultNetworkInstance(dut) - - // Set up NH#10, NH#11, NHG#2, IPv4Entry(192.0.2.111). - nh10 := nextHopEntry(10, defaultVRF, atePort2.ip(1)) - nh11 := nextHopEntry(11, defaultVRF, atePort2.ip(2)) - nhg2 := nextHopGroupEntry(2, defaultVRF, []nhInfo{{index: 10, weight: 1}, {index: 11, weight: 3}}) - ipEntry2 := ipv4Entry(nhgIPv4EntryMap[2], defaultVRF, 2, defaultVRF) - - gRIBI.Modify().AddEntry(t, nh10, nh11, nhg2, ipEntry2) - - // Set up NH#100, NH#101, NHG#3, IPv4Entry(192.0.2.222). - nh100 := nextHopEntry(100, defaultVRF, atePort2.ip(3)) - nh101 := nextHopEntry(101, defaultVRF, atePort2.ip(4)) - nhg3 := nextHopGroupEntry(3, defaultVRF, []nhInfo{{index: 100, weight: 3}, {index: 101, weight: 5}}) - ipEntry3 := ipv4Entry(nhgIPv4EntryMap[3], defaultVRF, 3, defaultVRF) - - gRIBI.Modify().AddEntry(t, nh100, nh101, nhg3, ipEntry3) - - // Set up NH#1, NH#2, NHG#1, IPv4Entry(198.18.196.1/22). - nh1 := nextHopEntry(1, defaultVRF, nhEntryIP1) - nh2 := nextHopEntry(2, defaultVRF, nhEntryIP2) - nhg1 := nextHopGroupEntry(1, defaultVRF, []nhInfo{{index: 1, weight: 1}, {index: 2, weight: 3}}) - ipEntry1 := ipv4Entry(nhgIPv4EntryMap[1], nonDefaultVRF, 1, defaultVRF) - - gRIBI.Modify().AddEntry(t, nh1, nh2, nhg1, ipEntry1) - - if err := awaitTimeout(ctx, gRIBI, t, time.Minute); err != nil { - t.Fatalf("Could not program entries via gRIBI, got err: %v", err) - } - - // Validate entries were installed in FIB. - for _, route := range nhgIPv4EntryMap { - chk.HasResult(t, gRIBI.Results(t), - fluent.OperationResult(). - WithIPv4Operation(route). - WithOperationType(constants.Add). - WithProgrammingResult(fluent.InstalledInFIB). - AsResult(), - chk.IgnoreOperationID(), - ) - } - - // Test traffic flows correctly and - wantWeights := map[string]float64{ - "1": 6.25, - "2": 18.75, - "3": 28.12, - "4": 46.87, - } - t.Run("testTraffic", func(t *testing.T) { - got := testTraffic(t, ate, top) - if diff := cmp.Diff(wantWeights, got, cmpopts.EquateApprox(0, tolerance)); diff != "" { - t.Errorf("Packet distribution ratios -want,+got:\n%s", diff) - } - }) - - t.Run("validateAFTWeights", func(t *testing.T) { - for nhg, weights := range map[uint64][]uint64{ - 2: {1, 3}, - 3: {3, 5}, - } { - got := aftNextHopWeights(t, dut, nhg, defaultVRF) - ok := cmp.Equal(weights, got, cmpopts.SortSlices(func(a, b uint64) bool { return a < b })) - if !ok { - t.Errorf("Valid weights not present for NI: %s, NHG: %d, got: %v, want: %v", defaultVRF, nhg, got, weights) - } - } - }) - - // Flush gRIBI routes after test. - if err := gribi.FlushAll(gRIBI); err != nil { - t.Error(err) - } -} - -// testHierarchicalWeightBoundaryScenario tests and validates traffic through all 18 Vlans. -func testHierarchicalWeightBoundaryScenario(ctx context.Context, t *testing.T, dut *ondatra.DUTDevice, - ate *ondatra.ATEDevice, top *ondatra.ATETopology, gRIBI *fluent.GRIBIClient) { - defaultVRF := deviations.DefaultNetworkInstance(dut) - - // Set up NH#10, NH#11, NHG#2, IPv4Entry(192.0.2.111). - nh10 := nextHopEntry(10, defaultVRF, atePort2.ip(1)) - nh11 := nextHopEntry(11, defaultVRF, atePort2.ip(2)) - nhg2 := nextHopGroupEntry(2, defaultVRF, []nhInfo{{index: 10, weight: 3}, {index: 11, weight: 5}}) - ipEntry2 := ipv4Entry(nhgIPv4EntryMap[2], defaultVRF, 2, defaultVRF) - - gRIBI.Modify().AddEntry(t, nh10, nh11, nhg2, ipEntry2) - - // Set up NH#100..NH#116, NHG#3, IPv4Entry(192.0.2.222). - nextHopWeights := []nhInfo{} - nhIdx := uint64(100) - gribiEntries := []fluent.GRIBIEntry{} - for i := 0; i < 16; i++ { - nh := nextHopEntry(nhIdx, defaultVRF, atePort2.ip(uint8(3+i))) - gribiEntries = append(gribiEntries, nh) - if i == 0 { - nextHopWeights = append(nextHopWeights, nhInfo{index: nhIdx, weight: 1}) - } else { - nextHopWeights = append(nextHopWeights, nhInfo{index: nhIdx, weight: 16}) - } - nhIdx++ - } - nhg3 := nextHopGroupEntry(3, defaultVRF, nextHopWeights) - ipEntry3 := ipv4Entry(nhgIPv4EntryMap[3], defaultVRF, 3, defaultVRF) - gribiEntries = append(gribiEntries, nhg3, ipEntry3) - - gRIBI.Modify().AddEntry(t, gribiEntries...) - - // Set up NH#1, NH#2, NHG#1, IPv4Entry(198.18.196.1/22). - nh1 := nextHopEntry(1, defaultVRF, nhEntryIP1) - nh2 := nextHopEntry(2, defaultVRF, nhEntryIP2) - nhg1 := nextHopGroupEntry(1, defaultVRF, []nhInfo{{index: 1, weight: 1}, {index: 2, weight: 31}}) - ipEntry1 := ipv4Entry(nhgIPv4EntryMap[1], nonDefaultVRF, 1, defaultVRF) - - gRIBI.Modify().AddEntry(t, nh1, nh2, nhg1, ipEntry1) - - if err := awaitTimeout(ctx, gRIBI, t, time.Minute); err != nil { - t.Fatalf("Could not program entries via gRIBI, got err: %v", err) - } - - // Validate entries were installed in FIB. - for _, route := range nhgIPv4EntryMap { - chk.HasResult(t, gRIBI.Results(t), - fluent.OperationResult(). - WithIPv4Operation(route). - WithOperationType(constants.Add). - WithProgrammingResult(fluent.InstalledInFIB). - AsResult(), - chk.IgnoreOperationID(), - ) - } - - wantWeights := map[string]float64{ - "1": 1.171, - "2": 1.953, - "3": 0.402, - } - // 6.432 weight for vlans 4 to 18. - for i := 4; i <= 18; i++ { - wantWeights[strconv.Itoa(i)] = 6.432 - } - t.Run("testTraffic", func(t *testing.T) { - got := testTraffic(t, ate, top) - - if deviations.HierarchicalWeightResolutionTolerance(dut) != tolerance { - tolerance = deviations.HierarchicalWeightResolutionTolerance(dut) - } - if diff := cmp.Diff(wantWeights, got, cmpopts.EquateApprox(0, tolerance)); diff != "" { - t.Errorf("Packet distribution ratios -want,+got:\n%s", diff) - } - }) - - t.Run("validateAFTWeights", func(t *testing.T) { - for nhg, weights := range map[uint64][]uint64{ - 2: {3, 5}, - 3: {1, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16}, - } { - got := aftNextHopWeights(t, dut, nhg, defaultVRF) - ok := cmp.Equal(weights, got, cmpopts.SortSlices(func(a, b uint64) bool { return a < b })) - if !ok { - t.Errorf("Valid weights not present for NI: %s, NHG: %d, got: %v, want: %v", defaultVRF, nhg, got, weights) - } - } - }) - - // Flush gRIBI routes after test. - if err := gribi.FlushAll(gRIBI); err != nil { - t.Error(err) - } -} - -func TestHierarchicalWeightResolution(t *testing.T) { - dut := ondatra.DUT(t, "dut") - ate := ondatra.ATE(t, "ate") - ctx := context.Background() - - // configure DUT. - configureDUT(t, dut) - - // Configure ATE ports and start Ethernet+IPv4. - top := ate.Topology().New() - atePort1.ConfigureATE(t, top, ate) - atePort2.ConfigureATE(t, top, ate) - top.Push(t) - top.StartProtocols(t) - - // Configure gRIBI with FIB_ACK. - gRIBI := configureGRIBIClient(t, dut) - - gRIBI.Start(ctx, t) - defer gRIBI.Stop(t) - - defer func() { - // Flush all gRIBI routes after test. - if err := gribi.FlushAll(gRIBI); err != nil { - t.Error(err) - } - }() - - gRIBI.StartSending(ctx, t) - if err := awaitTimeout(ctx, gRIBI, t, time.Minute); err != nil { - t.Fatalf("Await got error during session negotiation for gRIBI: %v", err) - } - gribi.BecomeLeader(t, gRIBI) - - // Flush existing gRIBI routes before test. - if err := gribi.FlushAll(gRIBI); err != nil { - t.Fatal(err) - } - - t.Run("TestBasicHierarchicalWeight", func(t *testing.T) { - testBasicHierarchicalWeight(ctx, t, dut, ate, top, gRIBI) - }) - - t.Run("TestHierarchicalWeightBoundaryScenario", func(t *testing.T) { - testHierarchicalWeightBoundaryScenario(ctx, t, dut, ate, top, gRIBI) - }) - - top.StopProtocols(t) -} diff --git a/feature/gribi/ate_tests/hierarchical_weight_resolution_test/metadata.textproto b/feature/gribi/ate_tests/hierarchical_weight_resolution_test/metadata.textproto deleted file mode 100644 index fdd67d8cbab..00000000000 --- a/feature/gribi/ate_tests/hierarchical_weight_resolution_test/metadata.textproto +++ /dev/null @@ -1,48 +0,0 @@ -# proto-file: github.com/openconfig/featureprofiles/proto/metadata.proto -# proto-message: Metadata - -uuid: "93695155-2898-47d4-9bbb-ac40611d3882" -plan_id: "TE-3.3" -description: "Hierarchical weight resolution" -testbed: TESTBED_DUT_ATE_2LINKS -platform_exceptions: { - platform: { - vendor: CISCO - } - deviations: { - hierarchical_weight_resolution_tolerance: 1.5 - ipv4_missing_enabled: true - interface_ref_interface_id_format: true - } -} -platform_exceptions: { - platform: { - vendor: JUNIPER - } - deviations: { - hierarchical_weight_resolution_tolerance: 0.4 - explicit_interface_ref_definition: true - } -} -platform_exceptions: { - platform: { - vendor: NOKIA - } - deviations: { - explicit_port_speed: true - explicit_interface_in_default_vrf: true - interface_enabled: true - } -} -platform_exceptions: { - platform: { - vendor: ARISTA - } - deviations: { - omit_l2_mtu: true - deprecated_vlan_id: true - interface_enabled: true - default_network_instance: "default" - } -} -tags: TAGS_TRANSIT diff --git a/feature/experimental/gribi/otg_tests/backup_nhg_action/README.md b/feature/gribi/otg_tests/backup_nhg_action/README.md similarity index 95% rename from feature/experimental/gribi/otg_tests/backup_nhg_action/README.md rename to feature/gribi/otg_tests/backup_nhg_action/README.md index c500f4c352d..5a99843fca5 100644 --- a/feature/experimental/gribi/otg_tests/backup_nhg_action/README.md +++ b/feature/gribi/otg_tests/backup_nhg_action/README.md @@ -94,15 +94,18 @@ Different test scenarios requires different setups. traffic with decapsulated traffic with destination IP as `InnerDstIP_1` at ATE port-4. -## Config Parameter coverage - -No new configuration covered. - -## Telemetry Parameter coverage - -No new telemetry covered. - -## Protocol/RPC Parameter coverage +## OpenConfig Path and RPC Coverage +```yaml +rpcs: + gnmi: + gNMI.Get: + gNMI.Set: + gNMI.Subscribe: + gribi: + gRIBI.Get: + gRIBI.Modify: + gRIBI.Flush: +``` ## Minimum DUT platform requirement diff --git a/feature/experimental/gribi/otg_tests/backup_nhg_action/backup_nhg_action_test.go b/feature/gribi/otg_tests/backup_nhg_action/backup_nhg_action_test.go similarity index 100% rename from feature/experimental/gribi/otg_tests/backup_nhg_action/backup_nhg_action_test.go rename to feature/gribi/otg_tests/backup_nhg_action/backup_nhg_action_test.go diff --git a/feature/experimental/gribi/otg_tests/backup_nhg_action/metadata.textproto b/feature/gribi/otg_tests/backup_nhg_action/metadata.textproto similarity index 100% rename from feature/experimental/gribi/otg_tests/backup_nhg_action/metadata.textproto rename to feature/gribi/otg_tests/backup_nhg_action/metadata.textproto diff --git a/feature/experimental/gribi/otg_tests/backup_nhg_action_pbf/README.md b/feature/gribi/otg_tests/backup_nhg_action_pbf/README.md similarity index 100% rename from feature/experimental/gribi/otg_tests/backup_nhg_action_pbf/README.md rename to feature/gribi/otg_tests/backup_nhg_action_pbf/README.md diff --git a/feature/experimental/gribi/otg_tests/backup_nhg_action_pbf/backup_nhg_action_pbf_test.go b/feature/gribi/otg_tests/backup_nhg_action_pbf/backup_nhg_action_pbf_test.go similarity index 100% rename from feature/experimental/gribi/otg_tests/backup_nhg_action_pbf/backup_nhg_action_pbf_test.go rename to feature/gribi/otg_tests/backup_nhg_action_pbf/backup_nhg_action_pbf_test.go diff --git a/feature/experimental/gribi/otg_tests/backup_nhg_action_pbf/metadata.textproto b/feature/gribi/otg_tests/backup_nhg_action_pbf/metadata.textproto similarity index 100% rename from feature/experimental/gribi/otg_tests/backup_nhg_action_pbf/metadata.textproto rename to feature/gribi/otg_tests/backup_nhg_action_pbf/metadata.textproto diff --git a/feature/gribi/otg_tests/backup_ngp_multiple_nh_pbf_test/README.md b/feature/gribi/otg_tests/backup_nhg_multiple_nh_pbf_test/README.md similarity index 100% rename from feature/gribi/otg_tests/backup_ngp_multiple_nh_pbf_test/README.md rename to feature/gribi/otg_tests/backup_nhg_multiple_nh_pbf_test/README.md diff --git a/feature/gribi/otg_tests/backup_ngp_multiple_nh_pbf_test/backup_nhg_multiple_nh_pbf_test.go b/feature/gribi/otg_tests/backup_nhg_multiple_nh_pbf_test/backup_nhg_multiple_nh_pbf_test.go similarity index 100% rename from feature/gribi/otg_tests/backup_ngp_multiple_nh_pbf_test/backup_nhg_multiple_nh_pbf_test.go rename to feature/gribi/otg_tests/backup_nhg_multiple_nh_pbf_test/backup_nhg_multiple_nh_pbf_test.go diff --git a/feature/gribi/otg_tests/backup_ngp_multiple_nh_pbf_test/metadata.textproto b/feature/gribi/otg_tests/backup_nhg_multiple_nh_pbf_test/metadata.textproto similarity index 100% rename from feature/gribi/otg_tests/backup_ngp_multiple_nh_pbf_test/metadata.textproto rename to feature/gribi/otg_tests/backup_nhg_multiple_nh_pbf_test/metadata.textproto diff --git a/feature/experimental/backup_nhg/otg_tests/backup_nhg_test/README.md b/feature/gribi/otg_tests/backup_nhg_single_nh_test/README.md similarity index 82% rename from feature/experimental/backup_nhg/otg_tests/backup_nhg_test/README.md rename to feature/gribi/otg_tests/backup_nhg_single_nh_test/README.md index bf5f86fcab1..0d940b7de61 100644 --- a/feature/experimental/backup_nhg/otg_tests/backup_nhg_test/README.md +++ b/feature/gribi/otg_tests/backup_nhg_single_nh_test/README.md @@ -31,21 +31,18 @@ containing a single NH. * Interface DUT port-2 is disabled. * Remove the entry for 192.0.2.254/32. -## Config Parameter coverage - -No new configuration covered. - -## Telemetry Parameter coverage - -No new telemetry covered. - -## Protocol/RPC Parameter coverage - -* gRIBI - * Modify - * ModifyRequest - * NextHopGroup - * backup_nexthop_group +## OpenConfig Path and RPC Coverage +```yaml +rpcs: + gnmi: + gNMI.Get: + gNMI.Set: + gNMI.Subscribe: + gribi: + gRIBI.Get: + gRIBI.Modify: + gRIBI.Flush: +``` ## Minimum DUT platform requirement diff --git a/feature/experimental/backup_nhg/otg_tests/backup_nhg_test/backup_nhg_test.go b/feature/gribi/otg_tests/backup_nhg_single_nh_test/backup_nhg_test.go similarity index 100% rename from feature/experimental/backup_nhg/otg_tests/backup_nhg_test/backup_nhg_test.go rename to feature/gribi/otg_tests/backup_nhg_single_nh_test/backup_nhg_test.go diff --git a/feature/experimental/backup_nhg/otg_tests/backup_nhg_test/metadata.textproto b/feature/gribi/otg_tests/backup_nhg_single_nh_test/metadata.textproto similarity index 100% rename from feature/experimental/backup_nhg/otg_tests/backup_nhg_test/metadata.textproto rename to feature/gribi/otg_tests/backup_nhg_single_nh_test/metadata.textproto diff --git a/feature/gribi/otg_tests/base_hierarchical_nhg_update/base_hierarchical_nhg_update_test.go b/feature/gribi/otg_tests/base_hierarchical_nhg_update/base_hierarchical_nhg_update_test.go index ae9289fb225..a2a46151860 100644 --- a/feature/gribi/otg_tests/base_hierarchical_nhg_update/base_hierarchical_nhg_update_test.go +++ b/feature/gribi/otg_tests/base_hierarchical_nhg_update/base_hierarchical_nhg_update_test.go @@ -323,15 +323,16 @@ func testBaseHierarchialNHG(ctx context.Context, t *testing.T, args *testArgs) { var op1, op3 *client.OpResult if deviations.GRIBIMACOverrideWithStaticARP(args.dut) || deviations.GRIBIMACOverrideStaticARPStaticRoute(args.dut) { nh, op1 = gribi.NHEntry(p2NHID, "MACwithInterface", dni, fluent.InstalledInFIB, &gribi.NHOptions{Interface: dutP2, Mac: pMAC, Dest: atePort2DummyIP.IPv4}) - args.client.AddEntries(t, []fluent.GRIBIEntry{nh}, []*client.OpResult{op1}) } else { - args.client.AddNH(t, p2NHID, "MACwithInterface", dni, fluent.InstalledInFIB, &gribi.NHOptions{Interface: dutP2, Mac: pMAC}) + nh, op1 = gribi.NHEntry(p2NHID, "MACwithInterface", dni, fluent.InstalledInFIB, &gribi.NHOptions{Interface: dutP2, Mac: pMAC}) } - args.client.AddNHG(t, virtualIPNHGID, map[uint64]uint64{p2NHID: 1}, dni, fluent.InstalledInFIB) + nhg, op2 := gribi.NHGEntry(virtualIPNHGID, map[uint64]uint64{p2NHID: 1}, dni, fluent.InstalledInFIB) + args.client.AddEntries(t, []fluent.GRIBIEntry{nh, nhg}, []*client.OpResult{op1, op2}) args.client.AddIPv4(t, virtualPfx, virtualIPNHGID, dni, dni, fluent.InstalledInFIB) - args.client.AddNH(t, dstNHID, virtualIP, dni, fluent.InstalledInFIB) - args.client.AddNHG(t, dstNHGID, map[uint64]uint64{dstNHID: 1}, dni, fluent.InstalledInFIB) + nh, op1 = gribi.NHEntry(dstNHID, virtualIP, dni, fluent.InstalledInFIB) + nhg, op2 = gribi.NHGEntry(dstNHGID, map[uint64]uint64{dstNHID: 1}, dni, fluent.InstalledInFIB) + args.client.AddEntries(t, []fluent.GRIBIEntry{nh, nhg}, []*client.OpResult{op1, op2}) if transit { args.client.AddIPv4(t, dstPfx, dstNHGID, niTeVrf111, dni, fluent.InstalledInFIB) @@ -344,17 +345,18 @@ func testBaseHierarchialNHG(ctx context.Context, t *testing.T, args *testArgs) { t.Logf("Adding a new NH via port %v with ID %v", dutP3, p3NHID) if deviations.GRIBIMACOverrideWithStaticARP(args.dut) || deviations.GRIBIMACOverrideStaticARPStaticRoute(args.dut) { nh, op3 = gribi.NHEntry(p3NHID, "MACwithInterface", dni, fluent.InstalledInFIB, &gribi.NHOptions{Interface: dutP3, Mac: pMAC, Dest: atePort3DummyIP.IPv4}) - args.client.AddEntries(t, []fluent.GRIBIEntry{nh}, []*client.OpResult{op3}) } else { - args.client.AddNH(t, p3NHID, "MACwithInterface", dni, fluent.InstalledInFIB, &gribi.NHOptions{Interface: dutP3, Mac: pMAC}) + nh, op3 = gribi.NHEntry(p3NHID, "MACwithInterface", dni, fluent.InstalledInFIB, &gribi.NHOptions{Interface: dutP3, Mac: pMAC}) } t.Logf("Performing implicit in-place replace with two next-hops (NH IDs: %v and %v)", p2NHID, p3NHID) - args.client.AddNHG(t, virtualIPNHGID, map[uint64]uint64{p2NHID: 1, p3NHID: 1}, dni, fluent.InstalledInFIB) + nhg, op2 = gribi.NHGEntry(virtualIPNHGID, map[uint64]uint64{p2NHID: 1, p3NHID: 1}, dni, fluent.InstalledInFIB) + args.client.AddEntries(t, []fluent.GRIBIEntry{nh, nhg}, []*client.OpResult{op1, op3, op2}) validateTrafficFlows(t, args.ate, nil, nil, []gosnappi.Flow{p2Flow, p3Flow}, startTraffic, args.client, false) t.Logf("Performing implicit in-place replace using the next-hop with ID %v", p3NHID) - args.client.AddNHG(t, virtualIPNHGID, map[uint64]uint64{p3NHID: 1}, dni, fluent.InstalledInFIB) + nhg, op2 = gribi.NHGEntry(virtualIPNHGID, map[uint64]uint64{p3NHID: 1}, dni, fluent.InstalledInFIB) + args.client.AddEntries(t, []fluent.GRIBIEntry{nh, nhg}, []*client.OpResult{op3, op2}) validateTrafficFlows(t, args.ate, []gosnappi.Flow{p3Flow}, []gosnappi.Flow{p2Flow}, nil, startTraffic, args.client, false) t.Logf("Performing implicit in-place replace using the next-hop with ID %v", p2NHID) diff --git a/feature/experimental/gribi/otg_tests/dut_daemon_failure/README.md b/feature/gribi/otg_tests/dut_daemon_failure/README.md similarity index 100% rename from feature/experimental/gribi/otg_tests/dut_daemon_failure/README.md rename to feature/gribi/otg_tests/dut_daemon_failure/README.md diff --git a/feature/experimental/gribi/otg_tests/dut_daemon_failure/dut_daemon_failure_test.go b/feature/gribi/otg_tests/dut_daemon_failure/dut_daemon_failure_test.go similarity index 100% rename from feature/experimental/gribi/otg_tests/dut_daemon_failure/dut_daemon_failure_test.go rename to feature/gribi/otg_tests/dut_daemon_failure/dut_daemon_failure_test.go diff --git a/feature/experimental/gribi/otg_tests/dut_daemon_failure/metadata.textproto b/feature/gribi/otg_tests/dut_daemon_failure/metadata.textproto similarity index 100% rename from feature/experimental/gribi/otg_tests/dut_daemon_failure/metadata.textproto rename to feature/gribi/otg_tests/dut_daemon_failure/metadata.textproto diff --git a/feature/experimental/gribi/otg_tests/fib_failed_due_to_hw_res_exhaust_test/README.md b/feature/gribi/otg_tests/fib_failed_due_to_hw_res_exhaust_test/README.md similarity index 85% rename from feature/experimental/gribi/otg_tests/fib_failed_due_to_hw_res_exhaust_test/README.md rename to feature/gribi/otg_tests/fib_failed_due_to_hw_res_exhaust_test/README.md index 94fb48612b5..1cf7be3987d 100644 --- a/feature/experimental/gribi/otg_tests/fib_failed_due_to_hw_res_exhaust_test/README.md +++ b/feature/gribi/otg_tests/fib_failed_due_to_hw_res_exhaust_test/README.md @@ -23,10 +23,18 @@ Validate gRIBI FIB_FAILED functionality. * Pick any route that received FIB_PROGRAMMED. Validate that traffic hitting the route should be forwarded to port2 -## Protocol/RPC Parameter coverage - -* gRIBI - * Flush +## OpenConfig Path and RPC Coverage +```yaml +rpcs: + gnmi: + gNMI.Get: + gNMI.Set: + gNMI.Subscribe: + gribi: + gRIBI.Get: + gRIBI.Modify: + gRIBI.Flush: +``` ## Config parameter coverage diff --git a/feature/experimental/gribi/otg_tests/fib_failed_due_to_hw_res_exhaust_test/fib_failed_due_to_hw_res_exhaust_test.go b/feature/gribi/otg_tests/fib_failed_due_to_hw_res_exhaust_test/fib_failed_due_to_hw_res_exhaust_test.go similarity index 86% rename from feature/experimental/gribi/otg_tests/fib_failed_due_to_hw_res_exhaust_test/fib_failed_due_to_hw_res_exhaust_test.go rename to feature/gribi/otg_tests/fib_failed_due_to_hw_res_exhaust_test/fib_failed_due_to_hw_res_exhaust_test.go index d30e5b5fcff..99761f18b35 100644 --- a/feature/experimental/gribi/otg_tests/fib_failed_due_to_hw_res_exhaust_test/fib_failed_due_to_hw_res_exhaust_test.go +++ b/feature/gribi/otg_tests/fib_failed_due_to_hw_res_exhaust_test/fib_failed_due_to_hw_res_exhaust_test.go @@ -19,6 +19,8 @@ import ( "encoding/binary" "fmt" "net" + "strconv" + "strings" "testing" "time" @@ -27,7 +29,6 @@ import ( "github.com/openconfig/featureprofiles/internal/deviations" "github.com/openconfig/featureprofiles/internal/fptest" "github.com/openconfig/featureprofiles/internal/gribi" - "github.com/openconfig/featureprofiles/internal/otgutils" "github.com/openconfig/gribigo/fluent" "github.com/openconfig/ondatra" "github.com/openconfig/ondatra/gnmi" @@ -64,6 +65,10 @@ const ( tolerance = 50 plenIPv4 = 30 plenIPv6 = 126 + fibPassedTraffic = "fibPassedTraffic" + fibFailedTraffic = "fibFailedTraffic" + dstTrackingf1 = "dstTrackingf1" + dstTrackingf2 = "dstTrackingf2" ) var ( @@ -102,8 +107,9 @@ var ( IPv4Len: plenIPv4, IPv6Len: plenIPv6, } - fibPassedDstRoute string - fibFailedDstRoute string + fibPassedDstRoute string + fibFailedDstRoute string + fibFailedDstRouteInHex string ) func configureBGP(dut *ondatra.DUTDevice) *oc.NetworkInstance_Protocol { @@ -143,7 +149,7 @@ func configureBGP(dut *ondatra.DUTDevice) *oc.NetworkInstance_Protocol { return niProto } -func configureOTG(t *testing.T, otg *otg.OTG) (gosnappi.BgpV6Peer, gosnappi.DeviceIpv6, gosnappi.Config) { +func configureOTG(t *testing.T, otg *otg.OTG, dstIPList []string) (gosnappi.BgpV6Peer, gosnappi.DeviceIpv6, gosnappi.Config) { t.Helper() config := gosnappi.NewConfig() port1 := config.Ports().Add().SetName("port1") @@ -168,6 +174,44 @@ func configureOTG(t *testing.T, otg *otg.OTG) (gosnappi.BgpV6Peer, gosnappi.Devi iDut1Bgp6Peer.SetPeerAddress(iDut1Ipv6.Gateway()).SetAsNumber(ateAS).SetAsType(gosnappi.BgpV6PeerAsType.EBGP) iDut1Bgp6Peer.LearnedInformationFilter().SetUnicastIpv4Prefix(true).SetUnicastIpv6Prefix(true) + flow1ipv4 := config.Flows().Add().SetName(fibPassedTraffic) + flow1ipv4.Metrics().SetEnable(true) + flow1ipv4.TxRx().Device(). + SetTxNames([]string{atePort1.Name + ".IPv4"}). + SetRxNames([]string{atePort2.Name + ".IPv4"}) + flow1ipv4.Size().SetFixed(512) + flow1ipv4.Rate().SetPps(100) + flow1ipv4.Duration().Continuous() + e1 := flow1ipv4.Packet().Add().Ethernet() + e1.Src().SetValue(atePort1.MAC) + v4 := flow1ipv4.Packet().Add().Ipv4() + v4.Src().SetValue(atePort1.IPv4) + v4.Dst().Increment().SetStart(dstIPList[0]) + + flow1ipv4.EgressPacket().Add().Ethernet() + ipTrackingf1 := flow1ipv4.EgressPacket().Add().Ipv4() + ipDstTrackingf1 := ipTrackingf1.Dst().MetricTags().Add() + ipDstTrackingf1.SetName(dstTrackingf1).SetOffset(22).SetLength(10) + + flow2ipv4 := config.Flows().Add().SetName(fibFailedTraffic) + flow2ipv4.Metrics().SetEnable(true) + flow2ipv4.TxRx().Device(). + SetTxNames([]string{atePort1.Name + ".IPv4"}). + SetRxNames([]string{atePort2.Name + ".IPv4"}) + flow2ipv4.Size().SetFixed(512) + flow2ipv4.Rate().SetPps(100) + flow2ipv4.Duration().Continuous() + e2 := flow2ipv4.Packet().Add().Ethernet() + e2.Src().SetValue(atePort1.MAC) + v4Flow2 := flow2ipv4.Packet().Add().Ipv4() + v4Flow2.Src().SetValue(atePort1.IPv4) + v4Flow2.Dst().SetValues(dstIPList[1:]) + + flow2ipv4.EgressPacket().Add().Ethernet() + ipTrackingf2 := flow2ipv4.EgressPacket().Add().Ipv4() + ipDstTrackingf2 := ipTrackingf2.Dst().MetricTags().Add() + ipDstTrackingf2.SetName(dstTrackingf2).SetOffset(22).SetLength(10) + t.Logf("Pushing config to ATE and starting protocols...") otg.PushConfig(t, config) time.Sleep(30 * time.Second) @@ -206,6 +250,8 @@ type testArgs struct { func TestFibFailDueToHwResExhaust(t *testing.T) { ctx := context.Background() dut := ondatra.DUT(t, "dut") + dstIPList := createIPv4Entries(t, fmt.Sprintf("%s/%d", dstIPBlock, 20)) + vipList := createIPv4Entries(t, fmt.Sprintf("%s/%d", vipBlock, 20)) configureDUT(t, dut) configureRoutePolicy(t, dut, "ALLOW", oc.RoutingPolicy_PolicyResultType_ACCEPT_ROUTE) @@ -243,7 +289,7 @@ func TestFibFailDueToHwResExhaust(t *testing.T) { var otgConfig gosnappi.Config var otgBgpPeer gosnappi.BgpV6Peer var otgIPv6Device gosnappi.DeviceIpv6 - otgBgpPeer, otgIPv6Device, otgConfig = configureOTG(t, otg) + otgBgpPeer, otgIPv6Device, otgConfig = configureOTG(t, otg, dstIPList) verifyBgpTelemetry(t, dut) @@ -287,7 +333,7 @@ func TestFibFailDueToHwResExhaust(t *testing.T) { otg: otg, } start := time.Now() - injectEntry(ctx, t, args) + injectEntry(ctx, t, args, dstIPList, vipList) t.Logf("Main Function: Time elapsed %.2f seconds since start", time.Since(start).Seconds()) t.Log("Send traffic to any of the programmed entries and validate.") @@ -297,50 +343,16 @@ func TestFibFailDueToHwResExhaust(t *testing.T) { func sendTraffic(t *testing.T, args *testArgs) { // Ensure that traffic can be forwarded between ATE port-1 and ATE port-2. t.Helper() - t.Logf("TestBGP:start otg Traffic config") - flow1ipv4 := args.otgConfig.Flows().Add().SetName("Flow1") - flow1ipv4.Metrics().SetEnable(true) - flow1ipv4.TxRx().Device(). - SetTxNames([]string{atePort1.Name + ".IPv4"}). - SetRxNames([]string{atePort2.Name + ".IPv4"}) - flow1ipv4.Size().SetFixed(512) - flow1ipv4.Rate().SetPps(100) - flow1ipv4.Duration().Continuous() - e1 := flow1ipv4.Packet().Add().Ethernet() - e1.Src().SetValue(atePort1.MAC) - v4 := flow1ipv4.Packet().Add().Ipv4() - v4.Src().SetValue(atePort1.IPv4) - v4.Dst().Increment().SetStart(fibPassedDstRoute) - flow2ipv4 := args.otgConfig.Flows().Add().SetName("Flow2") - flow2ipv4.Metrics().SetEnable(true) - flow2ipv4.TxRx().Device(). - SetTxNames([]string{atePort1.Name + ".IPv4"}). - SetRxNames([]string{atePort2.Name + ".IPv4"}) - flow2ipv4.Size().SetFixed(512) - flow2ipv4.Rate().SetPps(100) - flow2ipv4.Duration().Continuous() - e2 := flow2ipv4.Packet().Add().Ethernet() - e2.Src().SetValue(atePort1.MAC) - v4Flow2 := flow2ipv4.Packet().Add().Ipv4() - v4Flow2.Src().SetValue(atePort1.IPv4) - v4Flow2.Dst().Increment().SetStart(fibFailedDstRoute) + t.Logf("TestBGP:start otg Traffic") - args.otg.PushConfig(t, args.otgConfig) - time.Sleep(2 * time.Minute) - args.otg.StartProtocols(t) - otgutils.WaitForARP(t, args.ate.OTG(), args.otg.FetchConfig(t), "IPv4") t.Logf("Starting traffic") args.otg.StartTraffic(t) time.Sleep(15 * time.Second) t.Logf("Stop traffic") args.otg.StopTraffic(t) - verifyTraffic(t, args, flow1ipv4.Name(), !wantLoss) - /* - if !deviations.GRIBISkipFIBFailedTrafficForwardingCheck(args.dut) { - verifyTraffic(t, args, flow2ipv4.Name(), wantLoss) - } - */ + verifyTraffic(t, args, fibPassedTraffic, !wantLoss) + verifyTraffic(t, args, fibFailedTraffic, wantLoss) } func verifyTraffic(t *testing.T, args *testArgs, flowName string, wantLoss bool) { @@ -351,16 +363,31 @@ func verifyTraffic(t *testing.T, args *testArgs, flowName string, wantLoss bool) rxPackets := recvMetric.GetCounters().GetInPkts() lostPackets := txPackets - rxPackets var lossPct uint64 + trafficPassed := false if txPackets != 0 { lossPct = lostPackets * 100 / txPackets } else { t.Errorf("Traffic stats are not correct %v", recvMetric) } if wantLoss { - if lossPct < 100-tolerancePct { - t.Errorf("Traffic is expected to fail %s\n got %v, want 100%% failure", flowName, lossPct) + // If no rxPackets are received, the first route is fibFailedRoute, resulting in no packets being generated with tagged metrics. + if rxPackets > 0 { + etPath := gnmi.OTG().Flow(flowName).TaggedMetricAny() + ets := gnmi.GetAll(t, args.otg, etPath.State()) + for _, et := range ets { + tags := et.Tags + for _, tag := range tags { + if tag.GetTagName() == dstTrackingf2 && tag.GetTagValue().GetValueAsHex() == fibFailedDstRouteInHex { + trafficPassed = true + break + } + } + } + } + if trafficPassed { + t.Errorf("Traffic received on Failed FIB") } else { - t.Logf("Traffic Loss Test Passed!") + t.Logf("Traffic Test Passed!") } } else { if lossPct > tolerancePct { @@ -369,6 +396,7 @@ func verifyTraffic(t *testing.T, args *testArgs, flowName string, wantLoss bool) t.Logf("Traffic Test Passed!") } } + } func verifyBgpTelemetry(t *testing.T, dut *ondatra.DUTDevice) { @@ -466,15 +494,31 @@ func createIPv4Entries(t *testing.T, startIP string) []string { return entries } +func IPv4LastTenBitsToHex(ip string) string { + // Convert IPv4 address to a 32-bit integer + ipParts := strings.Split(ip, ".") + var ipInt uint32 + for i := 0; i < 4; i++ { + part, _ := strconv.Atoi(ipParts[i]) + ipInt = (ipInt << 8) | uint32(part) + } + + // Convert the IP address to binary string + ipBinary := fmt.Sprintf("%032b", ipInt) + // Extract the last 10 bits + last10Bits := ipBinary[len(ipBinary)-10:] + // Convert the last 10 bits to hexadecimal + last10Hex, _ := strconv.ParseInt(last10Bits, 2, 64) + return fmt.Sprintf("0x%03x", last10Hex) +} + // injectEntry programs gRIBI nh, nhg and ipv4 entry. -func injectEntry(ctx context.Context, t *testing.T, args *testArgs) { +func injectEntry(ctx context.Context, t *testing.T, args *testArgs, dstIPList []string, vipList []string) { t.Helper() - dstIPList := createIPv4Entries(t, fmt.Sprintf("%s/%d", dstIPBlock, 20)) - vipList := createIPv4Entries(t, fmt.Sprintf("%s/%d", vipBlock, 20)) j := uint64(0) routeAddLoop: - for i := uint64(1); i <= uint64(1500); i += 2 { + for i := uint64(1); i <= uint64(1000); i += 2 { vipNhIndex := i dstNhIndex := vipNhIndex + 1 @@ -503,6 +547,7 @@ routeAddLoop: if v.ProgrammingResult == aftspb.AFTResult_FIB_FAILED { t.Logf("FIB FAILED received %v", v.Details) fibFailedDstRoute = dstIPList[j] + fibFailedDstRouteInHex = IPv4LastTenBitsToHex(fibFailedDstRoute) break routeAddLoop } } @@ -512,7 +557,7 @@ routeAddLoop: // routes through gRIBI client. Since FIB is already full , we should get // FIB FAILED while programming gRIBI routes. Here we are trying to program // 1500 VIP/Dst entries along with unique NH/NHG entries. - if i >= 1498 { + if i >= 998 { t.Fatalf("FIB FAILED is not received as expected") } if j == 1 { diff --git a/feature/experimental/gribi/otg_tests/fib_failed_due_to_hw_res_exhaust_test/metadata.textproto b/feature/gribi/otg_tests/fib_failed_due_to_hw_res_exhaust_test/metadata.textproto similarity index 100% rename from feature/experimental/gribi/otg_tests/fib_failed_due_to_hw_res_exhaust_test/metadata.textproto rename to feature/gribi/otg_tests/fib_failed_due_to_hw_res_exhaust_test/metadata.textproto diff --git a/feature/gribi/otg_tests/gribi_route_test/README.md b/feature/gribi/otg_tests/gribi_route_test/README.md new file mode 100644 index 00000000000..2f709e4ab43 --- /dev/null +++ b/feature/gribi/otg_tests/gribi_route_test/README.md @@ -0,0 +1,174 @@ +# RT-14.2: GRIBI Route Test + +## Summary + +Ensure Traffic is Encap/Decap to NextHop based on Gribi structure. + +## Topology + +ATE port-1 <------> port-1 DUT +DUT port-2 <------> port-2 ATE +DUT port-3 <------> port-3 ATE + +## Variables +``` +# Magic source IP addresses used in this test + * ipv4_outer_src_111 = 198.51.100.111 + * ipv4PrefixEncapped = ipv4InnerDst = 138.0.11.8 + * ipv4PrefixNotEncapped = ipv4OuterDst222 = 198.50.100.65 +``` + +## Baseline + +### VRF Selection Policy + +``` +network-instances { + network-instance { + name: DEFAULT + policy-forwarding { + policies { + policy { + policy-id: "vrf_selection_policy_c" + rules { + rule { + sequence-id: 1 + ipv4 { + protocol: 4 + source-address: "ipv4_outer_src_111" + } + action { + network-instance: "ENCAP_TE_VRF_A" + } + } + rule { + sequence-id: 2 + ipv4 { + protocol: 41 + dscp-set: [dscp_encap_a_1, dscp_encap_a_2] + source-address: "ipv4_outer_src_222" + } + action { + network-instance: "TRANSIT_TE_VRF" + } + } + } + } + } + } + } +} +``` +``` +### Install the following gRIBI AFTs. + +- IPv4Entry {0.0.0.0/0 (TRANSIT_TE_VRF)} -> NHG#1 (DEFAULT VRF) -> { + {NH#1, DEFAULT VRF, weight:1}, + } + NH#1 -> { + decapsulate_header: OPENCONFIGAFTTYPESENCAPSULATIONHEADERTYPE_IPV4 + network_instance: "DEFAULT" + } +- IPv4Entry {198.50.100.64/32 (TRANSIT_TE_VRF)} -> NHG#2 (DEFAULT VRF) -> { + {NH#2, DEFAULT VRF, weight:1}, interface-ref:dut-port-2-interface, + } +- IPv4Entry {198.50.100.64/32 (TE_VRF_111)} -> NHG#3 (DEFAULT VRF) -> { + {NH#3, DEFAULT VRF, weight:1}, interface-ref:dut-port-2-interface, + } +- IPv4Entry {0.0.0.0/0 (ENCAP_TE_VRF_A)} -> NHG#5 (DEFAULT VRF) -> { + {NH#5, DEFAULT VRF, weight:1, interface-ref:dut-port-3-interface}, + } +- IPv4Entry {138.0.11.8/32 (ENCAP_TE_VRF_A)} -> NHG#4 (DEFAULT VRF) -> { + {NH#4, DEFAULT VRF, weight:1}, + } + NH#4 -> { + encapsulate_header: OPENCONFIGAFTTYPESENCAPSULATIONHEADERTYPE_IPV4 + ip_in_ip { + dst_ip: "198.50.100.64" + src_ip: "ipv4_outer_src_111" + } + network_instance: "TE_VRF_111" + } +``` +- Install a BGP route in default VRF to route traffic out of DUT port-3. + +## Procedure + +The DUT should be reset to the baseline after each of the following tests. + +Test-1, Match on source prefix, flow hits ENCAP_TE_VRF_A followed by TE_VRF_111 + +``` + 1. Send flow with source IP ipv4_outer_src_111 with destination IP ipv4PrefixEncapped. + 2. Verify v4 packet matched with tunnel prefix and encapped -> hit TE_VRF_111 + and egress via port-2. + 3. No traffic loss in steady state + +``` +Test-2, Match on source prefix, flow hits ENCAP_TE_VRF_A followed by Default VRF + +``` + 1. Send flow with source IP ipv4_outer_src_111 with destination IP ipv4PrefixNotEncapped. + 2. Verify v4 packet not matched with tunnel prefix and egress via port-3. + 3. No traffic loss in steady state + +``` +Test-3, Match on source prefix and protocol, flow hits TRANSIT_TE_VRF +match with Tunnel prefix /32 + +``` + 1. Send the following 4in4 flows to DUT port-1: + * inner_src: `ipv4_inner_src` + * inner_dst: `ipv4InnerDst` + * outter_src: `ipv4_outter_src_111` + * outter_dst: `ipv4_outter_decap_no_match` + * proto: `4` + 2. Verify packet matched with tunnel prefix and egress via port-2. + 3. No traffic loss in steady state + +``` +Test-4, Match on source prefix and protocol, flow hits TRANSIT_TE_VRF matched with 0/0 prefix, decap & sent to default vrf +``` + 1. Send the following 4in4 flows to DUT port-1: + * inner_src: `ipv4_inner_src` + * inner_dst: `ipv4InnerDst` + * outter_src: `ipv4_outter_src_111` + * outter_dst: `ipv4_outter_decap_match` + * proto: `4` + 2. Verify packet not matched with tunnel prefix, decap and failback + to default vrf. + 3. No traffic loss in steady state + +``` +## Config Parameter Coverage + +* network-instances/network-instance/name +* network-instances/network-instance/policy-forwarding/policies/policy/policy-id +* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/sequence-id +* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv4/protocol +* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv4/source-address +* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv6/source-address +* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/action/config/network-instance + +## Telemetry Parameter Coverage + +* network-instances/network-instance/name +* network-instances/network-instance/policy-forwarding/policies/policy/policy-id +* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/sequence-id +* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv4/protocol +* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv4/source-address +* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv6/source-address +* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/action/config/network-instance + +## OpenConfig Path and RPC Coverage +```yaml +rpcs: + gnmi: + gNMI.Get: + gNMI.Set: + gNMI.Subscribe: + gribi: + gRIBI.Get: + gRIBI.Modify: + gRIBI.Flush: +``` diff --git a/feature/gribi/otg_tests/gribi_route_test/gribi_route_test.go b/feature/gribi/otg_tests/gribi_route_test/gribi_route_test.go new file mode 100644 index 00000000000..b981ef03f55 --- /dev/null +++ b/feature/gribi/otg_tests/gribi_route_test/gribi_route_test.go @@ -0,0 +1,727 @@ +package gribi_route_test + +import ( + "context" + "fmt" + "log" + "os" + "strconv" + "testing" + "time" + + "github.com/google/gopacket" + "github.com/google/gopacket/layers" + "github.com/google/gopacket/pcap" + "github.com/open-traffic-generator/snappi/gosnappi" + "github.com/openconfig/featureprofiles/internal/attrs" + "github.com/openconfig/featureprofiles/internal/deviations" + "github.com/openconfig/featureprofiles/internal/fptest" + "github.com/openconfig/featureprofiles/internal/gribi" + "github.com/openconfig/featureprofiles/internal/otgutils" + "github.com/openconfig/gribigo/chk" + "github.com/openconfig/gribigo/constants" + "github.com/openconfig/gribigo/fluent" + "github.com/openconfig/ondatra" + "github.com/openconfig/ondatra/gnmi" + "github.com/openconfig/ondatra/gnmi/oc" + "github.com/openconfig/ondatra/otg" + "github.com/openconfig/ygnmi/ygnmi" + "github.com/openconfig/ygot/ygot" +) + +const ( + niTransitTeVrf = "TRANSIT_TE_VRF" + niEncapTeVrfA = "ENCAP_TE_VRF_A" + niTEVRF111 = "TE_VRF_111" + vrfPolC = "vrf_selection_policy_c" + seqIDBase = uint32(10) + ipv4OuterSrc111 = "198.51.100.111" + ipv4OuterSrc111WithMask = "198.51.100.111/32" + ipv4InnerDst = "138.0.11.8" + ipv4OuterDst111 = "198.50.100.64" + ipv4OuterDst222 = "198.50.100.65" + peerGrpName = "BGP-PEER-GROUP1" + asn = 65501 + tolerancePct = 2 + checkEncap = true +) + +var ( + dutPort1 = attrs.Attributes{ + Desc: "DUT Port 1", + IPv4: "192.0.2.1", + IPv4Len: 30, + } + dutPort2 = attrs.Attributes{ + Desc: "DUT Port 2", + IPv4: "192.0.2.5", + IPv4Len: 30, + } + dutPort3 = attrs.Attributes{ + Desc: "DUT Port 3", + IPv4: "192.0.2.9", + IPv4Len: 30, + } + + atePort1 = attrs.Attributes{ + Name: "port1", + MAC: "02:00:01:01:01:01", + Desc: "ATE Port 1", + IPv4: "192.0.2.2", + IPv4Len: 30, + } + atePort2 = attrs.Attributes{ + Name: "port2", + MAC: "02:00:02:01:01:01", + Desc: "ATE Port 2", + IPv4: "192.0.2.6", + IPv4Len: 30, + } + atePort3 = attrs.Attributes{ + Name: "port3", + MAC: "02:00:03:01:01:01", + Desc: "ATE Port 3", + IPv4: "192.0.2.10", + IPv4Len: 30, + } +) + +type bgpNeighbor struct { + Name string + dutIPv4 string + ateIPv4 string + MAC string +} + +var ( + bgpNbr1 = bgpNeighbor{ + Name: "port1", + dutIPv4: "192.0.2.1", + ateIPv4: "192.0.2.2", + MAC: "02:00:01:01:01:01", + } + bgpNbr2 = bgpNeighbor{ + Name: "port2", + dutIPv4: "192.0.2.5", + ateIPv4: "192.0.2.6", + MAC: "02:00:02:01:01:01", + } + bgpNbr3 = bgpNeighbor{ + Name: "port3", + dutIPv4: "192.0.2.9", + ateIPv4: "192.0.2.10", + MAC: "02:00:03:01:01:01", + } +) + +type packetValidation struct { + portName string + outDstIP []string + inHdrIP string + validateDecap bool + validateNoDecap bool + validateEncap bool +} + +type policyFwRule struct { + SeqID uint32 + family string + protocol oc.UnionUint8 + dscpSet []uint8 + sourceAddr string + ni string +} + +// testArgs holds the objects needed by a test case. +type testArgs struct { + dut *ondatra.DUTDevice + ctx context.Context + client *fluent.GRIBIClient + ate *ondatra.ATEDevice + otgConfig gosnappi.Config + otg *otg.OTG +} + +type flowArgs struct { + flowName string + outHdrSrcIP, outHdrDstIP string + InnHdrSrcIP, InnHdrDstIP string + InnHdrSrcIPv6, InnHdrDstIPv6 string + isIPInIP bool +} + +func TestMain(m *testing.M) { + fptest.RunTests(m) +} + +func TestGRIBIFailover(t *testing.T) { + dut := ondatra.DUT(t, "dut") + configureDUT(t, dut) + ate := ondatra.ATE(t, "ate") + top := configureOTG(t, ate) + t.Log("Configure VRF_Policy") + configureVrfSelectionPolicyC(t, dut) + t.Log("Configure GRIBI") + configureGribiRoute(t, dut) + + llAddress, found := gnmi.Watch(t, ate.OTG(), gnmi.OTG().Interface("port1.Eth").Ipv4Neighbor(dutPort1.IPv4).LinkLayerAddress().State(), time.Minute, func(val *ygnmi.Value[string]) bool { + return val.IsPresent() + }).Await(t) + if !found { + t.Fatalf("Could not get the LinkLayerAddress %s", llAddress) + } + dstMac, _ := llAddress.Val() + + verifyBgpTelemetry(t, dut) + + args := &testArgs{ + dut: dut, + ate: ate, + otgConfig: top, + otg: ate.OTG(), + } + t.Run("RT-14.2.1: Traffic Prefix Match to Tunnel Prefix, Encapped and Egress via Port2", func(t *testing.T) { + flow := createFlow(&flowArgs{flowName: "flow4in4", + InnHdrSrcIP: ipv4OuterSrc111, InnHdrDstIP: ipv4InnerDst}, dstMac) + sendTraffic(t, args, top, ate, flow, 30, []string{"port2"}) + if ok := verifyTrafficFlow(t, ate, flow); !ok { + t.Fatal("Packet Dropped, LossPct for flow ") + } + captureAndValidatePackets(t, args, &packetValidation{portName: atePort2.Name, + outDstIP: []string{ipv4OuterDst111}, inHdrIP: ipv4InnerDst, validateEncap: true}) + }) + + t.Run("RT-14.2.2: Traffic Prefix not Matched to Tunnel Prefix, Egress via Port3", func(t *testing.T) { + flow := createFlow(&flowArgs{flowName: "flow4in4", + InnHdrSrcIP: ipv4OuterSrc111, InnHdrDstIP: ipv4OuterDst222}, dstMac) + sendTraffic(t, args, top, ate, flow, 30, []string{"port3"}) + if ok := verifyTrafficFlow(t, ate, flow); !ok { + t.Fatal("Packet Dropped, LossPct for flow ") + } + }) + + t.Run("RT-14.2.3: Traffic Match to Transit_Vrf, Match Tunnel Prefix Egress to Port2", func(t *testing.T) { + flow := createFlow(&flowArgs{flowName: "flow4in4", + outHdrSrcIP: ipv4OuterSrc111, outHdrDstIP: ipv4OuterDst111, + InnHdrSrcIP: ipv4OuterSrc111, InnHdrDstIP: ipv4InnerDst, isIPInIP: true}, dstMac) + sendTraffic(t, args, top, ate, flow, 30, []string{"port2"}) + if ok := verifyTrafficFlow(t, ate, flow); !ok { + t.Fatal("Packet Dropped, LossPct for flow ") + } + captureAndValidatePackets(t, args, &packetValidation{portName: atePort2.Name, + outDstIP: []string{ipv4OuterDst111}, inHdrIP: ipv4InnerDst, validateNoDecap: true}) + }) + + t.Run("RT-14.2.4: Traffic Match to Transit_Vrf, noMatch Tunnel Prefix Egress to Port3", func(t *testing.T) { + flow := createFlow(&flowArgs{flowName: "flow4in4", + outHdrSrcIP: ipv4OuterSrc111, outHdrDstIP: ipv4OuterDst222, + InnHdrSrcIP: ipv4OuterSrc111, InnHdrDstIP: ipv4InnerDst, isIPInIP: true}, dstMac) + sendTraffic(t, args, top, ate, flow, 30, []string{"port3"}) + if ok := verifyTrafficFlow(t, ate, flow); !ok { + t.Fatal("Packet Dropped, LossPct for flow ") + } + captureAndValidatePackets(t, args, &packetValidation{portName: atePort3.Name, + outDstIP: []string{ipv4OuterDst222}, inHdrIP: ipv4InnerDst, validateDecap: true}) + }) +} + +// configureDUT configures port1-3 on the DUT. +func configureDUT(t *testing.T, dut *ondatra.DUTDevice) { + fptest.ConfigureDefaultNetworkInstance(t, dut) + t.Logf("configureDUT") + p1 := dut.Port(t, "port1") + p2 := dut.Port(t, "port2") + p3 := dut.Port(t, "port3") + + gnmi.Replace(t, dut, gnmi.OC().Interface(p1.Name()).Config(), dutPort1.NewOCInterface(p1.Name(), dut)) + gnmi.Replace(t, dut, gnmi.OC().Interface(p2.Name()).Config(), dutPort2.NewOCInterface(p2.Name(), dut)) + gnmi.Replace(t, dut, gnmi.OC().Interface(p3.Name()).Config(), dutPort3.NewOCInterface(p3.Name(), dut)) + + if deviations.ExplicitPortSpeed(dut) { + fptest.SetPortSpeed(t, p1) + fptest.SetPortSpeed(t, p2) + fptest.SetPortSpeed(t, p3) + } + if deviations.ExplicitInterfaceInDefaultVRF(dut) { + fptest.AssignToNetworkInstance(t, dut, p1.Name(), deviations.DefaultNetworkInstance(dut), 0) + fptest.AssignToNetworkInstance(t, dut, p2.Name(), deviations.DefaultNetworkInstance(dut), 0) + fptest.AssignToNetworkInstance(t, dut, p3.Name(), deviations.DefaultNetworkInstance(dut), 0) + } + configNonDefaultNetworkInstance(t, dut) + dutConfPath := gnmi.OC().NetworkInstance(deviations.DefaultNetworkInstance(dut)).Protocol(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, "BGP") + gnmi.Delete(t, dut, dutConfPath.Config()) + dutConf := bgpCreateNbr(asn, dut) + gnmi.Replace(t, dut, dutConfPath.Config(), dutConf) +} + +func bgpCreateNbr(localAs uint32, dut *ondatra.DUTDevice) *oc.NetworkInstance_Protocol { + dutOcRoot := &oc.Root{} + ni1 := dutOcRoot.GetOrCreateNetworkInstance(deviations.DefaultNetworkInstance(dut)) + niProto := ni1.GetOrCreateProtocol(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, "BGP") + bgp := niProto.GetOrCreateBgp() + + global := bgp.GetOrCreateGlobal() + global.RouterId = ygot.String(dutPort3.IPv4) + global.As = ygot.Uint32(localAs) + global.GetOrCreateAfiSafi(oc.BgpTypes_AFI_SAFI_TYPE_IPV4_UNICAST).Enabled = ygot.Bool(true) + global.GetOrCreateAfiSafi(oc.BgpTypes_AFI_SAFI_TYPE_IPV6_UNICAST).Enabled = ygot.Bool(true) + pg1 := bgp.GetOrCreatePeerGroup(peerGrpName) + pg1.PeerAs = ygot.Uint32(localAs) + + bgpNbr := bgp.GetOrCreateNeighbor(bgpNbr3.ateIPv4) + bgpNbr.PeerGroup = ygot.String(peerGrpName) + bgpNbr.PeerAs = ygot.Uint32(localAs) + bgpNbr.Enabled = ygot.Bool(true) + bgpNbrT := bgpNbr.GetOrCreateTransport() + bgpNbrT.LocalAddress = ygot.String(bgpNbr3.dutIPv4) + af4 := bgpNbr.GetOrCreateAfiSafi(oc.BgpTypes_AFI_SAFI_TYPE_IPV4_UNICAST) + af4.Enabled = ygot.Bool(true) + af6 := bgpNbr.GetOrCreateAfiSafi(oc.BgpTypes_AFI_SAFI_TYPE_IPV6_UNICAST) + af6.Enabled = ygot.Bool(true) + + return niProto +} + +// configureOTGBGP configure BGP on ATE +func configureOTGBGP(t *testing.T, dev gosnappi.Device, top gosnappi.Config, nbr bgpNeighbor) { + t.Helper() + iDutBgp := dev.Bgp().SetRouterId(nbr.ateIPv4) + iDutBgp4Peer := iDutBgp.Ipv4Interfaces().Add().SetIpv4Name(nbr.Name + ".IPv4").Peers().Add().SetName(nbr.Name + ".BGP4.peer") + iDutBgp4Peer.SetPeerAddress(nbr.dutIPv4).SetAsNumber(asn).SetAsType(gosnappi.BgpV4PeerAsType.IBGP) + iDutBgp4Peer.LearnedInformationFilter().SetUnicastIpv4Prefix(true).SetUnicastIpv6Prefix(false) + + bgpNeti1Bgp4PeerRoutes := iDutBgp4Peer.V4Routes().Add().SetName(nbr.Name + ".BGP4.Route") + bgpNeti1Bgp4PeerRoutes.SetNextHopIpv4Address(nbr.ateIPv4). + SetNextHopAddressType(gosnappi.BgpV4RouteRangeNextHopAddressType.IPV4). + SetNextHopMode(gosnappi.BgpV4RouteRangeNextHopMode.MANUAL) + bgpNeti1Bgp4PeerRoutes.Addresses().Add().SetAddress(ipv4InnerDst).SetPrefix(32).SetCount(1) +} + +func configureOTG(t *testing.T, ate *ondatra.ATEDevice) gosnappi.Config { + t.Logf("configureOTG") + config := gosnappi.NewConfig() + var dev gosnappi.Device + for i, ap := range []bgpNeighbor{bgpNbr1, bgpNbr2, bgpNbr3} { + // DUT and ATE ports are connected by the same names. + port := config.Ports().Add().SetName(ap.Name) + portName := fmt.Sprintf("port%s", strconv.Itoa(i+1)) + dev = config.Devices().Add().SetName(portName) + eth := dev.Ethernets().Add().SetName(portName + ".Eth").SetMac(ap.MAC) + eth.Connection().SetPortName(port.Name()) + eth.Ipv4Addresses().Add().SetName(portName + ".IPv4"). + SetAddress(ap.ateIPv4).SetGateway(ap.dutIPv4). + SetPrefix(30) + } + configureOTGBGP(t, dev, config, bgpNbr3) + ate.OTG().PushConfig(t, config) + ate.OTG().StartProtocols(t) + return config +} + +// seqIDOffset returns sequence ID offset added with seqIDBase (10), to avoid sequences +// like 1, 10, 11, 12,..., 2, 21, 22, ... while being sent by Ondatra to the DUT. +// It now generates sequences like 11, 12, 13, ..., 19, 20, 21,..., 99. +func seqIDOffset(dut *ondatra.DUTDevice, i uint32) uint32 { + if deviations.PfRequireSequentialOrderPbrRules(dut) { + return i + seqIDBase + } + return i +} + +// configureNetworkInstance configures vrfs DECAP_TE_VRF,ENCAP_TE_VRF_A,ENCAP_TE_VRF_B, +// TE_VRF_222, TE_VRF_111. +func configNonDefaultNetworkInstance(t *testing.T, dut *ondatra.DUTDevice) { + t.Helper() + c := &oc.Root{} + vrfs := []string{niTransitTeVrf, niEncapTeVrfA, niTEVRF111} + for _, vrf := range vrfs { + ni := c.GetOrCreateNetworkInstance(vrf) + ni.Type = oc.NetworkInstanceTypes_NETWORK_INSTANCE_TYPE_L3VRF + gnmi.Replace(t, dut, gnmi.OC().NetworkInstance(vrf).Config(), ni) + } + gnmi.Update(t, dut, gnmi.OC().NetworkInstance(deviations.DefaultNetworkInstance(dut)).Name().Config(), deviations.DefaultNetworkInstance(dut)) +} + +func configureVrfSelectionPolicyC(t *testing.T, dut *ondatra.DUTDevice) { + t.Helper() + d := &oc.Root{} + time.Sleep(100 * time.Second) + dutPolFwdPath := gnmi.OC().NetworkInstance(deviations.DefaultNetworkInstance(dut)).PolicyForwarding() + + pfRule1 := &policyFwRule{SeqID: 1, family: "ipv4", protocol: 4, sourceAddr: ipv4OuterSrc111WithMask, + ni: niTransitTeVrf} + pfRule2 := &policyFwRule{SeqID: 2, family: "ipv4", sourceAddr: ipv4OuterSrc111WithMask, + ni: niEncapTeVrfA} + + pfRuleList := []*policyFwRule{pfRule1, pfRule2} + ni := d.GetOrCreateNetworkInstance(deviations.DefaultNetworkInstance(dut)) + niP := ni.GetOrCreatePolicyForwarding() + niPf := niP.GetOrCreatePolicy(vrfPolC) + niPf.SetType(oc.Policy_Type_VRF_SELECTION_POLICY) + for _, pfRule := range pfRuleList { + pfR := niPf.GetOrCreateRule(seqIDOffset(dut, pfRule.SeqID)) + if pfRule.family == "ipv4" { + pfRProtoIP := pfR.GetOrCreateIpv4() + if pfRule.protocol != 0 { + pfRProtoIP.Protocol = oc.UnionUint8(pfRule.protocol) + } + if pfRule.sourceAddr != "" { + pfRProtoIP.SourceAddress = ygot.String(pfRule.sourceAddr) + } + } else if pfRule.family == "ipv6" { + pfRProtoIP := pfR.GetOrCreateIpv6() + if pfRule.dscpSet != nil { + pfRProtoIP.DscpSet = pfRule.dscpSet + } + } + + pfRAction := pfR.GetOrCreateAction() + pfRAction.NetworkInstance = ygot.String(pfRule.ni) + } + p1 := dut.Port(t, "port1") + interfaceID := p1.Name() + if deviations.InterfaceRefInterfaceIDFormat(dut) { + interfaceID = interfaceID + ".0" + } + intf := niP.GetOrCreateInterface(interfaceID) + intf.ApplyVrfSelectionPolicy = ygot.String(vrfPolC) + intf.GetOrCreateInterfaceRef().Interface = ygot.String(p1.Name()) + intf.GetOrCreateInterfaceRef().Subinterface = ygot.Uint32(0) + if deviations.InterfaceRefConfigUnsupported(dut) { + intf.InterfaceRef = nil + } + // gnmi.Update(t, dut, gnmi.OC().NetworkInstance("DEFAULT").Name().Config(), "DEFAULT") + gnmi.Replace(t, dut, dutPolFwdPath.Config(), niP) +} + +func configureGribiRoute(t *testing.T, dut *ondatra.DUTDevice) { + t.Helper() + ctx := context.Background() + gribic := dut.RawAPIs().GRIBI(t) + client := fluent.NewClient() + client.Connection().WithStub(gribic).WithPersistence().WithInitialElectionID(12, 0). + WithRedundancyMode(fluent.ElectedPrimaryClient).WithFIBACK() + client.Start(ctx, t) + defer client.Stop(t) + gribi.FlushAll(client) + client.StartSending(ctx, t) + gribi.BecomeLeader(t, client) + + tcArgs := &testArgs{ + ctx: ctx, + client: client, + dut: dut, + } + tcArgs.client.Modify().AddEntry(t, + fluent.NextHopEntry().WithNetworkInstance(deviations.DefaultNetworkInstance(tcArgs.dut)). + WithIndex(uint64(1)).WithDecapsulateHeader(fluent.IPinIP). + WithNextHopNetworkInstance(deviations.DefaultNetworkInstance(dut)), + fluent.NextHopGroupEntry().WithNetworkInstance(deviations.DefaultNetworkInstance(tcArgs.dut)). + WithID(uint64(1)).AddNextHop(uint64(1), uint64(1)), + + fluent.IPv4Entry().WithNetworkInstance(niTransitTeVrf).WithNextHopGroupNetworkInstance(deviations.DefaultNetworkInstance(dut)). + WithPrefix("0.0.0.0/0").WithNextHopGroup(uint64(1))) + + if err := awaitTimeout(tcArgs.ctx, t, tcArgs.client, 90*time.Second); err != nil { + t.Logf("Could not program entries via client, got err, check error codes: %v", err) + } + + tcArgs.client.Modify().AddEntry(t, + fluent.NextHopEntry().WithNetworkInstance(deviations.DefaultNetworkInstance(tcArgs.dut)). + WithIndex(uint64(2)).WithIPAddress(atePort2.IPv4), + fluent.NextHopGroupEntry().WithNetworkInstance(deviations.DefaultNetworkInstance(tcArgs.dut)). + WithID(uint64(2)).AddNextHop(uint64(2), uint64(1)), + + fluent.IPv4Entry().WithNetworkInstance(niTransitTeVrf).WithNextHopGroupNetworkInstance(deviations.DefaultNetworkInstance(dut)). + WithPrefix(ipv4OuterDst111+"/32").WithNextHopGroup(uint64(2))) + + if err := awaitTimeout(tcArgs.ctx, t, tcArgs.client, 90*time.Second); err != nil { + t.Logf("Could not program entries via client, got err, check error codes: %v", err) + } + + defaultVRFIPList := []string{"0.0.0.0/0", ipv4OuterDst111 + "/32"} + for ip := range defaultVRFIPList { + chk.HasResult(t, tcArgs.client.Results(t), + fluent.OperationResult(). + WithIPv4Operation(defaultVRFIPList[ip]). + WithOperationType(constants.Add). + WithProgrammingResult(fluent.InstalledInFIB). + AsResult(), + chk.IgnoreOperationID(), + ) + } + + tcArgs.client.Modify().AddEntry(t, + fluent.NextHopEntry().WithNetworkInstance(deviations.DefaultNetworkInstance(tcArgs.dut)). + WithIndex(uint64(3)).WithIPAddress(atePort2.IPv4), + fluent.NextHopGroupEntry().WithNetworkInstance(deviations.DefaultNetworkInstance(tcArgs.dut)). + WithID(uint64(3)).AddNextHop(uint64(3), uint64(1)), + + fluent.IPv4Entry().WithNetworkInstance(niTEVRF111). + WithNextHopGroupNetworkInstance(deviations.DefaultNetworkInstance(dut)). + WithPrefix(ipv4OuterDst111+"/32").WithNextHopGroup(uint64(3))) + + if err := awaitTimeout(tcArgs.ctx, t, tcArgs.client, 90*time.Second); err != nil { + t.Logf("Could not program entries via client, got err, check error codes: %v", err) + } + + chk.HasResult(t, tcArgs.client.Results(t), + fluent.OperationResult(). + WithIPv4Operation(ipv4OuterDst111+"/32"). + WithOperationType(constants.Add). + WithProgrammingResult(fluent.InstalledInFIB). + AsResult(), + chk.IgnoreOperationID(), + ) + // Encap + tcArgs.client.Modify().AddEntry(t, + fluent.NextHopEntry().WithNetworkInstance(deviations.DefaultNetworkInstance(tcArgs.dut)). + WithIndex(uint64(4)).WithEncapsulateHeader(fluent.IPinIP).WithIPinIP(ipv4OuterSrc111, ipv4OuterDst111). + WithNextHopNetworkInstance(niTEVRF111), + fluent.NextHopGroupEntry().WithNetworkInstance(deviations.DefaultNetworkInstance(tcArgs.dut)). + WithID(uint64(4)).AddNextHop(uint64(4), uint64(1)), + + fluent.IPv4Entry().WithNetworkInstance(niEncapTeVrfA). + WithNextHopGroupNetworkInstance(deviations.DefaultNetworkInstance(dut)). + WithPrefix(ipv4InnerDst+"/32").WithNextHopGroup(uint64(4))) + + if err := awaitTimeout(tcArgs.ctx, t, tcArgs.client, 90*time.Second); err != nil { + t.Logf("Could not program entries via client, got err, check error codes: %v", err) + } + + tcArgs.client.Modify().AddEntry(t, + fluent.NextHopEntry().WithNetworkInstance(deviations.DefaultNetworkInstance(tcArgs.dut)). + WithIndex(uint64(5)).WithIPAddress(atePort3.IPv4), + fluent.NextHopGroupEntry().WithNetworkInstance(deviations.DefaultNetworkInstance(tcArgs.dut)). + WithID(uint64(5)).AddNextHop(uint64(5), uint64(1)), + + fluent.IPv4Entry().WithNetworkInstance(niEncapTeVrfA). + WithNextHopGroupNetworkInstance(deviations.DefaultNetworkInstance(dut)). + WithPrefix("0.0.0.0/0").WithNextHopGroup(uint64(5))) + + if err := awaitTimeout(tcArgs.ctx, t, tcArgs.client, 90*time.Second); err != nil { + t.Logf("Could not program entries via client, got err, check error codes: %v", err) + } + + defaultVRFIPList = []string{"0.0.0.0/0", ipv4InnerDst + "/32"} + for ip := range defaultVRFIPList { + chk.HasResult(t, tcArgs.client.Results(t), + fluent.OperationResult(). + WithIPv4Operation(defaultVRFIPList[ip]). + WithOperationType(constants.Add). + WithProgrammingResult(fluent.InstalledInFIB). + AsResult(), + chk.IgnoreOperationID(), + ) + } + +} + +// awaitTimeout calls a fluent client Await, adding a timeout to the context. +func awaitTimeout(ctx context.Context, t testing.TB, c *fluent.GRIBIClient, timeout time.Duration) error { + t.Helper() + subctx, cancel := context.WithTimeout(ctx, timeout) + defer cancel() + return c.Await(subctx, t) +} + +func createFlow(flowValues *flowArgs, dstMac string) gosnappi.Flow { + flow := gosnappi.NewFlow().SetName(flowValues.flowName) + flow.Metrics().SetEnable(true) + flow.Size().SetFixed(512) + flow.Rate().SetPps(100) + flow.Duration().Continuous() + ethHeader := flow.Packet().Add().Ethernet() + ethHeader.Src().SetValue(atePort1.MAC) + ethHeader.Dst().SetValue(dstMac) + // Outer IP header + if flowValues.isIPInIP { + outerIPHdr := flow.Packet().Add().Ipv4() + outerIPHdr.Src().SetValue(flowValues.outHdrSrcIP) + outerIPHdr.Dst().SetValue(flowValues.outHdrDstIP) + innerIPHdr := flow.Packet().Add().Ipv4() + innerIPHdr.Src().SetValue(flowValues.InnHdrSrcIP) + innerIPHdr.Dst().SetValue(flowValues.InnHdrDstIP) + } else { + innerIPHdr := flow.Packet().Add().Ipv4() + innerIPHdr.Src().SetValue(flowValues.InnHdrSrcIP) + innerIPHdr.Dst().SetValue(flowValues.InnHdrDstIP) + } + return flow +} + +// testTraffic sends traffic flow for duration seconds and returns the +// number of packets sent out. +func sendTraffic(t *testing.T, args *testArgs, top gosnappi.Config, ate *ondatra.ATEDevice, flow gosnappi.Flow, duration int, port []string) { + t.Helper() + top.Flows().Clear() + + args.otgConfig.Captures().Clear() + args.otgConfig.Captures().Add().SetName("packetCapture"). + SetPortNames(port). + SetFormat(gosnappi.CaptureFormat.PCAP) + + flow.TxRx().Port().SetTxName("port1").SetRxNames([]string{"port2", "port3"}) + flow.Metrics().SetEnable(true) + top.Flows().Append(flow) + + ate.OTG().PushConfig(t, top) + time.Sleep(30 * time.Second) + ate.OTG().StartProtocols(t) + time.Sleep(30 * time.Second) + + cs := gosnappi.NewControlState() + cs.Port().Capture().SetState(gosnappi.StatePortCaptureState.START) + args.otg.SetControlState(t, cs) + + ate.OTG().StartTraffic(t) + time.Sleep(time.Duration(duration) * time.Second) + ate.OTG().StopTraffic(t) + + cs.Port().Capture().SetState(gosnappi.StatePortCaptureState.STOP) + args.otg.SetControlState(t, cs) + otgutils.LogFlowMetrics(t, ate.OTG(), top) + otgutils.LogPortMetrics(t, ate.OTG(), top) +} + +// verifyTrafficFlow verify the each flow on ATE +func verifyTrafficFlow(t *testing.T, ate *ondatra.ATEDevice, flow gosnappi.Flow) bool { + rxPkts := gnmi.Get(t, ate.OTG(), gnmi.OTG().Flow(flow.Name()).Counters().InPkts().State()) + txPkts := gnmi.Get(t, ate.OTG(), gnmi.OTG().Flow(flow.Name()).Counters().OutPkts().State()) + lostPkt := txPkts - rxPkts + if got := (lostPkt * 100 / txPkts); got >= tolerancePct { + return false + } + return true +} + +// verifyBgpTelemetry verifies BGP telemetry. +func verifyBgpTelemetry(t *testing.T, dut *ondatra.DUTDevice) { + t.Helper() + t.Logf("Verifying BGP state.") + bgpPath := gnmi.OC().NetworkInstance(deviations.DefaultNetworkInstance(dut)).Protocol(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, "BGP").Bgp() + + nbrPath := bgpPath.Neighbor(bgpNbr3.ateIPv4) + // Get BGP adjacency state. + t.Logf("Waiting for BGP neighbor to establish...") + var status *ygnmi.Value[oc.E_Bgp_Neighbor_SessionState] + status, ok := gnmi.Watch(t, dut, nbrPath.SessionState().State(), time.Minute, func(val *ygnmi.Value[oc.E_Bgp_Neighbor_SessionState]) bool { + state, ok := val.Val() + return ok && state == oc.Bgp_Neighbor_SessionState_ESTABLISHED + }).Await(t) + if !ok { + fptest.LogQuery(t, "BGP reported state", nbrPath.State(), gnmi.Get(t, dut, nbrPath.State())) + t.Fatal("No BGP neighbor formed") + } + state, _ := status.Val() + t.Logf("BGP adjacency for %s: %v", bgpNbr3.ateIPv4, state) + if want := oc.Bgp_Neighbor_SessionState_ESTABLISHED; state != want { + t.Errorf("BGP peer %s status got %d, want %d", bgpNbr3.ateIPv4, state, want) + } +} + +func captureAndValidatePackets(t *testing.T, args *testArgs, packetVal *packetValidation) { + bytes := args.otg.GetCapture(t, gosnappi.NewCaptureRequest().SetPortName(packetVal.portName)) + f, err := os.CreateTemp("", "pcap") + if err != nil { + t.Fatalf("ERROR: Could not create temporary pcap file: %v\n", err) + } + if _, err := f.Write(bytes); err != nil { + t.Fatalf("ERROR: Could not write bytes to pcap file: %v\n", err) + } + f.Close() + handle, err := pcap.OpenOffline(f.Name()) + if err != nil { + log.Fatal(err) + } + defer handle.Close() + packetSource := gopacket.NewPacketSource(handle, handle.LinkType()) + if packetVal.validateDecap { + validateTrafficDecap(t, packetSource) + } + if packetVal.validateNoDecap { + validateTrafficNonDecap(t, packetSource, packetVal.outDstIP[0], packetVal.inHdrIP) + } + if packetVal.validateEncap { + validateTrafficEncap(t, packetSource, packetVal.outDstIP, packetVal.inHdrIP) + } + args.otgConfig.Captures().Clear() + args.otg.PushConfig(t, args.otgConfig) + time.Sleep(30 * time.Second) +} + +func validateTrafficDecap(t *testing.T, packetSource *gopacket.PacketSource) { + t.Helper() + for packet := range packetSource.Packets() { + ipLayer := packet.Layer(layers.LayerTypeIPv4) + if ipLayer == nil { + continue + } + ipPacket, _ := ipLayer.(*layers.IPv4) + innerPacket := gopacket.NewPacket(ipPacket.Payload, ipPacket.NextLayerType(), gopacket.Default) + ipInnerLayer := innerPacket.Layer(layers.LayerTypeIPv4) + if ipInnerLayer != nil { + t.Errorf("Packets are not decapped, Inner IP header is not removed.") + } + } +} + +func validateTrafficNonDecap(t *testing.T, packetSource *gopacket.PacketSource, outDstIP, inHdrIP string) { + t.Helper() + t.Log("Validate traffic non decap routes") + var packetCheckCount uint32 = 1 + for packet := range packetSource.Packets() { + if packetCheckCount >= 5 { + break + } + ipLayer := packet.Layer(layers.LayerTypeIPv4) + if ipLayer == nil { + continue + } + ipPacket, _ := ipLayer.(*layers.IPv4) + innerPacket := gopacket.NewPacket(ipPacket.Payload, ipPacket.NextLayerType(), gopacket.Default) + ipInnerLayer := innerPacket.Layer(layers.LayerTypeIPv4) + if ipInnerLayer != nil { + if ipPacket.DstIP.String() != outDstIP { + t.Errorf("Negatice test for Decap failed. Traffic sent to route which does not match the decap route are decaped") + } + ipInnerPacket, _ := ipInnerLayer.(*layers.IPv4) + if ipInnerPacket.DstIP.String() != inHdrIP { + t.Errorf("Negatice test for Decap failed. Traffic sent to route which does not match the decap route are decaped") + } + t.Logf("Traffic for non decap routes passed.") + break + } + } +} + +func validateTrafficEncap(t *testing.T, packetSource *gopacket.PacketSource, outDstIP []string, innerIP string) { + t.Helper() + t.Log("Validate traffic non decap routes") + var packetCheckCount uint32 = 1 + for packet := range packetSource.Packets() { + if packetCheckCount >= 5 { + break + } + ipLayer := packet.Layer(layers.LayerTypeIPv4) + if ipLayer == nil { + continue + } + ipPacket, _ := ipLayer.(*layers.IPv4) + innerPacket := gopacket.NewPacket(ipPacket.Payload, ipPacket.NextLayerType(), gopacket.Default) + ipInnerLayer := innerPacket.Layer(layers.LayerTypeIPv4) + if ipInnerLayer != nil { + if len(outDstIP) == 2 { + if ipPacket.DstIP.String() != outDstIP[0] || ipPacket.DstIP.String() != outDstIP[1] { + t.Errorf("Packets are not encapsulated as expected") + } + } else { + if ipPacket.DstIP.String() != outDstIP[0] { + t.Errorf("Packets are not encapsulated as expected") + } + } + t.Logf("Traffic for encap routes passed.") + break + } + } +} diff --git a/feature/gribi/otg_tests/gribi_route_test/metadata.textproto b/feature/gribi/otg_tests/gribi_route_test/metadata.textproto new file mode 100644 index 00000000000..333a3e00ed4 --- /dev/null +++ b/feature/gribi/otg_tests/gribi_route_test/metadata.textproto @@ -0,0 +1,55 @@ +# proto-file: github.com/openconfig/featureprofiles/proto/metadata.proto +# proto-message: Metadata + +uuid: "8beaac46-9b7b-49c4-9bde-62ad630aa6c7" +plan_id: "RT-14.2" +description: "GRIBI Route Test" +testbed: TESTBED_DUT_ATE_4LINKS + +platform_exceptions: { + platform: { + vendor: CISCO + } + deviations: { + gribi_mac_override_with_static_arp: true + interface_ref_interface_id_format: true + pf_require_match_default_rule: true + pf_require_sequential_order_pbr_rules: true + ttl_copy_unsupported: true + isis_single_topology_required: true + } +} +platform_exceptions: { + platform: { + vendor: NOKIA + } + deviations: { + explicit_port_speed: true + explicit_interface_in_default_vrf: true + aggregate_atomic_update: true + interface_enabled: true + missing_value_for_defaults: true + missing_isis_interface_afi_safi_enable: true + } +} + +platform_exceptions: { + platform: { + vendor: ARISTA + } + deviations: { + interface_enabled: true + default_network_instance: "default" + omit_l2_mtu: true + isis_instance_enabled_required: true + isis_interface_afi_unsupported: true + missing_isis_interface_afi_safi_enable: true + isis_require_same_l1_metric_with_l2_metric: true + route_policy_under_afi_unsupported: true + static_protocol_name: "STATIC" + aggregate_atomic_update: true + missing_value_for_defaults: true + max_ecmp_paths: true + explicit_interface_in_default_vrf: false + } +} diff --git a/feature/gribi/otg_tests/gribi_scaling/gribi_scaling_test.go b/feature/gribi/otg_tests/gribi_scaling/gribi_scaling_test.go index 0d601a390aa..deb328c20c9 100644 --- a/feature/gribi/otg_tests/gribi_scaling/gribi_scaling_test.go +++ b/feature/gribi/otg_tests/gribi_scaling/gribi_scaling_test.go @@ -315,17 +315,37 @@ func TestScaling(t *testing.T) { }, ) createFlow(t, ate, top, vrfConfigs[1]) - + var maxEntries int = 10000 for _, vrfConfig := range vrfConfigs { entries := append(vrfConfig.NHs, vrfConfig.NHGs...) entries = append(entries, vrfConfig.V4Entries...) - client.Modify().AddEntry(t, entries...) - if err := awaitTimeout(ctx, client, t, 5*time.Minute); err != nil { - t.Fatalf("Could not program entries, got err: %v", err) + // Breaking more than 10k gribi entries from 1 modify operation into multiple + // modify operations with 10k entries each. + if len(entries) > maxEntries { + index := 0 + for idx := 0; idx < len(entries)/maxEntries; idx++ { + client.Modify().AddEntry(t, entries[index:maxEntries+index]...) + if err := awaitTimeout(ctx, client, t, 5*time.Minute); err != nil { + t.Fatalf("Could not program entries, got err: %v", err) + } + index += maxEntries + } + // Program the remaining entries less than 10k in another modify operation. + if len(entries)%maxEntries != 0 { + client.Modify().AddEntry(t, entries[index:]...) + if err := awaitTimeout(ctx, client, t, 5*time.Minute); err != nil { + t.Fatalf("Could not program entries, got err: %v", err) + } + } + + } else { + client.Modify().AddEntry(t, entries...) + if err := awaitTimeout(ctx, client, t, 5*time.Minute); err != nil { + t.Fatalf("Could not program entries, got err: %v", err) + } } t.Logf("Created %d NHs, %d NHGs, %d IPv4Entries in %s VRF", len(vrfConfig.NHs), len(vrfConfig.NHGs), len(vrfConfig.V4Entries), vrfConfig.Name) } - checkTraffic(t, ate, top) } diff --git a/feature/gribi/otg_tests/mpls_in_udp/README.md b/feature/gribi/otg_tests/mpls_in_udp/README.md new file mode 100644 index 00000000000..ad88513609d --- /dev/null +++ b/feature/gribi/otg_tests/mpls_in_udp/README.md @@ -0,0 +1,324 @@ +# TE-18.1 gRIBI MPLS in UDP Encapsulation and Decapsulation + +Create AFT entries using gRIBI to match on next hop group in a +network-instance and encapsulate the matching packets in MPLS in UDP. + +Create a policy routing configuration using gNMI to decapsulate MPLS +in UDP packets which are sent to a loopback address and apply to +the DUT. + +The MPLS in UDP encapsulation is expected to follow +[rfc7510](https://datatracker.ietf.org/doc/html/rfc7510#section-3), +but relaxing the requirement for a well-known destination UDP port. gRIBI is +expected to be able to set the destination UDP port. + +## Topology + +* [`featureprofiles/topologies/atedut_2.testbed`](https://github.com/openconfig/featureprofiles/blob/main/topologies/atedut_2.testbed) + +## Test setup + +TODO: Complete test environment setup steps + +inner_ipv6_dst_A = "2001:aa:bb::1/128" +inner_ipv6_dst_B = "2001:aa:bb::2/128" +inner_ipv6_default = "::/0" + +ipv4_inner_dst_A = "10.5.1.1/32" +ipv4_inner_dst_B = "10.5.1.2/32" +ipv4_inner_default = "0.0.0.0/0" + +outer_ipv6_src = "2001:f:a:1::0" +outer_ipv6_dst_A = "2001:f:c:e::1" +outer_ipv6_dst_B = "2001:f:c:e::2" +outer_ipv6_dst_def = "2001:1:1:1::0" +outer_dst_udp_port = "6635" +outer_dscp = "26" +outer_ip-ttl = "64" + +## Procedure + +### TE-18.1.1 Match and Encapsulate using gRIBI aft modify + +#### gRIBI RPC content + +The gRIBI client should send this proto message to the DUT to create AFT +entries. See [OC AFT Encap PR in progress](https://github.com/openconfig/public/pull/1153) +for the new OC AFT model nodes needed for this. + +TODO: The +[gRIBI v1 protobuf defintions](https://github.com/openconfig/gribi/blob/master/v1/proto/README.md) +will be generated from the afts tree. + +```proto +network_instances: { + network_instance: { + afts { + # + # entries used for "group_A" + ipv6_unicast { + ipv6_entry { + prefix: "inner_ipv6_dst_A" # this is an IPv6 entry for the origin/inner packet. + next_hop_group: 100 + } + } + ipv4_unicast { + ipv4_entry { + prefix: "ipv4_inner_dst_A" # this is an IPv4 entry for the origin/inner packet. + next_hop_group: 100 + } + } + next_hop_groups { + next_hop_group { + id: 100 + next_hops { # reference to a next-hop + next_hop: { + index: 100 + } + } + } + } + next_hops { + next_hop { + index: 100 + network_instance: "group_A" + encap-headers { + encap-header { + index: 1 + pushed_mpls_label_stack: [100,] + } + } + encap-headers { + encap-header { + index: 2 + src_ip: "outer_ipv6_src" + dst_ip: "outer_ipv6_dst_A" + dst_udp_port: "outer_dst_udp_port" + ip_ttl: "outer_ip-ttl" + dscp: "outer_dscp" + } + } + } + } + # + # entries used for "group_B" + ipv6_unicast { + ipv6_entry { + prefix: "inner_ipv6_dst_B" + next_hop_group: 200 + } + } + ipv4_unicast { + ipv4_entry { + prefix: "ipv4_inner_dst_B" + next_hop_group: 200 + } + } + next_hop_groups { + next_hop_group { + id: 200 + next_hops { # reference to a next-hop + next_hop: { + index: 200 + } + } + } + } + next_hops { + next_hop { + index: 200 + network_instance: "group_B" + encap-headers { + encap-header { + index: 1 + type : OPENCONFIG_AFT_TYPES:MPLS + mpls { + pushed_mpls_label_stack: [200,] + } + } + } + encap-headers { + encap-header { + index: 2 + type: OPENCONFIG_AFT_TYPES:UDP + udp { + src_ip: "outer_ipv6_src" + dst_ip: "outer_ipv6_dst_B" + dst_udp_port: "outer_dst_udp_port" + ip_ttl: "outer_ip-ttl" + dscp: "outer_dscp" + } + } + } + } + } + } + } +} +``` + +* Send traffic from ATE port 1 to DUT port 1 +* Validate afts next hop counters +* Using OTG, validate ATE port 2 receives MPLS-IN-UDP packets + * Validate destination IPs are outer_ipv6_dst_A and outer_ipv6_dst_B + * Validate MPLS label is set + +### TE-18.1.2 Validate prefix match rule for MPLS in GRE encap using default route + +Canonical OpenConfig for policy forwarding, matching IP prefix with action +encapsulate in GRE. + +```yaml +openconfig-network-instance: + network-instances: + - network-instance: "group_A" + afts: + policy-forwarding: + policies: + policy: "default encap rule" + config: + policy-id: "default encap rule" + type: PBR_POLICY + rules: + rule: 1 + config: + sequence-id: 1 + ipv6: + config: + destination-address: "inner_ipv6_default" + action: + encapsulate-mpls-in-gre: # TODO: add to OC model/PR in progress + targets: + target: "default_dst_1" + config: + id: "default_dst_1" + network-instance: "DEFAULT" + source-ip: "outer_ipv6_src" + destination-ip: "outer_ipv6_dst_def" + ip-ttl: outer_ip-ttl + dscp: outer_dscp + inner-ttl-min: 2 +``` + +* Generate the policy forwarding configuration +* Push the configuration to DUT using gnmi.Set with REPLACE option +* Configure ATE port 1 with traffic flow which does not match any AFT next hop route +* Generate traffic from ATE port 1 to ATE port 2 +* Validate ATE port 2 receives GRE traffic with correct inner and outer IPs + +### TE-18.1.3 - MPLS in GRE decapsulation set by gNMI + +Canonical OpenConfig for policy forwarding, matching IP prefix with action +decapsulate in GRE. # TODO: Move to dedicated README + +```yaml +openconfig-network-instance: + network-instances: + - network-instance: "DEFAULT" + afts: + policy-forwarding: + policies: + policy: "default decap rule" + config: + policy-id: "default decap rule" + type: PBR_POLICY + rules: + rule: 1 + config: + sequence-id: 1 + ipv6: + config: + destination-address: "decap_loopback_ipv6" + action: + decapsulate-mpls-in-gre: TRUE # TODO: add to OC model/PR in progress +``` + +* Push the gNMI the policy forwarding configuration +* Push the configuration to DUT using gnmi.Set with REPLACE option +* Configure ATE port 1 with traffic flow which matches the decap loopback IP address +* Generate traffic from ATE port 1 +* Validate ATE port 2 receives packets with correct VLAN and the inner inner_decap_ipv6 + +### TE-18.1.4 - MPLS in UDP decapsulation set by gNMI + +Canonical OpenConfig for policy forwarding, matching IP prefix with action +decapsulate MPLS in UDP. # TODO: Move to dedicated README + +```yaml +openconfig-network-instance: + network-instances: + - network-instance: "DEFAULT" + afts: + policy-forwarding: + policies: + policy: "default decap rule" + config: + policy-id: "default decap rule" + type: PBR_POLICY + rules: + rule: 1 + config: + sequence-id: 1 + ipv6: + config: + destination-address: "decap_loopback_ipv6" + action: + decapsulate-mpls-in-udp: TRUE +``` + +* Push the gNMI the policy forwarding configuration +* Push the configuration to DUT using gnmi.Set with REPLACE option +* Configure ATE port 1 with traffic flow + * Flow should have a packet encap format : outer_decap_udp_ipv6 <- MPLS label <- inner_decap_ipv6 +* Generate traffic from ATE port 1 +* Validate ATE port 2 receives the innermost IPv4 traffic with correct VLAN and inner_decap_ipv6 + +### TE-18.1.5 - Policy forwarding to encap and forward for BGP packets + +TODO: Specify a solution for ensuring BGP packets are matched, encapsulated +and forwarding to a specified destination using OC policy-forwarding terms. + +## OpenConfig Path and RPC Coverage + +```yaml +paths: + +# afts state paths set via gRIBI + # TODO: https://github.com/openconfig/public/pull/1153 + + #/network-instances/network-instance/afts/next-hop-groups/next-hop-group/state/id: + #/network-instances/network-instance/afts/next-hop-groups/next-hop-group/state/next-hop-group-id: + #/network-instances/network-instance/afts/next-hop-groups/next-hop-group/next-hops/next-hop/state/index: + #/network-instances/network-instance/afts/next-hop-groups/next-hop-group/next-hops/next-hop/state/network-instance: + #/network-instances/network-instance/afts/next-hops/next-hop/encap-headers/encap-header/state/index: + #/network-instances/network-instance/afts/next-hops/next-hop/encap-headers/encap-header/state/type: + #/network-instances/network-instance/afts/next-hops/next-hop/encap-headers/encap-header/state/mpls/pushed-mpls-label-stack: + #/network-instances/network-instance/afts/next-hops/next-hop/encap-headers/encap-header/state/udp/src-ip: + #/network-instances/network-instance/afts/next-hops/next-hop/encap-headers/encap-header/state/udp/dst-ip: + #/network-instances/network-instance/afts/next-hops/next-hop/encap-headers/encap-header/state/udp/dst-udp-port: + #/network-instances/network-instance/afts/next-hops/next-hop/encap-headers/encap-header/state/udp/ip-ttl: + #/network-instances/network-instance/afts/next-hops/next-hop/encap-headers/encap-header/state/udp/dscp: + +# afts next-hop counters + /network-instances/network-instance/afts/next-hops/next-hop/state/counters/packets-forwarded: + /network-instances/network-instance/afts/next-hops/next-hop/state/counters/octets-forwarded: + + +rpcs: + gnmi: + gNMI.Set: + union_replace: true + replace: true + gNMI.Subscribe: + on_change: true + gribi: + gRIBI.Modify: + network-instances:network-instance:afts:next-hops:next-hop:encapsulate_header: + network-instances:network-instance:afts:next-hops:next-hop:mpls-in-udp: + network-instances:network-instance:afts:next-hops:next-hop:decapsulate_header: + gRIBI.Flush: +``` + +## Required DUT platform + +* FFF diff --git a/feature/experimental/gribi/otg_tests/route_addition_during_failover_test/README.md b/feature/gribi/otg_tests/route_addition_during_failover_test/README.md similarity index 100% rename from feature/experimental/gribi/otg_tests/route_addition_during_failover_test/README.md rename to feature/gribi/otg_tests/route_addition_during_failover_test/README.md diff --git a/feature/experimental/gribi/otg_tests/route_addition_during_failover_test/metadata.textproto b/feature/gribi/otg_tests/route_addition_during_failover_test/metadata.textproto similarity index 100% rename from feature/experimental/gribi/otg_tests/route_addition_during_failover_test/metadata.textproto rename to feature/gribi/otg_tests/route_addition_during_failover_test/metadata.textproto diff --git a/feature/experimental/gribi/otg_tests/route_addition_during_failover_test/route_addition_during_failover_test.go b/feature/gribi/otg_tests/route_addition_during_failover_test/route_addition_during_failover_test.go similarity index 100% rename from feature/experimental/gribi/otg_tests/route_addition_during_failover_test/route_addition_during_failover_test.go rename to feature/gribi/otg_tests/route_addition_during_failover_test/route_addition_during_failover_test.go diff --git a/feature/experimental/gribi/otg_tests/route_removal_during_failover_test/README.md b/feature/gribi/otg_tests/route_removal_during_failover_test/README.md similarity index 100% rename from feature/experimental/gribi/otg_tests/route_removal_during_failover_test/README.md rename to feature/gribi/otg_tests/route_removal_during_failover_test/README.md diff --git a/feature/experimental/gribi/otg_tests/route_removal_during_failover_test/metadata.textproto b/feature/gribi/otg_tests/route_removal_during_failover_test/metadata.textproto similarity index 100% rename from feature/experimental/gribi/otg_tests/route_removal_during_failover_test/metadata.textproto rename to feature/gribi/otg_tests/route_removal_during_failover_test/metadata.textproto diff --git a/feature/experimental/gribi/otg_tests/route_removal_during_failover_test/route_removal_during_failover_test.go b/feature/gribi/otg_tests/route_removal_during_failover_test/route_removal_during_failover_test.go similarity index 100% rename from feature/experimental/gribi/otg_tests/route_removal_during_failover_test/route_removal_during_failover_test.go rename to feature/gribi/otg_tests/route_removal_during_failover_test/route_removal_during_failover_test.go diff --git a/feature/gribi/otg_tests/static_lsp_test/static_lsp_test.go b/feature/gribi/otg_tests/static_lsp_test/static_lsp_test.go index 712f8ebed32..46ad3a5a7c1 100644 --- a/feature/gribi/otg_tests/static_lsp_test/static_lsp_test.go +++ b/feature/gribi/otg_tests/static_lsp_test/static_lsp_test.go @@ -142,14 +142,18 @@ func configureOTG(t *testing.T) gosnappi.Config { // configureStaticLSP configures a static MPLS LSP with the provided parameters. func configureStaticLSP(t *testing.T, dut *ondatra.DUTDevice, lspName string, incomingLabel uint32, nextHopIP string) { d := &oc.Root{} - mplsCfg := d.GetOrCreateNetworkInstance(deviations.DefaultNetworkInstance(dut)).GetOrCreateMpls() + dni := deviations.DefaultNetworkInstance(dut) + defPath := gnmi.OC().NetworkInstance(deviations.DefaultNetworkInstance(dut)) + gnmi.Update(t, dut, defPath.Config(), &oc.NetworkInstance{ + Name: ygot.String(deviations.DefaultNetworkInstance(dut)), + Type: oc.NetworkInstanceTypes_NETWORK_INSTANCE_TYPE_DEFAULT_INSTANCE, + }) + mplsCfg := d.GetOrCreateNetworkInstance(dni).GetOrCreateMpls() staticMplsCfg := mplsCfg.GetOrCreateLsps().GetOrCreateStaticLsp(lspName) staticMplsCfg.GetOrCreateEgress().SetIncomingLabel(oc.UnionUint32(incomingLabel)) staticMplsCfg.GetOrCreateEgress().SetNextHop(nextHopIP) staticMplsCfg.GetOrCreateEgress().SetPushLabel(oc.Egress_PushLabel_IMPLICIT_NULL) - gnmi.Update(t, dut, gnmi.OC().NetworkInstance(deviations.DefaultNetworkInstance(dut)).Mpls().Config(), mplsCfg) - } func createTrafficFlow(t *testing.T, diff --git a/feature/experimental/gribi/otg_tests/vrf_policy_driven_te/README.md b/feature/gribi/otg_tests/vrf_policy_driven_te/README.md similarity index 100% rename from feature/experimental/gribi/otg_tests/vrf_policy_driven_te/README.md rename to feature/gribi/otg_tests/vrf_policy_driven_te/README.md diff --git a/feature/experimental/gribi/otg_tests/vrf_policy_driven_te/metadata.textproto b/feature/gribi/otg_tests/vrf_policy_driven_te/metadata.textproto similarity index 100% rename from feature/experimental/gribi/otg_tests/vrf_policy_driven_te/metadata.textproto rename to feature/gribi/otg_tests/vrf_policy_driven_te/metadata.textproto diff --git a/feature/experimental/gribi/otg_tests/vrf_policy_driven_te/vrf_policy_driven_te_test.go b/feature/gribi/otg_tests/vrf_policy_driven_te/vrf_policy_driven_te_test.go similarity index 100% rename from feature/experimental/gribi/otg_tests/vrf_policy_driven_te/vrf_policy_driven_te_test.go rename to feature/gribi/otg_tests/vrf_policy_driven_te/vrf_policy_driven_te_test.go diff --git a/feature/gribi/vrf_policy_driven_te/README.md b/feature/gribi/vrf_policy_driven_te/README.md deleted file mode 100644 index 41630244a0d..00000000000 --- a/feature/gribi/vrf_policy_driven_te/README.md +++ /dev/null @@ -1,819 +0,0 @@ -# TE-17.1 VRF selection policy driven TE - -## Summary - -Test VRF selection logic involving different decapsulation and encapsulation lookup scenarios via gRIBI. - -## Topology - -ATE port-1 <------> port-1 DUT -DUT port-2 <------> port-2 ATE -DUT port-3 <------> port-3 ATE -DUT port-4 <------> port-4 ATE -DUT port-5 <------> port-5 ATE -DUT port-6 <------> port-6 ATE -DUT port-7 <------> port-7 ATE -DUT port-8 <------> port-8 ATE - -## Variables - -``` -# DSCP value that will be matched to ENCAP_TE_VRF_A -* dscp_encap_a_1 = 10 -* dscp_encap_a_2 = 18 - -# DSCP value that will be matched to ENCAP_TE_VRF_B -* dscp_encap_b_1 = 20 -* dscp_encap_b_2 = 28 - -# DSCP value that will NOT be matched to any VRF for encapsulation. -* dscp_encap_no_match = 30 - -# Magic source IP addresses used in VRF selection policy -* ipv4_outer_src_111 = 198.51.100.111 -* ipv4_outer_src_222 = 198.51.100.222 - -# Magic destination MAC address -* magic_mac = 02:00:00:00:00:01` -``` - -vrf_selection_policy_c -``` -network-instances { - network-instance { - name: DEFAULT - policy-forwarding { - policies { - policy { - policy-id: "vrf_selection_policy_c" - rules { - rule { - sequence-id: 1 - ipv4 { - protocol: 4 - dscp-set: [dscp_encap_a_1, dscp_encap_a_2] - source-address: "ipv4_outer_src_222" - } - action { - decap-network-instance: "DECAP_TE_VRF" - post-network-instance: "ENCAP_TE_VRF_A" - decap-fallback-network-instance: "TE_VRF_222" - } - } - rule { - sequence-id: 2 - ipv4 { - protocol: 41 - dscp-set: [dscp_encap_a_1, dscp_encap_a_2] - source-address: "ipv4_outer_src_222" - } - action { - decap-network-instance: "DECAP_TE_VRF" - post-network-instance: "ENCAP_TE_VRF_A" - decap-fallback-network-instance: "TE_VRF_222" - } - } - rule { - sequence-id: 3 - ipv4 { - protocol: 4 - dscp-set: [dscp_encap_a_1, dscp_encap_a_2] - source-address: "ipv4_outer_src_111" - } - action { - decap-network-instance: "DECAP_TE_VRF" - post-network-instance: "ENCAP_TE_VRF_A" - decap-fallback-network-instance: "TE_VRF_111" - } - } - rule { - sequence-id: 4 - ipv4 { - protocol: 41 - dscp-set: [dscp_encap_a_1, dscp_encap_a_2] - source-address: "ipv4_outer_src_111" - } - action { - decap-network-instance: "DECAP_TE_VRF" - post-network-instance: "ENCAP_TE_VRF_A" - decap-fallback-network-instance: "TE_VRF_111" - } - } - rule { - sequence-id: 5 - ipv4 { - protocol: 4 - dscp-set: [dscp_encap_b_1, dscp_encap_b_2] - source-address: "ipv4_outer_src_222" - } - action { - decap-network-instance: "DECAP_TE_VRF" - post-network-instance: "ENCAP_TE_VRF_B" - decap-fallback-network-instance: "TE_VRF_222" - } - } - rule { - sequence-id: 6 - ipv4 { - protocol: 41 - dscp-set: [dscp_encap_b_1, dscp_encap_b_2] - source-address: "ipv4_outer_src_222" - } - action { - decap-network-instance: "DECAP_TE_VRF" - post-network-instance: "ENCAP_TE_VRF_B" - decap-fallback-network-instance: "TE_VRF_222" - } - } - rule { - sequence-id: 7 - ipv4 { - protocol: 4 - dscp-set: [dscp_encap_b_1, dscp_encap_b_2] - source-address: "ipv4_outer_src_111" - } - action { - decap-network-instance: "DECAP_TE_VRF" - post-network-instance: "ENCAP_TE_VRF_B" - decap-fallback-network-instance: "TE_VRF_111" - } - } - rule { - sequence-id: 8 - ipv4 { - protocol: 41 - dscp-set: [dscp_encap_b_1, dscp_encap_b_2] - source-address: "ipv4_outer_src_111" - } - action { - decap-network-instance: "DECAP_TE_VRF" - post-network-instance: "ENCAP_TE_VRF_B" - decap-fallback-network-instance: "TE_VRF_111" - } - } - rule { - sequence-id: 9 - ipv4 { - protocol: 4 - source-address: "ipv4_outer_src_222" - } - action { - decap-network-instance: "DECAP_TE_VRF" - post-network-instance: "DEFAULT" - decap-fallback-network-instance: "TE_VRF_222" - } - } - rule { - sequence-id: 10 - ipv4 { - protocol: 41 - source-address: "ipv4_outer_src_222" - } - action { - decap-network-instance: "DECAP_TE_VRF" - post-network-instance: "DEFAULT" - decap-fallback-network-instance: "TE_VRF_222" - } - } - rule { - sequence-id: 11 - ipv4 { - protocol: 4 - source-address: "ipv4_outer_src_111" - } - action { - decap-network-instance: "DECAP_TE_VRF" - post-network-instance: "DEFAULT" - decap-fallback-network-instance: "TE_VRF_111" - } - } - rule { - sequence-id: 12 - ipv4 { - protocol: 41 - source-address: "ipv4_outer_src_111" - } - action { - decap-network-instance: "DECAP_TE_VRF" - post-network-instance: "DEFAULT" - decap-fallback-network-instance: "TE_VRF_111" - } - } - rule { - sequence-id: 13 - ipv4 { - dscp-set: [dscp_encap_a_1, dscp_encap_a_2] - } - action { - network-instance: "ENCAP_TE_VRF_A" - } - } - rule { - sequence-id: 14 - ipv6 { - dscp-set: [dscp_encap_a_1, dscp_encap_a_2] - } - action { - network-instance: "ENCAP_TE_VRF_A" - } - } - rule { - sequence-id: 15 - ipv4 { - dscp-set: [dscp_encap_b_1, dscp_encap_b_2] - } - action { - network-instance: "ENCAP_TE_VRF_B" - } - } - rule { - sequence-id: 16 - ipv6 { - dscp-set: [dscp_encap_b_1, dscp_encap_b_2] - } - action { - network-instance: "ENCAP_TE_VRF_B" - } - } - rule { - sequence-id: 17 - action { - network-instance: "DEFAULT" - } - } - } - } - } - } - } -} -``` - -vrf_selection_policy_w -``` -network-instances { - network-instance { - name: DEFAULT - policy-forwarding { - policies { - policy { - policy-id: "vrf_selection_policy_w" - rules { - rule { - sequence-id: 1 - ipv4 { - protocol: 4 - dscp-set: [dscp_encap_a_1, dscp_encap_a_2] - source-address: "ipv4_outer_src_222" - } - action { - decap-network-instance: "DECAP_TE_VRF" - post-network-instance: "ENCAP_TE_VRF_A" - decap-fallback-network-instance: "TE_VRF_222" - } - } - rule { - sequence-id: 2 - ipv4 { - protocol: 41 - dscp-set: [dscp_encap_a_1, dscp_encap_a_2] - source-address: "ipv4_outer_src_222" - } - action { - decap-network-instance: "DECAP_TE_VRF" - post-network-instance: "ENCAP_TE_VRF_A" - decap-fallback-network-instance: "TE_VRF_222" - } - } - rule { - sequence-id: 3 - ipv4 { - protocol: 4 - dscp-set: [dscp_encap_a_1, dscp_encap_a_2] - source-address: "ipv4_outer_src_111" - } - action { - decap-network-instance: "DECAP_TE_VRF" - post-network-instance: "ENCAP_TE_VRF_A" - decap-fallback-network-instance: "TE_VRF_111" - } - } - rule { - sequence-id: 4 - ipv4 { - protocol: 41 - dscp-set: [dscp_encap_a_1, dscp_encap_a_2] - source-address: "ipv4_outer_src_111" - } - action { - decap-network-instance: "DECAP_TE_VRF" - post-network-instance: "ENCAP_TE_VRF_A" - decap-fallback-network-instance: "TE_VRF_111" - } - } - rule { - sequence-id: 5 - ipv4 { - protocol: 4 - dscp-set: [dscp_encap_b_1, dscp_encap_b_2] - source-address: "ipv4_outer_src_222" - } - action { - decap-network-instance: "DECAP_TE_VRF" - post-network-instance: "ENCAP_TE_VRF_B" - decap-fallback-network-instance: "TE_VRF_222" - } - } - rule { - sequence-id: 6 - ipv4 { - protocol: 41 - dscp-set: [dscp_encap_b_1, dscp_encap_b_2] - source-address: "ipv4_outer_src_222" - } - action { - decap-network-instance: "DECAP_TE_VRF" - post-network-instance: "ENCAP_TE_VRF_B" - decap-fallback-network-instance: "TE_VRF_222" - } - } - rule { - sequence-id: 7 - ipv4 { - protocol: 4 - dscp-set: [dscp_encap_b_1, dscp_encap_b_2] - source-address: "ipv4_outer_src_111" - } - action { - decap-network-instance: "DECAP_TE_VRF" - post-network-instance: "ENCAP_TE_VRF_B" - decap-fallback-network-instance: "TE_VRF_111" - } - } - rule { - sequence-id: 8 - ipv4 { - protocol: 41 - dscp-set: [dscp_encap_b_1, dscp_encap_b_2] - source-address: "ipv4_outer_src_111" - } - action { - decap-network-instance: "DECAP_TE_VRF" - post-network-instance: "ENCAP_TE_VRF_B" - decap-fallback-network-instance: "TE_VRF_111" - } - } - rule { - sequence-id: 9 - ipv4 { - protocol: 4 - source-address: "ipv4_outer_src_222" - } - action { - decap-network-instance: "DECAP_TE_VRF" - post-network-instance: "DEFAULT" - decap-fallback-network-instance: "TE_VRF_222" - } - } - rule { - sequence-id: 10 - ipv4 { - protocol: 41 - source-address: "ipv4_outer_src_222" - } - action { - decap-network-instance: "DECAP_TE_VRF" - post-network-instance: "DEFAULT" - decap-fallback-network-instance: "TE_VRF_222" - } - } - rule { - sequence-id: 11 - ipv4 { - protocol: 4 - source-address: "ipv4_outer_src_111" - } - action { - decap-network-instance: "DECAP_TE_VRF" - post-network-instance: "DEFAULT" - decap-fallback-network-instance: "TE_VRF_111" - } - } - rule { - sequence-id: 12 - ipv4 { - protocol: 41 - source-address: "ipv4_outer_src_111" - } - action { - decap-network-instance: "DECAP_TE_VRF" - post-network-instance: "DEFAULT" - decap-fallback-network-instance: "TE_VRF_111" - } - } - rule { - sequence-id: 13 - action { - network-instance: "DEFAULT" - } - } - } - } - } - } - } -} -``` - -## Baseline - -* Install the following gRIBI AFTs. - -``` -IPv4Entry {138.0.11.0/24 (ENCAP_TE_VRF_A)} -> NHG#101 (DEFAULT VRF) -> { - {NH#101, DEFAULT VRF, weight:1}, - {NH#102, DEFAULT VRF, weight:3}, - backup_next_hop_group: 200 // in case specific vendor implementation or bugs pruned the NHs. -} -IPv4Entry {138.0.11.0/24 (ENCAP_TE_VRF_B)} -> NHG#102 (DEFAULT VRF) -> { - {NH#101, DEFAULT VRF, weight:3}, - {NH#102, DEFAULT VRF, weight:1}, - backup_next_hop_group: 200 // in case specific vendor implementation or bugs pruned the NHs. -} -NH#101 -> { - encapsulate_header: OPENCONFIGAFTTYPESENCAPSULATIONHEADERTYPE_IPV4 - ip_in_ip { - dst_ip: "203.0.113.1" - src_ip: "ipv4_outer_src_111" - } - network_instance: "TE_VRF_111" -} -NH#102 -> { - encapsulate_header: OPENCONFIGAFTTYPESENCAPSULATIONHEADERTYPE_IPV4 - ip_in_ip { - dst_ip: "203.10.113.2" - src_ip: "ipv4_outer_src_111" - } - network_instance: "TE_VRF_111" -} - -NHG#200 (Default VRF) { - {NH#200, DEFAULT VRF, weight:1} -} -NH#200 -> { - network_instance: "DEFAULT" -} - -IPv4Entry {203.0.113.1/32 (TE_VRF_111)} -> NHG#1 (DEFAULT VRF) -> { - {NH#1, DEFAULT VRF, weight:1,ip_address=192.0.2.101}, - {NH#2, DEFAULT VRF, weight:3,ip_address=192.0.2.102}, - backup_next_hop_group: 1000 // re-encap to 203.0.113.100 -} -IPv4Entry {192.0.2.101/32 (DEFAULT VRF)} -> NHG#11 (DEFAULT VRF) -> { - {NH#11, DEFAULT VRF, weight:1,mac_address:magic_mac, interface-ref:dut-port-2-interface}, - {NH#12, DEFAULT VRF, weight:3,mac_address:magic_mac, interface-ref:dut-port-3-interface}, -} -IPv4Entry {192.0.2.102/32 (DEFAUlT VRF)} -> NHG#12 (DEFAULT VRF) -> { - {NH#13, DEFAULT VRF, weight:2,mac_address:magic_mac, interface-ref:dut-port-4-interface}, -} - -NHG#1000 (Default VRF) { - {NH#1000, DEFAULT VRF} -} -NH#1000 -> { - decapsulate_header: OPENCONFIGAFTTYPESENCAPSULATIONHEADERTYPE_IPV4 - encapsulate_header: OPENCONFIGAFTTYPESENCAPSULATIONHEADERTYPE_IPV4 - ip_in_ip { - dst_ip: "203.0.113.100" - src_ip: "ipv4_outer_src_222" - } - network_instance: "TE_VRF_222" -} - -IPv4Entry {203.0.113.100/32 (TE_VRF_222)} -> NHG#2 (DEFAULT VRF) -> { - {NH#3, DEFAULT VRF, weight:1,ip_address=192.0.2.103}, - backup_next_hop_group: 1001 // decap to DEFAULT VRF -} -IPv4Entry {192.0.2.103/32 (DEFAULT VRF)} -> NHG#13 (DEFAULT VRF) -> { - {NH#14, DEFAULT VRF, weight:1,mac_address:magic_mac, interface-ref:dut-port-5-interface}, -} -NHG#1001 (Default VRF) { - {NH#2001, DEFAULT VRF, weight:1} -} -NH#1001 -> { - decapsulate_header: OPENCONFIGAFTTYPESENCAPSULATIONHEADERTYPE_IPV4 - network_instance: "DEFAULT" -} - -// 203.10.113.2 is the tunnel IP address. Note that the NHG#3 is different than NHG#1. - -IPv4Entry {203.10.113.2/32 (TE_VRF_111)} -> NHG#3 (DEFAULT VRF) -> { - {NH#4, DEFAULT VRF, weight:1,ip_address=192.0.2.104}, - backup_next_hop_group: 1002 // re-encap to 203.10.113.101 -} -IPv4Entry {192.0.2.104/32 (DEFAULT VRF)} -> NHG#14 (DEFAULT VRF) -> { - {NH#15, DEFAULT VRF, weight:1,mac_address:magic_mac, interface-ref:dut-port-6-interface}, -} -NHG#1002 (DEFAULT VRF) { - {NH#1002, DEFAULT VRF} -} -NH#1002 -> { - decapsulate_header: OPENCONFIGAFTTYPESENCAPSULATIONHEADERTYPE_IPV4 - encapsulate_header: OPENCONFIGAFTTYPESENCAPSULATIONHEADERTYPE_IPV4 - ip_in_ip { - dst_ip: "203.0.113.101" - src_ip: "ipv4_outer_src_222" - } - network_instance: "TE_VRF_222" -} -IPv4Entry {203.0.113.101/32 (TE_VRF_222)} -> NHG#4 (DEFAULT VRF) -> { - {NH#5, DEFAULT VRF, weight:1,ip_address=192.0.2.103}, - backup_next_hop_group: 1001 // decap to DEFAULT VRF -} -IPv4Entry {192.0.2.103/32 (DEFAULT VRF)} -> NHG#15 (DEFAULT VRF) -> { - {NH#16, DEFAULT VRF, weight:1,mac_address:magic_mac, interface-ref:dut-port-7-interface}, -} - -``` - -* Install a BGP route resolved by ISIS in default VRF to rout traffic out of DUT port-8. - -* Install an 0/0 static route in ENCAP_VRF_A and ENCAP_VRF_B pointing to the DEFAULT VRF. - -## Procedure - -The DUT should be reset to the baseline after each of the following tests. - -#### Test-1, match on source and protocol, no match on DSCP; flow VRF_DECAP hit -> DEFAULT - -1. Using gRIBI to install the following entries in the `DECAP_TE_VRF`: - - ``` - IPv4Entry {192.51.100.1/24 (DECAP_TE_VRF)} -> NHG#1001 (DEFAULT VRF) -> { - {NH#1001, DEFAULT VRF, weight:1} - } - NH#1001 -> { - decapsulate_header: OPENCONFIGAFTTYPESDECAPSULATIONHEADERTYPE_IPV4 - } - ``` - -2. Apply vrf selection policy `vrf_selection_policy_w` to DUT port-1. - -3. Send the following 6in4 and 4in4 flows to DUT port-1: - - ``` - * inner_src: `ipv4_inner_src` - * inner_dst: `ipv4_inner_encap_match` - * dscp: `dscp_encap_no_match` - * outter_src: `ipv4_outter_src_111` - * outter_dst: `ipv4_outter_decap_match` - * dscp: `dscp_encap_no_match` - * proto: `4` - - * inner_src: `ipv6_inner_src` - * inner_dst: `ipv6_inner_encap_match` - * dscp: `dscp_encap_no_match` - * outter_src: `ipv4_outter_src_111` - * outter_dst: `ipv4_outter_decap_match` - * dscp: `dscp_encap_no_match` - * proto: `41` - ``` - -4. Verify that the packets have their outer v4 header stripped and are forwarded out of DUT port-8 per the BGP-ISIS routes in the DEFAULT VRF. - -5. Verify that the TTL value is copied from the outer header to the inner header. - -6. Change the subnet mask from /24 and repeat the test for the masks /32, /22, and /28 and verify again that the packets are decapped and forwarded correctly. - -7. Repeat the test with packets with a destination address that does not match the decap entry, and verify that such packets are not decapped. - -#### Test-2, match on source, protocol and DSCP, VRF_DECAP hit -> VRF_ENCAP_A miss -> DEFAULT - -1. Using gRIBI to install the following entries in the `DECAP_TE_VRF`: - - ``` - IPv4Entry {192.51.100.1/24 (DECAP_TE_VRF)} -> NHG#1001 (DEFAULT VRF) -> { - {NH#1001, DEFAULT VRF, weight:1} - } - NH#1001 -> { - decapsulate_header: OPENCONFIGAFTTYPESDECAPSULATIONHEADERTYPE_IPV4 - } - ``` - -2. Apply vrf selection policy `vrf_selection_policy_w` to DUT port-1. - -3. Send the following 6in4 and 4in4 flows to DUT port-1: - - ``` - * inner_src: `ipv4_inner_src` - * inner_dst: `ipv4_inner_encap_no_match` - * dscp: `dscp_encap_a_1` - * outter_src: `ipv4_outter_src_111` - * outter_dst: `ipv4_outter_decap_match` - * dscp: `dscp_encap_a_1` - * proto: `4` - - * inner_src: `ipv6_inner_src` - * inner_dst: `ipv6_inner_encap_no_match` - * dscp: `dscp_encap_a_1` - * outter_src: `ipv4_outter_src_111` - * outter_dst: `ipv4_outter_decap_match` - * dscp: `dscp_encap_a_1` - * proto: `41` - ``` - -4. Verify that the packets have their outer v4 header stripped and are forwarded out of DUT port-8 per the BGP-ISIS routes in the DEFAULT VRF. - -5. Verify that the TTL value is copied from the outer header to the inner header. - -6. Change the subnet mask from /24 and repeat the test for the masks /32, /22, and /28 and verify again that the packets are decapped and forwarded correctly. - -#### Test-3, Mixed Prefix Decap gRIBI Entries - -Support for decap actions with mixed prefixes installed through gRIBI - -1. Add the following gRIBI entries: - - ``` - IPv4Entry {192.51.129.0/22 (DECAP_TE_VRF)} -> NHG#1001 (DEFAULT VRF) -> { - {NH#1001, DEFAULT VRF, weight:1} - } - IPv4Entry {192.55.200.3/32 (DECAP_TE_VRF)} -> NHG#1001 (DEFAULT VRF) -> { - {NH#1001, DEFAULT VRF, weight:1} - } - - NH#1001 -> { - decapsulate_header: OPENCONFIGAFTTYPESDECAPSULATIONHEADERTYPE_IPV4 - } - ``` - -2. Apply vrf selection policy `vrf_selection_policy_w` to DUT port-1. - -3. Send the following 6in4 and 4in4 flows to DUT port-1: - - ``` - * inner_src: `ipv4_inner_src` - * inner_dst: `ipv4_inner_encap_match` - * dscp: `dscp_encap_no_match` - * outter_src: `ipv4_outter_src_111` - * outter_dst: `192.51.100.64` - * dscp: `dscp_encap_no_match` - * proto: `4` - - * inner_src: `ipv6_inner_src` - * inner_dst: `ipv6_inner_encap_match` - * dscp: `dscp_encap_no_match` - * outter_src: `ipv4_outter_src_111` - * outter_dst: `192.55.200.3` - * dscp: `dscp_encap_no_match` - * proto: `41` - - * inner_src: `ipv4_inner_src` - * inner_dst: `ipv4_inner_encap_match` - * dscp: `dscp_encap_no_match` - * outter_src: `ipv4_outter_src_111` - * outter_dst: `192.51.128.5` - * dscp: `dscp_encap_no_match` - * proto: `4` - ``` - -4. Verify that the packets have their outer v4 header stripped, and are forwarded according to the route in the DEFAULT VRF that matches the inner IP address. - -5. Repeat the test with packets with a destination address such as that does not match the decap route, and verify that such packets are not decapped. - -#### Test-4: Tunneled traffic with no decap - -Ensures that tunneled traffic is correctly forwarded when there is no match in the DECAP_VRF. The intent of this test is to ensure that the VRF selection policy correctly sends these packets to either `TE_VRF_111` or `TE_VRF_222`. - -1. Apply vrf selection policy `vrf_selection_policy_c` to DUT port-1. -2. Send 4in4 (IP protocol 4) and 6in4 (IP protocol 41) packets to DUT port-1 where - * The outer v4 header has the destination address 203.0.113.1. - * The outer v4 header has the source address ipv4_outer_src_111. - * The outer v4 header has DSCP value has `dscp_encap_no_match` and `dscp_encap_match` -3. We should expect that all egress packets (100%) are IPinIP encapped with 203.0.113.1 as the outer header, and egress on DUT port-2, port-3, port-4 and port-6 per the hierarchical weight. -4. Send 4in4 (IP protocol 4) and 6in4 (IP protocol 41) packets to DUT port-2 where - * The outer v4 header has the destination address 203.0.113.100. - * The outer v4 header has the source address ipv4_outer_src_222. - * The outer v4 header has DSCP value has `dscp_encap_no_match` and `dscp_encap_match` -We should expect that the egress traffic are 100% encapped with 203.0.113.100 as the outer header, and egress on DUT port-5. - -#### Test-5: match on "default term", send to default VRF - -Tests support for TE disabled IPinIP IPv4 (IP protocol 4) cluster traffic arriving on WAN facing ports. Specifically, this test verifies the tunnel traffic identification using ipv4_outer_src_111 and ipv4_outer_src_222 in the VRF selection policy. - -1. Apply vrf selection policy `vrf_selection_policy_w` to DUT port-1. -2. Send 6in4 and 4in4 packets to DUT port-1, where: - * The outer v4 header has the destination address 138.0.11.8. - * The outer v4 header has the source address that’s not ipv4_outer_src_111 or ipv4_outer_src_222. For example, we can use 198.100.200.123. -3. We should expect that all egress packets: - * 100% are still IPinIP (4in4) with outer v4 destination address as `138.0.11.8`. - * and, egressed out of DUT port-8 per the route in the DEFAULT VRF. -4. Send v4 packet with protocol `17` (not 6in4 or 4in4), where: - * The outer v4 header has the destination address 138.0.11.8. - * 50% of the packets with source address as ipv4_outer_src_111. - * 50% of the packets with source address as ipv4_outer_src_222. -5. We should expect that all egress packets: - * 100% are still of protocl `17` and with outer v4 destination address as `138.0.11.8`. - * and, egressed out of DUT port-8 per the route in the DEFAULT VRF. -6. Remove the matching route (e.g. stop the BGP routes) in the DEFAULT VRF and verify that the traffic are dropped. - -#### Test-6, decap then encap - -1. Apply vrf selection policy `vrf_selection_policy_w` to DUT port-1. - -2. Send the following packets to DUT port-1: - - ``` - * inner_src: `ipv4_inner_src` - * inner_dst: `ipv4_inner_encap_match` - * dscp: `dscp_encap_a_1` - * outter_src: `ipv4_outter_src_222` - * outter_dst: `ipv4_outter_decap_match` - * dscp: `dscp_encap_a_1` - * proto: `4` - ``` - - ``` - * inner_src: `ipv6_inner_src` - * inner_dst: `ipv6_inner_encap_match` - * dscp: `dscp_encap_a_1` - * outter_src: `ipv4_outter_src_111` - * outter_dst: `ipv4_outter_decap_match` - * dscp: `dscp_encap_a_1` - * proto: `41` - ``` - -3. We should expect that all egress packets: - - * are IPinIP encapped with outer source IP as `ipv4_outter_src_111` and dscp value `dscp_encap_a_1`. - * 1/4 are with 203.0.113.1 as the outer header destination IP. - * 3/4 are with 203.10.113.2 as the outer header destination IPs. - * egress on DUT port-2, port-3, port-4 and port-6 per the hierarchical weight. - -4. Send the following packets to DUT port -1 - - ``` - * inner_src: `ipv4_inner_src` - * inner_dst: `ipv4_inner_encap_match` - * dscp: `dscp_encap_b_1` - * outter_src: `ipv4_outter_src_111` - * outter_dst: `ipv4_outter_decap_match` - * dscp: `dscp_encap_b_1` - * proto: `4` - - * inner_src: `ipv6_inner_src` - * inner_dst: `ipv6_inner_encap_match` - * dscp: `dscp_encap_b_1` - * outter_src: `ipv4_outter_src_222` - * outter_dst: `ipv4_outter_decap_match` - * dscp: `dscp_encap_b_1` - * proto: `41` - ``` - -5. We should expect that all egress packets: - - * are IPinIP encapped with outer source IP as `ipv4_outter_src_111` and dscp value `dscp_encap_b_1`. - * 3/4 are with 203.0.113.1 as the outer header destination IP. - * 1/4 are with 203.10.113.2 as the outer header destination IPs. - * egress on DUT port-2, port-3, port-4 and port-6 per the hierarchical weight. - - -## Config Parameter Coverage - -* network-instances/network-instance/name -* network-instances/network-instance/policy-forwarding/policies/policy/policy-id -* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/sequence-id -* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv4/protocol -* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv4/dscp-set -* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv4/source-address -* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv6/protocol -* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv6/dscp-set -* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv6/source-address -* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/action/decap-network-instance -* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/action/post-network-instance -* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/action/decap-fallback-network-instance - -## Telemetry Parameter Coverage - -* network-instances/network-instance/name -* network-instances/network-instance/policy-forwarding/policies/policy/policy-id -* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/sequence-id -* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv4/protocol -* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv4/dscp-set -* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv4/source-address -* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv6/protocol -* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv6/dscp-set -* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/ipv6/source-address -* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/action/decap-network-instance -* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/action/post-network-instance -* network-instances/network-instance/policy-forwarding/policies/policy/rules/rule/action/decap-fallback-network-instance - -## Protocol/RPC Parameter Coverage - -* gRIBI: - * Modify - * ModifyRequest - -## Required DUT platform - -vRX \ No newline at end of file diff --git a/feature/interface/aggregate/otg_tests/aggregate_all_not_viable_test/README.md b/feature/interface/aggregate/otg_tests/aggregate_all_not_viable_test/README.md index 5949b55c30a..29c5cfd2c02 100644 --- a/feature/interface/aggregate/otg_tests/aggregate_all_not_viable_test/README.md +++ b/feature/interface/aggregate/otg_tests/aggregate_all_not_viable_test/README.md @@ -46,8 +46,9 @@ Ensure that when --all LAG member-- become set with forwarding-viable == FALSE 1. Advertise one network prefix (pfx2) from ATE LAG_2 and ATE LAG_3. - Establish iBGP between ATE and DUT over LGA using LAG interface IPs and advertise prefix pfx3 with BGP NH from pfx2 range. -- Programm via gRIBI route for prefix pfx4 with NHG pointing LAG_2 & LAG_3(all - ports are forwarding-viable at this point) with equal weight. +- Programm via gRIBI route for prefix pfx4 with NHG pointing to NH LAG_2 & backup + to NHG pointing to NH LAG_3(all ports are forwarding-viable at this point) + with equal weight. ## RT-5.7.1: For ISIS cost of LAG_2 lower than ISIS cost of LAG_3: #### Run traffic: @@ -64,9 +65,8 @@ Ensure that when --all LAG member-- become set with forwarding-viable == FALSE #### RT-5.7.1.2: Verify forwarding-viable behavior on an aggregate interface with all members down or set with forwarding-viable=FALSE. - Ensure ISIS adjacency is UP on DUT LAG_2 and ATE LAG_2 -- Disable/deactive laser on ATE port2; Now all LAG_2 members are either down - (port2) or set with forwarding-viable=FALSE -- Ensure that the ISIS adjacency times out on DUT LAG_2 and ATE LAG_2 +- Set with forwarding-viable=FALSE on port 2 (All Ports now on LAG_2 are set with FV=false) +- Ensure that the ISIS adjacency is UP on DUT LAG_2 and ATE LAG_2 - Ensure there is no layer3 traffic transmitted out of DUT ports 2-6 (LAG_2) - Ensure that traffic is received on all port3-6 and delivered to ATE LAG_1 - Ensure there are no packet losses in steady state (no congestion) for @@ -75,7 +75,7 @@ Ensure that when --all LAG member-- become set with forwarding-viable == FALSE traffic from ATE LAG_1 to ATE LAG_3 (pfx_2, pfx3). - Ensure there is no traffic received on DUT LAG_3 - Ensure that traffic from ATE port1 to pfx2, pfx3 are transmitted via DUT LAG3 -- Ensure that traffic from ATE port1 to pfx4 are transmitted out through NH pointing to LAG3 +- Ensure that traffic from ATE port1 to pfx4 are transmitted out through backup NHG pointing to NH LAG3 #### RT-5.7.1.3: Make the forwarding-viable transitions from FALSE --> TRUE on a ports 6 within the LAG_2 on the DUT - Ensure that only DUT port 6 of LAG ports has bidirectional traffic. @@ -85,6 +85,21 @@ Ensure that when --all LAG member-- become set with forwarding-viable == FALSE - Ensure there is no traffic received on DUT LAG_3 - Ensure there is no traffic transmitted on DUT LAG_3 +#### RT-5.7.1.4: Verify forwarding-viable behavior on an aggregate interface with some members are down with all member are set with forwarding-viable=FALSE. +- Ensure ISIS adjacency is UP on DUT LAG_2 and ATE LAG_2 +- Set with forwarding-viable=FALSE on port 2 and make down other ports on LAG_2 + (All Ports now on LAG_2 are set with FV=false and some ports are down) +- Ensure that the ISIS adjacency is UP on DUT LAG_2 and ATE LAG_2 +- Ensure there is no layer3 traffic transmitted out of DUT ports 2-6 (LAG_2) +- Ensure that traffic is received on all port3-6 and delivered to ATE LAG_1 +- Ensure there are no packet losses in steady state (no congestion) for + traffic from ATE LAG_2 to ATE LAG_1 (pfx_1). +- Ensure there are no packet losses in steady state (no congestion) for + traffic from ATE LAG_1 to ATE LAG_3 (pfx_2, pfx3). +- Ensure there is no traffic received on DUT LAG_3 +- Ensure that traffic from ATE port1 to pfx2, pfx3 are transmitted via DUT LAG3 +- Ensure that traffic from ATE port1 to pfx4 are transmitted out through NHG pointing to NH LAG3 + ## RT-5.7.2: For ISIS cost of LAG_2 equal to ISIS cost of LAG_3 #### Run traffic: @@ -99,11 +114,10 @@ Ensure that when --all LAG member-- become set with forwarding-viable == FALSE - Ensure that traffic is received on all port2-6 and ports7-8 and delivered to ATE port1 - Ensure there are no packet losses in steady state (no congestion) -#### RT-5.7.2.2: Verify forwarding-viable behavior on an aggregate interface with all members down or set with forwarding-viable=FALSE. +#### RT-5.7.2.2: Verify forwarding-viable behavior on an aggregate interface with all are set with forwarding-viable=FALSE. - Ensure ISIS adjacency is UP on DUT LAG_2 and ATE LAG_2 -- Disable/deactive laser on ATE port2; Now all LAG_2 members are either down (port2) or - set with forwarding-viable=FALSE -- Ensure that the ISIS adjacency times out on DUT LAG_2 and ATE LAG_2 +- Set with forwarding-viable=FALSE on port 2 (All Ports now on LAG_2 are set with FV=false) +- Ensure that the ISIS adjacency is UP on DUT LAG_2 and ATE LAG_2 - Ensure there is no traffic transmitted out of DUT ports 2-6 (LAG_2) - Ensure that traffic received on all port3-6 and ports7-8 is delivered to ATE LAG_1 - Ensure there are no packet losses in steady state (no congestion) for @@ -111,7 +125,7 @@ Ensure that when --all LAG member-- become set with forwarding-viable == FALSE - Ensure there are no packet losses in steady state (no congestion) for traffic from ATE LAG_1 to ATE LAG_3 (pfx_2, pfx3). - Ensure that traffic from ATE port1 to pfx2, pfx3 are transmitted via DUT LAG3 -- Ensure that traffic from ATE port1 to pfx4 are transmitted out through NH pointing to LAG3 +- Ensure that traffic from ATE port1 to pfx4 are transmitted out through NHG pointing to NH LAG3 #### RT-5.7.2.3: Make the forwarding-viable transitions from FALSE --> TRUE on a ports 6 within the LAG_2 on the DUT - Ensure that only DUT port 6 of LAG_2 and all ports of LAG_3 ports has bidirectional traffic. @@ -119,6 +133,21 @@ Ensure that when --all LAG member-- become set with forwarding-viable == FALSE - Ensure that traffic received on all port3-6 and ports7-8 is delivered to ATE port1 - Ensure there are no packet losses in steady state (no congestion). +#### RT-5.7.2.4: Verify forwarding-viable behavior on an aggregate interface with some members are down with all member are set with forwarding-viable=FALSE. +- Ensure ISIS adjacency is UP on DUT LAG_2 and ATE LAG_2 +- Set with forwarding-viable=FALSE and make down other ports on LAG_2 + (All Ports now on LAG_2 are set with FV=false and some ports are down) +- Ensure that the ISIS adjacency times out on DUT LAG_2 and ATE LAG_2 +- Ensure there is no traffic transmitted out of DUT ports 2-6 (LAG_2) +- Ensure that traffic received on all port3-6 and ports7-8 is delivered to ATE LAG_1 +- Ensure there are no packet losses in steady state (no congestion) for + traffic from ATE LAG_2, LAG_3 to ATE LAG_1 (pfx_1). +- Ensure there are no packet losses in steady state (no congestion) for + traffic from ATE LAG_1 to ATE LAG_3 (pfx_2, pfx3). +- Ensure that traffic from ATE port1 to pfx2, pfx3 are transmitted via DUT LAG3 +- Ensure that traffic from ATE port1 to pfx4 are transmitted out through NH pointing to LAG3 + + ## OpenConfig Path and RPC Coverage The below yaml defines the OC paths and RPC intended to be covered by this test. diff --git a/feature/interface/aggregate/otg_tests/aggregate_all_not_viable_test/aggregate_all_not_forwarding_viable_test.go b/feature/interface/aggregate/otg_tests/aggregate_all_not_viable_test/aggregate_all_not_forwarding_viable_test.go index 48cacf68dd8..1128fbf265a 100644 --- a/feature/interface/aggregate/otg_tests/aggregate_all_not_viable_test/aggregate_all_not_forwarding_viable_test.go +++ b/feature/interface/aggregate/otg_tests/aggregate_all_not_viable_test/aggregate_all_not_forwarding_viable_test.go @@ -77,6 +77,9 @@ const ( LAG1 = "lag1" LAG2 = "lag2" LAG3 = "lag3" + niTeVrf111 = "TE_VRF_111" + niRepairVrf = "REPAIR_VRF" + pfx1AdvV4WithMask = "100.0.1.0/24" ) type aggPortData struct { @@ -144,20 +147,20 @@ var ( IPv6Len: 128, } - pfx1AdvV4 = &ipAddr{ip: "100.0.1.0", prefix: 24} - pfx1AdvV6 = &ipAddr{ip: "2002:db8:64:64::0", prefix: 64} - pfx2AdvV4 = &ipAddr{ip: "100.0.2.0", prefix: 24} - pfx2AdvV6 = &ipAddr{ip: "2003:db8:64:64::0", prefix: 64} - pfx3AdvV4 = &ipAddr{ip: "100.0.3.0", prefix: 24} - pfx4AdvV4 = &ipAddr{ip: "100.0.4.0", prefix: 24} - pmd100GFRPorts []string - dutPortList []*ondatra.Port - atePortList []*ondatra.Port - rxPktsBeforeTraffic map[*ondatra.Port]uint64 - txPktsBeforeTraffic map[*ondatra.Port]uint64 - equalDistributionWeights = []uint64{50, 50} - ecmpTolerance = uint64(1) - ipRange = []uint32{254, 500} + pfx1AdvV4 = &ipAddr{ip: "100.0.1.0", prefix: 24} + pfx1AdvV6 = &ipAddr{ip: "2002:db8:64:64::0", prefix: 64} + pfx2AdvV4 = &ipAddr{ip: "100.0.2.0", prefix: 24} + pfx2AdvV6 = &ipAddr{ip: "2003:db8:64:64::0", prefix: 64} + pfx3AdvV4 = &ipAddr{ip: "100.0.3.0", prefix: 24} + pfx4AdvV4 = &ipAddr{ip: "100.0.4.0", prefix: 24} + pmd100GFRPorts []string + dutPortList []*ondatra.Port + atePortList []*ondatra.Port + rxPktsBeforeTraffic map[*ondatra.Port]uint64 + txPktsBeforeTraffic map[*ondatra.Port]uint64 + trafficDistributionWeights = []uint64{50, 50} + ecmpTolerance = uint64(1) + ipRange = []uint32{250, 500} dutAggMac []string ) @@ -173,18 +176,20 @@ func TestAggregateAllNotForwardingViable(t *testing.T) { ate := ondatra.ATE(t, "ate") aggIDs := configureDUT(t, dut) + configNonDefaultNetworkInstance(t, dut) changeMetric(t, dut, aggIDs[2], 30) top := configureATE(t, ate) + installGRIBIRoutes(t, dut, ate, top) ate.OTG().PushConfig(t, top) ate.OTG().StartProtocols(t) for _, aggID := range aggIDs { gnmi.Await(t, dut, gnmi.OC().Interface(aggID).OperStatus().State(), 60*time.Second, oc.Interface_OperStatus_UP) } - flows := createFlows(t, ate, top) ate.OTG().PushConfig(t, top) ate.OTG().StartProtocols(t) + for _, agg := range []*aggPortData{agg1, agg2, agg3} { bgpPath := ocpath.Root().NetworkInstance(deviations.DefaultNetworkInstance(dut)).Protocol(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, "BGP").Bgp() gnmi.Await(t, dut, bgpPath.Neighbor(agg.ateIPv4).SessionState().State(), time.Minute, oc.Bgp_Neighbor_SessionState_ESTABLISHED) @@ -216,11 +221,6 @@ func TestAggregateAllNotForwardingViable(t *testing.T) { configForwardingViable(t, dut, dutPortList[1:2], false) // Ensure ISIS Adjacency is Down on LAG_2 - if ok := awaitAdjacency(t, dut, aggIDs[1], oc.Isis_IsisInterfaceAdjState_DOWN); !ok { - if presence := gnmi.LookupAll(t, dut, ocpath.Root().NetworkInstance(deviations.DefaultNetworkInstance(dut)).Protocol(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_ISIS, isisInstance).Isis().Interface(aggIDs[1]).LevelAny().AdjacencyAny().AdjacencyState().State()); len(presence) > 0 { - t.Fatalf("ISIS Adjacency is Established on LAG_2 ") - } - } startTraffic(t, dut, ate, top) if err := confirmNonViableForwardingTraffic(t, dut, ate, atePortList[1:agg2.ateLagCount+1], dutPortList[1:agg2.ateLagCount+1]); err != nil { t.Fatal(err) @@ -255,8 +255,55 @@ func TestAggregateAllNotForwardingViable(t *testing.T) { t.Fatal("Packet Dropped, LossPct for flow ") } }) + + // Reset Forwarding-Viable to True for all the ports of LAG_2 + configForwardingViable(t, dut, dutPortList[1:agg2.ateLagCount], true) + + t.Run("RT-5.7.1.4: Setting Forwarding-Viable to False and Down some Port on Lag2", func(t *testing.T) { + // Ensure ISIS Adjacency is up on LAG_2 + if ok := awaitAdjacency(t, dut, aggIDs[1], oc.Isis_IsisInterfaceAdjState_UP); !ok { + t.Fatal("ISIS Adjacency is Down on LAG_2") + } + configForwardingViable(t, dut, dutPortList[1:agg2.ateLagCount+1], false) + // Ensure ISIS Adjacency is Down on LAG_2 + + if len(dut.Ports()) > 4 { + t.Logf("Bring Down Port2 and Port3") + setDUTInterfaceWithState(t, dut, []*ondatra.Port{dut.Port(t, "port2"), dut.Port(t, "port3")}, false) + } else { + t.Logf("Bring Down Port2") + setDUTInterfaceWithState(t, dut, []*ondatra.Port{dut.Port(t, "port2")}, false) + } + + // Ensure LAG2 is UP when all member are Forwarding unviable + gnmi.Await(t, dut, gnmi.OC().Interface(aggIDs[1]).OperStatus().State(), 60*time.Second, oc.Interface_OperStatus_UP) + startTraffic(t, dut, ate, top) + if len(dut.Ports()) > 4 { + if err := confirmNonViableForwardingTraffic(t, dut, ate, atePortList[1:agg2.ateLagCount+1], dutPortList[3:agg2.ateLagCount+1]); err != nil { + t.Fatal(err) + } + } else { + if err := confirmNonViableForwardingTraffic(t, dut, ate, atePortList[1:agg2.ateLagCount], dutPortList[2:agg2.ateLagCount]); err != nil { + t.Fatal(err) + } + } + // Ensure that traffic from ATE port1 to pfx4 transmitted out using LAG3 + if ok := verifyTrafficFlow(t, ate, flows[1:2], true); !ok { + t.Fatal("Packet Dropped, LossPct for flow ", flows[1].Name()) + } + // Ensure there is no traffic received on DUT LAG_3 + if got := validateLag3Traffic(t, dut, ate, dutPortList[(agg2.ateLagCount+1):]); got == true { + t.Fatal("Packets are Received on DUT LAG_3") + } + if ok := verifyTrafficFlow(t, ate, flows[0:1], true); !ok { + t.Fatal("Packet Dropped, LossPct for flow ", flows[0].Name()) + } + }) + t.Logf("Bring Up the Port2 and Port3") + setDUTInterfaceWithState(t, dut, []*ondatra.Port{dut.Port(t, "port2"), dut.Port(t, "port3")}, true) + // Reset Forwarding-Viable to True for all the ports of LAG_2 - configForwardingViable(t, dut, dutPortList[1:6], true) + configForwardingViable(t, dut, dutPortList[1:agg2.ateLagCount+1], true) // Change ISIS metric Equal for Both LAG_2 and LAG_3 changeMetric(t, dut, aggIDs[2], 20) @@ -276,9 +323,9 @@ func TestAggregateAllNotForwardingViable(t *testing.T) { if err := confirmNonViableForwardingTraffic(t, dut, ate, atePortList[2:(agg2.ateLagCount+1)], dutPortList[2:(agg2.ateLagCount+1)]); err != nil { t.Fatal(err) } - // Ensure Load Balancing 50:50 on LAG_2 and LAG_3 for prefix's pfx2, pfx3 and pfx4 + // Ensure Load WECMP on LAG_2 and LAG_3 for prefix's pfx2, pfx3 and pfx4 weights := trafficRXWeights(t, ate, []string{agg2.ateAggName, agg3.ateAggName}, flows[0]) - for idx, weight := range equalDistributionWeights { + for idx, weight := range trafficDistributionWeights { if got, want := weights[idx], weight; got < want-ecmpTolerance || got > want+ecmpTolerance { t.Errorf("ECMP Percentage for Aggregate Index: %d: got %d, want %d", idx+1, got, want) } @@ -294,12 +341,6 @@ func TestAggregateAllNotForwardingViable(t *testing.T) { t.Fatal("ISIS Adjacency is Down on LAG_2") } configForwardingViable(t, dut, dutPortList[1:2], false) - // Ensure ISIS Adjacency is Down on LAG_2 - if ok := awaitAdjacency(t, dut, aggIDs[1], oc.Isis_IsisInterfaceAdjState_DOWN); !ok { - if presence := gnmi.LookupAll(t, dut, ocpath.Root().NetworkInstance(deviations.DefaultNetworkInstance(dut)).Protocol(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_ISIS, isisInstance).Isis().Interface(aggIDs[1]).LevelAny().AdjacencyAny().AdjacencyState().State()); len(presence) > 0 { - t.Fatalf("ISIS Adjacency is Established on LAG_2") - } - } startTraffic(t, dut, ate, top) if err := confirmNonViableForwardingTraffic(t, dut, ate, atePortList[1:(agg2.ateLagCount+1)], dutPortList[1:(agg2.ateLagCount+1)]); err != nil { t.Fatal(err) @@ -330,6 +371,73 @@ func TestAggregateAllNotForwardingViable(t *testing.T) { t.Fatal("Packet Dropped, LossPct for flow ") } }) + + // Reset Forwarding-Viable to True for all the ports of LAG_2 + configForwardingViable(t, dut, dutPortList[1:agg2.ateLagCount], true) + + t.Run("RT-5.7.2.4: Setting Forwarding-Viable to False and Down some Port on Lag2", func(t *testing.T) { + // Ensure ISIS Adjacency is up on LAG_2 + if ok := awaitAdjacency(t, dut, aggIDs[1], oc.Isis_IsisInterfaceAdjState_UP); !ok { + t.Fatal("ISIS Adjacency is Down on LAG_2") + } + configForwardingViable(t, dut, dutPortList[1:agg2.ateLagCount+1], false) + // Ensure ISIS Adjacency is Down on LAG_2 + + if len(dut.Ports()) > 4 { + t.Logf("Bring Down Port2 and Port3") + setDUTInterfaceWithState(t, dut, []*ondatra.Port{dut.Port(t, "port2"), dut.Port(t, "port3")}, false) + } else { + t.Logf("Bring Down Port2") + setDUTInterfaceWithState(t, dut, []*ondatra.Port{dut.Port(t, "port2")}, false) + } + // Ensure LAG2 is UP when all member are Forwarding unviable + gnmi.Await(t, dut, gnmi.OC().Interface(aggIDs[1]).OperStatus().State(), 60*time.Second, oc.Interface_OperStatus_UP) + startTraffic(t, dut, ate, top) + if len(dut.Ports()) > 4 { + if err := confirmNonViableForwardingTraffic(t, dut, ate, atePortList[1:agg2.ateLagCount+1], dutPortList[3:agg2.ateLagCount+1]); err != nil { + t.Fatal(err) + } + } else { + if err := confirmNonViableForwardingTraffic(t, dut, ate, atePortList[1:agg2.ateLagCount], dutPortList[2:agg2.ateLagCount]); err != nil { + t.Fatal(err) + } + } + // Ensure that traffic from ATE port1 to pfx4 transmitted out using LAG3 + if ok := verifyTrafficFlow(t, ate, flows[1:2], true); !ok { + t.Fatal("Packet Dropped, LossPct for flow ", flows[1].Name()) + } + // Ensure there is traffic received on DUT LAG_3 + if got := validateLag3Traffic(t, dut, ate, dutPortList[(agg2.ateLagCount+1):]); got == false { + t.Fatal("Packets are Received on DUT LAG_3") + } + if ok := verifyTrafficFlow(t, ate, flows[0:1], true); !ok { + t.Fatal("Packet Dropped, LossPct for flow ", flows[0].Name()) + } + }) +} + +func setDUTInterfaceWithState(t testing.TB, dut *ondatra.DUTDevice, ports []*ondatra.Port, state bool) { + dc := gnmi.OC() + i := &oc.Interface{} + i.Enabled = ygot.Bool(state) + i.Type = oc.IETFInterfaces_InterfaceType_ethernetCsmacd + for _, p := range ports { + i.Name = ygot.String(p.Name()) + gnmi.Update(t, dut, dc.Interface(p.Name()).Config(), i) + } +} + +// configureNetworkInstance configures vrfs DECAP_TE_VRF,ENCAP_TE_VRF_A,ENCAP_TE_VRF_B, +// TE_VRF_222, TE_VRF_111. +func configNonDefaultNetworkInstance(t *testing.T, dut *ondatra.DUTDevice) { + t.Helper() + c := &oc.Root{} + vrfs := []string{niTeVrf111, niRepairVrf} + for _, vrf := range vrfs { + ni := c.GetOrCreateNetworkInstance(vrf) + ni.Type = oc.NetworkInstanceTypes_NETWORK_INSTANCE_TYPE_L3VRF + gnmi.Replace(t, dut, gnmi.OC().NetworkInstance(vrf).Config(), ni) + } } // configureDUT configures DUT @@ -343,6 +451,7 @@ func configureDUT(t *testing.T, dut *ondatra.DUTDevice) []string { if len(dut.Ports()) > 4 { agg2.ateLagCount = uint32(len(dut.Ports()) - 3) agg3.ateLagCount = 2 + trafficDistributionWeights = []uint64{33, 67} } var aggIDs []string for _, a := range []*aggPortData{agg1, agg2, agg3} { @@ -459,9 +568,6 @@ func configAggregateDUT(dut *ondatra.DUTDevice, i *oc.Interface, a *aggPortData) a4 := s4.GetOrCreateAddress(a.dutIPv4) a4.PrefixLength = ygot.Uint8(ipv4PLen) - // n4 := s4.GetOrCreateNeighbor(a.ateIPv4) - // n4.LinkLayerAddress = ygot.String(a.ateAggMAC) - s6 := s.GetOrCreateIpv6() if deviations.InterfaceEnabled(dut) { s6.Enabled = ygot.Bool(true) @@ -858,7 +964,6 @@ func installGRIBIRoutes(t *testing.T, dut *ondatra.DUTDevice, ate *ondatra.ATEDe client.Connection().WithStub(gribic).WithPersistence().WithInitialElectionID(12, 0). WithRedundancyMode(fluent.ElectedPrimaryClient).WithFIBACK() client.Start(ctx, t) - defer client.Stop(t) gribi.FlushAll(client) client.StartSending(ctx, t) gribi.BecomeLeader(t, client) @@ -871,34 +976,86 @@ func installGRIBIRoutes(t *testing.T, dut *ondatra.DUTDevice, ate *ondatra.ATEDe top: top, } - t.Logf("An IPv4Entry for %s is pointing to ATE LAG2 via gRIBI", pfx4AdvV4.ip+"/24") + t.Logf("An IPv4Entry for %s is pointing to ATE LAG2 and Backup NHG to LAG3 via gRIBI", pfx4AdvV4.ip+"/24") + // Programming AFT entries for backup NHG tcArgs.client.Modify().AddEntry(t, + fluent.NextHopEntry().WithNetworkInstance(deviations.DefaultNetworkInstance(dut)). + WithIndex(3000).WithNextHopNetworkInstance(niRepairVrf), + fluent.NextHopGroupEntry().WithNetworkInstance(deviations.DefaultNetworkInstance(dut)). + WithID(3000).AddNextHop(3000, 1), + fluent.NextHopEntry().WithNetworkInstance(deviations.DefaultNetworkInstance(tcArgs.dut)). - WithIndex(uint64(100)).WithIPAddress(agg2.ateIPv4), - fluent.NextHopEntry().WithNetworkInstance(deviations.DefaultNetworkInstance(tcArgs.dut)). - WithIndex(uint64(101)).WithIPAddress(agg3.ateIPv4), + WithIndex(uint64(1000)).WithIPAddress(agg3.ateIPv4), fluent.NextHopGroupEntry().WithNetworkInstance(deviations.DefaultNetworkInstance(tcArgs.dut)). - WithID(uint64(100)).AddNextHop(uint64(100), uint64(1)).AddNextHop(uint64(101), uint64(1))) + WithID(uint64(1000)).AddNextHop(uint64(1000), uint64(1)), + + fluent.IPv4Entry().WithNetworkInstance(niRepairVrf).WithNextHopGroupNetworkInstance(deviations.DefaultNetworkInstance(dut)). + WithPrefix(pfx4AdvV4.ip+"/24").WithNextHopGroup(1000)) + + if err := awaitTimeout(tcArgs.ctx, t, tcArgs.client, time.Minute); err != nil { + t.Logf("Could not program entries via client, got err, check error codes: %v", err) + } + + chk.HasResult(t, tcArgs.client.Results(t), + fluent.OperationResult(). + WithIPv4Operation(pfx4AdvV4.ip+"/24"). + WithOperationType(constants.Add). + WithProgrammingResult(fluent.InstalledInFIB). + AsResult(), + chk.IgnoreOperationID(), + ) + // Programming AFT entries for prefixes Encap in Default VRF tcArgs.client.Modify().AddEntry(t, + fluent.NextHopEntry().WithNetworkInstance(deviations.DefaultNetworkInstance(tcArgs.dut)). + WithIndex(uint64(1)).WithEncapsulateHeader(fluent.IPinIP). + WithIPinIP("100.0.1.254", "100.0.4.254"). + WithNextHopNetworkInstance(niTeVrf111), + fluent.NextHopGroupEntry().WithNetworkInstance(deviations.DefaultNetworkInstance(tcArgs.dut)). + WithID(uint64(1)).AddNextHop(uint64(1), uint64(1)), + fluent.IPv4Entry().WithNetworkInstance(deviations.DefaultNetworkInstance(tcArgs.dut)). - WithPrefix(pfx4AdvV4.ip+"/24").WithNextHopGroup(uint64(100))) + WithPrefix(pfx4AdvV4.ip+"/24").WithNextHopGroup(1). + WithNextHopGroupNetworkInstance(deviations.DefaultNetworkInstance(tcArgs.dut))) - if err := awaitTimeout(tcArgs.ctx, t, tcArgs.client, 5*time.Minute); err != nil { + if err := awaitTimeout(tcArgs.ctx, t, tcArgs.client, time.Minute); err != nil { t.Logf("Could not program entries via client, got err, check error codes: %v", err) } - defaultVRFIPList := []string{pfx4AdvV4.ip} - for ip := range defaultVRFIPList { - chk.HasResult(t, tcArgs.client.Results(t), - fluent.OperationResult(). - WithIPv4Operation(defaultVRFIPList[ip]+"/24"). - WithOperationType(constants.Add). - WithProgrammingResult(fluent.InstalledInFIB). - AsResult(), - chk.IgnoreOperationID(), - ) + + chk.HasResult(t, tcArgs.client.Results(t), + fluent.OperationResult(). + WithIPv4Operation(pfx4AdvV4.ip+"/24"). + WithOperationType(constants.Add). + WithProgrammingResult(fluent.InstalledInFIB). + AsResult(), + chk.IgnoreOperationID(), + ) + + // Programming AFT entries for encapped prefixes "100.0.4.254/32" + tcArgs.client.Modify().AddEntry(t, + fluent.NextHopEntry().WithNetworkInstance(deviations.DefaultNetworkInstance(tcArgs.dut)). + WithIndex(uint64(101)).WithIPAddress(agg2.ateIPv4), + fluent.NextHopGroupEntry().WithNetworkInstance(deviations.DefaultNetworkInstance(tcArgs.dut)). + WithID(uint64(101)).AddNextHop(uint64(101), uint64(1)).WithBackupNHG(3000), + + fluent.IPv4Entry().WithNetworkInstance(niTeVrf111). + WithPrefix("100.0.4.254/32").WithNextHopGroup(101). + WithNextHopGroupNetworkInstance(deviations.DefaultNetworkInstance(tcArgs.dut)), + ) + + if err := awaitTimeout(tcArgs.ctx, t, tcArgs.client, 5*time.Minute); err != nil { + t.Logf("Could not program entries via client, got err, check error codes: %v", err) } + + chk.HasResult(t, tcArgs.client.Results(t), + fluent.OperationResult(). + WithIPv4Operation("100.0.4.254/32"). + WithOperationType(constants.Add). + WithProgrammingResult(fluent.InstalledInFIB). + AsResult(), + chk.IgnoreOperationID(), + ) } // awaitTimeout calls a fluent client Await, adding a timeout to the context. diff --git a/feature/interface/aggregate/otg_tests/aggregate_all_not_viable_test/metadata.textproto b/feature/interface/aggregate/otg_tests/aggregate_all_not_viable_test/metadata.textproto index 0896d869a61..a7ce571869e 100644 --- a/feature/interface/aggregate/otg_tests/aggregate_all_not_viable_test/metadata.textproto +++ b/feature/interface/aggregate/otg_tests/aggregate_all_not_viable_test/metadata.textproto @@ -20,6 +20,19 @@ platform_exceptions: { } } +platform_exceptions: { + platform: { + vendor: CISCO + } + deviations: { + interface_ref_config_unsupported:true + wecmp_auto_unsupported: true + isis_loopback_required: true + weighted_ecmp_fixed_packet_verification: true + interface_ref_interface_id_format: true + } +} + platform_exceptions: { platform: { vendor: ARISTA diff --git a/feature/interface/aggregate/otg_tests/balancing_test/README.md b/feature/interface/aggregate/otg_tests/balancing_test/README.md index aceda7e25b6..d09453272e8 100644 --- a/feature/interface/aggregate/otg_tests/balancing_test/README.md +++ b/feature/interface/aggregate/otg_tests/balancing_test/README.md @@ -41,3 +41,26 @@ None ## Minimum DUT platform requirement vRX + +## OpenConfig Path and RPC Coverage + +The below yaml defines the OC paths and RPC intended to be covered by this test. + +```yaml +paths: + /interfaces/interface/ethernet/config/aggregate-id: + /interfaces/interface/aggregation/config/lag-type: + /lacp/config/system-priority: + /lacp/interfaces/interface/config/name: + /lacp/interfaces/interface/config/interval: + /lacp/interfaces/interface/config/lacp-mode: + /lacp/interfaces/interface/config/system-id-mac: + /lacp/interfaces/interface/config/system-priority: + +rpcs: + gnmi: + gNMI.Set: + union_replace: false + gNMI.Subscribe: + on_change: false +``` diff --git a/feature/interface/aggregate/otg_tests/balancing_test/balancing_test.go b/feature/interface/aggregate/otg_tests/balancing_test/balancing_test.go index 07b576adf29..0a84eef0ae2 100644 --- a/feature/interface/aggregate/otg_tests/balancing_test/balancing_test.go +++ b/feature/interface/aggregate/otg_tests/balancing_test/balancing_test.go @@ -569,6 +569,30 @@ func (tc *testCase) testFlow(t *testing.T, l3header string) { if pkts == 0 { t.Errorf("Flow sent packets: got %v, want non zero", pkts) } + + if deviations.InterfaceCountersUpdateDelayed(tc.dut) { + batch := gnmi.OCBatch() + for _, port := range tc.dutPorts[1:] { + batch.AddPaths(gnmi.OC().Interface(port.Name()).Counters()) + } + + _, ok := gnmi.Watch(t, tc.dut, batch.State(), time.Second*60, func(v *ygnmi.Value[*oc.Root]) bool { + got, present := v.Val() + if !present { + return false + } + totalPks := uint64(0) + for _, port := range tc.dutPorts[1:] { + totalPks += got.GetInterface(port.Name()).GetCounters().GetOutPkts() - beforeTrafficCounters[port.Name()].GetOutPkts() + } + return totalPks >= pkts + }).Await(t) + + if !ok { + t.Fatalf("Counters did not update in time") + } + } + afterTrafficCounters := tc.getCounters(t, "after") tc.verifyCounterDiff(t, beforeTrafficCounters, afterTrafficCounters) } diff --git a/feature/interface/aggregate/otg_tests/balancing_test/metadata.textproto b/feature/interface/aggregate/otg_tests/balancing_test/metadata.textproto index 68c8eb17c3a..f29298037aa 100644 --- a/feature/interface/aggregate/otg_tests/balancing_test/metadata.textproto +++ b/feature/interface/aggregate/otg_tests/balancing_test/metadata.textproto @@ -11,6 +11,7 @@ platform_exceptions: { } deviations: { ipv4_missing_enabled: true + interface_counters_update_delayed: true } } platform_exceptions: { diff --git a/feature/experimental/interface/interface_loopback_aggregate/otg_tests/interface_loopback_aggregate/README.md b/feature/interface/interface_loopback_aggregate/otg_tests/interface_loopback_aggregate/README.md similarity index 100% rename from feature/experimental/interface/interface_loopback_aggregate/otg_tests/interface_loopback_aggregate/README.md rename to feature/interface/interface_loopback_aggregate/otg_tests/interface_loopback_aggregate/README.md diff --git a/feature/experimental/interface/interface_loopback_aggregate/otg_tests/interface_loopback_aggregate/interface_loopback_aggregate_test.go b/feature/interface/interface_loopback_aggregate/otg_tests/interface_loopback_aggregate/interface_loopback_aggregate_test.go similarity index 100% rename from feature/experimental/interface/interface_loopback_aggregate/otg_tests/interface_loopback_aggregate/interface_loopback_aggregate_test.go rename to feature/interface/interface_loopback_aggregate/otg_tests/interface_loopback_aggregate/interface_loopback_aggregate_test.go diff --git a/feature/experimental/interface/interface_loopback_aggregate/otg_tests/interface_loopback_aggregate/metadata.textproto b/feature/interface/interface_loopback_aggregate/otg_tests/interface_loopback_aggregate/metadata.textproto similarity index 100% rename from feature/experimental/interface/interface_loopback_aggregate/otg_tests/interface_loopback_aggregate/metadata.textproto rename to feature/interface/interface_loopback_aggregate/otg_tests/interface_loopback_aggregate/metadata.textproto diff --git a/feature/interface/ip/ipv6_ND/otg_tests/disable_ipv6_nd_ra_test/disable_ipv6_nd_ra_test.go b/feature/interface/ip/ipv6_ND/otg_tests/disable_ipv6_nd_ra_test/disable_ipv6_nd_ra_test.go index 8682053691f..ac04a98cf85 100644 --- a/feature/interface/ip/ipv6_ND/otg_tests/disable_ipv6_nd_ra_test/disable_ipv6_nd_ra_test.go +++ b/feature/interface/ip/ipv6_ND/otg_tests/disable_ipv6_nd_ra_test/disable_ipv6_nd_ra_test.go @@ -83,6 +83,10 @@ func configureDUT(t *testing.T, dut *ondatra.DUTDevice) { gnmi.Replace(t, dut, d.Interface(p1.Name()).Config(), configInterfaceDUT(p1, &dutSrc, dut)) p2 := dut.Port(t, "port2") gnmi.Replace(t, dut, d.Interface(p2.Name()).Config(), configInterfaceDUT(p2, &dutDst, dut)) + if deviations.ExplicitInterfaceInDefaultVRF(dut) { + fptest.AssignToNetworkInstance(t, dut, p1.Name(), deviations.DefaultNetworkInstance(dut), 0) + fptest.AssignToNetworkInstance(t, dut, p2.Name(), deviations.DefaultNetworkInstance(dut), 0) + } } // Configures the given DUT interface. @@ -101,7 +105,6 @@ func configInterfaceDUT(p *ondatra.Port, a *attrs.Attributes, dut *ondatra.DUTDe routerAdvert.SetSuppress(routerAdvertisementDisabled) } else { routerAdvert.SetEnable(false) - routerAdvert.SetMode(oc.RouterAdvertisement_Mode_ALL) } return i } diff --git a/feature/interface/ip/ipv6_ND/otg_tests/disable_ipv6_nd_ra_test/metadata.textproto b/feature/interface/ip/ipv6_ND/otg_tests/disable_ipv6_nd_ra_test/metadata.textproto index fb71ef5385e..7e07c4a34fd 100644 --- a/feature/interface/ip/ipv6_ND/otg_tests/disable_ipv6_nd_ra_test/metadata.textproto +++ b/feature/interface/ip/ipv6_ND/otg_tests/disable_ipv6_nd_ra_test/metadata.textproto @@ -22,3 +22,12 @@ platform_exceptions: { ipv6_router_advertisement_interval_unsupported: true } } +platform_exceptions: { + platform: { + vendor: NOKIA + } + deviations: { + explicit_interface_in_default_vrf: true + interface_enabled: true + } +} \ No newline at end of file diff --git a/feature/interface/ip/ipv6_link_local/otg_tests/ipv6_link_local_test/ipv6_link_local_test.go b/feature/interface/ip/ipv6_link_local/otg_tests/ipv6_link_local_test/ipv6_link_local_test.go index 670ec45cc49..cdced10d75a 100644 --- a/feature/interface/ip/ipv6_link_local/otg_tests/ipv6_link_local_test/ipv6_link_local_test.go +++ b/feature/interface/ip/ipv6_link_local/otg_tests/ipv6_link_local_test/ipv6_link_local_test.go @@ -128,7 +128,9 @@ func TestIPv6LinkLocal(t *testing.T) { t.Run("Disable and Enable Port1", func(t *testing.T) { p1 := dut.Port(t, "port1") gnmi.Replace(t, dut, gnmi.OC().Interface(p1.Name()).Enabled().Config(), false) - gnmi.Await(t, dut, gnmi.OC().Interface(p1.Name()).Enabled().State(), 30*time.Second, false) + // gnmi.Await(t, dut, gnmi.OC().Interface(p1.Name()).Enabled().State(), 30*time.Second, false) + t.Logf("Sleeping for 30 seconds") + time.Sleep(30 * time.Second) gnmi.Replace(t, dut, gnmi.OC().Interface(p1.Name()).Enabled().Config(), true) otgutils.WaitForARP(t, ate.OTG(), top, "IPv6") t.Run("Interface Telemetry", func(t *testing.T) { @@ -182,9 +184,12 @@ func configureDUTLinkLocalInterface(t *testing.T, dut *ondatra.DUTDevice) { subInt4.Enabled = ygot.Bool(true) } subInt.GetOrCreateIpv6().Enabled = ygot.Bool(true) + if deviations.LinkLocalMaskLen(dut) { + dutSrc.IPv6Len = 128 + } subInt.GetOrCreateIpv6().GetOrCreateAddress(dutSrc.IPv6).SetType(oc.IfIp_Ipv6AddressType_LINK_LOCAL_UNICAST) + subInt.GetOrCreateIpv6().GetOrCreateAddress(dutSrc.IPv6).SetPrefixLength(dutSrc.IPv6Len) gnmi.Replace(t, dut, gnmi.OC().Interface(p1.Name()).Config(), srcIntf) - p2 := dut.Port(t, "port2") dstIntf := dutDst.NewOCInterface(p2.Name(), dut) dstSubInt := dstIntf.GetOrCreateSubinterface(0) @@ -193,8 +198,14 @@ func configureDUTLinkLocalInterface(t *testing.T, dut *ondatra.DUTDevice) { if deviations.InterfaceEnabled(dut) && !deviations.IPv4MissingEnabled(dut) { dstSubInt4.Enabled = ygot.Bool(true) } + if deviations.LinkLocalMaskLen(dut) { + dutDst.IPv6Len = 128 + } dstSubInt.GetOrCreateIpv6().GetOrCreateAddress(dutDst.IPv6).SetType(oc.IfIp_Ipv6AddressType_LINK_LOCAL_UNICAST) + dstSubInt.GetOrCreateIpv6().GetOrCreateAddress(dutDst.IPv6).SetPrefixLength(dutDst.IPv6Len) + gnmi.Replace(t, dut, gnmi.OC().Interface(p2.Name()).Config(), dstIntf) + if deviations.ExplicitInterfaceInDefaultVRF(dut) { fptest.AssignToNetworkInstance(t, dut, p1.Name(), deviations.DefaultNetworkInstance(dut), 0) fptest.AssignToNetworkInstance(t, dut, p2.Name(), deviations.DefaultNetworkInstance(dut), 0) diff --git a/feature/interface/ip/ipv6_link_local/otg_tests/ipv6_link_local_test/metadata.textproto b/feature/interface/ip/ipv6_link_local/otg_tests/ipv6_link_local_test/metadata.textproto index 79291e1f1a5..8be2f6d388a 100644 --- a/feature/interface/ip/ipv6_link_local/otg_tests/ipv6_link_local_test/metadata.textproto +++ b/feature/interface/ip/ipv6_link_local/otg_tests/ipv6_link_local_test/metadata.textproto @@ -14,6 +14,14 @@ platform_exceptions: { default_network_instance: "default" } } +platform_exceptions: { + platform: { + vendor: CISCO + } + deviations: { + link_local_mask_len: true + } +} # CISCOXR platform_exceptions: { platform: { vendor: NOKIA diff --git a/feature/experimental/interface/my_station_mac/otg_tests/my_station_mac_test/README.md b/feature/interface/my_station_mac/otg_tests/my_station_mac_test/README.md similarity index 100% rename from feature/experimental/interface/my_station_mac/otg_tests/my_station_mac_test/README.md rename to feature/interface/my_station_mac/otg_tests/my_station_mac_test/README.md diff --git a/feature/experimental/interface/my_station_mac/otg_tests/my_station_mac_test/metadata.textproto b/feature/interface/my_station_mac/otg_tests/my_station_mac_test/metadata.textproto similarity index 100% rename from feature/experimental/interface/my_station_mac/otg_tests/my_station_mac_test/metadata.textproto rename to feature/interface/my_station_mac/otg_tests/my_station_mac_test/metadata.textproto diff --git a/feature/experimental/interface/my_station_mac/otg_tests/my_station_mac_test/my_station_mac_test.go b/feature/interface/my_station_mac/otg_tests/my_station_mac_test/my_station_mac_test.go similarity index 100% rename from feature/experimental/interface/my_station_mac/otg_tests/my_station_mac_test/my_station_mac_test.go rename to feature/interface/my_station_mac/otg_tests/my_station_mac_test/my_station_mac_test.go diff --git a/feature/interface/singleton/otg_tests/singleton_test/README.md b/feature/interface/singleton/otg_tests/singleton_test/README.md index a80de7b2ef8..d8d218db6f9 100644 --- a/feature/interface/singleton/otg_tests/singleton_test/README.md +++ b/feature/interface/singleton/otg_tests/singleton_test/README.md @@ -169,3 +169,56 @@ a new testbed configuration with the desired port types. ## Minimum DUT Platform Requirement vRX + +## OpenConfig Path and RPC Coverage + +The below yaml defines the OC paths and RPC intended to be covered by this test. + +```yaml +paths: + /interfaces/interface/ethernet/state/counters/in-mac-pause-frames: + /interfaces/interface/ethernet/state/counters/out-mac-pause-frames: + /interfaces/interface/ethernet/state/mac-address: + /interfaces/interface/state/counters/in-broadcast-pkts: + /interfaces/interface/state/counters/in-discards: + /interfaces/interface/state/counters/in-errors: + /interfaces/interface/state/counters/in-multicast-pkts: + /interfaces/interface/state/counters/in-octets: + /interfaces/interface/state/counters/in-unicast-pkts: + /interfaces/interface/state/counters/in-unknown-protos: + /interfaces/interface/state/counters/out-broadcast-pkts: + /interfaces/interface/state/counters/out-discards: + /interfaces/interface/state/counters/out-errors: + /interfaces/interface/state/counters/out-multicast-pkts: + /interfaces/interface/state/counters/out-octets: + /interfaces/interface/state/counters/out-pkts: + /interfaces/interface/state/counters/out-unicast-pkts: + /interfaces/interface/subinterfaces/subinterface/ipv4/state/mtu: + /interfaces/interface/subinterfaces/subinterface/ipv6/state/mtu: + /interfaces/interface/state/oper-status: + /interfaces/interface/subinterfaces/subinterface/ipv4/addresses/address/ip: + /interfaces/interface/subinterfaces/subinterface/ipv4/state/counters/in-pkts: + /interfaces/interface/subinterfaces/subinterface/ipv4/state/counters/out-pkts: + /interfaces/interface/subinterfaces/subinterface/ipv6/addresses/address/ip: + /interfaces/interface/subinterfaces/subinterface/ipv6/state/counters/in-discarded-pkts: + /interfaces/interface/subinterfaces/subinterface/ipv6/state/counters/in-pkts: + /interfaces/interface/subinterfaces/subinterface/ipv6/state/counters/out-discarded-pkts: + /interfaces/interface/subinterfaces/subinterface/ipv6/state/counters/out-pkts: + /interfaces/interface/ethernet/state/aggregate-id: + /interfaces/interface/ethernet/state/port-speed: + /interfaces/interface/state/admin-status: + /interfaces/interface/state/description: + /interfaces/interface/state/type: + /interfaces/interface/subinterfaces/subinterface/ipv6/state/counters/out-forwarded-pkts: + /interfaces/interface/state/hardware-port: + /interfaces/interface/state/id: + /interfaces/interface/state/counters/in-fcs-errors: + /interfaces/interface/state/counters/carrier-transitions: + +rpcs: + gnmi: + gNMI.Set: + union_replace: false + gNMI.Subscribe: + on_change: false +``` diff --git a/feature/interface/singleton/otg_tests/singleton_test/metadata.textproto b/feature/interface/singleton/otg_tests/singleton_test/metadata.textproto index 76237f19190..926a5a3d560 100644 --- a/feature/interface/singleton/otg_tests/singleton_test/metadata.textproto +++ b/feature/interface/singleton/otg_tests/singleton_test/metadata.textproto @@ -12,6 +12,7 @@ platform_exceptions: { deviations: { ip_neighbor_missing: true ipv4_missing_enabled: true + interface_counters_update_delayed: true } } platform_exceptions: { diff --git a/feature/interface/singleton/otg_tests/singleton_test/singleton_test.go b/feature/interface/singleton/otg_tests/singleton_test/singleton_test.go index 4b38868f6ee..ffe41e929ff 100644 --- a/feature/interface/singleton/otg_tests/singleton_test/singleton_test.go +++ b/feature/interface/singleton/otg_tests/singleton_test/singleton_test.go @@ -30,6 +30,7 @@ import ( "github.com/openconfig/ondatra" "github.com/openconfig/ondatra/gnmi" "github.com/openconfig/ondatra/gnmi/oc" + "github.com/openconfig/ygnmi/ygnmi" "github.com/openconfig/ygot/ygot" otgtelemetry "github.com/openconfig/ondatra/gnmi/otg" @@ -430,6 +431,36 @@ func (tc *testCase) testFlow(t *testing.T, packetSize uint16, configIPHeader otg t.Logf("ap1 out-octets %d -> ap2 in-octets %d", aicp1.GetCounters().GetOutOctets(), aicp2.GetCounters().GetInOctets()) } + // Flow counters + otgutils.LogFlowMetrics(t, tc.ate.OTG(), tc.top) + fp := gnmi.Get(t, tc.ate.OTG(), gnmi.OTG().Flow(flow.Name()).State()) + fpc := fp.GetCounters() + + // Pragmatic check on the average in and out packet sizes. IPv4 may + // fragment the packet unless DF bit is set. IPv6 never fragments. + // Under no circumstances should DUT send packets greater than MTU. + + octets := fpc.GetOutOctets() + ateOutPkts := fpc.GetOutPkts() + ateInPkts := fpc.GetInPkts() + + if deviations.InterfaceCountersUpdateDelayed(tc.dut) { + batch := gnmi.OCBatch() + batch.AddPaths( + gnmi.OC().Interface(p1.Name()).Counters(), + gnmi.OC().Interface(p2.Name()).Counters(), + ) + gnmi.Watch(t, tc.dut, batch.State(), time.Second*60, func(v *ygnmi.Value[*oc.Root]) bool { + got, present := v.Val() + if !present { + return false + } + diffP1 := diffCounters(p1InBefore, inCounters(got.GetInterface(p1.Name()).GetCounters())) + diffP2 := diffCounters(p2OutBefore, outCounters(got.GetInterface(p2.Name()).GetCounters())) + return (diffP1.unicast+diffP1.drop >= ateOutPkts) && (diffP2.unicast >= ateInPkts-diffP2.drop) + }).Await(t) + } + // After Traffic Unicast, Multicast, Broadcast Counter p1InAfter := inCounters(gnmi.Get(t, tc.dut, p1Counter.State())) p2OutAfter := outCounters(gnmi.Get(t, tc.dut, p2Counter.State())) @@ -449,18 +480,6 @@ func (tc *testCase) testFlow(t *testing.T, packetSize uint16, configIPHeader otg t.Errorf("Large number of outbound Broadcast packets %d, want <= 100)", p2OutDiff.broadcast) } - // Flow counters - otgutils.LogFlowMetrics(t, tc.ate.OTG(), tc.top) - fp := gnmi.Get(t, tc.ate.OTG(), gnmi.OTG().Flow(flow.Name()).State()) - fpc := fp.GetCounters() - - // Pragmatic check on the average in and out packet sizes. IPv4 may - // fragment the packet unless DF bit is set. IPv6 never fragments. - // Under no circumstances should DUT send packets greater than MTU. - - octets := fpc.GetOutOctets() - ateOutPkts := fpc.GetOutPkts() - ateInPkts := fpc.GetInPkts() if ateOutPkts == 0 { t.Error("Flow did not send any packet") } else if avg := octets / ateOutPkts; avg > uint64(tc.mtu) { diff --git a/feature/interface/staticarp/otg_tests/static_arp_test/README.md b/feature/interface/staticarp/otg_tests/static_arp_test/README.md index 62fa0970b13..526c4fc8e83 100644 --- a/feature/interface/staticarp/otg_tests/static_arp_test/README.md +++ b/feature/interface/staticarp/otg_tests/static_arp_test/README.md @@ -37,3 +37,13 @@ are the destination MAC addresses of the packets seen by the OTG. * /interfaces/interface/subinterfaces/subinterface/ipv6/addresses/address/config/prefix-length * /interfaces/interface/subinterfaces/subinterface/ipv6/neighbors/neighbor/config/ip * /interfaces/interface/subinterfaces/subinterface/ipv6/neighbors/neighbor/config/link-layer-address + +## OpenConfig Path and RPC Coverage + +```yaml +rpcs: + gnmi: + gNMI.Get: + gNMI.Subscribe: + +``` \ No newline at end of file diff --git a/feature/interface/staticarp/otg_tests/static_arp_test/metadata.textproto b/feature/interface/staticarp/otg_tests/static_arp_test/metadata.textproto index 23329ae109b..2e8a9b92212 100644 --- a/feature/interface/staticarp/otg_tests/static_arp_test/metadata.textproto +++ b/feature/interface/staticarp/otg_tests/static_arp_test/metadata.textproto @@ -13,14 +13,6 @@ platform_exceptions: { ipv4_missing_enabled: true } } -platform_exceptions: { - platform: { - vendor: JUNIPER - } - deviations: { - enable_flowctrl_flag: true - } -} platform_exceptions: { platform: { vendor: NOKIA diff --git a/feature/interface/staticarp/otg_tests/static_arp_test/static_arp_test.go b/feature/interface/staticarp/otg_tests/static_arp_test/static_arp_test.go index a03fb89b463..b576c4fd267 100644 --- a/feature/interface/staticarp/otg_tests/static_arp_test/static_arp_test.go +++ b/feature/interface/staticarp/otg_tests/static_arp_test/static_arp_test.go @@ -127,9 +127,6 @@ func configInterfaceDUT(t *testing.T, p *ondatra.Port, me, peer *attrs.Attribute if me.MAC != "" { e := i.GetOrCreateEthernet() e.MacAddress = ygot.String(me.MAC) - if deviations.EnableFlowctrlFlag(dut) { - e.EnableFlowControl = ygot.Bool(true) - } } s := i.GetOrCreateSubinterface(0) @@ -296,13 +293,12 @@ func testFlow( } func TestStaticARP(t *testing.T) { - // Configure the ATE - ate := ondatra.ATE(t, "ate") - config := configureATE(t) - // Configure the DUT with dynamic ARP. configureDUT(t, noStaticMAC) + // Configure the ATE + ate := ondatra.ATE(t, "ate") + config := configureATE(t) ate.OTG().StartProtocols(t) otgutils.WaitForARP(t, ate.OTG(), config, "IPv4") dstMac := gnmi.Get(t, ate.OTG(), gnmi.OTG().Interface(ateSrc.Name+".Eth").Ipv4Neighbor(dutSrc.IPv4).LinkLayerAddress().State()) diff --git a/feature/isis/otg_tests/base_adjacencies_test/README.md b/feature/isis/otg_tests/base_adjacencies_test/README.md new file mode 100644 index 00000000000..1fc8c021715 --- /dev/null +++ b/feature/isis/otg_tests/base_adjacencies_test/README.md @@ -0,0 +1,207 @@ +# RT-2.1: Base IS-IS Process and Adjacencies + +## Summary + +Base IS-IS functionality and adjacency establishment. + +## Testbed type + +* [`featureprofiles/topologies/atedut_2.testbed`](https://github.com/openconfig/featureprofiles/blob/main/topologies/atedut_2.testbed) + +## Procedure + +### Test environment setup + +* DUT has an ingress port and 1 egress port. + + ``` + | | + [ ATE Port 1 ] ---- | DUT | ---- [ ATE Port 2 ] + | | + ``` + +### RT-2.1.1 Basic fields test + +* Configure DUT:port1 for an IS-IS session with ATE:port1. +* Read back the configuration to ensure that all fields are readable and + have been set properly (or correctly have their default value). +* Check that all relevant counters are readable and are 0 since the + adjacency has not yet been established. +* Push ATE configuration for the other end of the adjacency, and wait for + the adjacency to form. +* Check that the various state fields of the adjacency are reported + correctly. +* Check that error counters are still 0 and that packet counters have all + increased. + +### RT-2.1.2 Hello padding test + +* Configure IS-IS between DUT:port1 and ATE:port1 for each possible value + of hello padding (DISABLED, STRICT, etc.) +* Confirm in each case that that adjacency forms and the correct values + are reported back by the device. + +### RT-2.1.3 Authentication test + +* Configure IS-IS between DUT:port1 and ATE:port1 With authentication + disabled, then enabled in TEXT mode, then enabled in MD5 mode. +* Confirm in each case that that adjacency forms and the correct values + are reported back by the device. + +### RT-2.1.4 [TODO: https://github.com/openconfig/featureprofiles/issues/3421] + +* Configuration: + * Configure ISIS for ATE port-1 and DUT port-1. + * Configure both DUT and ATE interfaces as ISIS type point-to-point. +* Verification: + * Verify that ISIS adjacency is coming up. + * Verify the output of streaming telemetry path displaying the interface circuit-type as point-to-point. + +### RT-2.1.5 Routing test + +* Configure ISIS level authentication and hello authentication. +* Ensure that IPv4 and IPv6 prefixes that are advertised as attached + prefixes within each LSP are correctly installed into the DUT + routing table, by ensuring that packets are received to the attached + prefix when forwarded from ATE port-1. +* Ensure that IPv4 and IPv6 prefixes that are advertised as part of an + (emulated) neighboring system are installed into the DUT routing + table, and validate that packets are sent and received to them. +* With a known LSP content, ensure that the telemetry received from the + device for the LSP matches the expected content. + +### RT-2.1.6 [TODO: https://github.com/openconfig/featureprofiles/issues/3422] + +* Baseline Configuration on the DUT: + * Set the hello-interval to a standard value (10 seconds). + * Set the hello-multiplier to its default (3). + * Check that the streaming telemetry values are reported correctly by the DUT. +* Adjusting Hello-Interval configuration on the DUT: + * Change the hello-interval to a different value (15 seconds) in the DUT. + * Verify that IS-IS adjacency is coming up in the DUT. + * Verify that the updated Hello-Interval time is reflected in isis adjacency output in the ATE. + * Verify that the correct streaming telemetry values are reported correctly by the DUT. +* Adjusting Hello-Multiplier configuration on the DUT: + * Change the hello-multiplier to a different value (5) the DUT. + * Verify that IS-IS adjacency is coming up in the DUT. + * Verify that the updated Hello-Multiplier is reflected in isis adjacency output in the ATE. + * Verify that the correct streaming telemetry values are reported correctly by the DUT. + +## OpenConfig Path and RPC Coverage + +The below yaml defines the OC paths intended to be covered by this test. + +```yaml +paths: + ## Config paths + /network-instances/network-instance/protocols/protocol/isis/global/config/authentication-check: + /network-instances/network-instance/protocols/protocol/isis/global/config/net: + /network-instances/network-instance/protocols/protocol/isis/global/config/level-capability: + /network-instances/network-instance/protocols/protocol/isis/global/config/hello-padding: + /network-instances/network-instance/protocols/protocol/isis/global/afi-safi/af/config/enabled: + /network-instances/network-instance/protocols/protocol/isis/levels/level/config/level-number: + /network-instances/network-instance/protocols/protocol/isis/levels/level/config/enabled: + /network-instances/network-instance/protocols/protocol/isis/levels/level/authentication/config/enabled: + /network-instances/network-instance/protocols/protocol/isis/levels/level/authentication/config/auth-mode: + /network-instances/network-instance/protocols/protocol/isis/levels/level/authentication/config/auth-password: + /network-instances/network-instance/protocols/protocol/isis/levels/level/authentication/config/auth-type: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/config/interface-id: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/config/enabled: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/timers/config/csnp-interval: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/timers/config/lsp-pacing-interval: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/config/level-number: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/timers/config/hello-interval: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/timers/config/hello-multiplier: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/hello-authentication/config/auth-mode: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/hello-authentication/config/auth-password: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/hello-authentication/config/auth-type: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/hello-authentication/config/enabled: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/afi-safi/af/config/afi-name: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/afi-safi/af/config/safi-name: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/afi-safi/af/config/enabled: + + + ## State paths + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/state/circuit-type: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/system-id: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/afi-safi/af/state/afi-name: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/afi-safi/af/state/metric: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/afi-safi/af/state/safi-name: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/packet-counters/csnp/state/dropped: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/packet-counters/csnp/state/processed: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/packet-counters/csnp/state/received: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/packet-counters/csnp/state/sent: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/packet-counters/iih/state/dropped: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/packet-counters/iih/state/processed: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/packet-counters/iih/state/received: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/packet-counters/iih/state/retransmit: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/packet-counters/iih/state/sent: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/packet-counters/lsp/state/dropped: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/packet-counters/lsp/state/processed: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/packet-counters/lsp/state/received: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/packet-counters/lsp/state/retransmit: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/packet-counters/lsp/state/sent: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/packet-counters/psnp/state/dropped: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/packet-counters/psnp/state/processed: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/packet-counters/psnp/state/received: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/packet-counters/psnp/state/retransmit: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/packet-counters/psnp/state/sent: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/timers/state/hello-interval: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/timers/state/hello-multiplier: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/circuit-counters/state/adj-changes: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/circuit-counters/state/adj-number: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/circuit-counters/state/auth-fails: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/circuit-counters/state/auth-type-fails: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/circuit-counters/state/id-field-len-mismatches: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/circuit-counters/state/lan-dis-changes: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/circuit-counters/state/rejected-adj: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/adjacency-state: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/area-address: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/dis-system-id: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/local-extended-circuit-id: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/multi-topology: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-circuit-type: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-extended-circuit-id: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-ipv4-address: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-ipv6-address: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-snpa: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/nlpid: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/priority: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/restart-status: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/restart-support: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/restart-suppress: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/auth-fails: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/auth-type-fails: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/corrupted-lsps: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/database-overloads: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/exceed-max-seq-nums: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/id-len-mismatch: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/lsp-errors: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/max-area-address-mismatches: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/own-lsp-purges: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/seq-num-skips: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/spf-runs: + ###For LSDB - Examples of paths + /network-instances/network-instance/protocols/protocol/isis/levels/level/link-state-database/lsp/state/lsp-id: + /network-instances/network-instance/protocols/protocol/isis/levels/level/link-state-database/lsp/state/maximum-area-addresses: + /network-instances/network-instance/protocols/protocol/isis/levels/level/link-state-database/lsp/state/pdu-type: + /network-instances/network-instance/protocols/protocol/isis/levels/level/link-state-database/lsp/state/sequence-number: + /network-instances/network-instance/protocols/protocol/isis/levels/level/link-state-database/lsp/tlvs/tlv/state/type: + /network-instances/network-instance/protocols/protocol/isis/levels/level/link-state-database/lsp/tlvs/tlv/area-address/state/address: + /network-instances/network-instance/protocols/protocol/isis/levels/level/link-state-database/lsp/tlvs/tlv/hostname/state/hostname: + /network-instances/network-instance/protocols/protocol/isis/levels/level/link-state-database/lsp/tlvs/tlv/ipv4-interface-addresses/state/address: + /network-instances/network-instance/protocols/protocol/isis/levels/level/link-state-database/lsp/tlvs/tlv/ipv6-interface-addresses/state/address: + /network-instances/network-instance/protocols/protocol/isis/levels/level/link-state-database/lsp/tlvs/tlv/ipv4-te-router-id/state/router-id: + /network-instances/network-instance/protocols/protocol/isis/levels/level/link-state-database/lsp/tlvs/tlv/ipv6-te-router-id/state/router-id: + +rpcs: + gnmi: + gNMI.Set: + gNMI.Subscribe: +``` + +## Minimum DUT platform requirement + +* MFF - A modular form factor device containing LINECARDs, FABRIC and redundant CONTROLLER_CARD components +* FFF - fixed form factor +* vRX - virtual router device diff --git a/feature/experimental/isis/otg_tests/base_adjacencies_test/base_adjacencies_test.go b/feature/isis/otg_tests/base_adjacencies_test/base_adjacencies_test.go similarity index 100% rename from feature/experimental/isis/otg_tests/base_adjacencies_test/base_adjacencies_test.go rename to feature/isis/otg_tests/base_adjacencies_test/base_adjacencies_test.go diff --git a/feature/experimental/isis/otg_tests/base_adjacencies_test/metadata.textproto b/feature/isis/otg_tests/base_adjacencies_test/metadata.textproto similarity index 100% rename from feature/experimental/isis/otg_tests/base_adjacencies_test/metadata.textproto rename to feature/isis/otg_tests/base_adjacencies_test/metadata.textproto diff --git a/feature/experimental/isis/otg_tests/isis_change_lsp_lifetime_test/README.md b/feature/isis/otg_tests/isis_change_lsp_lifetime_test/README.md similarity index 70% rename from feature/experimental/isis/otg_tests/isis_change_lsp_lifetime_test/README.md rename to feature/isis/otg_tests/isis_change_lsp_lifetime_test/README.md index 02310135271..a7bd7a209cd 100644 --- a/feature/experimental/isis/otg_tests/isis_change_lsp_lifetime_test/README.md +++ b/feature/isis/otg_tests/isis_change_lsp_lifetime_test/README.md @@ -23,23 +23,18 @@ * Verify that the remaining lifetime of the lsp is remaining lifetime = configured lifetime - time passed since the LSP PDU generation. * Verify that once the new LSP PDU is generated the sequence number and checksum of the new LSP PDU is updated -## Config Parameter coverage - -* For prefix: - - * /network-instances/network-instance/protocols/protocol/isis/ - -* Parameters: - - * global/timers/config/lsp-lifetime-interval - -## Telemetry Parameter coverage - -* For prefix: - - * /network-instances/network-instance/protocols/protocol/isis/ - -* Parameters: - - * global/timers/state/lsp-lifetime-interval - * levels/level/link-state-database/lsp/state/remaining-lifetime +## OpenConfig Path and RPC Coverage +```yaml +paths: + ## Config Parameter Coverage + /network-instances/network-instance/protocols/protocol/isis/global/timers/config/lsp-lifetime-interval: + + ## Telemetry Parameter Coverage + /network-instances/network-instance/protocols/protocol/isis/global/timers/state/lsp-lifetime-interval: + /network-instances/network-instance/protocols/protocol/isis/levels/level/link-state-database/lsp/state/remaining-lifetime: + +rpcs: + gnmi: + gNMI.Subscribe: + gNMI.Set: +``` diff --git a/feature/experimental/isis/otg_tests/isis_change_lsp_lifetime_test/isis_change_lsp_lifetime_test.go b/feature/isis/otg_tests/isis_change_lsp_lifetime_test/isis_change_lsp_lifetime_test.go similarity index 100% rename from feature/experimental/isis/otg_tests/isis_change_lsp_lifetime_test/isis_change_lsp_lifetime_test.go rename to feature/isis/otg_tests/isis_change_lsp_lifetime_test/isis_change_lsp_lifetime_test.go diff --git a/feature/experimental/isis/otg_tests/isis_change_lsp_lifetime_test/metadata.textproto b/feature/isis/otg_tests/isis_change_lsp_lifetime_test/metadata.textproto similarity index 100% rename from feature/experimental/isis/otg_tests/isis_change_lsp_lifetime_test/metadata.textproto rename to feature/isis/otg_tests/isis_change_lsp_lifetime_test/metadata.textproto diff --git a/feature/experimental/isis/otg_tests/isis_drain_test/README.md b/feature/isis/otg_tests/isis_drain_test/README.md similarity index 84% rename from feature/experimental/isis/otg_tests/isis_drain_test/README.md rename to feature/isis/otg_tests/isis_drain_test/README.md index 8c2bf143e5f..67410a03579 100644 --- a/feature/experimental/isis/otg_tests/isis_drain_test/README.md +++ b/feature/isis/otg_tests/isis_drain_test/README.md @@ -12,15 +12,13 @@ Ensure that IS-IS metric change can drain traffic from a DUT trunk interface * Change the ISIS metric of trunk-2 to 1000 value. Validate that 100% of the traffic is going out of only trunk-3 and there is no traffic loss. * Revert back the ISIS metric on trunk-2. Validate that the traffic is going via both trunk-2 and trunk-3, and there is no traffic loss. -## Config Parameter Coverage - -## Telemetry Parameter Coverage - -## Protocol/RPC Parameter Coverage - -* IS-IS - * LSP - * TLV 22 metric field. +## OpenConfig Path and RPC Coverage +```yaml +rpcs: + gnmi: + gNMI.Subscribe: + gNMI.Set: +``` ## Minimum DUT Platform Requirement diff --git a/feature/experimental/isis/otg_tests/isis_drain_test/isis_drain_test.go b/feature/isis/otg_tests/isis_drain_test/isis_drain_test.go similarity index 100% rename from feature/experimental/isis/otg_tests/isis_drain_test/isis_drain_test.go rename to feature/isis/otg_tests/isis_drain_test/isis_drain_test.go diff --git a/feature/experimental/isis/otg_tests/isis_drain_test/metadata.textproto b/feature/isis/otg_tests/isis_drain_test/metadata.textproto similarity index 100% rename from feature/experimental/isis/otg_tests/isis_drain_test/metadata.textproto rename to feature/isis/otg_tests/isis_drain_test/metadata.textproto diff --git a/feature/isis/otg_tests/isis_interface_hello_padding_enable_test/README.md b/feature/isis/otg_tests/isis_interface_hello_padding_enable_test/README.md new file mode 100644 index 00000000000..7448bf4d1b8 --- /dev/null +++ b/feature/isis/otg_tests/isis_interface_hello_padding_enable_test/README.md @@ -0,0 +1,92 @@ +# RT-2.6: IS-IS Hello-Padding enabled at interface level + +## Summary + +* Base IS-IS functionality and adjacency establishment. +* Verifies isis adjacency by changing MTU. + +## Procedure + +* Configure IS-IS for ATE port-1 and DUT port-1. +* Configure DUT with global hello-padding enabled. +* Ensure that adjacencies are established with: + * Interface level hello padding is enabled. + * Verify that IPv4 and IPv6 IS-ISIS adjacency comes up fine. + * Verify the output of ST path displaying the status of ISIS hello padding. + * If we change the MTU on either side, then adjacency should not come up. + * Verify that IPv4 and IPv6 prefixes that are advertised by ATE correctly installed into DUTs route and forwarding table. + * TODO-Verify the Hellos are sent with Padding during adjacency turn-up if the padding is enabled adaptively/sometimes. + * Ensure that IPv4 and IPv6 prefixes that are advertised as part of an (emulated) neighboring system are installed into the DUT routing table, and validate that packets are sent and received to them. + +## OpenConfig Path and RPC Coverage +```yaml +paths: + ## Config Parameter Coverage + /network-instances/network-instance/protocols/protocol/isis/global/config/authentication-check: + /network-instances/network-instance/protocols/protocol/isis/global/config/net: + /network-instances/network-instance/protocols/protocol/isis/global/config/level-capability: + /network-instances/network-instance/protocols/protocol/isis/global/config/hello-padding: + /network-instances/network-instance/protocols/protocol/isis/global/afi-safi/af/config/enabled: + /network-instances/network-instance/protocols/protocol/isis/levels/level/config/level-number: + /network-instances/network-instance/protocols/protocol/isis/levels/level/config/enabled: + /network-instances/network-instance/protocols/protocol/isis/levels/level/authentication/config/enabled: + /network-instances/network-instance/protocols/protocol/isis/levels/level/authentication/config/auth-mode: + /network-instances/network-instance/protocols/protocol/isis/levels/level/authentication/config/auth-password: + /network-instances/network-instance/protocols/protocol/isis/levels/level/authentication/config/auth-type: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/config/interface-id: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/config/enabled: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/config/circuit-type: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/timers/config/csnp-interval: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/timers/config/lsp-pacing-interval: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/config/level-number: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/timers/config/hello-interval: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/timers/config/hello-multiplier: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/hello-authentication/config/auth-mode: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/hello-authentication/config/auth-password: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/hello-authentication/config/auth-type: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/hello-authentication/config/enabled: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/afi-safi/af/config/afi-name: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/afi-safi/af/config/safi-name: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/afi-safi/af/config/enabled: + + ## Telemetry Parameter Coverage + /network-instances/network-instance/protocols/protocol/isis/global/state/hello-padding: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/state/hello-padding: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/adjacency-state: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-ipv4-address: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-ipv6-address: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/system-id: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/area-address: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/dis-system-id: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/local-extended-circuit-id: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/multi-topology: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-circuit-type: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-extended-circuit-id: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-snpa: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/nlpid: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/priority: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/restart-status: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/restart-support: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/restart-suppress: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/afi-safi/af/state/afi-name: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/afi-safi/af/state/metric: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/afi-safi/af/state/safi-name: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/auth-fails: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/auth-type-fails: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/corrupted-lsps: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/database-overloads: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/exceed-max-seq-nums: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/id-len-mismatch: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/lsp-errors: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/manual-address-drop-from-areas: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/max-area-address-mismatches: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/own-lsp-purges: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/part-changes: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/seq-num-skips: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/spf-runs: + +rpcs: + gnmi: + gNMI.Subscribe: + gNMI.Set: +``` \ No newline at end of file diff --git a/feature/experimental/isis/otg_tests/isis_interface_hello_padding_enable_test/isis_interface_hello_padding_enable_test.go b/feature/isis/otg_tests/isis_interface_hello_padding_enable_test/isis_interface_hello_padding_enable_test.go similarity index 100% rename from feature/experimental/isis/otg_tests/isis_interface_hello_padding_enable_test/isis_interface_hello_padding_enable_test.go rename to feature/isis/otg_tests/isis_interface_hello_padding_enable_test/isis_interface_hello_padding_enable_test.go diff --git a/feature/experimental/isis/otg_tests/isis_interface_hello_padding_enable_test/metadata.textproto b/feature/isis/otg_tests/isis_interface_hello_padding_enable_test/metadata.textproto similarity index 100% rename from feature/experimental/isis/otg_tests/isis_interface_hello_padding_enable_test/metadata.textproto rename to feature/isis/otg_tests/isis_interface_hello_padding_enable_test/metadata.textproto diff --git a/feature/isis/otg_tests/isis_interface_level_passive_test/README.md b/feature/isis/otg_tests/isis_interface_level_passive_test/README.md new file mode 100644 index 00000000000..b0d7374a153 --- /dev/null +++ b/feature/isis/otg_tests/isis_interface_level_passive_test/README.md @@ -0,0 +1,95 @@ +# RT-2.11: IS-IS Passive is enabled at the area level + +## Summary + +* Verify isis adjacency with passive enabled under level. + +## Topology + +* ATE:port1 <-> port1:DUT:port2 <-> ATE:port2 + +## Procedure + +* Configure IS-IS for ATE port-1 and DUT port-1. +* Configure DUT interface with IS-IS passive configured at area level 2. + * Verify that IS-IS adjacency is not coming up in level-2 area for IPv4 and IPV6 address families. +* Undo the IS-IS passive configuration under level 2 + * Verify that IS-IS adjacency for IPv4 and IPV6 address families are coming up in the level-2 area. + * Verify that IPv4 and IPv6 prefixes that are advertised by ATE are correctly installed into DUTs route and forwarding table. + * Ensure that IPv4 and IPv6 prefixes that are advertised as part of an (emulated) neighboring system are installed into the DUT routing table, and validate that packets are sent and received to them. + * TODO-Verify the output of ST path displaying the interface as passive in ISIS database/adj table + +## OpenConfig Path and RPC Coverage +```yaml +paths: + ## Config Parameter Coverage + /network-instances/network-instance/protocols/protocol/isis/global/config/authentication-check: + /network-instances/network-instance/protocols/protocol/isis/global/config/net: + /network-instances/network-instance/protocols/protocol/isis/global/config/level-capability: + /network-instances/network-instance/protocols/protocol/isis/global/config/hello-padding: + /network-instances/network-instance/protocols/protocol/isis/global/afi-safi/af/config/enabled: + /network-instances/network-instance/protocols/protocol/isis/levels/level/config/level-number: + /network-instances/network-instance/protocols/protocol/isis/levels/level/config/enabled: + /network-instances/network-instance/protocols/protocol/isis/levels/level/authentication/config/enabled: + /network-instances/network-instance/protocols/protocol/isis/levels/level/authentication/config/auth-mode: + /network-instances/network-instance/protocols/protocol/isis/levels/level/authentication/config/auth-password: + /network-instances/network-instance/protocols/protocol/isis/levels/level/authentication/config/auth-type: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/config/interface-id: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/config/enabled: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/config/circuit-type: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/config/passive: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/timers/config/csnp-interval: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/timers/config/lsp-pacing-interval: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/config/level-number: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/config/passive: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/timers/config/hello-interval: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/timers/config/hello-multiplier: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/hello-authentication/config/auth-mode: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/hello-authentication/config/auth-password: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/hello-authentication/config/auth-type: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/hello-authentication/config/enabled: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/afi-safi/af/config/afi-name: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/afi-safi/af/config/safi-name: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/afi-safi/af/config/enabled: + + ## Telemetry Parameter Coverage + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/state/passive: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/state/passive: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/adjacency-state: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-ipv4-address: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-ipv6-address: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/system-id: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/area-address: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/dis-system-id: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/local-extended-circuit-id: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/multi-topology: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-circuit-type: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-extended-circuit-id: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-snpa: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/nlpid: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/priority: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/restart-status: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/restart-support: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/restart-suppress: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/afi-safi/af/state/afi-name: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/afi-safi/af/state/metric: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/afi-safi/af/state/safi-name: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/auth-fails: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/auth-type-fails: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/corrupted-lsps: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/database-overloads: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/exceed-max-seq-nums: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/id-len-mismatch: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/lsp-errors: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/manual-address-drop-from-areas: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/max-area-address-mismatches: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/own-lsp-purges: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/part-changes: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/seq-num-skips: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/spf-runs: + +rpcs: + gnmi: + gNMI.Subscribe: + gNMI.Set: +``` \ No newline at end of file diff --git a/feature/experimental/isis/otg_tests/isis_interface_level_passive_test/isis_interface_level_passive_test.go b/feature/isis/otg_tests/isis_interface_level_passive_test/isis_interface_level_passive_test.go similarity index 100% rename from feature/experimental/isis/otg_tests/isis_interface_level_passive_test/isis_interface_level_passive_test.go rename to feature/isis/otg_tests/isis_interface_level_passive_test/isis_interface_level_passive_test.go diff --git a/feature/experimental/isis/otg_tests/isis_interface_level_passive_test/metadata.textproto b/feature/isis/otg_tests/isis_interface_level_passive_test/metadata.textproto similarity index 100% rename from feature/experimental/isis/otg_tests/isis_interface_level_passive_test/metadata.textproto rename to feature/isis/otg_tests/isis_interface_level_passive_test/metadata.textproto diff --git a/feature/experimental/isis/otg_tests/isis_interface_passive_test/README.md b/feature/isis/otg_tests/isis_interface_passive_test/README.md similarity index 99% rename from feature/experimental/isis/otg_tests/isis_interface_passive_test/README.md rename to feature/isis/otg_tests/isis_interface_passive_test/README.md index cd87a3ba503..bf600ec87b0 100644 --- a/feature/experimental/isis/otg_tests/isis_interface_passive_test/README.md +++ b/feature/isis/otg_tests/isis_interface_passive_test/README.md @@ -76,7 +76,7 @@ paths: /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/exceed-max-seq-nums: /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/id-len-mismatch: /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/lsp-errors: -/network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/manual-address-drop-from-area : +/network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/manual-address-drop-from-areas: /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/max-area-address-mismatches: /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/own-lsp-purges: /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/part-changes : diff --git a/feature/experimental/isis/otg_tests/isis_interface_passive_test/isis_interface_passive_test.go b/feature/isis/otg_tests/isis_interface_passive_test/isis_interface_passive_test.go similarity index 100% rename from feature/experimental/isis/otg_tests/isis_interface_passive_test/isis_interface_passive_test.go rename to feature/isis/otg_tests/isis_interface_passive_test/isis_interface_passive_test.go diff --git a/feature/experimental/isis/otg_tests/isis_interface_passive_test/metadata.textproto b/feature/isis/otg_tests/isis_interface_passive_test/metadata.textproto similarity index 100% rename from feature/experimental/isis/otg_tests/isis_interface_passive_test/metadata.textproto rename to feature/isis/otg_tests/isis_interface_passive_test/metadata.textproto diff --git a/feature/experimental/isis/otg_tests/isis_metric_style_wide_enabled_test/README.md b/feature/isis/otg_tests/isis_metric_style_wide_enabled_test/README.md similarity index 100% rename from feature/experimental/isis/otg_tests/isis_metric_style_wide_enabled_test/README.md rename to feature/isis/otg_tests/isis_metric_style_wide_enabled_test/README.md diff --git a/feature/experimental/isis/otg_tests/isis_metric_style_wide_enabled_test/isis_metric_style_wide_enabled_test.go b/feature/isis/otg_tests/isis_metric_style_wide_enabled_test/isis_metric_style_wide_enabled_test.go similarity index 100% rename from feature/experimental/isis/otg_tests/isis_metric_style_wide_enabled_test/isis_metric_style_wide_enabled_test.go rename to feature/isis/otg_tests/isis_metric_style_wide_enabled_test/isis_metric_style_wide_enabled_test.go diff --git a/feature/experimental/isis/otg_tests/isis_metric_style_wide_enabled_test/metadata.textproto b/feature/isis/otg_tests/isis_metric_style_wide_enabled_test/metadata.textproto similarity index 100% rename from feature/experimental/isis/otg_tests/isis_metric_style_wide_enabled_test/metadata.textproto rename to feature/isis/otg_tests/isis_metric_style_wide_enabled_test/metadata.textproto diff --git a/feature/isis/otg_tests/isis_metric_style_wide_not_enabled_test/README.md b/feature/isis/otg_tests/isis_metric_style_wide_not_enabled_test/README.md new file mode 100644 index 00000000000..49fa92ad9b2 --- /dev/null +++ b/feature/isis/otg_tests/isis_metric_style_wide_not_enabled_test/README.md @@ -0,0 +1,94 @@ +# RT-2.8: IS-IS metric style wide not enabled + +## Summary + +* Base IS-IS functionality and adjacency establishment. +* Verifies route metric with wide metric disabled on DUT. + +## Procedure + +* TestISISWideMetricNotEnabled + + * Configure IS-IS for ATE port-1 and DUT port-1. + * Do not configure metric style wide under the area level. + * Enable wide metric style on ATE. + * Advertise ISIS prefixes from ATE with wide metrics (value > 63). + * Verify that IS-IS adjacency for IPv4 and IPV6 address family is coming up. + * Verify that IPv4 and IPv6 prefixes that are advertised by ATE correctly installed into DUTs route and forwarding table. + * TODO-Verify that the metrics of the IPv4 and IPv6 prefixes is 63. + * Ensure that IPv4 and IPv6 prefixes that are advertised as part of an (emulated) neighboring system are installed into the DUT routing table, and validate that packets are sent and received to them. + +## OpenConfig Path and RPC Coverage +```yaml +paths: + ## Config Parameter Coverage + /network-instances/network-instance/protocols/protocol/isis/global/config/authentication-check: + /network-instances/network-instance/protocols/protocol/isis/global/config/net: + /network-instances/network-instance/protocols/protocol/isis/global/config/level-capability: + /network-instances/network-instance/protocols/protocol/isis/global/config/hello-padding: + /network-instances/network-instance/protocols/protocol/isis/global/afi-safi/af/config/enabled: + /network-instances/network-instance/protocols/protocol/isis/levels/level/config/level-number: + /network-instances/network-instance/protocols/protocol/isis/levels/level/config/enabled: + /network-instances/network-instance/protocols/protocol/isis/levels/level/config/metric-style: + /network-instances/network-instance/protocols/protocol/isis/levels/level/authentication/config/enabled: + /network-instances/network-instance/protocols/protocol/isis/levels/level/authentication/config/auth-mode: + /network-instances/network-instance/protocols/protocol/isis/levels/level/authentication/config/auth-password: + /network-instances/network-instance/protocols/protocol/isis/levels/level/authentication/config/auth-type: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/config/interface-id: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/config/enabled: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/config/circuit-type: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/config/passive: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/timers/config/csnp-interval: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/timers/config/lsp-pacing-interval: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/config/level-number: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/config/passive: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/timers/config/hello-interval: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/timers/config/hello-multiplier: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/hello-authentication/config/auth-mode: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/hello-authentication/config/auth-password: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/hello-authentication/config/auth-type: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/hello-authentication/config/enabled: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/afi-safi/af/config/afi-name: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/afi-safi/af/config/safi-name: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/afi-safi/af/config/enabled: + + ## Telemetry Parameter Coverage + /network-instances/network-instance/protocols/protocol/isis/levels/level/state/metric-style: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/adjacency-state: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-ipv4-address: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-ipv6-address: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/system-id: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/area-address: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/dis-system-id: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/local-extended-circuit-id: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/multi-topology: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-circuit-type: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-extended-circuit-id: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/neighbor-snpa: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/nlpid: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/priority: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/restart-status: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/restart-support: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/adjacencies/adjacency/state/restart-suppress: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/afi-safi/af/state/afi-name: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/afi-safi/af/state/metric: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/afi-safi/af/state/safi-name: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/auth-fails: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/auth-type-fails: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/corrupted-lsps: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/database-overloads: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/exceed-max-seq-nums: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/id-len-mismatch: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/lsp-errors: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/manual-address-drop-from-areas: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/max-area-address-mismatches: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/own-lsp-purges: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/part-changes: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/seq-num-skips: + /network-instances/network-instance/protocols/protocol/isis/levels/level/system-level-counters/state/spf-runs: + +rpcs: + gnmi: + gNMI.Subscribe: + gNMI.Set: +``` \ No newline at end of file diff --git a/feature/experimental/isis/otg_tests/isis_metric_style_wide_not_enabled_test/isis_metric_style_wide_not_enabled_test.go b/feature/isis/otg_tests/isis_metric_style_wide_not_enabled_test/isis_metric_style_wide_not_enabled_test.go similarity index 100% rename from feature/experimental/isis/otg_tests/isis_metric_style_wide_not_enabled_test/isis_metric_style_wide_not_enabled_test.go rename to feature/isis/otg_tests/isis_metric_style_wide_not_enabled_test/isis_metric_style_wide_not_enabled_test.go diff --git a/feature/experimental/isis/otg_tests/isis_metric_style_wide_not_enabled_test/metadata.textproto b/feature/isis/otg_tests/isis_metric_style_wide_not_enabled_test/metadata.textproto similarity index 100% rename from feature/experimental/isis/otg_tests/isis_metric_style_wide_not_enabled_test/metadata.textproto rename to feature/isis/otg_tests/isis_metric_style_wide_not_enabled_test/metadata.textproto diff --git a/feature/experimental/isis/otg_tests/lsp_updates_test/README.md b/feature/isis/otg_tests/lsp_updates_test/README.md similarity index 58% rename from feature/experimental/isis/otg_tests/lsp_updates_test/README.md rename to feature/isis/otg_tests/lsp_updates_test/README.md index d207d7c482a..b1f4c16e5bc 100644 --- a/feature/experimental/isis/otg_tests/lsp_updates_test/README.md +++ b/feature/isis/otg_tests/lsp_updates_test/README.md @@ -20,26 +20,21 @@ Ensure that IS-IS updates reflect parameter changes on DUT. port via configuration, update value in configuration, and ensure that ATE and DUT telemetry reflects the change. -## Config Parameter Coverage - -For prefix: /network-instances/network-instance/protocols/protocol/isis/ - -Parameters: - -* global/lsp-bit/overload-bit/config/set-bit - -## Telemetry Parameter Coverage - -* /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/afi-safi/af/state/metric - -* /network-instances/network-instance/protocols/protocol/isis/global/lsp-bit/overload-bit/state/set-bit - -## Protocol/RPC Parameter Coverage - -* IS-IS - * LSP - * Flags - overload bit (5) - * TLV 22 metric field. +## OpenConfig Path and RPC Coverage +```yaml +paths: + ## Config Parameter Coverage + /network-instances/network-instance/protocols/protocol/isis/global/lsp-bit/overload-bit/config/set-bit: + + ## Telemetry Parameter Coverage + /network-instances/network-instance/protocols/protocol/isis/global/lsp-bit/overload-bit/state/set-bit: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/afi-safi/af/state/metric: + +rpcs: + gnmi: + gNMI.Subscribe: + gNMI.Set: +``` ## Minimum DUT Platform Requirement diff --git a/feature/experimental/isis/otg_tests/lsp_updates_test/lsp_updates_test.go b/feature/isis/otg_tests/lsp_updates_test/lsp_updates_test.go similarity index 100% rename from feature/experimental/isis/otg_tests/lsp_updates_test/lsp_updates_test.go rename to feature/isis/otg_tests/lsp_updates_test/lsp_updates_test.go diff --git a/feature/experimental/isis/otg_tests/lsp_updates_test/metadata.textproto b/feature/isis/otg_tests/lsp_updates_test/metadata.textproto similarity index 100% rename from feature/experimental/isis/otg_tests/lsp_updates_test/metadata.textproto rename to feature/isis/otg_tests/lsp_updates_test/metadata.textproto diff --git a/feature/isis/otg_tests/weighted_ecmp_test/metadata.textproto b/feature/isis/otg_tests/weighted_ecmp_test/metadata.textproto index 8057787e787..947afd21cf8 100644 --- a/feature/isis/otg_tests/weighted_ecmp_test/metadata.textproto +++ b/feature/isis/otg_tests/weighted_ecmp_test/metadata.textproto @@ -35,3 +35,11 @@ platform_exceptions: { weighted_ecmp_fixed_packet_verification: true } } +platform_exceptions: { + platform: { + vendor: JUNIPER + } + deviations: { + isis_level_enabled: true + } +} diff --git a/feature/isis/otg_tests/weighted_ecmp_test/weighted_ecmp_test.go b/feature/isis/otg_tests/weighted_ecmp_test/weighted_ecmp_test.go index 9e434f24e2a..ce6638892c2 100644 --- a/feature/isis/otg_tests/weighted_ecmp_test/weighted_ecmp_test.go +++ b/feature/isis/otg_tests/weighted_ecmp_test/weighted_ecmp_test.go @@ -9,7 +9,6 @@ import ( "github.com/open-traffic-generator/snappi/gosnappi" "github.com/openconfig/featureprofiles/internal/attrs" - "github.com/openconfig/featureprofiles/internal/cfgplugins" "github.com/openconfig/featureprofiles/internal/deviations" "github.com/openconfig/featureprofiles/internal/fptest" "github.com/openconfig/featureprofiles/internal/helpers" @@ -104,8 +103,8 @@ var ( agg4 = &aggPortData{ dutIPv4: "192.0.2.13", ateIPv4: "192.0.2.14", - dutIPv6: "2001:db8::14", - ateIPv6: "2001:db8::15", + dutIPv6: "2001:db8::15", + ateIPv6: "2001:db8::16", ateAggName: "lag4", ateAggMAC: "02:00:01:01:01:10", atePort1MAC: "02:00:01:01:01:11", @@ -174,12 +173,33 @@ func TestWeightedECMPForISIS(t *testing.T) { ate.OTG().PushConfig(t, top) ate.OTG().StartProtocols(t) VerifyISISTelemetry(t, dut, aggIDs, []*aggPortData{agg1, agg2}) + for _, agg := range []*aggPortData{agg1, agg2} { bgpPath := gnmi.OC().NetworkInstance(deviations.DefaultNetworkInstance(dut)).Protocol(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, "BGP").Bgp() gnmi.Await(t, dut, bgpPath.Neighbor(agg.ateLoopbackV4).SessionState().State(), 2*time.Minute, oc.Bgp_Neighbor_SessionState_ESTABLISHED) gnmi.Await(t, dut, bgpPath.Neighbor(agg.ateLoopbackV6).SessionState().State(), 2*time.Minute, oc.Bgp_Neighbor_SessionState_ESTABLISHED) } + statePath := gnmi.OC().NetworkInstance(deviations.DefaultNetworkInstance(dut)).Protocol(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, "BGP").Bgp() + + t.Log("Waiting for BGP v4 prefix to be installed") + got, found := gnmi.Watch(t, dut, statePath.Neighbor(agg2.ateLoopbackV4).AfiSafi(oc.BgpTypes_AFI_SAFI_TYPE_IPV4_UNICAST).Prefixes().Installed().State(), 120*time.Second, func(val *ygnmi.Value[uint32]) bool { + prefixCount, ok := val.Val() + return ok && prefixCount == 1 + }).Await(t) + if !found { + t.Fatalf("Installed prefixes v4 mismatch: got %v, want %v", got, 1) + } + + t.Log("Waiting for BGP v6 prefix to be installed") + got, found = gnmi.Watch(t, dut, statePath.Neighbor(agg2.ateLoopbackV6).AfiSafi(oc.BgpTypes_AFI_SAFI_TYPE_IPV6_UNICAST).Prefixes().Installed().State(), 120*time.Second, func(val *ygnmi.Value[uint32]) bool { + prefixCount, ok := val.Val() + return ok && prefixCount == 1 + }).Await(t) + if !found { + t.Fatalf("Installed prefixes v6 mismatch: got %v, want %v", got, 1) + } + startTraffic(t, ate, top) time.Sleep(time.Minute) t.Run("Equal_Distribution_Of_Traffic", func(t *testing.T) { @@ -427,7 +447,6 @@ func configureOTGBGP(t *testing.T, dev gosnappi.Device, agg *aggPortData, advV4, func configureOTGISIS(t *testing.T, dev gosnappi.Device, agg *aggPortData) { t.Helper() - dut := ondatra.DUT(t, "dut") isis := dev.Isis().SetSystemId(agg.ateISISSysID).SetName(agg.ateAggName + ".ISIS") isis.Basic().SetHostname(isis.Name()) isis.Advanced().SetAreaAddresses([]string{ateAreaAddress}) @@ -437,13 +456,12 @@ func configureOTGISIS(t *testing.T, dev gosnappi.Device, agg *aggPortData) { SetNetworkType(gosnappi.IsisInterfaceNetworkType.POINT_TO_POINT). SetLevelType(gosnappi.IsisInterfaceLevelType.LEVEL_2).SetMetric(10) isisInt.Advanced().SetAutoAdjustMtu(true).SetAutoAdjustArea(true).SetAutoAdjustSupportedProtocols(true) - if deviations.ISISLoopbackRequired(dut) { - // configure ISIS loopback interface and advertise them via ISIS. - isisPort2V4 := dev.Isis().V4Routes().Add().SetName(agg.ateAggName + ".ISISV4").SetLinkMetric(10) - isisPort2V4.Addresses().Add().SetAddress(agg.ateLoopbackV4).SetPrefix(32) - isisPort2V6 := dev.Isis().V6Routes().Add().SetName(agg.ateAggName + ".ISISV6").SetLinkMetric(10) - isisPort2V6.Addresses().Add().SetAddress(agg.ateLoopbackV6).SetPrefix(uint32(128)) - } + + // configure ISIS loopback interface and advertise them via ISIS. + isisPort2V4 := dev.Isis().V4Routes().Add().SetName(agg.ateAggName + ".ISISV4").SetLinkMetric(10) + isisPort2V4.Addresses().Add().SetAddress(agg.ateLoopbackV4).SetPrefix(32) + isisPort2V6 := dev.Isis().V6Routes().Add().SetName(agg.ateAggName + ".ISISV6").SetLinkMetric(10) + isisPort2V6.Addresses().Add().SetAddress(agg.ateLoopbackV6).SetPrefix(uint32(128)) } @@ -514,9 +532,6 @@ func configureDUT(t *testing.T, dut *ondatra.DUTDevice) []string { for _, aggID := range aggIDs { gnmi.Await(t, dut, gnmi.OC().Interface(aggID).AdminStatus().State(), 60*time.Second, oc.Interface_AdminStatus_UP) } - if !deviations.ISISLoopbackRequired(dut) { - configureStaticRouteToATELoopbacks(t, dut) - } configureRoutingPolicy(t, dut) configureDUTISIS(t, dut, aggIDs) configureDUTBGP(t, dut) @@ -563,50 +578,6 @@ func configureDUTLoopback(t *testing.T, dut *ondatra.DUTDevice) { } } -func configureStaticRouteToATELoopbacks(t *testing.T, dut *ondatra.DUTDevice) { - t.Helper() - - sr4ATE1 := &cfgplugins.StaticRouteCfg{ - NetworkInstance: deviations.DefaultNetworkInstance(dut), - Prefix: agg1.ateLoopbackV4 + "/32", - NextHops: map[string]oc.NetworkInstance_Protocol_Static_NextHop_NextHop_Union{ - "0": oc.UnionString(agg1.ateIPv4), - }, - } - sr6ATE1 := &cfgplugins.StaticRouteCfg{ - NetworkInstance: deviations.DefaultNetworkInstance(dut), - Prefix: agg1.ateLoopbackV6 + "/128", - NextHops: map[string]oc.NetworkInstance_Protocol_Static_NextHop_NextHop_Union{ - "0": oc.UnionString(agg1.ateIPv6), - }, - } - sr4ATE2 := &cfgplugins.StaticRouteCfg{ - NetworkInstance: deviations.DefaultNetworkInstance(dut), - Prefix: agg2.ateLoopbackV4 + "/32", - NextHops: map[string]oc.NetworkInstance_Protocol_Static_NextHop_NextHop_Union{ - "0": oc.UnionString(agg2.ateIPv4), - "1": oc.UnionString(agg3.ateIPv4), - "2": oc.UnionString(agg4.ateIPv4), - }, - } - sr6ATE2 := &cfgplugins.StaticRouteCfg{ - NetworkInstance: deviations.DefaultNetworkInstance(dut), - Prefix: agg2.ateLoopbackV6 + "/128", - NextHops: map[string]oc.NetworkInstance_Protocol_Static_NextHop_NextHop_Union{ - "0": oc.UnionString(agg2.ateIPv6), - "1": oc.UnionString(agg3.ateIPv6), - "2": oc.UnionString(agg4.ateIPv6), - }, - } - b := &gnmi.SetBatch{} - for _, cfg := range []*cfgplugins.StaticRouteCfg{sr4ATE1, sr6ATE1, sr4ATE2, sr6ATE2} { - if _, err := cfgplugins.NewStaticRouteCfg(b, cfg, dut); err != nil { - t.Fatalf("Failed to configure static route to ATE Loopback: %v", err) - } - } - b.Set(t, dut) -} - func configureDUTISIS(t *testing.T, dut *ondatra.DUTDevice, aggIDs []string) { t.Helper() @@ -632,6 +603,9 @@ func configureDUTISIS(t *testing.T, dut *ondatra.DUTDevice, aggIDs []string) { isisLevel2 := isis.GetOrCreateLevel(2) isisLevel2.MetricStyle = oc.Isis_MetricStyle_WIDE_METRIC + if deviations.ISISLevelEnabled(dut) { + isisLevel2.Enabled = ygot.Bool(true) + } if deviations.ISISLoopbackRequired(dut) { gnmi.Update(t, dut, gnmi.OC().Config(), d) // add loopback interface to ISIS diff --git a/feature/mpls/otg_tests/static_bgp_nexthop/README.md b/feature/mpls/otg_tests/static_bgp_nexthop/README.md new file mode 100644 index 00000000000..7ed0a06fe99 --- /dev/null +++ b/feature/mpls/otg_tests/static_bgp_nexthop/README.md @@ -0,0 +1,121 @@ +# MPLS-2.2: MPLS forwarding via static LSP to BGP next-hop. + +## Summary + +Validate static LSP functionality with BGP resolved next-hop. This test verifies that the DUT can forward MPLS traffic based on a static LSP that uses a next-hop resolved via BGP. + +## Testbed type + +* [`featureprofiles/topologies/atedut_4.testbed`](https://github.com/openconfig/featureprofiles/blob/main/topologies/atedut_4.testbed) + +## Procedure + +### Configuration + +1) Create the topology below: + + ``` + | | ---- | ATE Port 2 | ---- [eBGP peer] + [ ATE Port 1 ] ---- | DUT | | | + | | ---- | ATE Port 3 | + ``` + +2) Configure eBGP peer on ATE Port 2 interface and advertise `BGP-NH-V4= 203.0.200.0/24` and `BGP-NH-V6= 2001:db8:128:200::/64` +3) Configure static routes on the DUT to discard traffic destined for BGP-NH-V4 and BGP-NH-V6. These routes should point to a Null0 with an administrative distance of 254 to ensure they are less preferred than the BGP routes. This prevents the DUT from using its IGP to reach the BGP next-hops. +4) Enable MPLS forwarding. +5) Create egress static LSP for IPv4 and IPV6 traffic to pop the label and resolve the next-hop BGP-NH-V4 and BGP-NH-V6 respectivelly + +```yaml +network-instances: + - network-instance: + mpls: + lsps: + static-lsps: + - static-lsp: + config: + name: "lsp-egress-v4" + egress: + next-hop: 203.0.200.1 + incoming-label: 1000004 + - static-lsp: + config: + name: "lsp-egress-v6" + egress: + next-hop: 2001:db8:128:200::1 + incoming-label: 1000006 +``` + * Set resolve NH action for both LSPs. + +**TODO:** OC model does not support resolve next-hop option for LSPs. + +7) Configure static routes i.e. `IPV4-DST = 203.0.113.0/24` and `IPV6-DST = 2001:db8:128:128::/64` to ATE Port 3. +```yaml +network-instances: + - network-instance: + protocols: + - protocol: + static-routes: + - static: + config: + prefix: "203.0.113.0/24" + next-hops: + - next-hop: + config: + index: 1 + next-hop: "ATE PORT 3" + - static: + config: + prefix: "2001:db8:128:128::/64" + next-hops: + - next-hop: + config: + index: 1 + next-hop: "ATE PORT 3" +``` + +### MPLS-2.2.1: Verify IPv4 MPLS forwarding + +* Push the above DUT configuration. +* Start traffic flow with MPLS[lbl-1000004] and IPv4 destined to IPV4-DST. +* Verify that traffic arrives to ATE Port 2. + +### MPLS-2.2.2: Verify IPv6 MPLS forwarding + +* Push the above DUT configuration. +* Start traffic flow with MPLS[lbl-1000006] and IPv4 destined to IPV6-DST. +* Verify that traffic arrives to ATE Port 2. + +### MPLS-2.2.3: Verify IPv4 traffic discard when BGP-NH is not available. + +* Withdraw BGP-NH-V4 advertisement. +* Push the above DUT configuration. +* Start traffic flow with MPLS[lbl-1000004] and IPv4 destination set to IPV4-DST. +* Verify that traffic is discarded. + +### MPLS-2.2.4: Verify IPv6 traffic discard when BGP-NH is not available. + +* Withdraw BGP-NH-V6 advertisement. +* Push the above DUT configuration. +* Start traffic flow with MPLS[lbl-1000006] and IPv6 destination set to IPV6-DST. +* Verify that traffic is discarded. + +## OpenConfig Path and RPC Coverage + +```yaml +paths: + ## Config paths + /network-instances/network-instance/mpls/lsps/static-lsps/static-lsp/egress/config/incoming-label: + /network-instances/network-instance/mpls/lsps/static-lsps/static-lsp/egress/config/next-hop: + /network-instances/network-instance/protocols/protocol/static-routes/static/config/prefix: + /network-instances/network-instance/protocols/protocol/static-routes/static/next-hops/next-hop/config/next-hop: + /network-instances/network-instance/protocols/protocol/static-routes/static/next-hops/next-hop/config/index: + + +rpcs: + gnmi: + gNMI.Set: + union_replace: true + replace: true + gNMI.Subscribe: + on_change: true +``` \ No newline at end of file diff --git a/feature/mtu/largeippacket/otg_tests/large_ip_packet_transmission/README.md b/feature/mtu/largeippacket/otg_tests/large_ip_packet_transmission/README.md index 451b0999606..65b5c91b444 100644 --- a/feature/mtu/largeippacket/otg_tests/large_ip_packet_transmission/README.md +++ b/feature/mtu/largeippacket/otg_tests/large_ip_packet_transmission/README.md @@ -7,17 +7,70 @@ IPv4 and IPv6 packet sizes are sent over them. ## Procedure -* Configure DUT with routed input and output interfaces with an Ethernet MTU of 9216. +* Test environment setup + * Configure DUT with routed input and output interfaces with an Ethernet MTU of 9216. * Test should be executed with two different interface/connectivity profiles: 1) Standalone -- one input and one output port 2) Bundle with four input members and four output members -* Run traffic flows of the following size over IPv4 and IPv6 between ATE ports. - * 1500 Bytes - * 2000 Bytes - * 4000 Bytes - * 9202 Bytes -* Assert ATE reports packets sent and received count are the same, indicating no fragmentation, and - successful transit. + + An example OpenConfig configuration pushed to the DUT + + ```yaml + + openconfig-interfaces: + - interface: + name: 'tunnel1_if_name' + config: + name: 'tunnel1_if_name' + tunnel: # configures the tunnel parameters + config: + src: 'tunnel1_outer_ip_src' + dst: 'tunnel1_outer_ip_dst' + ttl: 'tunnel1_outer_ttl' + gre-key: 'tunnel1_outer_gre_key' + ipv4: + config: + mtu: 'tunnel1_inner_mtu' + addresses: + - address: + config: + ip: 'tunnel1_interface_ipv4' # For tunnel decap destination and/or route next-hop + prefix-length: 'tunnel1_interface_ipv4_prefixlen' + ipv6: + config: + mtu: 'tunnel1_inner_mtu' + addresses: + - address: + config: + ip: 'tunnel1_interface_ipv6' # For tunnel decap destination and/or route next-hop + prefix-length: 'tunnel1_interface_ipv6_prefixlen' + + +* MTU-1.3.1: Test with Physical and Bundle interfaces + * Run traffic flows of the following size over IPv4 and IPv6 between ATE ports. + * 1500 Bytes + * 2000 Bytes + * 4000 Bytes + * 9202 Bytes + * Assert ATE reports packets sent and received count are the same, indicating no fragmentation, and + successful transit. + +* MTU-1.3.2: Test w/ tunnel interfaces and forwarding plane via the physical and bundled interfaces [TODO: https://github.com/openconfig/featureprofiles/issues/3411] + * Configure DUT with a GRE tunnel interface. + * Tunnel interface uses /32 tunnel destination and loopback interface as the source of the tunnel. + * Ensure MTU configured on this tunnel interface is in context to the MTU on the egress physical/bundle interface. It is acceptable if the implementation doesn't support explicit MTU config on tunnel interfaces. Idea is for the tunnel interface to respect the egress physical/bundle interface MTU config. + * Configure a static route for the tunnel end point destination pointing at an exit interface. + * Pick 2 different /24 IPv4 and /64 IPv6 subnets each to emulate destination of payload traffic to be tunneled. Note: This is for the destination prefixes of the flows generated by ATE:Port1. + * Ensure you have static routes in place for the inner header destination to point at the exit interface (Physical/Bundle) + * Run traffic flows of the following size over IPv4 and IPv6. For each scenario, the MTU configured on the physical/bundle interfaces plus the tunnel interface must be the same. + * 1500 Bytes + * 2000 Bytes + * 4000 Bytes + * 9202 Bytes + * 9202 Bytes + * Assert ATE reports packets sent and received count are the same, indicating no fragmentation, and + successful transit. + * Run the above for GUE tunnel interface ## OpenConfig Path and RPC Coverage @@ -25,13 +78,52 @@ The below yaml defines the OC paths intended to be covered by this test. OC pat ```yaml paths: - ## Config Paths ## + # Config Paths /interfaces/interface/config/mtu: /interfaces/interface/subinterfaces/subinterface/ipv4/config/mtu: /interfaces/interface/subinterfaces/subinterface/ipv6/config/mtu: - - ## State Paths ## - # No coverage, validates success by checking flow statistics between ATE ports. + # TODO: OpenConfig definition required for Tunnel protocol under interfaces/interfaces/interface/tunnel/ as GRE, IP-IP, GUE etc. + /interfaces/interface/tunnel/config/dst: + /interfaces/interface/tunnel/config/src: + /interfaces/interface/tunnel/ipv4/addresses/address/config/ip: + /interfaces/interface/tunnel/ipv4/addresses/address/config/prefix-length: + /interfaces/interface/tunnel/ipv6/addresses/address/config/ip: + /interfaces/interface/tunnel/ipv6/addresses/address/config/prefix-length: + # State Paths + /interfaces/interface/state/counters/in-pkts: + /interfaces/interface/state/counters/in-octets: + /interfaces/interface/state/counters/out-pkts: + /interfaces/interface/state/counters/out-octets: + /interfaces/interface/state/counters/in-errors: + /interfaces/interface/state/counters/in-unicast-pkts: + /interfaces/interface/state/counters/in-discards: + /interfaces/interface/state/counters/out-errors: + /interfaces/interface/state/counters/out-unicast-pkts: + /interfaces/interface/state/counters/out-discards: + /interfaces/interface/tunnel/ipv4/state/counters/in-pkts: + /interfaces/interface/tunnel/ipv4/state/counters/in-octets: + /interfaces/interface/tunnel/ipv4/state/counters/out-pkts: + /interfaces/interface/tunnel/ipv4/state/counters/out-octets: + /interfaces/interface/tunnel/ipv4/state/counters/in-error-pkts: + /interfaces/interface/tunnel/ipv4/state/counters/in-forwarded-pkts: + /interfaces/interface/tunnel/ipv4/state/counters/in-forwarded-octets: + /interfaces/interface/tunnel/ipv4/state/counters/in-discarded-pkts: + /interfaces/interface/tunnel/ipv4/state/counters/out-error-pkts: + /interfaces/interface/tunnel/ipv4/state/counters/out-forwarded-pkts: + /interfaces/interface/tunnel/ipv4/state/counters/out-forwarded-octets: + /interfaces/interface/tunnel/ipv4/state/counters/out-discarded-pkts: + /interfaces/interface/tunnel/ipv6/state/counters/in-pkts: + /interfaces/interface/tunnel/ipv6/state/counters/in-octets: + /interfaces/interface/tunnel/ipv6/state/counters/out-pkts: + /interfaces/interface/tunnel/ipv6/state/counters/out-octets: + /interfaces/interface/tunnel/ipv6/state/counters/in-error-pkts: + /interfaces/interface/tunnel/ipv6/state/counters/in-forwarded-pkts: + /interfaces/interface/tunnel/ipv6/state/counters/in-forwarded-octets: + /interfaces/interface/tunnel/ipv6/state/counters/in-discarded-pkts: + /interfaces/interface/tunnel/ipv6/state/counters/out-error-pkts: + /interfaces/interface/tunnel/ipv6/state/counters/out-forwarded-pkts: + /interfaces/interface/tunnel/ipv6/state/counters/out-forwarded-octets: + /interfaces/interface/tunnel/ipv6/state/counters/out-discarded-pkts: rpcs: gnmi: diff --git a/feature/networkinstance/otg_tests/defaults_test/README.md b/feature/networkinstance/otg_tests/defaults_test/README.md index 9e7da08764d..a5ac736175e 100644 --- a/feature/networkinstance/otg_tests/defaults_test/README.md +++ b/feature/networkinstance/otg_tests/defaults_test/README.md @@ -2,12 +2,21 @@ TODO(robshakir): fill in test plan from code already written. +## Description + +This test verifies that the IPv4 and IPv6 address families are enabled within a network instance by default. + +## Test Procedure + +* Configure an ATE with port1 connected to DUT port1, and port2 connected to DUT port2. +* Configure the DUT to have: + * these interfaces within the `DEFAULT` network instance and validate that traffic can be forwarded between ATE port1 and ATE port2. + * these interfaces within a non-default `L3VRF` and validate that traffic can be forwarded between ATE port1 and ATE port2. + ## OpenConfig Path and RPC Coverage The below yaml defines the OC paths intended to be covered by this test. OC paths used for test setup are not listed here. -TODO(robshakir): fill in coverage from code already written. - ```yaml paths: rpcs: diff --git a/feature/experimental/p4rt/README.md b/feature/p4rt/README.md similarity index 94% rename from feature/experimental/p4rt/README.md rename to feature/p4rt/README.md index a2dc5701736..3acc900e9fc 100644 --- a/feature/experimental/p4rt/README.md +++ b/feature/p4rt/README.md @@ -52,9 +52,9 @@ This document specifies the requirements for p4rt test implementation. `p4rtutils.P4RTNodesByPort()`. ## OpenConfig Path and RPC Coverage - -The below yaml defines the OC paths intended to be covered by this test. OC paths used for test setup are not listed here. - ```yaml - +rpcs: + gnmi: + gNMI.Set: + gNMI.Subscribe: ``` diff --git a/feature/experimental/p4rt/otg_tests/base_p4rt/README.md b/feature/p4rt/otg_tests/base_p4rt/README.md similarity index 73% rename from feature/experimental/p4rt/otg_tests/base_p4rt/README.md rename to feature/p4rt/otg_tests/base_p4rt/README.md index e4ca8068fb1..e690e261459 100644 --- a/feature/experimental/p4rt/otg_tests/base_p4rt/README.md +++ b/feature/p4rt/otg_tests/base_p4rt/README.md @@ -24,19 +24,16 @@ Validate that the P4RT server can accept basic configuration and Read/Write RPCs * Repeat the same steps for another FAP and verify the Table entries. - -## Config Parameter Coverage - -* /components/component/integrated-circuit/config/node-id -* /interfaces/interface/config/id - - -## Telemetry Parameter coverage - -No new telemetry covered. - - -## Protocol/RPC Parameter coverage - -No new Protocol/RPC covered. +## OpenConfig Path and RPC Coverage +```yaml +paths: + /components/component/integrated-circuit/config/node-id: + platform_type: ["INTEGRATED_CIRCUIT"] + /interfaces/interface/config/id: +rpcs: + gnmi: + gNMI.Get: + gNMI.Set: + gNMI.Subscribe: +``` diff --git a/feature/experimental/p4rt/otg_tests/base_p4rt/base_p4rt_test.go b/feature/p4rt/otg_tests/base_p4rt/base_p4rt_test.go similarity index 100% rename from feature/experimental/p4rt/otg_tests/base_p4rt/base_p4rt_test.go rename to feature/p4rt/otg_tests/base_p4rt/base_p4rt_test.go diff --git a/feature/experimental/p4rt/otg_tests/base_p4rt/metadata.textproto b/feature/p4rt/otg_tests/base_p4rt/metadata.textproto similarity index 100% rename from feature/experimental/p4rt/otg_tests/base_p4rt/metadata.textproto rename to feature/p4rt/otg_tests/base_p4rt/metadata.textproto diff --git a/feature/experimental/p4rt/otg_tests/google_discovery_protocol_packetin_test/README.md b/feature/p4rt/otg_tests/google_discovery_protocol_packetin_test/README.md similarity index 86% rename from feature/experimental/p4rt/otg_tests/google_discovery_protocol_packetin_test/README.md rename to feature/p4rt/otg_tests/google_discovery_protocol_packetin_test/README.md index a5bffb0cdd9..8c5f6f83043 100644 --- a/feature/experimental/p4rt/otg_tests/google_discovery_protocol_packetin_test/README.md +++ b/feature/p4rt/otg_tests/google_discovery_protocol_packetin_test/README.md @@ -14,13 +14,14 @@ Verify that GDP packets are punted with correct metadata. * Verify that the packet has the ingress_singleton_port metadata set and it corresponds to the interface ID of the port that the packet was received on. -## Config Parameter coverage - -No new configuration covered. - -## Telemetry Parameter coverage - -No new telemetry covered. +## OpenConfig Path and RPC Coverage +```yaml +rpcs: + gnmi: + gNMI.Get: + gNMI.Set: + gNMI.Subscribe: +``` ## Minimum DUT platform requirement diff --git a/feature/experimental/p4rt/otg_tests/google_discovery_protocol_packetin_test/google_discovery_protocol_packetin_test.go b/feature/p4rt/otg_tests/google_discovery_protocol_packetin_test/google_discovery_protocol_packetin_test.go similarity index 100% rename from feature/experimental/p4rt/otg_tests/google_discovery_protocol_packetin_test/google_discovery_protocol_packetin_test.go rename to feature/p4rt/otg_tests/google_discovery_protocol_packetin_test/google_discovery_protocol_packetin_test.go diff --git a/feature/experimental/p4rt/otg_tests/google_discovery_protocol_packetin_test/metadata.textproto b/feature/p4rt/otg_tests/google_discovery_protocol_packetin_test/metadata.textproto similarity index 100% rename from feature/experimental/p4rt/otg_tests/google_discovery_protocol_packetin_test/metadata.textproto rename to feature/p4rt/otg_tests/google_discovery_protocol_packetin_test/metadata.textproto diff --git a/feature/experimental/p4rt/otg_tests/google_discovery_protocol_packetout_lag_test/README.md b/feature/p4rt/otg_tests/google_discovery_protocol_packetout_lag_test/README.md similarity index 100% rename from feature/experimental/p4rt/otg_tests/google_discovery_protocol_packetout_lag_test/README.md rename to feature/p4rt/otg_tests/google_discovery_protocol_packetout_lag_test/README.md diff --git a/feature/experimental/p4rt/otg_tests/google_discovery_protocol_packetout_lag_test/google_discovery_protocol_packetout_lag_test.go b/feature/p4rt/otg_tests/google_discovery_protocol_packetout_lag_test/google_discovery_protocol_packetout_lag_test.go similarity index 100% rename from feature/experimental/p4rt/otg_tests/google_discovery_protocol_packetout_lag_test/google_discovery_protocol_packetout_lag_test.go rename to feature/p4rt/otg_tests/google_discovery_protocol_packetout_lag_test/google_discovery_protocol_packetout_lag_test.go diff --git a/feature/experimental/p4rt/otg_tests/google_discovery_protocol_packetout_lag_test/metadata.textproto b/feature/p4rt/otg_tests/google_discovery_protocol_packetout_lag_test/metadata.textproto similarity index 100% rename from feature/experimental/p4rt/otg_tests/google_discovery_protocol_packetout_lag_test/metadata.textproto rename to feature/p4rt/otg_tests/google_discovery_protocol_packetout_lag_test/metadata.textproto diff --git a/feature/experimental/p4rt/otg_tests/google_discovery_protocol_packetout_test/README.md b/feature/p4rt/otg_tests/google_discovery_protocol_packetout_test/README.md similarity index 87% rename from feature/experimental/p4rt/otg_tests/google_discovery_protocol_packetout_test/README.md rename to feature/p4rt/otg_tests/google_discovery_protocol_packetout_test/README.md index 8d6fd5b5870..d1ba03f1f5b 100644 --- a/feature/experimental/p4rt/otg_tests/google_discovery_protocol_packetout_test/README.md +++ b/feature/p4rt/otg_tests/google_discovery_protocol_packetout_test/README.md @@ -15,15 +15,14 @@ Verify that GDP packets can be sent by the controller. * Repeat sending the packet in the same way but from the secondary connection. * Verify that the packet is not received on the ATE. - - -## Config Parameter coverage - -No new configuration covered. - -## Telemetry Parameter coverage - -No new telemetry covered. +## OpenConfig Path and RPC Coverage +```yaml +rpcs: + gnmi: + gNMI.Get: + gNMI.Set: + gNMI.Subscribe: +``` ## Minimum DUT platform requirement diff --git a/feature/experimental/p4rt/otg_tests/google_discovery_protocol_packetout_test/google_discovery_protocol_packetout_test.go b/feature/p4rt/otg_tests/google_discovery_protocol_packetout_test/google_discovery_protocol_packetout_test.go similarity index 100% rename from feature/experimental/p4rt/otg_tests/google_discovery_protocol_packetout_test/google_discovery_protocol_packetout_test.go rename to feature/p4rt/otg_tests/google_discovery_protocol_packetout_test/google_discovery_protocol_packetout_test.go diff --git a/feature/experimental/p4rt/otg_tests/google_discovery_protocol_packetout_test/metadata.textproto b/feature/p4rt/otg_tests/google_discovery_protocol_packetout_test/metadata.textproto similarity index 100% rename from feature/experimental/p4rt/otg_tests/google_discovery_protocol_packetout_test/metadata.textproto rename to feature/p4rt/otg_tests/google_discovery_protocol_packetout_test/metadata.textproto diff --git a/feature/experimental/p4rt/otg_tests/lldp_packetin_test/README.md b/feature/p4rt/otg_tests/lldp_packetin_test/README.md similarity index 85% rename from feature/experimental/p4rt/otg_tests/lldp_packetin_test/README.md rename to feature/p4rt/otg_tests/lldp_packetin_test/README.md index 4af42c8c091..e3398a89860 100644 --- a/feature/experimental/p4rt/otg_tests/lldp_packetin_test/README.md +++ b/feature/p4rt/otg_tests/lldp_packetin_test/README.md @@ -13,15 +13,14 @@ Verify that LLDP packets are punted with correct metadata. * Send an LLDP packet from the ATE and verify that it is received by the client. * Verify that the packet has the ingress_singleton_port metadata set and it corresponds to the interface ID of the port that the packet was received on. - - -## Config Parameter coverage - -No new configuration covered. - -## Telemetry Parameter coverage - -No new telemetry covered. +## OpenConfig Path and RPC Coverage +```yaml +rpcs: + gnmi: + gNMI.Get: + gNMI.Set: + gNMI.Subscribe: +``` ## Minimum DUT platform requirement diff --git a/feature/experimental/p4rt/otg_tests/lldp_packetin_test/lldp_packetin_test.go b/feature/p4rt/otg_tests/lldp_packetin_test/lldp_packetin_test.go similarity index 100% rename from feature/experimental/p4rt/otg_tests/lldp_packetin_test/lldp_packetin_test.go rename to feature/p4rt/otg_tests/lldp_packetin_test/lldp_packetin_test.go diff --git a/feature/experimental/p4rt/otg_tests/lldp_packetin_test/metadata.textproto b/feature/p4rt/otg_tests/lldp_packetin_test/metadata.textproto similarity index 100% rename from feature/experimental/p4rt/otg_tests/lldp_packetin_test/metadata.textproto rename to feature/p4rt/otg_tests/lldp_packetin_test/metadata.textproto diff --git a/feature/experimental/p4rt/otg_tests/lldp_packetout_test/README.md b/feature/p4rt/otg_tests/lldp_packetout_test/README.md similarity index 80% rename from feature/experimental/p4rt/otg_tests/lldp_packetout_test/README.md rename to feature/p4rt/otg_tests/lldp_packetout_test/README.md index ec9b4d9d73a..97616953d12 100644 --- a/feature/experimental/p4rt/otg_tests/lldp_packetout_test/README.md +++ b/feature/p4rt/otg_tests/lldp_packetout_test/README.md @@ -13,17 +13,13 @@ Verify that LLDP packets can be sent by the controller. * Send an LLDP packet from the client with egress_singleton_port set to one of the connected interfaces. * Verify that the LLDP packet is received on the ATE port connected to the indicated interface. - - - -## Config Parameter coverage - -No new configuration covered. - -## Telemetry Parameter coverage - -No new telemetry covered. - -## Minimum DUT platform requirement +## OpenConfig Path and RPC Coverage +```yaml +rpcs: + gnmi: + gNMI.Get: + gNMI.Set: + gNMI.Subscribe: +``` vRX if the vendor implementation supports FIB-ACK simulation, otherwise FFF. \ No newline at end of file diff --git a/feature/experimental/p4rt/otg_tests/lldp_packetout_test/lldp_packetout_test.go b/feature/p4rt/otg_tests/lldp_packetout_test/lldp_packetout_test.go similarity index 100% rename from feature/experimental/p4rt/otg_tests/lldp_packetout_test/lldp_packetout_test.go rename to feature/p4rt/otg_tests/lldp_packetout_test/lldp_packetout_test.go diff --git a/feature/experimental/p4rt/otg_tests/lldp_packetout_test/metadata.textproto b/feature/p4rt/otg_tests/lldp_packetout_test/metadata.textproto similarity index 100% rename from feature/experimental/p4rt/otg_tests/lldp_packetout_test/metadata.textproto rename to feature/p4rt/otg_tests/lldp_packetout_test/metadata.textproto diff --git a/feature/experimental/p4rt/otg_tests/performance_test/README.md b/feature/p4rt/otg_tests/performance_test/README.md similarity index 73% rename from feature/experimental/p4rt/otg_tests/performance_test/README.md rename to feature/p4rt/otg_tests/performance_test/README.md index 470f6c467be..fb7d6b31e32 100644 --- a/feature/experimental/p4rt/otg_tests/performance_test/README.md +++ b/feature/p4rt/otg_tests/performance_test/README.md @@ -15,21 +15,18 @@ Verify that both Packetin and Packetout traffic is handled by the P4RT server at * Setup packetout packets for GDP, LLDP and traceroute from the P4RT client. * Start both packetin and packetout traffic at the same rate simultaneously. * Verify no packetloss for both directions of traffic. -* Verify the metadata ID and the value for all three traffic types on the P4RT client for packetin. - - -## Config Parameter coverage - -* /components/component/integrated-circuit/config/node-id -* /interfaces/interface/config/id - - -## Telemetry Parameter coverage - -No new telemetry covered. - - -## Protocol/RPC Parameter coverage - -No new Protocol/RPC covered. +* Verify the metadata ID and the value for all three traffic types on the P4RT client for packetin. + +## OpenConfig Path and RPC Coverage +```yaml +paths: + /components/component/integrated-circuit/config/node-id: + platform_type: ["INTEGRATED_CIRCUIT"] + /interfaces/interface/config/id: +rpcs: + gnmi: + gNMI.Get: + gNMI.Set: + gNMI.Subscribe: +``` diff --git a/feature/experimental/p4rt/otg_tests/performance_test/metadata.textproto b/feature/p4rt/otg_tests/performance_test/metadata.textproto similarity index 100% rename from feature/experimental/p4rt/otg_tests/performance_test/metadata.textproto rename to feature/p4rt/otg_tests/performance_test/metadata.textproto diff --git a/feature/experimental/p4rt/otg_tests/performance_test/performance_test.go b/feature/p4rt/otg_tests/performance_test/performance_test.go similarity index 100% rename from feature/experimental/p4rt/otg_tests/performance_test/performance_test.go rename to feature/p4rt/otg_tests/performance_test/performance_test.go diff --git a/feature/experimental/p4rt/otg_tests/traceroute_packetin_test/README.md b/feature/p4rt/otg_tests/traceroute_packetin_test/README.md similarity index 73% rename from feature/experimental/p4rt/otg_tests/traceroute_packetin_test/README.md rename to feature/p4rt/otg_tests/traceroute_packetin_test/README.md index 8a69af7d868..0aee47016e4 100644 --- a/feature/experimental/p4rt/otg_tests/traceroute_packetin_test/README.md +++ b/feature/p4rt/otg_tests/traceroute_packetin_test/README.md @@ -16,19 +16,15 @@ Verify that Traceroute packets are punted with correct metadata. * Send IPv6 packets from the ATE with HopLimit=1 and verify that packets with HopLimit=1 are received by the client. * Verify that the packets have both ingress_singleton_port and egress_singleton_port metadata set. - -## Config Parameter coverage - -* /components/component/integrated-circuit/config/node-id -* /interfaces/interface/config/id - - -## Telemetry Parameter coverage - -No new telemetry covered. - - -## Protocol/RPC Parameter coverage - -No new Protocol/RPC covered. - +## OpenConfig Path and RPC Coverage +```yaml +paths: + /components/component/integrated-circuit/config/node-id: + platform_type: ["INTEGRATED_CIRCUIT"] + /interfaces/interface/config/id: +rpcs: + gnmi: + gNMI.Get: + gNMI.Set: + gNMI.Subscribe: +``` diff --git a/feature/experimental/p4rt/otg_tests/traceroute_packetin_test/metadata.textproto b/feature/p4rt/otg_tests/traceroute_packetin_test/metadata.textproto similarity index 100% rename from feature/experimental/p4rt/otg_tests/traceroute_packetin_test/metadata.textproto rename to feature/p4rt/otg_tests/traceroute_packetin_test/metadata.textproto diff --git a/feature/experimental/p4rt/otg_tests/traceroute_packetin_test/packetin_test.go b/feature/p4rt/otg_tests/traceroute_packetin_test/packetin_test.go similarity index 100% rename from feature/experimental/p4rt/otg_tests/traceroute_packetin_test/packetin_test.go rename to feature/p4rt/otg_tests/traceroute_packetin_test/packetin_test.go diff --git a/feature/experimental/p4rt/otg_tests/traceroute_packetin_test/traceroute_packetin_test.go b/feature/p4rt/otg_tests/traceroute_packetin_test/traceroute_packetin_test.go similarity index 100% rename from feature/experimental/p4rt/otg_tests/traceroute_packetin_test/traceroute_packetin_test.go rename to feature/p4rt/otg_tests/traceroute_packetin_test/traceroute_packetin_test.go diff --git a/feature/experimental/p4rt/otg_tests/traceroute_packetin_with_vrf_selection_test/README.md b/feature/p4rt/otg_tests/traceroute_packetin_with_vrf_selection_test/README.md similarity index 98% rename from feature/experimental/p4rt/otg_tests/traceroute_packetin_with_vrf_selection_test/README.md rename to feature/p4rt/otg_tests/traceroute_packetin_with_vrf_selection_test/README.md index d15347dad27..ec980072fd7 100644 --- a/feature/experimental/p4rt/otg_tests/traceroute_packetin_with_vrf_selection_test/README.md +++ b/feature/p4rt/otg_tests/traceroute_packetin_with_vrf_selection_test/README.md @@ -17,7 +17,7 @@ DUT port-8 <------> port-8 ATE ## Baseline setup -* Setup equivalent to [TE-17.1 vrf_policy_driven_te](https://github.com/openconfig/featureprofiles/blob/main/feature/experimental/gribi/otg_tests/vrf_policy_driven_te/README.md), including GRibi programming. +* Setup equivalent to [TE-17.1 vrf_policy_driven_te](https://github.com/openconfig/featureprofiles/blob/main/feature/gribi/otg_tests/vrf_policy_driven_te/README.md), including GRibi programming. * Install a BGP route resolved by ISIS in default VRF to route traffic out of DUT port-8 for 203.0.113.0. diff --git a/feature/experimental/p4rt/otg_tests/traceroute_packetin_with_vrf_selection_test/metadata.textproto b/feature/p4rt/otg_tests/traceroute_packetin_with_vrf_selection_test/metadata.textproto similarity index 100% rename from feature/experimental/p4rt/otg_tests/traceroute_packetin_with_vrf_selection_test/metadata.textproto rename to feature/p4rt/otg_tests/traceroute_packetin_with_vrf_selection_test/metadata.textproto diff --git a/feature/experimental/p4rt/otg_tests/traceroute_packetin_with_vrf_selection_test/packetin_test.go b/feature/p4rt/otg_tests/traceroute_packetin_with_vrf_selection_test/packetin_test.go similarity index 100% rename from feature/experimental/p4rt/otg_tests/traceroute_packetin_with_vrf_selection_test/packetin_test.go rename to feature/p4rt/otg_tests/traceroute_packetin_with_vrf_selection_test/packetin_test.go diff --git a/feature/experimental/p4rt/otg_tests/traceroute_packetin_with_vrf_selection_test/traceroute_packetin_test.go b/feature/p4rt/otg_tests/traceroute_packetin_with_vrf_selection_test/traceroute_packetin_test.go similarity index 100% rename from feature/experimental/p4rt/otg_tests/traceroute_packetin_with_vrf_selection_test/traceroute_packetin_test.go rename to feature/p4rt/otg_tests/traceroute_packetin_with_vrf_selection_test/traceroute_packetin_test.go diff --git a/feature/experimental/p4rt/otg_tests/traceroute_packetin_with_vrf_selection_test/traceroute_packetin_with_vrf_selection_test.go b/feature/p4rt/otg_tests/traceroute_packetin_with_vrf_selection_test/traceroute_packetin_with_vrf_selection_test.go similarity index 100% rename from feature/experimental/p4rt/otg_tests/traceroute_packetin_with_vrf_selection_test/traceroute_packetin_with_vrf_selection_test.go rename to feature/p4rt/otg_tests/traceroute_packetin_with_vrf_selection_test/traceroute_packetin_with_vrf_selection_test.go diff --git a/feature/experimental/p4rt/otg_tests/traceroute_packetout_test/README.md b/feature/p4rt/otg_tests/traceroute_packetout_test/README.md similarity index 100% rename from feature/experimental/p4rt/otg_tests/traceroute_packetout_test/README.md rename to feature/p4rt/otg_tests/traceroute_packetout_test/README.md diff --git a/feature/experimental/p4rt/otg_tests/traceroute_packetout_test/metadata.textproto b/feature/p4rt/otg_tests/traceroute_packetout_test/metadata.textproto similarity index 100% rename from feature/experimental/p4rt/otg_tests/traceroute_packetout_test/metadata.textproto rename to feature/p4rt/otg_tests/traceroute_packetout_test/metadata.textproto diff --git a/feature/experimental/p4rt/otg_tests/traceroute_packetout_test/packetout_test.go b/feature/p4rt/otg_tests/traceroute_packetout_test/packetout_test.go similarity index 100% rename from feature/experimental/p4rt/otg_tests/traceroute_packetout_test/packetout_test.go rename to feature/p4rt/otg_tests/traceroute_packetout_test/packetout_test.go diff --git a/feature/experimental/p4rt/otg_tests/traceroute_packetout_test/traceroute_packetout_test.go b/feature/p4rt/otg_tests/traceroute_packetout_test/traceroute_packetout_test.go similarity index 100% rename from feature/experimental/p4rt/otg_tests/traceroute_packetout_test/traceroute_packetout_test.go rename to feature/p4rt/otg_tests/traceroute_packetout_test/traceroute_packetout_test.go diff --git a/feature/experimental/p4rt/tests/metadata_validation_test/README.md b/feature/p4rt/tests/metadata_validation_test/README.md similarity index 81% rename from feature/experimental/p4rt/tests/metadata_validation_test/README.md rename to feature/p4rt/tests/metadata_validation_test/README.md index 8ad072ab172..8a311ea7d05 100644 --- a/feature/experimental/p4rt/tests/metadata_validation_test/README.md +++ b/feature/p4rt/tests/metadata_validation_test/README.md @@ -23,3 +23,16 @@ Validate the P4RT server handles Metadata set in Table Entry correctly. ## Notes * [P4RT Proto](https://github.com/p4lang/p4runtime/blob/main/proto/p4/v1/p4runtime.proto) + +## OpenConfig Path and RPC Coverage +```yaml +paths: + /components/component/integrated-circuit/config/node-id: + platform_type: ["INTEGRATED_CIRCUIT"] + /interfaces/interface/config/id: +rpcs: + gnmi: + gNMI.Get: + gNMI.Set: + gNMI.Subscribe: +``` diff --git a/feature/experimental/p4rt/tests/metadata_validation_test/metadata.textproto b/feature/p4rt/tests/metadata_validation_test/metadata.textproto similarity index 100% rename from feature/experimental/p4rt/tests/metadata_validation_test/metadata.textproto rename to feature/p4rt/tests/metadata_validation_test/metadata.textproto diff --git a/feature/experimental/p4rt/tests/metadata_validation_test/metadata_validation_test.go b/feature/p4rt/tests/metadata_validation_test/metadata_validation_test.go similarity index 100% rename from feature/experimental/p4rt/tests/metadata_validation_test/metadata_validation_test.go rename to feature/p4rt/tests/metadata_validation_test/metadata_validation_test.go diff --git a/feature/experimental/p4rt/tests/p4rt_election/README.md b/feature/p4rt/tests/p4rt_election/README.md similarity index 96% rename from feature/experimental/p4rt/tests/p4rt_election/README.md rename to feature/p4rt/tests/p4rt_election/README.md index 5b77cea3ccf..9226182e9e4 100644 --- a/feature/experimental/p4rt/tests/p4rt_election/README.md +++ b/feature/p4rt/tests/p4rt_election/README.md @@ -106,3 +106,16 @@ Validate the P4RT server handles primary election and failover. writes for clients with `election_id=9` & `election_id=10`. * TODO: Enable P4RT on an additional FAP and verify that the same set of scenarios work independently of the first FAP + +## OpenConfig Path and RPC Coverage +```yaml +paths: + /components/component/integrated-circuit/config/node-id: + platform_type: ["INTEGRATED_CIRCUIT"] + /interfaces/interface/config/id: +rpcs: + gnmi: + gNMI.Get: + gNMI.Set: + gNMI.Subscribe: +``` diff --git a/feature/experimental/p4rt/tests/p4rt_election/metadata.textproto b/feature/p4rt/tests/p4rt_election/metadata.textproto similarity index 100% rename from feature/experimental/p4rt/tests/p4rt_election/metadata.textproto rename to feature/p4rt/tests/p4rt_election/metadata.textproto diff --git a/feature/experimental/p4rt/tests/p4rt_election/p4rt_election_test.go b/feature/p4rt/tests/p4rt_election/p4rt_election_test.go similarity index 100% rename from feature/experimental/p4rt/tests/p4rt_election/p4rt_election_test.go rename to feature/p4rt/tests/p4rt_election/p4rt_election_test.go diff --git a/feature/experimental/p4rt/wbb.p4info.pb.txt b/feature/p4rt/wbb.p4info.pb.txt similarity index 100% rename from feature/experimental/p4rt/wbb.p4info.pb.txt rename to feature/p4rt/wbb.p4info.pb.txt diff --git a/feature/platform/tests/breakout_configuration/README.md b/feature/platform/tests/breakout_configuration/README.md new file mode 100644 index 00000000000..1cccdf903c4 --- /dev/null +++ b/feature/platform/tests/breakout_configuration/README.md @@ -0,0 +1,41 @@ +# PLT-1.1: Interface breakout Test + +## Summary + +Validate Interface breakout configuration. + +## Procedure + + +* This test is carried out for different breakout types +* Connect DUT with ATE to all interfaces in the breakout port +* Configure each interface with test IP addressing +* Verify correct interface state and speed reported +* Verify that DUT responds to ARP/ICMP on all tested interfaces + +## OpenConfig Path and RPC Coverage + +The below yaml defines the OC paths intended to be covered by this test. OC +paths used for test setup are not listed here. + +```yaml +paths: + /components/component/port/breakout-mode/groups/group/index: + platform_type: [ "PORT" ] + /components/component/port/breakout-mode/groups/group/config/index: + platform_type: [ "PORT" ] + /components/component/port/breakout-mode/groups/group/config/num-breakouts: + platform_type: [ "PORT" ] + /components/component/port/breakout-mode/groups/group/config/breakout-speed: + platform_type: [ "PORT" ] + /components/component/port/breakout-mode/groups/group/config/num-physical-channels: + platform_type: [ "PORT" ] +rpcs: + gnmi: + gNMI.Subscribe: + gNMI.Set: +``` + +## Minimum DUT Platform Requirement + +* Breakout types - 4x100G, 2x100G and 4x10G diff --git a/feature/experimental/platform/tests/optics_thresholds_test/README.md b/feature/platform/tests/optics_thresholds_test/README.md similarity index 52% rename from feature/experimental/platform/tests/optics_thresholds_test/README.md rename to feature/platform/tests/optics_thresholds_test/README.md index 39f318faab4..9126d3eb914 100644 --- a/feature/experimental/platform/tests/optics_thresholds_test/README.md +++ b/feature/platform/tests/optics_thresholds_test/README.md @@ -8,7 +8,7 @@ Validate optics high and low thresholds for input power, output power, temperatu * Connect at least one optical ethernet interface to ATE. * Check all the transceivers with inslalled optcs. -* Validate that the following optics threshold telemetry paths exist for each optics. +* Validate that the optics threshold telemetry paths exist for each optics. * Output power thresholds: * /components/component/Ethernet/properties/property/laser-tx-power-low-alarm-threshold/state/value * /components/component/Ethernet/properties/property/laser-tx-power-high-alarm-threshold/state/value @@ -30,32 +30,17 @@ Validate optics high and low thresholds for input power, output power, temperatu * /components/component/Ethernet/properties/property/laser-bias-current-low-warn-threshold/state/value * /components/component/Ethernet/properties/property/laser-bias-current-high-warn-threshold/state/value - -## Config Parameter coverage +## OpenConfig Path and RPC Coverage -* None +The below yaml defines the OC paths intended to be covered by this test. OC +paths used for test setup are not listed here. + +```yaml +rpcs: + gnmi: + gNMI.Subscribe: + gNMI.Set: +``` -## Telemetry Parameter coverage - * Output power thresholds: - * /components/component/Ethernet/properties/property/laser-tx-power-low-alarm-threshold/state/value - * /components/component/Ethernet/properties/property/laser-tx-power-high-alarm-threshold/state/value - * /components/component/Ethernet/properties/property/laser-tx-power-low-warn-threshold/state/value - * /components/component/Ethernet/properties/property/laser-tx-power-high-warn-threshold/state/value - * Input power threshold: - * /components/component/Ethernet/properties/property/laser-rx-power-low-alarm-threshold/state/value - * /components/component/Ethernet/properties/property/laser-rx-power-high-alarm-threshold/state/value - * /components/component/Ethernet/properties/property/laser-rx-power-low-warn-threshold/state/value - * /components/component/Ethernet/properties/property/laser-rx-power-high-warn-threshold/state/value - * Optics temperature threshold: - * /components/component/Ethernet/properties/property/laser-temperature-low-alarm-threshold/state/value - * /components/component/Ethernet/properties/property/laser-temperature-high-alarm-threshold/state/value - * /components/component/Ethernet/properties/property/laser-temperature-low-warn-threshold/state/value - * /components/component/Ethernet/properties/property/laser-temperature-high-warn-threshold/state/value - * Optics bias-current threshold: - * /components/component/Ethernet/properties/property/laser-bias-current-low-alarm-threshold/state/value - * /components/component/Ethernet/properties/property/laser-bias-current-high-alarm-threshold/state/value - * /components/component/Ethernet/properties/property/laser-bias-current-low-warn-threshold/state/value - * /components/component/Ethernet/properties/property/laser-bias-current-high-warn-threshold/state/value - ## Notes: * The model for optics threshold paths is not finalized. We may need to update those paths after the model is finalized. diff --git a/feature/experimental/platform/tests/optics_thresholds_test/metadata.textproto b/feature/platform/tests/optics_thresholds_test/metadata.textproto similarity index 100% rename from feature/experimental/platform/tests/optics_thresholds_test/metadata.textproto rename to feature/platform/tests/optics_thresholds_test/metadata.textproto diff --git a/feature/experimental/platform/tests/optics_thresholds_test/optics_thresholds_test.go b/feature/platform/tests/optics_thresholds_test/optics_thresholds_test.go similarity index 100% rename from feature/experimental/platform/tests/optics_thresholds_test/optics_thresholds_test.go rename to feature/platform/tests/optics_thresholds_test/optics_thresholds_test.go diff --git a/feature/platform/transceiver/tests/zr_cd_test/README.md b/feature/platform/transceiver/tests/zr_cd_test/README.md index 2c56e6d87d7..7895a20d051 100644 --- a/feature/platform/transceiver/tests/zr_cd_test/README.md +++ b/feature/platform/transceiver/tests/zr_cd_test/README.md @@ -7,6 +7,8 @@ Validate 400ZR optics module reports accurate CD telemetry values. Chromatic Dispersion is frequency dependent change in signal phase velocity due to fiber measured in ps/nm +The test must be repeated for each supported operational-mode or as agreed between the vendor and customer. + ## Procedure * Connect two ZR interfaces using a duplex LC fiber jumper such that TX diff --git a/feature/platform/transceiver/tests/zr_cd_test/zr_cd_test.go b/feature/platform/transceiver/tests/zr_cd_test/zr_cd_test.go index 95312d2398b..0d6e421d099 100644 --- a/feature/platform/transceiver/tests/zr_cd_test/zr_cd_test.go +++ b/feature/platform/transceiver/tests/zr_cd_test/zr_cd_test.go @@ -1,6 +1,7 @@ package zr_cd_test import ( + "flag" "testing" "time" @@ -13,7 +14,6 @@ import ( ) const ( - dp16QAM = 1 samplingInterval = 10 * time.Second minCDValue = -200 maxCDValue = 2400 @@ -30,8 +30,10 @@ const ( ) var ( - frequencies = []uint64{191400000, 196100000} // 400ZR OIF wavelength range - targetOutputPowers = []float64{-13, -9} // 400ZR OIF Tx power range + frequencies = []uint64{191400000, 196100000} // 400ZR OIF wavelength range + targetOutputPowers = []float64{-13, -9} // 400ZR OIF Tx power range + operationalModeFlag = flag.Int("operational_mode", 1, "vendor-specific operational-mode for the channel") + operationalMode uint16 ) func TestMain(m *testing.M) { @@ -93,6 +95,11 @@ func verifyAllCDValues(t *testing.T, dut1 *ondatra.DUTDevice, p1StreamInstant, p func TestCDValue(t *testing.T) { dut := ondatra.DUT(t, "dut") + if operationalModeFlag != nil { + operationalMode = uint16(*operationalModeFlag) + } else { + t.Fatalf("Please specify the vendor-specific operational-mode flag") + } fptest.ConfigureDefaultNetworkInstance(t, dut) dp1 := dut.Port(t, "port1") @@ -105,11 +112,10 @@ func TestCDValue(t *testing.T) { och1 := gnmi.Get(t, dut, gnmi.OC().Component(tr1).Transceiver().Channel(0).AssociatedOpticalChannel().State()) och2 := gnmi.Get(t, dut, gnmi.OC().Component(tr2).Transceiver().Channel(0).AssociatedOpticalChannel().State()) component1 := gnmi.OC().Component(och1) - for _, frequency := range frequencies { for _, targetOutputPower := range targetOutputPowers { - cfgplugins.ConfigOpticalChannel(t, dut, och1, frequency, targetOutputPower, dp16QAM) - cfgplugins.ConfigOpticalChannel(t, dut, och2, frequency, targetOutputPower, dp16QAM) + cfgplugins.ConfigOpticalChannel(t, dut, och1, frequency, targetOutputPower, operationalMode) + cfgplugins.ConfigOpticalChannel(t, dut, och2, frequency, targetOutputPower, operationalMode) // Wait for channels to be up. gnmi.Await(t, dut, gnmi.OC().Interface(dp1.Name()).OperStatus().State(), timeout, oc.Interface_OperStatus_UP) diff --git a/feature/platform/transceiver/tests/zr_fec_uncorrectable_frames_test/metadata.textproto b/feature/platform/transceiver/tests/zr_fec_uncorrectable_frames_test/metadata.textproto index 501d2cce28f..f2bd6231241 100644 --- a/feature/platform/transceiver/tests/zr_fec_uncorrectable_frames_test/metadata.textproto +++ b/feature/platform/transceiver/tests/zr_fec_uncorrectable_frames_test/metadata.textproto @@ -15,3 +15,13 @@ platform_exceptions: { missing_port_to_optical_channel_component_mapping: true } } +platform_exceptions: { + platform: { + vendor: CISCO + } + deviations: { + otn_channel_trib_unsupported: true + eth_channel_ingress_parameters_unsupported: true + eth_channel_assignment_cisco_numbering: true + } +} diff --git a/feature/platform/transceiver/tests/zr_fec_uncorrectable_frames_test/zr_fec_uncorrectable_frames_test.go b/feature/platform/transceiver/tests/zr_fec_uncorrectable_frames_test/zr_fec_uncorrectable_frames_test.go index 9cb628c6189..8dd5f140adf 100644 --- a/feature/platform/transceiver/tests/zr_fec_uncorrectable_frames_test/zr_fec_uncorrectable_frames_test.go +++ b/feature/platform/transceiver/tests/zr_fec_uncorrectable_frames_test/zr_fec_uncorrectable_frames_test.go @@ -83,9 +83,7 @@ func TestZrUncorrectableFrames(t *testing.T) { for _, port := range ports { t.Run(fmt.Sprintf("Port:%s", port), func(t *testing.T) { dp := dut.Port(t, port) - gnmi.Await(t, dut, gnmi.OC().Interface(dp.Name()).OperStatus().State(), intUpdateTime, oc.Interface_OperStatus_UP) - streamFecOtn := samplestream.New(t, dut, gnmi.OC().TerminalDevice().Channel(otnIndexes[dp.Name()]).Otn().FecUncorrectableBlocks().State(), sampleInterval) defer streamFecOtn.Close() validateFecUncorrectableBlocks(t, streamFecOtn) @@ -98,13 +96,13 @@ func TestZrUncorrectableFrames(t *testing.T) { // Disable interface i.Enabled = ygot.Bool(false) gnmi.Replace(t, dut, gnmi.OC().Interface(dp.Name()).Config(), i) - // Wait for the cooling off period + // Wait for the cooling-off period gnmi.Await(t, dut, gnmi.OC().Interface(dp.Name()).OperStatus().State(), intUpdateTime, oc.Interface_OperStatus_DOWN) // Enable interface i.Enabled = ygot.Bool(true) gnmi.Replace(t, dut, gnmi.OC().Interface(dp.Name()).Config(), i) - // Wait for the cooling off period + // Wait for the cooling-off period gnmi.Await(t, dut, gnmi.OC().Interface(dp.Name()).OperStatus().State(), intUpdateTime, oc.Interface_OperStatus_UP) validateFecUncorrectableBlocks(t, streamFecOtn) diff --git a/feature/platform/transceiver/tests/zr_firmware_version_test/zr_firmware_version_test.go b/feature/platform/transceiver/tests/zr_firmware_version_test/zr_firmware_version_test.go index b71efad53db..a5b9f9de78f 100644 --- a/feature/platform/transceiver/tests/zr_firmware_version_test/zr_firmware_version_test.go +++ b/feature/platform/transceiver/tests/zr_firmware_version_test/zr_firmware_version_test.go @@ -19,6 +19,7 @@ import ( "testing" "time" + "github.com/openconfig/featureprofiles/internal/cfgplugins" "github.com/openconfig/featureprofiles/internal/components" "github.com/openconfig/featureprofiles/internal/fptest" "github.com/openconfig/featureprofiles/internal/samplestream" @@ -29,7 +30,6 @@ import ( ) const ( - dp16QAM = 1 targetOutputPower = -10 frequency = 193100000 ) @@ -46,8 +46,13 @@ func configInterface(t *testing.T, dut1 *ondatra.DUTDevice, dp *ondatra.Port, en i.Enabled = ygot.Bool(enable) i.Type = oc.IETFInterfaces_InterfaceType_ethernetCsmacd gnmi.Replace(t, dut1, gnmi.OC().Interface(dp.Name()).Config(), i) - component := components.OpticalChannelComponentFromPort(t, dut1, dp) - gnmi.Replace(t, dut1, gnmi.OC().Component(component).OpticalChannel().Config(), &oc.Component_OpticalChannel{ + componentName := components.OpticalChannelComponentFromPort(t, dut1, dp) + // Set config container leaf for optical channel + component := gnmi.OC().Component(componentName) + gnmi.Replace(t, dut1, component.Config(), &oc.Component{ + Name: ygot.String(componentName), + }) + gnmi.Replace(t, dut1, component.OpticalChannel().Config(), &oc.Component_OpticalChannel{ TargetOutputPower: ygot.Float64(targetOutputPower), Frequency: ygot.Uint64(frequency), }) @@ -74,8 +79,8 @@ func TestZRFirmwareVersionState(t *testing.T) { dp2 := dut1.Port(t, "port2") t.Logf("dut1: %v", dut1) t.Logf("dut1 dp1 name: %v", dp1.Name()) - configInterface(t, dut1, dp1, true) - configInterface(t, dut1, dp2, true) + cfgplugins.InterfaceConfig(t, dut1, dp1) + cfgplugins.InterfaceConfig(t, dut1, dp2) gnmi.Await(t, dut1, gnmi.OC().Interface(dp1.Name()).OperStatus().State(), time.Minute*2, oc.Interface_OperStatus_UP) transceiverName := gnmi.Get(t, dut1, gnmi.OC().Interface(dp1.Name()).Transceiver().State()) // Check if TRANSCEIVER is of type 400ZR @@ -97,8 +102,8 @@ func TestZRFirmwareVersionStateInterfaceFlap(t *testing.T) { dp2 := dut1.Port(t, "port2") t.Logf("dut1: %v", dut1) t.Logf("dut1 dp1 name: %v", dp1.Name()) - configInterface(t, dut1, dp1, true) - configInterface(t, dut1, dp2, true) + cfgplugins.InterfaceConfig(t, dut1, dp1) + cfgplugins.InterfaceConfig(t, dut1, dp2) gnmi.Await(t, dut1, gnmi.OC().Interface(dp1.Name()).OperStatus().State(), time.Minute, oc.Interface_OperStatus_UP) transceiverName := gnmi.Get(t, dut1, gnmi.OC().Interface(dp1.Name()).Transceiver().State()) // Check if TRANSCEIVER is of type 400ZR @@ -111,7 +116,7 @@ func TestZRFirmwareVersionStateInterfaceFlap(t *testing.T) { p1Stream := samplestream.New(t, dut1, component1.FirmwareVersion().State(), 10*time.Second) - // Wait 60 sec cooling off period + // Wait 60 sec cooling-off period gnmi.Await(t, dut1, gnmi.OC().Interface(dp1.Name()).OperStatus().State(), 2*time.Minute, oc.Interface_OperStatus_DOWN) verifyFirmwareVersionValue(t, dut1, p1Stream) diff --git a/feature/platform/transceiver/tests/zr_input_output_power_test/README.md b/feature/platform/transceiver/tests/zr_input_output_power_test/README.md index f31a15d0b0b..db1563cfaca 100644 --- a/feature/platform/transceiver/tests/zr_input_output_power_test/README.md +++ b/feature/platform/transceiver/tests/zr_input_output_power_test/README.md @@ -17,6 +17,7 @@ power. * This is the total TX output power * Is mapped to component/optical-channel/ full path shown below +The test must be repeated for each supported operational-mode or as agreed between the vendor and customer. ## TRANSCEIVER-4.1 diff --git a/feature/platform/transceiver/tests/zr_input_output_power_test/zr_input_output_power_test.go b/feature/platform/transceiver/tests/zr_input_output_power_test/zr_input_output_power_test.go index 5395d293aeb..58b330065ac 100644 --- a/feature/platform/transceiver/tests/zr_input_output_power_test/zr_input_output_power_test.go +++ b/feature/platform/transceiver/tests/zr_input_output_power_test/zr_input_output_power_test.go @@ -1,6 +1,7 @@ package zr_input_output_power_test import ( + "flag" "testing" "time" @@ -14,7 +15,6 @@ import ( ) const ( - dp16QAM = uint16(1) samplingInterval = 10 * time.Second inactiveOCHRxPower = -30.0 inactiveOCHTxPower = -30.0 @@ -27,6 +27,8 @@ const ( var ( frequencies = []uint64{191400000, 196100000} targetOpticalPowers = []float64{-9, -13} + operationalModeFlag = flag.Int("operational_mode", 1, "vendor-specific operational-mode for the channel") + operationalMode uint16 ) func TestMain(m *testing.M) { @@ -35,7 +37,11 @@ func TestMain(m *testing.M) { func TestOpticalPower(t *testing.T) { dut := ondatra.DUT(t, "dut") - + if operationalModeFlag != nil { + operationalMode = uint16(*operationalModeFlag) + } else { + t.Fatalf("Please specify the vendor-specific operational-mode flag") + } fptest.ConfigureDefaultNetworkInstance(t, dut) var ( @@ -58,7 +64,7 @@ func TestOpticalPower(t *testing.T) { for _, targetOpticalPower := range targetOpticalPowers { // Configure OCH component and OTN and ETH logical channels. for _, p := range dut.Ports() { - cfgplugins.ConfigOpticalChannel(t, dut, ochs[p.Name()], frequency, targetOpticalPower, dp16QAM) + cfgplugins.ConfigOpticalChannel(t, dut, ochs[p.Name()], frequency, targetOpticalPower, operationalMode) } // Create sample steams for each port. diff --git a/feature/platform/transceiver/tests/zr_inventory_test/metadata.textproto b/feature/platform/transceiver/tests/zr_inventory_test/metadata.textproto index 02b3b95028f..c6eefbc266e 100644 --- a/feature/platform/transceiver/tests/zr_inventory_test/metadata.textproto +++ b/feature/platform/transceiver/tests/zr_inventory_test/metadata.textproto @@ -13,3 +13,11 @@ platform_exceptions: { missing_port_to_optical_channel_component_mapping: true } } +platform_exceptions: { + platform: { + vendor: CISCO + } + deviations: { + component_mfg_date_unsupported: true + } +} \ No newline at end of file diff --git a/feature/platform/transceiver/tests/zr_inventory_test/zr_inventory_test.go b/feature/platform/transceiver/tests/zr_inventory_test/zr_inventory_test.go index 66703f9a251..0d99c348697 100644 --- a/feature/platform/transceiver/tests/zr_inventory_test/zr_inventory_test.go +++ b/feature/platform/transceiver/tests/zr_inventory_test/zr_inventory_test.go @@ -5,6 +5,7 @@ import ( "time" "github.com/openconfig/featureprofiles/internal/cfgplugins" + "github.com/openconfig/featureprofiles/internal/deviations" "github.com/openconfig/featureprofiles/internal/fptest" "github.com/openconfig/featureprofiles/internal/samplestream" "github.com/openconfig/ondatra" @@ -13,7 +14,6 @@ import ( ) const ( - dp16QAM = 1 samplingInterval = 10 * time.Second timeout = 5 * time.Minute waitInterval = 30 * time.Second @@ -81,11 +81,13 @@ func TestInventory(t *testing.T) { samplestream.New(t, dut, component1.SerialNo().State(), samplingInterval), samplestream.New(t, dut, component1.PartNo().State(), samplingInterval), samplestream.New(t, dut, component1.MfgName().State(), samplingInterval), - samplestream.New(t, dut, component1.MfgDate().State(), samplingInterval), samplestream.New(t, dut, component1.HardwareVersion().State(), samplingInterval), samplestream.New(t, dut, component1.FirmwareVersion().State(), samplingInterval), // samplestream.New(t, dut1, component1.Description().State(), samplingInterval), ) + if !deviations.ComponentMfgDateUnsupported(dut) { + p1StreamsStr = append(p1StreamsStr, samplestream.New(t, dut, component1.MfgDate().State(), samplingInterval)) + } p1StreamsUnion = append(p1StreamsUnion, samplestream.New(t, dut, component1.Type().State(), samplingInterval)) verifyAllInventoryValues(t, p1StreamsStr, p1StreamsUnion) diff --git a/feature/platform/transceiver/tests/zr_laser_bias_current_test/zr_laser_bias_current_test.go b/feature/platform/transceiver/tests/zr_laser_bias_current_test/zr_laser_bias_current_test.go index 80e67d6649b..bdc31e8f363 100644 --- a/feature/platform/transceiver/tests/zr_laser_bias_current_test/zr_laser_bias_current_test.go +++ b/feature/platform/transceiver/tests/zr_laser_bias_current_test/zr_laser_bias_current_test.go @@ -15,10 +15,10 @@ package zr_laser_bias_current_test import ( - "reflect" "testing" "time" + "github.com/openconfig/featureprofiles/internal/cfgplugins" "github.com/openconfig/featureprofiles/internal/components" "github.com/openconfig/featureprofiles/internal/deviations" "github.com/openconfig/featureprofiles/internal/fptest" @@ -29,12 +29,6 @@ import ( "github.com/openconfig/ygot/ygot" ) -const ( - dp16QAM = 1 - targetOutputPower = -10 - frequency = 193500000 -) - func TestMain(m *testing.M) { fptest.RunTests(m) } @@ -43,93 +37,73 @@ func TestMain(m *testing.M) { // dut:port1 <--> port2:dut // -func verifyLaserBiasCurrent(t *testing.T, pStream *samplestream.SampleStream[float64], sensorName string) float64 { - laserBias := pStream.Next() +func verifyLaserBiasValue(t *testing.T, laserBiasValue float64) { + t.Helper() + if laserBiasValue <= 0 && laserBiasValue >= 131 { + t.Errorf("The laser bias value is not between 0 and 131") + } +} + +func verifyLaserBiasCurrentAll(t *testing.T, p1Stream *samplestream.SampleStream[*oc.Component_OpticalChannel_LaserBiasCurrent], dut1 *ondatra.DUTDevice) { + laserBias := p1Stream.Next() if laserBias == nil { - t.Fatalf("laserBias telemetry %q was not streamed in the most recent subscription interval", sensorName) + t.Fatalf("laserBias telemetry was not streamed in the most recent subscription interval") } laserBiasVal, ok := laserBias.Val() if !ok { - t.Fatalf("LaserBias %q telemetry is not present", sensorName) - } - if reflect.TypeOf(laserBiasVal).Kind() != reflect.Float64 { - t.Errorf("Return value is not type float64") - } - if laserBiasVal <= 0 && laserBiasVal >= 131 { - t.Errorf("The laser bias value is not between 0 and 131") + t.Fatalf("LaserBias telemetry is not present") } - t.Logf("laserBias value: %f", laserBiasVal) - return laserBiasVal -} - -func verifyLaserBiasCurrentAll(t *testing.T, pStreamInstant *samplestream.SampleStream[float64], pStreamAvg *samplestream.SampleStream[float64], pStreamMax *samplestream.SampleStream[float64], pStreamMin *samplestream.SampleStream[float64], dut1 *ondatra.DUTDevice) { - laserbiasInstant := verifyLaserBiasCurrent(t, pStreamInstant, "laserbiasInstant") - t.Logf("laserBias Instant value: %f", laserbiasInstant) + laserBiasInstant := laserBiasVal.GetInstant() + t.Logf("laserBias Instant value: %f", laserBiasInstant) if deviations.MissingZROpticalChannelTunableParametersTelemetry(dut1) { t.Log("Skipping Min/Max/Avg Tunable Parameters Telemetry validation. Deviation MissingZROpticalChannelTunableParametersTelemetry enabled.") } else { - laserbiasMin := verifyLaserBiasCurrent(t, pStreamMin, "laserbiasMin") - t.Logf("laserBias Min value: %f", laserbiasMin) - laserbiasMax := verifyLaserBiasCurrent(t, pStreamMax, "laserbiasMax") - t.Logf("laserBias Max value: %f", laserbiasMax) - laserbiasAvg := verifyLaserBiasCurrent(t, pStreamAvg, "laserbiasAvg") - t.Logf("laserBias Avg value: %f", laserbiasAvg) - if laserbiasAvg >= laserbiasMin && laserbiasAvg <= laserbiasMax { - t.Logf("The average is between the maximum and minimum values") + laserBiasMin := laserBiasVal.GetMin() + verifyLaserBiasValue(t, laserBiasMin) + t.Logf("laserBias Min value: %f", laserBiasMin) + laserBiasMax := laserBiasVal.GetMax() + verifyLaserBiasValue(t, laserBiasMax) + t.Logf("laserBias Max value: %f", laserBiasMax) + laserBiasAvg := laserBiasVal.GetAvg() + verifyLaserBiasValue(t, laserBiasAvg) + t.Logf("laserBias Avg value: %f", laserBiasMin) + if laserBiasAvg >= laserBiasMin && laserBiasAvg <= laserBiasMax { + t.Logf("The average %f is between the maximum and minimum values", laserBiasAvg) } else { - t.Fatalf("The average is not between the maximum and minimum values Avg:%f Min:%f Max:%f", laserbiasAvg, laserbiasMin, laserbiasMax) + t.Fatalf("The average is not between the maximum and minimum values Avg:%f Min:%f Max:%f", laserBiasAvg, laserBiasMin, laserBiasMax) } } } -func interfaceConfig(t *testing.T, dut1 *ondatra.DUTDevice, dp *ondatra.Port) { - d := &oc.Root{} - i := d.GetOrCreateInterface(dp.Name()) - i.Enabled = ygot.Bool(true) - i.Type = oc.IETFInterfaces_InterfaceType_ethernetCsmacd - gnmi.Replace(t, dut1, gnmi.OC().Interface(dp.Name()).Config(), i) - OCcomponent := components.OpticalChannelComponentFromPort(t, dut1, dp) - gnmi.Replace(t, dut1, gnmi.OC().Component(OCcomponent).OpticalChannel().Config(), &oc.Component_OpticalChannel{ - TargetOutputPower: ygot.Float64(targetOutputPower), - Frequency: ygot.Uint64(frequency), - }) -} - func TestZRLaserBiasCurrentState(t *testing.T) { dut1 := ondatra.DUT(t, "dut") dp1 := dut1.Port(t, "port1") dp2 := dut1.Port(t, "port2") t.Logf("dut1: %v", dut1) t.Logf("dut1 dp1 name: %v", dp1.Name()) - interfaceConfig(t, dut1, dp1) - interfaceConfig(t, dut1, dp2) + cfgplugins.InterfaceConfig(t, dut1, dp1) + cfgplugins.InterfaceConfig(t, dut1, dp2) intUpdateTime := 2 * time.Minute gnmi.Await(t, dut1, gnmi.OC().Interface(dp1.Name()).OperStatus().State(), intUpdateTime, oc.Interface_OperStatus_UP) transceiverState := gnmi.Get(t, dut1, gnmi.OC().Interface(dp1.Name()).Transceiver().State()) if dp1.PMD() != ondatra.PMD400GBASEZR { t.Fatalf("%s Transceiver is not 400ZR its of type: %v", transceiverState, dp1.PMD()) } - OCcomponent := components.OpticalChannelComponentFromPort(t, dut1, dp1) - component1 := gnmi.OC().Component(OCcomponent) - p1StreamInstant := samplestream.New(t, dut1, component1.OpticalChannel().LaserBiasCurrent().Instant().State(), 10*time.Second) - p1StreamMin := samplestream.New(t, dut1, component1.OpticalChannel().LaserBiasCurrent().Min().State(), 10*time.Second) - p1StreamMax := samplestream.New(t, dut1, component1.OpticalChannel().LaserBiasCurrent().Max().State(), 10*time.Second) - p1StreamAvg := samplestream.New(t, dut1, component1.OpticalChannel().LaserBiasCurrent().Avg().State(), 10*time.Second) - defer p1StreamAvg.Close() - defer p1StreamMax.Close() - defer p1StreamMin.Close() - defer p1StreamInstant.Close() - verifyLaserBiasCurrentAll(t, p1StreamInstant, p1StreamAvg, p1StreamMax, p1StreamMin, dut1) + componentName := components.OpticalChannelComponentFromPort(t, dut1, dp1) + component := gnmi.OC().Component(componentName) + p1Stream := samplestream.New(t, dut1, component.OpticalChannel().LaserBiasCurrent().State(), 10*time.Second) + defer p1Stream.Close() + verifyLaserBiasCurrentAll(t, p1Stream, dut1) } -func TestZRLaserBiasCurrentStateInterface_Flap(t *testing.T) { +func TestZRLaserBiasCurrentStateInterfaceFlap(t *testing.T) { dut1 := ondatra.DUT(t, "dut") dp1 := dut1.Port(t, "port1") dp2 := dut1.Port(t, "port2") t.Logf("dut1: %v", dut1) t.Logf("dut1 dp1 name: %v", dp1.Name()) - interfaceConfig(t, dut1, dp1) - interfaceConfig(t, dut1, dp2) + cfgplugins.InterfaceConfig(t, dut1, dp1) + cfgplugins.InterfaceConfig(t, dut1, dp2) intUpdateTime := 2 * time.Minute // Check interface is up gnmi.Await(t, dut1, gnmi.OC().Interface(dp1.Name()).OperStatus().State(), intUpdateTime, oc.Interface_OperStatus_UP) @@ -144,25 +118,19 @@ func TestZRLaserBiasCurrentStateInterface_Flap(t *testing.T) { i.Enabled = ygot.Bool(false) i.Type = oc.IETFInterfaces_InterfaceType_ethernetCsmacd gnmi.Replace(t, dut1, gnmi.OC().Interface(dp1.Name()).Config(), i) - OCcomponent := components.OpticalChannelComponentFromPort(t, dut1, dp1) - component1 := gnmi.OC().Component(OCcomponent) - p1StreamInstant := samplestream.New(t, dut1, component1.OpticalChannel().LaserBiasCurrent().Instant().State(), 10*time.Second) - p1StreamMin := samplestream.New(t, dut1, component1.OpticalChannel().LaserBiasCurrent().Min().State(), 10*time.Second) - p1StreamMax := samplestream.New(t, dut1, component1.OpticalChannel().LaserBiasCurrent().Max().State(), 10*time.Second) - p1StreamAvg := samplestream.New(t, dut1, component1.OpticalChannel().LaserBiasCurrent().Avg().State(), 10*time.Second) - defer p1StreamInstant.Close() - defer p1StreamMin.Close() - defer p1StreamMax.Close() - defer p1StreamAvg.Close() - verifyLaserBiasCurrentAll(t, p1StreamInstant, p1StreamAvg, p1StreamMax, p1StreamMin, dut1) - // Wait 120 sec cooling off period + componentName := components.OpticalChannelComponentFromPort(t, dut1, dp1) + component := gnmi.OC().Component(componentName) + p1Stream := samplestream.New(t, dut1, component.OpticalChannel().LaserBiasCurrent().State(), 10*time.Second) + defer p1Stream.Close() + verifyLaserBiasCurrentAll(t, p1Stream, dut1) + // Wait 120 sec cooling-off period gnmi.Await(t, dut1, gnmi.OC().Interface(dp1.Name()).OperStatus().State(), intUpdateTime, oc.Interface_OperStatus_DOWN) + verifyLaserBiasCurrentAll(t, p1Stream, dut1) // Enable interface - verifyLaserBiasCurrentAll(t, p1StreamInstant, p1StreamAvg, p1StreamMax, p1StreamMin, dut1) i.Enabled = ygot.Bool(true) gnmi.Replace(t, dut1, gnmi.OC().Interface(dp1.Name()).Config(), i) gnmi.Await(t, dut1, gnmi.OC().Interface(dp1.Name()).OperStatus().State(), intUpdateTime, oc.Interface_OperStatus_UP) - verifyLaserBiasCurrentAll(t, p1StreamInstant, p1StreamAvg, p1StreamMax, p1StreamMin, dut1) + verifyLaserBiasCurrentAll(t, p1Stream, dut1) } func TestZRLaserBiasCurrentStateTransceiverOnOff(t *testing.T) { @@ -171,8 +139,8 @@ func TestZRLaserBiasCurrentStateTransceiverOnOff(t *testing.T) { dp2 := dut1.Port(t, "port2") t.Logf("dut1: %v", dut1) t.Logf("dut1 dp1 name: %v", dp1.Name()) - interfaceConfig(t, dut1, dp1) - interfaceConfig(t, dut1, dp2) + cfgplugins.InterfaceConfig(t, dut1, dp1) + cfgplugins.InterfaceConfig(t, dut1, dp2) intUpdateTime := 2 * time.Minute gnmi.Await(t, dut1, gnmi.OC().Interface(dp1.Name()).OperStatus().State(), intUpdateTime, oc.Interface_OperStatus_UP) transceiverState := gnmi.Get(t, dut1, gnmi.OC().Interface(dp1.Name()).Transceiver().State()) @@ -180,21 +148,17 @@ func TestZRLaserBiasCurrentStateTransceiverOnOff(t *testing.T) { if dp1.PMD() != ondatra.PMD400GBASEZR { t.Fatalf("%s Transceiver is not 400ZR its of type: %v", transceiverState, dp1.PMD()) } - OCcomponent := components.OpticalChannelComponentFromPort(t, dut1, dp1) - component1 := gnmi.OC().Component(OCcomponent) - p1StreamInstant := samplestream.New(t, dut1, component1.OpticalChannel().LaserBiasCurrent().Instant().State(), 10*time.Second) - p1StreamMin := samplestream.New(t, dut1, component1.OpticalChannel().LaserBiasCurrent().Min().State(), 10*time.Second) - p1StreamMax := samplestream.New(t, dut1, component1.OpticalChannel().LaserBiasCurrent().Max().State(), 10*time.Second) - p1StreamAvg := samplestream.New(t, dut1, component1.OpticalChannel().LaserBiasCurrent().Avg().State(), 10*time.Second) - defer p1StreamInstant.Close() - defer p1StreamMin.Close() - defer p1StreamMax.Close() - defer p1StreamAvg.Close() - // Disable interface transceiver power off + componentName := components.OpticalChannelComponentFromPort(t, dut1, dp1) + component := gnmi.OC().Component(componentName) + p1Stream := samplestream.New(t, dut1, component.OpticalChannel().LaserBiasCurrent().State(), 10*time.Second) + defer p1Stream.Close() + verifyLaserBiasCurrentAll(t, p1Stream, dut1) + // power off interface transceiver + gnmi.Update(t, dut1, gnmi.OC().Component(dp1.Name()).Name().Config(), dp1.Name()) gnmi.Update(t, dut1, gnmi.OC().Component(dp1.Name()).Transceiver().Enabled().Config(), false) - verifyLaserBiasCurrentAll(t, p1StreamInstant, p1StreamAvg, p1StreamMax, p1StreamMin, dut1) - // Enable interface transceiver power on + verifyLaserBiasCurrentAll(t, p1Stream, dut1) + // power on interface transceiver gnmi.Update(t, dut1, gnmi.OC().Component(dp1.Name()).Transceiver().Enabled().Config(), true) gnmi.Await(t, dut1, gnmi.OC().Interface(dp1.Name()).OperStatus().State(), intUpdateTime, oc.Interface_OperStatus_UP) - verifyLaserBiasCurrentAll(t, p1StreamInstant, p1StreamAvg, p1StreamMax, p1StreamMin, dut1) + verifyLaserBiasCurrentAll(t, p1Stream, dut1) } diff --git a/feature/platform/transceiver/tests/zr_supply_voltage_test/zr_supply_voltage_test.go b/feature/platform/transceiver/tests/zr_supply_voltage_test/zr_supply_voltage_test.go index c05b29aae9f..3fc74a0e274 100644 --- a/feature/platform/transceiver/tests/zr_supply_voltage_test/zr_supply_voltage_test.go +++ b/feature/platform/transceiver/tests/zr_supply_voltage_test/zr_supply_voltage_test.go @@ -83,7 +83,7 @@ func TestZrSupplyVoltage(t *testing.T) { // Disable interface i.Enabled = ygot.Bool(false) gnmi.Replace(t, dut, gnmi.OC().Interface(dp.Name()).Config(), i) - // Wait for the cooling off period + // Wait for the cooling-off period gnmi.Await(t, dut, gnmi.OC().Interface(dp.Name()).OperStatus().State(), intUpdateTime, oc.Interface_OperStatus_DOWN) volInstNew := verifyVoltageValue(t, streamInst, "Instant") @@ -92,7 +92,7 @@ func TestZrSupplyVoltage(t *testing.T) { // Enable interface again. i.Enabled = ygot.Bool(true) gnmi.Replace(t, dut, gnmi.OC().Interface(dp.Name()).Config(), i) - // Wait for the cooling off period + // Wait for the cooling-off period gnmi.Await(t, dut, gnmi.OC().Interface(dp.Name()).OperStatus().State(), intUpdateTime, oc.Interface_OperStatus_UP) }) } diff --git a/feature/platform/transceiver/tests/zr_temperature_test/metadata.textproto b/feature/platform/transceiver/tests/zr_temperature_test/metadata.textproto index cf055bacbc7..73787e4b97c 100644 --- a/feature/platform/transceiver/tests/zr_temperature_test/metadata.textproto +++ b/feature/platform/transceiver/tests/zr_temperature_test/metadata.textproto @@ -16,3 +16,11 @@ platform_exceptions: { missing_zr_optical_channel_tunable_parameters_telemetry: true } } +platform_exceptions: { + platform: { + vendor: CISCO + } + deviations: { + use_parent_component_for_temperature_telemetry: true + } +} \ No newline at end of file diff --git a/feature/platform/transceiver/tests/zr_temperature_test/zr_temperature_test.go b/feature/platform/transceiver/tests/zr_temperature_test/zr_temperature_test.go index d23599054c9..38f3c3f133a 100644 --- a/feature/platform/transceiver/tests/zr_temperature_test/zr_temperature_test.go +++ b/feature/platform/transceiver/tests/zr_temperature_test/zr_temperature_test.go @@ -19,7 +19,7 @@ import ( "testing" "time" - "github.com/openconfig/featureprofiles/internal/components" + "github.com/openconfig/featureprofiles/internal/cfgplugins" "github.com/openconfig/featureprofiles/internal/deviations" "github.com/openconfig/featureprofiles/internal/fptest" "github.com/openconfig/featureprofiles/internal/samplestream" @@ -30,10 +30,7 @@ import ( ) const ( - sensorType = oc.PlatformTypes_OPENCONFIG_HARDWARE_COMPONENT_SENSOR - dp16QAM = 1 - targetOutputPower = -10 - frequency = 193500000 + sensorType = oc.PlatformTypes_OPENCONFIG_HARDWARE_COMPONENT_SENSOR ) func TestMain(m *testing.M) { @@ -44,19 +41,6 @@ func TestMain(m *testing.M) { // // dut:port1 <--> port2:dut -func interfaceConfig(t *testing.T, dut1 *ondatra.DUTDevice, dp *ondatra.Port) { - d := &oc.Root{} - i := d.GetOrCreateInterface(dp.Name()) - i.Enabled = ygot.Bool(true) - i.Type = oc.IETFInterfaces_InterfaceType_ethernetCsmacd - gnmi.Replace(t, dut1, gnmi.OC().Interface(dp.Name()).Config(), i) - OCcomponent := components.OpticalChannelComponentFromPort(t, dut1, dp) - gnmi.Replace(t, dut1, gnmi.OC().Component(OCcomponent).OpticalChannel().Config(), &oc.Component_OpticalChannel{ - TargetOutputPower: ygot.Float64(targetOutputPower), - Frequency: ygot.Uint64(frequency), - }) -} - func verifyTemperatureSensorValue(t *testing.T, pStream *samplestream.SampleStream[float64], sensorName string) float64 { temperatureSample := pStream.Next() if temperatureSample == nil { @@ -83,37 +67,39 @@ func TestZRTemperatureState(t *testing.T) { t.Logf("dut1: %v", dut1) t.Logf("dut1 dp1 name: %v", dp1.Name()) intUpdateTime := 2 * time.Minute - interfaceConfig(t, dut1, dp1) - interfaceConfig(t, dut1, dp2) + cfgplugins.InterfaceConfig(t, dut1, dp1) + cfgplugins.InterfaceConfig(t, dut1, dp2) gnmi.Await(t, dut1, gnmi.OC().Interface(dp1.Name()).OperStatus().State(), intUpdateTime, oc.Interface_OperStatus_UP) transceiverName := gnmi.Get(t, dut1, gnmi.OC().Interface(dp1.Name()).Transceiver().State()) // Check if TRANSCEIVER is of type 400ZR if dp1.PMD() != ondatra.PMD400GBASEZR { t.Fatalf("%s Transceiver is not 400ZR its of type: %v", transceiverName, dp1.PMD()) } - component1 := gnmi.OC().Component(transceiverName) - subcomponents := gnmi.LookupAll[*oc.Component_Subcomponent](t, dut1, component1.SubcomponentAny().State()) - for _, s := range subcomponents { - subc, ok := s.Val() - if ok { - sensorComponent := gnmi.Get[*oc.Component](t, dut1, gnmi.OC().Component(subc.GetName()).State()) - if sensorComponent.GetType() == sensorType { - scomponent := gnmi.OC().Component(sensorComponent.GetName()) - if scomponent != nil { - component1 = scomponent + compWithTemperature := gnmi.OC().Component(transceiverName) + if !deviations.UseParentComponentForTemperatureTelemetry(dut1) { + subcomponents := gnmi.LookupAll[*oc.Component_Subcomponent](t, dut1, compWithTemperature.SubcomponentAny().State()) + for _, s := range subcomponents { + subc, ok := s.Val() + if ok { + sensorComponent := gnmi.Get[*oc.Component](t, dut1, gnmi.OC().Component(subc.GetName()).State()) + if sensorComponent.GetType() == sensorType { + scomponent := gnmi.OC().Component(sensorComponent.GetName()) + if scomponent != nil { + compWithTemperature = scomponent + } } } } } - p1StreamInstant := samplestream.New(t, dut1, component1.Temperature().Instant().State(), 10*time.Second) + p1StreamInstant := samplestream.New(t, dut1, compWithTemperature.Temperature().Instant().State(), 10*time.Second) temperatureInstant := verifyTemperatureSensorValue(t, p1StreamInstant, "Instant") t.Logf("Port1 dut1 %s Instant Temperature: %v", dp1.Name(), temperatureInstant) if deviations.MissingZROpticalChannelTunableParametersTelemetry(dut1) { t.Log("Skipping Min/Max/Avg Tunable Parameters Telemetry validation. Deviation MissingZROpticalChannelTunableParametersTelemetry enabled.") } else { - p1StreamAvg := samplestream.New(t, dut1, component1.Temperature().Avg().State(), 10*time.Second) - p1StreamMin := samplestream.New(t, dut1, component1.Temperature().Min().State(), 10*time.Second) - p1StreamMax := samplestream.New(t, dut1, component1.Temperature().Max().State(), 10*time.Second) + p1StreamAvg := samplestream.New(t, dut1, compWithTemperature.Temperature().Avg().State(), 10*time.Second) + p1StreamMin := samplestream.New(t, dut1, compWithTemperature.Temperature().Min().State(), 10*time.Second) + p1StreamMax := samplestream.New(t, dut1, compWithTemperature.Temperature().Max().State(), 10*time.Second) temperatureMax := verifyTemperatureSensorValue(t, p1StreamMax, "Max") t.Logf("Port1 dut1 %s Max Temperature: %v", dp1.Name(), temperatureMax) @@ -139,8 +125,8 @@ func TestZRTemperatureStateInterfaceFlap(t *testing.T) { dp2 := dut1.Port(t, "port2") t.Logf("dut1: %v", dut1) t.Logf("dut1 dp1 name: %v", dp1.Name()) - interfaceConfig(t, dut1, dp1) - interfaceConfig(t, dut1, dp2) + cfgplugins.InterfaceConfig(t, dut1, dp1) + cfgplugins.InterfaceConfig(t, dut1, dp2) intUpdateTime := 2 * time.Minute gnmi.Await(t, dut1, gnmi.OC().Interface(dp1.Name()).OperStatus().State(), intUpdateTime, oc.Interface_OperStatus_UP) transceiverName := gnmi.Get(t, dut1, gnmi.OC().Interface(dp1.Name()).Transceiver().State()) @@ -152,26 +138,29 @@ func TestZRTemperatureStateInterfaceFlap(t *testing.T) { d := &oc.Root{} i := d.GetOrCreateInterface(dp1.Name()) i.Enabled = ygot.Bool(false) + i.Type = oc.IETFInterfaces_InterfaceType_ethernetCsmacd gnmi.Replace(t, dut1, gnmi.OC().Interface(dp1.Name()).Config(), i) - component1 := gnmi.OC().Component(transceiverName) - subcomponents := gnmi.LookupAll[*oc.Component_Subcomponent](t, dut1, component1.SubcomponentAny().State()) - for _, s := range subcomponents { - subc, ok := s.Val() - if ok { - sensorComponent := gnmi.Get[*oc.Component](t, dut1, gnmi.OC().Component(subc.GetName()).State()) - if sensorComponent.GetType() == sensorType { - scomponent := gnmi.OC().Component(sensorComponent.GetName()) - if scomponent != nil { - component1 = scomponent + compWithTemperature := gnmi.OC().Component(transceiverName) + if !deviations.UseParentComponentForTemperatureTelemetry(dut1) { + subcomponents := gnmi.LookupAll[*oc.Component_Subcomponent](t, dut1, compWithTemperature.SubcomponentAny().State()) + for _, s := range subcomponents { + subc, ok := s.Val() + if ok { + sensorComponent := gnmi.Get[*oc.Component](t, dut1, gnmi.OC().Component(subc.GetName()).State()) + if sensorComponent.GetType() == sensorType { + scomponent := gnmi.OC().Component(sensorComponent.GetName()) + if scomponent != nil { + compWithTemperature = scomponent + } } } } } - p1StreamInstant := samplestream.New(t, dut1, component1.Temperature().Instant().State(), 10*time.Second) - p1StreamAvg := samplestream.New(t, dut1, component1.Temperature().Avg().State(), 10*time.Second) - p1StreamMin := samplestream.New(t, dut1, component1.Temperature().Min().State(), 10*time.Second) - p1StreamMax := samplestream.New(t, dut1, component1.Temperature().Max().State(), 10*time.Second) - // Wait 120 sec cooling off period + p1StreamInstant := samplestream.New(t, dut1, compWithTemperature.Temperature().Instant().State(), 10*time.Second) + p1StreamAvg := samplestream.New(t, dut1, compWithTemperature.Temperature().Avg().State(), 10*time.Second) + p1StreamMin := samplestream.New(t, dut1, compWithTemperature.Temperature().Min().State(), 10*time.Second) + p1StreamMax := samplestream.New(t, dut1, compWithTemperature.Temperature().Max().State(), 10*time.Second) + // Wait 120 sec cooling-off period gnmi.Await(t, dut1, gnmi.OC().Interface(dp1.Name()).OperStatus().State(), intUpdateTime, oc.Interface_OperStatus_DOWN) temperatureInstant := verifyTemperatureSensorValue(t, p1StreamInstant, "Instant") t.Logf("Port1 dut1 %s Instant Temperature: %v", dp1.Name(), temperatureInstant) diff --git a/feature/platform/transceiver/tests/zr_tunable_parameters_test/metadata.textproto b/feature/platform/transceiver/tests/zr_tunable_parameters_test/metadata.textproto index 5bd64161c63..e90ee70f530 100644 --- a/feature/platform/transceiver/tests/zr_tunable_parameters_test/metadata.textproto +++ b/feature/platform/transceiver/tests/zr_tunable_parameters_test/metadata.textproto @@ -13,4 +13,4 @@ platform_exceptions: { default_network_instance: "default" missing_zr_optical_channel_tunable_parameters_telemetry: true } -} +} \ No newline at end of file diff --git a/feature/experimental/policy/otg_tests/prefix_set_test/README.md b/feature/policy_forwarding/otg_tests/prefix_set_test/README.md similarity index 100% rename from feature/experimental/policy/otg_tests/prefix_set_test/README.md rename to feature/policy_forwarding/otg_tests/prefix_set_test/README.md diff --git a/feature/experimental/policy/otg_tests/prefix_set_test/metadata.textproto b/feature/policy_forwarding/otg_tests/prefix_set_test/metadata.textproto similarity index 100% rename from feature/experimental/policy/otg_tests/prefix_set_test/metadata.textproto rename to feature/policy_forwarding/otg_tests/prefix_set_test/metadata.textproto diff --git a/feature/experimental/policy/otg_tests/prefix_set_test/prefix_set_test.go b/feature/policy_forwarding/otg_tests/prefix_set_test/prefix_set_test.go similarity index 100% rename from feature/experimental/policy/otg_tests/prefix_set_test/prefix_set_test.go rename to feature/policy_forwarding/otg_tests/prefix_set_test/prefix_set_test.go diff --git a/feature/experimental/policy/policy_vrf_selection/otg_tests/base_vrf_selection/README.md b/feature/policy_forwarding/policy_vrf_selection/otg_tests/base_vrf_selection/README.md similarity index 100% rename from feature/experimental/policy/policy_vrf_selection/otg_tests/base_vrf_selection/README.md rename to feature/policy_forwarding/policy_vrf_selection/otg_tests/base_vrf_selection/README.md diff --git a/feature/experimental/policy/policy_vrf_selection/otg_tests/base_vrf_selection/base_vrf_selection_test.go b/feature/policy_forwarding/policy_vrf_selection/otg_tests/base_vrf_selection/base_vrf_selection_test.go similarity index 100% rename from feature/experimental/policy/policy_vrf_selection/otg_tests/base_vrf_selection/base_vrf_selection_test.go rename to feature/policy_forwarding/policy_vrf_selection/otg_tests/base_vrf_selection/base_vrf_selection_test.go diff --git a/feature/experimental/policy/policy_vrf_selection/otg_tests/base_vrf_selection/metadata.textproto b/feature/policy_forwarding/policy_vrf_selection/otg_tests/base_vrf_selection/metadata.textproto similarity index 100% rename from feature/experimental/policy/policy_vrf_selection/otg_tests/base_vrf_selection/metadata.textproto rename to feature/policy_forwarding/policy_vrf_selection/otg_tests/base_vrf_selection/metadata.textproto diff --git a/feature/experimental/policy/policy_vrf_selection/otg_tests/protocol_dscp_rules_for_vrf_selection_test/README.md b/feature/policy_forwarding/policy_vrf_selection/otg_tests/protocol_dscp_rules_for_vrf_selection_test/README.md similarity index 100% rename from feature/experimental/policy/policy_vrf_selection/otg_tests/protocol_dscp_rules_for_vrf_selection_test/README.md rename to feature/policy_forwarding/policy_vrf_selection/otg_tests/protocol_dscp_rules_for_vrf_selection_test/README.md diff --git a/feature/experimental/policy/policy_vrf_selection/otg_tests/protocol_dscp_rules_for_vrf_selection_test/metadata.textproto b/feature/policy_forwarding/policy_vrf_selection/otg_tests/protocol_dscp_rules_for_vrf_selection_test/metadata.textproto similarity index 100% rename from feature/experimental/policy/policy_vrf_selection/otg_tests/protocol_dscp_rules_for_vrf_selection_test/metadata.textproto rename to feature/policy_forwarding/policy_vrf_selection/otg_tests/protocol_dscp_rules_for_vrf_selection_test/metadata.textproto diff --git a/feature/experimental/policy/policy_vrf_selection/otg_tests/protocol_dscp_rules_for_vrf_selection_test/protocol_dscp_rules_for_vrf_selection_test.go b/feature/policy_forwarding/policy_vrf_selection/otg_tests/protocol_dscp_rules_for_vrf_selection_test/protocol_dscp_rules_for_vrf_selection_test.go similarity index 100% rename from feature/experimental/policy/policy_vrf_selection/otg_tests/protocol_dscp_rules_for_vrf_selection_test/protocol_dscp_rules_for_vrf_selection_test.go rename to feature/policy_forwarding/policy_vrf_selection/otg_tests/protocol_dscp_rules_for_vrf_selection_test/protocol_dscp_rules_for_vrf_selection_test.go diff --git a/feature/qos/otg_tests/ingress_police_default/README.md b/feature/qos/otg_tests/ingress_police_default/README.md new file mode 100644 index 00000000000..df47044e638 --- /dev/null +++ b/feature/qos/otg_tests/ingress_police_default/README.md @@ -0,0 +1,195 @@ +# DP-2.4 Police traffic on input matching all packets using 1 rate, 2 color marker + +## Summary + +Use the gRIBI applied ip entries from TE-18.1 gRIBI. +Configure an ingress scheduler to police traffic using a 1 rate, 2 color policer and attach the scheduler to the interface without a classifier. +Lack of match conditions will cause all packets to be matched. +Send traffic to validate the policer. + +## Topology + +* [`featureprofiles/topologies/atedut_2.testbed`](https://github.com/openconfig/featureprofiles/blob/main/topologies/atedut_2.testbed) + +## Test setup + +Use TE-18.1 test environment setup. + +## Procedure + +### DP-2.4.1 Generate and push configuration + +* Generate config for 2 scheduler polices with an input rate limit. +* Apply scheduler to DUT subinterface with vlan. +* Use gnmi.Replace to push the config to the DUT. + +```json +{ + "openconfig-qos": { + "scheduler-policies": [ + { + "scheduler-policy": null, + "config": { + "name": "limit_1Gb" + }, + "schedulers": [ + { + "scheduler": null, + "config": { + "sequence": 1, + "type": "ONE_RATE_TWO_COLOR" + }, + "inputs": [ + { + "input": "my input policer 1Gb", + "config": { + "id": "my input policer 1Gb", + "input-type": "QUEUE", + "queue": "dummy_input_queue_A" + } + } + ], + "one-rate-two-color": { + "config": { + "cir": 1000000000, + "bc": 100000, + "queuing-behavior": "POLICE" + }, + "exceed-action": { + "config": { + "drop": true + } + } + } + } + ] + }, + { + "scheduler-policy": null, + "config": { + "name": "limit_2Gb" + }, + "schedulers": [ + { + "scheduler": null, + "config": { + "sequence": 1, + "type": "ONE_RATE_TWO_COLOR" + }, + "inputs": [ + { + "input": "my input policer 2Gb", + "config": { + "id": "my input policer 2Gb", + "input-type": "QUEUE", + "queue": "dummy_input_queue_B" + } + } + ], + "one-rate-two-color": { + "config": { + "cir": 2000000000, + "bc": 100000, + "queuing-behavior": "POLICE" + }, + "exceed-action": { + "config": { + "drop": true + } + } + } + } + ] + } + ], + # + # Interfaces input are mapped to the desired scheduler. + "interfaces": [ + { + "interface": null, + "config": { + "interface-id": "PortChannel1.100" + }, + "input": { + "scheduler-policy": { + "config": { + "name": "limit_group_A_1Gb" + } + } + } + }, + { + "interface": null, + "config": { + "interface-id": "PortChannel1.200" + }, + "input": { + "scheduler-policy": { + "config": { + "name": "limit_group_B_1Gb" + } + } + } + } + ] + } +} +``` + +### DP-2.4.2 Test traffic + +* Send traffic + * Send flow A traffic from ATE port 1 to DUT for dest_A at 0.7Gbps (note cir is 1Gbps). + * Send flow B traffic from ATE port 1 to DUT for to dest_B at 1.5Gbps (note cir is 2Gbps). + * Validate qos counters per DUT. + * Validate qos counters by ATE port. + * Validate packets are received by ATE port 2. + * Validate DUT qos interface scheduler counters count packets as conforming-pkts and conforming-octets + * Validate at OTG that 0 packets are lost on flow A and flow B + * When the outer packet is IPv6, the flow-label should be inspected on the ATE. + * If the inner packet is IPv4, the outer IPv6 flow label should be computed based on the IPv4 5 tuple src,dst address and ports, plus protocol. + * If the inner packet is IPv6, the inner flow label should be copied to the outer packet. + * To validate the flow label, use the ATE to verify that the packets for + * flow A all have the same flow label + * flow B have the same flow label + * flow A and B labels do not match + * Increase traffic on flow to dest_B to 2Gbps + * Validate that flow dest_B experiences ~50% packet loss (+/- 1%) + + +#### OpenConfig Path and RPC Coverage + +```yaml +paths: + # qos scheduler config + /qos/scheduler-policies/scheduler-policy/config/name: + /qos/scheduler-policies/scheduler-policy/schedulers/scheduler/config/type: + /qos/scheduler-policies/scheduler-policy/schedulers/scheduler/one-rate-two-color/config/cir: + /qos/scheduler-policies/scheduler-policy/schedulers/scheduler/one-rate-two-color/config/bc: + /qos/scheduler-policies/scheduler-policy/schedulers/scheduler/one-rate-two-color/config/queuing-behavior: + /qos/scheduler-policies/scheduler-policy/schedulers/scheduler/one-rate-two-color/exceed-action/config/drop: + + # qos interfaces config + /qos/interfaces/interface/config/interface-id: + /qos/interfaces/interface/input/scheduler-policy/config/name: + + # qos interface scheduler counters + /qos/interfaces/interface/input/scheduler-policy/schedulers/scheduler/state/conforming-pkts: + /qos/interfaces/interface/input/scheduler-policy/schedulers/scheduler/state/conforming-octets: + /qos/interfaces/interface/input/scheduler-policy/schedulers/scheduler/state/exceeding-pkts: + /qos/interfaces/interface/input/scheduler-policy/schedulers/scheduler/state/exceeding-octets: + +rpcs: + gnmi: + gNMI.Set: + union_replace: true + replace: true + gNMI.Subscribe: + on_change: true +``` + +## Required DUT platform + +* FFF + + diff --git a/feature/experimental/replay/tests/diff_command_trees/README.md b/feature/replay/tests/diff_command_trees/README.md similarity index 62% rename from feature/experimental/replay/tests/diff_command_trees/README.md rename to feature/replay/tests/diff_command_trees/README.md index 91720b7d422..61ddc439b53 100644 --- a/feature/experimental/replay/tests/diff_command_trees/README.md +++ b/feature/replay/tests/diff_command_trees/README.md @@ -7,3 +7,17 @@ diff the command trees" error when applying certain gNMI config on Arista devices. At this time, no vendor is expected to run this test. + +## OpenConfig Path and RPC Coverage + +```yaml +rpcs: + gnmi: + gNMI.Get: + gNMI.Set: + gNMI.Subscribe: + gribi: + gRIBI.Get: + gRIBI.Modify: + gRIBI.Flush: +``` diff --git a/feature/experimental/replay/tests/diff_command_trees/diff_command_trees_test.go b/feature/replay/tests/diff_command_trees/diff_command_trees_test.go similarity index 100% rename from feature/experimental/replay/tests/diff_command_trees/diff_command_trees_test.go rename to feature/replay/tests/diff_command_trees/diff_command_trees_test.go diff --git a/feature/experimental/replay/tests/diff_command_trees/metadata.textproto b/feature/replay/tests/diff_command_trees/metadata.textproto similarity index 100% rename from feature/experimental/replay/tests/diff_command_trees/metadata.textproto rename to feature/replay/tests/diff_command_trees/metadata.textproto diff --git a/feature/experimental/replay/tests/p4rt_replay/README.md b/feature/replay/tests/p4rt_replay/README.md similarity index 54% rename from feature/experimental/replay/tests/p4rt_replay/README.md rename to feature/replay/tests/p4rt_replay/README.md index 6861b35f9cb..f23fe835e7e 100644 --- a/feature/experimental/replay/tests/p4rt_replay/README.md +++ b/feature/replay/tests/p4rt_replay/README.md @@ -6,3 +6,17 @@ This is an example record/replay test. It is meant to reproduce an error when replaying P4RT messages. At this time, no vendor is expected to run this test. + +## OpenConfig Path and RPC Coverage + +```yaml +rpcs: + gnmi: + gNMI.Get: + gNMI.Set: + gNMI.Subscribe: + gribi: + gRIBI.Get: + gRIBI.Modify: + gRIBI.Flush: +``` diff --git a/feature/experimental/replay/tests/p4rt_replay/metadata.textproto b/feature/replay/tests/p4rt_replay/metadata.textproto similarity index 100% rename from feature/experimental/replay/tests/p4rt_replay/metadata.textproto rename to feature/replay/tests/p4rt_replay/metadata.textproto diff --git a/feature/experimental/replay/tests/p4rt_replay/p4rt_replay_test.go b/feature/replay/tests/p4rt_replay/p4rt_replay_test.go similarity index 100% rename from feature/experimental/replay/tests/p4rt_replay/p4rt_replay_test.go rename to feature/replay/tests/p4rt_replay/p4rt_replay_test.go diff --git a/feature/replay/tests/presession_test/README.md b/feature/replay/tests/presession_test/README.md new file mode 100644 index 00000000000..f1528f687b0 --- /dev/null +++ b/feature/replay/tests/presession_test/README.md @@ -0,0 +1,20 @@ +# Replay-1.0: Record/replay presession test + +## Summary + +This is an example record/replay test. +At this time, no vendor is expected to run this test. + +## OpenConfig Path and RPC Coverage + +```yaml +rpcs: + gnmi: + gNMI.Get: + gNMI.Set: + gNMI.Subscribe: + gribi: + gRIBI.Get: + gRIBI.Modify: + gRIBI.Flush: +``` diff --git a/feature/experimental/replay/tests/presession_test/metadata.textproto b/feature/replay/tests/presession_test/metadata.textproto similarity index 100% rename from feature/experimental/replay/tests/presession_test/metadata.textproto rename to feature/replay/tests/presession_test/metadata.textproto diff --git a/feature/experimental/replay/tests/presession_test/presession_test.go b/feature/replay/tests/presession_test/presession_test.go similarity index 100% rename from feature/experimental/replay/tests/presession_test/presession_test.go rename to feature/replay/tests/presession_test/presession_test.go diff --git a/feature/experimental/security/aaa/kne_tests/tls_authentication_over_grpc_test/README.md b/feature/security/aaa/kne_tests/tls_authentication_over_grpc_test/README.md similarity index 91% rename from feature/experimental/security/aaa/kne_tests/tls_authentication_over_grpc_test/README.md rename to feature/security/aaa/kne_tests/tls_authentication_over_grpc_test/README.md index 4515b12bb87..f1e22c2734e 100644 --- a/feature/experimental/security/aaa/kne_tests/tls_authentication_over_grpc_test/README.md +++ b/feature/security/aaa/kne_tests/tls_authentication_over_grpc_test/README.md @@ -25,17 +25,13 @@ and gRPC connections. * Ensure gNMI set/get requests are denied with incorrect login or incorrect password. -## Config Parameter coverage - -N/A - -## Telemetry Parameter coverage - -N/A - -## Protocol/RPC Parameter coverage - -N/A +## OpenConfig Path and RPC Coverage +```yaml +rpcs: + gnmi: + gNMI.Set: + gNMI.Subscribe: +``` ## Minimum DUT platform requirement diff --git a/feature/experimental/security/aaa/kne_tests/tls_authentication_over_grpc_test/metadata.textproto b/feature/security/aaa/kne_tests/tls_authentication_over_grpc_test/metadata.textproto similarity index 100% rename from feature/experimental/security/aaa/kne_tests/tls_authentication_over_grpc_test/metadata.textproto rename to feature/security/aaa/kne_tests/tls_authentication_over_grpc_test/metadata.textproto diff --git a/feature/experimental/security/aaa/kne_tests/tls_authentication_over_grpc_test/tls_authentication_over_grpc_test.go b/feature/security/aaa/kne_tests/tls_authentication_over_grpc_test/tls_authentication_over_grpc_test.go similarity index 100% rename from feature/experimental/security/aaa/kne_tests/tls_authentication_over_grpc_test/tls_authentication_over_grpc_test.go rename to feature/security/aaa/kne_tests/tls_authentication_over_grpc_test/tls_authentication_over_grpc_test.go diff --git a/feature/security/gnsi/credentialz/tests/README.md b/feature/security/gnsi/credentialz/tests/README.md index 5a6e51e3d13..08442078f8d 100644 --- a/feature/security/gnsi/credentialz/tests/README.md +++ b/feature/security/gnsi/credentialz/tests/README.md @@ -63,6 +63,19 @@ stream.Send( ) ``` +### Configure and enable GLOME + +``` +stream.Send( + RotateHostParametersRequest { + enabled: true, + key: "4242424242424242424242424242424242424242424242", + key_version: 4, + url_prefix: "https://example.invalid", + } +) +``` + ### Populate Authorized Principals ``` @@ -204,7 +217,7 @@ and * Create a ssh CA keypair with `ssh-keygen -f /tmp/ca`. * Fetch the ssh server's host public key. * Sign the public key from the previous step into a host certificate using the - CA key `ssh-keygen -s /tmp/ca -I dut -h -n dut.test.com -V +52w + CA key `ssh-keygen -s /tmp/ca -I dut -h -n dut.example.invalid -V +52w /location/of/host/public_key.pub` * Add the certificate to the server (see RotateHostParameters, AuthenticationArtifacts, certificate) @@ -281,6 +294,28 @@ and * Ensure that access rejects telemetry counter is incremented `/oc-sys:system/oc-sys:ssh-server/oc-sys:state:counters:access-rejects` +### Credentialz-6, GLOME Configuration + +#### Setup +* Create a glome key with `glome` following [these + instructions](https://github.com/google/glome?tab=readme-ov-file#getting-started). +* Send a RotateHostParameters GlomeRequest message, with key, key_version, and + prefix_url. + +#### Pass case +* Attempt a console connection. + * Prompt must include a GLOME challenge. + * Use the `glome` binary along with your generated key to generate an + authorization code. + * Use the authorization code at the console prompt. + * Authorization must succeed. + * Ensure telemetry values for version and enabled match what was set in Setup. + +#### Fail case +* Attempt a console connection. + * Enter `fake-authorization-code` in the prompt. + * Authentication must fail. +======= ## OpenConfig Path and RPC Coverage The below yaml defines the OC paths intended to be covered by this test. OC paths used for test setup are not listed here. @@ -292,4 +327,3 @@ rpcs: gnsi: credentialz.v1.Credentialz.RotateAccountCredentials: ``` - diff --git a/feature/sflow/otg_tests/sflow_base_test/README.md b/feature/sflow/otg_tests/sflow_base_test/README.md index 840cdf540e8..b83b28e15e2 100644 --- a/feature/sflow/otg_tests/sflow_base_test/README.md +++ b/feature/sflow/otg_tests/sflow_base_test/README.md @@ -6,7 +6,7 @@ Verify configuration of sflow and sFlow sample data. ## Procedure -* SFLOW-1.1 Configure sFlow on DUT +* SFLOW-1.1 Configure sFlow on DUT on a non-default VRF * Configure DUT and ATE with 2 ports * Configure DUT to send sflow samples to ATE port 2 * Set sample source address, sample size 256Bytes, one sample per 1M packets and DSCP=32 @@ -20,10 +20,10 @@ Verify configuration of sflow and sFlow sample data. | mflow3 | 100000 | 512 | IP | TCP | | lflow3 | 100000 | 1500 | IP | TCP | -* Verify captured packets are formatted like an sFlow packet - * Verify sample size is 256B - * Verify 1 sample sent to collector address per 1M packets generated by ATE - * Verify sample packet is set with DSCP=32 + * Verify captured packets are formatted like an sFlow packet + * Verify sample size is 256B + * Verify 1 sample sent to collector address per 1M packets generated by ATE + * Verify sample packet is set with DSCP=32 * SFLOW-1.3 [TODO #2346]( https://github.com/openconfig/featureprofiles/issues/2346): Additional sflow packet verifications * Using the same packets captured in SFLOW-1.2 verify @@ -34,57 +34,57 @@ Verify configuration of sflow and sFlow sample data. * Next hop source mask * Next hop destination mask -## Config Parameter coverage - -/sampling/sflow/config/agent-id-ipv4 -/sampling/sflow/config/agent-id-ipv6 -/sampling/sflow/config/dscp -/sampling/sflow/config/egress-sampling-rate -/sampling/sflow/config/enabled -/sampling/sflow/config/ingress-sampling-rate -/sampling/sflow/config/polling-interval -/sampling/sflow/config/sample-size -/sampling/sflow/config/source-address -/sampling/sflow/interfaces/interface/config/name -/sampling/sflow/interfaces/interface/config/enabled -/sampling/sflow/interfaces/interface/config/egress-sampling-rate -/sampling/sflow/interfaces/interface/config/ingress-sampling-rate -/sampling/sflow/interfaces/interface/config/polling-interval - -/sampling/sflow/collectors/collector/address -/sampling/sflow/collectors/collector/config/address -/sampling/sflow/collectors/collector/config/network-instance -/sampling/sflow/collectors/collector/config/port -/sampling/sflow/collectors/collector/config/source-address -/sampling/sflow/collectors/collector/port - -## Telemetry Parameter coverage - -/sampling/sflow/state/agent-id-ipv4 -/sampling/sflow/state/agent-id-ipv6 -/sampling/sflow/state/dscp -/sampling/sflow/state/egress-sampling-rate -/sampling/sflow/state/enabled -/sampling/sflow/state/ingress-sampling-rate -/sampling/sflow/state/polling-interval -/sampling/sflow/state/sample-size -/sampling/sflow/state/source-address -/sampling/sflow/interfaces/interface/state/name -/sampling/sflow/interfaces/interface/state/enabled -/sampling/sflow/interfaces/interface/state/egress-sampling-rate -/sampling/sflow/interfaces/interface/state/ingress-sampling-rate -/sampling/sflow/interfaces/interface/state/polling-interval - -/sampling/sflow/collectors/collector/address -/sampling/sflow/collectors/collector/state/address -/sampling/sflow/collectors/collector/state/network-instance -/sampling/sflow/collectors/collector/state/port -/sampling/sflow/collectors/collector/state/source-address -/sampling/sflow/collectors/collector/port - -## Protocol/RPC Parameter coverage - -N/A +## OpenConfig Path and RPC Coverage + +```yaml +paths: + ## Config Parameter coverage + /sampling/sflow/config/agent-id-ipv4: + /sampling/sflow/config/agent-id-ipv6: + /sampling/sflow/config/dscp: + /sampling/sflow/config/egress-sampling-rate: + /sampling/sflow/config/enabled: + /sampling/sflow/config/ingress-sampling-rate: + /sampling/sflow/config/polling-interval: + /sampling/sflow/config/sample-size: + /sampling/sflow/interfaces/interface/config/name: + /sampling/sflow/interfaces/interface/config/enabled: + /sampling/sflow/interfaces/interface/config/egress-sampling-rate: + /sampling/sflow/interfaces/interface/config/ingress-sampling-rate: + /sampling/sflow/interfaces/interface/config/polling-interval: + + /sampling/sflow/collectors/collector/config/address: + /sampling/sflow/collectors/collector/config/network-instance: + /sampling/sflow/collectors/collector/config/port: + /sampling/sflow/collectors/collector/config/source-address: + + ## Telemetry Parameter coverage + /sampling/sflow/state/agent-id-ipv4: + /sampling/sflow/state/agent-id-ipv6: + /sampling/sflow/state/dscp: + /sampling/sflow/state/egress-sampling-rate: + /sampling/sflow/state/enabled: + /sampling/sflow/state/ingress-sampling-rate: + /sampling/sflow/state/polling-interval: + /sampling/sflow/state/sample-size: + /sampling/sflow/interfaces/interface/state/name: + /sampling/sflow/interfaces/interface/state/enabled: + /sampling/sflow/interfaces/interface/state/egress-sampling-rate: + /sampling/sflow/interfaces/interface/state/ingress-sampling-rate: + /sampling/sflow/interfaces/interface/state/polling-interval: + + /sampling/sflow/collectors/collector/address: + /sampling/sflow/collectors/collector/state/address: + /sampling/sflow/collectors/collector/state/network-instance: + /sampling/sflow/collectors/collector/state/port: + /sampling/sflow/collectors/collector/state/source-address: + /sampling/sflow/collectors/collector/port: + +rpcs: + gnmi: + gNMI.Set: + gNMI.Subscribe: +``` ## Minimum DUT platform requirement diff --git a/feature/sflow/otg_tests/sflow_base_test/metadata.textproto b/feature/sflow/otg_tests/sflow_base_test/metadata.textproto index d34f121c0cb..362a5a39bb7 100644 --- a/feature/sflow/otg_tests/sflow_base_test/metadata.textproto +++ b/feature/sflow/otg_tests/sflow_base_test/metadata.textproto @@ -34,5 +34,6 @@ platform_exceptions: { interface_enabled: true default_network_instance: "default" static_protocol_name: "STATIC" + sflow_source_address_update_unsupported: true } } diff --git a/feature/sflow/otg_tests/sflow_base_test/sflow_base_test.go b/feature/sflow/otg_tests/sflow_base_test/sflow_base_test.go index a305c3e1035..f2c61917635 100644 --- a/feature/sflow/otg_tests/sflow_base_test/sflow_base_test.go +++ b/feature/sflow/otg_tests/sflow_base_test/sflow_base_test.go @@ -15,41 +15,58 @@ package sflow_base_test import ( + "fmt" + "net" + "os" "testing" + "time" + "github.com/google/gopacket" + "github.com/google/gopacket/layers" + "github.com/google/gopacket/pcap" + "github.com/open-traffic-generator/snappi/gosnappi" "github.com/openconfig/featureprofiles/internal/attrs" "github.com/openconfig/featureprofiles/internal/cfgplugins" "github.com/openconfig/featureprofiles/internal/deviations" "github.com/openconfig/featureprofiles/internal/fptest" + "github.com/openconfig/featureprofiles/internal/otgutils" "github.com/openconfig/ondatra" "github.com/openconfig/ondatra/gnmi" "github.com/openconfig/ondatra/gnmi/oc" + "github.com/openconfig/ondatra/netutil" "github.com/openconfig/ygot/ygot" ) const ( - ipv4PrefixLen = 30 - frameSize = 512 // size of packets in bytes to generate with ATE - packetsToSend = 10000000 // 10 million - ppsRate = 1000000 // 1 million - plenIPv4 = 30 - plenIPv6 = 126 - lossTolerance = 0 + ipv4PrefixLen = 30 + plenIPv4 = 30 + plenIPv6 = 126 + lossTolerance = 1 + mgmtVRF = "mvrf1" + sampleTolerance = 0.8 + samplingRate = 1000000 ) var ( - staticRoute = &cfgplugins.StaticRouteCfg{ - NetworkInstance: "DEFAULT", + staticRouteV4 = &cfgplugins.StaticRouteCfg{ + NetworkInstance: mgmtVRF, Prefix: "192.0.2.128/30", NextHops: map[string]oc.NetworkInstance_Protocol_Static_NextHop_NextHop_Union{ "0": oc.UnionString("192.0.2.6"), }, } + staticRouteV6 = &cfgplugins.StaticRouteCfg{ + NetworkInstance: mgmtVRF, + Prefix: "2001:db8::128/126", + NextHops: map[string]oc.NetworkInstance_Protocol_Static_NextHop_NextHop_Union{ + "1": oc.UnionString("2001:db8::6"), + }, + } dutSrc = &attrs.Attributes{ Desc: "DUT to ATE source", IPv4: "192.0.2.1", IPv4Len: plenIPv4, - IPv6: "2001:db8::2", + IPv6: "2001:db8::1", IPv6Len: plenIPv6, } dutDst = &attrs.Attributes{ @@ -59,37 +76,73 @@ var ( IPv6: "2001:db8::5", IPv6Len: plenIPv6, } -) - -func TestMain(m *testing.M) { - fptest.RunTests(m) -} - -// configInterfaceDUT configures the DUT interfaces. -func configInterfaceDUT(p1 *ondatra.Port, a *attrs.Attributes, dut *ondatra.DUTDevice) *oc.Interface { + ateSrc = &attrs.Attributes{ + Name: "ateSrc", + Desc: "ATE to DUT source", + IPv4: "192.0.2.2", + IPv4Len: plenIPv4, + IPv6: "2001:db8::2", + IPv6Len: plenIPv6, + MAC: "02:00:01:01:01:01", + } + ateDst = &attrs.Attributes{ + Name: "ateDst", + Desc: "ATE to DUT destination", + IPv4: "192.0.2.6", + IPv4Len: plenIPv4, + IPv6: "2001:db8::6", + IPv6Len: plenIPv6, + MAC: "02:00:02:01:01:01", + } - i := &oc.Interface{Name: ygot.String(p1.Name())} + loopbackSubIntfNum = 1 - i.Description = ygot.String(a.Desc) - i.Type = oc.IETFInterfaces_InterfaceType_ethernetCsmacd - if deviations.InterfaceEnabled(dut) { - i.Enabled = ygot.Bool(true) + dutlo0Attrs = attrs.Attributes{ + Desc: "Loopback ip", + IPv4: "203.0.113.1", + IPv6: "2001:db8::203:0:113:1", + IPv4Len: 32, + IPv6Len: 128, } - s := i.GetOrCreateSubinterface(0) - s4 := s.GetOrCreateIpv4() - if deviations.InterfaceEnabled(dut) && !deviations.IPv4MissingEnabled(dut) { - s4.Enabled = ygot.Bool(true) + flowConfigs = []flowConfig{ + { + name: "flowS", + packetsToSend: 1000000, + ppsRate: 100000, + frameSize: 64, + }, + { + name: "flowM", + packetsToSend: 1000000, + ppsRate: 100000, + frameSize: 512, + }, + { + name: "flowL", + packetsToSend: 1000000, + ppsRate: 100000, + frameSize: 1500, + }, } - s4.GetOrCreateAddress(a.IPv4).PrefixLength = ygot.Uint8(plenIPv4) +) - s6 := s.GetOrCreateIpv6() - if deviations.InterfaceEnabled(dut) { - s6.Enabled = ygot.Bool(true) - } - s6.GetOrCreateAddress(a.IPv6).PrefixLength = ygot.Uint8(plenIPv6) +type flowConfig struct { + name string + packetsToSend uint32 + ppsRate uint64 + frameSize uint32 +} + +type IPType string + +const ( + IPv4 = "IPv4" + IPv6 = "IPv6" +) - return i +func TestMain(m *testing.M) { + fptest.RunTests(m) } // configureDUTBaseline configures port1 and port2 on the DUT. @@ -98,10 +151,10 @@ func configureDUTBaseline(t *testing.T, dut *ondatra.DUTDevice) { d := gnmi.OC() p1 := dut.Port(t, "port1") - gnmi.Replace(t, dut, d.Interface(p1.Name()).Config(), configInterfaceDUT(p1, dutSrc, dut)) + gnmi.Replace(t, dut, d.Interface(p1.Name()).Config(), dutSrc.NewOCInterface(p1.Name(), dut)) p2 := dut.Port(t, "port2") - gnmi.Replace(t, dut, d.Interface(p2.Name()).Config(), configInterfaceDUT(p2, dutDst, dut)) + gnmi.Replace(t, dut, d.Interface(p2.Name()).Config(), dutDst.NewOCInterface(p2.Name(), dut)) if deviations.ExplicitPortSpeed(dut) { fptest.SetPortSpeed(t, p1) @@ -114,25 +167,48 @@ func configureDUTBaseline(t *testing.T, dut *ondatra.DUTDevice) { } // TestSFlowTraffic configures a DUT for sFlow client and collector endpoint and uses ATE to send -// traffic which the DUT should sample and send sFlow packets to a collector. ATE captures the +// traffic which the DUT should sample and send sFlow packets to a collector. ATE captures the // sflow packets which are decoded by the test to verify they are valid sflow packets. func TestSFlowTraffic(t *testing.T) { dut := ondatra.DUT(t, "dut") + p1 := dut.Port(t, "port1") + p2 := dut.Port(t, "port2") - // configure interfaces on DUT - // TODO: consider refactoring interface configs into cfgplugins - configureDUTBaseline(t, dut) + ate := ondatra.ATE(t, "ate") + + switch dut.Vendor() { + case ondatra.JUNIPER: + loopbackSubIntfNum = 0 + } + + loopbackIntfName := netutil.LoopbackInterface(t, dut, loopbackSubIntfNum) + + // Configure DUT + if !deviations.InterfaceConfigVRFBeforeAddress(dut) { + configureDUTBaseline(t, dut) + configureLoopbackOnDUT(t, dut) + } - srBatch := &gnmi.SetBatch{} fptest.ConfigureDefaultNetworkInstance(t, dut) - cfgplugins.NewStaticRouteCfg(srBatch, staticRoute, dut) - srBatch.Set(t, dut) + addInterfacesToVRF(t, dut, mgmtVRF, []string{p1.Name(), p2.Name(), loopbackIntfName}) - sfBatch := &gnmi.SetBatch{} - cfgplugins.NewSFlowGlobalCfg(sfBatch, nil, dut) - cfgplugins.NewSFlowCollector(sfBatch, nil, dut) + // For interface configuration, Arista prefers config Vrf first then the IP address + if deviations.InterfaceConfigVRFBeforeAddress(dut) { + configureDUTBaseline(t, dut) + configureLoopbackOnDUT(t, dut) + } + + config := configureATE(t, ate) + otgutils.WaitForARP(t, ate.OTG(), config, "IPv4") + + srBatch := &gnmi.SetBatch{} + cfgplugins.NewStaticRouteCfg(srBatch, staticRouteV4, dut) + cfgplugins.NewStaticRouteCfg(srBatch, staticRouteV6, dut) + srBatch.Set(t, dut) t.Run("SFLOW-1.1_ReplaceDUTConfigSFlow", func(t *testing.T) { + sfBatch := &gnmi.SetBatch{} + cfgplugins.NewSFlowGlobalCfg(t, sfBatch, nil, dut, mgmtVRF, loopbackIntfName, dutlo0Attrs.IPv4, dutlo0Attrs.IPv6) sfBatch.Set(t, dut) gotSamplingConfig := gnmi.Get(t, dut, gnmi.OC().Sampling().Sflow().Config()) @@ -148,6 +224,7 @@ func TestSFlowTraffic(t *testing.T) { } t.Logf("Got sampling config: %v", json) }) + /* TODO: implement this when a suitable ygot.diffBatch function exists // Validate DUT sampling config matches what we set it to diff, err := ygot.Diff(gotSamplingConfig, sfBatch) @@ -159,6 +236,223 @@ func TestSFlowTraffic(t *testing.T) { } }) */ - // TODO: Configure ATE - // TODO: Send traffic, capture and decode + + t.Run("SFLOW-1.2_TestFlowFixed", func(t *testing.T) { + t.Run("SFLOW-1.2.1_IPv4", func(t *testing.T) { + enableCapture(t, ate, config, IPv4) + testFlowFixed(t, ate, config, IPv4) + }) + t.Run("SFLOW-1.2.2_IPv6", func(t *testing.T) { + enableCapture(t, ate, config, IPv6) + testFlowFixed(t, ate, config, IPv6) + }) + }) +} + +func testFlowFixed(t *testing.T, ate *ondatra.ATEDevice, config gosnappi.Config, ip IPType) { + for _, fc := range flowConfigs { + flowName := string(ip) + fc.name + t.Run(flowName, func(t *testing.T) { + createFlow(t, ate, config, fc, ip) + + cs := startCapture(t, ate, config) + + sleepTime := time.Duration(fc.packetsToSend/uint32(fc.ppsRate)) + 5 + ate.OTG().StartTraffic(t) + time.Sleep(sleepTime * time.Second) + ate.OTG().StopTraffic(t) + + stopCapture(t, ate, cs) + + otgutils.LogFlowMetrics(t, ate.OTG(), config) + otgutils.LogPortMetrics(t, ate.OTG(), config) + + loss := otgutils.GetFlowLossPct(t, ate.OTG(), flowName, 10*time.Second) + if loss > lossTolerance { + t.Errorf("Loss percent for IPv4 Traffic: got: %f, want %f", loss, float64(lossTolerance)) + } + + processCapture(t, ate, config, ip, fc) + }) + } +} + +func startCapture(t *testing.T, ate *ondatra.ATEDevice, config gosnappi.Config) gosnappi.ControlState { + t.Helper() + + cs := gosnappi.NewControlState() + cs.Port().Capture().SetState(gosnappi.StatePortCaptureState.START) + ate.OTG().SetControlState(t, cs) + + return cs +} + +func stopCapture(t *testing.T, ate *ondatra.ATEDevice, cs gosnappi.ControlState) { + t.Helper() + cs.Port().Capture().SetState(gosnappi.StatePortCaptureState.STOP) + ate.OTG().SetControlState(t, cs) +} + +func processCapture(t *testing.T, ate *ondatra.ATEDevice, config gosnappi.Config, ip IPType, fc flowConfig) { + bytes := ate.OTG().GetCapture(t, gosnappi.NewCaptureRequest().SetPortName(config.Ports().Items()[1].Name())) + time.Sleep(30 * time.Second) + pcapFile, err := os.CreateTemp("", "pcap") + if err != nil { + t.Errorf("ERROR: Could not create temporary pcap file: %v\n", err) + } + if _, err := pcapFile.Write(bytes); err != nil { + t.Errorf("ERROR: Could not write bytes to pcap file: %v\n", err) + } + pcapFile.Close() + validatePackets(t, pcapFile.Name(), ip, fc) +} + +func configureATE(t *testing.T, ate *ondatra.ATEDevice) gosnappi.Config { + config := gosnappi.NewConfig() + p1 := ate.Port(t, "port1") + p2 := ate.Port(t, "port2") + ateSrc.AddToOTG(config, p1, dutSrc) + ateDst.AddToOTG(config, p2, dutDst) + + ate.OTG().PushConfig(t, config) + ate.OTG().StartProtocols(t) + + return config +} + +func enableCapture(t *testing.T, ate *ondatra.ATEDevice, config gosnappi.Config, ip IPType) { + t.Helper() + + config.Captures().Clear() + // enable packet capture on this port + cap := config.Captures().Add().SetName("sFlowpacketCapture"). + SetPortNames([]string{config.Ports().Items()[1].Name()}). + SetFormat(gosnappi.CaptureFormat.PCAP) + filter := cap.Filters().Add() + if ip == IPv4 { + // filter on hex value of IPv4 - 203.0.113.1 + filter.Ipv4().Src().SetValue("cb007101") + } else { + // filter on hex value of IPv6 - 2001:db8::203:0:113:1 + filter.Ipv6().Src().SetValue("20010db8000000000203000001130001") + } + + ate.OTG().PushConfig(t, config) + ate.OTG().StartProtocols(t) + + pb, _ := config.Marshal().ToProto() + t.Log(pb.GetCaptures()) +} + +func addInterfacesToVRF(t *testing.T, dut *ondatra.DUTDevice, vrfname string, intfNames []string) { + root := &oc.Root{} + mgmtNI := root.GetOrCreateNetworkInstance(vrfname) + mgmtNI.Type = oc.NetworkInstanceTypes_NETWORK_INSTANCE_TYPE_L3VRF + for _, intfName := range intfNames { + vi := mgmtNI.GetOrCreateInterface(intfName) + vi.Interface = ygot.String(intfName) + vi.Subinterface = ygot.Uint32(0) + } + gnmi.Replace(t, dut, gnmi.OC().NetworkInstance(mgmtVRF).Config(), mgmtNI) + t.Logf("Added interface %v to VRF %s", intfNames, vrfname) +} + +func configureLoopbackOnDUT(t *testing.T, dut *ondatra.DUTDevice) { + loopbackIntfName := netutil.LoopbackInterface(t, dut, loopbackSubIntfNum) + loop := dutlo0Attrs.NewOCInterface(loopbackIntfName, dut) + loop.Type = oc.IETFInterfaces_InterfaceType_softwareLoopback + loop.Description = ygot.String(fmt.Sprintf("Port %s", loopbackIntfName)) + gnmi.Update(t, dut, gnmi.OC().Interface(loopbackIntfName).Config(), loop) + t.Logf("Got DUT IPv4, IPv6 loopback address: %v, %v", dutlo0Attrs.IPv4, dutlo0Attrs.IPv6) +} + +func createFlow(t *testing.T, ate *ondatra.ATEDevice, config gosnappi.Config, fc flowConfig, ip IPType) { + config.Flows().Clear() + + t.Log("Configuring traffic flow") + flow := config.Flows().Add().SetName(string(ip) + fc.name) + flow.Metrics().SetEnable(true) + flow.Size().SetFixed(fc.frameSize) + flow.Rate().SetPps(fc.ppsRate) + flow.Duration().FixedPackets().SetPackets(fc.packetsToSend) + e1 := flow.Packet().Add().Ethernet() + e1.Src().SetValues([]string{ateSrc.MAC}) + + switch ip { + case IPv4: + flow.TxRx().Device(). + SetTxNames([]string{"ateSrc.IPv4"}). + SetRxNames([]string{"ateDst.IPv4"}) + v4 := flow.Packet().Add().Ipv4() + v4.Src().SetValue(ateSrc.IPv4) + v4.Dst().SetValue(ateDst.IPv4) + case IPv6: + flow.TxRx().Device(). + SetTxNames([]string{"ateSrc.IPv6"}). + SetRxNames([]string{"ateDst.IPv6"}) + v6 := flow.Packet().Add().Ipv6() + v6.Src().SetValue(ateSrc.IPv6) + v6.Dst().SetValue(ateDst.IPv6) + } + + ate.OTG().PushConfig(t, config) + ate.OTG().StartProtocols(t) +} + +func validatePackets(t *testing.T, filename string, ip IPType, fc flowConfig) { + handle, err := pcap.OpenOffline(filename) + if err != nil { + t.Fatal(err) + } + defer handle.Close() + + loopbackIP := net.ParseIP(dutlo0Attrs.IPv4) + if ip == IPv6 { + loopbackIP = net.ParseIP(dutlo0Attrs.IPv6) + } + packetSource := gopacket.NewPacketSource(handle, handle.LinkType()) + + found := false + packetCount := 0 + sflowSamples := uint32(0) + for packet := range packetSource.Packets() { + if ipLayer := packet.Layer(layers.LayerTypeIPv4); ipLayer != nil { + ipv4, _ := ipLayer.(*layers.IPv4) + if ipv4.SrcIP.Equal(loopbackIP) { + t.Logf("tos %d, payload %d, content %d, length %d", ipv4.TOS, len(ipv4.Payload), len(ipv4.Contents), ipv4.Length) + if ipv4.TOS == 32 { + found = true + break + } + } + } else if ipLayer := packet.Layer(layers.LayerTypeIPv6); ipLayer != nil { + ipv6, _ := ipLayer.(*layers.IPv6) + if ipv6.SrcIP.Equal(loopbackIP) { + t.Logf("tos %d, payload %d, content %d, length %d", ipv6.TrafficClass, len(ipv6.Payload), len(ipv6.Contents), ipv6.Length) + if ipv6.TrafficClass == 32 { + found = true + break + } + } + } + + } + if !found { + t.Error("sflow packets not found") + } + + for packet := range packetSource.Packets() { + if sflowLayer := packet.Layer(layers.LayerTypeSFlow); sflowLayer != nil { + sflow := sflowLayer.(*layers.SFlowDatagram) + packetCount++ + sflowSamples += sflow.SampleCount + t.Logf("SFlow Packet count: %v - SampleCount: %v", packetCount, sflowSamples) + } + } + + expectedSampleCount := float64(fc.packetsToSend / samplingRate) + minAllowedSamples := expectedSampleCount * sampleTolerance + if sflowSamples < uint32(minAllowedSamples) { + t.Errorf("SFlow sample count %v, want > %v", sflowSamples, expectedSampleCount) + } } diff --git a/feature/staticroute/otg_tests/basic_static_route_support_test/README.md b/feature/staticroute/otg_tests/basic_static_route_support_test/README.md index a50aa04c701..1127cffe981 100644 --- a/feature/staticroute/otg_tests/basic_static_route_support_test/README.md +++ b/feature/staticroute/otg_tests/basic_static_route_support_test/README.md @@ -16,8 +16,8 @@ #### Initial Setup: -* Connect DUT port-1, port-2 and port-3 to ATE port-1, port-2 and port-3 - respectively +* Connect DUT port-1, port-2, port-3 and port-4 to ATE port-1, port-2, port-3 + and port-4 respectively * Configure IPv4/IPv6 addresses on DUT and ATE the interfaces * Configure one IPv4 destination i.e. `ipv4-network = 203.0.113.0/24` connected to ATE port 1 and 2 @@ -177,9 +177,24 @@ 203.0.113.0/24` and `ipv6-network 2001:db8:128:128::/64` * Validate that traffic is NOT received from DUT +### RT-1.26.9 + +#### Test to validate add and remove to next-hops in a static route + +* Configure one IPv4 static route i.e. ipv4-route with the next hop set to the + IPv4 address of ATE port-2(0 index) and port-3(1 index). +* Validate next-hops of `ipv4-route` static route and indexes. +* Update IPv4 static route i.e. ipv4-route with the next hop set to the IPv4 + address of ATE port-1(0 index), port-2(1 index), port-3(2 index) and + port-4(3 index). +* Validate next-hops of `ipv4-route` static route and indexes. +* Remove two next hops at index 0 and 3 added in previous step. +* Validate next-hops of `ipv4-route` static route and indexes. + ## OpenConfig Path and RPC Coverage -The below yaml defines the OC paths intended to be covered by this test. OC paths used for test setup are not listed here. +The below yaml defines the OC paths intended to be covered by this test. OC +paths used for test setup are not listed here. ```yaml paths: diff --git a/feature/staticroute/otg_tests/basic_static_route_support_test/basic_static_route_support_test.go b/feature/staticroute/otg_tests/basic_static_route_support_test/basic_static_route_support_test.go index fbfd8da98ef..932e28281af 100644 --- a/feature/staticroute/otg_tests/basic_static_route_support_test/basic_static_route_support_test.go +++ b/feature/staticroute/otg_tests/basic_static_route_support_test/basic_static_route_support_test.go @@ -102,6 +102,23 @@ var ( IPv6: "2001:db8::192:0:2:a", IPv6Len: ipv6PrefixLen, } + + dutPort4 = attrs.Attributes{ + Desc: "dutPort4", + IPv4: "192.0.2.13", + IPv4Len: ipv4PrefixLen, + IPv6: "2001:db8::192:0:2:d", + IPv6Len: ipv6PrefixLen, + } + + atePort4 = attrs.Attributes{ + Name: "atePort4", + MAC: "02:00:01:01:01:04", + IPv4: "192.0.2.14", + IPv4Len: ipv4PrefixLen, + IPv6: "2001:db8::192:0:2:e", + IPv6Len: ipv6PrefixLen, + } ) func TestMain(m *testing.M) { @@ -209,6 +226,92 @@ func TestBasicStaticRouteSupport(t *testing.T) { } } +func TestStaticRouteAddRemove(t *testing.T) { + dut := ondatra.DUT(t, "dut") + configureDUT(t, dut) + + ate := ondatra.ATE(t, "ate") + top := gosnappi.NewConfig() + configureOTG(t, ate, top) + + ate.OTG().PushConfig(t, top) + ate.OTG().StartProtocols(t) + defer ate.OTG().StopProtocols(t) + otgutils.WaitForARP(t, ate.OTG(), top, "IPv4") + + prefix := ipAddr{address: v4Route, prefix: v4RoutePrefix} + b := &gnmi.SetBatch{} + sV4 := &cfgplugins.StaticRouteCfg{ + NetworkInstance: deviations.DefaultNetworkInstance(dut), + Prefix: prefix.cidr(t), + NextHops: map[string]oc.NetworkInstance_Protocol_Static_NextHop_NextHop_Union{ + "0": oc.UnionString(atePort2.IPv4), + "1": oc.UnionString(atePort3.IPv4), + }, + } + if _, err := cfgplugins.NewStaticRouteCfg(b, sV4, dut); err != nil { + t.Fatalf("Failed to configure IPv4 static route: %v", err) + } + b.Set(t, dut) + validateStaticRoute(t, dut, prefix.cidr(t), sV4) + + // add 2 new nextHops, one at 0 index and another at 3 index + b = &gnmi.SetBatch{} + sV4 = &cfgplugins.StaticRouteCfg{ + NetworkInstance: deviations.DefaultNetworkInstance(dut), + Prefix: prefix.cidr(t), + NextHops: map[string]oc.NetworkInstance_Protocol_Static_NextHop_NextHop_Union{ + "0": oc.UnionString(atePort1.IPv4), + "1": oc.UnionString(atePort2.IPv4), + "2": oc.UnionString(atePort3.IPv4), + "3": oc.UnionString(atePort4.IPv4), + }, + } + if _, err := cfgplugins.NewStaticRouteCfg(b, sV4, dut); err != nil { + t.Fatalf("Failed to configure IPv4 static route: %v", err) + } + b.Set(t, dut) + validateStaticRoute(t, dut, prefix.cidr(t), sV4) + + // remove previously added indexes + b = &gnmi.SetBatch{} + sV4 = &cfgplugins.StaticRouteCfg{ + NetworkInstance: deviations.DefaultNetworkInstance(dut), + Prefix: prefix.cidr(t), + NextHops: map[string]oc.NetworkInstance_Protocol_Static_NextHop_NextHop_Union{ + "0": oc.UnionString(atePort2.IPv4), + "1": oc.UnionString(atePort3.IPv4), + }, + } + if _, err := cfgplugins.NewStaticRouteCfg(b, sV4, dut); err != nil { + t.Fatalf("Failed to configure IPv4 static route: %v", err) + } + b.Set(t, dut) + validateStaticRoute(t, dut, prefix.cidr(t), sV4) +} + +func validateStaticRoute(t *testing.T, dut *ondatra.DUTDevice, prefix string, sV4 *cfgplugins.StaticRouteCfg) { + sp := gnmi.OC().NetworkInstance(deviations.DefaultNetworkInstance(dut)).Protocol(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_STATIC, deviations.StaticProtocolName(dut)) + gnmi.Await(t, dut, sp.Static(prefix).Prefix().State(), 120*time.Second, prefix) + + if deviations.SkipStaticNexthopCheck(dut) { + nexthops := gnmi.LookupAll(t, dut, sp.Static(prefix).NextHopAny().NextHop().State()) + if got, want := len(nexthops), len(sV4.NextHops); got != want { + t.Errorf("Static route next hop count - %s: got: %v, want: %v", prefix, got, want) + } + } else { + // Validate both the routes i.e. ipv4-route-[a|b] are configured and reported + // correctly + gotStatic := gnmi.Get(t, dut, sp.Static(prefix).State()) + t.Logf("Static route %s: got: %v, want: %v", prefix, len(gotStatic.NextHop), len(sV4.NextHops)) + for index, nextHop := range gotStatic.NextHop { + if got, want := nextHop.GetNextHop(), sV4.NextHops[index]; got != want { + t.Errorf("Static route %s: got: %v, want: %v", prefix, got, want) + } + } + } +} + func TestDisableRecursiveNextHopResolution(t *testing.T) { dut := ondatra.DUT(t, "dut") if deviations.UnsupportedStaticRouteNextHopRecurse(dut) { @@ -1208,23 +1311,29 @@ func configureDUT(t *testing.T, dut *ondatra.DUTDevice) { p1 := dut.Port(t, "port1") p2 := dut.Port(t, "port2") p3 := dut.Port(t, "port3") + p4 := dut.Port(t, "port4") b := &gnmi.SetBatch{} i1 := dutPort1.NewOCInterface(p1.Name(), dut) i2 := dutPort2.NewOCInterface(p2.Name(), dut) i3 := dutPort3.NewOCInterface(p3.Name(), dut) + i4 := dutPort4.NewOCInterface(p4.Name(), dut) if deviations.IPv6StaticRouteWithIPv4NextHopRequiresStaticARP(dut) { i1.GetOrCreateSubinterface(0).GetOrCreateIpv6().GetOrCreateNeighbor(dummyV6).LinkLayerAddress = ygot.String(dummyMAC) i2.GetOrCreateSubinterface(0).GetOrCreateIpv6().GetOrCreateNeighbor(dummyV6).LinkLayerAddress = ygot.String(dummyMAC) + i3.GetOrCreateSubinterface(0).GetOrCreateIpv6().GetOrCreateNeighbor(dummyV6).LinkLayerAddress = ygot.String(dummyMAC) + i4.GetOrCreateSubinterface(0).GetOrCreateIpv6().GetOrCreateNeighbor(dummyV6).LinkLayerAddress = ygot.String(dummyMAC) } gnmi.BatchReplace(b, gnmi.OC().Interface(p1.Name()).Config(), i1) gnmi.BatchReplace(b, gnmi.OC().Interface(p2.Name()).Config(), i2) gnmi.BatchReplace(b, gnmi.OC().Interface(p3.Name()).Config(), i3) + gnmi.BatchReplace(b, gnmi.OC().Interface(p4.Name()).Config(), i4) b.Set(t, dut) if deviations.ExplicitPortSpeed(dut) { fptest.SetPortSpeed(t, p1) fptest.SetPortSpeed(t, p2) fptest.SetPortSpeed(t, p3) + fptest.SetPortSpeed(t, p4) } fptest.ConfigureDefaultNetworkInstance(t, dut) @@ -1233,6 +1342,7 @@ func configureDUT(t *testing.T, dut *ondatra.DUTDevice) { fptest.AssignToNetworkInstance(t, dut, p1.Name(), deviations.DefaultNetworkInstance(dut), 0) fptest.AssignToNetworkInstance(t, dut, p2.Name(), deviations.DefaultNetworkInstance(dut), 0) fptest.AssignToNetworkInstance(t, dut, p3.Name(), deviations.DefaultNetworkInstance(dut), 0) + fptest.AssignToNetworkInstance(t, dut, p4.Name(), deviations.DefaultNetworkInstance(dut), 0) } } @@ -1241,11 +1351,13 @@ func configureOTG(t *testing.T, ate *ondatra.ATEDevice, top gosnappi.Config) []g p1 := ate.Port(t, "port1") p2 := ate.Port(t, "port2") p3 := ate.Port(t, "port3") + p4 := ate.Port(t, "port4") d1 := atePort1.AddToOTG(top, p1, &dutPort1) d2 := atePort2.AddToOTG(top, p2, &dutPort2) d3 := atePort3.AddToOTG(top, p3, &dutPort3) - return []gosnappi.Device{d1, d2, d3} + d4 := atePort4.AddToOTG(top, p4, &dutPort4) + return []gosnappi.Device{d1, d2, d3, d4} } func (td *testData) advertiseRoutesWithISIS(t *testing.T) { diff --git a/feature/staticroute/otg_tests/basic_static_route_support_test/metadata.textproto b/feature/staticroute/otg_tests/basic_static_route_support_test/metadata.textproto index 34fb8af4eaf..af7f010bc52 100644 --- a/feature/staticroute/otg_tests/basic_static_route_support_test/metadata.textproto +++ b/feature/staticroute/otg_tests/basic_static_route_support_test/metadata.textproto @@ -36,7 +36,6 @@ platform_exceptions: { unsupported_static_route_next_hop_recurse: true static_route_with_explicit_metric: true interface_ref_config_unsupported: true - } } platform_exceptions: { diff --git a/feature/system/aaa/README.md b/feature/system/aaa/README.md new file mode 100644 index 00000000000..d91e7603bb4 --- /dev/null +++ b/feature/system/aaa/README.md @@ -0,0 +1,169 @@ +# SYS-3.1: AAA and TACACS+ Configuration Verification Test Suite + + +## Summary + +This test suite aims to thoroughly validate the correct implementation of the AAA (Authentication, Authorization, and Accounting) framework with TACACS+ and local authentication on a device. + +## Testbed type + +* [`featureprofiles/topologies/dut.testbed`](https://github.com/openconfig/featureprofiles/blob/main/topologies/dut.testbed) + +## Procedure + +### Test environment setup + +#### Configuration + +* Configure the loopback interface with IPv4 and IPv6 address and netmasks of /32, /64 respectively + +### SYS-3.1.1 User Configuration Test + +* Create a user on the DUT with the following parameters: + ```yaml + system: + aaa: + authentication: + users: + - user: + config: + username: "testuser" + password: "password" + role: SYSTEM_ROLE_ADMIN + ``` +* Verification: + * Get the device configuration via gNMI and verify the successful creation of the "testuser" account with the specified parameters. + +### SYS-3.1.2 TACACS+ Server Configuration Test + +* Configuration: + * Configure a TACACS server on the DUT as below: + * Host IP: 192.168.1.1 + * Port: 49 + * Key: tacacs_password + * Timeout: 4 + * Configure the source IP address of a selected interface for all outgoing TACACS+ packets as the loopback interface. + ```yaml + system: + aaa: + server-groups: + server-group: + config: + name: "my_server_group" + servers: + - server: + config: + name: "tacacs_server_1" + address: 192.168.1.1 + timeout: 4 + tacacs: + config: + port: 49 + source-address: dut_loopback_address + secret-key: acacs_password + ``` +* Verification: + * Get the device configuration via gNMI and verify that the TACACS+ server has been successfully created with the correct parameters. + +### SYS-3.1.3 AAA Authentication Configuration Test + +* Configuration: + * Configure the DUT to use TACACS+ as the primary authentication method and local authentication as a fallback option. + ```yaml + system: + aaa: + authentication: + config: + authentication-method: [TACACS_ALL, LOCAL] + ``` +* Verification: + * Use gNMI to get the device's current configuration and verify that the authentication settings match the intended design. + +### SYS-3.1.4 AAA Authorization Configuration Test + +* Configuration: + * Configure command authorization to exclusively utilize the TACACS+ server. + * Configure authorization for configuration mode to primarily use the TACACS+ server and fall back to local authorization if the TACACS+ server is unavailable or does not respond. + ```yaml + system: + aaa: + authorization: + config: + authorization-method: [TACACS_ALL, LOCAL] + events: + config: + - event-type: AAA_AUTHORIZATION_EVENT_COMMAND + - event-type: AAA_AUTHORIZATION_EVENT_CONFIG + ``` +* Verification: + * Use gNMI to Get the device's current configuration and verify its alignment with the intended authorization settings.. + +### SYS-3.1.5 AAA Accounting Configuration Test + +* Configuration: + * Activate accounting for command line interface (CLI) commands on the device under test (DUT). + * Activate accounting for login sessions on the DUT. + * Activate accounting for system event logs on the DUT. + ```yaml + system: + aaa: + accounting: + config: + name: "my_server_group" + accounting-method: TACACS_ALL + events: + config: + - event-type: AAA_ACCOUNTING_EVENT_COMMAND + record: START_STOP + - event-type: AAA_ACCOUNTING_EVENT_LOGIN + record: START_STOP + ``` +* Verification: + * Use gNMI to get the device's configuration and validate that the accounting settings are correctly implemented as intended. + +## OpenConfig Path and RPC Coverage + +The below yaml defines the OC paths intended to be covered by this test. + +```yaml +paths: + ## Config paths + /system/aaa/authentication/users/user/config/username: + /system/aaa/authentication/users/user/config/password-hashed: + /system/aaa/authentication/users/user/config/role: + /system/aaa/authorization/config/authorization-method: + /system/aaa/accounting/config/accounting-method: + /system/aaa/accounting/events/event/config/event-type: + /system/aaa/accounting/events/event/config/record: + /system/aaa/server-groups/server-group/servers/server/config/address: + /system/aaa/server-groups/server-group/servers/server/config/timeout: + /system/aaa/server-groups/server-group/servers/server/tacacs/config/port: + /system/aaa/server-groups/server-group/servers/server/tacacs/config/secret-key: + /system/aaa/server-groups/server-group/servers/server/tacacs/config/secret-key-hashed: + /system/aaa/server-groups/server-group/servers/server/tacacs/config/source-address: + + ## State paths + /system/aaa/authentication/users/user/state/username: + /system/aaa/authentication/users/user/state/password-hashed: + /system/aaa/authentication/users/user/state/role: + /system/aaa/authorization/state/authorization-method: + /system/aaa/accounting/state/accounting-method: + /system/aaa/accounting/events/event/state/event-type: + /system/aaa/accounting/events/event/state/record: + /system/aaa/server-groups/server-group/servers/server/state/address: + /system/aaa/server-groups/server-group/servers/server/state/timeout: + /system/aaa/server-groups/server-group/servers/server/tacacs/state/port: + /system/aaa/server-groups/server-group/servers/server/tacacs/state/secret-key: + /system/aaa/server-groups/server-group/servers/server/tacacs/state/secret-key-hashed: + /system/aaa/server-groups/server-group/servers/server/tacacs/state/source-address: + + +rpcs: + gnmi: + gNMI.Set: + gNMI.Subscribe: +``` + +## Minimum DUT platform requirement + +* VRX diff --git a/feature/experimental/system/gnmi/benchmarking/internal/setup/setup.go b/feature/system/gnmi/benchmarking/internal/setup/setup.go similarity index 100% rename from feature/experimental/system/gnmi/benchmarking/internal/setup/setup.go rename to feature/system/gnmi/benchmarking/internal/setup/setup.go diff --git a/feature/experimental/system/gnmi/benchmarking/otg_tests/drained_configuration_convergence_time/README.md b/feature/system/gnmi/benchmarking/otg_tests/drained_configuration_convergence_time/README.md similarity index 59% rename from feature/experimental/system/gnmi/benchmarking/otg_tests/drained_configuration_convergence_time/README.md rename to feature/system/gnmi/benchmarking/otg_tests/drained_configuration_convergence_time/README.md index 80b76298f1e..43312a43c90 100644 --- a/feature/experimental/system/gnmi/benchmarking/otg_tests/drained_configuration_convergence_time/README.md +++ b/feature/system/gnmi/benchmarking/otg_tests/drained_configuration_convergence_time/README.md @@ -35,21 +35,24 @@ defined in the case): * Measure time between t=0 and all BGP received routes on ATE to report changed metric. -## Config Parameter coverage - - * BGP - * /routing-policy/policy-definitions/policy-definition/statements/statement/actions/bgp-actions/config/set-med - * /routing-policy/policy-definitions/policy-definition/statements/statement/actions/bgp-actions/set-as-path-prepend/config/repeat-n - * /routing-policy/policy-definitions/policy-definition/statements/statement/actions/bgp-actions/set-as-path-prepend/config/as-number - - * ISIS - * /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/afi-safi/af/state/metric - * /network-instances/network-instance/protocols/protocol/isis/global/lsp-bit/overload-bit/state/set-bit - -## Telemetry Parameter coverage - - * ISIS - * /interfaces/interfaces/levels/level/adjacencies/adjacency/state/adjacency-state - * BGP - * /afi-safis/afi-safi/state/prefixes/sent - * /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor +## OpenConfig Path and RPC Coverage + +The below yaml defines the OC paths intended to be covered by this test. OC +paths used for test setup are not listed here. + +```yaml +paths: + ## Config Parameter coverage + /routing-policy/policy-definitions/policy-definition/statements/statement/actions/bgp-actions/config/set-med: + /routing-policy/policy-definitions/policy-definition/statements/statement/actions/bgp-actions/set-as-path-prepend/config/repeat-n: + /routing-policy/policy-definitions/policy-definition/statements/statement/actions/bgp-actions/set-as-path-prepend/config/asn: + /network-instances/network-instance/protocols/protocol/isis/interfaces/interface/levels/level/afi-safi/af/state/metric: + /network-instances/network-instance/protocols/protocol/isis/global/lsp-bit/overload-bit/state/set-bit: + + ## Telemetry Parameter coverage + /network-instances/network-instance/protocols/protocol/bgp/neighbors/neighbor/afi-safis/afi-safi/state/prefixes/sent: +rpcs: + gnmi: + gNMI.Subscribe: + gNMI.Set: +``` diff --git a/feature/experimental/system/gnmi/benchmarking/otg_tests/drained_configuration_convergence_time/drained_configuration_convergence_time_bgp_test.go b/feature/system/gnmi/benchmarking/otg_tests/drained_configuration_convergence_time/drained_configuration_convergence_time_bgp_test.go similarity index 99% rename from feature/experimental/system/gnmi/benchmarking/otg_tests/drained_configuration_convergence_time/drained_configuration_convergence_time_bgp_test.go rename to feature/system/gnmi/benchmarking/otg_tests/drained_configuration_convergence_time/drained_configuration_convergence_time_bgp_test.go index 3b12bc1d5e5..53bdf999d3f 100644 --- a/feature/experimental/system/gnmi/benchmarking/otg_tests/drained_configuration_convergence_time/drained_configuration_convergence_time_bgp_test.go +++ b/feature/system/gnmi/benchmarking/otg_tests/drained_configuration_convergence_time/drained_configuration_convergence_time_bgp_test.go @@ -21,7 +21,7 @@ import ( "time" "github.com/google/go-cmp/cmp" - "github.com/openconfig/featureprofiles/feature/experimental/system/gnmi/benchmarking/internal/setup" + "github.com/openconfig/featureprofiles/feature/system/gnmi/benchmarking/internal/setup" "github.com/openconfig/featureprofiles/internal/deviations" "github.com/openconfig/featureprofiles/internal/fptest" "github.com/openconfig/ondatra" diff --git a/feature/experimental/system/gnmi/benchmarking/otg_tests/drained_configuration_convergence_time/drained_configuration_convergence_time_isis_test.go b/feature/system/gnmi/benchmarking/otg_tests/drained_configuration_convergence_time/drained_configuration_convergence_time_isis_test.go similarity index 98% rename from feature/experimental/system/gnmi/benchmarking/otg_tests/drained_configuration_convergence_time/drained_configuration_convergence_time_isis_test.go rename to feature/system/gnmi/benchmarking/otg_tests/drained_configuration_convergence_time/drained_configuration_convergence_time_isis_test.go index e8bf2d5cfd2..fbdbba61792 100644 --- a/feature/experimental/system/gnmi/benchmarking/otg_tests/drained_configuration_convergence_time/drained_configuration_convergence_time_isis_test.go +++ b/feature/system/gnmi/benchmarking/otg_tests/drained_configuration_convergence_time/drained_configuration_convergence_time_isis_test.go @@ -20,7 +20,7 @@ import ( "testing" "time" - "github.com/openconfig/featureprofiles/feature/experimental/system/gnmi/benchmarking/internal/setup" + "github.com/openconfig/featureprofiles/feature/system/gnmi/benchmarking/internal/setup" "github.com/openconfig/featureprofiles/internal/deviations" "github.com/openconfig/ondatra" "github.com/openconfig/ondatra/gnmi" diff --git a/feature/experimental/system/gnmi/benchmarking/otg_tests/drained_configuration_convergence_time/metadata.textproto b/feature/system/gnmi/benchmarking/otg_tests/drained_configuration_convergence_time/metadata.textproto similarity index 100% rename from feature/experimental/system/gnmi/benchmarking/otg_tests/drained_configuration_convergence_time/metadata.textproto rename to feature/system/gnmi/benchmarking/otg_tests/drained_configuration_convergence_time/metadata.textproto diff --git a/feature/experimental/system/gnmi/benchmarking/tests/full_configuration_replace_test/README.md b/feature/system/gnmi/benchmarking/tests/full_configuration_replace_test/README.md similarity index 100% rename from feature/experimental/system/gnmi/benchmarking/tests/full_configuration_replace_test/README.md rename to feature/system/gnmi/benchmarking/tests/full_configuration_replace_test/README.md diff --git a/feature/experimental/system/gnmi/benchmarking/tests/full_configuration_replace_test/full_configuration_replace_test.go b/feature/system/gnmi/benchmarking/tests/full_configuration_replace_test/full_configuration_replace_test.go similarity index 97% rename from feature/experimental/system/gnmi/benchmarking/tests/full_configuration_replace_test/full_configuration_replace_test.go rename to feature/system/gnmi/benchmarking/tests/full_configuration_replace_test/full_configuration_replace_test.go index e07d56bb4aa..03d8878c59e 100644 --- a/feature/experimental/system/gnmi/benchmarking/tests/full_configuration_replace_test/full_configuration_replace_test.go +++ b/feature/system/gnmi/benchmarking/tests/full_configuration_replace_test/full_configuration_replace_test.go @@ -19,7 +19,7 @@ import ( "testing" "time" - "github.com/openconfig/featureprofiles/feature/experimental/system/gnmi/benchmarking/internal/setup" + "github.com/openconfig/featureprofiles/feature/system/gnmi/benchmarking/internal/setup" "github.com/openconfig/featureprofiles/internal/args" "github.com/openconfig/featureprofiles/internal/deviations" "github.com/openconfig/featureprofiles/internal/fptest" diff --git a/feature/experimental/system/gnmi/benchmarking/tests/full_configuration_replace_test/metadata.textproto b/feature/system/gnmi/benchmarking/tests/full_configuration_replace_test/metadata.textproto similarity index 100% rename from feature/experimental/system/gnmi/benchmarking/tests/full_configuration_replace_test/metadata.textproto rename to feature/system/gnmi/benchmarking/tests/full_configuration_replace_test/metadata.textproto diff --git a/feature/experimental/system/health/tests/system_generic_health_check/README.md b/feature/system/health/tests/system_generic_health_check/README.md similarity index 100% rename from feature/experimental/system/health/tests/system_generic_health_check/README.md rename to feature/system/health/tests/system_generic_health_check/README.md diff --git a/feature/experimental/system/health/tests/system_generic_health_check/metadata.textproto b/feature/system/health/tests/system_generic_health_check/metadata.textproto similarity index 100% rename from feature/experimental/system/health/tests/system_generic_health_check/metadata.textproto rename to feature/system/health/tests/system_generic_health_check/metadata.textproto diff --git a/feature/experimental/system/health/tests/system_generic_health_check/system_generic_health_check_test.go b/feature/system/health/tests/system_generic_health_check/system_generic_health_check_test.go similarity index 100% rename from feature/experimental/system/health/tests/system_generic_health_check/system_generic_health_check_test.go rename to feature/system/health/tests/system_generic_health_check/system_generic_health_check_test.go diff --git a/feature/system/management/otg_tests/management_ha_test/management_ha_test.go b/feature/system/management/otg_tests/management_ha_test/management_ha_test.go index b1da32ac404..9a92d63f2ce 100644 --- a/feature/system/management/otg_tests/management_ha_test/management_ha_test.go +++ b/feature/system/management/otg_tests/management_ha_test/management_ha_test.go @@ -54,8 +54,24 @@ var ( IPv4Len: 32, IPv6Len: 128, } - - mgmtVRF = "mvrf1" + mgmtVRF = map[ondatra.Vendor]string{ + ondatra.JUNIPER: "mvrf1", + ondatra.ARISTA: "mvrf1", + ondatra.CISCO: "mgmtvrf1", + ondatra.NOKIA: "mgmtvrf1", + } + loopbackIntf = map[ondatra.Vendor]int{ + ondatra.JUNIPER: 0, + ondatra.ARISTA: 1, + ondatra.CISCO: 1, + ondatra.NOKIA: 1, + } + loopbackSubIntf = map[ondatra.Vendor]int32{ + ondatra.JUNIPER: 10, + ondatra.ARISTA: 0, + ondatra.CISCO: 0, + ondatra.NOKIA: 0, + } bgpPorts = []string{"port1", "port2"} lossTolerance = float64(1) @@ -71,11 +87,10 @@ func TestManagementHA1(t *testing.T) { p2 := dut.Port(t, "port2") p3 := dut.Port(t, "port3") p4 := dut.Port(t, "port4") - loopbackIntfName := netutil.LoopbackInterface(t, dut, 1) - createInterfaces(t, dut, []string{p1.Name(), p2.Name(), p3.Name(), p4.Name(), loopbackIntfName}) - addInterfacesToVRF(t, dut, mgmtVRF, []string{p1.Name(), p2.Name(), p3.Name(), p4.Name(), loopbackIntfName}) - - bs := cfgplugins.NewBGPSession(t, cfgplugins.PortCount4, &mgmtVRF) + loopbackIntfName := netutil.LoopbackInterface(t, dut, loopbackIntf[dut.Vendor()]) + mgmtVRFName := mgmtVRF[dut.Vendor()] + createAndAddInterfacesToVRF(t, dut, mgmtVRFName, []string{p1.Name(), p2.Name(), p3.Name(), p4.Name(), loopbackIntfName}, []uint32{0, 0, 0, 0, uint32(loopbackSubIntf[dut.Vendor()])}) + bs := cfgplugins.NewBGPSession(t, cfgplugins.PortCount4, &mgmtVRFName) bs.WithEBGP( t, []oc.E_BgpTypes_AFI_SAFI_TYPE{oc.BgpTypes_AFI_SAFI_TYPE_IPV6_UNICAST}, @@ -87,12 +102,12 @@ func TestManagementHA1(t *testing.T) { g := bs.DUTConf.GetOrCreateNetworkInstance(deviations.DefaultNetworkInstance(dut)).GetOrCreateProtocol(cfgplugins.PTBGP, "BGP").GetOrCreateBgp().GetOrCreateGlobal() g.GetOrCreateAfiSafi(oc.BgpTypes_AFI_SAFI_TYPE_L3VPN_IPV6_UNICAST).Enabled = ygot.Bool(true) } - bgp := bs.DUTConf.GetOrCreateNetworkInstance(mgmtVRF).GetOrCreateProtocol(cfgplugins.PTBGP, "BGP").GetOrCreateBgp() + bgp := bs.DUTConf.GetOrCreateNetworkInstance(mgmtVRFName).GetOrCreateProtocol(cfgplugins.PTBGP, "BGP").GetOrCreateBgp() bgp.GetOrCreateGlobal().GetOrCreateAfiSafi(oc.BgpTypes_AFI_SAFI_TYPE_IPV6_UNICAST).GetOrCreateUseMultiplePaths().GetOrCreateEbgp() if deviations.SetNoPeerGroup(dut) || deviations.PeerGroupDefEbgpVrfUnsupported(dut) { - bs.DUTConf.GetOrCreateNetworkInstance(mgmtVRF).GetOrCreateProtocol(cfgplugins.PTBGP, "BGP").GetOrCreateBgp().PeerGroup = nil - neighbors := bs.DUTConf.GetOrCreateNetworkInstance(mgmtVRF).GetOrCreateProtocol(cfgplugins.PTBGP, "BGP").GetOrCreateBgp().Neighbor + bs.DUTConf.GetOrCreateNetworkInstance(mgmtVRFName).GetOrCreateProtocol(cfgplugins.PTBGP, "BGP").GetOrCreateBgp().PeerGroup = nil + neighbors := bs.DUTConf.GetOrCreateNetworkInstance(mgmtVRFName).GetOrCreateProtocol(cfgplugins.PTBGP, "BGP").GetOrCreateBgp().Neighbor for _, neighbor := range neighbors { neighbor.PeerGroup = nil } @@ -103,11 +118,11 @@ func TestManagementHA1(t *testing.T) { if deviations.ExplicitEnableBGPOnDefaultVRF(dut) { bs.DUTConf.GetOrCreateNetworkInstance(deviations.DefaultNetworkInstance(dut)).GetOrCreateProtocol(cfgplugins.PTBGP, "BGP").GetOrCreateBgp().GetOrCreateGlobal().SetAs(cfgplugins.DutAS) } - if dut.Vendor() != ondatra.NOKIA { - bs.DUTConf.GetOrCreateNetworkInstance(mgmtVRF).SetRouteDistinguisher(fmt.Sprintf("%d:%d", cfgplugins.DutAS, 100)) + if dut.Vendor() != ondatra.NOKIA && dut.Vendor() != ondatra.JUNIPER { + bs.DUTConf.GetOrCreateNetworkInstance(mgmtVRFName).SetRouteDistinguisher(fmt.Sprintf("%d:%d", cfgplugins.DutAS, 100)) } bs.PushAndStart(t) - if verfied := verifyDUTBGPEstablished(t, bs.DUT, mgmtVRF); verfied { + if verfied := verifyDUTBGPEstablished(t, bs.DUT, mgmtVRFName); verfied { t.Log("DUT BGP sessions established") } else { t.Fatalf("BGP sessions not established") @@ -145,7 +160,8 @@ func TestManagementHA1(t *testing.T) { otgutils.LogPortMetrics(t, bs.ATE.OTG(), bs.ATETop) framesTx := gnmi.Get(t, bs.ATE.OTG(), gnmi.OTG().Port(bs.ATE.Port(t, "port4").ID()).Counters().OutFrames().State()) framesRx := gnmi.Get(t, bs.ATE.OTG(), gnmi.OTG().Port(bs.ATE.Port(t, "port2").ID()).Counters().InFrames().State()) - if lossPct(float64(framesTx), float64(framesRx)) > lossTolerance { + lossV6 := otgutils.GetFlowLossPct(t, bs.ATE.OTG(), "v6Flow", 10*time.Second) + if lossV6 > lossTolerance || framesRx < framesTx { t.Errorf("Frames sent/received: got: %d, want: %d", framesRx, framesTx) } }) @@ -178,13 +194,17 @@ func TestManagementHA1(t *testing.T) { otgutils.LogPortMetrics(t, bs.ATE.OTG(), bs.ATETop) framesTx := gnmi.Get(t, bs.ATE.OTG(), gnmi.OTG().Port(bs.ATE.Port(t, "port4").ID()).Counters().OutFrames().State()) framesRx := gnmi.Get(t, bs.ATE.OTG(), gnmi.OTG().Port(bs.ATE.Port(t, "port1").ID()).Counters().InFrames().State()) - if lossPct(float64(framesTx), float64(framesRx)) > lossTolerance { + lossV6 := otgutils.GetFlowLossPct(t, bs.ATE.OTG(), "v6Flow", 10*time.Second) + if lossV6 > lossTolerance || framesRx < framesTx { t.Errorf("Frames sent/received: got: %d, want: %d", framesRx, framesTx) } }) defer func() { - gnmi.Delete(t, dut, gnmi.OC().NetworkInstance(mgmtVRF).Config()) + batchConfig := &gnmi.SetBatch{} + gnmi.BatchDelete(batchConfig, gnmi.OC().Interface(loopbackIntfName).Config()) + gnmi.BatchDelete(batchConfig, gnmi.OC().NetworkInstance(mgmtVRFName).Config()) + batchConfig.Set(t, dut) }() } @@ -213,6 +233,7 @@ func createFlowV6(t *testing.T, bs *cfgplugins.BGPSession) { } func configureStaticRoute(t *testing.T, dut *ondatra.DUTDevice, nextHopIP string) { + mgmtVRFName := mgmtVRF[dut.Vendor()] c := &oc.NetworkInstance_Protocol{ Identifier: oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_STATIC, Name: ygot.String(deviations.StaticProtocolName(dut)), @@ -225,7 +246,7 @@ func configureStaticRoute(t *testing.T, dut *ondatra.DUTDevice, nextHopIP string } else { nh.Preference = ygot.Uint32(220) } - sp := gnmi.OC().NetworkInstance(mgmtVRF).Protocol(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_STATIC, deviations.StaticProtocolName(dut)) + sp := gnmi.OC().NetworkInstance(mgmtVRFName).Protocol(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_STATIC, deviations.StaticProtocolName(dut)) gnmi.Update(t, dut, sp.Config(), c) gnmi.Replace(t, dut, sp.Static(defaultRoute+"/0").Config(), s) } @@ -250,39 +271,39 @@ func configureEmulatedNetworks(bs *cfgplugins.BGPSession) { } func configureLoopbackOnDUT(t *testing.T, dut *ondatra.DUTDevice) { - loopbackIntfName := netutil.LoopbackInterface(t, dut, 1) + loopbackIntfName := netutil.LoopbackInterface(t, dut, loopbackIntf[dut.Vendor()]) + dutlo0Attrs.Subinterface = uint32(loopbackSubIntf[dut.Vendor()]) loop := dutlo0Attrs.NewOCInterface(loopbackIntfName, dut) loop.Type = oc.IETFInterfaces_InterfaceType_softwareLoopback gnmi.Update(t, dut, gnmi.OC().Interface(loopbackIntfName).Config(), loop) t.Logf("Got DUT IPv6 loopback address: %v", dutlo0Attrs.IPv6) } -func createInterfaces(t *testing.T, dut *ondatra.DUTDevice, intfNames []string) { +func createAndAddInterfacesToVRF(t *testing.T, dut *ondatra.DUTDevice, vrfname string, intfNames []string, unit []uint32) { root := &oc.Root{} + batchConfig := &gnmi.SetBatch{} for index, intfName := range intfNames { i := root.GetOrCreateInterface(intfName) i.Type = oc.IETFInterfaces_InterfaceType_ethernetCsmacd i.Description = ygot.String(fmt.Sprintf("Port %s", strconv.Itoa(index+1))) - if intfName == netutil.LoopbackInterface(t, dut, 1) { + if intfName == netutil.LoopbackInterface(t, dut, loopbackIntf[dut.Vendor()]) { i.Type = oc.IETFInterfaces_InterfaceType_softwareLoopback i.Description = ygot.String(fmt.Sprintf("Port %s", intfName)) } - si := i.GetOrCreateSubinterface(0) + si := i.GetOrCreateSubinterface(unit[index]) si.Enabled = ygot.Bool(true) - gnmi.Update(t, dut, gnmi.OC().Interface(intfName).Config(), i) + gnmi.BatchUpdate(batchConfig, gnmi.OC().Interface(intfName).Config(), i) } -} -func addInterfacesToVRF(t *testing.T, dut *ondatra.DUTDevice, vrfname string, intfNames []string) { - root := &oc.Root{} mgmtNI := root.GetOrCreateNetworkInstance(vrfname) mgmtNI.Type = oc.NetworkInstanceTypes_NETWORK_INSTANCE_TYPE_L3VRF - for _, intfName := range intfNames { + for index, intfName := range intfNames { vi := mgmtNI.GetOrCreateInterface(intfName) vi.Interface = ygot.String(intfName) - vi.Subinterface = ygot.Uint32(0) + vi.Subinterface = ygot.Uint32(unit[index]) } - gnmi.Replace(t, dut, gnmi.OC().NetworkInstance(mgmtVRF).Config(), mgmtNI) + gnmi.BatchReplace(batchConfig, gnmi.OC().NetworkInstance(vrfname).Config(), mgmtNI) + batchConfig.Set(t, dut) t.Logf("Added interface %v to VRF %s", intfNames, vrfname) } @@ -303,7 +324,7 @@ func verifyDUTBGPEstablished(t *testing.T, dut *ondatra.DUTDevice, ni string) bo func advertiseDUTLoopbackToATE(t *testing.T, dut *ondatra.DUTDevice, bs *cfgplugins.BGPSession) { t.Helper() - + mgmtVRFName := mgmtVRF[dut.Vendor()] batchSet := &gnmi.SetBatch{} root := &oc.Root{} @@ -333,35 +354,36 @@ func advertiseDUTLoopbackToATE(t *testing.T, dut *ondatra.DUTDevice, bs *cfgplug if err != nil { t.Fatalf("Failed to create CLI ygnmi query: %v", err) } - cliCfg := getCiscoCLIRedisConfig("BGP", cfgplugins.DutAS, mgmtVRF) + cliCfg := getCiscoCLIRedisConfig("BGP", cfgplugins.DutAS, mgmtVRFName) gnmi.BatchUpdate(batchSet, cliPath, cliCfg) } else { stmt.GetOrCreateConditions().SetInstallProtocolEq(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_DIRECTLY_CONNECTED) - } - stmt.GetOrCreateActions().PolicyResult = oc.RoutingPolicy_PolicyResultType_ACCEPT_ROUTE - for _, neighbor := range []string{bs.ATEPorts[0].IPv6, bs.ATEPorts[1].IPv6} { - pathV6 := gnmi.OC().NetworkInstance(mgmtVRF).Protocol(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, "BGP").Bgp().Neighbor(neighbor).AfiSafi(oc.BgpTypes_AFI_SAFI_TYPE_IPV6_UNICAST).ApplyPolicy() - policyV6 := root.GetOrCreateNetworkInstance(mgmtVRF).GetOrCreateProtocol(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, "BGP").GetOrCreateBgp().GetOrCreateNeighbor(neighbor).GetOrCreateAfiSafi(oc.BgpTypes_AFI_SAFI_TYPE_IPV6_UNICAST).GetOrCreateApplyPolicy() - policyV6.SetExportPolicy([]string{"rp"}) - gnmi.BatchUpdate(batchSet, pathV6.Config(), policyV6) + stmt.GetOrCreateActions().PolicyResult = oc.RoutingPolicy_PolicyResultType_ACCEPT_ROUTE + for _, neighbor := range []string{bs.ATEPorts[0].IPv6, bs.ATEPorts[1].IPv6} { + pathV6 := gnmi.OC().NetworkInstance(mgmtVRFName).Protocol(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, "BGP").Bgp().Neighbor(neighbor).AfiSafi(oc.BgpTypes_AFI_SAFI_TYPE_IPV6_UNICAST).ApplyPolicy() + policyV6 := root.GetOrCreateNetworkInstance(mgmtVRFName).GetOrCreateProtocol(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, "BGP").GetOrCreateBgp().GetOrCreateNeighbor(neighbor).GetOrCreateAfiSafi(oc.BgpTypes_AFI_SAFI_TYPE_IPV6_UNICAST).GetOrCreateApplyPolicy() + policyV6.SetExportPolicy([]string{"rp"}) + gnmi.BatchUpdate(batchSet, pathV6.Config(), policyV6) + } } } else { - tableConn := root.GetOrCreateNetworkInstance(mgmtVRF).GetOrCreateTableConnection(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_DIRECTLY_CONNECTED, oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, oc.Types_ADDRESS_FAMILY_IPV6) + tableConn := root.GetOrCreateNetworkInstance(mgmtVRFName).GetOrCreateTableConnection(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_DIRECTLY_CONNECTED, oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, oc.Types_ADDRESS_FAMILY_IPV6) if !deviations.SkipSettingDisableMetricPropagation(dut) { tableConn.SetDisableMetricPropagation(false) } tableConn.SetDefaultImportPolicy(oc.RoutingPolicy_DefaultPolicyType_REJECT_ROUTE) tableConn.SetImportPolicy([]string{"rp"}) - gnmi.BatchUpdate(batchSet, gnmi.OC().NetworkInstance(mgmtVRF).TableConnection(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_DIRECTLY_CONNECTED, oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, oc.Types_ADDRESS_FAMILY_IPV6).Config(), tableConn) + gnmi.BatchUpdate(batchSet, gnmi.OC().NetworkInstance(mgmtVRFName).TableConnection(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_DIRECTLY_CONNECTED, oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, oc.Types_ADDRESS_FAMILY_IPV6).Config(), tableConn) - tableConn1 := root.GetOrCreateNetworkInstance(mgmtVRF).GetOrCreateTableConnection(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_DIRECTLY_CONNECTED, oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, oc.Types_ADDRESS_FAMILY_IPV4) + tableConn1 := root.GetOrCreateNetworkInstance(mgmtVRFName).GetOrCreateTableConnection(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_DIRECTLY_CONNECTED, oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, oc.Types_ADDRESS_FAMILY_IPV4) tableConn1.SetImportPolicy([]string{"rp"}) - gnmi.BatchUpdate(batchSet, gnmi.OC().NetworkInstance(mgmtVRF).TableConnection(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_DIRECTLY_CONNECTED, oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, oc.Types_ADDRESS_FAMILY_IPV4).Config(), tableConn1) + gnmi.BatchUpdate(batchSet, gnmi.OC().NetworkInstance(mgmtVRFName).TableConnection(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_DIRECTLY_CONNECTED, oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, oc.Types_ADDRESS_FAMILY_IPV4).Config(), tableConn1) } batchSet.Set(t, dut) } func configureImportExportBGPPolicy(t *testing.T, bs *cfgplugins.BGPSession, dut *ondatra.DUTDevice) { + mgmtVRFName := mgmtVRF[dut.Vendor()] root := &oc.Root{} batchSet := &gnmi.SetBatch{} @@ -405,8 +427,8 @@ func configureImportExportBGPPolicy(t *testing.T, bs *cfgplugins.BGPSession, dut gnmi.BatchUpdate(batchSet, gnmi.OC().RoutingPolicy().Config(), rp) for _, neighbor := range []string{bs.ATEPorts[0].IPv6, bs.ATEPorts[1].IPv6} { - pathV6 := gnmi.OC().NetworkInstance(mgmtVRF).Protocol(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, "BGP").Bgp().Neighbor(neighbor).AfiSafi(oc.BgpTypes_AFI_SAFI_TYPE_IPV6_UNICAST).ApplyPolicy() - policyV6 := root.GetOrCreateNetworkInstance(mgmtVRF).GetOrCreateProtocol(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, "BGP").GetOrCreateBgp().GetOrCreateNeighbor(neighbor).GetOrCreateAfiSafi(oc.BgpTypes_AFI_SAFI_TYPE_IPV6_UNICAST).GetOrCreateApplyPolicy() + pathV6 := gnmi.OC().NetworkInstance(mgmtVRFName).Protocol(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, "BGP").Bgp().Neighbor(neighbor).AfiSafi(oc.BgpTypes_AFI_SAFI_TYPE_IPV6_UNICAST).ApplyPolicy() + policyV6 := root.GetOrCreateNetworkInstance(mgmtVRFName).GetOrCreateProtocol(oc.PolicyTypes_INSTALL_PROTOCOL_TYPE_BGP, "BGP").GetOrCreateBgp().GetOrCreateNeighbor(neighbor).GetOrCreateAfiSafi(oc.BgpTypes_AFI_SAFI_TYPE_IPV6_UNICAST).GetOrCreateApplyPolicy() policyV6.SetImportPolicy([]string{"importRoutePolicy"}) policyV6.SetExportPolicy([]string{"exportRoutePolicy"}) gnmi.BatchUpdate(batchSet, pathV6.Config(), policyV6) diff --git a/feature/experimental/tunnel/otg_tests/tunnel_acl_based_test/README.md b/feature/tunnel/otg_tests/tunnel_acl_based_test/README.md similarity index 66% rename from feature/experimental/tunnel/otg_tests/tunnel_acl_based_test/README.md rename to feature/tunnel/otg_tests/tunnel_acl_based_test/README.md index 073bc96cac8..f7f4769287a 100644 --- a/feature/experimental/tunnel/otg_tests/tunnel_acl_based_test/README.md +++ b/feature/tunnel/otg_tests/tunnel_acl_based_test/README.md @@ -14,10 +14,20 @@ Verify the DSCP value of original packet header after GRE acl based tunnel encap * verify dscp value of original packet after encapsulation. * verify that no traffic drops in all flows. -## Config Parameter coverage - -* /acl/interfaces/interface/ingress-acl-sets/ingress-acl-set/config/set-name -* /acl/interfaces/interface/ingress-acl-sets/ingress-acl-set/config/set-type +## OpenConfig Path and RPC Coverage + +The below yaml defines the OC paths intended to be covered by this test. OC +paths used for test setup are not listed here. + +```yaml +paths: + /acl/interfaces/interface/ingress-acl-sets/ingress-acl-set/config/set-name: + /acl/interfaces/interface/ingress-acl-sets/ingress-acl-set/config/type: +rpcs: + gnmi: + gNMI.Subscribe: + gNMI.Set: +``` ## Validation coverage diff --git a/feature/experimental/tunnel/otg_tests/tunnel_acl_based_test/metadata.textproto b/feature/tunnel/otg_tests/tunnel_acl_based_test/metadata.textproto similarity index 100% rename from feature/experimental/tunnel/otg_tests/tunnel_acl_based_test/metadata.textproto rename to feature/tunnel/otg_tests/tunnel_acl_based_test/metadata.textproto diff --git a/feature/experimental/tunnel/otg_tests/tunnel_acl_based_test/tun_acl_dscp_test.go b/feature/tunnel/otg_tests/tunnel_acl_based_test/tun_acl_dscp_test.go similarity index 100% rename from feature/experimental/tunnel/otg_tests/tunnel_acl_based_test/tun_acl_dscp_test.go rename to feature/tunnel/otg_tests/tunnel_acl_based_test/tun_acl_dscp_test.go diff --git a/feature/experimental/tunnel/otg_tests/tunnel_interface_based_ipv6_gre_encapsulation_test/README.md b/feature/tunnel/otg_tests/tunnel_interface_based_ipv6_gre_encapsulation_test/README.md similarity index 94% rename from feature/experimental/tunnel/otg_tests/tunnel_interface_based_ipv6_gre_encapsulation_test/README.md rename to feature/tunnel/otg_tests/tunnel_interface_based_ipv6_gre_encapsulation_test/README.md index 0bfc7dbe99f..076b0069e74 100644 --- a/feature/experimental/tunnel/otg_tests/tunnel_interface_based_ipv6_gre_encapsulation_test/README.md +++ b/feature/tunnel/otg_tests/tunnel_interface_based_ipv6_gre_encapsulation_test/README.md @@ -71,4 +71,13 @@ Validate Interface based Ipv6 GRE Tunnel Config. - state/counters/out-forwarded-pkts - state/counters/out-forwarded-octets - state/counters/out-discarded-pkt - - Fragmentation and assembly counters Filter counters Output to display the traffic is spread across the different tunnel subnet ranges/NH groups/Interfaces \ No newline at end of file + - Fragmentation and assembly counters Filter counters Output to display the traffic is spread across the different tunnel subnet ranges/NH groups/Interfaces + +## OpenConfig Path and RPC Coverage +```yaml +rpcs: + gnmi: + gNMI.Get: + gNMI.Set: + gNMI.Subscribe: +``` diff --git a/feature/experimental/tunnel/otg_tests/tunnel_interface_based_ipv6_gre_encapsulation_test/metadata.textproto b/feature/tunnel/otg_tests/tunnel_interface_based_ipv6_gre_encapsulation_test/metadata.textproto similarity index 100% rename from feature/experimental/tunnel/otg_tests/tunnel_interface_based_ipv6_gre_encapsulation_test/metadata.textproto rename to feature/tunnel/otg_tests/tunnel_interface_based_ipv6_gre_encapsulation_test/metadata.textproto diff --git a/feature/experimental/tunnel/otg_tests/tunnel_interface_based_ipv6_gre_encapsulation_test/tunnel_interface_based_ipv6_gre_encapsulation_test.go b/feature/tunnel/otg_tests/tunnel_interface_based_ipv6_gre_encapsulation_test/tunnel_interface_based_ipv6_gre_encapsulation_test.go similarity index 100% rename from feature/experimental/tunnel/otg_tests/tunnel_interface_based_ipv6_gre_encapsulation_test/tunnel_interface_based_ipv6_gre_encapsulation_test.go rename to feature/tunnel/otg_tests/tunnel_interface_based_ipv6_gre_encapsulation_test/tunnel_interface_based_ipv6_gre_encapsulation_test.go diff --git a/feature/experimental/tunnel/otg_tests/tunnel_interface_based_resize_test/README.md b/feature/tunnel/otg_tests/tunnel_interface_based_resize_test/README.md similarity index 98% rename from feature/experimental/tunnel/otg_tests/tunnel_interface_based_resize_test/README.md rename to feature/tunnel/otg_tests/tunnel_interface_based_resize_test/README.md index 1bdd0384ace..24925300655 100644 --- a/feature/experimental/tunnel/otg_tests/tunnel_interface_based_resize_test/README.md +++ b/feature/tunnel/otg_tests/tunnel_interface_based_resize_test/README.md @@ -101,3 +101,12 @@ TODO: OpenConfig definition required for Tunnel protocol under interfaces/interf * state/counters/out-forwarded-pkts * state/counters/out-forwarded-octets * state/counters/out-discarded-pkts + +## OpenConfig Path and RPC Coverage +```yaml +rpcs: + gnmi: + gNMI.Get: + gNMI.Set: + gNMI.Subscribe: +``` diff --git a/go.mod b/go.mod index cbbf859e66c..c93984c9271 100644 --- a/go.mod +++ b/go.mod @@ -4,11 +4,11 @@ go 1.21 require ( cloud.google.com/go/pubsub v1.36.1 - cloud.google.com/go/storage v1.36.0 + cloud.google.com/go/storage v1.38.0 github.com/cisco-open/go-p4 v0.1.2 github.com/go-git/go-billy/v5 v5.5.0 github.com/go-git/go-git/v5 v5.11.0 - github.com/golang/glog v1.2.0 + github.com/golang/glog v1.2.1 github.com/google/go-cmp v0.6.0 github.com/google/go-github/v50 v50.1.0 github.com/google/gopacket v1.1.19 @@ -19,34 +19,34 @@ require ( github.com/openconfig/containerz v0.0.0-20240620162940-e0bf23af17d6 github.com/openconfig/entity-naming v0.0.0-20230912181021-7ac806551a31 github.com/openconfig/gnmi v0.11.0 - github.com/openconfig/gnoi v0.4.1-0.20240501161656-1d16819bab6a + github.com/openconfig/gnoi v0.4.1 github.com/openconfig/gnoigo v0.0.0-20240320202954-ebd033e3542c - github.com/openconfig/gnsi v1.4.5 + github.com/openconfig/gnsi v1.6.0 github.com/openconfig/gocloser v0.0.0-20220310182203-c6c950ed3b0b github.com/openconfig/goyang v1.4.5 github.com/openconfig/gribi v1.0.0 - github.com/openconfig/gribigo v0.0.0-20231213034307-d0abeba7f432 + github.com/openconfig/gribigo v0.0.0-20240829231637-69cf06726cc3 github.com/openconfig/kne v0.1.18 github.com/openconfig/models-ci v1.0.2-0.20231113233730-f0986391428e - github.com/openconfig/ondatra v0.6.0 + github.com/openconfig/ondatra v0.6.1 github.com/openconfig/replayer v0.0.0-20240110192655-4e9cf83d8d30 github.com/openconfig/testt v0.0.0-20220311054427-efbb1a32ec07 github.com/openconfig/ygnmi v0.11.1 - github.com/openconfig/ygot v0.29.18 + github.com/openconfig/ygot v0.29.19 github.com/p4lang/p4runtime v1.4.0-rc.5.0.20220728214547-13f0d02a521e github.com/pborman/uuid v1.2.1 github.com/protocolbuffers/txtpbfmt v0.0.0-20220608084003-fc78c767cd6a github.com/spf13/cobra v1.8.0 github.com/spf13/pflag v1.0.5 - github.com/spf13/viper v1.18.2 + github.com/spf13/viper v1.19.0 github.com/yoheimuta/go-protoparser/v4 v4.9.0 github.com/yuin/goldmark v1.4.13 - golang.org/x/crypto v0.21.0 - golang.org/x/exp v0.0.0-20240325151524-a685a6edb6d8 - golang.org/x/text v0.14.0 - google.golang.org/api v0.162.0 - google.golang.org/grpc v1.63.2 - google.golang.org/protobuf v1.34.1 + golang.org/x/crypto v0.27.0 + golang.org/x/exp v0.0.0-20240604190554-fc45aab8b7f8 + golang.org/x/text v0.18.0 + google.golang.org/api v0.171.0 + google.golang.org/grpc v1.66.2 + google.golang.org/protobuf v1.34.2 gopkg.in/yaml.v2 v2.4.0 gopkg.in/yaml.v3 v3.0.1 k8s.io/klog/v2 v2.120.1 @@ -55,14 +55,14 @@ require ( require ( github.com/Masterminds/semver/v3 v3.2.1 // indirect github.com/Microsoft/go-winio v0.6.1 // indirect - golang.org/x/oauth2 v0.17.0 + golang.org/x/oauth2 v0.21.0 ) require ( bitbucket.org/creachadair/stringset v0.0.14 // indirect - cloud.google.com/go v0.112.0 // indirect - cloud.google.com/go/compute v1.24.0 // indirect - cloud.google.com/go/compute/metadata v0.2.3 // indirect + cel.dev/expr v0.15.0 // indirect + cloud.google.com/go v0.112.1 // indirect + cloud.google.com/go/compute/metadata v0.3.0 // indirect cloud.google.com/go/iam v1.1.6 // indirect dario.cat/mergo v1.0.0 // indirect github.com/ProtonMail/go-crypto v0.0.0-20230828082145-3c4c8a2d2371 // indirect @@ -70,16 +70,16 @@ require ( github.com/carlmontanari/difflibgo v0.0.0-20210718194309-31b9e131c298 // indirect github.com/cenkalti/backoff/v4 v4.1.3 // indirect github.com/census-instrumentation/opencensus-proto v0.4.1 // indirect - github.com/cespare/xxhash/v2 v2.2.0 // indirect + github.com/cespare/xxhash/v2 v2.3.0 // indirect github.com/cloudflare/circl v1.3.7 // indirect - github.com/cncf/xds/go v0.0.0-20231128003011-0fa0005c9caa // indirect + github.com/cncf/xds/go v0.0.0-20240423153145-555b57ec207b // indirect github.com/creack/pty v1.1.18 // indirect github.com/cyphar/filepath-securejoin v0.2.4 // indirect github.com/davecgh/go-spew v1.1.2-0.20180830191138-d8f796af33cc // indirect github.com/drivenets/cdnos-controller v1.7.4 // indirect github.com/emicklei/go-restful/v3 v3.10.2 // indirect github.com/emirpasic/gods v1.18.1 // indirect - github.com/envoyproxy/go-control-plane v0.12.0 // indirect + github.com/envoyproxy/go-control-plane v0.12.1-0.20240621013728-1eb8caab5155 // indirect github.com/envoyproxy/protoc-gen-validate v1.0.4 // indirect github.com/evanphx/json-patch/v5 v5.6.0 // indirect github.com/felixge/httpsnoop v1.0.4 // indirect @@ -99,7 +99,7 @@ require ( github.com/google/gofuzz v1.2.0 // indirect github.com/google/s2a-go v0.1.7 // indirect github.com/googleapis/enterprise-certificate-proxy v0.3.2 // indirect - github.com/googleapis/gax-go/v2 v2.12.0 // indirect + github.com/googleapis/gax-go/v2 v2.12.3 // indirect github.com/hashicorp/hcl v1.0.0 // indirect github.com/imdario/mergo v0.3.15 // indirect github.com/inconshreveable/mousetrap v1.1.0 // indirect @@ -125,11 +125,12 @@ require ( github.com/openconfig/grpctunnel v0.0.0-20220819142823-6f5422b8ca70 // indirect github.com/openconfig/lemming/operator v0.2.0 // indirect github.com/patrickmn/go-cache v2.1.0+incompatible // indirect - github.com/pelletier/go-toml/v2 v2.2.0 // indirect + github.com/pelletier/go-toml/v2 v2.2.2 // indirect github.com/pjbgf/sha1cd v0.3.0 // indirect github.com/pkg/errors v0.9.1 // indirect + github.com/planetscale/vtprotobuf v0.6.1-0.20240319094008-0393e58bdf10 // indirect github.com/rogpeppe/go-internal v1.11.0 // indirect - github.com/sagikazarmark/locafero v0.4.0 // indirect + github.com/sagikazarmark/locafero v0.6.0 // indirect github.com/sagikazarmark/slog-shim v0.1.0 // indirect github.com/scrapli/scrapligo v1.1.11 // indirect github.com/scrapli/scrapligocfg v1.0.0 // indirect @@ -144,24 +145,23 @@ require ( github.com/subosito/gotenv v1.6.0 // indirect github.com/xanzy/ssh-agent v0.3.3 // indirect go.opencensus.io v0.24.0 // indirect - go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc v0.47.0 // indirect - go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.47.0 // indirect - go.opentelemetry.io/otel v1.22.0 // indirect - go.opentelemetry.io/otel/metric v1.22.0 // indirect - go.opentelemetry.io/otel/trace v1.22.0 // indirect + go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc v0.49.0 // indirect + go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.49.0 // indirect + go.opentelemetry.io/otel v1.24.0 // indirect + go.opentelemetry.io/otel/metric v1.24.0 // indirect + go.opentelemetry.io/otel/trace v1.24.0 // indirect go.uber.org/atomic v1.11.0 // indirect go.uber.org/multierr v1.11.0 // indirect - golang.org/x/mod v0.16.0 // indirect - golang.org/x/net v0.23.0 // indirect - golang.org/x/sync v0.6.0 // indirect - golang.org/x/sys v0.20.0 // indirect - golang.org/x/term v0.18.0 // indirect + golang.org/x/mod v0.18.0 // indirect + golang.org/x/net v0.29.0 // indirect + golang.org/x/sync v0.8.0 // indirect + golang.org/x/sys v0.25.0 // indirect + golang.org/x/term v0.24.0 // indirect golang.org/x/time v0.5.0 // indirect - golang.org/x/tools v0.19.0 // indirect - google.golang.org/appengine v1.6.8 // indirect + golang.org/x/tools v0.22.0 // indirect google.golang.org/genproto v0.0.0-20240227224415-6ceb2ff114de // indirect - google.golang.org/genproto/googleapis/api v0.0.0-20240227224415-6ceb2ff114de // indirect - google.golang.org/genproto/googleapis/rpc v0.0.0-20240401170217-c3f982113cda // indirect + google.golang.org/genproto/googleapis/api v0.0.0-20240604185151-ef581f913117 // indirect + google.golang.org/genproto/googleapis/rpc v0.0.0-20240903143218-8af14fe29dc1 // indirect gopkg.in/inf.v0 v0.9.1 // indirect gopkg.in/ini.v1 v1.67.0 // indirect gopkg.in/warnings.v0 v0.1.2 // indirect diff --git a/go.sum b/go.sum index 0838dc64992..454fb06c5bc 100644 --- a/go.sum +++ b/go.sum @@ -1,5 +1,7 @@ bitbucket.org/creachadair/stringset v0.0.14 h1:t1ejQyf8utS4GZV/4fM+1gvYucggZkfhb+tMobDxYOE= bitbucket.org/creachadair/stringset v0.0.14/go.mod h1:Ej8fsr6rQvmeMDf6CCWMWGb14H9mz8kmDgPPTdiVT0w= +cel.dev/expr v0.15.0 h1:O1jzfJCQBfL5BFoYktaxwIhuttaQPsVWerH9/EEKx0w= +cel.dev/expr v0.15.0/go.mod h1:TRSuuV7DlVCE/uwv5QbAiW/v8l5O8C4eEPHeu7gf7Sg= cloud.google.com/go v0.26.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw= cloud.google.com/go v0.34.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw= cloud.google.com/go v0.38.0/go.mod h1:990N+gfupTy94rShfmMCWGDn0LpTmnzTp2qbd1dvSRU= @@ -46,8 +48,9 @@ cloud.google.com/go v0.110.8/go.mod h1:Iz8AkXJf1qmxC3Oxoep8R1T36w8B92yU29PcBhHO5 cloud.google.com/go v0.110.9/go.mod h1:rpxevX/0Lqvlbc88b7Sc1SPNdyK1riNBTUU6JXhYNpM= cloud.google.com/go v0.110.10/go.mod h1:v1OoFqYxiBkUrruItNM3eT4lLByNjxmJSV/xDKJNnic= cloud.google.com/go v0.111.0/go.mod h1:0mibmpKP1TyOOFYQY5izo0LnT+ecvOQ0Sg3OdmMiNRU= -cloud.google.com/go v0.112.0 h1:tpFCD7hpHFlQ8yPwT3x+QeXqc2T6+n6T+hmABHfDUSM= cloud.google.com/go v0.112.0/go.mod h1:3jEEVwZ/MHU4djK5t5RHuKOA/GbLddgTdVubX1qnPD4= +cloud.google.com/go v0.112.1 h1:uJSeirPke5UNZHIb4SxfZklVSiWWVqW4oXlETwZziwM= +cloud.google.com/go v0.112.1/go.mod h1:+Vbu+Y1UU+I1rjmzeMOb/8RfkKJK2Gyxi1X6jJCZLo4= cloud.google.com/go/accessapproval v1.4.0/go.mod h1:zybIuC3KpDOvotz59lFe5qxRZx6C75OtwbisN56xYB4= cloud.google.com/go/accessapproval v1.5.0/go.mod h1:HFy3tuiGvMdcd/u+Cu5b9NkO1pEICJ46IR82PoUdplw= cloud.google.com/go/accessapproval v1.6.0/go.mod h1:R0EiYnwV5fsRFiKZkPHr6mwyk2wxUJ30nL4j2pcFY2E= @@ -319,13 +322,12 @@ cloud.google.com/go/compute v1.23.0/go.mod h1:4tCnrn48xsqlwSAiLf1HXMQk8CONslYbdi cloud.google.com/go/compute v1.23.1/go.mod h1:CqB3xpmPKKt3OJpW2ndFIXnA9A4xAy/F3Xp1ixncW78= cloud.google.com/go/compute v1.23.2/go.mod h1:JJ0atRC0J/oWYiiVBmsSsrRnh92DhZPG4hFDcR04Rns= cloud.google.com/go/compute v1.23.3/go.mod h1:VCgBUoMnIVIR0CscqQiPJLAG25E3ZRZMzcFZeQ+h8CI= -cloud.google.com/go/compute v1.24.0 h1:phWcR2eWzRJaL/kOiJwfFsPs4BaKq1j6vnpZrc1YlVg= -cloud.google.com/go/compute v1.24.0/go.mod h1:kw1/T+h/+tK2LJK0wiPPx1intgdAM3j/g3hFDlscY40= cloud.google.com/go/compute/metadata v0.1.0/go.mod h1:Z1VN+bulIf6bt4P/C37K4DyZYZEXYonfTBHHFPO/4UU= cloud.google.com/go/compute/metadata v0.2.0/go.mod h1:zFmK7XCadkQkj6TtorcaGlCW1hT1fIilQDwofLpJ20k= cloud.google.com/go/compute/metadata v0.2.1/go.mod h1:jgHgmJd2RKBGzXqF5LR2EZMGxBkeanZ9wwa75XHJgOM= -cloud.google.com/go/compute/metadata v0.2.3 h1:mg4jlk7mCAj6xXp9UJ4fjI9VUI5rubuGBW5aJ7UnBMY= cloud.google.com/go/compute/metadata v0.2.3/go.mod h1:VAV5nSsACxMJvgaAuX6Pk2AawlZn8kiOGuCv6gTkwuA= +cloud.google.com/go/compute/metadata v0.3.0 h1:Tz+eQXMEqDIKRsmY3cHTL6FVaynIjX2QxYC4trgAKZc= +cloud.google.com/go/compute/metadata v0.3.0/go.mod h1:zFmK7XCadkQkj6TtorcaGlCW1hT1fIilQDwofLpJ20k= cloud.google.com/go/contactcenterinsights v1.3.0/go.mod h1:Eu2oemoePuEFc/xKFPjbTuPSj0fYJcPls9TFlPNnHHY= cloud.google.com/go/contactcenterinsights v1.4.0/go.mod h1:L2YzkGbPsv+vMQMCADxJoT9YiTTnSEd6fEvCeHTYVck= cloud.google.com/go/contactcenterinsights v1.6.0/go.mod h1:IIDlT6CLcDoyv79kDv8iWxMSTZhLxSCofVV5W6YFM/w= @@ -1064,8 +1066,9 @@ cloud.google.com/go/storage v1.27.0/go.mod h1:x9DOL8TK/ygDUMieqwfhdpQryTeEkhGKMi cloud.google.com/go/storage v1.28.1/go.mod h1:Qnisd4CqDdo6BGs2AD5LLnEsmSQ80wQ5ogcBBKhU86Y= cloud.google.com/go/storage v1.29.0/go.mod h1:4puEjyTKnku6gfKoTfNOU/W+a9JyuVNxjpS5GBrB8h4= cloud.google.com/go/storage v1.30.1/go.mod h1:NfxhC0UJE1aXSx7CIIbCf7y9HKT7BiccwkR7+P7gN8E= -cloud.google.com/go/storage v1.36.0 h1:P0mOkAcaJxhCTvAkMhxMfrTKiNcub4YmmPBtlhAyTr8= cloud.google.com/go/storage v1.36.0/go.mod h1:M6M/3V/D3KpzMTJyPOR/HU6n2Si5QdaXYEsng2xgOs8= +cloud.google.com/go/storage v1.38.0 h1:Az68ZRGlnNTpIBbLjSMIV2BDcwwXYlRlQzis0llkpJg= +cloud.google.com/go/storage v1.38.0/go.mod h1:tlUADB0mAb9BgYls9lq+8MGkfzOXuLrnHXlpHmvFJoY= cloud.google.com/go/storagetransfer v1.5.0/go.mod h1:dxNzUopWy7RQevYFHewchb29POFv3/AaBgnhqzqiK0w= cloud.google.com/go/storagetransfer v1.6.0/go.mod h1:y77xm4CQV/ZhFZH75PLEXY0ROiS7Gh6pSKrM8dJyg6I= cloud.google.com/go/storagetransfer v1.7.0/go.mod h1:8Giuj1QNb1kfLAiWM1bN6dHzfdlDAVC9rv9abHot2W4= @@ -1250,8 +1253,9 @@ github.com/census-instrumentation/opencensus-proto v0.4.1 h1:iKLQ0xPNFxR/2hzXZMr github.com/census-instrumentation/opencensus-proto v0.4.1/go.mod h1:4T9NM4+4Vw91VeyqjLS6ao50K5bOcLKN6Q42XnYaRYw= github.com/cespare/xxhash v1.1.0/go.mod h1:XrSqR1VqqWfGrhpAt58auRo0WTKS1nRRg3ghfAqPWnc= github.com/cespare/xxhash/v2 v2.1.1/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs= -github.com/cespare/xxhash/v2 v2.2.0 h1:DC2CZ1Ep5Y4k3ZQ899DldepgrayRUGE6BBZ/cd9Cj44= github.com/cespare/xxhash/v2 v2.2.0/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs= +github.com/cespare/xxhash/v2 v2.3.0 h1:UL815xU9SqsFlibzuggzjXhog7bL6oX9BbNZnL2UFvs= +github.com/cespare/xxhash/v2 v2.3.0/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs= github.com/chzyer/logex v1.1.10/go.mod h1:+Ywpsq7O8HXn0nuIou7OrIPyXbp3wmkHB+jjWRnGsAI= github.com/chzyer/readline v0.0.0-20180603132655-2972be24d48e/go.mod h1:nSuG5e5PlCu98SY8svDHJxuZscDgtXS6KTTbou5AhLI= github.com/chzyer/test v0.0.0-20180213035817-a1ea475d72b1/go.mod h1:Q3SI9o4m/ZMnBNeIyt5eFwwo7qiLfzFZmjNmxjkiQlU= @@ -1276,8 +1280,9 @@ github.com/cncf/xds/go v0.0.0-20230105202645-06c439db220b/go.mod h1:eXthEFrGJvWH github.com/cncf/xds/go v0.0.0-20230310173818-32f1caf87195/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= github.com/cncf/xds/go v0.0.0-20230428030218-4003588d1b74/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= github.com/cncf/xds/go v0.0.0-20230607035331-e9ce68804cb4/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= -github.com/cncf/xds/go v0.0.0-20231128003011-0fa0005c9caa h1:jQCWAUqqlij9Pgj2i/PB79y4KOPYVyFYdROxgaCwdTQ= github.com/cncf/xds/go v0.0.0-20231128003011-0fa0005c9caa/go.mod h1:x/1Gn8zydmfq8dk6e9PdstVsDgu9RuyIIJqAaF//0IM= +github.com/cncf/xds/go v0.0.0-20240423153145-555b57ec207b h1:ga8SEFjZ60pxLcmhnThWgvH2wg8376yUJmPhEH4H3kw= +github.com/cncf/xds/go v0.0.0-20240423153145-555b57ec207b/go.mod h1:W+zGtBO5Y1IgJhy4+A9GOqVhqLpfZi+vwmdNXUehLA8= github.com/cpuguy83/go-md2man/v2 v2.0.3/go.mod h1:tgQtvFlXSQOSOSIRvRPT7W67SCa46tRHOmNcaadrF8o= github.com/creack/pty v1.1.9/go.mod h1:oKZEueFk5CKHvIhNR5MUki03XCEU+Q6VDXinZuGJ33E= github.com/creack/pty v1.1.18 h1:n56/Zwd5o6whRC5PMGretI4IdRLlmBXYNjScPaBgsbY= @@ -1318,8 +1323,9 @@ github.com/envoyproxy/go-control-plane v0.10.3/go.mod h1:fJJn/j26vwOu972OllsvAgJ github.com/envoyproxy/go-control-plane v0.11.0/go.mod h1:VnHyVMpzcLvCFt9yUz1UnCwHLhwx1WguiVDV7pTG/tI= github.com/envoyproxy/go-control-plane v0.11.1-0.20230524094728-9239064ad72f/go.mod h1:sfYdkwUW4BA3PbKjySwjJy+O4Pu0h62rlqCMHNk+K+Q= github.com/envoyproxy/go-control-plane v0.11.1/go.mod h1:uhMcXKCQMEJHiAb0w+YGefQLaTEw+YhGluxZkrTmD0g= -github.com/envoyproxy/go-control-plane v0.12.0 h1:4X+VP1GHd1Mhj6IB5mMeGbLCleqxjletLK6K0rbxyZI= github.com/envoyproxy/go-control-plane v0.12.0/go.mod h1:ZBTaoJ23lqITozF0M6G4/IragXCQKCnYbmlmtHvwRG0= +github.com/envoyproxy/go-control-plane v0.12.1-0.20240621013728-1eb8caab5155 h1:IgJPqnrlY2Mr4pYB6oaMKvFvwJ9H+X6CCY5x1vCTcpc= +github.com/envoyproxy/go-control-plane v0.12.1-0.20240621013728-1eb8caab5155/go.mod h1:5Wkq+JduFtdAXihLmeTJf+tRYIT4KBc2vPXDhwVo1pA= github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c= github.com/envoyproxy/protoc-gen-validate v0.6.7/go.mod h1:dyJXwwfPK2VSqiB9Klm1J6romD608Ba7Hij42vrOBCo= github.com/envoyproxy/protoc-gen-validate v0.9.1/go.mod h1:OKNgG7TCp5pF4d6XftA0++PMirau2/yoOwVac3AbF2w= @@ -1394,8 +1400,9 @@ github.com/golang/glog v0.0.0-20160126235308-23def4e6c14b/go.mod h1:SBH7ygxi8pfU github.com/golang/glog v1.0.0/go.mod h1:EWib/APOK0SL3dFbYqvxE3UYd8E6s1ouQ7iEp/0LWV4= github.com/golang/glog v1.1.0/go.mod h1:pfYeQZ3JWZoXTV5sFc986z3HTpwQs9At6P4ImfuP3NQ= github.com/golang/glog v1.1.2/go.mod h1:zR+okUeTbrL6EL3xHUDxZuEtGv04p5shwip1+mL/rLQ= -github.com/golang/glog v1.2.0 h1:uCdmnmatrKCgMBlM4rMuJZWOkPDqdbZPnrMXDY4gI68= github.com/golang/glog v1.2.0/go.mod h1:6AhwSGph0fcJtXVM/PEHPqZlFeoLxhs7/t5UDAwmO+w= +github.com/golang/glog v1.2.1 h1:OptwRhECazUx5ix5TTWC3EZhsZEHWcYWY4FQHTIubm4= +github.com/golang/glog v1.2.1/go.mod h1:6AhwSGph0fcJtXVM/PEHPqZlFeoLxhs7/t5UDAwmO+w= github.com/golang/groupcache v0.0.0-20190702054246-869f871628b6/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= github.com/golang/groupcache v0.0.0-20191227052852-215e87163ea7/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= github.com/golang/groupcache v0.0.0-20200121045136-8c9f03a8e57e/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= @@ -1526,8 +1533,9 @@ github.com/googleapis/gax-go/v2 v2.7.1/go.mod h1:4orTrqY6hXxxaUL4LHIPl6lGo8vAE38 github.com/googleapis/gax-go/v2 v2.8.0/go.mod h1:4orTrqY6hXxxaUL4LHIPl6lGo8vAE38/qKbhSAKP6QI= github.com/googleapis/gax-go/v2 v2.10.0/go.mod h1:4UOEnMCrxsSqQ940WnTiD6qJ63le2ev3xfyagutxiPw= github.com/googleapis/gax-go/v2 v2.11.0/go.mod h1:DxmR61SGKkGLa2xigwuZIQpkCI2S5iydzRfb3peWZJI= -github.com/googleapis/gax-go/v2 v2.12.0 h1:A+gCJKdRfqXkr+BIRGtZLibNXf0m1f9E4HG56etFpas= github.com/googleapis/gax-go/v2 v2.12.0/go.mod h1:y+aIqrI5eb1YGMVJfuV3185Ts/D7qKpsEkdD5+I6QGU= +github.com/googleapis/gax-go/v2 v2.12.3 h1:5/zPPDvw8Q1SuXjrqrZslrqT7dL/uJT2CQii/cLCKqA= +github.com/googleapis/gax-go/v2 v2.12.3/go.mod h1:AKloxT6GtNbaLm8QTNSidHUVsHYcBHwWRvkNFJUQcS4= github.com/googleapis/go-type-adapters v1.0.0/go.mod h1:zHW75FOG2aur7gAO2B+MLby+cLsWGBF62rFAi7WjWO4= github.com/googleapis/google-cloud-go-testing v0.0.0-20200911160855-bcd43fbb19e8/go.mod h1:dvDLG8qkwmyD9a/MJJN3XJcT3xFxOKAvTZGvuZmac9g= github.com/gorilla/mux v1.8.1 h1:TuBL49tXwgrFYWhqrNgrUNEY92u81SPhu7sTdzQEiWY= @@ -1558,6 +1566,8 @@ github.com/jbenet/go-context v0.0.0-20150711004518-d14ea06fba99/go.mod h1:1lJo3i github.com/jessevdk/go-flags v1.4.0/go.mod h1:4FA24M0QyGHXBuZZK/XkWh8h0e1EYbRYJSGM75WSRxI= github.com/josharian/intern v1.0.0 h1:vlS4z54oSdjm0bgjRigI+G1HpF+tI+9rE5LLzOg8HmY= github.com/josharian/intern v1.0.0/go.mod h1:5DoeVV0s6jJacbCEi61lwdGj/aVlrQvzHFFd8Hwg//Y= +github.com/josharian/native v1.1.0 h1:uuaP0hAbW7Y4l0ZRQ6C9zfb7Mg1mbFKry/xzDAfmtLA= +github.com/josharian/native v1.1.0/go.mod h1:7X/raswPFr05uY3HiLlYeyQntB6OO7E/d2Cu7qoaN2w= github.com/json-iterator/go v1.1.12 h1:PV8peI4a0ysnczrg+LtxykD8LfKY9ML6u2jnxaEnrnM= github.com/json-iterator/go v1.1.12/go.mod h1:e30LSqwooZae/UwlEbR2852Gd8hjQvJoHmT4TnhNGBo= github.com/jstemmer/go-junit-report v0.0.0-20190106144839-af01ea7f8024/go.mod h1:6v2b51hI/fHJwM22ozAgKL4VKDeJcHhJFhtBdhmNjmU= @@ -1569,8 +1579,8 @@ github.com/jung-kurt/gofpdf v1.0.3-0.20190309125859-24315acbbda5/go.mod h1:7Id9E github.com/k-sone/critbitgo v1.4.0 h1:l71cTyBGeh6X5ATh6Fibgw3+rtNT80BA0uNNWgkPrbE= github.com/k-sone/critbitgo v1.4.0/go.mod h1:7E6pyoyADnFxlUBEKcnfS49b7SUAQGMK+OAp/UQvo0s= github.com/kballard/go-shellquote v0.0.0-20180428030007-95032a82bc51/go.mod h1:CzGEWj7cYgsdH8dAjBGEr58BoE7ScuLd+fwFZ44+/x8= -github.com/kentik/patricia v1.2.0 h1:WZcp8V8GQhsya0bMZuXktEH/Wz+aBlhiMle4tExkj6M= -github.com/kentik/patricia v1.2.0/go.mod h1:6jY40ESetsbfi04/S12iJlsiS6DYL2B2W+WAcqoDHtw= +github.com/kentik/patricia v1.2.1 h1:+ZyPXnEiFLbmT1yZR0JRfRUuNXmxROXdzI8YiSpTx5w= +github.com/kentik/patricia v1.2.1/go.mod h1:6jY40ESetsbfi04/S12iJlsiS6DYL2B2W+WAcqoDHtw= github.com/kevinburke/ssh_config v1.2.0 h1:x584FjTGwHzMwvHx18PXxbBVzfnxogHaAReU4gf13a4= github.com/kevinburke/ssh_config v1.2.0/go.mod h1:CT57kijsi8u/K/BOFA39wgDQJ9CxiF4nAY/ojJ6r6mM= github.com/kisielk/errcheck v1.5.0/go.mod h1:pFxgyoBC7bSaBwPgfKdkLd5X25qrDl4LWUI2bnpBCr8= @@ -1607,6 +1617,12 @@ github.com/mattn/go-sqlite3 v1.14.14/go.mod h1:NyWgC/yNuGj7Q9rpYnZvas74GogHl5/Z4 github.com/mattn/go-sqlite3 v1.14.15/go.mod h1:2eHXhiwb8IkHr+BDWZGa96P6+rkvnG63S2DGjv9HUNg= github.com/matttproud/golang_protobuf_extensions v1.0.4 h1:mmDVorXM7PCGKw94cs5zkfA9PSy5pEvNWRP0ET0TIVo= github.com/matttproud/golang_protobuf_extensions v1.0.4/go.mod h1:BSXmuO+STAnVfrANrmjBb36TMTDstsz7MSK+HVaYKv4= +github.com/mdlayher/genetlink v1.3.2 h1:KdrNKe+CTu+IbZnm/GVUMXSqBBLqcGpRDa0xkQy56gw= +github.com/mdlayher/genetlink v1.3.2/go.mod h1:tcC3pkCrPUGIKKsCsp0B3AdaaKuHtaxoJRz3cc+528o= +github.com/mdlayher/netlink v1.7.2 h1:/UtM3ofJap7Vl4QWCPDGXY8d3GIY2UGSDbK+QWmY8/g= +github.com/mdlayher/netlink v1.7.2/go.mod h1:xraEF7uJbxLhc5fpHL4cPe221LI2bdttWlU+ZGLfQSw= +github.com/mdlayher/socket v0.5.1 h1:VZaqt6RkGkt2OE9l3GcC6nZkqD3xKeQLyfleW/uBcos= +github.com/mdlayher/socket v0.5.1/go.mod h1:TjPLHI1UgwEv5J1B5q0zTZq12A/6H7nKmtTanQE37IQ= github.com/minio/asm2plan9s v0.0.0-20200509001527-cdd76441f9d8/go.mod h1:mC1jAcsrzbxHt8iiaC+zU4b1ylILSosueou12R++wfY= github.com/minio/c2goasm v0.0.0-20190812172519-36a3d3bbc4f3/go.mod h1:RagcQ7I8IeTMnF8JTXieKnO4Z6JCsikNEzj0DwauVzE= github.com/mitchellh/go-wordwrap v1.0.1 h1:TLuKupo69TCn6TQSyGxwI1EblZZEsQ0vMlAFQflz0v0= @@ -1646,14 +1662,14 @@ github.com/openconfig/gnmi v0.0.0-20200508230933-d19cebf5e7be/go.mod h1:M/EcuapN github.com/openconfig/gnmi v0.10.0/go.mod h1:Y9os75GmSkhHw2wX8sMsxfI7qRGAEcDh8NTa5a8vj6E= github.com/openconfig/gnmi v0.11.0 h1:H7pLIb/o3xObu3+x0Fv9DCK7TH3FUh7mNwbYe+34hFw= github.com/openconfig/gnmi v0.11.0/go.mod h1:9oJSQPPCpNvfMRj8e4ZoLVAw4wL8HyxXbiDlyuexCGU= -github.com/openconfig/gnoi v0.4.1-0.20240501161656-1d16819bab6a h1:wDllmsI9aUalYMF3Z0VQa2GZv8hcaHYfZsSNJARuUfk= -github.com/openconfig/gnoi v0.4.1-0.20240501161656-1d16819bab6a/go.mod h1:QVnt7KL8l6WphIfLuHHpgZfNO+MoXE610gSLOLV9VcI= +github.com/openconfig/gnoi v0.4.1 h1:sONbBqRBKjPT6voRAFqhTkUIatAajBp+YRLCWgyS4Dk= +github.com/openconfig/gnoi v0.4.1/go.mod h1:KDWxp9YvfRNR5BbiLy6uQSzHUpGhAtO8C80XXKLqNqU= github.com/openconfig/gnoigo v0.0.0-20240320202954-ebd033e3542c h1:egPgBUBDn0XEtbz0CvE+Bh/I/3iTzwzMq5/rmtPJdQs= github.com/openconfig/gnoigo v0.0.0-20240320202954-ebd033e3542c/go.mod h1:Se/HklUcFVcCGB66khgYouiesLRPoa4UL1ovvmE/68k= github.com/openconfig/gnpsi v0.3.2 h1:+bl1bXMOTrWOcGydWB+8wGgvxlgvL8Y6joAiWFU5sog= github.com/openconfig/gnpsi v0.3.2/go.mod h1:+Qj2PwadJ/jvGkH6H/A3XO9ZRKQRVtl3A30ubwz0M18= -github.com/openconfig/gnsi v1.4.5 h1:ZkUVN+HDg0GFe3wIYocWjPqjOHZP3vVEB+NIctaYV6c= -github.com/openconfig/gnsi v1.4.5/go.mod h1:i4guw9Vn3Mn/aUKB/2z84Moe2P811H3SV3g0Cu0X4h8= +github.com/openconfig/gnsi v1.6.0 h1:PfQa9Gy0lH1sHqA2L3Gj2fEh2zPMbWxMmIRQv2Nk1T8= +github.com/openconfig/gnsi v1.6.0/go.mod h1:RiHTEIb2ruIeWOOamms6vqbZtgmajDx+g5YJlF2hZ0k= github.com/openconfig/gocloser v0.0.0-20220310182203-c6c950ed3b0b h1:NSYuxdlOWLldNpid1dThR6Dci96juXioUguMho6aliI= github.com/openconfig/gocloser v0.0.0-20220310182203-c6c950ed3b0b/go.mod h1:uhC/ybmPapgeyAL2b9ZrUQ+DZE+DB+J+/7377PX+lek= github.com/openconfig/goyang v0.0.0-20200115183954-d0a48929f0ea/go.mod h1:dhXaV0JgHJzdrHi2l+w0fZrwArtXL7jEFoiqLEdmkvU= @@ -1664,20 +1680,20 @@ github.com/openconfig/goyang v1.4.5/go.mod h1:sdNZi/wdTZyLNBNfgLzmmbi7kISm7FskMD github.com/openconfig/gribi v0.1.1-0.20210423184541-ce37eb4ba92f/go.mod h1:OoH46A2kV42cIXGyviYmAlGmn6cHjGduyC2+I9d/iVs= github.com/openconfig/gribi v1.0.0 h1:xMwEg0mBD+21mOxuFOw0d9dBKuIPwJEhMUUeUulZdLg= github.com/openconfig/gribi v1.0.0/go.mod h1:VFqGH2ZPFIfnKTimP4/AQB4OK0eySW5muJNFxXAwP6k= -github.com/openconfig/gribigo v0.0.0-20231213034307-d0abeba7f432 h1:LADwzfGipdbqKnvHtbvN/MSZ3ttE9sli2B5VAAA8hpk= -github.com/openconfig/gribigo v0.0.0-20231213034307-d0abeba7f432/go.mod h1:fW2+Z2NiQ5L3hY/wrDsZBIvGYrM5ryHIzjHeVTiPzuM= +github.com/openconfig/gribigo v0.0.0-20240829231637-69cf06726cc3 h1:6w4kOXdXXLv3eASi3iXe3a0uHnhtrXmUx7fUqDt2FzA= +github.com/openconfig/gribigo v0.0.0-20240829231637-69cf06726cc3/go.mod h1:SVfLdNTmy/dIfScQFpljYKs0NGQ2n37h4GlZ9fVS+fA= github.com/openconfig/grpctunnel v0.0.0-20220819142823-6f5422b8ca70 h1:t6SvvdfWCMlw0XPlsdxO8EgO+q/fXnTevDjdYREKFwU= github.com/openconfig/grpctunnel v0.0.0-20220819142823-6f5422b8ca70/go.mod h1:OmTWe7RyZj2CIzIgy4ovEBzCLBJzRvWSZmn7u02U9gU= github.com/openconfig/kne v0.1.18 h1:8D9SexWhj6knxfvEficyVj0F13GIvF1pQz7TKwVDSUI= github.com/openconfig/kne v0.1.18/go.mod h1:VMKjKI9FoVTLh4uN94uoaFZCp1CDkml2Ms2qOi1B2WM= -github.com/openconfig/lemming v0.3.2-0.20230914210403-c6484d12af0a h1:JNiu6/3IWtESSq6N+dH65MYaeiDi5CF1Jck5YGvf3JE= -github.com/openconfig/lemming v0.3.2-0.20230914210403-c6484d12af0a/go.mod h1:fC8o1NYR9yEmDmoIVaCZQY+iP9RSxujYzckUGSkpWD8= +github.com/openconfig/lemming v0.4.1-0.20240731191322-a759a5e931a6 h1:MeZOAM3KyyJwCNRskjCuz9N1VXB20TPiOkyNYuZcbP8= +github.com/openconfig/lemming v0.4.1-0.20240731191322-a759a5e931a6/go.mod h1:mHnxyt20ewF4FznTqy+Op/CnCqXRNB7rJ/mm3wSJGxc= github.com/openconfig/lemming/operator v0.2.0 h1:dovZnR6lQkOHXcODli1NDOr/GVYrBY05KS5X11jxVbw= github.com/openconfig/lemming/operator v0.2.0/go.mod h1:LKgEXSR5VK2CAeh2uKijKAXFj42uQuwakrCHVPF0iII= github.com/openconfig/models-ci v1.0.2-0.20231113233730-f0986391428e h1:6N4jXpZa/SXYcNpJFjjZvenxO/xnTwuUCgCEinhNLfU= github.com/openconfig/models-ci v1.0.2-0.20231113233730-f0986391428e/go.mod h1:w38G/kObu95PbtwMYVp6SKhkHCegJFwL8B58Ns84g4s= -github.com/openconfig/ondatra v0.6.0 h1:wKedHwumAjJTFrbtEdWu71S4S6fO2IEXWgI6mQPtHho= -github.com/openconfig/ondatra v0.6.0/go.mod h1:8w9H5yGPctJrdeORW/WCK1sos+goQCqIx8ABTLNPR68= +github.com/openconfig/ondatra v0.6.1 h1:/N3mm4iJX3G8HcASu+qAKcJc/lJqKEaD8MFd6aRVWqc= +github.com/openconfig/ondatra v0.6.1/go.mod h1:ol5PMSLtZJEYPrTwTFpRCyQvAFeA5vQUTAEYFiAlXz0= github.com/openconfig/replayer v0.0.0-20240110192655-4e9cf83d8d30 h1:KcHS08m7nFHq/D03ZfZKKNCSaS1jsuvdF3lCyDjPWJc= github.com/openconfig/replayer v0.0.0-20240110192655-4e9cf83d8d30/go.mod h1:VQ8FdPVaHwxKtamhcrwkPsvTeeoEgFYNK1xE8nHD0S8= github.com/openconfig/testt v0.0.0-20220311054427-efbb1a32ec07 h1:X631iD/B0ximGFb5P9LY5wHju4SiedxUhc5UZEo7VSw= @@ -1687,9 +1703,11 @@ github.com/openconfig/ygnmi v0.11.1/go.mod h1:naCxQR+/wBItM82ilJXWgapCRkrx8bphBm github.com/openconfig/ygot v0.6.0/go.mod h1:o30svNf7O0xK+R35tlx95odkDmZWS9JyWWQSmIhqwAs= github.com/openconfig/ygot v0.10.4/go.mod h1:oCQNdXnv7dWc8scTDgoFkauv1wwplJn5HspHcjlxSAQ= github.com/openconfig/ygot v0.13.2/go.mod h1:kJN0yCXIH07dOXvNBEFm3XxXdnDD5NI6K99tnD5x49c= -github.com/openconfig/ygot v0.29.18 h1:vgG2r7RVwaVDXgHtpsCNW+qdSGSdxqRxUfRN2rPCy7M= -github.com/openconfig/ygot v0.29.18/go.mod h1:sp6roPPmVDcTCF2E3qTjILA+jzJMkZ9d6spC9KLMqpc= +github.com/openconfig/ygot v0.29.19 h1:3bbAWbCBVjyjHgeROvT38LQ7pAxcjtm7C2vNVj/rvEE= +github.com/openconfig/ygot v0.29.19/go.mod h1:8/FXt4tc5wSfYDEJbGGumxmxwJ55Xuv12oO/jCyEins= github.com/opentracing/opentracing-go v1.1.0/go.mod h1:UkNAQd3GIcIGf0SeVgPpRdFStlNbqXla1AfSYxPUl2o= +github.com/osrg/gobgp/v3 v3.27.1-0.20240614010451-0148e2d22dcf h1:KrVLbjNucHf+LrrGcwrH6hN0RyfmbPx9Vk5/iBsFfYY= +github.com/osrg/gobgp/v3 v3.27.1-0.20240614010451-0148e2d22dcf/go.mod h1:ZGeSti9mURR/o5hf5R6T1FM5g1yiEBZbhP+TuqYJUpI= github.com/p4lang/p4runtime v1.4.0-rc.5.0.20220728214547-13f0d02a521e h1:AfZKoikDXbZ7zWvO/lvCRzLo7i6lM+gNleYVMxPiWyQ= github.com/p4lang/p4runtime v1.4.0-rc.5.0.20220728214547-13f0d02a521e/go.mod h1:m9laObIMXM9N1ElGXijc66/MSM5eheZJLRLxg/TG+fU= github.com/patrickmn/go-cache v2.1.0+incompatible h1:HRMgzkcYKYpi3C8ajMPV8OFXaaRUnok+kx1WdO15EQc= @@ -1698,8 +1716,8 @@ github.com/pborman/getopt v0.0.0-20190409184431-ee0cd42419d3/go.mod h1:85jBQOZwp github.com/pborman/getopt v1.1.0/go.mod h1:FxXoW1Re00sQG/+KIkuSqRL/LwQgSkv7uyac+STFsbk= github.com/pborman/uuid v1.2.1 h1:+ZZIw58t/ozdjRaXh/3awHfmWRbzYxJoAdNJxe/3pvw= github.com/pborman/uuid v1.2.1/go.mod h1:X/NO0urCmaxf9VXbdlT7C2Yzkj2IKimNn4k+gtPdI/k= -github.com/pelletier/go-toml/v2 v2.2.0 h1:QLgLl2yMN7N+ruc31VynXs1vhMZa7CeHHejIeBAsoHo= -github.com/pelletier/go-toml/v2 v2.2.0/go.mod h1:1t835xjRzz80PqgE6HHgN2JOsmgYu/h4qDAS4n929Rs= +github.com/pelletier/go-toml/v2 v2.2.2 h1:aYUidT7k73Pcl9nb2gScu7NSrKCSHIDE89b3+6Wq+LM= +github.com/pelletier/go-toml/v2 v2.2.2/go.mod h1:1t835xjRzz80PqgE6HHgN2JOsmgYu/h4qDAS4n929Rs= github.com/phpdave11/gofpdf v1.4.2/go.mod h1:zpO6xFn9yxo3YLyMvW8HcKWVdbNqgIfOOp2dXMnm1mY= github.com/phpdave11/gofpdi v1.0.12/go.mod h1:vBmVV0Do6hSBHC8uKUQ71JGW+ZGQq74llk/7bXwjDoI= github.com/phpdave11/gofpdi v1.0.13/go.mod h1:vBmVV0Do6hSBHC8uKUQ71JGW+ZGQq74llk/7bXwjDoI= @@ -1712,6 +1730,8 @@ github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4= github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= github.com/pkg/sftp v1.10.1/go.mod h1:lYOWFsE0bwd1+KfKJaKeuokY15vzFx25BLbzYYoAxZI= github.com/pkg/sftp v1.13.1/go.mod h1:3HaPG6Dq1ILlpPZRO0HVMrsydcdLt6HRDccSgb87qRg= +github.com/planetscale/vtprotobuf v0.6.1-0.20240319094008-0393e58bdf10 h1:GFCKgmp0tecUJ0sJuv4pzYCqS9+RGSn52M3FUwPs+uo= +github.com/planetscale/vtprotobuf v0.6.1-0.20240319094008-0393e58bdf10/go.mod h1:t/avpk3KcrXxUnYOhZhMXJlSEyie6gQbtLq5NM3loB8= github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2 h1:Jamvg5psRIccs7FGNTlIRMkT8wgtp5eCXdBlqhYGL6U= github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= @@ -1721,8 +1741,9 @@ github.com/prometheus/client_model v0.0.0-20190812154241-14fe0d1b01d4/go.mod h1: github.com/prometheus/client_model v0.2.0/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA= github.com/prometheus/client_model v0.3.0/go.mod h1:LDGWKZIo7rky3hgvBe+caln+Dr3dPggB5dvjtD7w9+w= github.com/prometheus/client_model v0.4.0/go.mod h1:oMQmHW1/JoDwqLtg57MGgP/Fb1CJEYF2imWWhWtMkYU= -github.com/prometheus/client_model v0.5.0 h1:VQw1hfvPvk3Uv6Qf29VrPF32JB6rtbgI6cYPYQjL0Qw= github.com/prometheus/client_model v0.5.0/go.mod h1:dTiFglRmd66nLR9Pv9f0mZi7B7fk5Pm3gvsjB5tr+kI= +github.com/prometheus/client_model v0.6.0 h1:k1v3CzpSRUTrKMppY35TLwPvxHqBu0bYgxZzqGIgaos= +github.com/prometheus/client_model v0.6.0/go.mod h1:NTQHnmxFpouOD0DpvP4XujX3CdOAGQPoaGhyTchlyt8= github.com/prometheus/common v0.42.0 h1:EKsfXEYo4JpWMHH5cg+KOUWeuJSov1Id8zGR8eeI1YM= github.com/prometheus/common v0.42.0/go.mod h1:xBwqVerjNdUDjgODMpudtOMwlOwf2SaTr1yjz4b7Zbc= github.com/prometheus/procfs v0.9.0 h1:wzCHvIvM5SxWqYvwgVL7yJY8Lz3PKn49KQtpgMYJfhI= @@ -1740,8 +1761,8 @@ github.com/rogpeppe/go-internal v1.11.0/go.mod h1:ddIwULY96R17DhadqLgMfk9H9tvdUz github.com/russross/blackfriday/v2 v2.1.0/go.mod h1:+Rmxgy9KzJVeS9/2gXHxylqXiyQDYRxCVz55jmeOWTM= github.com/ruudk/golang-pdf417 v0.0.0-20181029194003-1af4ab5afa58/go.mod h1:6lfFZQK844Gfx8o5WFuvpxWRwnSoipWe/p622j1v06w= github.com/ruudk/golang-pdf417 v0.0.0-20201230142125-a7e3863a1245/go.mod h1:pQAZKsJ8yyVxGRWYNEm9oFB8ieLgKFnamEyDmSA0BRk= -github.com/sagikazarmark/locafero v0.4.0 h1:HApY1R9zGo4DBgr7dqsTH/JJxLTTsOt7u6keLGt6kNQ= -github.com/sagikazarmark/locafero v0.4.0/go.mod h1:Pe1W6UlPYUk/+wc/6KFhbORCfqzgYEpgQ3O5fPuL3H4= +github.com/sagikazarmark/locafero v0.6.0 h1:ON7AQg37yzcRPU69mt7gwhFEBwxI6P9T4Qu3N51bwOk= +github.com/sagikazarmark/locafero v0.6.0/go.mod h1:77OmuIc6VTraTXKXIs/uvUxKGUXjE1GbemJYHqdNjX0= github.com/sagikazarmark/slog-shim v0.1.0 h1:diDBnUNK9N/354PgrxMywXnAwEr1QZcOr6gto+ugjYE= github.com/sagikazarmark/slog-shim v0.1.0/go.mod h1:SrcSrq8aKtyuqEI1uvTDTK1arOWRIczQRv+GVI1AkeQ= github.com/scrapli/scrapligo v1.0.0/go.mod h1:jvRMdb90MNnswMiku8UNXj8JZaOIPhwhcqqFwr9qeoY= @@ -1775,8 +1796,8 @@ github.com/spf13/cobra v1.8.0 h1:7aJaZx1B85qltLMc546zn58BxxfZdR/W22ej9CFoEf0= github.com/spf13/cobra v1.8.0/go.mod h1:WXLWApfZ71AjXPya3WOlMsY9yMs7YeiHhFVlvLyhcho= github.com/spf13/pflag v1.0.5 h1:iy+VFUOCP1a+8yFto/drg2CJ5u0yRoB7fZw3DKv/JXA= github.com/spf13/pflag v1.0.5/go.mod h1:McXfInJRrz4CZXVZOBLb0bTZqETkiAhM9Iw0y3An2Bg= -github.com/spf13/viper v1.18.2 h1:LUXCnvUvSM6FXAsj6nnfc8Q2tp1dIgUfY9Kc8GsSOiQ= -github.com/spf13/viper v1.18.2/go.mod h1:EKmWIqdnk5lOcmR72yw6hS+8OPYcwD0jteitLMVB+yk= +github.com/spf13/viper v1.19.0 h1:RWq5SEjt8o25SROyN3z2OrDB9l7RPd3lwTWU8EcEdcI= +github.com/spf13/viper v1.19.0/go.mod h1:GQUN9bilAbhU/jgc1bKs99f/suXKeUMct8Adx5+Ntkg= github.com/srl-labs/srl-controller v0.6.1 h1:hHduqG41wglpeVPD85RALTwWWcS+NqvU8V1pHJMQIZo= github.com/srl-labs/srl-controller v0.6.1/go.mod h1:PedxdPZPtDcC+wDOKhG6uXR4xgkHxb4JhW1cXNk/eaY= github.com/srl-labs/srlinux-scrapli v0.6.0 h1:YQjckD+a7f6u2M+k4SmJUrDa7BFvoOTb2mMbPe6hLZM= @@ -1807,8 +1828,6 @@ github.com/vishvananda/netlink v1.2.1-beta.2 h1:Llsql0lnQEbHj0I1OuKyp8otXp0r3q0m github.com/vishvananda/netlink v1.2.1-beta.2/go.mod h1:twkDnbuQxJYemMlGd4JFIcuhgX83tXhKS2B/PRMpOho= github.com/vishvananda/netns v0.0.4 h1:Oeaw1EM2JMxD51g9uhtC0D7erkIjgmj8+JZc26m1YX8= github.com/vishvananda/netns v0.0.4/go.mod h1:SpkAiCQRtJ6TvvxPnOSyH3BMl6unz3xZlaprSwhNNJM= -github.com/wenovus/gobgp/v3 v3.0.0-20230831013712-6d33842cbf42 h1:jse5eORjbrlTIOPzOO3cpm4feJ16ZCntxzAHSdcWuy4= -github.com/wenovus/gobgp/v3 v3.0.0-20230831013712-6d33842cbf42/go.mod h1:P+5INtnzris2TTpWI4m1/RwqCUhniEqc/SOZw5CQCMo= github.com/xanzy/ssh-agent v0.3.3 h1:+/15pJfg/RsTxqYcX6fHqOXZwwMP+2VyYWJeWM2qQFM= github.com/xanzy/ssh-agent v0.3.3/go.mod h1:6dzNDKs0J9rVPHPhaGCukekBHKqfl+L3KghI1Bc68Uw= github.com/xeipuuv/gojsonpointer v0.0.0-20180127040702-4e3ac2762d5f/go.mod h1:N2zxlSyiKSe5eX1tZViRH5QA0qijqEDrYZiPEAiq3wU= @@ -1838,26 +1857,27 @@ go.opencensus.io v0.23.0/go.mod h1:XItmlyltB5F7CS4xOC1DcqMoFqwtC6OG2xF7mCv7P7E= go.opencensus.io v0.24.0 h1:y73uSU6J157QMP2kn2r30vwW1A2W2WFwSCGnAVxeaD0= go.opencensus.io v0.24.0/go.mod h1:vNK8G9p7aAivkbmorf4v+7Hgx+Zs0yY+0fOtgBfjQKo= go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc v0.46.1/go.mod h1:4UoMYEZOC0yN/sPGH76KPkkU7zgiEWYWL9vwmbnTJPE= -go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc v0.47.0 h1:UNQQKPfTDe1J81ViolILjTKPr9WetKW6uei2hFgJmFs= -go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc v0.47.0/go.mod h1:r9vWsPS/3AQItv3OSlEJ/E4mbrhUbbw18meOjArPtKQ= +go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc v0.49.0 h1:4Pp6oUg3+e/6M4C0A/3kJ2VYa++dsWVTtGgLVj5xtHg= +go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc v0.49.0/go.mod h1:Mjt1i1INqiaoZOMGR1RIUJN+i3ChKoFRqzrRQhlkbs0= go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.46.1/go.mod h1:sEGXWArGqc3tVa+ekntsN65DmVbVeW+7lTKTjZF3/Fo= -go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.47.0 h1:sv9kVfal0MK0wBMCOGr+HeJm9v803BkJxGrk2au7j08= -go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.47.0/go.mod h1:SK2UL73Zy1quvRPonmOmRDiWk1KBV3LyIeeIxcEApWw= +go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.49.0 h1:jq9TW8u3so/bN+JPT166wjOI6/vQPF6Xe7nMNIltagk= +go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.49.0/go.mod h1:p8pYQP+m5XfbZm9fxtSKAbM6oIllS7s2AfxrChvc7iw= go.opentelemetry.io/otel v1.19.0/go.mod h1:i0QyjOq3UPoTzff0PJB2N66fb4S0+rSbSB15/oyH9fY= go.opentelemetry.io/otel v1.21.0/go.mod h1:QZzNPQPm1zLX4gZK4cMi+71eaorMSGT3A4znnUvNNEo= -go.opentelemetry.io/otel v1.22.0 h1:xS7Ku+7yTFvDfDraDIJVpw7XPyuHlB9MCiqqX5mcJ6Y= -go.opentelemetry.io/otel v1.22.0/go.mod h1:eoV4iAi3Ea8LkAEI9+GFT44O6T/D0GWAVFyZVCC6pMI= +go.opentelemetry.io/otel v1.24.0 h1:0LAOdjNmQeSTzGBzduGe/rU4tZhMwL5rWgtp9Ku5Jfo= +go.opentelemetry.io/otel v1.24.0/go.mod h1:W7b9Ozg4nkF5tWI5zsXkaKKDjdVjpD4oAt9Qi/MArHo= go.opentelemetry.io/otel/metric v1.19.0/go.mod h1:L5rUsV9kM1IxCj1MmSdS+JQAcVm319EUrDVLrt7jqt8= go.opentelemetry.io/otel/metric v1.21.0/go.mod h1:o1p3CA8nNHW8j5yuQLdc1eeqEaPfzug24uvsyIEJRWM= -go.opentelemetry.io/otel/metric v1.22.0 h1:lypMQnGyJYeuYPhOM/bgjbFM6WE44W1/T45er4d8Hhg= -go.opentelemetry.io/otel/metric v1.22.0/go.mod h1:evJGjVpZv0mQ5QBRJoBF64yMuOf4xCWdXjK8pzFvliY= +go.opentelemetry.io/otel/metric v1.24.0 h1:6EhoGWWK28x1fbpA4tYTOWBkPefTDQnb8WSGXlc88kI= +go.opentelemetry.io/otel/metric v1.24.0/go.mod h1:VYhLe1rFfxuTXLgj4CBiyz+9WYBA8pNGJgDcSFRKBco= go.opentelemetry.io/otel/sdk v1.19.0/go.mod h1:NedEbbS4w3C6zElbLdPJKOpJQOrGUJ+GfzpjUvI0v1A= -go.opentelemetry.io/otel/sdk v1.21.0 h1:FTt8qirL1EysG6sTQRZ5TokkU8d0ugCj8htOgThZXQ8= go.opentelemetry.io/otel/sdk v1.21.0/go.mod h1:Nna6Yv7PWTdgJHVRD9hIYywQBRx7pbox6nwBnZIxl/E= +go.opentelemetry.io/otel/sdk v1.22.0 h1:6coWHw9xw7EfClIC/+O31R8IY3/+EiRFHevmHafB2Gw= +go.opentelemetry.io/otel/sdk v1.22.0/go.mod h1:iu7luyVGYovrRpe2fmj3CVKouQNdTOkxtLzPvPz1DOc= go.opentelemetry.io/otel/trace v1.19.0/go.mod h1:mfaSyvGyEJEI0nyV2I4qhNQnbBOUUmYZpYojqMnX2vo= go.opentelemetry.io/otel/trace v1.21.0/go.mod h1:LGbsEB0f9LGjN+OZaQQ26sohbOmiMR+BaslueVtS/qQ= -go.opentelemetry.io/otel/trace v1.22.0 h1:Hg6pPujv0XG9QaVbGOBVHunyuLcCC3jN7WEhPx83XD0= -go.opentelemetry.io/otel/trace v1.22.0/go.mod h1:RbbHXVqKES9QhzZq/fE5UnOSILqRt40a21sPw2He1xo= +go.opentelemetry.io/otel/trace v1.24.0 h1:CsKnnL4dUAr/0llH9FKuc698G04IrpWV0MQA/Y1YELI= +go.opentelemetry.io/otel/trace v1.24.0/go.mod h1:HPc3Xr/cOApsBI154IU0OI0HJexz+aw5uPdbs3UCjNU= go.opentelemetry.io/proto/otlp v0.7.0/go.mod h1:PqfVotwruBrMGOCsRd/89rSnXhoiJIqeYNgFYFoEGnI= go.opentelemetry.io/proto/otlp v0.15.0/go.mod h1:H7XAot3MsfNsj7EXtrA2q5xSNQ10UqI405h3+duxN4U= go.opentelemetry.io/proto/otlp v0.19.0/go.mod h1:H7XAot3MsfNsj7EXtrA2q5xSNQ10UqI405h3+duxN4U= @@ -1900,8 +1920,8 @@ golang.org/x/crypto v0.15.0/go.mod h1:4ChreQoLWfG3xLDer1WdlH5NdlQ3+mwnQq1YTKY+72 golang.org/x/crypto v0.16.0/go.mod h1:gCAAfMLgwOJRpTjQ2zCCt2OcSfYMTeZVSRtQlPC7Nq4= golang.org/x/crypto v0.17.0/go.mod h1:gCAAfMLgwOJRpTjQ2zCCt2OcSfYMTeZVSRtQlPC7Nq4= golang.org/x/crypto v0.18.0/go.mod h1:R0j02AL6hcrfOiy9T4ZYp/rcWeMxM3L6QYxlOuEG1mg= -golang.org/x/crypto v0.21.0 h1:X31++rzVUdKhX5sWmSOFZxx8UW/ldWx55cbf08iNAMA= -golang.org/x/crypto v0.21.0/go.mod h1:0BP7YvVV9gBbVKyeTG0Gyn+gZm94bibOW5BjDEYAOMs= +golang.org/x/crypto v0.27.0 h1:GXm2NjJrPaiv/h1tb2UH8QfgC/hOf/+z0p6PT8o1w7A= +golang.org/x/crypto v0.27.0/go.mod h1:1Xngt8kV6Dvbssa53Ziq6Eqn0HqbZi5Z6R0ZpwQzt70= golang.org/x/exp v0.0.0-20180321215751-8460e604b9de/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= golang.org/x/exp v0.0.0-20180807140117-3d87b88a115f/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= golang.org/x/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= @@ -1917,8 +1937,8 @@ golang.org/x/exp v0.0.0-20200119233911-0405dc783f0a/go.mod h1:2RIsYlXP63K8oxa1u0 golang.org/x/exp v0.0.0-20200207192155-f17229e696bd/go.mod h1:J/WKrq2StrnmMY6+EHIKF9dgMWnmCNThgcyBT1FY9mM= golang.org/x/exp v0.0.0-20200224162631-6cc2880d07d6/go.mod h1:3jZMyOhIsHpP37uCMkUooju7aAi5cS1Q23tOzKc+0MU= golang.org/x/exp v0.0.0-20220827204233-334a2380cb91/go.mod h1:cyybsKvd6eL0RnXn6p/Grxp8F5bW7iYuBgsNCOHpMYE= -golang.org/x/exp v0.0.0-20240325151524-a685a6edb6d8 h1:aAcj0Da7eBAtrTp03QXWvm88pSyOt+UgdZw2BFZ+lEw= -golang.org/x/exp v0.0.0-20240325151524-a685a6edb6d8/go.mod h1:CQ1k9gNrJ50XIzaKCRR2hssIjF07kZFEiieALBM/ARQ= +golang.org/x/exp v0.0.0-20240604190554-fc45aab8b7f8 h1:LoYXNGAShUG3m/ehNk4iFctuhGX/+R1ZpfJ4/ia80JM= +golang.org/x/exp v0.0.0-20240604190554-fc45aab8b7f8/go.mod h1:jj3sYF3dwk5D+ghuXyeI3r5MFf+NT2An6/9dOA95KSI= golang.org/x/image v0.0.0-20180708004352-c73c2afc3b81/go.mod h1:ux5Hcp/YLpHSI86hEcLt0YII63i6oz57MZXIpbrjZUs= golang.org/x/image v0.0.0-20190227222117-0694c2d4d067/go.mod h1:kZ7UVZpmo3dzQBMxlp+ypCbDeSB+sBbTgSJuh5dn5js= golang.org/x/image v0.0.0-20190802002840-cff245a6509b/go.mod h1:FeLwcggjj3mMvU+oOTbSwawSJRM1uh48EjtB4UJZlP0= @@ -1964,8 +1984,8 @@ golang.org/x/mod v0.9.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs= golang.org/x/mod v0.10.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs= golang.org/x/mod v0.11.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs= golang.org/x/mod v0.12.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs= -golang.org/x/mod v0.16.0 h1:QX4fJ0Rr5cPQCF7O9lh9Se4pmwfwskqZfq5moyldzic= -golang.org/x/mod v0.16.0/go.mod h1:hTbmBsO62+eylJbnUtE2MGJUyE7QWk4xUqPFrRgJ+7c= +golang.org/x/mod v0.18.0 h1:5+9lSbEzPSdWkH32vYPBwEpX8KwDbM52Ud9xBUvNlb0= +golang.org/x/mod v0.18.0/go.mod h1:hTbmBsO62+eylJbnUtE2MGJUyE7QWk4xUqPFrRgJ+7c= golang.org/x/net v0.0.0-20180724234803-3673e40ba225/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20180826012351-8a410e7b638d/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20190108225652-1e06a53dbb7e/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= @@ -2037,8 +2057,8 @@ golang.org/x/net v0.17.0/go.mod h1:NxSsAGuq816PNPmqtQdLE42eU2Fs7NoRIZrHJAlaCOE= golang.org/x/net v0.18.0/go.mod h1:/czyP5RqHAH4odGYxBJ1qz0+CE5WZ+2j1YgoEo8F2jQ= golang.org/x/net v0.19.0/go.mod h1:CfAk/cbD4CthTvqiEl8NpboMuiuOYsAr/7NOjZJtv1U= golang.org/x/net v0.20.0/go.mod h1:z8BVo6PvndSri0LbOE3hAn0apkU+1YvI6E70E9jsnvY= -golang.org/x/net v0.23.0 h1:7EYJ93RZ9vYSZAIb2x3lnuvqO5zneoD6IvWjuhfxjTs= -golang.org/x/net v0.23.0/go.mod h1:JKghWKKOSdJwpW2GEx0Ja7fmaKnMsbu+MWVZTokSYmg= +golang.org/x/net v0.29.0 h1:5ORfpBpCs4HzDYoodCDBbwHzdR5UrLBZ3sOnUJmFoHo= +golang.org/x/net v0.29.0/go.mod h1:gLkgy8jTGERgjzMic6DS9+SP0ajcu6Xu3Orq/SpETg0= golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U= golang.org/x/oauth2 v0.0.0-20190226205417-e64efc72b421/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= golang.org/x/oauth2 v0.0.0-20190604053449-0f29369cfe45/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= @@ -2074,8 +2094,8 @@ golang.org/x/oauth2 v0.11.0/go.mod h1:LdF7O/8bLR/qWK9DrpXmbHLTouvRHK0SgJl0GmDBch golang.org/x/oauth2 v0.13.0/go.mod h1:/JMhi4ZRXAf4HG9LiNmxvk+45+96RUlVThiH8FzNBn0= golang.org/x/oauth2 v0.15.0/go.mod h1:q48ptWNTY5XWf+JNten23lcvHpLJ0ZSxF5ttTHKVCAM= golang.org/x/oauth2 v0.16.0/go.mod h1:hqZ+0LWXsiVoZpeld6jVt06P3adbS2Uu911W1SsJv2o= -golang.org/x/oauth2 v0.17.0 h1:6m3ZPmLEFdVxKKWnKq4VqZ60gutO35zm+zrAHVmHyDQ= -golang.org/x/oauth2 v0.17.0/go.mod h1:OzPDGQiuQMguemayvdylqddI7qcD9lnSDb+1FiwQ5HA= +golang.org/x/oauth2 v0.21.0 h1:tsimM75w1tF/uws5rbeHzIWxEqElMehnc+iW793zsZs= +golang.org/x/oauth2 v0.21.0/go.mod h1:XYTD2NtWslqkgxebSiOHnXEap4TF09sJSc7H1sXbhtI= golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20181108010431-42b317875d0f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20181221193216-37e7f081c4d4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= @@ -2096,8 +2116,9 @@ golang.org/x/sync v0.2.0/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.3.0/go.mod h1:FU7BRWz2tNW+3quACPkgCx/L+uEAv1htQ0V83Z9Rj+Y= golang.org/x/sync v0.4.0/go.mod h1:FU7BRWz2tNW+3quACPkgCx/L+uEAv1htQ0V83Z9Rj+Y= golang.org/x/sync v0.5.0/go.mod h1:Czt+wKu1gCyEFDUtn0jG5QVvpJ6rzVqr5aXyt9drQfk= -golang.org/x/sync v0.6.0 h1:5BMeUDZ7vkXGfEr1x9B4bRcTH4lpkTkpdh0T/J+qjbQ= golang.org/x/sync v0.6.0/go.mod h1:Czt+wKu1gCyEFDUtn0jG5QVvpJ6rzVqr5aXyt9drQfk= +golang.org/x/sync v0.8.0 h1:3NFvSEYkUoMifnESzZl15y791HH1qU2xm6eCJU5ZPXQ= +golang.org/x/sync v0.8.0/go.mod h1:Czt+wKu1gCyEFDUtn0jG5QVvpJ6rzVqr5aXyt9drQfk= golang.org/x/sys v0.0.0-20180830151530-49385e6e1522/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20190312061237-fead79001313/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= @@ -2192,8 +2213,8 @@ golang.org/x/sys v0.13.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.14.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= golang.org/x/sys v0.15.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= golang.org/x/sys v0.16.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= -golang.org/x/sys v0.20.0 h1:Od9JTbYCk261bKm4M/mw7AklTlFYIa0bIp9BgSm1S8Y= -golang.org/x/sys v0.20.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= +golang.org/x/sys v0.25.0 h1:r+8e+loiHxRqhXVl6ML1nO3l1+oFoWbnlu2Ehimmi34= +golang.org/x/sys v0.25.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= golang.org/x/term v0.1.0/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= @@ -2212,8 +2233,8 @@ golang.org/x/term v0.13.0/go.mod h1:LTmsnFJwVN6bCy1rVCoS+qHT1HhALEFxKncY3WNNh4U= golang.org/x/term v0.14.0/go.mod h1:TySc+nGkYR6qt8km8wUhuFRTVSMIX3XPR58y2lC8vww= golang.org/x/term v0.15.0/go.mod h1:BDl952bC7+uMoWR75FIrCDx79TPU9oHkTZ9yRbYOrX0= golang.org/x/term v0.16.0/go.mod h1:yn7UURbUtPyrVJPGPq404EukNFxcm/foM+bV/bfcDsY= -golang.org/x/term v0.18.0 h1:FcHjZXDMxI8mM3nwhX9HlKop4C0YQvCVCdwYl2wOtE8= -golang.org/x/term v0.18.0/go.mod h1:ILwASektA3OnRv7amZ1xhE/KTR+u50pbXfZ03+6Nx58= +golang.org/x/term v0.24.0 h1:Mh5cbb+Zk2hqqXNO7S1iTjEphVL+jb8ZWaqh/g+JWkM= +golang.org/x/term v0.24.0/go.mod h1:lOBK/LVxemqiMij05LGJ0tzNr8xlmwBRJ81PX6wVLH8= golang.org/x/text v0.0.0-20170915032832-14c0d48ead0c/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.1-0.20180807135948-17ff2d5776d2/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= @@ -2234,8 +2255,9 @@ golang.org/x/text v0.10.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE= golang.org/x/text v0.11.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE= golang.org/x/text v0.12.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE= golang.org/x/text v0.13.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE= -golang.org/x/text v0.14.0 h1:ScX5w1eTa3QqT8oi6+ziP7dTV1S2+ALU0bI+0zXKWiQ= golang.org/x/text v0.14.0/go.mod h1:18ZOQIKpY8NJVqYksKHtTdi31H5itFRjB5/qKTNYzSU= +golang.org/x/text v0.18.0 h1:XvMDiNzPAl0jr17s6W9lcaIhGUfUORdGCNsuLmPG224= +golang.org/x/text v0.18.0/go.mod h1:BuEKDfySbSR4drPmRPG/7iBdf8hvFMuRexcpahXilzY= golang.org/x/time v0.0.0-20181108054448-85acf8d2951c/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/time v0.0.0-20190308202827-9d24e82272b4/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/time v0.0.0-20191024005414-555d28b269f0/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= @@ -2312,8 +2334,8 @@ golang.org/x/tools v0.8.0/go.mod h1:JxBZ99ISMI5ViVkT1tr6tdNmXeTrcpVSD3vZ1RsRdN4= golang.org/x/tools v0.9.1/go.mod h1:owI94Op576fPu3cIGQeHs3joujW/2Oc6MtlxbF5dfNc= golang.org/x/tools v0.10.0/go.mod h1:UJwyiVBsOA2uwvK/e5OY3GTpDUJriEd+/YlqAwLPmyM= golang.org/x/tools v0.13.0/go.mod h1:HvlwmtVNQAhOuCjW7xxvovg8wbNq7LwfXh/k7wXUl58= -golang.org/x/tools v0.19.0 h1:tfGCXNR1OsFG+sVdLAitlpjAvD/I6dHDKnYrpEZUHkw= -golang.org/x/tools v0.19.0/go.mod h1:qoJWxmGSIBmAeriMx19ogtrEPrGtDbPK634QFIcLAhc= +golang.org/x/tools v0.22.0 h1:gqSGLZqv+AI9lIQzniJ0nZDRG5GBPsSi+DRNHWNz6yA= +golang.org/x/tools v0.22.0/go.mod h1:aCwcsjqvq7Yqt6TNyX7QMU2enbQ/Gt0bo6krSeEri+c= golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= @@ -2401,8 +2423,8 @@ google.golang.org/api v0.139.0/go.mod h1:CVagp6Eekz9CjGZ718Z+sloknzkDJE7Vc1Ckj9+ google.golang.org/api v0.149.0/go.mod h1:Mwn1B7JTXrzXtnvmzQE2BD6bYZQ8DShKZDZbeN9I7qI= google.golang.org/api v0.150.0/go.mod h1:ccy+MJ6nrYFgE3WgRx/AMXOxOmU8Q4hSa+jjibzhxcg= google.golang.org/api v0.155.0/go.mod h1:GI5qK5f40kCpHfPn6+YzGAByIKWv8ujFnmoWm7Igduk= -google.golang.org/api v0.162.0 h1:Vhs54HkaEpkMBdgGdOT2P6F0csGG/vxDS0hWHJzmmps= -google.golang.org/api v0.162.0/go.mod h1:6SulDkfoBIg4NFmCuZ39XeeAgSHCPecfSUuDyYlAHs0= +google.golang.org/api v0.171.0 h1:w174hnBPqut76FzW5Qaupt7zY8Kql6fiVjgys4f58sU= +google.golang.org/api v0.171.0/go.mod h1:Hnq5AHm4OTMt2BUVjael2CWZFD6vksJdWCWiUAmjC9o= google.golang.org/appengine v1.1.0/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9YwlJXL52JkM= google.golang.org/appengine v1.4.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= google.golang.org/appengine v1.5.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= @@ -2410,7 +2432,6 @@ google.golang.org/appengine v1.6.1/go.mod h1:i06prIuMbXzDqacNJfV5OdTW448YApPu5ww google.golang.org/appengine v1.6.5/go.mod h1:8WjMMxjGQR8xUklV/ARdw2HLXBOI7O7uCIDZVag1xfc= google.golang.org/appengine v1.6.6/go.mod h1:8WjMMxjGQR8xUklV/ARdw2HLXBOI7O7uCIDZVag1xfc= google.golang.org/appengine v1.6.7/go.mod h1:8WjMMxjGQR8xUklV/ARdw2HLXBOI7O7uCIDZVag1xfc= -google.golang.org/appengine v1.6.8 h1:IhEN5q69dyKagZPYMSdIjS2HqprW324FRQZJcGqPAsM= google.golang.org/appengine v1.6.8/go.mod h1:1jJ3jBArFh5pcgW8gCtRJnepW8FzD1V44FJffLiz/Ds= google.golang.org/genproto v0.0.0-20180817151627-c66870c02cf8/go.mod h1:JiN7NxoALGmiZfu7CAH4rXhgtRTLTxftemlI0sWmxmc= google.golang.org/genproto v0.0.0-20190307195333-5fe7a883aa19/go.mod h1:VzzqZJRnGkLBvHegQrXjBqPurQTc5/KpmUdxsrq26oE= @@ -2598,8 +2619,8 @@ google.golang.org/genproto/googleapis/api v0.0.0-20231212172506-995d672761c0/go. google.golang.org/genproto/googleapis/api v0.0.0-20240102182953-50ed04b92917/go.mod h1:CmlNWB9lSezaYELKS5Ym1r44VrrbPUa7JTvw+6MbpJ0= google.golang.org/genproto/googleapis/api v0.0.0-20240116215550-a9fa1716bcac/go.mod h1:B5xPO//w8qmBDjGReYLpR6UJPnkldGkCSMoH/2vxJeg= google.golang.org/genproto/googleapis/api v0.0.0-20240123012728-ef4313101c80/go.mod h1:4jWUdICTdgc3Ibxmr8nAJiiLHwQBY0UI0XZcEMaFKaA= -google.golang.org/genproto/googleapis/api v0.0.0-20240227224415-6ceb2ff114de h1:jFNzHPIeuzhdRwVhbZdiym9q0ory/xY3sA+v2wPg8I0= -google.golang.org/genproto/googleapis/api v0.0.0-20240227224415-6ceb2ff114de/go.mod h1:5iCWqnniDlqZHrd3neWVTOwvh/v6s3232omMecelax8= +google.golang.org/genproto/googleapis/api v0.0.0-20240604185151-ef581f913117 h1:+rdxYoE3E5htTEWIe15GlN6IfvbURM//Jt0mmkmm6ZU= +google.golang.org/genproto/googleapis/api v0.0.0-20240604185151-ef581f913117/go.mod h1:OimBR/bc1wPO9iV4NC2bpyjy3VnAwZh5EBPQdtaE5oo= google.golang.org/genproto/googleapis/bytestream v0.0.0-20230530153820-e85fd2cbaebc/go.mod h1:ylj+BE99M198VPbBh6A8d9n3w8fChvyLK3wwBOjXBFA= google.golang.org/genproto/googleapis/bytestream v0.0.0-20230807174057-1744710a1577/go.mod h1:NjCQG/D8JandXxM57PZbAJL1DCNL6EypA0vPPwfsc7c= google.golang.org/genproto/googleapis/bytestream v0.0.0-20231030173426-d783a09b4405/go.mod h1:GRUCuLdzVqZte8+Dl/D4N25yLzcGqqWaYkeVOwulFqw= @@ -2627,8 +2648,8 @@ google.golang.org/genproto/googleapis/rpc v0.0.0-20231212172506-995d672761c0/go. google.golang.org/genproto/googleapis/rpc v0.0.0-20240102182953-50ed04b92917/go.mod h1:xtjpI3tXFPP051KaWnhvxkiubL/6dJ18vLVf7q2pTOU= google.golang.org/genproto/googleapis/rpc v0.0.0-20240116215550-a9fa1716bcac/go.mod h1:daQN87bsDqDoe316QbbvX60nMoJQa4r6Ds0ZuoAe5yA= google.golang.org/genproto/googleapis/rpc v0.0.0-20240123012728-ef4313101c80/go.mod h1:PAREbraiVEVGVdTZsVWjSbbTtSyGbAgIIvni8a8CD5s= -google.golang.org/genproto/googleapis/rpc v0.0.0-20240401170217-c3f982113cda h1:LI5DOvAxUPMv/50agcLLoo+AdWc1irS9Rzz4vPuD1V4= -google.golang.org/genproto/googleapis/rpc v0.0.0-20240401170217-c3f982113cda/go.mod h1:WtryC6hu0hhx87FDGxWCDptyssuo68sk10vYjF+T9fY= +google.golang.org/genproto/googleapis/rpc v0.0.0-20240903143218-8af14fe29dc1 h1:pPJltXNxVzT4pK9yD8vR9X75DaWYYmLGMsEvBfFQZzQ= +google.golang.org/genproto/googleapis/rpc v0.0.0-20240903143218-8af14fe29dc1/go.mod h1:UqMtugtsSgubUsoxbuAoiCXvqvErP7Gf0so0mK9tHxU= google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c= google.golang.org/grpc v1.20.1/go.mod h1:10oTOabMzJvdu6/UiuZezV6QK5dSlG84ov/aaiqXj38= google.golang.org/grpc v1.21.1/go.mod h1:oYelfM1adQP15Ek0mdvEgi9Df8B9CZIaU1084ijfRaM= @@ -2681,8 +2702,8 @@ google.golang.org/grpc v1.59.0/go.mod h1:aUPDwccQo6OTjy7Hct4AfBPD1GptF4fyUjIkQ9Y google.golang.org/grpc v1.60.0/go.mod h1:OlCHIeLYqSSsLi6i49B5QGdzaMZK9+M7LXN2FKz4eGM= google.golang.org/grpc v1.60.1/go.mod h1:OlCHIeLYqSSsLi6i49B5QGdzaMZK9+M7LXN2FKz4eGM= google.golang.org/grpc v1.62.1/go.mod h1:IWTG0VlJLCh1SkC58F7np9ka9mx/WNkjl4PGJaiq+QE= -google.golang.org/grpc v1.63.2 h1:MUeiw1B2maTVZthpU5xvASfTh3LDbxHd6IJ6QQVU+xM= -google.golang.org/grpc v1.63.2/go.mod h1:WAX/8DgncnokcFUldAxq7GeB5DXHDbMF+lLvDomNkRA= +google.golang.org/grpc v1.66.2 h1:3QdXkuq3Bkh7w+ywLdLvM56cmGvQHUMZpiCzt6Rqaoo= +google.golang.org/grpc v1.66.2/go.mod h1:s3/l6xSSCURdVfAnL+TqCNMyTDAGN6+lZeVxnZR128Y= google.golang.org/grpc/cmd/protoc-gen-go-grpc v1.1.0/go.mod h1:6Kw0yEErY5E/yWrBtf03jp27GLLJujG4z/JK95pnjjw= google.golang.org/protobuf v0.0.0-20200109180630-ec00e32a8dfd/go.mod h1:DFci5gLYBciE7Vtevhsrf46CRTquxDuWsQurQQe4oz8= google.golang.org/protobuf v0.0.0-20200221191635-4d8936d0db64/go.mod h1:kwYJMbMJ01Woi6D6+Kah6886xMZcty6N08ah7+eCXa0= @@ -2704,8 +2725,8 @@ google.golang.org/protobuf v1.30.0/go.mod h1:HV8QOd/L58Z+nl8r43ehVNZIU/HEI6OcFqw google.golang.org/protobuf v1.31.0/go.mod h1:HV8QOd/L58Z+nl8r43ehVNZIU/HEI6OcFqwMG9pJV4I= google.golang.org/protobuf v1.32.0/go.mod h1:c6P6GXX6sHbq/GpV6MGZEdwhWPcYBgnhAHhKbcUYpos= google.golang.org/protobuf v1.33.0/go.mod h1:c6P6GXX6sHbq/GpV6MGZEdwhWPcYBgnhAHhKbcUYpos= -google.golang.org/protobuf v1.34.1 h1:9ddQBjfCyZPOHPUiPxpYESBLc+T8P3E+Vo4IbKZgFWg= -google.golang.org/protobuf v1.34.1/go.mod h1:c6P6GXX6sHbq/GpV6MGZEdwhWPcYBgnhAHhKbcUYpos= +google.golang.org/protobuf v1.34.2 h1:6xV6lTsCfpGD21XK49h7MhtcApnLqkfYgPcdHftf6hg= +google.golang.org/protobuf v1.34.2/go.mod h1:qYOHts0dSfpeUzUFpOMr/WGzszTmLH+DiWniOlNbLDw= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v1.0.0-20190902080502-41f04d3bba15/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= diff --git a/internal/attrs/attrs.go b/internal/attrs/attrs.go index d8f42e2c644..d1444ebd7af 100644 --- a/internal/attrs/attrs.go +++ b/internal/attrs/attrs.go @@ -34,17 +34,18 @@ import ( // and for an ATETopology. All fields are optional; only those that are // non-empty will be set when configuring an interface. type Attributes struct { - IPv4 string - IPv4Sec string // Secondary IPv4 address - IPv6 string - MAC string - Name string // Interface name, only applied to ATE ports. - Desc string // Description, only applied to DUT interfaces. - IPv4Len uint8 // Prefix length for IPv4. - IPv4LenSec uint8 // Prefix length for Secondary IPv4 address. - IPv6Len uint8 // Prefix length for IPv6. - MTU uint16 - ID uint32 // /interfaces/interface/state/id p4rt interface id + IPv4 string + IPv4Sec string // Secondary IPv4 address + IPv6 string + MAC string + Name string // Interface name, only applied to ATE ports. + Desc string // Description, only applied to DUT interfaces. + Subinterface uint32 //Subinterface + IPv4Len uint8 // Prefix length for IPv4. + IPv4LenSec uint8 // Prefix length for Secondary IPv4 address. + IPv6Len uint8 // Prefix length for IPv6. + MTU uint16 + ID uint32 // /interfaces/interface/state/id p4rt interface id } // IPv4CIDR constructs the IPv4 CIDR notation with the given prefix @@ -76,7 +77,7 @@ func (a *Attributes) ConfigOCInterface(intf *oc.Interface, dut *ondatra.DUTDevic e.MacAddress = ygot.String(a.MAC) } - s := intf.GetOrCreateSubinterface(0) + s := intf.GetOrCreateSubinterface(a.Subinterface) if a.IPv4 != "" { s4 := s.GetOrCreateIpv4() if deviations.InterfaceEnabled(dut) && !deviations.IPv4MissingEnabled(dut) { diff --git a/internal/cfgplugins/interface.go b/internal/cfgplugins/interface.go index cee56b81fb3..fdef68680b5 100644 --- a/internal/cfgplugins/interface.go +++ b/internal/cfgplugins/interface.go @@ -15,10 +15,10 @@ package cfgplugins import ( - "fmt" "math" "testing" + "github.com/openconfig/featureprofiles/internal/components" "github.com/openconfig/featureprofiles/internal/deviations" "github.com/openconfig/ondatra" "github.com/openconfig/ondatra/gnmi" @@ -33,30 +33,6 @@ const ( targetFrequencyToleranceMHz = 100000 ) -// opticalChannelComponentFromPort returns the name of the optical channel component for the given -// port. -func opticalChannelComponentFromPort(t *testing.T, dut *ondatra.DUTDevice, p *ondatra.Port) string { - t.Helper() - if deviations.MissingPortToOpticalChannelMapping(dut) { - transceiverName := gnmi.Get(t, dut, gnmi.OC().Interface(p.Name()).Transceiver().State()) - return fmt.Sprintf("%s-Optical0", transceiverName) - } - compName := gnmi.Get(t, dut, gnmi.OC().Interface(p.Name()).HardwarePort().State()) - for { - comp, ok := gnmi.Lookup(t, dut, gnmi.OC().Component(compName).State()).Val() - if !ok { - t.Fatalf("Recursive optical channel lookup failed for port: %s, component %s not found.", p.Name(), compName) - } - if comp.GetType() == oc.PlatformTypes_OPENCONFIG_HARDWARE_COMPONENT_OPTICAL_CHANNEL { - return compName - } - if comp.GetParent() == "" { - t.Fatalf("Recursive optical channel lookup failed for port: %s, parent of component %s not found.", p.Name(), compName) - } - compName = comp.GetParent() - } -} - // InterfaceConfig configures the interface with the given port. func InterfaceConfig(t *testing.T, dut *ondatra.DUTDevice, dp *ondatra.Port) { t.Helper() @@ -65,8 +41,9 @@ func InterfaceConfig(t *testing.T, dut *ondatra.DUTDevice, dp *ondatra.Port) { i.Enabled = ygot.Bool(true) i.Type = oc.IETFInterfaces_InterfaceType_ethernetCsmacd gnmi.Replace(t, dut, gnmi.OC().Interface(dp.Name()).Config(), i) - ocComponent := opticalChannelComponentFromPort(t, dut, dp) + ocComponent := components.OpticalChannelComponentFromPort(t, dut, dp) t.Logf("Got opticalChannelComponent from port: %s", ocComponent) + gnmi.Update(t, dut, gnmi.OC().Component(ocComponent).Name().Config(), ocComponent) gnmi.Replace(t, dut, gnmi.OC().Component(ocComponent).OpticalChannel().Config(), &oc.Component_OpticalChannel{ TargetOutputPower: ygot.Float64(targetOutputPowerdBm), Frequency: ygot.Uint64(targetFrequencyMHz), @@ -76,7 +53,7 @@ func InterfaceConfig(t *testing.T, dut *ondatra.DUTDevice, dp *ondatra.Port) { // ValidateInterfaceConfig validates the output power and frequency for the given port. func ValidateInterfaceConfig(t *testing.T, dut *ondatra.DUTDevice, dp *ondatra.Port) { t.Helper() - ocComponent := opticalChannelComponentFromPort(t, dut, dp) + ocComponent := components.OpticalChannelComponentFromPort(t, dut, dp) t.Logf("Got opticalChannelComponent from port: %s", ocComponent) outputPower := gnmi.Get(t, dut, gnmi.OC().Component(ocComponent).OpticalChannel().TargetOutputPower().State()) @@ -101,6 +78,7 @@ func ToggleInterface(t *testing.T, dut *ondatra.DUTDevice, intf string, isEnable // ConfigOpticalChannel configures the optical channel. func ConfigOpticalChannel(t *testing.T, dut *ondatra.DUTDevice, och string, frequency uint64, targetOpticalPower float64, operationalMode uint16) { + gnmi.Update(t, dut, gnmi.OC().Component(och).Name().Config(), och) gnmi.Replace(t, dut, gnmi.OC().Component(och).OpticalChannel().Config(), &oc.Component_OpticalChannel{ OperationalMode: ygot.Uint16(operationalMode), Frequency: ygot.Uint64(frequency), @@ -111,43 +89,70 @@ func ConfigOpticalChannel(t *testing.T, dut *ondatra.DUTDevice, och string, freq // ConfigOTNChannel configures the OTN channel. func ConfigOTNChannel(t *testing.T, dut *ondatra.DUTDevice, och string, otnIndex, ethIndex uint32) { t.Helper() - gnmi.Replace(t, dut, gnmi.OC().TerminalDevice().Channel(otnIndex).Config(), &oc.TerminalDevice_Channel{ - Description: ygot.String("OTN Logical Channel"), - Index: ygot.Uint32(otnIndex), - LogicalChannelType: oc.TransportTypes_LOGICAL_ELEMENT_PROTOCOL_TYPE_PROT_OTN, - TribProtocol: oc.TransportTypes_TRIBUTARY_PROTOCOL_TYPE_PROT_400GE, - Assignment: map[uint32]*oc.TerminalDevice_Channel_Assignment{ - 0: { - Index: ygot.Uint32(0), - OpticalChannel: ygot.String(och), - Description: ygot.String("OTN to Optical Channel"), - Allocation: ygot.Float64(400), - AssignmentType: oc.Assignment_AssignmentType_OPTICAL_CHANNEL, + if deviations.OTNChannelTribUnsupported(dut) { + gnmi.Replace(t, dut, gnmi.OC().TerminalDevice().Channel(otnIndex).Config(), &oc.TerminalDevice_Channel{ + Description: ygot.String("OTN Logical Channel"), + Index: ygot.Uint32(otnIndex), + LogicalChannelType: oc.TransportTypes_LOGICAL_ELEMENT_PROTOCOL_TYPE_PROT_OTN, + Assignment: map[uint32]*oc.TerminalDevice_Channel_Assignment{ + 0: { + Index: ygot.Uint32(1), + OpticalChannel: ygot.String(och), + Description: ygot.String("OTN to Optical Channel"), + Allocation: ygot.Float64(400), + AssignmentType: oc.Assignment_AssignmentType_OPTICAL_CHANNEL, + }, }, - 1: { - Index: ygot.Uint32(1), - LogicalChannel: ygot.Uint32(ethIndex), - Description: ygot.String("OTN to ETH"), - Allocation: ygot.Float64(400), - AssignmentType: oc.Assignment_AssignmentType_LOGICAL_CHANNEL, + }) + } else { + gnmi.Replace(t, dut, gnmi.OC().TerminalDevice().Channel(otnIndex).Config(), &oc.TerminalDevice_Channel{ + Description: ygot.String("OTN Logical Channel"), + Index: ygot.Uint32(otnIndex), + LogicalChannelType: oc.TransportTypes_LOGICAL_ELEMENT_PROTOCOL_TYPE_PROT_OTN, + TribProtocol: oc.TransportTypes_TRIBUTARY_PROTOCOL_TYPE_PROT_400GE, + Assignment: map[uint32]*oc.TerminalDevice_Channel_Assignment{ + 0: { + Index: ygot.Uint32(0), + OpticalChannel: ygot.String(och), + Description: ygot.String("OTN to Optical Channel"), + Allocation: ygot.Float64(400), + AssignmentType: oc.Assignment_AssignmentType_OPTICAL_CHANNEL, + }, + 1: { + Index: ygot.Uint32(1), + LogicalChannel: ygot.Uint32(ethIndex), + Description: ygot.String("OTN to ETH"), + Allocation: ygot.Float64(400), + AssignmentType: oc.Assignment_AssignmentType_LOGICAL_CHANNEL, + }, }, - }, - }) + }) + } } // ConfigETHChannel configures the ETH channel. func ConfigETHChannel(t *testing.T, dut *ondatra.DUTDevice, interfaceName, transceiverName string, otnIndex, ethIndex uint32) { t.Helper() - gnmi.Replace(t, dut, gnmi.OC().TerminalDevice().Channel(ethIndex).Config(), &oc.TerminalDevice_Channel{ - Description: ygot.String("ETH Logical Channel"), - Index: ygot.Uint32(ethIndex), - LogicalChannelType: oc.TransportTypes_LOGICAL_ELEMENT_PROTOCOL_TYPE_PROT_ETHERNET, - TribProtocol: oc.TransportTypes_TRIBUTARY_PROTOCOL_TYPE_PROT_400GE, - Ingress: &oc.TerminalDevice_Channel_Ingress{ + var ingress = &oc.TerminalDevice_Channel_Ingress{} + if !deviations.EthChannelIngressParametersUnsupported(dut) { + ingress = &oc.TerminalDevice_Channel_Ingress{ Interface: ygot.String(interfaceName), Transceiver: ygot.String(transceiverName), - }, - Assignment: map[uint32]*oc.TerminalDevice_Channel_Assignment{ + } + } + var assignment = map[uint32]*oc.TerminalDevice_Channel_Assignment{} + if deviations.EthChannelAssignmentCiscoNumbering(dut) { + assignment = map[uint32]*oc.TerminalDevice_Channel_Assignment{ + 0: { + Index: ygot.Uint32(1), + LogicalChannel: ygot.Uint32(otnIndex), + Description: ygot.String("ETH to OTN"), + Allocation: ygot.Float64(400), + AssignmentType: oc.Assignment_AssignmentType_LOGICAL_CHANNEL, + }, + } + } else { + assignment = map[uint32]*oc.TerminalDevice_Channel_Assignment{ 0: { Index: ygot.Uint32(0), LogicalChannel: ygot.Uint32(otnIndex), @@ -155,6 +160,16 @@ func ConfigETHChannel(t *testing.T, dut *ondatra.DUTDevice, interfaceName, trans Allocation: ygot.Float64(400), AssignmentType: oc.Assignment_AssignmentType_LOGICAL_CHANNEL, }, - }, - }) + } + } + channel := &oc.TerminalDevice_Channel{ + Description: ygot.String("ETH Logical Channel"), + Index: ygot.Uint32(ethIndex), + LogicalChannelType: oc.TransportTypes_LOGICAL_ELEMENT_PROTOCOL_TYPE_PROT_ETHERNET, + TribProtocol: oc.TransportTypes_TRIBUTARY_PROTOCOL_TYPE_PROT_400GE, + RateClass: oc.TransportTypes_TRIBUTARY_RATE_CLASS_TYPE_TRIB_RATE_400G, + Ingress: ingress, + Assignment: assignment, + } + gnmi.Replace(t, dut, gnmi.OC().TerminalDevice().Channel(ethIndex).Config(), channel) } diff --git a/internal/cfgplugins/sflow.go b/internal/cfgplugins/sflow.go index 51b57546fa4..bf0086daba0 100644 --- a/internal/cfgplugins/sflow.go +++ b/internal/cfgplugins/sflow.go @@ -15,7 +15,11 @@ package cfgplugins import ( + "fmt" + "testing" + "github.com/openconfig/featureprofiles/internal/deviations" + "github.com/openconfig/featureprofiles/internal/helpers" "github.com/openconfig/ondatra" "github.com/openconfig/ondatra/gnmi" "github.com/openconfig/ondatra/gnmi/oc" @@ -26,7 +30,7 @@ import ( // configuration including any deviations for the device. // If sfglobal is nil, default values are provided. // The SFlow configuration is returned to give the caller an option to override default values. -func NewSFlowGlobalCfg(batch *gnmi.SetBatch, newcfg *oc.Sampling_Sflow, d *ondatra.DUTDevice) *oc.Sampling_Sflow { +func NewSFlowGlobalCfg(t *testing.T, batch *gnmi.SetBatch, newcfg *oc.Sampling_Sflow, d *ondatra.DUTDevice, ni, intfName string, srcAddrV4 string, srcAddrV6 string) *oc.Sampling_Sflow { c := new(oc.Sampling_Sflow) if newcfg == nil { @@ -35,12 +39,12 @@ func NewSFlowGlobalCfg(batch *gnmi.SetBatch, newcfg *oc.Sampling_Sflow, d *ondat c.IngressSamplingRate = ygot.Uint32(1000000) // c.EgressSamplingRate = ygot.Uint32(1000000), TODO: verify if EgressSamplingRate is a required DUT feature c.Dscp = ygot.Uint8(8) - coll := new(oc.Sampling_Sflow_Collector) - coll.SetAddress("192.0.2.129") - coll.SetPort(6343) - coll.SetSourceAddress("192.0.2.5") - coll.SetNetworkInstance(deviations.DefaultNetworkInstance(d)) - c.AppendCollector(coll) + c.GetOrCreateInterface(d.Port(t, "port1").Name()).Enabled = ygot.Bool(true) + c.GetOrCreateInterface(d.Port(t, "port2").Name()).Enabled = ygot.Bool(true) + coll := NewSFlowCollector(t, batch, nil, d, ni, intfName, srcAddrV4, srcAddrV6) + for _, col := range coll { + c.AppendCollector(col) + } } else { *c = *newcfg } @@ -52,19 +56,55 @@ func NewSFlowGlobalCfg(batch *gnmi.SetBatch, newcfg *oc.Sampling_Sflow, d *ondat // NewSFlowCollector creates a collector to be appended to SFlowConfig. // If sfc is nil, default values are provided. -func NewSFlowCollector(batch *gnmi.SetBatch, newcfg *oc.Sampling_Sflow_Collector, d *ondatra.DUTDevice) *oc.Sampling_Sflow_Collector { - c := new(oc.Sampling_Sflow_Collector) +func NewSFlowCollector(t *testing.T, batch *gnmi.SetBatch, newcfg *oc.Sampling_Sflow_Collector, d *ondatra.DUTDevice, ni, intfName string, srcAddrV4 string, srcAddrV6 string) []*oc.Sampling_Sflow_Collector { + coll := []*oc.Sampling_Sflow_Collector{} if newcfg == nil { - c.SetAddress("192.0.2.129") - c.SetPort(6343) - c.SetSourceAddress("192.0.2.5") + intf := gnmi.Get[*oc.Interface](t, d, gnmi.OC().Interface(intfName).State()) + + cV4 := new(oc.Sampling_Sflow_Collector) + cV4.SetAddress("192.0.2.129") + cV4.SetPort(6343) + + if deviations.SflowSourceAddressUpdateUnsupported(d) { + sFlowSourceAddressCli := "" + switch d.Vendor() { + case ondatra.ARISTA: + sFlowSourceAddressCli = fmt.Sprintf("sflow vrf %s source-interface %s", ni, intf.GetName()) + } + if sFlowSourceAddressCli != "" { + helpers.GnmiCLIConfig(t, d, sFlowSourceAddressCli) + } + } else { + cV4.SetSourceAddress(srcAddrV4) + } + cV4.SetNetworkInstance(ni) + coll = append(coll, cV4) + + cV6 := new(oc.Sampling_Sflow_Collector) + cV6.SetAddress("2001:db8::129") + cV6.SetPort(6343) + if deviations.SflowSourceAddressUpdateUnsupported(d) { + sFlowSourceAddressCli := "" + switch d.Vendor() { + case ondatra.ARISTA: + sFlowSourceAddressCli = fmt.Sprintf("sflow vrf %s source-interface %s", ni, intf.GetName()) + } + if sFlowSourceAddressCli != "" { + helpers.GnmiCLIConfig(t, d, sFlowSourceAddressCli) + } + } else { + cV6.SetSourceAddress(srcAddrV6) + } + cV6.SetNetworkInstance(ni) + coll = append(coll, cV6) } else { - *c = *newcfg + coll = append(coll, newcfg) } - c.SetNetworkInstance(normalizeNIName("DEFAULT", d)) - gnmi.BatchReplace(batch, gnmi.OC().Sampling().Sflow().Collector(c.GetAddress(), c.GetPort()).Config(), c) + for _, c := range coll { + gnmi.BatchReplace(batch, gnmi.OC().Sampling().Sflow().Collector(c.GetAddress(), c.GetPort()).Config(), c) + } - return c + return coll } diff --git a/internal/components/components.go b/internal/components/components.go index 6878df539d0..c2e6a8b2896 100644 --- a/internal/components/components.go +++ b/internal/components/components.go @@ -212,18 +212,13 @@ func OpticalChannelComponentFromPort(t *testing.T, dut *ondatra.DUTDevice, p *on t.Fatal("Manual Optical channel name required when deviation missing_port_to_optical_channel_component_mapping applied.") } } - compName := gnmi.Get(t, dut, gnmi.OC().Interface(p.Name()).HardwarePort().State()) - for { - comp, ok := gnmi.Lookup(t, dut, gnmi.OC().Component(compName).State()).Val() - if !ok { - t.Fatalf("Recursive optical channel lookup failed for port: %s, component %s not found.", p.Name(), compName) - } - if comp.GetType() == oc.PlatformTypes_OPENCONFIG_HARDWARE_COMPONENT_OPTICAL_CHANNEL { - return compName - } - if comp.GetParent() == "" { - t.Fatalf("Recursive optical channel lookup failed for port: %s, parent of component %s not found.", p.Name(), compName) - } - compName = comp.GetParent() + transceiverName := gnmi.Get(t, dut, gnmi.OC().Interface(p.Name()).Transceiver().State()) + if transceiverName == "" { + t.Fatalf("Associated Transceiver for Interface (%v) not found!", p.Name()) + } + opticalChannelName := gnmi.Get(t, dut, gnmi.OC().Component(transceiverName).Transceiver().Channel(0).AssociatedOpticalChannel().State()) + if opticalChannelName == "" { + t.Fatalf("Associated Optical Channel for Transceiver (%v) not found!", transceiverName) } + return opticalChannelName } diff --git a/internal/core/core.go b/internal/core/core.go index 20f0032fccf..2d3b7ac0210 100644 --- a/internal/core/core.go +++ b/internal/core/core.go @@ -31,7 +31,6 @@ import ( "github.com/openconfig/ondatra" "github.com/openconfig/ondatra/binding" "github.com/openconfig/ondatra/eventlis" - "google.golang.org/grpc" fpb "github.com/openconfig/gnoi/file" opb "github.com/openconfig/ondatra/proto" @@ -88,7 +87,7 @@ func newChecker(dut binding.DUT) (*checker, error) { if _, ok := vendorCoreFileNamePattern[dutVendor]; !ok { return nil, fmt.Errorf("add support for vendor %v in var vendorCoreFileNamePattern", dutVendor) } - gClients, err := dut.DialGNOI(context.Background(), grpc.WithBlock()) + gClients, err := dut.DialGNOI(context.Background()) if err != nil { return nil, err } diff --git a/internal/deviations/deviations.go b/internal/deviations/deviations.go index bc9f6e50ec6..16757a9ef72 100644 --- a/internal/deviations/deviations.go +++ b/internal/deviations/deviations.go @@ -720,11 +720,6 @@ func SkipStaticNexthopCheck(dut *ondatra.DUTDevice) bool { return lookupDUTDeviations(dut).GetSkipStaticNexthopCheck() } -// EnableFlowctrlFlag returns if device needs set leaf specific enable flag. -func EnableFlowctrlFlag(dut *ondatra.DUTDevice) bool { - return lookupDUTDeviations(dut).GetEnableFlowctrlFlag() -} - // Ipv6RouterAdvertisementConfigUnsupported returns true for devices which don't support Ipv6 RouterAdvertisement configuration func Ipv6RouterAdvertisementConfigUnsupported(dut *ondatra.DUTDevice) bool { return lookupDUTDeviations(dut).GetIpv6RouterAdvertisementConfigUnsupported() @@ -1120,6 +1115,12 @@ func DefaultImportExportPolicyUnsupported(dut *ondatra.DUTDevice) bool { return lookupDUTDeviations(dut).GetDefaultImportExportPolicyUnsupported() } +// CommunityInvertAnyUnsupported returns true when device +// does not support community invert any. +func CommunityInvertAnyUnsupported(dut *ondatra.DUTDevice) bool { + return lookupDUTDeviations(dut).GetCommunityInvertAnyUnsupported() +} + // Ipv6RouterAdvertisementIntervalUnsupported returns true for devices which don't support Ipv6 RouterAdvertisement interval configuration func Ipv6RouterAdvertisementIntervalUnsupported(dut *ondatra.DUTDevice) bool { return lookupDUTDeviations(dut).GetIpv6RouterAdvertisementIntervalUnsupported() @@ -1129,3 +1130,44 @@ func Ipv6RouterAdvertisementIntervalUnsupported(dut *ondatra.DUTDevice) bool { func DecapNHWithNextHopNIUnsupported(dut *ondatra.DUTDevice) bool { return lookupDUTDeviations(dut).GetDecapNhWithNexthopNiUnsupported() } + +// SflowSourceAddressUpdateUnsupported returns true if sflow source address update is unsupported +func SflowSourceAddressUpdateUnsupported(dut *ondatra.DUTDevice) bool { + return lookupDUTDeviations(dut).GetSflowSourceAddressUpdateUnsupported() +} + +// LinkLocalMaskLen returns true if linklocal mask length is not 64 +func LinkLocalMaskLen(dut *ondatra.DUTDevice) bool { + return lookupDUTDeviations(dut).GetLinkLocalMaskLen() +} + +// UseParentComponentForTemperatureTelemetry returns true if parent component supports temperature telemetry +func UseParentComponentForTemperatureTelemetry(dut *ondatra.DUTDevice) bool { + return lookupDUTDeviations(dut).GetUseParentComponentForTemperatureTelemetry() +} + +// ComponentMfgDateUnsupported returns true if component's mfg-date leaf is unsupported +func ComponentMfgDateUnsupported(dut *ondatra.DUTDevice) bool { + return lookupDUTDeviations(dut).GetComponentMfgDateUnsupported() +} + +// InterfaceCountersUpdateDelayed returns true if telemetry for interface counters +// does not return the latest counter values. +func InterfaceCountersUpdateDelayed(dut *ondatra.DUTDevice) bool { + return lookupDUTDeviations(dut).GetInterfaceCountersUpdateDelayed() +} + +// OTNChannelTribUnsupported returns true if TRIB parameter is unsupported under OTN channel configuration +func OTNChannelTribUnsupported(dut *ondatra.DUTDevice) bool { + return lookupDUTDeviations(dut).GetOtnChannelTribUnsupported() +} + +// EthChannelIngressParametersUnsupported returns true if ingress parameters are unsupported under ETH channel configuration +func EthChannelIngressParametersUnsupported(dut *ondatra.DUTDevice) bool { + return lookupDUTDeviations(dut).GetEthChannelIngressParametersUnsupported() +} + +// EthChannelAssignmentCiscoNumbering returns true if eth channel assignment index starts from 1 instead of 0 +func EthChannelAssignmentCiscoNumbering(dut *ondatra.DUTDevice) bool { + return lookupDUTDeviations(dut).GetEthChannelAssignmentCiscoNumbering() +} diff --git a/internal/fptest/runtests.go b/internal/fptest/runtests.go index 608a77465e0..14d819c91d0 100644 --- a/internal/fptest/runtests.go +++ b/internal/fptest/runtests.go @@ -75,6 +75,7 @@ func testbedPathFromMetadata() (string, error) { mpb.Metadata_TESTBED_DUT_ATE_9LINKS_LAG: "atedut_9_lag.testbed", mpb.Metadata_TESTBED_DUT_DUT_ATE_2LINKS: "dutdutate.testbed", mpb.Metadata_TESTBED_DUT_ATE_8LINKS: "atedut_8.testbed", + mpb.Metadata_TESTBED_DUT_400ZR: "dut_400zr.testbed", } testbedFile, ok := testbedToFile[testbed] if !ok { diff --git a/internal/gnoi/gnoi.go b/internal/gnoi/gnoi.go index 48eec464b83..cf7892ecea6 100644 --- a/internal/gnoi/gnoi.go +++ b/internal/gnoi/gnoi.go @@ -40,6 +40,7 @@ var ( }, ondatra.CISCO: { GRIBI: "emsd", + OCAGENT: "emsd", P4RT: "emsd", ROUTING: "emsd", }, diff --git a/proto/metadata.proto b/proto/metadata.proto index 79ea95524fc..bc6bd7fb913 100644 --- a/proto/metadata.proto +++ b/proto/metadata.proto @@ -393,9 +393,6 @@ message Metadata { // Devices which does not support nexthop index state // Juniper: b/304729237 bool skip_static_nexthop_check = 136; - // Devices which needs to enable leaf specific flag - // Juniper: b/319202763 - bool enable_flowctrl_flag = 137; // Device doesn't support router advertisement enable and mode config // Juniper: b/316173974 bool ipv6_router_advertisement_config_unsupported = 138; @@ -561,7 +558,7 @@ message Metadata { // equal to the canonical hardware model name of its device. bool model_name_unsupported = 194; // community_match_with_redistribution_unsupported is set to true for devices that do not support matching community at the redistribution attach point. - bool community_match_with_redistribution_unsupported = 195; + bool community_match_with_redistribution_unsupported = 195; // Devices that do not support components/component/state/install-component // and components/component/state/install-position. bool install_position_and_install_component_unsupported = 196; @@ -578,7 +575,7 @@ message Metadata { // weighted ecmp feature verification using fixed packet bool weighted_ecmp_fixed_packet_verification = 202; // Override default NextHop scale while enabling encap/decap scale - // CISCO: + // CISCO: bool override_default_nh_scale = 203; // Devices that donot support setting bgp extended community set bool bgp_extended_community_set_unsupported = 204; @@ -606,7 +603,26 @@ message Metadata { bool ipv6_router_advertisement_interval_unsupported = 214; // Decap NH with NextHopNetworkInstance is unsupported bool decap_nh_with_nexthop_ni_unsupported = 215; - + // Juniper: b/356898098 + bool community_invert_any_unsupported = 216; + // SFlow source address update is unsupported + // Arista: b/357914789 + bool sflow_source_address_update_unsupported = 217; + // Linklocal mask length is not 64 + // Cisco: b/368271859 + bool link_local_mask_len = 218; + // use parent component for temperature telemetry + bool use_parent_component_for_temperature_telemetry = 219; + // component manufactured date is unsupported + bool component_mfg_date_unsupported = 220; + // trib protocol field under otn channel config unsupported + bool otn_channel_trib_unsupported = 221; + // ingress parameters under eth channel config unsupported + bool eth_channel_ingress_parameters_unsupported = 222; + // Cisco numbering for eth channel assignment starts from 1 instead of 0 + bool eth_channel_assignment_cisco_numbering = 223; + // Devices needs time to update interface counters. + bool interface_counters_update_delayed = 224; // Reserved field numbers and identifiers. reserved 84, 9, 28, 20, 90, 97, 55, 89, 19, 36, 35, 40, 173; } diff --git a/proto/metadata_go_proto/metadata.pb.go b/proto/metadata_go_proto/metadata.pb.go index 5cd0ecc4a8a..139b2058c16 100644 --- a/proto/metadata_go_proto/metadata.pb.go +++ b/proto/metadata_go_proto/metadata.pb.go @@ -14,8 +14,8 @@ // Code generated by protoc-gen-go. DO NOT EDIT. // versions: -// protoc-gen-go v1.33.0 -// protoc v3.21.12 +// protoc-gen-go v1.34.2 +// protoc v5.27.1 // source: metadata.proto package metadata_go_proto @@ -674,9 +674,6 @@ type Metadata_Deviations struct { // Devices which does not support nexthop index state // Juniper: b/304729237 SkipStaticNexthopCheck bool `protobuf:"varint,136,opt,name=skip_static_nexthop_check,json=skipStaticNexthopCheck,proto3" json:"skip_static_nexthop_check,omitempty"` - // Devices which needs to enable leaf specific flag - // Juniper: b/319202763 - EnableFlowctrlFlag bool `protobuf:"varint,137,opt,name=enable_flowctrl_flag,json=enableFlowctrlFlag,proto3" json:"enable_flowctrl_flag,omitempty"` // Device doesn't support router advertisement enable and mode config // Juniper: b/316173974 Ipv6RouterAdvertisementConfigUnsupported bool `protobuf:"varint,138,opt,name=ipv6_router_advertisement_config_unsupported,json=ipv6RouterAdvertisementConfigUnsupported,proto3" json:"ipv6_router_advertisement_config_unsupported,omitempty"` @@ -888,6 +885,26 @@ type Metadata_Deviations struct { Ipv6RouterAdvertisementIntervalUnsupported bool `protobuf:"varint,214,opt,name=ipv6_router_advertisement_interval_unsupported,json=ipv6RouterAdvertisementIntervalUnsupported,proto3" json:"ipv6_router_advertisement_interval_unsupported,omitempty"` // Decap NH with NextHopNetworkInstance is unsupported DecapNhWithNexthopNiUnsupported bool `protobuf:"varint,215,opt,name=decap_nh_with_nexthop_ni_unsupported,json=decapNhWithNexthopNiUnsupported,proto3" json:"decap_nh_with_nexthop_ni_unsupported,omitempty"` + // Juniper: b/356898098 + CommunityInvertAnyUnsupported bool `protobuf:"varint,216,opt,name=community_invert_any_unsupported,json=communityInvertAnyUnsupported,proto3" json:"community_invert_any_unsupported,omitempty"` + // SFlow source address update is unsupported + // Arista: b/357914789 + SflowSourceAddressUpdateUnsupported bool `protobuf:"varint,217,opt,name=sflow_source_address_update_unsupported,json=sflowSourceAddressUpdateUnsupported,proto3" json:"sflow_source_address_update_unsupported,omitempty"` + // Linklocal mask length is not 64 + // Cisco: b/368271859 + LinkLocalMaskLen bool `protobuf:"varint,218,opt,name=link_local_mask_len,json=linkLocalMaskLen,proto3" json:"link_local_mask_len,omitempty"` + // use parent component for temperature telemetry + UseParentComponentForTemperatureTelemetry bool `protobuf:"varint,219,opt,name=use_parent_component_for_temperature_telemetry,json=useParentComponentForTemperatureTelemetry,proto3" json:"use_parent_component_for_temperature_telemetry,omitempty"` + // component manufactured date is unsupported + ComponentMfgDateUnsupported bool `protobuf:"varint,220,opt,name=component_mfg_date_unsupported,json=componentMfgDateUnsupported,proto3" json:"component_mfg_date_unsupported,omitempty"` + // trib protocol field under otn channel config unsupported + OtnChannelTribUnsupported bool `protobuf:"varint,221,opt,name=otn_channel_trib_unsupported,json=otnChannelTribUnsupported,proto3" json:"otn_channel_trib_unsupported,omitempty"` + // ingress parameters under eth channel config unsupported + EthChannelIngressParametersUnsupported bool `protobuf:"varint,222,opt,name=eth_channel_ingress_parameters_unsupported,json=ethChannelIngressParametersUnsupported,proto3" json:"eth_channel_ingress_parameters_unsupported,omitempty"` + // Cisco numbering for eth channel assignment starts from 1 instead of 0 + EthChannelAssignmentCiscoNumbering bool `protobuf:"varint,223,opt,name=eth_channel_assignment_cisco_numbering,json=ethChannelAssignmentCiscoNumbering,proto3" json:"eth_channel_assignment_cisco_numbering,omitempty"` + // Devices needs time to update interface counters. + InterfaceCountersUpdateDelayed bool `protobuf:"varint,224,opt,name=interface_counters_update_delayed,json=interfaceCountersUpdateDelayed,proto3" json:"interface_counters_update_delayed,omitempty"` } func (x *Metadata_Deviations) Reset() { @@ -1741,13 +1758,6 @@ func (x *Metadata_Deviations) GetSkipStaticNexthopCheck() bool { return false } -func (x *Metadata_Deviations) GetEnableFlowctrlFlag() bool { - if x != nil { - return x.EnableFlowctrlFlag - } - return false -} - func (x *Metadata_Deviations) GetIpv6RouterAdvertisementConfigUnsupported() bool { if x != nil { return x.Ipv6RouterAdvertisementConfigUnsupported @@ -2287,6 +2297,69 @@ func (x *Metadata_Deviations) GetDecapNhWithNexthopNiUnsupported() bool { return false } +func (x *Metadata_Deviations) GetCommunityInvertAnyUnsupported() bool { + if x != nil { + return x.CommunityInvertAnyUnsupported + } + return false +} + +func (x *Metadata_Deviations) GetSflowSourceAddressUpdateUnsupported() bool { + if x != nil { + return x.SflowSourceAddressUpdateUnsupported + } + return false +} + +func (x *Metadata_Deviations) GetLinkLocalMaskLen() bool { + if x != nil { + return x.LinkLocalMaskLen + } + return false +} + +func (x *Metadata_Deviations) GetUseParentComponentForTemperatureTelemetry() bool { + if x != nil { + return x.UseParentComponentForTemperatureTelemetry + } + return false +} + +func (x *Metadata_Deviations) GetComponentMfgDateUnsupported() bool { + if x != nil { + return x.ComponentMfgDateUnsupported + } + return false +} + +func (x *Metadata_Deviations) GetOtnChannelTribUnsupported() bool { + if x != nil { + return x.OtnChannelTribUnsupported + } + return false +} + +func (x *Metadata_Deviations) GetEthChannelIngressParametersUnsupported() bool { + if x != nil { + return x.EthChannelIngressParametersUnsupported + } + return false +} + +func (x *Metadata_Deviations) GetEthChannelAssignmentCiscoNumbering() bool { + if x != nil { + return x.EthChannelAssignmentCiscoNumbering + } + return false +} + +func (x *Metadata_Deviations) GetInterfaceCountersUpdateDelayed() bool { + if x != nil { + return x.InterfaceCountersUpdateDelayed + } + return false +} + type Metadata_PlatformExceptions struct { state protoimpl.MessageState sizeCache protoimpl.SizeCache @@ -2350,7 +2423,7 @@ var file_metadata_proto_rawDesc = []byte{ 0x74, 0x69, 0x6e, 0x67, 0x1a, 0x31, 0x67, 0x69, 0x74, 0x68, 0x75, 0x62, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x6f, 0x70, 0x65, 0x6e, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x2f, 0x6f, 0x6e, 0x64, 0x61, 0x74, 0x72, 0x61, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x2f, 0x74, 0x65, 0x73, 0x74, 0x62, 0x65, - 0x64, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x22, 0xaa, 0x79, 0x0a, 0x08, 0x4d, 0x65, 0x74, 0x61, + 0x64, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x22, 0xb2, 0x7e, 0x0a, 0x08, 0x4d, 0x65, 0x74, 0x61, 0x64, 0x61, 0x74, 0x61, 0x12, 0x12, 0x0a, 0x04, 0x75, 0x75, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x75, 0x75, 0x69, 0x64, 0x12, 0x17, 0x0a, 0x07, 0x70, 0x6c, 0x61, 0x6e, 0x5f, 0x69, 0x64, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x06, 0x70, 0x6c, 0x61, 0x6e, 0x49, @@ -2384,7 +2457,7 @@ var file_metadata_proto_rawDesc = []byte{ 0x67, 0x65, 0x78, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x52, 0x14, 0x73, 0x6f, 0x66, 0x74, 0x77, 0x61, 0x72, 0x65, 0x56, 0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x52, 0x65, 0x67, 0x65, 0x78, 0x4a, 0x04, 0x08, 0x02, 0x10, 0x03, 0x52, 0x0e, 0x68, 0x61, 0x72, 0x64, 0x77, 0x61, 0x72, 0x65, 0x5f, - 0x6d, 0x6f, 0x64, 0x65, 0x6c, 0x1a, 0xfd, 0x70, 0x0a, 0x0a, 0x44, 0x65, 0x76, 0x69, 0x61, 0x74, + 0x6d, 0x6f, 0x64, 0x65, 0x6c, 0x1a, 0x85, 0x76, 0x0a, 0x0a, 0x44, 0x65, 0x76, 0x69, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x12, 0x30, 0x0a, 0x14, 0x69, 0x70, 0x76, 0x34, 0x5f, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6e, 0x67, 0x5f, 0x65, 0x6e, 0x61, 0x62, 0x6c, 0x65, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x12, 0x69, 0x70, 0x76, 0x34, 0x4d, 0x69, 0x73, 0x73, 0x69, 0x6e, 0x67, 0x45, @@ -2910,418 +2983,459 @@ var file_metadata_proto_rawDesc = []byte{ 0x70, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x69, 0x63, 0x5f, 0x6e, 0x65, 0x78, 0x74, 0x68, 0x6f, 0x70, 0x5f, 0x63, 0x68, 0x65, 0x63, 0x6b, 0x18, 0x88, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x16, 0x73, 0x6b, 0x69, 0x70, 0x53, 0x74, 0x61, 0x74, 0x69, 0x63, 0x4e, 0x65, 0x78, 0x74, 0x68, 0x6f, 0x70, - 0x43, 0x68, 0x65, 0x63, 0x6b, 0x12, 0x31, 0x0a, 0x14, 0x65, 0x6e, 0x61, 0x62, 0x6c, 0x65, 0x5f, - 0x66, 0x6c, 0x6f, 0x77, 0x63, 0x74, 0x72, 0x6c, 0x5f, 0x66, 0x6c, 0x61, 0x67, 0x18, 0x89, 0x01, - 0x20, 0x01, 0x28, 0x08, 0x52, 0x12, 0x65, 0x6e, 0x61, 0x62, 0x6c, 0x65, 0x46, 0x6c, 0x6f, 0x77, - 0x63, 0x74, 0x72, 0x6c, 0x46, 0x6c, 0x61, 0x67, 0x12, 0x5f, 0x0a, 0x2c, 0x69, 0x70, 0x76, 0x36, - 0x5f, 0x72, 0x6f, 0x75, 0x74, 0x65, 0x72, 0x5f, 0x61, 0x64, 0x76, 0x65, 0x72, 0x74, 0x69, 0x73, - 0x65, 0x6d, 0x65, 0x6e, 0x74, 0x5f, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x5f, 0x75, 0x6e, 0x73, - 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0x8a, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, - 0x28, 0x69, 0x70, 0x76, 0x36, 0x52, 0x6f, 0x75, 0x74, 0x65, 0x72, 0x41, 0x64, 0x76, 0x65, 0x72, - 0x74, 0x69, 0x73, 0x65, 0x6d, 0x65, 0x6e, 0x74, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x55, 0x6e, - 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x5d, 0x0a, 0x2b, 0x70, 0x72, 0x65, - 0x66, 0x69, 0x78, 0x5f, 0x6c, 0x69, 0x6d, 0x69, 0x74, 0x5f, 0x65, 0x78, 0x63, 0x65, 0x65, 0x64, - 0x65, 0x64, 0x5f, 0x74, 0x65, 0x6c, 0x65, 0x6d, 0x65, 0x74, 0x72, 0x79, 0x5f, 0x75, 0x6e, 0x73, - 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0x8b, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, - 0x27, 0x70, 0x72, 0x65, 0x66, 0x69, 0x78, 0x4c, 0x69, 0x6d, 0x69, 0x74, 0x45, 0x78, 0x63, 0x65, - 0x65, 0x64, 0x65, 0x64, 0x54, 0x65, 0x6c, 0x65, 0x6d, 0x65, 0x74, 0x72, 0x79, 0x55, 0x6e, 0x73, - 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x43, 0x0a, 0x1e, 0x73, 0x6b, 0x69, 0x70, - 0x5f, 0x73, 0x65, 0x74, 0x74, 0x69, 0x6e, 0x67, 0x5f, 0x61, 0x6c, 0x6c, 0x6f, 0x77, 0x5f, 0x6d, - 0x75, 0x6c, 0x74, 0x69, 0x70, 0x6c, 0x65, 0x5f, 0x61, 0x73, 0x18, 0x8c, 0x01, 0x20, 0x01, 0x28, - 0x08, 0x52, 0x1a, 0x73, 0x6b, 0x69, 0x70, 0x53, 0x65, 0x74, 0x74, 0x69, 0x6e, 0x67, 0x41, 0x6c, - 0x6c, 0x6f, 0x77, 0x4d, 0x75, 0x6c, 0x74, 0x69, 0x70, 0x6c, 0x65, 0x41, 0x73, 0x12, 0x40, 0x0a, - 0x1d, 0x73, 0x6b, 0x69, 0x70, 0x5f, 0x70, 0x62, 0x66, 0x5f, 0x77, 0x69, 0x74, 0x68, 0x5f, 0x64, - 0x65, 0x63, 0x61, 0x70, 0x5f, 0x65, 0x6e, 0x63, 0x61, 0x70, 0x5f, 0x76, 0x72, 0x66, 0x18, 0x8d, - 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x18, 0x73, 0x6b, 0x69, 0x70, 0x50, 0x62, 0x66, 0x57, 0x69, - 0x74, 0x68, 0x44, 0x65, 0x63, 0x61, 0x70, 0x45, 0x6e, 0x63, 0x61, 0x70, 0x56, 0x72, 0x66, 0x12, - 0x31, 0x0a, 0x14, 0x74, 0x74, 0x6c, 0x5f, 0x63, 0x6f, 0x70, 0x79, 0x5f, 0x75, 0x6e, 0x73, 0x75, - 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0x8e, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x12, - 0x74, 0x74, 0x6c, 0x43, 0x6f, 0x70, 0x79, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, - 0x65, 0x64, 0x12, 0x4b, 0x0a, 0x22, 0x67, 0x72, 0x69, 0x62, 0x69, 0x5f, 0x64, 0x65, 0x63, 0x61, - 0x70, 0x5f, 0x6d, 0x69, 0x78, 0x65, 0x64, 0x5f, 0x70, 0x6c, 0x65, 0x6e, 0x5f, 0x75, 0x6e, 0x73, - 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0x8f, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, - 0x1e, 0x67, 0x72, 0x69, 0x62, 0x69, 0x44, 0x65, 0x63, 0x61, 0x70, 0x4d, 0x69, 0x78, 0x65, 0x64, - 0x50, 0x6c, 0x65, 0x6e, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, - 0x2e, 0x0a, 0x13, 0x73, 0x6b, 0x69, 0x70, 0x5f, 0x69, 0x73, 0x69, 0x73, 0x5f, 0x73, 0x65, 0x74, - 0x5f, 0x6c, 0x65, 0x76, 0x65, 0x6c, 0x18, 0x90, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x10, 0x73, - 0x6b, 0x69, 0x70, 0x49, 0x73, 0x69, 0x73, 0x53, 0x65, 0x74, 0x4c, 0x65, 0x76, 0x65, 0x6c, 0x12, - 0x44, 0x0a, 0x1f, 0x73, 0x6b, 0x69, 0x70, 0x5f, 0x69, 0x73, 0x69, 0x73, 0x5f, 0x73, 0x65, 0x74, - 0x5f, 0x6d, 0x65, 0x74, 0x72, 0x69, 0x63, 0x5f, 0x73, 0x74, 0x79, 0x6c, 0x65, 0x5f, 0x74, 0x79, - 0x70, 0x65, 0x18, 0x91, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1a, 0x73, 0x6b, 0x69, 0x70, 0x49, - 0x73, 0x69, 0x73, 0x53, 0x65, 0x74, 0x4d, 0x65, 0x74, 0x72, 0x69, 0x63, 0x53, 0x74, 0x79, 0x6c, - 0x65, 0x54, 0x79, 0x70, 0x65, 0x12, 0x40, 0x0a, 0x1d, 0x73, 0x6b, 0x69, 0x70, 0x5f, 0x73, 0x65, - 0x74, 0x5f, 0x72, 0x70, 0x5f, 0x6d, 0x61, 0x74, 0x63, 0x68, 0x5f, 0x73, 0x65, 0x74, 0x5f, 0x6f, - 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x18, 0x92, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x18, 0x73, - 0x6b, 0x69, 0x70, 0x53, 0x65, 0x74, 0x52, 0x70, 0x4d, 0x61, 0x74, 0x63, 0x68, 0x53, 0x65, 0x74, - 0x4f, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x12, 0x55, 0x0a, 0x27, 0x73, 0x6b, 0x69, 0x70, 0x5f, - 0x73, 0x65, 0x74, 0x74, 0x69, 0x6e, 0x67, 0x5f, 0x64, 0x69, 0x73, 0x61, 0x62, 0x6c, 0x65, 0x5f, - 0x6d, 0x65, 0x74, 0x72, 0x69, 0x63, 0x5f, 0x70, 0x72, 0x6f, 0x70, 0x61, 0x67, 0x61, 0x74, 0x69, - 0x6f, 0x6e, 0x18, 0x93, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x23, 0x73, 0x6b, 0x69, 0x70, 0x53, - 0x65, 0x74, 0x74, 0x69, 0x6e, 0x67, 0x44, 0x69, 0x73, 0x61, 0x62, 0x6c, 0x65, 0x4d, 0x65, 0x74, - 0x72, 0x69, 0x63, 0x50, 0x72, 0x6f, 0x70, 0x61, 0x67, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x62, - 0x0a, 0x2e, 0x62, 0x67, 0x70, 0x5f, 0x63, 0x6f, 0x6e, 0x64, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x73, - 0x5f, 0x6d, 0x61, 0x74, 0x63, 0x68, 0x5f, 0x63, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, - 0x5f, 0x73, 0x65, 0x74, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, - 0x18, 0x94, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x29, 0x62, 0x67, 0x70, 0x43, 0x6f, 0x6e, 0x64, - 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x4d, 0x61, 0x74, 0x63, 0x68, 0x43, 0x6f, 0x6d, 0x6d, 0x75, - 0x6e, 0x69, 0x74, 0x79, 0x53, 0x65, 0x74, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, - 0x65, 0x64, 0x12, 0x41, 0x0a, 0x1d, 0x70, 0x66, 0x5f, 0x72, 0x65, 0x71, 0x75, 0x69, 0x72, 0x65, - 0x5f, 0x6d, 0x61, 0x74, 0x63, 0x68, 0x5f, 0x64, 0x65, 0x66, 0x61, 0x75, 0x6c, 0x74, 0x5f, 0x72, - 0x75, 0x6c, 0x65, 0x18, 0x95, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x19, 0x70, 0x66, 0x52, 0x65, - 0x71, 0x75, 0x69, 0x72, 0x65, 0x4d, 0x61, 0x74, 0x63, 0x68, 0x44, 0x65, 0x66, 0x61, 0x75, 0x6c, - 0x74, 0x52, 0x75, 0x6c, 0x65, 0x12, 0x67, 0x0a, 0x31, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6e, 0x67, - 0x5f, 0x70, 0x6f, 0x72, 0x74, 0x5f, 0x74, 0x6f, 0x5f, 0x6f, 0x70, 0x74, 0x69, 0x63, 0x61, 0x6c, - 0x5f, 0x63, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x5f, 0x63, 0x6f, 0x6d, 0x70, 0x6f, 0x6e, 0x65, - 0x6e, 0x74, 0x5f, 0x6d, 0x61, 0x70, 0x70, 0x69, 0x6e, 0x67, 0x18, 0x96, 0x01, 0x20, 0x01, 0x28, - 0x08, 0x52, 0x2b, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6e, 0x67, 0x50, 0x6f, 0x72, 0x74, 0x54, 0x6f, - 0x4f, 0x70, 0x74, 0x69, 0x63, 0x61, 0x6c, 0x43, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x43, 0x6f, - 0x6d, 0x70, 0x6f, 0x6e, 0x65, 0x6e, 0x74, 0x4d, 0x61, 0x70, 0x70, 0x69, 0x6e, 0x67, 0x12, 0x2b, - 0x0a, 0x11, 0x73, 0x6b, 0x69, 0x70, 0x5f, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, - 0x5f, 0x6f, 0x70, 0x18, 0x97, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x0f, 0x73, 0x6b, 0x69, 0x70, - 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x4f, 0x70, 0x12, 0x51, 0x0a, 0x25, 0x72, - 0x65, 0x6f, 0x72, 0x64, 0x65, 0x72, 0x5f, 0x63, 0x61, 0x6c, 0x6c, 0x73, 0x5f, 0x66, 0x6f, 0x72, - 0x5f, 0x76, 0x65, 0x6e, 0x64, 0x6f, 0x72, 0x5f, 0x63, 0x6f, 0x6d, 0x70, 0x61, 0x74, 0x69, 0x62, - 0x69, 0x6c, 0x74, 0x79, 0x18, 0x98, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x21, 0x72, 0x65, 0x6f, - 0x72, 0x64, 0x65, 0x72, 0x43, 0x61, 0x6c, 0x6c, 0x73, 0x46, 0x6f, 0x72, 0x56, 0x65, 0x6e, 0x64, - 0x6f, 0x72, 0x43, 0x6f, 0x6d, 0x70, 0x61, 0x74, 0x69, 0x62, 0x69, 0x6c, 0x74, 0x79, 0x12, 0x44, - 0x0a, 0x1f, 0x61, 0x64, 0x64, 0x5f, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6e, 0x67, 0x5f, 0x62, 0x61, - 0x73, 0x65, 0x5f, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x5f, 0x76, 0x69, 0x61, 0x5f, 0x63, 0x6c, - 0x69, 0x18, 0x99, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1a, 0x61, 0x64, 0x64, 0x4d, 0x69, 0x73, - 0x73, 0x69, 0x6e, 0x67, 0x42, 0x61, 0x73, 0x65, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x56, 0x69, - 0x61, 0x43, 0x6c, 0x69, 0x12, 0x33, 0x0a, 0x15, 0x73, 0x6b, 0x69, 0x70, 0x5f, 0x6d, 0x61, 0x63, - 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x5f, 0x63, 0x68, 0x65, 0x63, 0x6b, 0x18, 0x9a, 0x01, - 0x20, 0x01, 0x28, 0x08, 0x52, 0x13, 0x73, 0x6b, 0x69, 0x70, 0x4d, 0x61, 0x63, 0x61, 0x64, 0x64, - 0x72, 0x65, 0x73, 0x73, 0x43, 0x68, 0x65, 0x63, 0x6b, 0x12, 0x3d, 0x0a, 0x1b, 0x62, 0x67, 0x70, - 0x5f, 0x72, 0x69, 0x62, 0x5f, 0x6f, 0x63, 0x5f, 0x70, 0x61, 0x74, 0x68, 0x5f, 0x75, 0x6e, 0x73, - 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0x9b, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, - 0x17, 0x62, 0x67, 0x70, 0x52, 0x69, 0x62, 0x4f, 0x63, 0x50, 0x61, 0x74, 0x68, 0x55, 0x6e, 0x73, - 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x30, 0x0a, 0x14, 0x73, 0x6b, 0x69, 0x70, - 0x5f, 0x70, 0x72, 0x65, 0x66, 0x69, 0x78, 0x5f, 0x73, 0x65, 0x74, 0x5f, 0x6d, 0x6f, 0x64, 0x65, - 0x18, 0x9c, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x11, 0x73, 0x6b, 0x69, 0x70, 0x50, 0x72, 0x65, - 0x66, 0x69, 0x78, 0x53, 0x65, 0x74, 0x4d, 0x6f, 0x64, 0x65, 0x12, 0x38, 0x0a, 0x18, 0x73, 0x65, - 0x74, 0x5f, 0x6d, 0x65, 0x74, 0x72, 0x69, 0x63, 0x5f, 0x61, 0x73, 0x5f, 0x70, 0x72, 0x65, 0x66, - 0x65, 0x72, 0x65, 0x6e, 0x63, 0x65, 0x18, 0x9d, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x15, 0x73, - 0x65, 0x74, 0x4d, 0x65, 0x74, 0x72, 0x69, 0x63, 0x41, 0x73, 0x50, 0x72, 0x65, 0x66, 0x65, 0x72, - 0x65, 0x6e, 0x63, 0x65, 0x12, 0x72, 0x0a, 0x38, 0x69, 0x70, 0x76, 0x36, 0x5f, 0x73, 0x74, 0x61, - 0x74, 0x69, 0x63, 0x5f, 0x72, 0x6f, 0x75, 0x74, 0x65, 0x5f, 0x77, 0x69, 0x74, 0x68, 0x5f, 0x69, - 0x70, 0x76, 0x34, 0x5f, 0x6e, 0x65, 0x78, 0x74, 0x5f, 0x68, 0x6f, 0x70, 0x5f, 0x72, 0x65, 0x71, - 0x75, 0x69, 0x72, 0x65, 0x73, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x69, 0x63, 0x5f, 0x61, 0x72, 0x70, - 0x18, 0x9e, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x2f, 0x69, 0x70, 0x76, 0x36, 0x53, 0x74, 0x61, - 0x74, 0x69, 0x63, 0x52, 0x6f, 0x75, 0x74, 0x65, 0x57, 0x69, 0x74, 0x68, 0x49, 0x70, 0x76, 0x34, - 0x4e, 0x65, 0x78, 0x74, 0x48, 0x6f, 0x70, 0x52, 0x65, 0x71, 0x75, 0x69, 0x72, 0x65, 0x73, 0x53, - 0x74, 0x61, 0x74, 0x69, 0x63, 0x41, 0x72, 0x70, 0x12, 0x50, 0x0a, 0x25, 0x70, 0x66, 0x5f, 0x72, - 0x65, 0x71, 0x75, 0x69, 0x72, 0x65, 0x5f, 0x73, 0x65, 0x71, 0x75, 0x65, 0x6e, 0x74, 0x69, 0x61, - 0x6c, 0x5f, 0x6f, 0x72, 0x64, 0x65, 0x72, 0x5f, 0x70, 0x62, 0x72, 0x5f, 0x72, 0x75, 0x6c, 0x65, - 0x73, 0x18, 0x9f, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x20, 0x70, 0x66, 0x52, 0x65, 0x71, 0x75, - 0x69, 0x72, 0x65, 0x53, 0x65, 0x71, 0x75, 0x65, 0x6e, 0x74, 0x69, 0x61, 0x6c, 0x4f, 0x72, 0x64, - 0x65, 0x72, 0x50, 0x62, 0x72, 0x52, 0x75, 0x6c, 0x65, 0x73, 0x12, 0x61, 0x0a, 0x2e, 0x6d, 0x69, - 0x73, 0x73, 0x69, 0x6e, 0x67, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x69, 0x63, 0x5f, 0x72, 0x6f, 0x75, - 0x74, 0x65, 0x5f, 0x6e, 0x65, 0x78, 0x74, 0x5f, 0x68, 0x6f, 0x70, 0x5f, 0x6d, 0x65, 0x74, 0x72, - 0x69, 0x63, 0x5f, 0x74, 0x65, 0x6c, 0x65, 0x6d, 0x65, 0x74, 0x72, 0x79, 0x18, 0xa0, 0x01, 0x20, - 0x01, 0x28, 0x08, 0x52, 0x28, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6e, 0x67, 0x53, 0x74, 0x61, 0x74, - 0x69, 0x63, 0x52, 0x6f, 0x75, 0x74, 0x65, 0x4e, 0x65, 0x78, 0x74, 0x48, 0x6f, 0x70, 0x4d, 0x65, - 0x74, 0x72, 0x69, 0x63, 0x54, 0x65, 0x6c, 0x65, 0x6d, 0x65, 0x74, 0x72, 0x79, 0x12, 0x58, 0x0a, - 0x29, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x5f, 0x73, 0x74, 0x61, - 0x74, 0x69, 0x63, 0x5f, 0x72, 0x6f, 0x75, 0x74, 0x65, 0x5f, 0x6e, 0x65, 0x78, 0x74, 0x5f, 0x68, - 0x6f, 0x70, 0x5f, 0x72, 0x65, 0x63, 0x75, 0x72, 0x73, 0x65, 0x18, 0xa1, 0x01, 0x20, 0x01, 0x28, - 0x08, 0x52, 0x24, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x53, 0x74, - 0x61, 0x74, 0x69, 0x63, 0x52, 0x6f, 0x75, 0x74, 0x65, 0x4e, 0x65, 0x78, 0x74, 0x48, 0x6f, 0x70, - 0x52, 0x65, 0x63, 0x75, 0x72, 0x73, 0x65, 0x12, 0x5d, 0x0a, 0x2c, 0x6d, 0x69, 0x73, 0x73, 0x69, + 0x43, 0x68, 0x65, 0x63, 0x6b, 0x12, 0x5f, 0x0a, 0x2c, 0x69, 0x70, 0x76, 0x36, 0x5f, 0x72, 0x6f, + 0x75, 0x74, 0x65, 0x72, 0x5f, 0x61, 0x64, 0x76, 0x65, 0x72, 0x74, 0x69, 0x73, 0x65, 0x6d, 0x65, + 0x6e, 0x74, 0x5f, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, + 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0x8a, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x28, 0x69, 0x70, + 0x76, 0x36, 0x52, 0x6f, 0x75, 0x74, 0x65, 0x72, 0x41, 0x64, 0x76, 0x65, 0x72, 0x74, 0x69, 0x73, + 0x65, 0x6d, 0x65, 0x6e, 0x74, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x55, 0x6e, 0x73, 0x75, 0x70, + 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x5d, 0x0a, 0x2b, 0x70, 0x72, 0x65, 0x66, 0x69, 0x78, + 0x5f, 0x6c, 0x69, 0x6d, 0x69, 0x74, 0x5f, 0x65, 0x78, 0x63, 0x65, 0x65, 0x64, 0x65, 0x64, 0x5f, + 0x74, 0x65, 0x6c, 0x65, 0x6d, 0x65, 0x74, 0x72, 0x79, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, + 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0x8b, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x27, 0x70, 0x72, + 0x65, 0x66, 0x69, 0x78, 0x4c, 0x69, 0x6d, 0x69, 0x74, 0x45, 0x78, 0x63, 0x65, 0x65, 0x64, 0x65, + 0x64, 0x54, 0x65, 0x6c, 0x65, 0x6d, 0x65, 0x74, 0x72, 0x79, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, + 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x43, 0x0a, 0x1e, 0x73, 0x6b, 0x69, 0x70, 0x5f, 0x73, 0x65, + 0x74, 0x74, 0x69, 0x6e, 0x67, 0x5f, 0x61, 0x6c, 0x6c, 0x6f, 0x77, 0x5f, 0x6d, 0x75, 0x6c, 0x74, + 0x69, 0x70, 0x6c, 0x65, 0x5f, 0x61, 0x73, 0x18, 0x8c, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1a, + 0x73, 0x6b, 0x69, 0x70, 0x53, 0x65, 0x74, 0x74, 0x69, 0x6e, 0x67, 0x41, 0x6c, 0x6c, 0x6f, 0x77, + 0x4d, 0x75, 0x6c, 0x74, 0x69, 0x70, 0x6c, 0x65, 0x41, 0x73, 0x12, 0x40, 0x0a, 0x1d, 0x73, 0x6b, + 0x69, 0x70, 0x5f, 0x70, 0x62, 0x66, 0x5f, 0x77, 0x69, 0x74, 0x68, 0x5f, 0x64, 0x65, 0x63, 0x61, + 0x70, 0x5f, 0x65, 0x6e, 0x63, 0x61, 0x70, 0x5f, 0x76, 0x72, 0x66, 0x18, 0x8d, 0x01, 0x20, 0x01, + 0x28, 0x08, 0x52, 0x18, 0x73, 0x6b, 0x69, 0x70, 0x50, 0x62, 0x66, 0x57, 0x69, 0x74, 0x68, 0x44, + 0x65, 0x63, 0x61, 0x70, 0x45, 0x6e, 0x63, 0x61, 0x70, 0x56, 0x72, 0x66, 0x12, 0x31, 0x0a, 0x14, + 0x74, 0x74, 0x6c, 0x5f, 0x63, 0x6f, 0x70, 0x79, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, + 0x72, 0x74, 0x65, 0x64, 0x18, 0x8e, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x12, 0x74, 0x74, 0x6c, + 0x43, 0x6f, 0x70, 0x79, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, + 0x4b, 0x0a, 0x22, 0x67, 0x72, 0x69, 0x62, 0x69, 0x5f, 0x64, 0x65, 0x63, 0x61, 0x70, 0x5f, 0x6d, + 0x69, 0x78, 0x65, 0x64, 0x5f, 0x70, 0x6c, 0x65, 0x6e, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, + 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0x8f, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1e, 0x67, 0x72, + 0x69, 0x62, 0x69, 0x44, 0x65, 0x63, 0x61, 0x70, 0x4d, 0x69, 0x78, 0x65, 0x64, 0x50, 0x6c, 0x65, + 0x6e, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x2e, 0x0a, 0x13, + 0x73, 0x6b, 0x69, 0x70, 0x5f, 0x69, 0x73, 0x69, 0x73, 0x5f, 0x73, 0x65, 0x74, 0x5f, 0x6c, 0x65, + 0x76, 0x65, 0x6c, 0x18, 0x90, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x10, 0x73, 0x6b, 0x69, 0x70, + 0x49, 0x73, 0x69, 0x73, 0x53, 0x65, 0x74, 0x4c, 0x65, 0x76, 0x65, 0x6c, 0x12, 0x44, 0x0a, 0x1f, + 0x73, 0x6b, 0x69, 0x70, 0x5f, 0x69, 0x73, 0x69, 0x73, 0x5f, 0x73, 0x65, 0x74, 0x5f, 0x6d, 0x65, + 0x74, 0x72, 0x69, 0x63, 0x5f, 0x73, 0x74, 0x79, 0x6c, 0x65, 0x5f, 0x74, 0x79, 0x70, 0x65, 0x18, + 0x91, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1a, 0x73, 0x6b, 0x69, 0x70, 0x49, 0x73, 0x69, 0x73, + 0x53, 0x65, 0x74, 0x4d, 0x65, 0x74, 0x72, 0x69, 0x63, 0x53, 0x74, 0x79, 0x6c, 0x65, 0x54, 0x79, + 0x70, 0x65, 0x12, 0x40, 0x0a, 0x1d, 0x73, 0x6b, 0x69, 0x70, 0x5f, 0x73, 0x65, 0x74, 0x5f, 0x72, + 0x70, 0x5f, 0x6d, 0x61, 0x74, 0x63, 0x68, 0x5f, 0x73, 0x65, 0x74, 0x5f, 0x6f, 0x70, 0x74, 0x69, + 0x6f, 0x6e, 0x73, 0x18, 0x92, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x18, 0x73, 0x6b, 0x69, 0x70, + 0x53, 0x65, 0x74, 0x52, 0x70, 0x4d, 0x61, 0x74, 0x63, 0x68, 0x53, 0x65, 0x74, 0x4f, 0x70, 0x74, + 0x69, 0x6f, 0x6e, 0x73, 0x12, 0x55, 0x0a, 0x27, 0x73, 0x6b, 0x69, 0x70, 0x5f, 0x73, 0x65, 0x74, + 0x74, 0x69, 0x6e, 0x67, 0x5f, 0x64, 0x69, 0x73, 0x61, 0x62, 0x6c, 0x65, 0x5f, 0x6d, 0x65, 0x74, + 0x72, 0x69, 0x63, 0x5f, 0x70, 0x72, 0x6f, 0x70, 0x61, 0x67, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x18, + 0x93, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x23, 0x73, 0x6b, 0x69, 0x70, 0x53, 0x65, 0x74, 0x74, + 0x69, 0x6e, 0x67, 0x44, 0x69, 0x73, 0x61, 0x62, 0x6c, 0x65, 0x4d, 0x65, 0x74, 0x72, 0x69, 0x63, + 0x50, 0x72, 0x6f, 0x70, 0x61, 0x67, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x62, 0x0a, 0x2e, 0x62, + 0x67, 0x70, 0x5f, 0x63, 0x6f, 0x6e, 0x64, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x5f, 0x6d, 0x61, + 0x74, 0x63, 0x68, 0x5f, 0x63, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x5f, 0x73, 0x65, + 0x74, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0x94, 0x01, + 0x20, 0x01, 0x28, 0x08, 0x52, 0x29, 0x62, 0x67, 0x70, 0x43, 0x6f, 0x6e, 0x64, 0x69, 0x74, 0x69, + 0x6f, 0x6e, 0x73, 0x4d, 0x61, 0x74, 0x63, 0x68, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, + 0x79, 0x53, 0x65, 0x74, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, + 0x41, 0x0a, 0x1d, 0x70, 0x66, 0x5f, 0x72, 0x65, 0x71, 0x75, 0x69, 0x72, 0x65, 0x5f, 0x6d, 0x61, + 0x74, 0x63, 0x68, 0x5f, 0x64, 0x65, 0x66, 0x61, 0x75, 0x6c, 0x74, 0x5f, 0x72, 0x75, 0x6c, 0x65, + 0x18, 0x95, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x19, 0x70, 0x66, 0x52, 0x65, 0x71, 0x75, 0x69, + 0x72, 0x65, 0x4d, 0x61, 0x74, 0x63, 0x68, 0x44, 0x65, 0x66, 0x61, 0x75, 0x6c, 0x74, 0x52, 0x75, + 0x6c, 0x65, 0x12, 0x67, 0x0a, 0x31, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6e, 0x67, 0x5f, 0x70, 0x6f, + 0x72, 0x74, 0x5f, 0x74, 0x6f, 0x5f, 0x6f, 0x70, 0x74, 0x69, 0x63, 0x61, 0x6c, 0x5f, 0x63, 0x68, + 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x5f, 0x63, 0x6f, 0x6d, 0x70, 0x6f, 0x6e, 0x65, 0x6e, 0x74, 0x5f, + 0x6d, 0x61, 0x70, 0x70, 0x69, 0x6e, 0x67, 0x18, 0x96, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x2b, + 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6e, 0x67, 0x50, 0x6f, 0x72, 0x74, 0x54, 0x6f, 0x4f, 0x70, 0x74, + 0x69, 0x63, 0x61, 0x6c, 0x43, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x43, 0x6f, 0x6d, 0x70, 0x6f, + 0x6e, 0x65, 0x6e, 0x74, 0x4d, 0x61, 0x70, 0x70, 0x69, 0x6e, 0x67, 0x12, 0x2b, 0x0a, 0x11, 0x73, + 0x6b, 0x69, 0x70, 0x5f, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x5f, 0x6f, 0x70, + 0x18, 0x97, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x0f, 0x73, 0x6b, 0x69, 0x70, 0x43, 0x6f, 0x6e, + 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x4f, 0x70, 0x12, 0x51, 0x0a, 0x25, 0x72, 0x65, 0x6f, 0x72, + 0x64, 0x65, 0x72, 0x5f, 0x63, 0x61, 0x6c, 0x6c, 0x73, 0x5f, 0x66, 0x6f, 0x72, 0x5f, 0x76, 0x65, + 0x6e, 0x64, 0x6f, 0x72, 0x5f, 0x63, 0x6f, 0x6d, 0x70, 0x61, 0x74, 0x69, 0x62, 0x69, 0x6c, 0x74, + 0x79, 0x18, 0x98, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x21, 0x72, 0x65, 0x6f, 0x72, 0x64, 0x65, + 0x72, 0x43, 0x61, 0x6c, 0x6c, 0x73, 0x46, 0x6f, 0x72, 0x56, 0x65, 0x6e, 0x64, 0x6f, 0x72, 0x43, + 0x6f, 0x6d, 0x70, 0x61, 0x74, 0x69, 0x62, 0x69, 0x6c, 0x74, 0x79, 0x12, 0x44, 0x0a, 0x1f, 0x61, + 0x64, 0x64, 0x5f, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6e, 0x67, 0x5f, 0x62, 0x61, 0x73, 0x65, 0x5f, + 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x5f, 0x76, 0x69, 0x61, 0x5f, 0x63, 0x6c, 0x69, 0x18, 0x99, + 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1a, 0x61, 0x64, 0x64, 0x4d, 0x69, 0x73, 0x73, 0x69, 0x6e, + 0x67, 0x42, 0x61, 0x73, 0x65, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x56, 0x69, 0x61, 0x43, 0x6c, + 0x69, 0x12, 0x33, 0x0a, 0x15, 0x73, 0x6b, 0x69, 0x70, 0x5f, 0x6d, 0x61, 0x63, 0x61, 0x64, 0x64, + 0x72, 0x65, 0x73, 0x73, 0x5f, 0x63, 0x68, 0x65, 0x63, 0x6b, 0x18, 0x9a, 0x01, 0x20, 0x01, 0x28, + 0x08, 0x52, 0x13, 0x73, 0x6b, 0x69, 0x70, 0x4d, 0x61, 0x63, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, + 0x73, 0x43, 0x68, 0x65, 0x63, 0x6b, 0x12, 0x3d, 0x0a, 0x1b, 0x62, 0x67, 0x70, 0x5f, 0x72, 0x69, + 0x62, 0x5f, 0x6f, 0x63, 0x5f, 0x70, 0x61, 0x74, 0x68, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, + 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0x9b, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x17, 0x62, 0x67, + 0x70, 0x52, 0x69, 0x62, 0x4f, 0x63, 0x50, 0x61, 0x74, 0x68, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, + 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x30, 0x0a, 0x14, 0x73, 0x6b, 0x69, 0x70, 0x5f, 0x70, 0x72, + 0x65, 0x66, 0x69, 0x78, 0x5f, 0x73, 0x65, 0x74, 0x5f, 0x6d, 0x6f, 0x64, 0x65, 0x18, 0x9c, 0x01, + 0x20, 0x01, 0x28, 0x08, 0x52, 0x11, 0x73, 0x6b, 0x69, 0x70, 0x50, 0x72, 0x65, 0x66, 0x69, 0x78, + 0x53, 0x65, 0x74, 0x4d, 0x6f, 0x64, 0x65, 0x12, 0x38, 0x0a, 0x18, 0x73, 0x65, 0x74, 0x5f, 0x6d, + 0x65, 0x74, 0x72, 0x69, 0x63, 0x5f, 0x61, 0x73, 0x5f, 0x70, 0x72, 0x65, 0x66, 0x65, 0x72, 0x65, + 0x6e, 0x63, 0x65, 0x18, 0x9d, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x15, 0x73, 0x65, 0x74, 0x4d, + 0x65, 0x74, 0x72, 0x69, 0x63, 0x41, 0x73, 0x50, 0x72, 0x65, 0x66, 0x65, 0x72, 0x65, 0x6e, 0x63, + 0x65, 0x12, 0x72, 0x0a, 0x38, 0x69, 0x70, 0x76, 0x36, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x69, 0x63, + 0x5f, 0x72, 0x6f, 0x75, 0x74, 0x65, 0x5f, 0x77, 0x69, 0x74, 0x68, 0x5f, 0x69, 0x70, 0x76, 0x34, + 0x5f, 0x6e, 0x65, 0x78, 0x74, 0x5f, 0x68, 0x6f, 0x70, 0x5f, 0x72, 0x65, 0x71, 0x75, 0x69, 0x72, + 0x65, 0x73, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x69, 0x63, 0x5f, 0x61, 0x72, 0x70, 0x18, 0x9e, 0x01, + 0x20, 0x01, 0x28, 0x08, 0x52, 0x2f, 0x69, 0x70, 0x76, 0x36, 0x53, 0x74, 0x61, 0x74, 0x69, 0x63, + 0x52, 0x6f, 0x75, 0x74, 0x65, 0x57, 0x69, 0x74, 0x68, 0x49, 0x70, 0x76, 0x34, 0x4e, 0x65, 0x78, + 0x74, 0x48, 0x6f, 0x70, 0x52, 0x65, 0x71, 0x75, 0x69, 0x72, 0x65, 0x73, 0x53, 0x74, 0x61, 0x74, + 0x69, 0x63, 0x41, 0x72, 0x70, 0x12, 0x50, 0x0a, 0x25, 0x70, 0x66, 0x5f, 0x72, 0x65, 0x71, 0x75, + 0x69, 0x72, 0x65, 0x5f, 0x73, 0x65, 0x71, 0x75, 0x65, 0x6e, 0x74, 0x69, 0x61, 0x6c, 0x5f, 0x6f, + 0x72, 0x64, 0x65, 0x72, 0x5f, 0x70, 0x62, 0x72, 0x5f, 0x72, 0x75, 0x6c, 0x65, 0x73, 0x18, 0x9f, + 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x20, 0x70, 0x66, 0x52, 0x65, 0x71, 0x75, 0x69, 0x72, 0x65, + 0x53, 0x65, 0x71, 0x75, 0x65, 0x6e, 0x74, 0x69, 0x61, 0x6c, 0x4f, 0x72, 0x64, 0x65, 0x72, 0x50, + 0x62, 0x72, 0x52, 0x75, 0x6c, 0x65, 0x73, 0x12, 0x61, 0x0a, 0x2e, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6e, 0x67, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x69, 0x63, 0x5f, 0x72, 0x6f, 0x75, 0x74, 0x65, 0x5f, - 0x64, 0x72, 0x6f, 0x70, 0x5f, 0x6e, 0x65, 0x78, 0x74, 0x5f, 0x68, 0x6f, 0x70, 0x5f, 0x74, 0x65, - 0x6c, 0x65, 0x6d, 0x65, 0x74, 0x72, 0x79, 0x18, 0xa2, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x26, - 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6e, 0x67, 0x53, 0x74, 0x61, 0x74, 0x69, 0x63, 0x52, 0x6f, 0x75, - 0x74, 0x65, 0x44, 0x72, 0x6f, 0x70, 0x4e, 0x65, 0x78, 0x74, 0x48, 0x6f, 0x70, 0x54, 0x65, 0x6c, - 0x65, 0x6d, 0x65, 0x74, 0x72, 0x79, 0x12, 0x73, 0x0a, 0x37, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6e, - 0x67, 0x5f, 0x7a, 0x72, 0x5f, 0x6f, 0x70, 0x74, 0x69, 0x63, 0x61, 0x6c, 0x5f, 0x63, 0x68, 0x61, - 0x6e, 0x6e, 0x65, 0x6c, 0x5f, 0x74, 0x75, 0x6e, 0x61, 0x62, 0x6c, 0x65, 0x5f, 0x70, 0x61, 0x72, - 0x61, 0x6d, 0x65, 0x74, 0x65, 0x72, 0x73, 0x5f, 0x74, 0x65, 0x6c, 0x65, 0x6d, 0x65, 0x74, 0x72, - 0x79, 0x18, 0xa3, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x31, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6e, - 0x67, 0x5a, 0x72, 0x4f, 0x70, 0x74, 0x69, 0x63, 0x61, 0x6c, 0x43, 0x68, 0x61, 0x6e, 0x6e, 0x65, - 0x6c, 0x54, 0x75, 0x6e, 0x61, 0x62, 0x6c, 0x65, 0x50, 0x61, 0x72, 0x61, 0x6d, 0x65, 0x74, 0x65, - 0x72, 0x73, 0x54, 0x65, 0x6c, 0x65, 0x6d, 0x65, 0x74, 0x72, 0x79, 0x12, 0x46, 0x0a, 0x1f, 0x70, - 0x6c, 0x71, 0x5f, 0x72, 0x65, 0x66, 0x6c, 0x65, 0x63, 0x74, 0x6f, 0x72, 0x5f, 0x73, 0x74, 0x61, - 0x74, 0x73, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xa4, - 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1c, 0x70, 0x6c, 0x71, 0x52, 0x65, 0x66, 0x6c, 0x65, 0x63, - 0x74, 0x6f, 0x72, 0x53, 0x74, 0x61, 0x74, 0x73, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, - 0x74, 0x65, 0x64, 0x12, 0x4b, 0x0a, 0x22, 0x70, 0x6c, 0x71, 0x5f, 0x67, 0x65, 0x6e, 0x65, 0x72, - 0x61, 0x74, 0x6f, 0x72, 0x5f, 0x63, 0x61, 0x70, 0x61, 0x62, 0x69, 0x6c, 0x69, 0x74, 0x69, 0x65, - 0x73, 0x5f, 0x6d, 0x61, 0x78, 0x5f, 0x6d, 0x74, 0x75, 0x18, 0xa5, 0x01, 0x20, 0x01, 0x28, 0x0d, - 0x52, 0x1e, 0x70, 0x6c, 0x71, 0x47, 0x65, 0x6e, 0x65, 0x72, 0x61, 0x74, 0x6f, 0x72, 0x43, 0x61, - 0x70, 0x61, 0x62, 0x69, 0x6c, 0x69, 0x74, 0x69, 0x65, 0x73, 0x4d, 0x61, 0x78, 0x4d, 0x74, 0x75, + 0x6e, 0x65, 0x78, 0x74, 0x5f, 0x68, 0x6f, 0x70, 0x5f, 0x6d, 0x65, 0x74, 0x72, 0x69, 0x63, 0x5f, + 0x74, 0x65, 0x6c, 0x65, 0x6d, 0x65, 0x74, 0x72, 0x79, 0x18, 0xa0, 0x01, 0x20, 0x01, 0x28, 0x08, + 0x52, 0x28, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6e, 0x67, 0x53, 0x74, 0x61, 0x74, 0x69, 0x63, 0x52, + 0x6f, 0x75, 0x74, 0x65, 0x4e, 0x65, 0x78, 0x74, 0x48, 0x6f, 0x70, 0x4d, 0x65, 0x74, 0x72, 0x69, + 0x63, 0x54, 0x65, 0x6c, 0x65, 0x6d, 0x65, 0x74, 0x72, 0x79, 0x12, 0x58, 0x0a, 0x29, 0x75, 0x6e, + 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x69, 0x63, + 0x5f, 0x72, 0x6f, 0x75, 0x74, 0x65, 0x5f, 0x6e, 0x65, 0x78, 0x74, 0x5f, 0x68, 0x6f, 0x70, 0x5f, + 0x72, 0x65, 0x63, 0x75, 0x72, 0x73, 0x65, 0x18, 0xa1, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x24, + 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x53, 0x74, 0x61, 0x74, 0x69, + 0x63, 0x52, 0x6f, 0x75, 0x74, 0x65, 0x4e, 0x65, 0x78, 0x74, 0x48, 0x6f, 0x70, 0x52, 0x65, 0x63, + 0x75, 0x72, 0x73, 0x65, 0x12, 0x5d, 0x0a, 0x2c, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6e, 0x67, 0x5f, + 0x73, 0x74, 0x61, 0x74, 0x69, 0x63, 0x5f, 0x72, 0x6f, 0x75, 0x74, 0x65, 0x5f, 0x64, 0x72, 0x6f, + 0x70, 0x5f, 0x6e, 0x65, 0x78, 0x74, 0x5f, 0x68, 0x6f, 0x70, 0x5f, 0x74, 0x65, 0x6c, 0x65, 0x6d, + 0x65, 0x74, 0x72, 0x79, 0x18, 0xa2, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x26, 0x6d, 0x69, 0x73, + 0x73, 0x69, 0x6e, 0x67, 0x53, 0x74, 0x61, 0x74, 0x69, 0x63, 0x52, 0x6f, 0x75, 0x74, 0x65, 0x44, + 0x72, 0x6f, 0x70, 0x4e, 0x65, 0x78, 0x74, 0x48, 0x6f, 0x70, 0x54, 0x65, 0x6c, 0x65, 0x6d, 0x65, + 0x74, 0x72, 0x79, 0x12, 0x73, 0x0a, 0x37, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6e, 0x67, 0x5f, 0x7a, + 0x72, 0x5f, 0x6f, 0x70, 0x74, 0x69, 0x63, 0x61, 0x6c, 0x5f, 0x63, 0x68, 0x61, 0x6e, 0x6e, 0x65, + 0x6c, 0x5f, 0x74, 0x75, 0x6e, 0x61, 0x62, 0x6c, 0x65, 0x5f, 0x70, 0x61, 0x72, 0x61, 0x6d, 0x65, + 0x74, 0x65, 0x72, 0x73, 0x5f, 0x74, 0x65, 0x6c, 0x65, 0x6d, 0x65, 0x74, 0x72, 0x79, 0x18, 0xa3, + 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x31, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6e, 0x67, 0x5a, 0x72, + 0x4f, 0x70, 0x74, 0x69, 0x63, 0x61, 0x6c, 0x43, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x54, 0x75, + 0x6e, 0x61, 0x62, 0x6c, 0x65, 0x50, 0x61, 0x72, 0x61, 0x6d, 0x65, 0x74, 0x65, 0x72, 0x73, 0x54, + 0x65, 0x6c, 0x65, 0x6d, 0x65, 0x74, 0x72, 0x79, 0x12, 0x46, 0x0a, 0x1f, 0x70, 0x6c, 0x71, 0x5f, + 0x72, 0x65, 0x66, 0x6c, 0x65, 0x63, 0x74, 0x6f, 0x72, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x73, 0x5f, + 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xa4, 0x01, 0x20, 0x01, + 0x28, 0x08, 0x52, 0x1c, 0x70, 0x6c, 0x71, 0x52, 0x65, 0x66, 0x6c, 0x65, 0x63, 0x74, 0x6f, 0x72, + 0x53, 0x74, 0x61, 0x74, 0x73, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x4b, 0x0a, 0x22, 0x70, 0x6c, 0x71, 0x5f, 0x67, 0x65, 0x6e, 0x65, 0x72, 0x61, 0x74, 0x6f, 0x72, 0x5f, 0x63, 0x61, 0x70, 0x61, 0x62, 0x69, 0x6c, 0x69, 0x74, 0x69, 0x65, 0x73, 0x5f, 0x6d, - 0x61, 0x78, 0x5f, 0x70, 0x70, 0x73, 0x18, 0xa6, 0x01, 0x20, 0x01, 0x28, 0x04, 0x52, 0x1e, 0x70, + 0x61, 0x78, 0x5f, 0x6d, 0x74, 0x75, 0x18, 0xa5, 0x01, 0x20, 0x01, 0x28, 0x0d, 0x52, 0x1e, 0x70, 0x6c, 0x71, 0x47, 0x65, 0x6e, 0x65, 0x72, 0x61, 0x74, 0x6f, 0x72, 0x43, 0x61, 0x70, 0x61, 0x62, - 0x69, 0x6c, 0x69, 0x74, 0x69, 0x65, 0x73, 0x4d, 0x61, 0x78, 0x50, 0x70, 0x73, 0x12, 0x57, 0x0a, - 0x28, 0x62, 0x67, 0x70, 0x5f, 0x65, 0x78, 0x74, 0x65, 0x6e, 0x64, 0x65, 0x64, 0x5f, 0x63, 0x6f, - 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x5f, 0x69, 0x6e, 0x64, 0x65, 0x78, 0x5f, 0x75, 0x6e, - 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xa7, 0x01, 0x20, 0x01, 0x28, 0x08, - 0x52, 0x24, 0x62, 0x67, 0x70, 0x45, 0x78, 0x74, 0x65, 0x6e, 0x64, 0x65, 0x64, 0x43, 0x6f, 0x6d, - 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x49, 0x6e, 0x64, 0x65, 0x78, 0x55, 0x6e, 0x73, 0x75, 0x70, - 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x4b, 0x0a, 0x22, 0x62, 0x67, 0x70, 0x5f, 0x63, 0x6f, - 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x5f, 0x73, 0x65, 0x74, 0x5f, 0x72, 0x65, 0x66, 0x73, - 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xa8, 0x01, 0x20, - 0x01, 0x28, 0x08, 0x52, 0x1e, 0x62, 0x67, 0x70, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, - 0x79, 0x53, 0x65, 0x74, 0x52, 0x65, 0x66, 0x73, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, - 0x74, 0x65, 0x64, 0x12, 0x1c, 0x0a, 0x09, 0x72, 0x69, 0x62, 0x5f, 0x77, 0x65, 0x63, 0x6d, 0x70, - 0x18, 0xa9, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x08, 0x72, 0x69, 0x62, 0x57, 0x65, 0x63, 0x6d, - 0x70, 0x12, 0x43, 0x0a, 0x1d, 0x74, 0x61, 0x62, 0x6c, 0x65, 0x5f, 0x63, 0x6f, 0x6e, 0x6e, 0x65, - 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, - 0x65, 0x64, 0x18, 0xaa, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1b, 0x74, 0x61, 0x62, 0x6c, 0x65, - 0x43, 0x6f, 0x6e, 0x6e, 0x65, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x55, 0x6e, 0x73, 0x75, 0x70, - 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x46, 0x0a, 0x20, 0x75, 0x73, 0x65, 0x5f, 0x76, 0x65, - 0x6e, 0x64, 0x6f, 0x72, 0x5f, 0x6e, 0x61, 0x74, 0x69, 0x76, 0x65, 0x5f, 0x74, 0x61, 0x67, 0x5f, - 0x73, 0x65, 0x74, 0x5f, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x18, 0xab, 0x01, 0x20, 0x01, 0x28, - 0x08, 0x52, 0x1b, 0x75, 0x73, 0x65, 0x56, 0x65, 0x6e, 0x64, 0x6f, 0x72, 0x4e, 0x61, 0x74, 0x69, - 0x76, 0x65, 0x54, 0x61, 0x67, 0x53, 0x65, 0x74, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x12, 0x3f, - 0x0a, 0x1c, 0x73, 0x6b, 0x69, 0x70, 0x5f, 0x62, 0x67, 0x70, 0x5f, 0x73, 0x65, 0x6e, 0x64, 0x5f, - 0x63, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x5f, 0x74, 0x79, 0x70, 0x65, 0x18, 0xac, - 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x18, 0x73, 0x6b, 0x69, 0x70, 0x42, 0x67, 0x70, 0x53, 0x65, - 0x6e, 0x64, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x54, 0x79, 0x70, 0x65, 0x12, - 0x5e, 0x0a, 0x2c, 0x62, 0x67, 0x70, 0x5f, 0x61, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x5f, 0x73, - 0x65, 0x74, 0x5f, 0x63, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x5f, 0x6d, 0x65, 0x74, - 0x68, 0x6f, 0x64, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, - 0xae, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x27, 0x62, 0x67, 0x70, 0x41, 0x63, 0x74, 0x69, 0x6f, - 0x6e, 0x73, 0x53, 0x65, 0x74, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x4d, 0x65, - 0x74, 0x68, 0x6f, 0x64, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, - 0x2a, 0x0a, 0x11, 0x73, 0x65, 0x74, 0x5f, 0x6e, 0x6f, 0x5f, 0x70, 0x65, 0x65, 0x72, 0x5f, 0x67, - 0x72, 0x6f, 0x75, 0x70, 0x18, 0xaf, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x0e, 0x73, 0x65, 0x74, - 0x4e, 0x6f, 0x50, 0x65, 0x65, 0x72, 0x47, 0x72, 0x6f, 0x75, 0x70, 0x12, 0x46, 0x0a, 0x20, 0x62, - 0x67, 0x70, 0x5f, 0x63, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x5f, 0x6d, 0x65, 0x6d, - 0x62, 0x65, 0x72, 0x5f, 0x69, 0x73, 0x5f, 0x61, 0x5f, 0x73, 0x74, 0x72, 0x69, 0x6e, 0x67, 0x18, - 0xb0, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1b, 0x62, 0x67, 0x70, 0x43, 0x6f, 0x6d, 0x6d, 0x75, - 0x6e, 0x69, 0x74, 0x79, 0x4d, 0x65, 0x6d, 0x62, 0x65, 0x72, 0x49, 0x73, 0x41, 0x53, 0x74, 0x72, - 0x69, 0x6e, 0x67, 0x12, 0x59, 0x0a, 0x2a, 0x69, 0x70, 0x76, 0x34, 0x5f, 0x73, 0x74, 0x61, 0x74, - 0x69, 0x63, 0x5f, 0x72, 0x6f, 0x75, 0x74, 0x65, 0x5f, 0x77, 0x69, 0x74, 0x68, 0x5f, 0x69, 0x70, - 0x76, 0x36, 0x5f, 0x6e, 0x68, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, - 0x64, 0x18, 0xb1, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x24, 0x69, 0x70, 0x76, 0x34, 0x53, 0x74, - 0x61, 0x74, 0x69, 0x63, 0x52, 0x6f, 0x75, 0x74, 0x65, 0x57, 0x69, 0x74, 0x68, 0x49, 0x70, 0x76, - 0x36, 0x4e, 0x68, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x59, - 0x0a, 0x2a, 0x69, 0x70, 0x76, 0x36, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x69, 0x63, 0x5f, 0x72, 0x6f, - 0x75, 0x74, 0x65, 0x5f, 0x77, 0x69, 0x74, 0x68, 0x5f, 0x69, 0x70, 0x76, 0x34, 0x5f, 0x6e, 0x68, - 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xb2, 0x01, 0x20, - 0x01, 0x28, 0x08, 0x52, 0x24, 0x69, 0x70, 0x76, 0x36, 0x53, 0x74, 0x61, 0x74, 0x69, 0x63, 0x52, - 0x6f, 0x75, 0x74, 0x65, 0x57, 0x69, 0x74, 0x68, 0x49, 0x70, 0x76, 0x34, 0x4e, 0x68, 0x55, 0x6e, - 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x39, 0x0a, 0x19, 0x73, 0x74, 0x61, - 0x74, 0x69, 0x63, 0x5f, 0x72, 0x6f, 0x75, 0x74, 0x65, 0x5f, 0x77, 0x69, 0x74, 0x68, 0x5f, 0x64, - 0x72, 0x6f, 0x70, 0x5f, 0x6e, 0x68, 0x18, 0xb3, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x15, 0x73, - 0x74, 0x61, 0x74, 0x69, 0x63, 0x52, 0x6f, 0x75, 0x74, 0x65, 0x57, 0x69, 0x74, 0x68, 0x44, 0x72, - 0x6f, 0x70, 0x4e, 0x68, 0x12, 0x49, 0x0a, 0x21, 0x73, 0x74, 0x61, 0x74, 0x69, 0x63, 0x5f, 0x72, - 0x6f, 0x75, 0x74, 0x65, 0x5f, 0x77, 0x69, 0x74, 0x68, 0x5f, 0x65, 0x78, 0x70, 0x6c, 0x69, 0x63, - 0x69, 0x74, 0x5f, 0x6d, 0x65, 0x74, 0x72, 0x69, 0x63, 0x18, 0xb4, 0x01, 0x20, 0x01, 0x28, 0x08, - 0x52, 0x1d, 0x73, 0x74, 0x61, 0x74, 0x69, 0x63, 0x52, 0x6f, 0x75, 0x74, 0x65, 0x57, 0x69, 0x74, - 0x68, 0x45, 0x78, 0x70, 0x6c, 0x69, 0x63, 0x69, 0x74, 0x4d, 0x65, 0x74, 0x72, 0x69, 0x63, 0x12, - 0x44, 0x0a, 0x1e, 0x62, 0x67, 0x70, 0x5f, 0x64, 0x65, 0x66, 0x61, 0x75, 0x6c, 0x74, 0x5f, 0x70, - 0x6f, 0x6c, 0x69, 0x63, 0x79, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, - 0x64, 0x18, 0xb5, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1b, 0x62, 0x67, 0x70, 0x44, 0x65, 0x66, - 0x61, 0x75, 0x6c, 0x74, 0x50, 0x6f, 0x6c, 0x69, 0x63, 0x79, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, - 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x4a, 0x0a, 0x22, 0x65, 0x78, 0x70, 0x6c, 0x69, 0x63, 0x69, - 0x74, 0x5f, 0x65, 0x6e, 0x61, 0x62, 0x6c, 0x65, 0x5f, 0x62, 0x67, 0x70, 0x5f, 0x6f, 0x6e, 0x5f, - 0x64, 0x65, 0x66, 0x61, 0x75, 0x6c, 0x74, 0x5f, 0x76, 0x72, 0x66, 0x18, 0xb6, 0x01, 0x20, 0x01, - 0x28, 0x08, 0x52, 0x1d, 0x65, 0x78, 0x70, 0x6c, 0x69, 0x63, 0x69, 0x74, 0x45, 0x6e, 0x61, 0x62, - 0x6c, 0x65, 0x42, 0x67, 0x70, 0x4f, 0x6e, 0x44, 0x65, 0x66, 0x61, 0x75, 0x6c, 0x74, 0x56, 0x72, - 0x66, 0x12, 0x45, 0x0a, 0x1f, 0x72, 0x6f, 0x75, 0x74, 0x69, 0x6e, 0x67, 0x5f, 0x70, 0x6f, 0x6c, - 0x69, 0x63, 0x79, 0x5f, 0x74, 0x61, 0x67, 0x5f, 0x73, 0x65, 0x74, 0x5f, 0x65, 0x6d, 0x62, 0x65, - 0x64, 0x64, 0x65, 0x64, 0x18, 0xb7, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1b, 0x72, 0x6f, 0x75, - 0x74, 0x69, 0x6e, 0x67, 0x50, 0x6f, 0x6c, 0x69, 0x63, 0x79, 0x54, 0x61, 0x67, 0x53, 0x65, 0x74, - 0x45, 0x6d, 0x62, 0x65, 0x64, 0x64, 0x65, 0x64, 0x12, 0x50, 0x0a, 0x26, 0x73, 0x6b, 0x69, 0x70, - 0x5f, 0x61, 0x66, 0x69, 0x5f, 0x73, 0x61, 0x66, 0x69, 0x5f, 0x70, 0x61, 0x74, 0x68, 0x5f, 0x66, - 0x6f, 0x72, 0x5f, 0x62, 0x67, 0x70, 0x5f, 0x6d, 0x75, 0x6c, 0x74, 0x69, 0x70, 0x6c, 0x65, 0x5f, - 0x61, 0x73, 0x18, 0xb8, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1f, 0x73, 0x6b, 0x69, 0x70, 0x41, - 0x66, 0x69, 0x53, 0x61, 0x66, 0x69, 0x50, 0x61, 0x74, 0x68, 0x46, 0x6f, 0x72, 0x42, 0x67, 0x70, - 0x4d, 0x75, 0x6c, 0x74, 0x69, 0x70, 0x6c, 0x65, 0x41, 0x73, 0x12, 0x4c, 0x0a, 0x22, 0x63, 0x6f, - 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x5f, 0x6d, 0x65, 0x6d, 0x62, 0x65, 0x72, 0x5f, 0x72, - 0x65, 0x67, 0x65, 0x78, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, - 0x18, 0xb9, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1f, 0x63, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, - 0x74, 0x79, 0x4d, 0x65, 0x6d, 0x62, 0x65, 0x72, 0x52, 0x65, 0x67, 0x65, 0x78, 0x55, 0x6e, 0x73, - 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x46, 0x0a, 0x20, 0x73, 0x61, 0x6d, 0x65, - 0x5f, 0x70, 0x6f, 0x6c, 0x69, 0x63, 0x79, 0x5f, 0x61, 0x74, 0x74, 0x61, 0x63, 0x68, 0x65, 0x64, - 0x5f, 0x74, 0x6f, 0x5f, 0x61, 0x6c, 0x6c, 0x5f, 0x61, 0x66, 0x69, 0x73, 0x18, 0xba, 0x01, 0x20, - 0x01, 0x28, 0x08, 0x52, 0x1b, 0x73, 0x61, 0x6d, 0x65, 0x50, 0x6f, 0x6c, 0x69, 0x63, 0x79, 0x41, - 0x74, 0x74, 0x61, 0x63, 0x68, 0x65, 0x64, 0x54, 0x6f, 0x41, 0x6c, 0x6c, 0x41, 0x66, 0x69, 0x73, - 0x12, 0x49, 0x0a, 0x21, 0x73, 0x6b, 0x69, 0x70, 0x5f, 0x73, 0x65, 0x74, 0x74, 0x69, 0x6e, 0x67, - 0x5f, 0x73, 0x74, 0x61, 0x74, 0x65, 0x6d, 0x65, 0x6e, 0x74, 0x5f, 0x66, 0x6f, 0x72, 0x5f, 0x70, - 0x6f, 0x6c, 0x69, 0x63, 0x79, 0x18, 0xbb, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1d, 0x73, 0x6b, - 0x69, 0x70, 0x53, 0x65, 0x74, 0x74, 0x69, 0x6e, 0x67, 0x53, 0x74, 0x61, 0x74, 0x65, 0x6d, 0x65, - 0x6e, 0x74, 0x46, 0x6f, 0x72, 0x50, 0x6f, 0x6c, 0x69, 0x63, 0x79, 0x12, 0x42, 0x0a, 0x1d, 0x73, - 0x6b, 0x69, 0x70, 0x5f, 0x63, 0x68, 0x65, 0x63, 0x6b, 0x69, 0x6e, 0x67, 0x5f, 0x61, 0x74, 0x74, - 0x72, 0x69, 0x62, 0x75, 0x74, 0x65, 0x5f, 0x69, 0x6e, 0x64, 0x65, 0x78, 0x18, 0xbc, 0x01, 0x20, - 0x01, 0x28, 0x08, 0x52, 0x1a, 0x73, 0x6b, 0x69, 0x70, 0x43, 0x68, 0x65, 0x63, 0x6b, 0x69, 0x6e, - 0x67, 0x41, 0x74, 0x74, 0x72, 0x69, 0x62, 0x75, 0x74, 0x65, 0x49, 0x6e, 0x64, 0x65, 0x78, 0x12, - 0x55, 0x0a, 0x27, 0x66, 0x6c, 0x61, 0x74, 0x74, 0x65, 0x6e, 0x5f, 0x70, 0x6f, 0x6c, 0x69, 0x63, - 0x79, 0x5f, 0x77, 0x69, 0x74, 0x68, 0x5f, 0x6d, 0x75, 0x6c, 0x74, 0x69, 0x70, 0x6c, 0x65, 0x5f, - 0x73, 0x74, 0x61, 0x74, 0x65, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x18, 0xbd, 0x01, 0x20, 0x01, 0x28, - 0x08, 0x52, 0x23, 0x66, 0x6c, 0x61, 0x74, 0x74, 0x65, 0x6e, 0x50, 0x6f, 0x6c, 0x69, 0x63, 0x79, - 0x57, 0x69, 0x74, 0x68, 0x4d, 0x75, 0x6c, 0x74, 0x69, 0x70, 0x6c, 0x65, 0x53, 0x74, 0x61, 0x74, - 0x65, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x12, 0x48, 0x0a, 0x20, 0x64, 0x65, 0x66, 0x61, 0x75, 0x6c, - 0x74, 0x5f, 0x72, 0x6f, 0x75, 0x74, 0x65, 0x5f, 0x70, 0x6f, 0x6c, 0x69, 0x63, 0x79, 0x5f, 0x75, - 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xbe, 0x01, 0x20, 0x01, 0x28, - 0x08, 0x52, 0x1d, 0x64, 0x65, 0x66, 0x61, 0x75, 0x6c, 0x74, 0x52, 0x6f, 0x75, 0x74, 0x65, 0x50, - 0x6f, 0x6c, 0x69, 0x63, 0x79, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, - 0x12, 0x35, 0x0a, 0x16, 0x73, 0x6c, 0x61, 0x61, 0x63, 0x5f, 0x70, 0x72, 0x65, 0x66, 0x69, 0x78, - 0x5f, 0x6c, 0x65, 0x6e, 0x67, 0x74, 0x68, 0x31, 0x32, 0x38, 0x18, 0xbf, 0x01, 0x20, 0x01, 0x28, - 0x08, 0x52, 0x14, 0x73, 0x6c, 0x61, 0x61, 0x63, 0x50, 0x72, 0x65, 0x66, 0x69, 0x78, 0x4c, 0x65, - 0x6e, 0x67, 0x74, 0x68, 0x31, 0x32, 0x38, 0x12, 0x4d, 0x0a, 0x23, 0x62, 0x67, 0x70, 0x5f, 0x6d, - 0x61, 0x78, 0x5f, 0x6d, 0x75, 0x6c, 0x74, 0x69, 0x70, 0x61, 0x74, 0x68, 0x5f, 0x70, 0x61, 0x74, - 0x68, 0x73, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xc0, - 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1f, 0x62, 0x67, 0x70, 0x4d, 0x61, 0x78, 0x4d, 0x75, 0x6c, - 0x74, 0x69, 0x70, 0x61, 0x74, 0x68, 0x50, 0x61, 0x74, 0x68, 0x73, 0x55, 0x6e, 0x73, 0x75, 0x70, - 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x59, 0x0a, 0x29, 0x6d, 0x75, 0x6c, 0x74, 0x69, 0x70, - 0x61, 0x74, 0x68, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x5f, - 0x6e, 0x65, 0x69, 0x67, 0x68, 0x62, 0x6f, 0x72, 0x5f, 0x6f, 0x72, 0x5f, 0x61, 0x66, 0x69, 0x73, - 0x61, 0x66, 0x69, 0x18, 0xc1, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x25, 0x6d, 0x75, 0x6c, 0x74, - 0x69, 0x70, 0x61, 0x74, 0x68, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, - 0x4e, 0x65, 0x69, 0x67, 0x68, 0x62, 0x6f, 0x72, 0x4f, 0x72, 0x41, 0x66, 0x69, 0x73, 0x61, 0x66, - 0x69, 0x12, 0x35, 0x0a, 0x16, 0x6d, 0x6f, 0x64, 0x65, 0x6c, 0x5f, 0x6e, 0x61, 0x6d, 0x65, 0x5f, - 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xc2, 0x01, 0x20, 0x01, - 0x28, 0x08, 0x52, 0x14, 0x6d, 0x6f, 0x64, 0x65, 0x6c, 0x4e, 0x61, 0x6d, 0x65, 0x55, 0x6e, 0x73, - 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x65, 0x0a, 0x2f, 0x63, 0x6f, 0x6d, 0x6d, - 0x75, 0x6e, 0x69, 0x74, 0x79, 0x5f, 0x6d, 0x61, 0x74, 0x63, 0x68, 0x5f, 0x77, 0x69, 0x74, 0x68, - 0x5f, 0x72, 0x65, 0x64, 0x69, 0x73, 0x74, 0x72, 0x69, 0x62, 0x75, 0x74, 0x69, 0x6f, 0x6e, 0x5f, - 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xc3, 0x01, 0x20, 0x01, - 0x28, 0x08, 0x52, 0x2b, 0x63, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x4d, 0x61, 0x74, - 0x63, 0x68, 0x57, 0x69, 0x74, 0x68, 0x52, 0x65, 0x64, 0x69, 0x73, 0x74, 0x72, 0x69, 0x62, 0x75, - 0x74, 0x69, 0x6f, 0x6e, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, - 0x6a, 0x0a, 0x32, 0x69, 0x6e, 0x73, 0x74, 0x61, 0x6c, 0x6c, 0x5f, 0x70, 0x6f, 0x73, 0x69, 0x74, - 0x69, 0x6f, 0x6e, 0x5f, 0x61, 0x6e, 0x64, 0x5f, 0x69, 0x6e, 0x73, 0x74, 0x61, 0x6c, 0x6c, 0x5f, - 0x63, 0x6f, 0x6d, 0x70, 0x6f, 0x6e, 0x65, 0x6e, 0x74, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, - 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xc4, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x2d, 0x69, 0x6e, - 0x73, 0x74, 0x61, 0x6c, 0x6c, 0x50, 0x6f, 0x73, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x41, 0x6e, 0x64, - 0x49, 0x6e, 0x73, 0x74, 0x61, 0x6c, 0x6c, 0x43, 0x6f, 0x6d, 0x70, 0x6f, 0x6e, 0x65, 0x6e, 0x74, - 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x57, 0x0a, 0x29, 0x65, - 0x6e, 0x63, 0x61, 0x70, 0x5f, 0x74, 0x75, 0x6e, 0x6e, 0x65, 0x6c, 0x5f, 0x73, 0x68, 0x75, 0x74, - 0x5f, 0x62, 0x61, 0x63, 0x6b, 0x75, 0x70, 0x5f, 0x6e, 0x68, 0x67, 0x5f, 0x7a, 0x65, 0x72, 0x6f, - 0x5f, 0x74, 0x72, 0x61, 0x66, 0x66, 0x69, 0x63, 0x18, 0xc5, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, - 0x23, 0x65, 0x6e, 0x63, 0x61, 0x70, 0x54, 0x75, 0x6e, 0x6e, 0x65, 0x6c, 0x53, 0x68, 0x75, 0x74, - 0x42, 0x61, 0x63, 0x6b, 0x75, 0x70, 0x4e, 0x68, 0x67, 0x5a, 0x65, 0x72, 0x6f, 0x54, 0x72, 0x61, - 0x66, 0x66, 0x69, 0x63, 0x12, 0x25, 0x0a, 0x0e, 0x6d, 0x61, 0x78, 0x5f, 0x65, 0x63, 0x6d, 0x70, - 0x5f, 0x70, 0x61, 0x74, 0x68, 0x73, 0x18, 0xc6, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x0c, 0x6d, - 0x61, 0x78, 0x45, 0x63, 0x6d, 0x70, 0x50, 0x61, 0x74, 0x68, 0x73, 0x12, 0x35, 0x0a, 0x16, 0x77, - 0x65, 0x63, 0x6d, 0x70, 0x5f, 0x61, 0x75, 0x74, 0x6f, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, - 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xc7, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x14, 0x77, 0x65, - 0x63, 0x6d, 0x70, 0x41, 0x75, 0x74, 0x6f, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, - 0x65, 0x64, 0x12, 0x4e, 0x0a, 0x23, 0x72, 0x6f, 0x75, 0x74, 0x69, 0x6e, 0x67, 0x5f, 0x70, 0x6f, - 0x6c, 0x69, 0x63, 0x79, 0x5f, 0x63, 0x68, 0x61, 0x69, 0x6e, 0x69, 0x6e, 0x67, 0x5f, 0x75, 0x6e, - 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xc8, 0x01, 0x20, 0x01, 0x28, 0x08, - 0x52, 0x20, 0x72, 0x6f, 0x75, 0x74, 0x69, 0x6e, 0x67, 0x50, 0x6f, 0x6c, 0x69, 0x63, 0x79, 0x43, - 0x68, 0x61, 0x69, 0x6e, 0x69, 0x6e, 0x67, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, - 0x65, 0x64, 0x12, 0x35, 0x0a, 0x16, 0x69, 0x73, 0x69, 0x73, 0x5f, 0x6c, 0x6f, 0x6f, 0x70, 0x62, - 0x61, 0x63, 0x6b, 0x5f, 0x72, 0x65, 0x71, 0x75, 0x69, 0x72, 0x65, 0x64, 0x18, 0xc9, 0x01, 0x20, - 0x01, 0x28, 0x08, 0x52, 0x14, 0x69, 0x73, 0x69, 0x73, 0x4c, 0x6f, 0x6f, 0x70, 0x62, 0x61, 0x63, - 0x6b, 0x52, 0x65, 0x71, 0x75, 0x69, 0x72, 0x65, 0x64, 0x12, 0x55, 0x0a, 0x27, 0x77, 0x65, 0x69, - 0x67, 0x68, 0x74, 0x65, 0x64, 0x5f, 0x65, 0x63, 0x6d, 0x70, 0x5f, 0x66, 0x69, 0x78, 0x65, 0x64, - 0x5f, 0x70, 0x61, 0x63, 0x6b, 0x65, 0x74, 0x5f, 0x76, 0x65, 0x72, 0x69, 0x66, 0x69, 0x63, 0x61, - 0x74, 0x69, 0x6f, 0x6e, 0x18, 0xca, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x23, 0x77, 0x65, 0x69, - 0x67, 0x68, 0x74, 0x65, 0x64, 0x45, 0x63, 0x6d, 0x70, 0x46, 0x69, 0x78, 0x65, 0x64, 0x50, 0x61, - 0x63, 0x6b, 0x65, 0x74, 0x56, 0x65, 0x72, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74, 0x69, 0x6f, 0x6e, - 0x12, 0x3a, 0x0a, 0x19, 0x6f, 0x76, 0x65, 0x72, 0x72, 0x69, 0x64, 0x65, 0x5f, 0x64, 0x65, 0x66, - 0x61, 0x75, 0x6c, 0x74, 0x5f, 0x6e, 0x68, 0x5f, 0x73, 0x63, 0x61, 0x6c, 0x65, 0x18, 0xcb, 0x01, - 0x20, 0x01, 0x28, 0x08, 0x52, 0x16, 0x6f, 0x76, 0x65, 0x72, 0x72, 0x69, 0x64, 0x65, 0x44, 0x65, - 0x66, 0x61, 0x75, 0x6c, 0x74, 0x4e, 0x68, 0x53, 0x63, 0x61, 0x6c, 0x65, 0x12, 0x53, 0x0a, 0x26, - 0x62, 0x67, 0x70, 0x5f, 0x65, 0x78, 0x74, 0x65, 0x6e, 0x64, 0x65, 0x64, 0x5f, 0x63, 0x6f, 0x6d, - 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x5f, 0x73, 0x65, 0x74, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, - 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xcc, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x22, 0x62, + 0x69, 0x6c, 0x69, 0x74, 0x69, 0x65, 0x73, 0x4d, 0x61, 0x78, 0x4d, 0x74, 0x75, 0x12, 0x4b, 0x0a, + 0x22, 0x70, 0x6c, 0x71, 0x5f, 0x67, 0x65, 0x6e, 0x65, 0x72, 0x61, 0x74, 0x6f, 0x72, 0x5f, 0x63, + 0x61, 0x70, 0x61, 0x62, 0x69, 0x6c, 0x69, 0x74, 0x69, 0x65, 0x73, 0x5f, 0x6d, 0x61, 0x78, 0x5f, + 0x70, 0x70, 0x73, 0x18, 0xa6, 0x01, 0x20, 0x01, 0x28, 0x04, 0x52, 0x1e, 0x70, 0x6c, 0x71, 0x47, + 0x65, 0x6e, 0x65, 0x72, 0x61, 0x74, 0x6f, 0x72, 0x43, 0x61, 0x70, 0x61, 0x62, 0x69, 0x6c, 0x69, + 0x74, 0x69, 0x65, 0x73, 0x4d, 0x61, 0x78, 0x50, 0x70, 0x73, 0x12, 0x57, 0x0a, 0x28, 0x62, 0x67, + 0x70, 0x5f, 0x65, 0x78, 0x74, 0x65, 0x6e, 0x64, 0x65, 0x64, 0x5f, 0x63, 0x6f, 0x6d, 0x6d, 0x75, + 0x6e, 0x69, 0x74, 0x79, 0x5f, 0x69, 0x6e, 0x64, 0x65, 0x78, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, + 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xa7, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x24, 0x62, 0x67, 0x70, 0x45, 0x78, 0x74, 0x65, 0x6e, 0x64, 0x65, 0x64, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, - 0x69, 0x74, 0x79, 0x53, 0x65, 0x74, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, - 0x64, 0x12, 0x59, 0x0a, 0x2a, 0x62, 0x67, 0x70, 0x5f, 0x73, 0x65, 0x74, 0x5f, 0x65, 0x78, 0x74, - 0x5f, 0x63, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x5f, 0x73, 0x65, 0x74, 0x5f, 0x72, - 0x65, 0x66, 0x73, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, - 0xcd, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x24, 0x62, 0x67, 0x70, 0x53, 0x65, 0x74, 0x45, 0x78, - 0x74, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x53, 0x65, 0x74, 0x52, 0x65, 0x66, - 0x73, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x51, 0x0a, 0x25, - 0x62, 0x67, 0x70, 0x5f, 0x64, 0x65, 0x6c, 0x65, 0x74, 0x65, 0x5f, 0x6c, 0x69, 0x6e, 0x6b, 0x5f, - 0x62, 0x61, 0x6e, 0x64, 0x77, 0x69, 0x64, 0x74, 0x68, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, - 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xce, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x21, 0x62, 0x67, - 0x70, 0x44, 0x65, 0x6c, 0x65, 0x74, 0x65, 0x4c, 0x69, 0x6e, 0x6b, 0x42, 0x61, 0x6e, 0x64, 0x77, - 0x69, 0x64, 0x74, 0x68, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, - 0x4f, 0x0a, 0x24, 0x71, 0x6f, 0x73, 0x5f, 0x69, 0x6e, 0x71, 0x75, 0x65, 0x75, 0x65, 0x5f, 0x64, - 0x72, 0x6f, 0x70, 0x5f, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x65, 0x72, 0x5f, 0x75, 0x6e, 0x73, 0x75, - 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xcf, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x20, - 0x71, 0x6f, 0x73, 0x49, 0x6e, 0x71, 0x75, 0x65, 0x75, 0x65, 0x44, 0x72, 0x6f, 0x70, 0x43, 0x6f, - 0x75, 0x6e, 0x74, 0x65, 0x72, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, - 0x12, 0x53, 0x0a, 0x26, 0x62, 0x67, 0x70, 0x5f, 0x65, 0x78, 0x70, 0x6c, 0x69, 0x63, 0x69, 0x74, + 0x69, 0x74, 0x79, 0x49, 0x6e, 0x64, 0x65, 0x78, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, + 0x74, 0x65, 0x64, 0x12, 0x4b, 0x0a, 0x22, 0x62, 0x67, 0x70, 0x5f, 0x63, 0x6f, 0x6d, 0x6d, 0x75, + 0x6e, 0x69, 0x74, 0x79, 0x5f, 0x73, 0x65, 0x74, 0x5f, 0x72, 0x65, 0x66, 0x73, 0x5f, 0x75, 0x6e, + 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xa8, 0x01, 0x20, 0x01, 0x28, 0x08, + 0x52, 0x1e, 0x62, 0x67, 0x70, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x53, 0x65, + 0x74, 0x52, 0x65, 0x66, 0x73, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, + 0x12, 0x1c, 0x0a, 0x09, 0x72, 0x69, 0x62, 0x5f, 0x77, 0x65, 0x63, 0x6d, 0x70, 0x18, 0xa9, 0x01, + 0x20, 0x01, 0x28, 0x08, 0x52, 0x08, 0x72, 0x69, 0x62, 0x57, 0x65, 0x63, 0x6d, 0x70, 0x12, 0x43, + 0x0a, 0x1d, 0x74, 0x61, 0x62, 0x6c, 0x65, 0x5f, 0x63, 0x6f, 0x6e, 0x6e, 0x65, 0x63, 0x74, 0x69, + 0x6f, 0x6e, 0x73, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, + 0xaa, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1b, 0x74, 0x61, 0x62, 0x6c, 0x65, 0x43, 0x6f, 0x6e, + 0x6e, 0x65, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, + 0x74, 0x65, 0x64, 0x12, 0x46, 0x0a, 0x20, 0x75, 0x73, 0x65, 0x5f, 0x76, 0x65, 0x6e, 0x64, 0x6f, + 0x72, 0x5f, 0x6e, 0x61, 0x74, 0x69, 0x76, 0x65, 0x5f, 0x74, 0x61, 0x67, 0x5f, 0x73, 0x65, 0x74, + 0x5f, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x18, 0xab, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1b, + 0x75, 0x73, 0x65, 0x56, 0x65, 0x6e, 0x64, 0x6f, 0x72, 0x4e, 0x61, 0x74, 0x69, 0x76, 0x65, 0x54, + 0x61, 0x67, 0x53, 0x65, 0x74, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x12, 0x3f, 0x0a, 0x1c, 0x73, + 0x6b, 0x69, 0x70, 0x5f, 0x62, 0x67, 0x70, 0x5f, 0x73, 0x65, 0x6e, 0x64, 0x5f, 0x63, 0x6f, 0x6d, + 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x5f, 0x74, 0x79, 0x70, 0x65, 0x18, 0xac, 0x01, 0x20, 0x01, + 0x28, 0x08, 0x52, 0x18, 0x73, 0x6b, 0x69, 0x70, 0x42, 0x67, 0x70, 0x53, 0x65, 0x6e, 0x64, 0x43, + 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x54, 0x79, 0x70, 0x65, 0x12, 0x5e, 0x0a, 0x2c, + 0x62, 0x67, 0x70, 0x5f, 0x61, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x5f, 0x73, 0x65, 0x74, 0x5f, + 0x63, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x5f, 0x6d, 0x65, 0x74, 0x68, 0x6f, 0x64, + 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xae, 0x01, 0x20, + 0x01, 0x28, 0x08, 0x52, 0x27, 0x62, 0x67, 0x70, 0x41, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x53, + 0x65, 0x74, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x4d, 0x65, 0x74, 0x68, 0x6f, + 0x64, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x2a, 0x0a, 0x11, + 0x73, 0x65, 0x74, 0x5f, 0x6e, 0x6f, 0x5f, 0x70, 0x65, 0x65, 0x72, 0x5f, 0x67, 0x72, 0x6f, 0x75, + 0x70, 0x18, 0xaf, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x0e, 0x73, 0x65, 0x74, 0x4e, 0x6f, 0x50, + 0x65, 0x65, 0x72, 0x47, 0x72, 0x6f, 0x75, 0x70, 0x12, 0x46, 0x0a, 0x20, 0x62, 0x67, 0x70, 0x5f, + 0x63, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x5f, 0x6d, 0x65, 0x6d, 0x62, 0x65, 0x72, + 0x5f, 0x69, 0x73, 0x5f, 0x61, 0x5f, 0x73, 0x74, 0x72, 0x69, 0x6e, 0x67, 0x18, 0xb0, 0x01, 0x20, + 0x01, 0x28, 0x08, 0x52, 0x1b, 0x62, 0x67, 0x70, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, + 0x79, 0x4d, 0x65, 0x6d, 0x62, 0x65, 0x72, 0x49, 0x73, 0x41, 0x53, 0x74, 0x72, 0x69, 0x6e, 0x67, + 0x12, 0x59, 0x0a, 0x2a, 0x69, 0x70, 0x76, 0x34, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x69, 0x63, 0x5f, + 0x72, 0x6f, 0x75, 0x74, 0x65, 0x5f, 0x77, 0x69, 0x74, 0x68, 0x5f, 0x69, 0x70, 0x76, 0x36, 0x5f, + 0x6e, 0x68, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xb1, + 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x24, 0x69, 0x70, 0x76, 0x34, 0x53, 0x74, 0x61, 0x74, 0x69, + 0x63, 0x52, 0x6f, 0x75, 0x74, 0x65, 0x57, 0x69, 0x74, 0x68, 0x49, 0x70, 0x76, 0x36, 0x4e, 0x68, + 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x59, 0x0a, 0x2a, 0x69, + 0x70, 0x76, 0x36, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x69, 0x63, 0x5f, 0x72, 0x6f, 0x75, 0x74, 0x65, + 0x5f, 0x77, 0x69, 0x74, 0x68, 0x5f, 0x69, 0x70, 0x76, 0x34, 0x5f, 0x6e, 0x68, 0x5f, 0x75, 0x6e, + 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xb2, 0x01, 0x20, 0x01, 0x28, 0x08, + 0x52, 0x24, 0x69, 0x70, 0x76, 0x36, 0x53, 0x74, 0x61, 0x74, 0x69, 0x63, 0x52, 0x6f, 0x75, 0x74, + 0x65, 0x57, 0x69, 0x74, 0x68, 0x49, 0x70, 0x76, 0x34, 0x4e, 0x68, 0x55, 0x6e, 0x73, 0x75, 0x70, + 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x39, 0x0a, 0x19, 0x73, 0x74, 0x61, 0x74, 0x69, 0x63, + 0x5f, 0x72, 0x6f, 0x75, 0x74, 0x65, 0x5f, 0x77, 0x69, 0x74, 0x68, 0x5f, 0x64, 0x72, 0x6f, 0x70, + 0x5f, 0x6e, 0x68, 0x18, 0xb3, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x15, 0x73, 0x74, 0x61, 0x74, + 0x69, 0x63, 0x52, 0x6f, 0x75, 0x74, 0x65, 0x57, 0x69, 0x74, 0x68, 0x44, 0x72, 0x6f, 0x70, 0x4e, + 0x68, 0x12, 0x49, 0x0a, 0x21, 0x73, 0x74, 0x61, 0x74, 0x69, 0x63, 0x5f, 0x72, 0x6f, 0x75, 0x74, + 0x65, 0x5f, 0x77, 0x69, 0x74, 0x68, 0x5f, 0x65, 0x78, 0x70, 0x6c, 0x69, 0x63, 0x69, 0x74, 0x5f, + 0x6d, 0x65, 0x74, 0x72, 0x69, 0x63, 0x18, 0xb4, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1d, 0x73, + 0x74, 0x61, 0x74, 0x69, 0x63, 0x52, 0x6f, 0x75, 0x74, 0x65, 0x57, 0x69, 0x74, 0x68, 0x45, 0x78, + 0x70, 0x6c, 0x69, 0x63, 0x69, 0x74, 0x4d, 0x65, 0x74, 0x72, 0x69, 0x63, 0x12, 0x44, 0x0a, 0x1e, + 0x62, 0x67, 0x70, 0x5f, 0x64, 0x65, 0x66, 0x61, 0x75, 0x6c, 0x74, 0x5f, 0x70, 0x6f, 0x6c, 0x69, + 0x63, 0x79, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xb5, + 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1b, 0x62, 0x67, 0x70, 0x44, 0x65, 0x66, 0x61, 0x75, 0x6c, + 0x74, 0x50, 0x6f, 0x6c, 0x69, 0x63, 0x79, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, + 0x65, 0x64, 0x12, 0x4a, 0x0a, 0x22, 0x65, 0x78, 0x70, 0x6c, 0x69, 0x63, 0x69, 0x74, 0x5f, 0x65, + 0x6e, 0x61, 0x62, 0x6c, 0x65, 0x5f, 0x62, 0x67, 0x70, 0x5f, 0x6f, 0x6e, 0x5f, 0x64, 0x65, 0x66, + 0x61, 0x75, 0x6c, 0x74, 0x5f, 0x76, 0x72, 0x66, 0x18, 0xb6, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, + 0x1d, 0x65, 0x78, 0x70, 0x6c, 0x69, 0x63, 0x69, 0x74, 0x45, 0x6e, 0x61, 0x62, 0x6c, 0x65, 0x42, + 0x67, 0x70, 0x4f, 0x6e, 0x44, 0x65, 0x66, 0x61, 0x75, 0x6c, 0x74, 0x56, 0x72, 0x66, 0x12, 0x45, + 0x0a, 0x1f, 0x72, 0x6f, 0x75, 0x74, 0x69, 0x6e, 0x67, 0x5f, 0x70, 0x6f, 0x6c, 0x69, 0x63, 0x79, + 0x5f, 0x74, 0x61, 0x67, 0x5f, 0x73, 0x65, 0x74, 0x5f, 0x65, 0x6d, 0x62, 0x65, 0x64, 0x64, 0x65, + 0x64, 0x18, 0xb7, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1b, 0x72, 0x6f, 0x75, 0x74, 0x69, 0x6e, + 0x67, 0x50, 0x6f, 0x6c, 0x69, 0x63, 0x79, 0x54, 0x61, 0x67, 0x53, 0x65, 0x74, 0x45, 0x6d, 0x62, + 0x65, 0x64, 0x64, 0x65, 0x64, 0x12, 0x50, 0x0a, 0x26, 0x73, 0x6b, 0x69, 0x70, 0x5f, 0x61, 0x66, + 0x69, 0x5f, 0x73, 0x61, 0x66, 0x69, 0x5f, 0x70, 0x61, 0x74, 0x68, 0x5f, 0x66, 0x6f, 0x72, 0x5f, + 0x62, 0x67, 0x70, 0x5f, 0x6d, 0x75, 0x6c, 0x74, 0x69, 0x70, 0x6c, 0x65, 0x5f, 0x61, 0x73, 0x18, + 0xb8, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1f, 0x73, 0x6b, 0x69, 0x70, 0x41, 0x66, 0x69, 0x53, + 0x61, 0x66, 0x69, 0x50, 0x61, 0x74, 0x68, 0x46, 0x6f, 0x72, 0x42, 0x67, 0x70, 0x4d, 0x75, 0x6c, + 0x74, 0x69, 0x70, 0x6c, 0x65, 0x41, 0x73, 0x12, 0x4c, 0x0a, 0x22, 0x63, 0x6f, 0x6d, 0x6d, 0x75, + 0x6e, 0x69, 0x74, 0x79, 0x5f, 0x6d, 0x65, 0x6d, 0x62, 0x65, 0x72, 0x5f, 0x72, 0x65, 0x67, 0x65, + 0x78, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xb9, 0x01, + 0x20, 0x01, 0x28, 0x08, 0x52, 0x1f, 0x63, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x4d, + 0x65, 0x6d, 0x62, 0x65, 0x72, 0x52, 0x65, 0x67, 0x65, 0x78, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, + 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x46, 0x0a, 0x20, 0x73, 0x61, 0x6d, 0x65, 0x5f, 0x70, 0x6f, + 0x6c, 0x69, 0x63, 0x79, 0x5f, 0x61, 0x74, 0x74, 0x61, 0x63, 0x68, 0x65, 0x64, 0x5f, 0x74, 0x6f, + 0x5f, 0x61, 0x6c, 0x6c, 0x5f, 0x61, 0x66, 0x69, 0x73, 0x18, 0xba, 0x01, 0x20, 0x01, 0x28, 0x08, + 0x52, 0x1b, 0x73, 0x61, 0x6d, 0x65, 0x50, 0x6f, 0x6c, 0x69, 0x63, 0x79, 0x41, 0x74, 0x74, 0x61, + 0x63, 0x68, 0x65, 0x64, 0x54, 0x6f, 0x41, 0x6c, 0x6c, 0x41, 0x66, 0x69, 0x73, 0x12, 0x49, 0x0a, + 0x21, 0x73, 0x6b, 0x69, 0x70, 0x5f, 0x73, 0x65, 0x74, 0x74, 0x69, 0x6e, 0x67, 0x5f, 0x73, 0x74, + 0x61, 0x74, 0x65, 0x6d, 0x65, 0x6e, 0x74, 0x5f, 0x66, 0x6f, 0x72, 0x5f, 0x70, 0x6f, 0x6c, 0x69, + 0x63, 0x79, 0x18, 0xbb, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1d, 0x73, 0x6b, 0x69, 0x70, 0x53, + 0x65, 0x74, 0x74, 0x69, 0x6e, 0x67, 0x53, 0x74, 0x61, 0x74, 0x65, 0x6d, 0x65, 0x6e, 0x74, 0x46, + 0x6f, 0x72, 0x50, 0x6f, 0x6c, 0x69, 0x63, 0x79, 0x12, 0x42, 0x0a, 0x1d, 0x73, 0x6b, 0x69, 0x70, + 0x5f, 0x63, 0x68, 0x65, 0x63, 0x6b, 0x69, 0x6e, 0x67, 0x5f, 0x61, 0x74, 0x74, 0x72, 0x69, 0x62, + 0x75, 0x74, 0x65, 0x5f, 0x69, 0x6e, 0x64, 0x65, 0x78, 0x18, 0xbc, 0x01, 0x20, 0x01, 0x28, 0x08, + 0x52, 0x1a, 0x73, 0x6b, 0x69, 0x70, 0x43, 0x68, 0x65, 0x63, 0x6b, 0x69, 0x6e, 0x67, 0x41, 0x74, + 0x74, 0x72, 0x69, 0x62, 0x75, 0x74, 0x65, 0x49, 0x6e, 0x64, 0x65, 0x78, 0x12, 0x55, 0x0a, 0x27, + 0x66, 0x6c, 0x61, 0x74, 0x74, 0x65, 0x6e, 0x5f, 0x70, 0x6f, 0x6c, 0x69, 0x63, 0x79, 0x5f, 0x77, + 0x69, 0x74, 0x68, 0x5f, 0x6d, 0x75, 0x6c, 0x74, 0x69, 0x70, 0x6c, 0x65, 0x5f, 0x73, 0x74, 0x61, + 0x74, 0x65, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x18, 0xbd, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x23, + 0x66, 0x6c, 0x61, 0x74, 0x74, 0x65, 0x6e, 0x50, 0x6f, 0x6c, 0x69, 0x63, 0x79, 0x57, 0x69, 0x74, + 0x68, 0x4d, 0x75, 0x6c, 0x74, 0x69, 0x70, 0x6c, 0x65, 0x53, 0x74, 0x61, 0x74, 0x65, 0x6d, 0x65, + 0x6e, 0x74, 0x73, 0x12, 0x48, 0x0a, 0x20, 0x64, 0x65, 0x66, 0x61, 0x75, 0x6c, 0x74, 0x5f, 0x72, + 0x6f, 0x75, 0x74, 0x65, 0x5f, 0x70, 0x6f, 0x6c, 0x69, 0x63, 0x79, 0x5f, 0x75, 0x6e, 0x73, 0x75, + 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xbe, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1d, + 0x64, 0x65, 0x66, 0x61, 0x75, 0x6c, 0x74, 0x52, 0x6f, 0x75, 0x74, 0x65, 0x50, 0x6f, 0x6c, 0x69, + 0x63, 0x79, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x35, 0x0a, + 0x16, 0x73, 0x6c, 0x61, 0x61, 0x63, 0x5f, 0x70, 0x72, 0x65, 0x66, 0x69, 0x78, 0x5f, 0x6c, 0x65, + 0x6e, 0x67, 0x74, 0x68, 0x31, 0x32, 0x38, 0x18, 0xbf, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x14, + 0x73, 0x6c, 0x61, 0x61, 0x63, 0x50, 0x72, 0x65, 0x66, 0x69, 0x78, 0x4c, 0x65, 0x6e, 0x67, 0x74, + 0x68, 0x31, 0x32, 0x38, 0x12, 0x4d, 0x0a, 0x23, 0x62, 0x67, 0x70, 0x5f, 0x6d, 0x61, 0x78, 0x5f, + 0x6d, 0x75, 0x6c, 0x74, 0x69, 0x70, 0x61, 0x74, 0x68, 0x5f, 0x70, 0x61, 0x74, 0x68, 0x73, 0x5f, + 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xc0, 0x01, 0x20, 0x01, + 0x28, 0x08, 0x52, 0x1f, 0x62, 0x67, 0x70, 0x4d, 0x61, 0x78, 0x4d, 0x75, 0x6c, 0x74, 0x69, 0x70, + 0x61, 0x74, 0x68, 0x50, 0x61, 0x74, 0x68, 0x73, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, + 0x74, 0x65, 0x64, 0x12, 0x59, 0x0a, 0x29, 0x6d, 0x75, 0x6c, 0x74, 0x69, 0x70, 0x61, 0x74, 0x68, + 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x5f, 0x6e, 0x65, 0x69, + 0x67, 0x68, 0x62, 0x6f, 0x72, 0x5f, 0x6f, 0x72, 0x5f, 0x61, 0x66, 0x69, 0x73, 0x61, 0x66, 0x69, + 0x18, 0xc1, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x25, 0x6d, 0x75, 0x6c, 0x74, 0x69, 0x70, 0x61, + 0x74, 0x68, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x4e, 0x65, 0x69, + 0x67, 0x68, 0x62, 0x6f, 0x72, 0x4f, 0x72, 0x41, 0x66, 0x69, 0x73, 0x61, 0x66, 0x69, 0x12, 0x35, + 0x0a, 0x16, 0x6d, 0x6f, 0x64, 0x65, 0x6c, 0x5f, 0x6e, 0x61, 0x6d, 0x65, 0x5f, 0x75, 0x6e, 0x73, + 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xc2, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, + 0x14, 0x6d, 0x6f, 0x64, 0x65, 0x6c, 0x4e, 0x61, 0x6d, 0x65, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, + 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x65, 0x0a, 0x2f, 0x63, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, + 0x74, 0x79, 0x5f, 0x6d, 0x61, 0x74, 0x63, 0x68, 0x5f, 0x77, 0x69, 0x74, 0x68, 0x5f, 0x72, 0x65, + 0x64, 0x69, 0x73, 0x74, 0x72, 0x69, 0x62, 0x75, 0x74, 0x69, 0x6f, 0x6e, 0x5f, 0x75, 0x6e, 0x73, + 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xc3, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, + 0x2b, 0x63, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x4d, 0x61, 0x74, 0x63, 0x68, 0x57, + 0x69, 0x74, 0x68, 0x52, 0x65, 0x64, 0x69, 0x73, 0x74, 0x72, 0x69, 0x62, 0x75, 0x74, 0x69, 0x6f, + 0x6e, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x6a, 0x0a, 0x32, + 0x69, 0x6e, 0x73, 0x74, 0x61, 0x6c, 0x6c, 0x5f, 0x70, 0x6f, 0x73, 0x69, 0x74, 0x69, 0x6f, 0x6e, + 0x5f, 0x61, 0x6e, 0x64, 0x5f, 0x69, 0x6e, 0x73, 0x74, 0x61, 0x6c, 0x6c, 0x5f, 0x63, 0x6f, 0x6d, + 0x70, 0x6f, 0x6e, 0x65, 0x6e, 0x74, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, + 0x65, 0x64, 0x18, 0xc4, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x2d, 0x69, 0x6e, 0x73, 0x74, 0x61, + 0x6c, 0x6c, 0x50, 0x6f, 0x73, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x41, 0x6e, 0x64, 0x49, 0x6e, 0x73, + 0x74, 0x61, 0x6c, 0x6c, 0x43, 0x6f, 0x6d, 0x70, 0x6f, 0x6e, 0x65, 0x6e, 0x74, 0x55, 0x6e, 0x73, + 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x57, 0x0a, 0x29, 0x65, 0x6e, 0x63, 0x61, + 0x70, 0x5f, 0x74, 0x75, 0x6e, 0x6e, 0x65, 0x6c, 0x5f, 0x73, 0x68, 0x75, 0x74, 0x5f, 0x62, 0x61, + 0x63, 0x6b, 0x75, 0x70, 0x5f, 0x6e, 0x68, 0x67, 0x5f, 0x7a, 0x65, 0x72, 0x6f, 0x5f, 0x74, 0x72, + 0x61, 0x66, 0x66, 0x69, 0x63, 0x18, 0xc5, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x23, 0x65, 0x6e, + 0x63, 0x61, 0x70, 0x54, 0x75, 0x6e, 0x6e, 0x65, 0x6c, 0x53, 0x68, 0x75, 0x74, 0x42, 0x61, 0x63, + 0x6b, 0x75, 0x70, 0x4e, 0x68, 0x67, 0x5a, 0x65, 0x72, 0x6f, 0x54, 0x72, 0x61, 0x66, 0x66, 0x69, + 0x63, 0x12, 0x25, 0x0a, 0x0e, 0x6d, 0x61, 0x78, 0x5f, 0x65, 0x63, 0x6d, 0x70, 0x5f, 0x70, 0x61, + 0x74, 0x68, 0x73, 0x18, 0xc6, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x0c, 0x6d, 0x61, 0x78, 0x45, + 0x63, 0x6d, 0x70, 0x50, 0x61, 0x74, 0x68, 0x73, 0x12, 0x35, 0x0a, 0x16, 0x77, 0x65, 0x63, 0x6d, + 0x70, 0x5f, 0x61, 0x75, 0x74, 0x6f, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, + 0x65, 0x64, 0x18, 0xc7, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x14, 0x77, 0x65, 0x63, 0x6d, 0x70, + 0x41, 0x75, 0x74, 0x6f, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, + 0x4e, 0x0a, 0x23, 0x72, 0x6f, 0x75, 0x74, 0x69, 0x6e, 0x67, 0x5f, 0x70, 0x6f, 0x6c, 0x69, 0x63, + 0x79, 0x5f, 0x63, 0x68, 0x61, 0x69, 0x6e, 0x69, 0x6e, 0x67, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, + 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xc8, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x20, 0x72, + 0x6f, 0x75, 0x74, 0x69, 0x6e, 0x67, 0x50, 0x6f, 0x6c, 0x69, 0x63, 0x79, 0x43, 0x68, 0x61, 0x69, + 0x6e, 0x69, 0x6e, 0x67, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, + 0x35, 0x0a, 0x16, 0x69, 0x73, 0x69, 0x73, 0x5f, 0x6c, 0x6f, 0x6f, 0x70, 0x62, 0x61, 0x63, 0x6b, + 0x5f, 0x72, 0x65, 0x71, 0x75, 0x69, 0x72, 0x65, 0x64, 0x18, 0xc9, 0x01, 0x20, 0x01, 0x28, 0x08, + 0x52, 0x14, 0x69, 0x73, 0x69, 0x73, 0x4c, 0x6f, 0x6f, 0x70, 0x62, 0x61, 0x63, 0x6b, 0x52, 0x65, + 0x71, 0x75, 0x69, 0x72, 0x65, 0x64, 0x12, 0x55, 0x0a, 0x27, 0x77, 0x65, 0x69, 0x67, 0x68, 0x74, + 0x65, 0x64, 0x5f, 0x65, 0x63, 0x6d, 0x70, 0x5f, 0x66, 0x69, 0x78, 0x65, 0x64, 0x5f, 0x70, 0x61, + 0x63, 0x6b, 0x65, 0x74, 0x5f, 0x76, 0x65, 0x72, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74, 0x69, 0x6f, + 0x6e, 0x18, 0xca, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x23, 0x77, 0x65, 0x69, 0x67, 0x68, 0x74, + 0x65, 0x64, 0x45, 0x63, 0x6d, 0x70, 0x46, 0x69, 0x78, 0x65, 0x64, 0x50, 0x61, 0x63, 0x6b, 0x65, + 0x74, 0x56, 0x65, 0x72, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x3a, 0x0a, + 0x19, 0x6f, 0x76, 0x65, 0x72, 0x72, 0x69, 0x64, 0x65, 0x5f, 0x64, 0x65, 0x66, 0x61, 0x75, 0x6c, + 0x74, 0x5f, 0x6e, 0x68, 0x5f, 0x73, 0x63, 0x61, 0x6c, 0x65, 0x18, 0xcb, 0x01, 0x20, 0x01, 0x28, + 0x08, 0x52, 0x16, 0x6f, 0x76, 0x65, 0x72, 0x72, 0x69, 0x64, 0x65, 0x44, 0x65, 0x66, 0x61, 0x75, + 0x6c, 0x74, 0x4e, 0x68, 0x53, 0x63, 0x61, 0x6c, 0x65, 0x12, 0x53, 0x0a, 0x26, 0x62, 0x67, 0x70, 0x5f, 0x65, 0x78, 0x74, 0x65, 0x6e, 0x64, 0x65, 0x64, 0x5f, 0x63, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, - 0x69, 0x74, 0x79, 0x5f, 0x65, 0x6e, 0x61, 0x62, 0x6c, 0x65, 0x18, 0xd0, 0x01, 0x20, 0x01, 0x28, - 0x08, 0x52, 0x22, 0x62, 0x67, 0x70, 0x45, 0x78, 0x70, 0x6c, 0x69, 0x63, 0x69, 0x74, 0x45, 0x78, - 0x74, 0x65, 0x6e, 0x64, 0x65, 0x64, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x45, - 0x6e, 0x61, 0x62, 0x6c, 0x65, 0x12, 0x4d, 0x0a, 0x23, 0x6d, 0x61, 0x74, 0x63, 0x68, 0x5f, 0x74, - 0x61, 0x67, 0x5f, 0x73, 0x65, 0x74, 0x5f, 0x63, 0x6f, 0x6e, 0x64, 0x69, 0x74, 0x69, 0x6f, 0x6e, - 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xd1, 0x01, 0x20, - 0x01, 0x28, 0x08, 0x52, 0x1f, 0x6d, 0x61, 0x74, 0x63, 0x68, 0x54, 0x61, 0x67, 0x53, 0x65, 0x74, - 0x43, 0x6f, 0x6e, 0x64, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, - 0x72, 0x74, 0x65, 0x64, 0x12, 0x4c, 0x0a, 0x23, 0x70, 0x65, 0x65, 0x72, 0x5f, 0x67, 0x72, 0x6f, - 0x75, 0x70, 0x5f, 0x64, 0x65, 0x66, 0x5f, 0x65, 0x62, 0x67, 0x70, 0x5f, 0x76, 0x72, 0x66, 0x5f, - 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xd2, 0x01, 0x20, 0x01, - 0x28, 0x08, 0x52, 0x1e, 0x70, 0x65, 0x65, 0x72, 0x47, 0x72, 0x6f, 0x75, 0x70, 0x44, 0x65, 0x66, - 0x45, 0x62, 0x67, 0x70, 0x56, 0x72, 0x66, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, - 0x65, 0x64, 0x12, 0x5a, 0x0a, 0x2a, 0x72, 0x65, 0x64, 0x69, 0x73, 0x5f, 0x63, 0x6f, 0x6e, 0x6e, - 0x65, 0x63, 0x74, 0x65, 0x64, 0x5f, 0x75, 0x6e, 0x64, 0x65, 0x72, 0x5f, 0x65, 0x62, 0x67, 0x70, - 0x5f, 0x76, 0x72, 0x66, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, - 0x18, 0xd3, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x25, 0x72, 0x65, 0x64, 0x69, 0x73, 0x43, 0x6f, - 0x6e, 0x6e, 0x65, 0x63, 0x74, 0x65, 0x64, 0x55, 0x6e, 0x64, 0x65, 0x72, 0x45, 0x62, 0x67, 0x70, - 0x56, 0x72, 0x66, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x57, - 0x0a, 0x2a, 0x62, 0x67, 0x70, 0x5f, 0x61, 0x66, 0x69, 0x5f, 0x73, 0x61, 0x66, 0x69, 0x5f, 0x69, - 0x6e, 0x5f, 0x64, 0x65, 0x66, 0x61, 0x75, 0x6c, 0x74, 0x5f, 0x6e, 0x69, 0x5f, 0x62, 0x65, 0x66, - 0x6f, 0x72, 0x65, 0x5f, 0x6f, 0x74, 0x68, 0x65, 0x72, 0x5f, 0x6e, 0x69, 0x18, 0xd4, 0x01, 0x20, - 0x01, 0x28, 0x08, 0x52, 0x22, 0x62, 0x67, 0x70, 0x41, 0x66, 0x69, 0x53, 0x61, 0x66, 0x69, 0x49, - 0x6e, 0x44, 0x65, 0x66, 0x61, 0x75, 0x6c, 0x74, 0x4e, 0x69, 0x42, 0x65, 0x66, 0x6f, 0x72, 0x65, - 0x4f, 0x74, 0x68, 0x65, 0x72, 0x4e, 0x69, 0x12, 0x57, 0x0a, 0x28, 0x64, 0x65, 0x66, 0x61, 0x75, - 0x6c, 0x74, 0x5f, 0x69, 0x6d, 0x70, 0x6f, 0x72, 0x74, 0x5f, 0x65, 0x78, 0x70, 0x6f, 0x72, 0x74, - 0x5f, 0x70, 0x6f, 0x6c, 0x69, 0x63, 0x79, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, - 0x74, 0x65, 0x64, 0x18, 0xd5, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x24, 0x64, 0x65, 0x66, 0x61, - 0x75, 0x6c, 0x74, 0x49, 0x6d, 0x70, 0x6f, 0x72, 0x74, 0x45, 0x78, 0x70, 0x6f, 0x72, 0x74, 0x50, - 0x6f, 0x6c, 0x69, 0x63, 0x79, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, - 0x12, 0x63, 0x0a, 0x2e, 0x69, 0x70, 0x76, 0x36, 0x5f, 0x72, 0x6f, 0x75, 0x74, 0x65, 0x72, 0x5f, - 0x61, 0x64, 0x76, 0x65, 0x72, 0x74, 0x69, 0x73, 0x65, 0x6d, 0x65, 0x6e, 0x74, 0x5f, 0x69, 0x6e, - 0x74, 0x65, 0x72, 0x76, 0x61, 0x6c, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, - 0x65, 0x64, 0x18, 0xd6, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x2a, 0x69, 0x70, 0x76, 0x36, 0x52, - 0x6f, 0x75, 0x74, 0x65, 0x72, 0x41, 0x64, 0x76, 0x65, 0x72, 0x74, 0x69, 0x73, 0x65, 0x6d, 0x65, - 0x6e, 0x74, 0x49, 0x6e, 0x74, 0x65, 0x72, 0x76, 0x61, 0x6c, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, - 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x4e, 0x0a, 0x24, 0x64, 0x65, 0x63, 0x61, 0x70, 0x5f, 0x6e, - 0x68, 0x5f, 0x77, 0x69, 0x74, 0x68, 0x5f, 0x6e, 0x65, 0x78, 0x74, 0x68, 0x6f, 0x70, 0x5f, 0x6e, - 0x69, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xd7, 0x01, - 0x20, 0x01, 0x28, 0x08, 0x52, 0x1f, 0x64, 0x65, 0x63, 0x61, 0x70, 0x4e, 0x68, 0x57, 0x69, 0x74, - 0x68, 0x4e, 0x65, 0x78, 0x74, 0x68, 0x6f, 0x70, 0x4e, 0x69, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, - 0x6f, 0x72, 0x74, 0x65, 0x64, 0x4a, 0x04, 0x08, 0x54, 0x10, 0x55, 0x4a, 0x04, 0x08, 0x09, 0x10, - 0x0a, 0x4a, 0x04, 0x08, 0x1c, 0x10, 0x1d, 0x4a, 0x04, 0x08, 0x14, 0x10, 0x15, 0x4a, 0x04, 0x08, - 0x5a, 0x10, 0x5b, 0x4a, 0x04, 0x08, 0x61, 0x10, 0x62, 0x4a, 0x04, 0x08, 0x37, 0x10, 0x38, 0x4a, - 0x04, 0x08, 0x59, 0x10, 0x5a, 0x4a, 0x04, 0x08, 0x13, 0x10, 0x14, 0x4a, 0x04, 0x08, 0x24, 0x10, - 0x25, 0x4a, 0x04, 0x08, 0x23, 0x10, 0x24, 0x4a, 0x04, 0x08, 0x28, 0x10, 0x29, 0x4a, 0x06, 0x08, - 0xad, 0x01, 0x10, 0xae, 0x01, 0x1a, 0xa0, 0x01, 0x0a, 0x12, 0x50, 0x6c, 0x61, 0x74, 0x66, 0x6f, - 0x72, 0x6d, 0x45, 0x78, 0x63, 0x65, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x12, 0x41, 0x0a, 0x08, - 0x70, 0x6c, 0x61, 0x74, 0x66, 0x6f, 0x72, 0x6d, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x25, - 0x2e, 0x6f, 0x70, 0x65, 0x6e, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x2e, 0x74, 0x65, 0x73, 0x74, - 0x69, 0x6e, 0x67, 0x2e, 0x4d, 0x65, 0x74, 0x61, 0x64, 0x61, 0x74, 0x61, 0x2e, 0x50, 0x6c, 0x61, - 0x74, 0x66, 0x6f, 0x72, 0x6d, 0x52, 0x08, 0x70, 0x6c, 0x61, 0x74, 0x66, 0x6f, 0x72, 0x6d, 0x12, - 0x47, 0x0a, 0x0a, 0x64, 0x65, 0x76, 0x69, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x18, 0x02, 0x20, - 0x01, 0x28, 0x0b, 0x32, 0x27, 0x2e, 0x6f, 0x70, 0x65, 0x6e, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, - 0x2e, 0x74, 0x65, 0x73, 0x74, 0x69, 0x6e, 0x67, 0x2e, 0x4d, 0x65, 0x74, 0x61, 0x64, 0x61, 0x74, - 0x61, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x52, 0x0a, 0x64, 0x65, - 0x76, 0x69, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x22, 0xfa, 0x01, 0x0a, 0x07, 0x54, 0x65, 0x73, - 0x74, 0x62, 0x65, 0x64, 0x12, 0x17, 0x0a, 0x13, 0x54, 0x45, 0x53, 0x54, 0x42, 0x45, 0x44, 0x5f, - 0x55, 0x4e, 0x53, 0x50, 0x45, 0x43, 0x49, 0x46, 0x49, 0x45, 0x44, 0x10, 0x00, 0x12, 0x0f, 0x0a, - 0x0b, 0x54, 0x45, 0x53, 0x54, 0x42, 0x45, 0x44, 0x5f, 0x44, 0x55, 0x54, 0x10, 0x01, 0x12, 0x1a, - 0x0a, 0x16, 0x54, 0x45, 0x53, 0x54, 0x42, 0x45, 0x44, 0x5f, 0x44, 0x55, 0x54, 0x5f, 0x44, 0x55, - 0x54, 0x5f, 0x34, 0x4c, 0x49, 0x4e, 0x4b, 0x53, 0x10, 0x02, 0x12, 0x1a, 0x0a, 0x16, 0x54, 0x45, - 0x53, 0x54, 0x42, 0x45, 0x44, 0x5f, 0x44, 0x55, 0x54, 0x5f, 0x41, 0x54, 0x45, 0x5f, 0x32, 0x4c, - 0x49, 0x4e, 0x4b, 0x53, 0x10, 0x03, 0x12, 0x1a, 0x0a, 0x16, 0x54, 0x45, 0x53, 0x54, 0x42, 0x45, - 0x44, 0x5f, 0x44, 0x55, 0x54, 0x5f, 0x41, 0x54, 0x45, 0x5f, 0x34, 0x4c, 0x49, 0x4e, 0x4b, 0x53, - 0x10, 0x04, 0x12, 0x1e, 0x0a, 0x1a, 0x54, 0x45, 0x53, 0x54, 0x42, 0x45, 0x44, 0x5f, 0x44, 0x55, - 0x54, 0x5f, 0x41, 0x54, 0x45, 0x5f, 0x39, 0x4c, 0x49, 0x4e, 0x4b, 0x53, 0x5f, 0x4c, 0x41, 0x47, - 0x10, 0x05, 0x12, 0x1e, 0x0a, 0x1a, 0x54, 0x45, 0x53, 0x54, 0x42, 0x45, 0x44, 0x5f, 0x44, 0x55, - 0x54, 0x5f, 0x44, 0x55, 0x54, 0x5f, 0x41, 0x54, 0x45, 0x5f, 0x32, 0x4c, 0x49, 0x4e, 0x4b, 0x53, - 0x10, 0x06, 0x12, 0x1a, 0x0a, 0x16, 0x54, 0x45, 0x53, 0x54, 0x42, 0x45, 0x44, 0x5f, 0x44, 0x55, - 0x54, 0x5f, 0x41, 0x54, 0x45, 0x5f, 0x38, 0x4c, 0x49, 0x4e, 0x4b, 0x53, 0x10, 0x07, 0x12, 0x15, - 0x0a, 0x11, 0x54, 0x45, 0x53, 0x54, 0x42, 0x45, 0x44, 0x5f, 0x44, 0x55, 0x54, 0x5f, 0x34, 0x30, - 0x30, 0x5a, 0x52, 0x10, 0x08, 0x22, 0x6d, 0x0a, 0x04, 0x54, 0x61, 0x67, 0x73, 0x12, 0x14, 0x0a, - 0x10, 0x54, 0x41, 0x47, 0x53, 0x5f, 0x55, 0x4e, 0x53, 0x50, 0x45, 0x43, 0x49, 0x46, 0x49, 0x45, - 0x44, 0x10, 0x00, 0x12, 0x14, 0x0a, 0x10, 0x54, 0x41, 0x47, 0x53, 0x5f, 0x41, 0x47, 0x47, 0x52, - 0x45, 0x47, 0x41, 0x54, 0x49, 0x4f, 0x4e, 0x10, 0x01, 0x12, 0x18, 0x0a, 0x14, 0x54, 0x41, 0x47, - 0x53, 0x5f, 0x44, 0x41, 0x54, 0x41, 0x43, 0x45, 0x4e, 0x54, 0x45, 0x52, 0x5f, 0x45, 0x44, 0x47, - 0x45, 0x10, 0x02, 0x12, 0x0d, 0x0a, 0x09, 0x54, 0x41, 0x47, 0x53, 0x5f, 0x45, 0x44, 0x47, 0x45, - 0x10, 0x03, 0x12, 0x10, 0x0a, 0x0c, 0x54, 0x41, 0x47, 0x53, 0x5f, 0x54, 0x52, 0x41, 0x4e, 0x53, - 0x49, 0x54, 0x10, 0x04, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33, + 0x69, 0x74, 0x79, 0x5f, 0x73, 0x65, 0x74, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, + 0x74, 0x65, 0x64, 0x18, 0xcc, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x22, 0x62, 0x67, 0x70, 0x45, + 0x78, 0x74, 0x65, 0x6e, 0x64, 0x65, 0x64, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, + 0x53, 0x65, 0x74, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x59, + 0x0a, 0x2a, 0x62, 0x67, 0x70, 0x5f, 0x73, 0x65, 0x74, 0x5f, 0x65, 0x78, 0x74, 0x5f, 0x63, 0x6f, + 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x5f, 0x73, 0x65, 0x74, 0x5f, 0x72, 0x65, 0x66, 0x73, + 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xcd, 0x01, 0x20, + 0x01, 0x28, 0x08, 0x52, 0x24, 0x62, 0x67, 0x70, 0x53, 0x65, 0x74, 0x45, 0x78, 0x74, 0x43, 0x6f, + 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x53, 0x65, 0x74, 0x52, 0x65, 0x66, 0x73, 0x55, 0x6e, + 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x51, 0x0a, 0x25, 0x62, 0x67, 0x70, + 0x5f, 0x64, 0x65, 0x6c, 0x65, 0x74, 0x65, 0x5f, 0x6c, 0x69, 0x6e, 0x6b, 0x5f, 0x62, 0x61, 0x6e, + 0x64, 0x77, 0x69, 0x64, 0x74, 0x68, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, + 0x65, 0x64, 0x18, 0xce, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x21, 0x62, 0x67, 0x70, 0x44, 0x65, + 0x6c, 0x65, 0x74, 0x65, 0x4c, 0x69, 0x6e, 0x6b, 0x42, 0x61, 0x6e, 0x64, 0x77, 0x69, 0x64, 0x74, + 0x68, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x4f, 0x0a, 0x24, + 0x71, 0x6f, 0x73, 0x5f, 0x69, 0x6e, 0x71, 0x75, 0x65, 0x75, 0x65, 0x5f, 0x64, 0x72, 0x6f, 0x70, + 0x5f, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x65, 0x72, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, + 0x72, 0x74, 0x65, 0x64, 0x18, 0xcf, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x20, 0x71, 0x6f, 0x73, + 0x49, 0x6e, 0x71, 0x75, 0x65, 0x75, 0x65, 0x44, 0x72, 0x6f, 0x70, 0x43, 0x6f, 0x75, 0x6e, 0x74, + 0x65, 0x72, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x53, 0x0a, + 0x26, 0x62, 0x67, 0x70, 0x5f, 0x65, 0x78, 0x70, 0x6c, 0x69, 0x63, 0x69, 0x74, 0x5f, 0x65, 0x78, + 0x74, 0x65, 0x6e, 0x64, 0x65, 0x64, 0x5f, 0x63, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, + 0x5f, 0x65, 0x6e, 0x61, 0x62, 0x6c, 0x65, 0x18, 0xd0, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x22, + 0x62, 0x67, 0x70, 0x45, 0x78, 0x70, 0x6c, 0x69, 0x63, 0x69, 0x74, 0x45, 0x78, 0x74, 0x65, 0x6e, + 0x64, 0x65, 0x64, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x45, 0x6e, 0x61, 0x62, + 0x6c, 0x65, 0x12, 0x4d, 0x0a, 0x23, 0x6d, 0x61, 0x74, 0x63, 0x68, 0x5f, 0x74, 0x61, 0x67, 0x5f, + 0x73, 0x65, 0x74, 0x5f, 0x63, 0x6f, 0x6e, 0x64, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x5f, 0x75, 0x6e, + 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xd1, 0x01, 0x20, 0x01, 0x28, 0x08, + 0x52, 0x1f, 0x6d, 0x61, 0x74, 0x63, 0x68, 0x54, 0x61, 0x67, 0x53, 0x65, 0x74, 0x43, 0x6f, 0x6e, + 0x64, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, + 0x64, 0x12, 0x4c, 0x0a, 0x23, 0x70, 0x65, 0x65, 0x72, 0x5f, 0x67, 0x72, 0x6f, 0x75, 0x70, 0x5f, + 0x64, 0x65, 0x66, 0x5f, 0x65, 0x62, 0x67, 0x70, 0x5f, 0x76, 0x72, 0x66, 0x5f, 0x75, 0x6e, 0x73, + 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xd2, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, + 0x1e, 0x70, 0x65, 0x65, 0x72, 0x47, 0x72, 0x6f, 0x75, 0x70, 0x44, 0x65, 0x66, 0x45, 0x62, 0x67, + 0x70, 0x56, 0x72, 0x66, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, + 0x5a, 0x0a, 0x2a, 0x72, 0x65, 0x64, 0x69, 0x73, 0x5f, 0x63, 0x6f, 0x6e, 0x6e, 0x65, 0x63, 0x74, + 0x65, 0x64, 0x5f, 0x75, 0x6e, 0x64, 0x65, 0x72, 0x5f, 0x65, 0x62, 0x67, 0x70, 0x5f, 0x76, 0x72, + 0x66, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xd3, 0x01, + 0x20, 0x01, 0x28, 0x08, 0x52, 0x25, 0x72, 0x65, 0x64, 0x69, 0x73, 0x43, 0x6f, 0x6e, 0x6e, 0x65, + 0x63, 0x74, 0x65, 0x64, 0x55, 0x6e, 0x64, 0x65, 0x72, 0x45, 0x62, 0x67, 0x70, 0x56, 0x72, 0x66, + 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x57, 0x0a, 0x2a, 0x62, + 0x67, 0x70, 0x5f, 0x61, 0x66, 0x69, 0x5f, 0x73, 0x61, 0x66, 0x69, 0x5f, 0x69, 0x6e, 0x5f, 0x64, + 0x65, 0x66, 0x61, 0x75, 0x6c, 0x74, 0x5f, 0x6e, 0x69, 0x5f, 0x62, 0x65, 0x66, 0x6f, 0x72, 0x65, + 0x5f, 0x6f, 0x74, 0x68, 0x65, 0x72, 0x5f, 0x6e, 0x69, 0x18, 0xd4, 0x01, 0x20, 0x01, 0x28, 0x08, + 0x52, 0x22, 0x62, 0x67, 0x70, 0x41, 0x66, 0x69, 0x53, 0x61, 0x66, 0x69, 0x49, 0x6e, 0x44, 0x65, + 0x66, 0x61, 0x75, 0x6c, 0x74, 0x4e, 0x69, 0x42, 0x65, 0x66, 0x6f, 0x72, 0x65, 0x4f, 0x74, 0x68, + 0x65, 0x72, 0x4e, 0x69, 0x12, 0x57, 0x0a, 0x28, 0x64, 0x65, 0x66, 0x61, 0x75, 0x6c, 0x74, 0x5f, + 0x69, 0x6d, 0x70, 0x6f, 0x72, 0x74, 0x5f, 0x65, 0x78, 0x70, 0x6f, 0x72, 0x74, 0x5f, 0x70, 0x6f, + 0x6c, 0x69, 0x63, 0x79, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, + 0x18, 0xd5, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x24, 0x64, 0x65, 0x66, 0x61, 0x75, 0x6c, 0x74, + 0x49, 0x6d, 0x70, 0x6f, 0x72, 0x74, 0x45, 0x78, 0x70, 0x6f, 0x72, 0x74, 0x50, 0x6f, 0x6c, 0x69, + 0x63, 0x79, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x63, 0x0a, + 0x2e, 0x69, 0x70, 0x76, 0x36, 0x5f, 0x72, 0x6f, 0x75, 0x74, 0x65, 0x72, 0x5f, 0x61, 0x64, 0x76, + 0x65, 0x72, 0x74, 0x69, 0x73, 0x65, 0x6d, 0x65, 0x6e, 0x74, 0x5f, 0x69, 0x6e, 0x74, 0x65, 0x72, + 0x76, 0x61, 0x6c, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, + 0xd6, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x2a, 0x69, 0x70, 0x76, 0x36, 0x52, 0x6f, 0x75, 0x74, + 0x65, 0x72, 0x41, 0x64, 0x76, 0x65, 0x72, 0x74, 0x69, 0x73, 0x65, 0x6d, 0x65, 0x6e, 0x74, 0x49, + 0x6e, 0x74, 0x65, 0x72, 0x76, 0x61, 0x6c, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, + 0x65, 0x64, 0x12, 0x4e, 0x0a, 0x24, 0x64, 0x65, 0x63, 0x61, 0x70, 0x5f, 0x6e, 0x68, 0x5f, 0x77, + 0x69, 0x74, 0x68, 0x5f, 0x6e, 0x65, 0x78, 0x74, 0x68, 0x6f, 0x70, 0x5f, 0x6e, 0x69, 0x5f, 0x75, + 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xd7, 0x01, 0x20, 0x01, 0x28, + 0x08, 0x52, 0x1f, 0x64, 0x65, 0x63, 0x61, 0x70, 0x4e, 0x68, 0x57, 0x69, 0x74, 0x68, 0x4e, 0x65, + 0x78, 0x74, 0x68, 0x6f, 0x70, 0x4e, 0x69, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, + 0x65, 0x64, 0x12, 0x48, 0x0a, 0x20, 0x63, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x5f, + 0x69, 0x6e, 0x76, 0x65, 0x72, 0x74, 0x5f, 0x61, 0x6e, 0x79, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, + 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xd8, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1d, 0x63, + 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x49, 0x6e, 0x76, 0x65, 0x72, 0x74, 0x41, 0x6e, + 0x79, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x55, 0x0a, 0x27, + 0x73, 0x66, 0x6c, 0x6f, 0x77, 0x5f, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x5f, 0x61, 0x64, 0x64, + 0x72, 0x65, 0x73, 0x73, 0x5f, 0x75, 0x70, 0x64, 0x61, 0x74, 0x65, 0x5f, 0x75, 0x6e, 0x73, 0x75, + 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xd9, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x23, + 0x73, 0x66, 0x6c, 0x6f, 0x77, 0x53, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x41, 0x64, 0x64, 0x72, 0x65, + 0x73, 0x73, 0x55, 0x70, 0x64, 0x61, 0x74, 0x65, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, + 0x74, 0x65, 0x64, 0x12, 0x2e, 0x0a, 0x13, 0x6c, 0x69, 0x6e, 0x6b, 0x5f, 0x6c, 0x6f, 0x63, 0x61, + 0x6c, 0x5f, 0x6d, 0x61, 0x73, 0x6b, 0x5f, 0x6c, 0x65, 0x6e, 0x18, 0xda, 0x01, 0x20, 0x01, 0x28, + 0x08, 0x52, 0x10, 0x6c, 0x69, 0x6e, 0x6b, 0x4c, 0x6f, 0x63, 0x61, 0x6c, 0x4d, 0x61, 0x73, 0x6b, + 0x4c, 0x65, 0x6e, 0x12, 0x62, 0x0a, 0x2e, 0x75, 0x73, 0x65, 0x5f, 0x70, 0x61, 0x72, 0x65, 0x6e, + 0x74, 0x5f, 0x63, 0x6f, 0x6d, 0x70, 0x6f, 0x6e, 0x65, 0x6e, 0x74, 0x5f, 0x66, 0x6f, 0x72, 0x5f, + 0x74, 0x65, 0x6d, 0x70, 0x65, 0x72, 0x61, 0x74, 0x75, 0x72, 0x65, 0x5f, 0x74, 0x65, 0x6c, 0x65, + 0x6d, 0x65, 0x74, 0x72, 0x79, 0x18, 0xdb, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x29, 0x75, 0x73, + 0x65, 0x50, 0x61, 0x72, 0x65, 0x6e, 0x74, 0x43, 0x6f, 0x6d, 0x70, 0x6f, 0x6e, 0x65, 0x6e, 0x74, + 0x46, 0x6f, 0x72, 0x54, 0x65, 0x6d, 0x70, 0x65, 0x72, 0x61, 0x74, 0x75, 0x72, 0x65, 0x54, 0x65, + 0x6c, 0x65, 0x6d, 0x65, 0x74, 0x72, 0x79, 0x12, 0x44, 0x0a, 0x1e, 0x63, 0x6f, 0x6d, 0x70, 0x6f, + 0x6e, 0x65, 0x6e, 0x74, 0x5f, 0x6d, 0x66, 0x67, 0x5f, 0x64, 0x61, 0x74, 0x65, 0x5f, 0x75, 0x6e, + 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xdc, 0x01, 0x20, 0x01, 0x28, 0x08, + 0x52, 0x1b, 0x63, 0x6f, 0x6d, 0x70, 0x6f, 0x6e, 0x65, 0x6e, 0x74, 0x4d, 0x66, 0x67, 0x44, 0x61, + 0x74, 0x65, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x40, 0x0a, + 0x1c, 0x6f, 0x74, 0x6e, 0x5f, 0x63, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x5f, 0x74, 0x72, 0x69, + 0x62, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xdd, 0x01, + 0x20, 0x01, 0x28, 0x08, 0x52, 0x19, 0x6f, 0x74, 0x6e, 0x43, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, + 0x54, 0x72, 0x69, 0x62, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, + 0x5b, 0x0a, 0x2a, 0x65, 0x74, 0x68, 0x5f, 0x63, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x5f, 0x69, + 0x6e, 0x67, 0x72, 0x65, 0x73, 0x73, 0x5f, 0x70, 0x61, 0x72, 0x61, 0x6d, 0x65, 0x74, 0x65, 0x72, + 0x73, 0x5f, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x18, 0xde, 0x01, + 0x20, 0x01, 0x28, 0x08, 0x52, 0x26, 0x65, 0x74, 0x68, 0x43, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, + 0x49, 0x6e, 0x67, 0x72, 0x65, 0x73, 0x73, 0x50, 0x61, 0x72, 0x61, 0x6d, 0x65, 0x74, 0x65, 0x72, + 0x73, 0x55, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72, 0x74, 0x65, 0x64, 0x12, 0x53, 0x0a, 0x26, + 0x65, 0x74, 0x68, 0x5f, 0x63, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x5f, 0x61, 0x73, 0x73, 0x69, + 0x67, 0x6e, 0x6d, 0x65, 0x6e, 0x74, 0x5f, 0x63, 0x69, 0x73, 0x63, 0x6f, 0x5f, 0x6e, 0x75, 0x6d, + 0x62, 0x65, 0x72, 0x69, 0x6e, 0x67, 0x18, 0xdf, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x22, 0x65, + 0x74, 0x68, 0x43, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x41, 0x73, 0x73, 0x69, 0x67, 0x6e, 0x6d, + 0x65, 0x6e, 0x74, 0x43, 0x69, 0x73, 0x63, 0x6f, 0x4e, 0x75, 0x6d, 0x62, 0x65, 0x72, 0x69, 0x6e, + 0x67, 0x12, 0x4a, 0x0a, 0x21, 0x69, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x5f, 0x63, + 0x6f, 0x75, 0x6e, 0x74, 0x65, 0x72, 0x73, 0x5f, 0x75, 0x70, 0x64, 0x61, 0x74, 0x65, 0x5f, 0x64, + 0x65, 0x6c, 0x61, 0x79, 0x65, 0x64, 0x18, 0xe0, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x1e, 0x69, + 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x43, 0x6f, 0x75, 0x6e, 0x74, 0x65, 0x72, 0x73, + 0x55, 0x70, 0x64, 0x61, 0x74, 0x65, 0x44, 0x65, 0x6c, 0x61, 0x79, 0x65, 0x64, 0x4a, 0x04, 0x08, + 0x54, 0x10, 0x55, 0x4a, 0x04, 0x08, 0x09, 0x10, 0x0a, 0x4a, 0x04, 0x08, 0x1c, 0x10, 0x1d, 0x4a, + 0x04, 0x08, 0x14, 0x10, 0x15, 0x4a, 0x04, 0x08, 0x5a, 0x10, 0x5b, 0x4a, 0x04, 0x08, 0x61, 0x10, + 0x62, 0x4a, 0x04, 0x08, 0x37, 0x10, 0x38, 0x4a, 0x04, 0x08, 0x59, 0x10, 0x5a, 0x4a, 0x04, 0x08, + 0x13, 0x10, 0x14, 0x4a, 0x04, 0x08, 0x24, 0x10, 0x25, 0x4a, 0x04, 0x08, 0x23, 0x10, 0x24, 0x4a, + 0x04, 0x08, 0x28, 0x10, 0x29, 0x4a, 0x06, 0x08, 0xad, 0x01, 0x10, 0xae, 0x01, 0x1a, 0xa0, 0x01, + 0x0a, 0x12, 0x50, 0x6c, 0x61, 0x74, 0x66, 0x6f, 0x72, 0x6d, 0x45, 0x78, 0x63, 0x65, 0x70, 0x74, + 0x69, 0x6f, 0x6e, 0x73, 0x12, 0x41, 0x0a, 0x08, 0x70, 0x6c, 0x61, 0x74, 0x66, 0x6f, 0x72, 0x6d, + 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x25, 0x2e, 0x6f, 0x70, 0x65, 0x6e, 0x63, 0x6f, 0x6e, + 0x66, 0x69, 0x67, 0x2e, 0x74, 0x65, 0x73, 0x74, 0x69, 0x6e, 0x67, 0x2e, 0x4d, 0x65, 0x74, 0x61, + 0x64, 0x61, 0x74, 0x61, 0x2e, 0x50, 0x6c, 0x61, 0x74, 0x66, 0x6f, 0x72, 0x6d, 0x52, 0x08, 0x70, + 0x6c, 0x61, 0x74, 0x66, 0x6f, 0x72, 0x6d, 0x12, 0x47, 0x0a, 0x0a, 0x64, 0x65, 0x76, 0x69, 0x61, + 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x27, 0x2e, 0x6f, 0x70, + 0x65, 0x6e, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x2e, 0x74, 0x65, 0x73, 0x74, 0x69, 0x6e, 0x67, + 0x2e, 0x4d, 0x65, 0x74, 0x61, 0x64, 0x61, 0x74, 0x61, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x61, 0x74, + 0x69, 0x6f, 0x6e, 0x73, 0x52, 0x0a, 0x64, 0x65, 0x76, 0x69, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x73, + 0x22, 0xfa, 0x01, 0x0a, 0x07, 0x54, 0x65, 0x73, 0x74, 0x62, 0x65, 0x64, 0x12, 0x17, 0x0a, 0x13, + 0x54, 0x45, 0x53, 0x54, 0x42, 0x45, 0x44, 0x5f, 0x55, 0x4e, 0x53, 0x50, 0x45, 0x43, 0x49, 0x46, + 0x49, 0x45, 0x44, 0x10, 0x00, 0x12, 0x0f, 0x0a, 0x0b, 0x54, 0x45, 0x53, 0x54, 0x42, 0x45, 0x44, + 0x5f, 0x44, 0x55, 0x54, 0x10, 0x01, 0x12, 0x1a, 0x0a, 0x16, 0x54, 0x45, 0x53, 0x54, 0x42, 0x45, + 0x44, 0x5f, 0x44, 0x55, 0x54, 0x5f, 0x44, 0x55, 0x54, 0x5f, 0x34, 0x4c, 0x49, 0x4e, 0x4b, 0x53, + 0x10, 0x02, 0x12, 0x1a, 0x0a, 0x16, 0x54, 0x45, 0x53, 0x54, 0x42, 0x45, 0x44, 0x5f, 0x44, 0x55, + 0x54, 0x5f, 0x41, 0x54, 0x45, 0x5f, 0x32, 0x4c, 0x49, 0x4e, 0x4b, 0x53, 0x10, 0x03, 0x12, 0x1a, + 0x0a, 0x16, 0x54, 0x45, 0x53, 0x54, 0x42, 0x45, 0x44, 0x5f, 0x44, 0x55, 0x54, 0x5f, 0x41, 0x54, + 0x45, 0x5f, 0x34, 0x4c, 0x49, 0x4e, 0x4b, 0x53, 0x10, 0x04, 0x12, 0x1e, 0x0a, 0x1a, 0x54, 0x45, + 0x53, 0x54, 0x42, 0x45, 0x44, 0x5f, 0x44, 0x55, 0x54, 0x5f, 0x41, 0x54, 0x45, 0x5f, 0x39, 0x4c, + 0x49, 0x4e, 0x4b, 0x53, 0x5f, 0x4c, 0x41, 0x47, 0x10, 0x05, 0x12, 0x1e, 0x0a, 0x1a, 0x54, 0x45, + 0x53, 0x54, 0x42, 0x45, 0x44, 0x5f, 0x44, 0x55, 0x54, 0x5f, 0x44, 0x55, 0x54, 0x5f, 0x41, 0x54, + 0x45, 0x5f, 0x32, 0x4c, 0x49, 0x4e, 0x4b, 0x53, 0x10, 0x06, 0x12, 0x1a, 0x0a, 0x16, 0x54, 0x45, + 0x53, 0x54, 0x42, 0x45, 0x44, 0x5f, 0x44, 0x55, 0x54, 0x5f, 0x41, 0x54, 0x45, 0x5f, 0x38, 0x4c, + 0x49, 0x4e, 0x4b, 0x53, 0x10, 0x07, 0x12, 0x15, 0x0a, 0x11, 0x54, 0x45, 0x53, 0x54, 0x42, 0x45, + 0x44, 0x5f, 0x44, 0x55, 0x54, 0x5f, 0x34, 0x30, 0x30, 0x5a, 0x52, 0x10, 0x08, 0x22, 0x6d, 0x0a, + 0x04, 0x54, 0x61, 0x67, 0x73, 0x12, 0x14, 0x0a, 0x10, 0x54, 0x41, 0x47, 0x53, 0x5f, 0x55, 0x4e, + 0x53, 0x50, 0x45, 0x43, 0x49, 0x46, 0x49, 0x45, 0x44, 0x10, 0x00, 0x12, 0x14, 0x0a, 0x10, 0x54, + 0x41, 0x47, 0x53, 0x5f, 0x41, 0x47, 0x47, 0x52, 0x45, 0x47, 0x41, 0x54, 0x49, 0x4f, 0x4e, 0x10, + 0x01, 0x12, 0x18, 0x0a, 0x14, 0x54, 0x41, 0x47, 0x53, 0x5f, 0x44, 0x41, 0x54, 0x41, 0x43, 0x45, + 0x4e, 0x54, 0x45, 0x52, 0x5f, 0x45, 0x44, 0x47, 0x45, 0x10, 0x02, 0x12, 0x0d, 0x0a, 0x09, 0x54, + 0x41, 0x47, 0x53, 0x5f, 0x45, 0x44, 0x47, 0x45, 0x10, 0x03, 0x12, 0x10, 0x0a, 0x0c, 0x54, 0x41, + 0x47, 0x53, 0x5f, 0x54, 0x52, 0x41, 0x4e, 0x53, 0x49, 0x54, 0x10, 0x04, 0x62, 0x06, 0x70, 0x72, + 0x6f, 0x74, 0x6f, 0x33, } var ( @@ -3338,7 +3452,7 @@ func file_metadata_proto_rawDescGZIP() []byte { var file_metadata_proto_enumTypes = make([]protoimpl.EnumInfo, 2) var file_metadata_proto_msgTypes = make([]protoimpl.MessageInfo, 4) -var file_metadata_proto_goTypes = []interface{}{ +var file_metadata_proto_goTypes = []any{ (Metadata_Testbed)(0), // 0: openconfig.testing.Metadata.Testbed (Metadata_Tags)(0), // 1: openconfig.testing.Metadata.Tags (*Metadata)(nil), // 2: openconfig.testing.Metadata @@ -3367,7 +3481,7 @@ func file_metadata_proto_init() { return } if !protoimpl.UnsafeEnabled { - file_metadata_proto_msgTypes[0].Exporter = func(v interface{}, i int) interface{} { + file_metadata_proto_msgTypes[0].Exporter = func(v any, i int) any { switch v := v.(*Metadata); i { case 0: return &v.state @@ -3379,7 +3493,7 @@ func file_metadata_proto_init() { return nil } } - file_metadata_proto_msgTypes[1].Exporter = func(v interface{}, i int) interface{} { + file_metadata_proto_msgTypes[1].Exporter = func(v any, i int) any { switch v := v.(*Metadata_Platform); i { case 0: return &v.state @@ -3391,7 +3505,7 @@ func file_metadata_proto_init() { return nil } } - file_metadata_proto_msgTypes[2].Exporter = func(v interface{}, i int) interface{} { + file_metadata_proto_msgTypes[2].Exporter = func(v any, i int) any { switch v := v.(*Metadata_Deviations); i { case 0: return &v.state @@ -3403,7 +3517,7 @@ func file_metadata_proto_init() { return nil } } - file_metadata_proto_msgTypes[3].Exporter = func(v interface{}, i int) interface{} { + file_metadata_proto_msgTypes[3].Exporter = func(v any, i int) any { switch v := v.(*Metadata_PlatformExceptions); i { case 0: return &v.state diff --git a/proto/ocpaths.proto b/proto/ocpaths.proto index 46f3bd41717..ea7d21e6d57 100644 --- a/proto/ocpaths.proto +++ b/proto/ocpaths.proto @@ -58,6 +58,10 @@ message OCPath { // A set of opaque tags that are used for this path. These tags can be used // to group paths according to use-case specific criteria. repeated string tags = 4; + + // GNMIRpc describes expected (or supported) behavior for a particular + // Openconfig path. + GNMIRpc gnmi_rpc = 5; } // OCPathConstraint enumerates platform_types that are required to be supported @@ -76,3 +80,39 @@ message OCPathConstraint { string platform_type = 1; } } + +// GNMIRpc describes expected (or supported) behavior for a particular +// Openconfig path. +message GNMIRpc { + bool get = 1; + bool set = 2; + bool subscribe = 3; + + // SubscribeMode, describes how updates are triggered for the request. + enum SubscribeMode { + UNSPECIFIED_SUBSCRIBE_MODE = 0; + NO_READ_SUPPORT = 1; // No requirement / support for path. + STREAM = 2; // Values streamed by the target (Sec. 3.5.1.5.2). + ONCE = 3; // Values sent once-off by the target (Sec. 3.5.1.5.1). + POLL = 4; // Values sent in response to a poll request (Sec. 3.5.1.5.3). + } + repeated SubscribeMode sub_mode = 4; + + // StreamMode is the mode of a streamed subscription, specifying how the + // target must return values for that subscription. + // Reference: gNMI Specification Section 3.5.1.3 + enum StreamMode { + UNSPECIFIED_STREAM_MODE = 0; + NO_STREAMING_SUPPORT = 1; // No requirement / support for streaming path. + TARGET_DEFINED = 2; // The target selects for each element. + ON_CHANGE = 3; // The target sends an update on element value change. + SAMPLE = 4; // The target samples values according to the interval. + } + repeated StreamMode stream_mode = 5; + + // If listed as part of a requirement, sample_interval_nanoseconds is the + // maximum allowable interval between updates. + // If listed as part of the description of level of support, it should be the + // smallest, recommended value. + uint64 sample_interval_nanoseconds = 6; +} diff --git a/testregistry.textproto b/testregistry.textproto index 9d6599b39fd..9d0f6823aa4 100644 --- a/testregistry.textproto +++ b/testregistry.textproto @@ -72,6 +72,21 @@ test: { readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/acl/otg_tests/acl_update_test/README.md" exec: " " } +test: { + id: "attestz-1" + description: "Validate attestz for initial install" + readme: "https://github.com/openconfig/featureprofiles/tree/main/feature/system/attestz/tests/README.md" +} +test: { + id: "attestz-2" + description: "Validate oIAK and oIDevID rotation" + readme: "https://github.com/openconfig/featureprofiles/tree/main/feature/system/attestz/tests/README.md" +} +test: { + id: "attestz-3" + description: "Validate post-install re-attestation" + readme: "https://github.com/openconfig/featureprofiles/tree/main/feature/system/attestz/tests/README.md" +} test: { id: "Authz-1" description: "test policy behaviors, and probe results matches actual client results" @@ -254,6 +269,10 @@ test: { readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/qos/ate_tests/wrr_traffic_test/README.md" exec: " " } +test: { + id: "DP-2.4" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/qos/otg_tests/ingress_police_nhg/README.md" +} test: { id: "FP-1.1" description: "Power admin DOWN/UP Test" @@ -262,7 +281,7 @@ test: { test: { id: "Health-1.1" description: "Generic Health Check" - readme: "https://github.com/openconfig/featureprofiles/blob/d26ac7fac5406af29c9a582b8d8ee73d56953e3b/feature/experimental/system/health/tests/system_generic_health_check/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/system/health/tests/system_generic_health_check/README.md" exec: " " } test: { @@ -321,7 +340,7 @@ test: { } test: { id: "P4RT-1.1" - readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/experimental/p4rt/otg_tests/base_p4rt/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/p4rt/otg_tests/base_p4rt/README.md" } test: { id: "P4RT-1.2" @@ -329,56 +348,80 @@ test: { } test: { id: "P4RT-2.1" - readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/experimental/p4rt/tests/p4rt_election/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/p4rt/tests/p4rt_election/README.md" } test: { id: "P4RT-2.2" - readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/experimental/p4rt/tests/metadata_validation_test/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/p4rt/tests/metadata_validation_test/README.md" } test: { id: "P4RT-3.1" - readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/experimental/p4rt/otg_tests/google_discovery_protocol_packetin_test/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/p4rt/otg_tests/google_discovery_protocol_packetin_test/README.md" } test: { id: "P4RT-3.2" - readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/experimental/p4rt/otg_tests/google_discovery_protocol_packetout_test/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/p4rt/otg_tests/google_discovery_protocol_packetout_test/README.md" } test: { id: "P4RT-5.1" - readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/experimental/p4rt/otg_tests/traceroute_packetin_test/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/p4rt/otg_tests/traceroute_packetin_test/README.md" } test: { id: "P4RT-5.2" - readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/experimental/p4rt/otg_tests/traceroute_packetout_test/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/p4rt/otg_tests/traceroute_packetout_test/README.md" } test: { id: "P4RT-6.1" - readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/experimental/p4rt/otg_tests/performance_test/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/p4rt/otg_tests/performance_test/README.md" } test: { id: "P4RT-7.1" - readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/experimental/p4rt/otg_tests/lldp_packetin_test/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/p4rt/otg_tests/lldp_packetin_test/README.md" } test: { id: "P4RT-7.2" - readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/experimental/p4rt/otg_tests/lldp_packetout_test/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/p4rt/otg_tests/lldp_packetout_test/README.md" } test: { id: "PF-1.1" description: "IPv4/IPv6 policy-forwarding to indirect NH matching DSCP/TC" - readme: "https://github.com/openconfig/featureprofiles/feature/policy_forwarding/otg_tests/match_dscp_indirect_next_hop/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/policy_forwarding/otg_tests/match_dscp_indirect_next_hop/README.md" exec: " " } test: { id: "PF-1.2" description: "Policy-based traffic GRE Encapsulation to IPv4 GRE tunnel" - readme: "https://github.com/openconfig/featureprofiles/feature/policy_forwarding/encapsulation/otg_tests/encap_gre_ipv4/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/policy_forwarding/encapsulation/otg_tests/encap_gre_ipv4/README.md" + exec: " " +} +test: { + id: "PF-1.3" + description: "Policy-based Static GUE Encapsulation to IPv4 tunnel" + readme: " " + exec: " " +} +test: { + id: "PF-1.4" + description: "Interface based GUE Decapsulation to IPv4 tunnel" + readme: " " + exec: " " +} +test: { + id: "PF-1.5" + description: "Interface based MPLSoGUE Decapsulation to IPv4 tunnel" + readme: " " + exec: " " +} +test: { + id: "PF-1.6" + description: "IPv4 & IPV6 based traffic steering from Non-default VRF to Default VRF using Policy based VRF selection" + readme: "" exec: " " } test: { id: "PLT-1.1" description: "Interface breakout Test" - readme: "https://github.com/openconfig/featureprofiles/feature/experimental/platform/tests/breakout_configuration/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/platform/tests/breakout_configuration/README.md" exec: " " } test: { @@ -433,13 +476,13 @@ test: { test: { id: "RT-1.11" description: "RT-1.11: BGP remove private AS" - readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/experimental/bgp/ate_tests/bgp_remove_private_as/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/bgp/otg_tests/bgp_remove_private_as/README.md" exec: " " } test: { id: "RT-1.12" description: "RT-1.12: BGP always compare MED" - readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/experimental/bgp/ate_tests/bgp_always_compare_med/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/bgp/otg_tests/bgp_always_compare_med/README.md" exec: " " } test: { @@ -481,7 +524,7 @@ test: { test: { id: "RT-1.19" description: "BGP 2-Byte and 4-Byte ASN support" - readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/experimental/bgp/otg_tests/bgp_2byte_4byte_asn/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/bgp/otg_tests/bgp_2byte_4byte_asn/README.md" exec: " " } test: { @@ -505,7 +548,7 @@ test: { test: { id: "RT-1.24" description: "BGP 2-byte and 4-byte ASN support with policy" - readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/experimental/bgp/otg_tests/bgp_2byte_4byte_asn_policy_test/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/bgp/otg_tests/bgp_2byte_4byte_asn_policy_test/README.md" exec: " " } test: { @@ -553,17 +596,23 @@ test: { test: { id: "RT-1.32" description: "BGP policy actions - MED, LocPref, prepend, flow-control" - readme: "https://github.com/openconfig/featureprofiles/feature/bgp/policybase/otg_tests/actions-MED_LocPref_prepend_flow-control/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/bgp/policybase/otg_tests/actions-MED_LocPref_prepend_flow-control/README.md" exec: " " } test: { id: "RT-1.33" - readme: "https://github.com/openconfig/featureprofiles/feature/bgp/policybase/otg_tests/prefix_set_test/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/bgp/policybase/otg_tests/prefix_set_test/README.md" } test: { id: "RT-1.34" description: "Administrative Distance test for iBGP and eBGP" - readme: "https://github.com/openconfig/featureprofiles/feature/bgp/admin_distance/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/bgp/admin_distance/README.md" + exec: " " +} +test: { + id: "RT-1.35" + description: "Extended routes retention" + readme: "" exec: " " } test: { @@ -581,7 +630,7 @@ test: { test: { id: "RT-1.53" description: "Prefix-set test" - readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/experimental/policy/prefix_set/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/policy_forwarding/otg_tests/prefix_set_test/README.md" exec: " " } test: { @@ -658,13 +707,13 @@ test: { test: { id: "RT-2.14" description: "ISIS Drain Test" - readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/experimental/isis/otg_tests/isis_drain_test/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/isis/otg_tests/isis_drain_test/README.md" exec: " " } test: { id: "RT-2.2" description: "IS-IS LSP Updates" - readme: "https://github.com/openconfig/featureprofiles/feature/experimental/isis/otg_tests/lsp_updates_test/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/isis/otg_tests/lsp_updates_test/README.md" } test: { id: "RT-2.6" @@ -693,13 +742,31 @@ test: { test: { id: "RT-3.1" description: "Policy based VRF selection base" - readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/experimental/policy/policy_vrf_selection/ate_tests/base_vrf_selection/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/policy_forwarding/policy_vrf_selection/otg_tests/base_vrf_selection/README.md" exec: " " } test: { id: "RT-3.2" description: "Policy based VRF selection with multiple protocol and DSCP values" - readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/experimental/policy/policy_vrf_selection/ate_tests/protocol_dscp_rules_for_vrf_selection_test/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/policy_forwarding/policy_vrf_selection/otg_tests/protocol_dscp_rules_for_vrf_selection_test/README.md" + exec: " " +} +test: { + id: "RT-3.3" + description: "Multiple VRFs and GUE DECAP in Default VRF" + readme: "" + exec: " " +} +test: { + id: "RT-3.31" + description: "DSCP based traffic steering from default VRF to non-Default VRF using Policy based VRF selection plus GUE DECAP" + readme: "" + exec: " " +} +test: { + id: "RT-3.32" + description: "DSCP based traffic steering from Non-default VRF to Default VRF using Policy based VRF selection plus GUE DECAP and ENCAP" + readme: "" exec: " " } test: { @@ -765,7 +832,7 @@ test: { test: { id: "RT-5.6" description: "Interface Loopback mode" - readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/experimental/interface/interface_loopback_aggregate/otg_tests/interface_loopback_aggregate/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/interface/interface_loopback_aggregate/otg_tests/interface_loopback_aggregate/README.md" } test: { id: "RT-5.7" @@ -828,7 +895,7 @@ test: { test: { id: "RT-7.5" description: "BGP Policy - Set Link Bandwidth Community" - readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/experimental/bgp/otg_tests/link_bandwidth_test/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/bgp/otg_tests/link_bandwidth_test/README.md" } test: { id: "RT-7.6" @@ -879,7 +946,7 @@ test: { } test: { id: "Replay-1.2" - readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/experimental/replay/tests/p4rt_replay/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/replay/tests/p4rt_replay/README.md" } test: { id: "SFLOW-1" @@ -946,16 +1013,27 @@ test: { } test: { id: "TE-16.1" + description: "gRIBI Traffic Engineering - Basic encapsulation tests" readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/gribi/otg_tests/basic_encap_test/README.md" } test: { id: "TE-16.2" - description: "gRIBI encapsulation FRR scenarios" + description: "gRIBI Traffic Engineering encapsulation FRR scenarios" readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/gribi/otg_tests/encap_frr/README.md" } +test: { + id: "TE-16.3" + description: "gRIBI Traffic Engineering Encapsulation with Re-encap NI FRR scenarios" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/gribi/otg_tests/encap_frr_with_reencap_vrf_test/README.md" +} test: { id: "TE-17.1" - readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/experimental/gribi/otg_tests/vrf_policy_driven_te/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/gribi/otg_tests/vrf_policy_driven_te/README.md" +} +test { + id: "TE-18.1" + description: "MPLS in UDP Encapsulation with QoS scheduler" + readme: "" } test: { id: "TE-2.1" @@ -1500,7 +1578,7 @@ test: { test: { id: "gNMI-1.20" description: "Telemetry: Optics Thresholds" - readme: "https://github.com/openconfig/featureprofiles/feature/experimental/platform/tests/optics_thresholds_test/README.md" + readme: "https://github.com/openconfig/featureprofiles/blob/main/feature/platform/tests/optics_thresholds_test/README.md" exec: " " } test: { diff --git a/topologies/binding/binding.go b/topologies/binding/binding.go index 43c9eb3e895..d47f7ce18eb 100644 --- a/topologies/binding/binding.go +++ b/topologies/binding/binding.go @@ -46,7 +46,7 @@ import ( var ( // To be stubbed out by unit tests. - grpcDialContextFn = grpc.DialContext + grpcDialContextFn = grpc.NewClient gosnappiNewAPIFn = gosnappi.NewApi ) @@ -473,7 +473,7 @@ func dialConn(ctx context.Context, dev introspect.Introspector, svc introspect.S } func dialOpts(bopts *bindpb.Options) ([]grpc.DialOption, error) { - opts := []grpc.DialOption{grpc.WithBlock()} + opts := []grpc.DialOption{grpc.WithDisableRetry()} switch { case bopts.Insecure: tc := insecure.NewCredentials() @@ -523,10 +523,10 @@ func makeDialer(params *svcParams, bopts *bindpb.Options) (*introspect.Dialer, e DialFunc: func(ctx context.Context, target string, opts ...grpc.DialOption) (*grpc.ClientConn, error) { if bopts.Timeout != 0 { var cancelFunc context.CancelFunc - ctx, cancelFunc = context.WithTimeout(ctx, time.Duration(bopts.Timeout)*time.Second) + _, cancelFunc = context.WithTimeout(ctx, time.Duration(bopts.Timeout)*time.Second) defer cancelFunc() } - return grpcDialContextFn(ctx, target, opts...) + return grpcDialContextFn(target, opts...) }, DialTarget: bopts.Target, DialOpts: opts, diff --git a/topologies/binding/binding_test.go b/topologies/binding/binding_test.go index 25243928e98..5a13b066457 100644 --- a/topologies/binding/binding_test.go +++ b/topologies/binding/binding_test.go @@ -244,7 +244,7 @@ func TestDialOTGTimeout(t *testing.T) { r: resolver{&bindpb.Binding{}}, dev: &bindpb.Device{Otg: &bindpb.Options{Timeout: timeoutSecs}}, } - grpcDialContextFn = func(context.Context, string, ...grpc.DialOption) (*grpc.ClientConn, error) { + grpcDialContextFn = func(string, ...grpc.DialOption) (*grpc.ClientConn, error) { return nil, nil } gosnappiNewAPIFn = func() gosnappi.Api { diff --git a/topologies/binding/gnsi.go b/topologies/binding/gnsi.go index 7469edf20b3..6f55ec99da9 100644 --- a/topologies/binding/gnsi.go +++ b/topologies/binding/gnsi.go @@ -43,5 +43,8 @@ func (g gnsiConn) Credentialz() credpb.CredentialzClient { func (g gnsiConn) Acctz() accpb.AcctzClient { return accpb.NewAcctzClient(g.conn) } +func (g gnsiConn) AcctzStream() accpb.AcctzStreamClient { + return accpb.NewAcctzStreamClient(g.conn) +} var _ = binding.GNSIClients(gnsiConn{})