go.ligato.io/vpp-agent/v3@v3.5.0/examples/tutorials/07_vpp-connection/main.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 main 16 17 import ( 18 "log" 19 "time" 20 21 "go.fd.io/govpp/api" 22 "go.fd.io/govpp/binapi/ethernet_types" 23 interfaces "go.fd.io/govpp/binapi/interface" 24 "go.ligato.io/cn-infra/v2/agent" 25 26 "go.ligato.io/vpp-agent/v3/plugins/govppmux" 27 ) 28 29 func main() { 30 // Create an instance of our plugin. 31 p := new(HelloWorld) 32 p.GoVPPMux = &govppmux.DefaultPlugin 33 34 // Create new agent with our plugin instance. 35 a := agent.NewAgent(agent.AllPlugins(p)) 36 37 // Run starts the agent with plugins, wait until shutdown 38 // and then stops the agent and its plugins. 39 if err := a.Start(); err != nil { 40 log.Fatalln(err) 41 } 42 43 p.syncVppCall() 44 p.asyncVppCall() 45 p.multiRequestCall() 46 47 if err := a.Stop(); err != nil { 48 log.Fatalln(err) 49 } 50 } 51 52 // HelloWorld represents our plugin. 53 type HelloWorld struct { 54 vppChan api.Channel 55 56 GoVPPMux govppmux.API 57 } 58 59 // String is used to identify the plugin by giving it name. 60 func (p *HelloWorld) String() string { 61 return "HelloWorld" 62 } 63 64 // Init is executed on agent initialization. 65 func (p *HelloWorld) Init() (err error) { 66 log.Println("Hello World!") 67 68 if p.vppChan, err = p.GoVPPMux.NewAPIChannel(); err != nil { 69 panic(err) 70 } 71 72 return nil 73 } 74 75 func (p *HelloWorld) syncVppCall() { 76 // prepare request 77 mac, err := ethernet_types.ParseMacAddress("00:00:00:00:00:01") 78 if err != nil { 79 log.Panicf("ParseMacAddress failed: %v", err) 80 } 81 request := &interfaces.CreateLoopback{ 82 MacAddress: mac, 83 } 84 // prepare reply 85 reply := &interfaces.CreateLoopbackReply{} 86 // send request and obtain reply 87 err = p.vppChan.SendRequest(request).ReceiveReply(reply) 88 if err != nil { 89 panic(err) 90 } 91 // check return value 92 if reply.Retval != 0 { 93 log.Panicf("Sync call loopback create returned %d", reply.Retval) 94 } 95 96 log.Printf("Sync call created loopback with index %d", reply.SwIfIndex) 97 } 98 99 func (p *HelloWorld) asyncVppCall() { 100 // prepare requests 101 mac1, err := ethernet_types.ParseMacAddress("00:00:00:00:00:02") 102 if err != nil { 103 log.Panicf("ParseMacAddress failed: %v", err) 104 } 105 mac2, err := ethernet_types.ParseMacAddress("00:00:00:00:00:03") 106 if err != nil { 107 log.Panicf("ParseMacAddress failed: %v", err) 108 } 109 request1 := &interfaces.CreateLoopback{ 110 MacAddress: mac1, 111 } 112 request2 := &interfaces.CreateLoopback{ 113 MacAddress: mac2, 114 } 115 116 // obtain contexts 117 reqCtx1 := p.vppChan.SendRequest(request1) 118 reqCtx2 := p.vppChan.SendRequest(request2) 119 120 // wait a bit 121 time.Sleep(2 * time.Second) 122 123 // prepare replies 124 reply1 := &interfaces.CreateLoopbackReply{} 125 reply2 := &interfaces.CreateLoopbackReply{} 126 127 // receive replies 128 if err := reqCtx1.ReceiveReply(reply1); err != nil { 129 panic(err) 130 } 131 if err := reqCtx2.ReceiveReply(reply2); err != nil { 132 panic(err) 133 } 134 135 log.Printf("Async call created loopbacks with indexes %d and %d", 136 reply1.SwIfIndex, reply2.SwIfIndex) 137 } 138 139 func (p *HelloWorld) multiRequestCall() { 140 // prepare request 141 request := &interfaces.SwInterfaceDump{} 142 multiReqCtx := p.vppChan.SendMultiRequest(request) 143 144 // read replies in the loop 145 for { 146 reply := &interfaces.SwInterfaceDetails{} 147 last, err := multiReqCtx.ReceiveReply(reply) 148 if err != nil { 149 panic(err) 150 } 151 if last { 152 break 153 } 154 log.Printf("received VPP interface with index %d", reply.SwIfIndex) 155 } 156 } 157 158 // Close is executed on agent shutdown. 159 func (p *HelloWorld) Close() error { 160 p.vppChan.Close() 161 log.Println("Goodbye World!") 162 return nil 163 }