sourceForgeSender.go 1.1 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455
  1. // +build linux
  2. package udp
  3. import (
  4. "net"
  5. "os"
  6. "syscall"
  7. )
  8. //Currently, Only IPv4 Forge is supported
  9. func TransmitSocket(src net.Addr, dst net.Addr) (net.Conn, error) {
  10. var fd int
  11. var err error
  12. fd, err = syscall.Socket(syscall.AF_INET, syscall.SOCK_DGRAM, 0)
  13. if err != nil {
  14. return nil, err
  15. }
  16. err = syscall.SetsockoptInt(fd, syscall.SOL_SOCKET, syscall.SO_REUSEADDR, 1)
  17. if err != nil {
  18. return nil, err
  19. }
  20. err = syscall.SetsockoptInt(fd, syscall.SOL_IP, syscall.IP_TRANSPARENT, 1)
  21. if err != nil {
  22. return nil, err
  23. }
  24. ip := src.(*net.UDPAddr).IP.To4()
  25. var ip2 [4]byte
  26. copy(ip2[:], ip)
  27. srcaddr := syscall.SockaddrInet4{}
  28. srcaddr.Addr = ip2
  29. srcaddr.Port = src.(*net.UDPAddr).Port
  30. err = syscall.Bind(fd, &srcaddr)
  31. if err != nil {
  32. return nil, err
  33. }
  34. ipd := dst.(*net.UDPAddr).IP.To4()
  35. var ip2d [4]byte
  36. copy(ip2d[:], ipd)
  37. dstaddr := syscall.SockaddrInet4{}
  38. dstaddr.Addr = ip2d
  39. dstaddr.Port = dst.(*net.UDPAddr).Port
  40. err = syscall.Connect(fd, &dstaddr)
  41. if err != nil {
  42. return nil, err
  43. }
  44. fdf := os.NewFile(uintptr(fd), "/dev/udp/")
  45. c, err := net.FileConn(fdf)
  46. if err != nil {
  47. return nil, err
  48. }
  49. return c, nil
  50. }