go.ligato.io/vpp-agent/v3@v3.5.0/plugins/vpp/ipsecplugin/vppcalls/vpp2101/ipsec_vppcalls_test.go (about)

     1  //  Copyright (c) 2019 Cisco and/or its affiliates.
     2  //
     3  //  Licensed under the Apache License, Version 2.0 (the "License");
     4  //  you may not use this file except in compliance with the License.
     5  //  You may obtain a copy of the License at:
     6  //
     7  //      http://www.apache.org/licenses/LICENSE-2.0
     8  //
     9  //  Unless required by applicable law or agreed to in writing, software
    10  //  distributed under the License is distributed on an "AS IS" BASIS,
    11  //  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    12  //  See the License for the specific language governing permissions and
    13  //  limitations under the License.
    14  
    15  package vpp2101_test
    16  
    17  import (
    18  	"encoding/hex"
    19  	"fmt"
    20  	"testing"
    21  
    22  	. "github.com/onsi/gomega"
    23  	"go.ligato.io/cn-infra/v2/logging/logrus"
    24  
    25  	"go.ligato.io/vpp-agent/v3/plugins/vpp/binapi/vpp2101/ip_types"
    26  	vpp_ipsec "go.ligato.io/vpp-agent/v3/plugins/vpp/binapi/vpp2101/ipsec"
    27  	"go.ligato.io/vpp-agent/v3/plugins/vpp/binapi/vpp2101/ipsec_types"
    28  	"go.ligato.io/vpp-agent/v3/plugins/vpp/ifplugin/ifaceidx"
    29  	"go.ligato.io/vpp-agent/v3/plugins/vpp/ipsecplugin/vppcalls"
    30  	"go.ligato.io/vpp-agent/v3/plugins/vpp/ipsecplugin/vppcalls/vpp2101"
    31  	"go.ligato.io/vpp-agent/v3/plugins/vpp/vppmock"
    32  	ipsec "go.ligato.io/vpp-agent/v3/proto/ligato/vpp/ipsec"
    33  )
    34  
    35  func ipToAddr(ip string) ip_types.Address {
    36  	addr, err := vpp2101.IPToAddress(ip)
    37  	if err != nil {
    38  		panic(fmt.Sprintf("invalid IP: %s", ip))
    39  	}
    40  	return addr
    41  }
    42  
    43  func TestVppAddSPD(t *testing.T) {
    44  	ctx, ipSecHandler, _ := ipSecTestSetup(t)
    45  	defer ctx.TeardownTestCtx()
    46  
    47  	ctx.MockVpp.MockReply(&vpp_ipsec.IpsecSpdAddDelReply{})
    48  
    49  	err := ipSecHandler.AddSPD(10)
    50  
    51  	Expect(err).ShouldNot(HaveOccurred())
    52  	Expect(ctx.MockChannel.Msg).To(BeEquivalentTo(&vpp_ipsec.IpsecSpdAddDel{
    53  		IsAdd: true,
    54  		SpdID: 10,
    55  	}))
    56  }
    57  
    58  func TestVppDelSPD(t *testing.T) {
    59  	ctx, ipSecHandler, _ := ipSecTestSetup(t)
    60  	defer ctx.TeardownTestCtx()
    61  
    62  	ctx.MockVpp.MockReply(&vpp_ipsec.IpsecSpdAddDelReply{})
    63  
    64  	err := ipSecHandler.DeleteSPD(10)
    65  
    66  	Expect(err).ShouldNot(HaveOccurred())
    67  	Expect(ctx.MockChannel.Msg).To(BeEquivalentTo(&vpp_ipsec.IpsecSpdAddDel{
    68  		IsAdd: false,
    69  		SpdID: 10,
    70  	}))
    71  }
    72  
    73  func TestVppAddSP(t *testing.T) {
    74  	ctx, ipSecHandler, _ := ipSecTestSetup(t)
    75  	defer ctx.TeardownTestCtx()
    76  
    77  	ctx.MockVpp.MockReply(&vpp_ipsec.IpsecSpdEntryAddDelReply{})
    78  
    79  	err := ipSecHandler.AddSP(&ipsec.SecurityPolicy{
    80  		SaIndex:    5,
    81  		SpdIndex:   10,
    82  		Priority:   10,
    83  		IsOutbound: true,
    84  	})
    85  
    86  	Expect(err).ShouldNot(HaveOccurred())
    87  	Expect(ctx.MockChannel.Msg).To(BeEquivalentTo(&vpp_ipsec.IpsecSpdEntryAddDel{
    88  		IsAdd: true,
    89  		Entry: vpp_ipsec.IpsecSpdEntry{
    90  			SpdID:              10,
    91  			SaID:               5,
    92  			Priority:           10,
    93  			IsOutbound:         true,
    94  			RemoteAddressStart: ipToAddr("0.0.0.0"),
    95  			RemoteAddressStop:  ipToAddr("255.255.255.255"),
    96  			LocalAddressStart:  ipToAddr("0.0.0.0"),
    97  			LocalAddressStop:   ipToAddr("255.255.255.255"),
    98  			RemotePortStop:     65535,
    99  			LocalPortStop:      65535,
   100  		},
   101  	}))
   102  }
   103  
   104  func TestVppDelSP(t *testing.T) {
   105  	ctx, ipSecHandler, _ := ipSecTestSetup(t)
   106  	defer ctx.TeardownTestCtx()
   107  
   108  	ctx.MockVpp.MockReply(&vpp_ipsec.IpsecSpdEntryAddDelReply{})
   109  
   110  	err := ipSecHandler.DeleteSP(&ipsec.SecurityPolicy{
   111  		SpdIndex:   10,
   112  		SaIndex:    2,
   113  		Priority:   5,
   114  		IsOutbound: true,
   115  	})
   116  
   117  	Expect(err).ShouldNot(HaveOccurred())
   118  	Expect(ctx.MockChannel.Msg).To(BeEquivalentTo(&vpp_ipsec.IpsecSpdEntryAddDel{
   119  		IsAdd: false,
   120  		Entry: vpp_ipsec.IpsecSpdEntry{
   121  			SpdID:              10,
   122  			SaID:               2,
   123  			Priority:           5,
   124  			IsOutbound:         true,
   125  			RemoteAddressStart: ipToAddr("0.0.0.0"),
   126  			RemoteAddressStop:  ipToAddr("255.255.255.255"),
   127  			LocalAddressStart:  ipToAddr("0.0.0.0"),
   128  			LocalAddressStop:   ipToAddr("255.255.255.255"),
   129  			RemotePortStop:     65535,
   130  			LocalPortStop:      65535,
   131  		},
   132  	}))
   133  }
   134  
   135  func TestVppInterfaceAddSPD(t *testing.T) {
   136  	ctx, ipSecHandler, ifIndex := ipSecTestSetup(t)
   137  	defer ctx.TeardownTestCtx()
   138  
   139  	ctx.MockVpp.MockReply(&vpp_ipsec.IpsecInterfaceAddDelSpdReply{})
   140  
   141  	ifIndex.Put("if1", &ifaceidx.IfaceMetadata{SwIfIndex: 2})
   142  
   143  	err := ipSecHandler.AddSPDInterface(10, &ipsec.SecurityPolicyDatabase_Interface{
   144  		Name: "if1",
   145  	})
   146  
   147  	Expect(err).ShouldNot(HaveOccurred())
   148  	Expect(ctx.MockChannel.Msg).To(BeEquivalentTo(&vpp_ipsec.IpsecInterfaceAddDelSpd{
   149  		IsAdd:     true,
   150  		SpdID:     10,
   151  		SwIfIndex: 2,
   152  	}))
   153  }
   154  
   155  func TestVppInterfaceDelSPD(t *testing.T) {
   156  	ctx, ipSecHandler, ifIndex := ipSecTestSetup(t)
   157  	defer ctx.TeardownTestCtx()
   158  
   159  	ctx.MockVpp.MockReply(&vpp_ipsec.IpsecInterfaceAddDelSpdReply{})
   160  
   161  	ifIndex.Put("if1", &ifaceidx.IfaceMetadata{SwIfIndex: 2})
   162  
   163  	err := ipSecHandler.DeleteSPDInterface(10, &ipsec.SecurityPolicyDatabase_Interface{
   164  		Name: "if1",
   165  	})
   166  
   167  	Expect(err).ShouldNot(HaveOccurred())
   168  	Expect(ctx.MockChannel.Msg).To(BeEquivalentTo(&vpp_ipsec.IpsecInterfaceAddDelSpd{
   169  		IsAdd:     false,
   170  		SpdID:     10,
   171  		SwIfIndex: 2,
   172  	}))
   173  }
   174  
   175  func ipSecTestSetup(t *testing.T) (*vppmock.TestCtx, vppcalls.IPSecVppAPI, ifaceidx.IfaceMetadataIndexRW) {
   176  	ctx := vppmock.SetupTestCtx(t)
   177  	log := logrus.NewLogger("test-log")
   178  	ifIndex := ifaceidx.NewIfaceIndex(log, "ipsec-test-ifidx")
   179  	ipSecHandler := vpp2101.NewIPSecVppHandler(ctx.MockChannel, ifIndex, log)
   180  	return ctx, ipSecHandler, ifIndex
   181  }
   182  
   183  func TestVppAddSA(t *testing.T) {
   184  	ctx, ipSecHandler, _ := ipSecTestSetup(t)
   185  	defer ctx.TeardownTestCtx()
   186  
   187  	ctx.MockVpp.MockReply(&vpp_ipsec.IpsecSadEntryAddDelReply{})
   188  
   189  	cryptoKey, err := hex.DecodeString("")
   190  	Expect(err).To(BeNil())
   191  
   192  	err = ipSecHandler.AddSA(&ipsec.SecurityAssociation{
   193  		Index:         1,
   194  		Spi:           uint32(1001),
   195  		UseEsn:        true,
   196  		UseAntiReplay: true,
   197  		Protocol:      ipsec.SecurityAssociation_ESP,
   198  	})
   199  
   200  	Expect(err).ShouldNot(HaveOccurred())
   201  	Expect(ctx.MockChannel.Msg).To(BeEquivalentTo(&vpp_ipsec.IpsecSadEntryAddDel{
   202  		IsAdd: true,
   203  		Entry: ipsec_types.IpsecSadEntry{
   204  			Protocol: ipsec_types.IPSEC_API_PROTO_ESP,
   205  			SadID:    1,
   206  			Spi:      1001,
   207  			CryptoKey: ipsec_types.Key{
   208  				Length: uint8(len(cryptoKey)),
   209  				Data:   cryptoKey,
   210  			},
   211  			IntegrityKey: ipsec_types.Key{
   212  				Length: uint8(len(cryptoKey)),
   213  				Data:   cryptoKey,
   214  			},
   215  			Flags:      ipsec_types.IPSEC_API_SAD_FLAG_USE_ESN | ipsec_types.IPSEC_API_SAD_FLAG_USE_ANTI_REPLAY,
   216  			UDPSrcPort: ^uint16(0),
   217  			UDPDstPort: ^uint16(0),
   218  		},
   219  	}))
   220  }
   221  
   222  func TestVppDelSA(t *testing.T) {
   223  	ctx, ipSecHandler, _ := ipSecTestSetup(t)
   224  	defer ctx.TeardownTestCtx()
   225  
   226  	ctx.MockVpp.MockReply(&vpp_ipsec.IpsecSadEntryAddDelReply{})
   227  
   228  	cryptoKey, err := hex.DecodeString("")
   229  	Expect(err).To(BeNil())
   230  
   231  	err = ipSecHandler.DeleteSA(&ipsec.SecurityAssociation{
   232  		Index:         1,
   233  		Spi:           uint32(1001),
   234  		UseEsn:        true,
   235  		UseAntiReplay: true,
   236  		Protocol:      ipsec.SecurityAssociation_ESP,
   237  	})
   238  
   239  	Expect(err).ShouldNot(HaveOccurred())
   240  	Expect(ctx.MockChannel.Msg).To(BeEquivalentTo(&vpp_ipsec.IpsecSadEntryAddDel{
   241  		IsAdd: false,
   242  		Entry: ipsec_types.IpsecSadEntry{
   243  			SadID: 1,
   244  			Spi:   1001,
   245  			CryptoKey: ipsec_types.Key{
   246  				Length: uint8(len(cryptoKey)),
   247  				Data:   cryptoKey,
   248  			},
   249  			IntegrityKey: ipsec_types.Key{
   250  				Length: uint8(len(cryptoKey)),
   251  				Data:   cryptoKey,
   252  			},
   253  			Flags:      ipsec_types.IPSEC_API_SAD_FLAG_USE_ESN | ipsec_types.IPSEC_API_SAD_FLAG_USE_ANTI_REPLAY,
   254  			Protocol:   ipsec_types.IPSEC_API_PROTO_ESP,
   255  			UDPSrcPort: ^uint16(0),
   256  			UDPDstPort: ^uint16(0),
   257  		},
   258  	}))
   259  }
   260  
   261  func TestVppAddSATunnelMode(t *testing.T) {
   262  	ctx, ipSecHandler, _ := ipSecTestSetup(t)
   263  	defer ctx.TeardownTestCtx()
   264  
   265  	ctx.MockVpp.MockReply(&vpp_ipsec.IpsecSadEntryAddDelReply{})
   266  
   267  	cryptoKey, err := hex.DecodeString("")
   268  	Expect(err).To(BeNil())
   269  
   270  	err = ipSecHandler.AddSA(&ipsec.SecurityAssociation{
   271  		Index:         1,
   272  		Spi:           uint32(1001),
   273  		TunnelSrcAddr: "10.1.0.1",
   274  		TunnelDstAddr: "20.1.0.1",
   275  		Protocol:      ipsec.SecurityAssociation_ESP,
   276  	})
   277  
   278  	Expect(err).ShouldNot(HaveOccurred())
   279  	Expect(ctx.MockChannel.Msg).To(BeEquivalentTo(&vpp_ipsec.IpsecSadEntryAddDel{
   280  		IsAdd: true,
   281  		Entry: ipsec_types.IpsecSadEntry{
   282  			SadID: 1,
   283  			Spi:   1001,
   284  			CryptoKey: ipsec_types.Key{
   285  				Length: uint8(len(cryptoKey)),
   286  				Data:   cryptoKey,
   287  			},
   288  			IntegrityKey: ipsec_types.Key{
   289  				Length: uint8(len(cryptoKey)),
   290  				Data:   cryptoKey,
   291  			},
   292  			TunnelSrc: ip_types.Address{
   293  				Af: ip_types.ADDRESS_IP4,
   294  				Un: ip_types.AddressUnionIP4(ip_types.IP4Address{10, 1, 0, 1}),
   295  			},
   296  			TunnelDst: ip_types.Address{
   297  				Af: ip_types.ADDRESS_IP4,
   298  				Un: ip_types.AddressUnionIP4(ip_types.IP4Address{20, 1, 0, 1}),
   299  			},
   300  			Flags:      ipsec_types.IPSEC_API_SAD_FLAG_IS_TUNNEL,
   301  			Protocol:   ipsec_types.IPSEC_API_PROTO_ESP,
   302  			UDPSrcPort: ^uint16(0),
   303  			UDPDstPort: ^uint16(0),
   304  		},
   305  	}))
   306  }
   307  
   308  func TestVppAddSATunnelModeIPv6(t *testing.T) {
   309  	ctx, ipSecHandler, _ := ipSecTestSetup(t)
   310  	defer ctx.TeardownTestCtx()
   311  
   312  	ctx.MockVpp.MockReply(&vpp_ipsec.IpsecSadEntryAddDelReply{})
   313  
   314  	cryptoKey, err := hex.DecodeString("")
   315  	Expect(err).To(BeNil())
   316  
   317  	err = ipSecHandler.AddSA(&ipsec.SecurityAssociation{
   318  		Index:         1,
   319  		Spi:           uint32(1001),
   320  		TunnelSrcAddr: "1234::",
   321  		TunnelDstAddr: "abcd::",
   322  		Protocol:      ipsec.SecurityAssociation_ESP,
   323  	})
   324  
   325  	Expect(err).ShouldNot(HaveOccurred())
   326  	Expect(ctx.MockChannel.Msg).To(BeEquivalentTo(&vpp_ipsec.IpsecSadEntryAddDel{
   327  		IsAdd: true,
   328  		Entry: ipsec_types.IpsecSadEntry{
   329  			SadID: 1,
   330  			Spi:   1001,
   331  			CryptoKey: ipsec_types.Key{
   332  				Length: uint8(len(cryptoKey)),
   333  				Data:   cryptoKey,
   334  			},
   335  			IntegrityKey: ipsec_types.Key{
   336  				Length: uint8(len(cryptoKey)),
   337  				Data:   cryptoKey,
   338  			},
   339  			TunnelSrc: ip_types.Address{
   340  				Af: ip_types.ADDRESS_IP6,
   341  				Un: ip_types.AddressUnion{XXX_UnionData: [16]byte{18, 52}},
   342  			},
   343  			TunnelDst: ip_types.Address{
   344  				Af: ip_types.ADDRESS_IP6,
   345  				Un: ip_types.AddressUnion{XXX_UnionData: [16]byte{171, 205}},
   346  			},
   347  			Flags:      ipsec_types.IPSEC_API_SAD_FLAG_IS_TUNNEL | ipsec_types.IPSEC_API_SAD_FLAG_IS_TUNNEL_V6,
   348  			Protocol:   ipsec_types.IPSEC_API_PROTO_ESP,
   349  			UDPSrcPort: ^uint16(0),
   350  			UDPDstPort: ^uint16(0),
   351  		},
   352  	}))
   353  }
   354  
   355  func TestVppAddTunnelProtection(t *testing.T) {
   356  	ctx, ipSecHandler, ifIndex := ipSecTestSetup(t)
   357  	defer ctx.TeardownTestCtx()
   358  
   359  	ifIndex.Put("ipip-tunnel", &ifaceidx.IfaceMetadata{SwIfIndex: 5})
   360  
   361  	ctx.MockVpp.MockReply(&vpp_ipsec.IpsecTunnelProtectUpdateReply{})
   362  	err := ipSecHandler.AddTunnelProtection(&ipsec.TunnelProtection{
   363  		Interface: "ipip-tunnel",
   364  		SaOut:     []uint32{10},
   365  		SaIn:      []uint32{20, 30},
   366  	})
   367  
   368  	Expect(err).ShouldNot(HaveOccurred())
   369  	Expect(ctx.MockChannel.Msg).To(BeEquivalentTo(&vpp_ipsec.IpsecTunnelProtectUpdate{
   370  		Tunnel: vpp_ipsec.IpsecTunnelProtect{
   371  			SwIfIndex: 5,
   372  			SaOut:     10,
   373  			NSaIn:     2,
   374  			SaIn:      []uint32{20, 30},
   375  		},
   376  	}))
   377  }
   378  
   379  func TestVppDelTunnelProtection(t *testing.T) {
   380  	ctx, ipSecHandler, ifIndex := ipSecTestSetup(t)
   381  	defer ctx.TeardownTestCtx()
   382  
   383  	ifIndex.Put("ipip-tunnel", &ifaceidx.IfaceMetadata{SwIfIndex: 5})
   384  
   385  	ctx.MockVpp.MockReply(&vpp_ipsec.IpsecTunnelProtectDelReply{})
   386  
   387  	err := ipSecHandler.DeleteTunnelProtection(&ipsec.TunnelProtection{
   388  		Interface: "ipip-tunnel",
   389  	})
   390  
   391  	Expect(err).ShouldNot(HaveOccurred())
   392  	Expect(ctx.MockChannel.Msg).To(BeEquivalentTo(&vpp_ipsec.IpsecTunnelProtectDel{
   393  		SwIfIndex: 5,
   394  	}))
   395  }