proxy.cc 2.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687
  1. // -*- mode: cpp; mode: fold -*-
  2. // Description /*{{{*/
  3. /* ######################################################################
  4. Proxy - Proxy releated functions
  5. ##################################################################### */
  6. /*}}}*/
  7. // Include Files /*{{{*/
  8. #include<apt-pkg/configuration.h>
  9. #include<apt-pkg/error.h>
  10. #include<apt-pkg/fileutl.h>
  11. #include<apt-pkg/strutl.h>
  12. #include<iostream>
  13. #include <unistd.h>
  14. #include "proxy.h"
  15. // AutoDetectProxy - auto detect proxy /*{{{*/
  16. // ---------------------------------------------------------------------
  17. /* */
  18. bool AutoDetectProxy(URI &URL)
  19. {
  20. // we support both http/https debug options
  21. bool Debug = _config->FindB("Debug::Acquire::"+URL.Access,false);
  22. // the user already explicitly set a proxy for this host
  23. if(_config->Find("Acquire::"+URL.Access+"::proxy::"+URL.Host, "") != "")
  24. return true;
  25. // option is "Acquire::http::Proxy-Auto-Detect" but we allow the old
  26. // name without the dash ("-")
  27. std::string AutoDetectProxyCmd = _config->Find("Acquire::"+URL.Access+"::Proxy-Auto-Detect",
  28. _config->Find("Acquire::"+URL.Access+"::ProxyAutoDetect"));
  29. if (AutoDetectProxyCmd.empty())
  30. return true;
  31. if (Debug)
  32. std::clog << "Using auto proxy detect command: " << AutoDetectProxyCmd << std::endl;
  33. int Pipes[2] = {-1,-1};
  34. if (pipe(Pipes) != 0)
  35. return _error->Errno("pipe", "Failed to create Pipe");
  36. pid_t Process = ExecFork();
  37. if (Process == 0)
  38. {
  39. close(Pipes[0]);
  40. dup2(Pipes[1],STDOUT_FILENO);
  41. SetCloseExec(STDOUT_FILENO,false);
  42. std::string foo = URL;
  43. const char *Args[4];
  44. Args[0] = AutoDetectProxyCmd.c_str();
  45. Args[1] = foo.c_str();
  46. Args[2] = 0;
  47. execv(Args[0],(char **)Args);
  48. std::cerr << "Failed to exec method " << Args[0] << std::endl;
  49. _exit(100);
  50. }
  51. char buf[512];
  52. int InFd = Pipes[0];
  53. close(Pipes[1]);
  54. int res = read(InFd, buf, sizeof(buf)-1);
  55. ExecWait(Process, "ProxyAutoDetect", true);
  56. if (res < 0)
  57. return _error->Errno("read", "Failed to read");
  58. if (res == 0)
  59. return _error->Warning("ProxyAutoDetect returned no data");
  60. // add trailing \0
  61. buf[res] = 0;
  62. if (Debug)
  63. std::clog << "auto detect command returned: '" << buf << "'" << std::endl;
  64. if (strstr(buf, URL.Access.c_str()) == buf)
  65. _config->Set("Acquire::"+URL.Access+"::proxy::"+URL.Host, _strstrip(buf));
  66. return true;
  67. }
  68. /*}}}*/