common.go 9.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376
  1. package conf
  2. import (
  3. "encoding/json"
  4. "fmt"
  5. "strconv"
  6. "strings"
  7. "github.com/xtls/xray-core/common/errors"
  8. "github.com/xtls/xray-core/common/net"
  9. "github.com/xtls/xray-core/common/platform"
  10. "github.com/xtls/xray-core/common/protocol"
  11. )
  12. type StringList []string
  13. func NewStringList(raw []string) *StringList {
  14. list := StringList(raw)
  15. return &list
  16. }
  17. func (v StringList) Len() int {
  18. return len(v)
  19. }
  20. // UnmarshalJSON implements encoding/json.Unmarshaler.UnmarshalJSON
  21. func (v *StringList) UnmarshalJSON(data []byte) error {
  22. var strarray []string
  23. if err := json.Unmarshal(data, &strarray); err == nil {
  24. *v = *NewStringList(strarray)
  25. return nil
  26. }
  27. var rawstr string
  28. if err := json.Unmarshal(data, &rawstr); err == nil {
  29. strlist := strings.Split(rawstr, ",")
  30. *v = *NewStringList(strlist)
  31. return nil
  32. }
  33. return errors.New("unknown format of a string list: " + string(data))
  34. }
  35. type Address struct {
  36. net.Address
  37. }
  38. // MarshalJSON implements encoding/json.Marshaler.MarshalJSON
  39. func (v *Address) MarshalJSON() ([]byte, error) {
  40. return json.Marshal(v.Address.String())
  41. }
  42. // UnmarshalJSON implements encoding/json.Unmarshaler.UnmarshalJSON
  43. func (v *Address) UnmarshalJSON(data []byte) error {
  44. var rawStr string
  45. if err := json.Unmarshal(data, &rawStr); err != nil {
  46. return errors.New("invalid address: ", string(data)).Base(err)
  47. }
  48. if strings.HasPrefix(rawStr, "env:") {
  49. rawStr = platform.NewEnvFlag(rawStr[4:]).GetValue(func() string { return "" })
  50. }
  51. v.Address = net.ParseAddress(rawStr)
  52. return nil
  53. }
  54. func (v *Address) Build() *net.IPOrDomain {
  55. return net.NewIPOrDomain(v.Address)
  56. }
  57. type Network string
  58. func (v Network) Build() net.Network {
  59. switch strings.ToLower(string(v)) {
  60. case "tcp":
  61. return net.Network_TCP
  62. case "udp":
  63. return net.Network_UDP
  64. case "unix":
  65. return net.Network_UNIX
  66. default:
  67. return net.Network_Unknown
  68. }
  69. }
  70. type NetworkList []Network
  71. // UnmarshalJSON implements encoding/json.Unmarshaler.UnmarshalJSON
  72. func (v *NetworkList) UnmarshalJSON(data []byte) error {
  73. var strarray []Network
  74. if err := json.Unmarshal(data, &strarray); err == nil {
  75. nl := NetworkList(strarray)
  76. *v = nl
  77. return nil
  78. }
  79. var rawstr Network
  80. if err := json.Unmarshal(data, &rawstr); err == nil {
  81. strlist := strings.Split(string(rawstr), ",")
  82. nl := make([]Network, len(strlist))
  83. for idx, network := range strlist {
  84. nl[idx] = Network(network)
  85. }
  86. *v = nl
  87. return nil
  88. }
  89. return errors.New("unknown format of a string list: " + string(data))
  90. }
  91. func (v *NetworkList) Build() []net.Network {
  92. if v == nil {
  93. return []net.Network{net.Network_TCP}
  94. }
  95. list := make([]net.Network, 0, len(*v))
  96. for _, network := range *v {
  97. list = append(list, network.Build())
  98. }
  99. return list
  100. }
  101. func parseIntPort(data []byte) (net.Port, error) {
  102. var intPort uint32
  103. err := json.Unmarshal(data, &intPort)
  104. if err != nil {
  105. return net.Port(0), err
  106. }
  107. return net.PortFromInt(intPort)
  108. }
  109. func parseStringPort(s string) (net.Port, net.Port, error) {
  110. if strings.HasPrefix(s, "env:") {
  111. s = platform.NewEnvFlag(s[4:]).GetValue(func() string { return "" })
  112. }
  113. pair := strings.SplitN(s, "-", 2)
  114. if len(pair) == 0 {
  115. return net.Port(0), net.Port(0), errors.New("invalid port range: ", s)
  116. }
  117. if len(pair) == 1 {
  118. port, err := net.PortFromString(pair[0])
  119. return port, port, err
  120. }
  121. fromPort, err := net.PortFromString(pair[0])
  122. if err != nil {
  123. return net.Port(0), net.Port(0), err
  124. }
  125. toPort, err := net.PortFromString(pair[1])
  126. if err != nil {
  127. return net.Port(0), net.Port(0), err
  128. }
  129. return fromPort, toPort, nil
  130. }
  131. func parseJSONStringPort(data []byte) (net.Port, net.Port, error) {
  132. var s string
  133. err := json.Unmarshal(data, &s)
  134. if err != nil {
  135. return net.Port(0), net.Port(0), err
  136. }
  137. return parseStringPort(s)
  138. }
  139. type PortRange struct {
  140. From uint32
  141. To uint32
  142. }
  143. func (v *PortRange) Build() *net.PortRange {
  144. return &net.PortRange{
  145. From: v.From,
  146. To: v.To,
  147. }
  148. }
  149. // MarshalJSON implements encoding/json.Marshaler.MarshalJSON
  150. func (v *PortRange) MarshalJSON() ([]byte, error) {
  151. return json.Marshal(v.String())
  152. }
  153. func (port *PortRange) String() string {
  154. if port.From == port.To {
  155. return strconv.Itoa(int(port.From))
  156. } else {
  157. return fmt.Sprintf("%d-%d", port.From, port.To)
  158. }
  159. }
  160. // UnmarshalJSON implements encoding/json.Unmarshaler.UnmarshalJSON
  161. func (v *PortRange) UnmarshalJSON(data []byte) error {
  162. port, err := parseIntPort(data)
  163. if err == nil {
  164. v.From = uint32(port)
  165. v.To = uint32(port)
  166. return nil
  167. }
  168. from, to, err := parseJSONStringPort(data)
  169. if err == nil {
  170. v.From = uint32(from)
  171. v.To = uint32(to)
  172. if v.From > v.To {
  173. return errors.New("invalid port range ", v.From, " -> ", v.To)
  174. }
  175. return nil
  176. }
  177. return errors.New("invalid port range: ", string(data))
  178. }
  179. type PortList struct {
  180. Range []PortRange
  181. }
  182. func (list *PortList) Build() *net.PortList {
  183. portList := new(net.PortList)
  184. for _, r := range list.Range {
  185. portList.Range = append(portList.Range, r.Build())
  186. }
  187. return portList
  188. }
  189. // MarshalJSON implements encoding/json.Marshaler.MarshalJSON
  190. func (v *PortList) MarshalJSON() ([]byte, error) {
  191. portStr := v.String()
  192. port, err := strconv.Atoi(portStr)
  193. if err == nil {
  194. return json.Marshal(port)
  195. } else {
  196. return json.Marshal(portStr)
  197. }
  198. }
  199. func (v PortList) String() string {
  200. ports := []string{}
  201. for _, port := range v.Range {
  202. ports = append(ports, port.String())
  203. }
  204. return strings.Join(ports, ",")
  205. }
  206. // UnmarshalJSON implements encoding/json.Unmarshaler.UnmarshalJSON
  207. func (list *PortList) UnmarshalJSON(data []byte) error {
  208. var listStr string
  209. var number uint32
  210. if err := json.Unmarshal(data, &listStr); err != nil {
  211. if err2 := json.Unmarshal(data, &number); err2 != nil {
  212. return errors.New("invalid port: ", string(data)).Base(err2)
  213. }
  214. }
  215. rangelist := strings.Split(listStr, ",")
  216. for _, rangeStr := range rangelist {
  217. trimmed := strings.TrimSpace(rangeStr)
  218. if len(trimmed) > 0 {
  219. if strings.Contains(trimmed, "-") || strings.Contains(trimmed, "env:") {
  220. from, to, err := parseStringPort(trimmed)
  221. if err != nil {
  222. return errors.New("invalid port range: ", trimmed).Base(err)
  223. }
  224. list.Range = append(list.Range, PortRange{From: uint32(from), To: uint32(to)})
  225. } else {
  226. port, err := parseIntPort([]byte(trimmed))
  227. if err != nil {
  228. return errors.New("invalid port: ", trimmed).Base(err)
  229. }
  230. list.Range = append(list.Range, PortRange{From: uint32(port), To: uint32(port)})
  231. }
  232. }
  233. }
  234. if number != 0 {
  235. list.Range = append(list.Range, PortRange{From: number, To: number})
  236. }
  237. return nil
  238. }
  239. type User struct {
  240. EmailString string `json:"email"`
  241. LevelByte byte `json:"level"`
  242. }
  243. func (v *User) Build() *protocol.User {
  244. return &protocol.User{
  245. Email: v.EmailString,
  246. Level: uint32(v.LevelByte),
  247. }
  248. }
  249. // Int32Range deserializes from "1-2" or 1, so can deserialize from both int and number.
  250. // Negative integers can be passed as sentinel values, but do not parse as ranges.
  251. // Value will be exchanged if From > To, use .Left and .Right to get original value if need.
  252. type Int32Range struct {
  253. Left int32
  254. Right int32
  255. From int32
  256. To int32
  257. }
  258. // MarshalJSON implements encoding/json.Marshaler.MarshalJSON
  259. func (v *Int32Range) MarshalJSON() ([]byte, error) {
  260. return json.Marshal(v.String())
  261. }
  262. func (v Int32Range) String() string {
  263. if v.Left == v.Right {
  264. return strconv.Itoa(int(v.Left))
  265. } else {
  266. return fmt.Sprintf("%d-%d", v.Left, v.Right)
  267. }
  268. }
  269. // UnmarshalJSON implements encoding/json.Unmarshaler.UnmarshalJSON
  270. func (v *Int32Range) UnmarshalJSON(data []byte) error {
  271. defer v.ensureOrder()
  272. var str string
  273. var rawint int32
  274. if err := json.Unmarshal(data, &str); err == nil {
  275. left, right, err := ParseRangeString(str)
  276. if err == nil {
  277. v.Left, v.Right = int32(left), int32(right)
  278. return nil
  279. }
  280. } else if err := json.Unmarshal(data, &rawint); err == nil {
  281. v.Left = rawint
  282. v.Right = rawint
  283. return nil
  284. }
  285. return errors.New("Invalid integer range, expected either string of form \"1-2\" or plain integer.")
  286. }
  287. // ensureOrder() gives value to .From & .To and make sure .From < .To
  288. func (r *Int32Range) ensureOrder() {
  289. r.From, r.To = r.Left, r.Right
  290. if r.From > r.To {
  291. r.From, r.To = r.To, r.From
  292. }
  293. }
  294. // "-114-514" → ["-114","514"]
  295. // "-1919--810" → ["-1919","-810"]
  296. func splitFromSecondDash(s string) []string {
  297. parts := strings.SplitN(s, "-", 3)
  298. if len(parts) < 3 {
  299. return []string{s}
  300. }
  301. return []string{parts[0] + "-" + parts[1], parts[2]}
  302. }
  303. // Parse rang in string. Support negative number.
  304. // eg: "114-514" "-114-514" "-1919--810" "114514" ""(return 0)
  305. func ParseRangeString(str string) (int, int, error) {
  306. // for number in string format like "114" or "-1"
  307. if value, err := strconv.Atoi(str); err == nil {
  308. return value, value, nil
  309. }
  310. // for empty "", we treat it as 0
  311. if str == "" {
  312. return 0, 0, nil
  313. }
  314. // for range value, like "114-514"
  315. var pair []string
  316. // Process sth like "-114-514" "-1919--810"
  317. if strings.HasPrefix(str, "-") {
  318. pair = splitFromSecondDash(str)
  319. } else {
  320. pair = strings.SplitN(str, "-", 2)
  321. }
  322. if len(pair) == 2 {
  323. left, err := strconv.Atoi(pair[0])
  324. right, err2 := strconv.Atoi(pair[1])
  325. if err == nil && err2 == nil {
  326. return left, right, nil
  327. }
  328. }
  329. return 0, 0, errors.New("invalid range string: ", str)
  330. }