proxy_linux.go 2.0 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788
  1. //go:build linux && !android
  2. package settings
  3. import (
  4. "os"
  5. "os/exec"
  6. "strings"
  7. "github.com/sagernet/sing-box/log"
  8. "github.com/sagernet/sing/common"
  9. E "github.com/sagernet/sing/common/exceptions"
  10. F "github.com/sagernet/sing/common/format"
  11. )
  12. var (
  13. hasGSettings bool
  14. sudoUser string
  15. )
  16. func init() {
  17. hasGSettings = common.Error(exec.LookPath("gsettings")) == nil
  18. if os.Getuid() == 0 {
  19. sudoUser = os.Getenv("SUDO_USER")
  20. }
  21. }
  22. func runAsUser(name string, args ...string) error {
  23. if os.Getuid() != 0 {
  24. return runCommand(name, args...)
  25. } else if sudoUser != "" {
  26. return runCommand("su", "-", sudoUser, "-c", F.ToString(name, " ", strings.Join(args, " ")))
  27. } else {
  28. return E.New("set system proxy: unable to set as root")
  29. }
  30. }
  31. func ClearSystemProxy() error {
  32. if hasGSettings {
  33. return runAsUser("gsettings", "set", "org.gnome.system.proxy", "mode", "none")
  34. }
  35. return nil
  36. }
  37. func SetSystemProxy(port uint16, mixed bool) error {
  38. if hasGSettings {
  39. err := runAsUser("gsettings", "set", "org.gnome.system.proxy.http", "enabled", "true")
  40. if err != nil {
  41. return err
  42. }
  43. if mixed {
  44. err = setGnomeProxy(port, "ftp", "http", "https", "socks")
  45. if err != nil {
  46. return err
  47. }
  48. } else {
  49. err = setGnomeProxy(port, "http", "https")
  50. if err != nil {
  51. return err
  52. }
  53. }
  54. err = runAsUser("gsettings", "set", "org.gnome.system.proxy", "use-same-proxy", F.ToString(mixed))
  55. if err != nil {
  56. return err
  57. }
  58. err = runAsUser("gsettings", "set", "org.gnome.system.proxy", "mode", "manual")
  59. if err != nil {
  60. return err
  61. }
  62. } else {
  63. log.Warn("set system proxy: unsupported desktop environment")
  64. }
  65. return nil
  66. }
  67. func setGnomeProxy(port uint16, proxyTypes ...string) error {
  68. for _, proxyType := range proxyTypes {
  69. err := runAsUser("gsettings", "set", "org.gnome.system.proxy."+proxyType, "host", "127.0.0.1")
  70. if err != nil {
  71. return err
  72. }
  73. err = runAsUser("gsettings", "set", "org.gnome.system.proxy."+proxyType, "port", F.ToString(port))
  74. if err != nil {
  75. return err
  76. }
  77. }
  78. return nil
  79. }