github.com/jshiv/can-go@v0.2.1-0.20210224011015-069e90e90bdf/pkg/socketcan/dialraw_linux.go (about) 1 // +build linux 2 // +build go1.12 3 4 package socketcan 5 6 import ( 7 "fmt" 8 "net" 9 "os" 10 11 "golang.org/x/sys/unix" 12 ) 13 14 func dialRaw(device string) (conn net.Conn, err error) { 15 defer func() { 16 if err != nil { 17 err = &net.OpError{Op: "dial", Net: canRawNetwork, Addr: &canRawAddr{device: device}, Err: err} 18 } 19 }() 20 ifi, err := net.InterfaceByName(device) 21 if err != nil { 22 return nil, fmt.Errorf("interface %s: %w", device, err) 23 } 24 fd, err := unix.Socket(unix.AF_CAN, unix.SOCK_RAW, unix.CAN_RAW) 25 if err != nil { 26 return nil, fmt.Errorf("socket: %w", err) 27 } 28 // put fd in non-blocking mode so the created file will be registered by the runtime poller (Go >= 1.12) 29 if err := unix.SetNonblock(fd, true); err != nil { 30 return nil, fmt.Errorf("set nonblock: %w", err) 31 } 32 if err := unix.Bind(fd, &unix.SockaddrCAN{Ifindex: ifi.Index}); err != nil { 33 return nil, fmt.Errorf("bind: %w", err) 34 } 35 return &fileConn{ra: &canRawAddr{device: device}, f: os.NewFile(uintptr(fd), "can")}, nil 36 }