Skip to content

Instantly share code, notes, and snippets.

@fedepaol
Created April 8, 2021 09:05
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save fedepaol/f2c398d3e35b56b9da37a9f646bcafa8 to your computer and use it in GitHub Desktop.
Save fedepaol/f2c398d3e35b56b9da37a9f646bcafa8 to your computer and use it in GitHub Desktop.
Sample Go application to check connectivity binding to a device, useful for VRF
package main
import (
"context"
"flag"
"fmt"
"log"
"net"
"syscall"
)
func main() {
s := flag.Bool("server", false, "server")
address := flag.String("address", "127.0.0.1:80", "address")
vrfName := flag.String("vrf", "", "vrf")
flag.Parse()
if *s {
listen(*address, *vrfName)
} else {
dial(*address, *vrfName)
}
}
func listen(address, vrfName string) {
lc := net.ListenConfig{Control: controlOnConnSetup(vrfName)}
ln, err := lc.Listen(context.Background(), "tcp", address)
if err != nil {
log.Fatal(err)
}
ln.Accept()
fmt.Println("Accepted")
ln.Close()
}
func dial(address, vrfName string) {
d := net.Dialer{Control: controlOnConnSetup(vrfName)}
conn, err := d.Dial("tcp", address)
if err != nil {
log.Fatal(err)
}
conn.Close()
}
func controlOnConnSetup(vrfName string) func(network string, address string, c syscall.RawConn) error {
return func(network string, address string, c syscall.RawConn) error {
if vrfName == "" {
return nil
}
var operr error
fn := func(fd uintptr) {
operr = syscall.SetsockoptString(int(fd), syscall.SOL_SOCKET, syscall.SO_BINDTODEVICE, vrfName)
}
if err := c.Control(fn); err != nil {
return err
}
if operr != nil {
return operr
}
return nil
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment