ip_set.go 1.9 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798
  1. package srs
  2. import (
  3. "encoding/binary"
  4. "io"
  5. "net/netip"
  6. "os"
  7. "unsafe"
  8. M "github.com/sagernet/sing/common/metadata"
  9. "github.com/sagernet/sing/common/varbin"
  10. "go4.org/netipx"
  11. )
  12. type myIPSet struct {
  13. rr []myIPRange
  14. }
  15. type myIPRange struct {
  16. from netip.Addr
  17. to netip.Addr
  18. }
  19. func readIPSet(reader varbin.Reader) (*netipx.IPSet, error) {
  20. version, err := reader.ReadByte()
  21. if err != nil {
  22. return nil, err
  23. }
  24. if version != 1 {
  25. return nil, os.ErrInvalid
  26. }
  27. // WTF why using uint64 here
  28. var length uint64
  29. err = binary.Read(reader, binary.BigEndian, &length)
  30. if err != nil {
  31. return nil, err
  32. }
  33. mySet := &myIPSet{
  34. rr: make([]myIPRange, length),
  35. }
  36. for i := range mySet.rr {
  37. fromLen, err := binary.ReadUvarint(reader)
  38. if err != nil {
  39. return nil, err
  40. }
  41. fromBytes := make([]byte, fromLen)
  42. _, err = io.ReadFull(reader, fromBytes)
  43. if err != nil {
  44. return nil, err
  45. }
  46. toLen, err := binary.ReadUvarint(reader)
  47. if err != nil {
  48. return nil, err
  49. }
  50. toBytes := make([]byte, toLen)
  51. _, err = io.ReadFull(reader, toBytes)
  52. if err != nil {
  53. return nil, err
  54. }
  55. mySet.rr[i].from = M.AddrFromIP(fromBytes)
  56. mySet.rr[i].to = M.AddrFromIP(toBytes)
  57. }
  58. return (*netipx.IPSet)(unsafe.Pointer(mySet)), nil
  59. }
  60. func writeIPSet(writer varbin.Writer, set *netipx.IPSet) error {
  61. err := writer.WriteByte(1)
  62. if err != nil {
  63. return err
  64. }
  65. mySet := (*myIPSet)(unsafe.Pointer(set))
  66. err = binary.Write(writer, binary.BigEndian, uint64(len(mySet.rr)))
  67. if err != nil {
  68. return err
  69. }
  70. for _, rr := range mySet.rr {
  71. fromBytes := rr.from.AsSlice()
  72. _, err = varbin.WriteUvarint(writer, uint64(len(fromBytes)))
  73. if err != nil {
  74. return err
  75. }
  76. _, err = writer.Write(fromBytes)
  77. if err != nil {
  78. return err
  79. }
  80. toBytes := rr.to.AsSlice()
  81. _, err = varbin.WriteUvarint(writer, uint64(len(toBytes)))
  82. if err != nil {
  83. return err
  84. }
  85. _, err = writer.Write(toBytes)
  86. if err != nil {
  87. return err
  88. }
  89. }
  90. return nil
  91. }