"testing"
"time"
- "git.fd.io/govpp.git/adapter/mock"
- "git.fd.io/govpp.git/core/bin_api/vpe"
- "git.fd.io/govpp.git/examples/bin_api/interfaces"
- "git.fd.io/govpp.git/examples/bin_api/memif"
- "git.fd.io/govpp.git/examples/bin_api/tap"
+ . "github.com/onsi/gomega"
+ "git.fd.io/govpp.git/adapter/mock"
"git.fd.io/govpp.git/api"
- . "github.com/onsi/gomega"
+ "git.fd.io/govpp.git/examples/binapi/interfaces"
+ "git.fd.io/govpp.git/examples/binapi/memif"
+ "git.fd.io/govpp.git/examples/binapi/vpe"
)
type testCtx struct {
RegisterTestingT(t)
ctx := &testCtx{
- mockVpp: &mock.VppAdapter{},
+ mockVpp: mock.NewVppAdapter(),
}
var err error
ctx.conn.Disconnect()
}
-func TestRequestReplyTapConnect(t *testing.T) {
- ctx := setupTest(t)
- defer ctx.teardownTest()
-
- ctx.mockVpp.MockReply(&tap.TapConnectReply{
- Retval: 10,
- SwIfIndex: 1,
- })
- request := &tap.TapConnect{
- TapName: []byte("test-tap-name"),
- UseRandomMac: 1,
- }
- reply := &tap.TapConnectReply{}
-
- err := ctx.ch.SendRequest(request).ReceiveReply(reply)
- Expect(err).ShouldNot(HaveOccurred())
- Expect(reply.Retval).To(BeEquivalentTo(10), "Incorrect retval value for TapConnectReply")
- Expect(reply.SwIfIndex).To(BeEquivalentTo(1), "Incorrect SwIfIndex value for TapConnectReply")
-}
-
-func TestRequestReplyTapModify(t *testing.T) {
- ctx := setupTest(t)
- defer ctx.teardownTest()
-
- ctx.mockVpp.MockReply(&tap.TapModifyReply{
- Retval: 15,
- SwIfIndex: 2,
- })
- request := &tap.TapModify{
- TapName: []byte("test-tap-modify"),
- UseRandomMac: 1,
- CustomDevInstance: 1,
- }
- reply := &tap.TapModifyReply{}
-
- err := ctx.ch.SendRequest(request).ReceiveReply(reply)
- Expect(err).ShouldNot(HaveOccurred())
- Expect(reply.Retval).To(BeEquivalentTo(15), "Incorrect retval value for TapModifyReply")
- Expect(reply.SwIfIndex).To(BeEquivalentTo(2), "Incorrect SwIfIndex value for TapModifyReply")
-}
-
-func TestRequestReplyTapDelete(t *testing.T) {
- ctx := setupTest(t)
- defer ctx.teardownTest()
-
- ctx.mockVpp.MockReply(&tap.TapDeleteReply{
- Retval: 20,
- })
- request := &tap.TapDelete{
- SwIfIndex: 3,
- }
- reply := &tap.TapDeleteReply{}
-
- err := ctx.ch.SendRequest(request).ReceiveReply(reply)
- Expect(err).ShouldNot(HaveOccurred())
- Expect(reply.Retval).To(BeEquivalentTo(20), "Incorrect retval value for TapDeleteReply")
-}
-
-func TestRequestReplySwInterfaceTapDump(t *testing.T) {
- ctx := setupTest(t)
- defer ctx.teardownTest()
-
- byteName := []byte("dev-name-test")
- ctx.mockVpp.MockReply(&tap.SwInterfaceTapDetails{
- SwIfIndex: 25,
- DevName: byteName,
- })
- request := &tap.SwInterfaceTapDump{}
- reply := &tap.SwInterfaceTapDetails{}
-
- err := ctx.ch.SendRequest(request).ReceiveReply(reply)
- Expect(err).ShouldNot(HaveOccurred())
- Expect(reply.SwIfIndex).To(BeEquivalentTo(25), "Incorrect SwIfIndex value for SwInterfaceTapDetails")
- Expect(reply.DevName).ToNot(BeNil(), "Incorrect DevName value for SwInterfaceTapDetails")
-}
-
func TestRequestReplyMemifCreate(t *testing.T) {
ctx := setupTest(t)
defer ctx.teardownTest()
+ // mock reply
ctx.mockVpp.MockReply(&memif.MemifCreateReply{
- Retval: 22,
SwIfIndex: 4,
})
+
request := &memif.MemifCreate{
Role: 10,
ID: 12,
err := ctx.ch.SendRequest(request).ReceiveReply(reply)
Expect(err).ShouldNot(HaveOccurred())
- Expect(reply.Retval).To(BeEquivalentTo(22), "Incorrect Retval value for MemifCreate")
- Expect(reply.SwIfIndex).To(BeEquivalentTo(4), "Incorrect SwIfIndex value for MemifCreate")
+ Expect(reply.Retval).To(BeEquivalentTo(0),
+ "Incorrect Retval value for MemifCreate")
+ Expect(reply.SwIfIndex).To(BeEquivalentTo(4),
+ "Incorrect SwIfIndex value for MemifCreate")
}
func TestRequestReplyMemifDelete(t *testing.T) {
ctx := setupTest(t)
defer ctx.teardownTest()
- ctx.mockVpp.MockReply(&memif.MemifDeleteReply{
- Retval: 24,
- })
+ // mock reply
+ ctx.mockVpp.MockReply(&memif.MemifDeleteReply{})
+
request := &memif.MemifDelete{
SwIfIndex: 15,
}
err := ctx.ch.SendRequest(request).ReceiveReply(reply)
Expect(err).ShouldNot(HaveOccurred())
- Expect(reply.Retval).To(BeEquivalentTo(24), "Incorrect Retval value for MemifDelete")
}
func TestRequestReplyMemifDetails(t *testing.T) {
ctx := setupTest(t)
defer ctx.teardownTest()
+ // mock reply
ctx.mockVpp.MockReply(&memif.MemifDetails{
SwIfIndex: 25,
IfName: []byte("memif-name"),
Role: 0,
})
+
request := &memif.MemifDump{}
reply := &memif.MemifDetails{}
err := ctx.ch.SendRequest(request).ReceiveReply(reply)
Expect(err).ShouldNot(HaveOccurred())
- Expect(reply.SwIfIndex).To(BeEquivalentTo(25), "Incorrect SwIfIndex value for MemifDetails")
- Expect(reply.IfName).ToNot(BeEmpty(), "MemifDetails IfName is empty byte array")
- Expect(reply.Role).To(BeEquivalentTo(0), "Incorrect Role value for MemifDetails")
-}
-
-func TestMultiRequestReplySwInterfaceTapDump(t *testing.T) {
- ctx := setupTest(t)
- defer ctx.teardownTest()
-
- // mock reply
- var msgs []api.Message
- for i := 1; i <= 10; i++ {
- msgs = append(msgs, &tap.SwInterfaceTapDetails{
- SwIfIndex: uint32(i),
- DevName: []byte("dev-name-test"),
- })
- }
- ctx.mockVpp.MockReply(msgs...)
- ctx.mockVpp.MockReply(&vpe.ControlPingReply{})
-
- reqCtx := ctx.ch.SendMultiRequest(&tap.SwInterfaceTapDump{})
- cnt := 0
- for {
- msg := &tap.SwInterfaceTapDetails{}
- stop, err := reqCtx.ReceiveReply(msg)
- if stop {
- break // break out of the loop
- }
- Expect(err).ShouldNot(HaveOccurred())
- cnt++
- }
- Expect(cnt).To(BeEquivalentTo(10))
+ Expect(reply.SwIfIndex).To(BeEquivalentTo(25),
+ "Incorrect SwIfIndex value for MemifDetails")
+ Expect(reply.IfName).ToNot(BeEmpty(),
+ "MemifDetails IfName is empty byte array")
+ Expect(reply.Role).To(BeEquivalentTo(0),
+ "Incorrect Role value for MemifDetails")
}
func TestMultiRequestReplySwInterfaceMemifDump(t *testing.T) {
})
}
ctx.mockVpp.MockReply(msgs...)
- ctx.mockVpp.MockReply(&vpe.ControlPingReply{})
+ ctx.mockVpp.MockReply(&ControlPingReply{})
reqCtx := ctx.ch.SendMultiRequest(&memif.MemifDump{})
cnt := 0
msg := &memif.MemifDetails{}
stop, err := reqCtx.ReceiveReply(msg)
if stop {
- break // break out of the loop
+ break
}
Expect(err).ShouldNot(HaveOccurred())
cnt++
Expect(cnt).To(BeEquivalentTo(10))
}
-func TestNotifications(t *testing.T) {
- ctx := setupTest(t)
- defer ctx.teardownTest()
-
- // subscribe for notification
- notifChan := make(chan api.Message, 1)
- subs, err := ctx.ch.SubscribeNotification(notifChan, interfaces.NewSwInterfaceSetFlags)
- Expect(err).ShouldNot(HaveOccurred())
-
- // mock the notification and force its delivery
- ctx.mockVpp.MockReply(&interfaces.SwInterfaceSetFlags{
- SwIfIndex: 3,
- AdminUpDown: 1,
- })
- ctx.mockVpp.SendMsg(0, []byte(""))
-
- // receive the notification
- var notif *interfaces.SwInterfaceSetFlags
- Eventually(func() *interfaces.SwInterfaceSetFlags {
- select {
- case n := <-notifChan:
- notif = n.(*interfaces.SwInterfaceSetFlags)
- return notif
- default:
- return nil
- }
- }).ShouldNot(BeNil())
-
- // verify the received notifications
- Expect(notif.SwIfIndex).To(BeEquivalentTo(3), "Incorrect SwIfIndex value for SwInterfaceSetFlags")
- Expect(notif.AdminUpDown).To(BeEquivalentTo(1), "Incorrect AdminUpDown value for SwInterfaceSetFlags")
-
- ctx.ch.UnsubscribeNotification(subs)
-}
-
func TestNotificationEvent(t *testing.T) {
ctx := setupTest(t)
defer ctx.teardownTest()
// subscribe for notification
notifChan := make(chan api.Message, 1)
- subs, err := ctx.ch.SubscribeNotification(notifChan, interfaces.NewSwInterfaceEvent)
+ sub, err := ctx.ch.SubscribeNotification(notifChan, &interfaces.SwInterfaceEvent{})
Expect(err).ShouldNot(HaveOccurred())
- // mock the notification and force its delivery
+ // mock event and force its delivery
ctx.mockVpp.MockReply(&interfaces.SwInterfaceEvent{
SwIfIndex: 2,
LinkUpDown: 1,
Expect(notif.SwIfIndex).To(BeEquivalentTo(2), "Incorrect SwIfIndex value for SwInterfaceSetFlags")
Expect(notif.LinkUpDown).To(BeEquivalentTo(1), "Incorrect LinkUpDown value for SwInterfaceSetFlags")
- ctx.ch.UnsubscribeNotification(subs)
-}
-
-func TestCheckMessageCompatibility(t *testing.T) {
- ctx := setupTest(t)
- defer ctx.teardownTest()
-
- err := ctx.ch.CheckMessageCompatibility(&interfaces.SwInterfaceSetFlags{})
+ err = sub.Unsubscribe()
Expect(err).ShouldNot(HaveOccurred())
}
+
func TestSetReplyTimeout(t *testing.T) {
ctx := setupTest(t)
defer ctx.teardownTest()
ctx.ch.SetReplyTimeout(time.Millisecond)
+ // mock reply
+ ctx.mockVpp.MockReply(&ControlPingReply{})
+
// first one request should work
- ctx.mockVpp.MockReply(&vpe.ControlPingReply{})
- err := ctx.ch.SendRequest(&vpe.ControlPing{}).ReceiveReply(&vpe.ControlPingReply{})
+ err := ctx.ch.SendRequest(&ControlPing{}).ReceiveReply(&ControlPingReply{})
Expect(err).ShouldNot(HaveOccurred())
// no other reply ready - expect timeout
- err = ctx.ch.SendRequest(&vpe.ControlPing{}).ReceiveReply(&vpe.ControlPingReply{})
+ err = ctx.ch.SendRequest(&ControlPing{}).ReceiveReply(&ControlPingReply{})
Expect(err).Should(HaveOccurred())
Expect(err.Error()).To(ContainSubstring("timeout"))
}
ctx := setupTest(t)
defer ctx.teardownTest()
- ctx.ch.SetReplyTimeout(time.Millisecond)
+ ctx.ch.SetReplyTimeout(time.Millisecond * 100)
- var msgs []api.Message
- for i := 1; i <= 3; i++ {
- msgs = append(msgs, &interfaces.SwInterfaceDetails{
- SwIfIndex: uint32(i),
+ // mock reply
+ ctx.mockVpp.MockReply(
+ &interfaces.SwInterfaceDetails{
+ SwIfIndex: 1,
InterfaceName: []byte("if-name-test"),
- })
- }
- ctx.mockVpp.MockReply(msgs...)
- ctx.mockVpp.MockReply(&vpe.ControlPingReply{})
+ },
+ &interfaces.SwInterfaceDetails{
+ SwIfIndex: 2,
+ InterfaceName: []byte("if-name-test"),
+ },
+ &interfaces.SwInterfaceDetails{
+ SwIfIndex: 3,
+ InterfaceName: []byte("if-name-test"),
+ },
+ )
+ ctx.mockVpp.MockReply(&ControlPingReply{})
cnt := 0
sendMultiRequest := func() error {
for {
msg := &interfaces.SwInterfaceDetails{}
stop, err := reqCtx.ReceiveReply(msg)
- if stop {
- break // break out of the loop
- }
if err != nil {
return err
}
+ if stop {
+ break
+ }
cnt++
}
return nil
defer ctx.teardownTest()
// invalid context 1
- reqCtx1 := &requestCtxData{}
- err := reqCtx1.ReceiveReply(&vpe.ControlPingReply{})
+ reqCtx1 := &requestCtx{}
+ err := reqCtx1.ReceiveReply(&ControlPingReply{})
Expect(err).Should(HaveOccurred())
Expect(err.Error()).To(ContainSubstring("invalid request context"))
// invalid context 2
- reqCtx2 := &multiRequestCtxData{}
- _, err = reqCtx2.ReceiveReply(&vpe.ControlPingReply{})
+ reqCtx2 := &multiRequestCtx{}
+ _, err = reqCtx2.ReceiveReply(&ControlPingReply{})
Expect(err).Should(HaveOccurred())
Expect(err.Error()).To(ContainSubstring("invalid request context"))
// NU
- reqCtx3 := &requestCtxData{}
+ reqCtx3 := &requestCtx{}
err = reqCtx3.ReceiveReply(nil)
Expect(err).Should(HaveOccurred())
Expect(err.Error()).To(ContainSubstring("invalid request context"))
SeqNum: 1,
})
}
- msgs = append(msgs, mock.MsgWithContext{Msg: &vpe.ControlPingReply{}, Multipart: true, SeqNum: 1})
+ msgs = append(msgs, mock.MsgWithContext{Msg: &ControlPingReply{}, Multipart: true, SeqNum: 1})
for i := 1; i <= 3; i++ {
msgs = append(msgs,
SeqNum: 2,
})
}
- msgs = append(msgs, mock.MsgWithContext{Msg: &vpe.ControlPingReply{}, Multipart: true, SeqNum: 2})
+ msgs = append(msgs, mock.MsgWithContext{Msg: &ControlPingReply{}, Multipart: true, SeqNum: 2})
ctx.mockVpp.MockReplyWithContext(msgs...)
msg := &interfaces.SwInterfaceDetails{}
stop, err := reqCtx.ReceiveReply(msg)
if stop {
- break // break out of the loop
+ break
}
if err != nil {
return err
ctx.ch.SetReplyTimeout(time.Millisecond)
+ // mock reply
+ ctx.mockVpp.MockReplyWithContext(mock.MsgWithContext{Msg: &ControlPingReply{}, SeqNum: 1})
// first one request should work
- ctx.mockVpp.MockReplyWithContext(mock.MsgWithContext{Msg: &vpe.ControlPingReply{}, SeqNum: 1})
- err := ctx.ch.SendRequest(&vpe.ControlPing{}).ReceiveReply(&vpe.ControlPingReply{})
+
+ err := ctx.ch.SendRequest(&ControlPing{}).ReceiveReply(&ControlPingReply{})
Expect(err).ShouldNot(HaveOccurred())
- err = ctx.ch.SendRequest(&vpe.ControlPing{}).ReceiveReply(&vpe.ControlPingReply{})
+ err = ctx.ch.SendRequest(&ControlPing{}).ReceiveReply(&ControlPingReply{})
Expect(err).Should(HaveOccurred())
Expect(err.Error()).To(ContainSubstring("timeout"))
ctx.mockVpp.MockReplyWithContext(
// simulating late reply
- mock.MsgWithContext{Msg: &vpe.ControlPingReply{}, SeqNum: 2},
+ mock.MsgWithContext{
+ Msg: &ControlPingReply{},
+ SeqNum: 2,
+ },
// normal reply for next request
- mock.MsgWithContext{Msg: &tap.TapConnectReply{}, SeqNum: 3})
-
- req := &tap.TapConnect{
- TapName: []byte("test-tap-name"),
- UseRandomMac: 1,
+ mock.MsgWithContext{
+ Msg: &interfaces.SwInterfaceSetFlagsReply{},
+ SeqNum: 3,
+ },
+ )
+
+ req := &interfaces.SwInterfaceSetFlags{
+ SwIfIndex: 1,
+ AdminUpDown: 1,
}
- reply := &tap.TapConnectReply{}
+ reply := &interfaces.SwInterfaceSetFlagsReply{}
// should succeed
err = ctx.ch.SendRequest(req).ReceiveReply(reply)
ctx.ch.SetReplyTimeout(time.Millisecond * 100)
+ // mock reply
+ ctx.mockVpp.MockReplyWithContext(mock.MsgWithContext{Msg: &ControlPingReply{}, SeqNum: 1})
+
// first one request should work
- ctx.mockVpp.MockReplyWithContext(mock.MsgWithContext{Msg: &vpe.ControlPingReply{}, SeqNum: 1})
- err := ctx.ch.SendRequest(&vpe.ControlPing{}).ReceiveReply(&vpe.ControlPingReply{})
+ err := ctx.ch.SendRequest(&ControlPing{}).ReceiveReply(&ControlPingReply{})
Expect(err).ShouldNot(HaveOccurred())
cnt := 0
msg := &interfaces.SwInterfaceDetails{}
stop, err := reqCtx.ReceiveReply(msg)
if stop {
- break // break out of the loop
+ break
}
if err != nil {
return err
SeqNum: 2,
})
}
- msgs = append(msgs, mock.MsgWithContext{Msg: &vpe.ControlPingReply{}, Multipart: true, SeqNum: 2})
+ msgs = append(msgs, mock.MsgWithContext{Msg: &ControlPingReply{}, Multipart: true, SeqNum: 2})
ctx.mockVpp.MockReplyWithContext(msgs...)
// normal reply for next request
- ctx.mockVpp.MockReplyWithContext(mock.MsgWithContext{Msg: &tap.TapConnectReply{}, SeqNum: 3})
+ ctx.mockVpp.MockReplyWithContext(mock.MsgWithContext{Msg: &interfaces.SwInterfaceSetFlagsReply{}, SeqNum: 3})
- req := &tap.TapConnect{
- TapName: []byte("test-tap-name"),
- UseRandomMac: 1,
+ req := &interfaces.SwInterfaceSetFlags{
+ SwIfIndex: 1,
+ AdminUpDown: 1,
}
- reply := &tap.TapConnectReply{}
+ reply := &interfaces.SwInterfaceSetFlagsReply{}
// should succeed
err = ctx.ch.SendRequest(req).ReceiveReply(reply)
ctx := setupTest(t)
defer ctx.teardownTest()
- // first one request should work
+ // mock reply
ctx.mockVpp.MockReply(&vpe.ShowVersionReply{})
+ ctx.mockVpp.MockReply(&vpe.ShowVersionReply{})
+
+ // first one request should work
err := ctx.ch.SendRequest(&vpe.ShowVersion{}).ReceiveReply(&vpe.ShowVersionReply{})
Expect(err).ShouldNot(HaveOccurred())
// second should fail with error invalid message ID
- ctx.mockVpp.MockReply(&vpe.ShowVersionReply{})
- err = ctx.ch.SendRequest(&vpe.ControlPing{}).ReceiveReply(&vpe.ControlPingReply{})
+ err = ctx.ch.SendRequest(&ControlPing{}).ReceiveReply(&ControlPingReply{})
Expect(err).Should(HaveOccurred())
Expect(err.Error()).To(ContainSubstring("invalid message ID"))
}