9 "git.fd.io/govpp.git/api"
10 "github.com/edwarnicke/exechelper"
11 "github.com/edwarnicke/govpp/binapi/af_packet"
12 "github.com/edwarnicke/govpp/binapi/ethernet_types"
13 interfaces "github.com/edwarnicke/govpp/binapi/interface"
14 "github.com/edwarnicke/govpp/binapi/interface_types"
15 ip_types "github.com/edwarnicke/govpp/binapi/ip_types"
16 "github.com/edwarnicke/govpp/binapi/session"
17 "github.com/edwarnicke/govpp/binapi/tapv2"
18 "github.com/edwarnicke/govpp/binapi/vlib"
19 "github.com/edwarnicke/vpphelper"
23 workDir, _ = os.Getwd()
26 type ConfFn func(context.Context, api.Connection) error
31 func configureProxyTcp(ifName0, ipAddr0, ifName1, ipAddr1 string) ConfFn {
32 return func(ctx context.Context,
33 vppConn api.Connection) error {
35 _, err := configureAfPacket(ctx, vppConn, ifName0, ipAddr0)
37 fmt.Printf("failed to create af packet: %v", err)
40 _, err = configureAfPacket(ctx, vppConn, ifName1, ipAddr1)
42 fmt.Printf("failed to create af packet: %v", err)
49 func (a *Actions) ConfigureVppProxy(args []string) *ActionResult {
50 ctx, cancel := newVppContext()
53 con, vppErrCh := vpphelper.StartAndDialContext(ctx,
54 vpphelper.WithVppConfig(configTemplate),
55 vpphelper.WithRootDir(workDir))
56 exitOnErrCh(ctx, cancel, vppErrCh)
58 confFn := configureProxyTcp("vpp0", "10.0.0.2/24", "vpp1", "10.0.1.2/24")
59 err := confFn(ctx, con)
61 return NewActionResult(err, ActionResultWithDesc("configuration failed"))
63 writeSyncFile(OkResult())
68 func (a *Actions) ConfigureEnvoyProxy(args []string) *ActionResult {
73 Append("use-app-socket-api").
74 Append("evt_qs_memfd_seg").
75 Append("event-queue-length 100000").Close()
76 ctx, cancel := newVppContext()
79 con, vppErrCh := vpphelper.StartAndDialContext(ctx,
80 vpphelper.WithVppConfig(configTemplate+startup.ToString()),
81 vpphelper.WithRootDir(workDir))
82 exitOnErrCh(ctx, cancel, vppErrCh)
84 confFn := configureProxyTcp("vpp0", "10.0.0.2/24", "vpp1", "10.0.1.2/24")
85 err := confFn(ctx, con)
87 return NewActionResult(err, ActionResultWithDesc("configuration failed"))
89 err0 := exechelper.Run("chmod 777 -R " + workDir)
91 return NewActionResult(err, ActionResultWithDesc("setting permissions failed"))
93 writeSyncFile(OkResult())
98 func getArgs() string {
100 for i := 2; i < len(os.Args); i++ {
101 s = s + " " + os.Args[i]
106 func ApiCliInband(root, cmd string) *ActionResult {
107 ctx, _ := newVppContext()
108 con := vpphelper.DialContext(ctx, filepath.Join(root, "/var/run/vpp/api.sock"))
109 cliInband := vlib.CliInband{Cmd: cmd}
110 cliInbandReply, err := vlib.NewServiceClient(con).CliInband(ctx, &cliInband)
111 return NewActionResult(err, ActionResultWithStdout(cliInbandReply.Reply))
114 func (a *Actions) RunEchoSrvInternal(args []string) *ActionResult {
115 cmd := fmt.Sprintf("test echo server %s uri tcp://10.10.10.1/1234", getArgs())
116 return ApiCliInband(workDir, cmd)
119 func (a *Actions) RunEchoClnInternal(args []string) *ActionResult {
120 cmd := fmt.Sprintf("test echo client %s uri tcp://10.10.10.1/1234", getArgs())
121 return ApiCliInband(workDir, cmd)
124 func configure2vethsTopo(ifName, interfaceAddress, namespaceId string, secret uint64, optionalHardwareAddress ...string) ConfFn {
125 return func(ctx context.Context,
126 vppConn api.Connection) error {
128 var swIfIndex interface_types.InterfaceIndex
130 if optionalHardwareAddress == nil {
131 swIfIndex, err = configureAfPacket(ctx, vppConn, ifName, interfaceAddress)
133 swIfIndex, err = configureAfPacket(ctx, vppConn, ifName, interfaceAddress, optionalHardwareAddress[0])
136 fmt.Printf("failed to create af packet: %v", err)
138 _, er := session.NewServiceClient(vppConn).AppNamespaceAddDelV2(ctx, &session.AppNamespaceAddDelV2{
140 SwIfIndex: swIfIndex,
141 NamespaceID: namespaceId,
144 fmt.Printf("add app namespace: %v", err)
148 _, er1 := session.NewServiceClient(vppConn).SessionEnableDisable(ctx, &session.SessionEnableDisable{
152 fmt.Printf("session enable %v", err)
159 func (a *Actions) Configure2Veths(args []string) *ActionResult {
162 NewStanza("session").
164 Append("use-app-socket-api").Close()
166 ctx, cancel := newVppContext()
169 vppConfig, err := deserializeVppConfig(args[2])
171 return NewActionResult(err, ActionResultWithDesc("deserializing configuration failed"))
174 con, vppErrCh := vpphelper.StartAndDialContext(ctx,
175 vpphelper.WithVppConfig(vppConfig.getTemplate()+startup.ToString()),
176 vpphelper.WithRootDir(workDir))
177 exitOnErrCh(ctx, cancel, vppErrCh)
179 var fn func(context.Context, api.Connection) error
180 switch vppConfig.Variant {
182 fn = configure2vethsTopo("vppsrv", "10.10.10.1/24", "1", 1)
183 case "srv-with-preset-hw-addr":
184 fn = configure2vethsTopo("vppsrv", "10.10.10.1/24", "1", 1, "00:00:5e:00:53:01")
188 fn = configure2vethsTopo("vppcln", "10.10.10.2/24", "2", 2)
192 return NewActionResult(err, ActionResultWithDesc("configuration failed"))
194 writeSyncFile(OkResult())
199 func configureAfPacket(ctx context.Context, vppCon api.Connection,
200 name, interfaceAddress string, optionalHardwareAddress ...string) (interface_types.InterfaceIndex, error) {
202 ifaceClient := interfaces.NewServiceClient(vppCon)
203 afPacketCreate := af_packet.AfPacketCreateV2{
204 UseRandomHwAddr: true,
208 if len(optionalHardwareAddress) > 0 {
209 afPacketCreate.HwAddr, err = ethernet_types.ParseMacAddress(optionalHardwareAddress[0])
211 fmt.Printf("failed to parse mac address: %v", err)
214 afPacketCreate.UseRandomHwAddr = false
216 afPacketCreateRsp, err := af_packet.NewServiceClient(vppCon).AfPacketCreateV2(ctx, &afPacketCreate)
218 fmt.Printf("failed to create af packet: %v", err)
221 _, err = ifaceClient.SwInterfaceSetFlags(ctx, &interfaces.SwInterfaceSetFlags{
222 SwIfIndex: afPacketCreateRsp.SwIfIndex,
223 Flags: interface_types.IF_STATUS_API_FLAG_ADMIN_UP,
226 fmt.Printf("set interface state up failed: %v\n", err)
229 ipPrefix, err := ip_types.ParseAddressWithPrefix(interfaceAddress)
231 fmt.Printf("parse ip address %v\n", err)
234 ipAddress := &interfaces.SwInterfaceAddDelAddress{
236 SwIfIndex: afPacketCreateRsp.SwIfIndex,
239 _, errx := ifaceClient.SwInterfaceAddDelAddress(ctx, ipAddress)
241 fmt.Printf("add ip address %v\n", err)
244 return afPacketCreateRsp.SwIfIndex, nil
247 func (a *Actions) ConfigureHttpTps(args []string) *ActionResult {
248 ctx, cancel := newVppContext()
250 con, vppErrCh := vpphelper.StartAndDialContext(ctx,
251 vpphelper.WithVppConfig(configTemplate))
252 exitOnErrCh(ctx, cancel, vppErrCh)
254 confFn := configureProxyTcp("vpp0", "10.0.0.2/24", "vpp1", "10.0.1.2/24")
255 err := confFn(ctx, con)
257 return NewActionResult(err, ActionResultWithDesc("configuration failed"))
260 _, err = session.NewServiceClient(con).SessionEnableDisable(ctx, &session.SessionEnableDisable{
264 return NewActionResult(err, ActionResultWithDesc("configuration failed"))
266 Vppcli("", "http tps uri tcp://0.0.0.0/8080")
267 writeSyncFile(OkResult())
272 func (a *Actions) ConfigureTap(args []string) *ActionResult {
275 NewStanza("session").
277 Append("use-app-socket-api").Close()
279 ctx, cancel := newVppContext()
281 con, vppErrCh := vpphelper.StartAndDialContext(ctx,
282 vpphelper.WithRootDir(workDir),
283 vpphelper.WithVppConfig(configTemplate+startup.ToString()))
284 exitOnErrCh(ctx, cancel, vppErrCh)
285 ifaceClient := interfaces.NewServiceClient(con)
287 pref, err := ip_types.ParseIP4Prefix("10.10.10.2/24")
289 return NewActionResult(err, ActionResultWithDesc("failed to parse ip4 address"))
291 createTapReply, err := tapv2.NewServiceClient(con).TapCreateV2(ctx, &tapv2.TapCreateV2{
294 HostIP4PrefixSet: true,
295 HostIP4Prefix: ip_types.IP4AddressWithPrefix(pref),
298 return NewActionResult(err, ActionResultWithDesc("failed to configure tap"))
300 ipPrefix, err := ip_types.ParseAddressWithPrefix("10.10.10.1/24")
302 return NewActionResult(err, ActionResultWithDesc("parsing ip address failed"))
304 ipAddress := &interfaces.SwInterfaceAddDelAddress{
306 SwIfIndex: createTapReply.SwIfIndex,
309 _, errx := ifaceClient.SwInterfaceAddDelAddress(ctx, ipAddress)
311 return NewActionResult(err, ActionResultWithDesc("configuring ip address failed"))
313 _, err = ifaceClient.SwInterfaceSetFlags(ctx, &interfaces.SwInterfaceSetFlags{
314 SwIfIndex: createTapReply.SwIfIndex,
315 Flags: interface_types.IF_STATUS_API_FLAG_ADMIN_UP,
318 return NewActionResult(err, ActionResultWithDesc("failed to set interface state"))
320 _, err = session.NewServiceClient(con).SessionEnableDisable(ctx, &session.SessionEnableDisable{
324 return NewActionResult(err, ActionResultWithDesc("configuration failed"))
326 writeSyncFile(OkResult())