免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
12下一页
最近访问板块 发新帖
查看: 3785 | 回复: 11
打印 上一主题 下一主题

关于路由封锁的问题! [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2006-09-24 22:55 |只看该作者 |倒序浏览
我这里原来是1条2M的ADSL通过路由器(路由器型号:TENDA-TEI6609)共享6台机器上网,这几天电信封锁了路由上网。局域网机能上QQ,有是开网页经常弹出电信的提示(说侦查到有多台机共享上网),通过多次刷新几次可以解决网页问题,但是游戏基本上是进去就断开连接。不知道各位高手有没有遇到类似问题,有什么办法可以解决,听说是电信用了种叫“网络尖兵”的硬件。有解决办法吗?谢谢!在线等待高手指教!

论坛徽章:
0
2 [报告]
发表于 2006-09-24 23:03 |只看该作者
你用pf或者nf做个nat代理,不相信还会被发现……

论坛徽章:
0
3 [报告]
发表于 2006-09-24 23:30 |只看该作者
能不能具体点啊,小第水平有限,不太懂!谢谢

论坛徽章:
0
4 [报告]
发表于 2006-09-24 23:46 |只看该作者
很急,自己顶下!

论坛徽章:
0
5 [报告]
发表于 2006-09-24 23:54 |只看该作者
如果你用windows的话恐怕我帮不上什么忙。

只是在windows下可以使用代理。我这里有一个proxy.c程序,你可以拿去试试。

论坛徽章:
0
6 [报告]
发表于 2006-09-24 23:56 |只看该作者
好的,谢谢!

论坛徽章:
0
7 [报告]
发表于 2006-09-25 00:04 |只看该作者
原帖由 ccnuwy 于 2006-9-24 23:56 发表
好的,谢谢!


我马上贴出来。

论坛徽章:
0
8 [报告]
发表于 2006-09-25 00:10 |只看该作者
文件比较大,我把它分为了两个部分,使用的时候要合并起来。

  1. /* Simple WEB Proxy for Linux and perhaps other systems
  2. *     by Willy Tarreau
  3. *
  4. *             This program is used to redirect HTTP requests
  5. *             it receives to the right HTTP server, or to
  6. *             another instance of itself, on an other host.
  7. *             It acts like a proxy and all the Web browsers
  8. *             that will have to use it must be setup to use
  9. *             it as the HTTP Proxy. It then allows several
  10. *             hosts on a network to access the Web via one
  11. *             only server, which is particularly interesting
  12. *             in case of a server connected to an Internet
  13. *             provider via a modem with PPP.
  14. *
  15. *             One interesting aspect is that it doesn't require
  16. *             superuser privileges to run  :-)
  17. *
  18. * Authors:    based on stuff by
  19. *                 Willy Tarreau <tarreau@aemiaif.ibp.fr>
  20. *
  21. *             Multithreaded code, POST http method, SIGPIPE, fixes, ...
  22. *                    (rework)
  23. *                 Pavel Krauz <kra@fsid.cvut.cz>
  24. *
  25. *
  26. * Todo:       - Make a list of hosts and network which can be
  27. *               accessed directly, and those which need another
  28. *               proxy.
  29. *             - add an option to supply an access log with
  30. *               hostnames and requests.
  31. *
  32. *  Copyright (C) 1996  <Willy Tarreau>
  33. *  E-mail: tarreau@aemiaif.ibp.fr
  34. *
  35. *  This program is free software; you can redistribute it and/or modify
  36. *  it under the terms of the GNU General Public License as published by
  37. *  the Free Software Foundation; either version 2 of the License, or
  38. *  (at your option) any later version.
  39. *
  40. *  This program is distributed in the hope that it will be useful,
  41. *  but WITHOUT ANY WARRANTY; without even the implied warranty of
  42. *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  43. *  GNU General Public License for more details.
  44. *
  45. *  You should have received a copy of the GNU General Public License
  46. *  along with this program; if not, write to the Free Software
  47. *  Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  48. *
  49. */

  50. #include <stdio.h>
  51. #include <stdlib.h>
  52. #include <errno.h>
  53. #include <sys/types.h>
  54. #include <sys/socket.h>
  55. #include <sys/wait.h>
  56. #include <netinet/in.h>
  57. #include <netdb.h>
  58. #include <signal.h>
  59. #include <string.h>
  60. #include <unistd.h>
  61. #include <setjmp.h>
  62. #include <pthread.h>
  63. #if (defined WIN32 || defined _WIN32) && defined __CYGWIN__
  64. #include <windows.h>
  65. #endif

  66. /* default listen port */
  67. #define LISTENPORT  8080

  68. /*
  69. * default timeout for any read or write, in seconds
  70. */
  71. #define TIMEOUT_OUT                 60

  72. /*
  73. * exit timeout for idle thread
  74. */
  75. #define TIMEOUT_THREAD_EXIT        15

  76. /* length of data buffer in chars */
  77. #define LDATA       1024

  78. /* length of remote server address */
  79. #define LADR        128

  80. /* default port to connect to if unspecified */
  81. #define DEFAULTPORT 80

  82. /*
  83. * max proxy threads for requests
  84. */
  85. #if 1
  86. #define MAX_PROXY_THREADS        64
  87. #else
  88. #define MAX_PROXY_THREADS        4
  89. #endif

  90. int ConnectToProxy = 0;                /* 1 here means this program will connect to another instance of it
  91.                                    0 means we'll connect directly to the Internet */
  92. char NextProxyAdr[128];                /* the name of the host where the next instance of the program runs */
  93. int NextProxyPort;                /* and its port */
  94. int NoCache = 0;                /* if not 0, prevents web browsers from retrieving pages in their own
  95.                                    cache when the users does a "Reload" action */
  96. int timeout_out = TIMEOUT_OUT;
  97. int max_proxy_threads = MAX_PROXY_THREADS;

  98. struct th_proxy_struct {
  99.         pthread_t th;                /* only for server */

  100.         struct th_proxy_struct *next_free;
  101.         pthread_mutex_t mu;
  102.         pthread_cond_t cond;
  103.         int sock_in;
  104. };

  105. pthread_mutex_t free_q_mu;
  106. pthread_cond_t free_q_cond;
  107. struct th_proxy_struct *free_q;
  108. int thread_count = 0;        /* protected with free_q_mu */
  109. pthread_key_t key_alarm;

  110. pthread_mutex_t gethostbyname_mu;        /* used for protect gethostbyname
  111.                                          * for gethostbyname_r it isn't needed
  112.                                          */

  113. void request_alarm(int n);
  114. void server(int sockListen, struct sockaddr_in *inputSocket);
  115. void *client(struct th_proxy_struct *th_proxy);
  116. void displaysyntax(void);

  117. char *BADREQ =
  118. "HTTP/1.0 400 ERROR\r\n"
  119. "Server: thproxyd\r\n"
  120. "Content-type: text/html\r\n"
  121. "\r\n"
  122. "<HEAD><TITLE>400 Bad Request</TITLE></HEAD>\n"
  123. "<BODY><H1>400 Bad Request</H1>\n"
  124. "Your client sent a query that this server could not\n"
  125. "understand.<P>\n"
  126. "Reason: Invalid or unsupported method.<P>\n"
  127. "</BODY>\n";

  128. char *SERVERR =
  129. "HTTP/1.0 500 ERROR\r\n"
  130. "Server: thproxyd\r\n"
  131. "Content-type: text/html\r\n"
  132. "\r\n"
  133. "<HEAD><TITLE>500 Server Error</TITLE></HEAD>\n"
  134. "<BODY><H1>500 Server Error</H1>\n"
  135. "Internal proxy error while processing your query.<P>\n"
  136. "Reason: Internal proxy error.<P>\n"
  137. "</BODY>\n";

  138. char *SERVCOERR =
  139. "HTTP/1.0 500 ERROR\r\n"
  140. "Server: thproxyd\r\n"
  141. "Content-type: text/html\r\n"
  142. "\r\n"
  143. "<HEAD><TITLE>500 Server Error</TITLE></HEAD>\n"
  144. "<BODY><H1>500 Server Error</H1>\n"
  145. "Internal proxy error while processing your query.<P>\n"
  146. "Reason: Invalid connection.<P>\n"
  147. "</BODY>\n";

  148. char *SERVDNSERR =
  149. "HTTP/1.0 500 ERROR\r\n"
  150. "Server: thproxyd\r\n"
  151. "Content-type: text/html\r\n"
  152. "\r\n"
  153. "<HEAD><TITLE>500 Server Error</TITLE></HEAD>\n"
  154. "<BODY><H1>500 Server Error</H1>\n"
  155. "Internal proxy error while processing your query.<P>\n"
  156. "Reason: Bad address - DNS cann't resolve address.<P>\n"
  157. "</BODY>\n";

  158. char *SERVTIMEOUT =
  159. "HTTP/1.0 500 ERROR\r\n"
  160. "Server: thproxyd\r\n"
  161. "Content-type: text/html\r\n"
  162. "\r\n"
  163. "<HEAD><TITLE>500 Server Error</TITLE></HEAD>\n"
  164. "<BODY><H1>500 Server Error</H1>\n"
  165. "Internal proxy error while processing your query.<P>\n"
  166. "Reason: Server time out while connection establishment or data transfer.<P>\n"
  167. "</BODY>\n";

  168. char *POSTERR =
  169. "HTTP/1.0 500 ERROR\r\n"
  170. "Server: thproxyd\r\n"
  171. "Content-type: text/html\r\n"
  172. "\r\n"
  173. "<HEAD><TITLE>500 Proxy Server Error</TITLE></HEAD>\n"
  174. "<BODY><H1>500 Proxy Server Error</H1>\n"
  175. "Failed to POST.<P>\n"
  176. "Reason: post method error ???.<P>\n"
  177. "</BODY>\n";


  178. #if (defined WIN32 || defined _WIN32) && !defined CONSOLE_PROXY

  179. void real_main(
  180. # ifndef NO_ARGS
  181. int argc, char **argv);
  182. # else
  183. void);
  184. # endif

  185. int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nShowCmd)
  186. {
  187.         char buf[256]={0};
  188.         if (!hPrevInstance) {
  189.         const char args[3][256]={"./mproxy\0",NULL}; /* in fact we can custom our args */
  190. #ifndef NO_ARGS
  191.         real_main(1,args); /* a stupid idea to run on Win32 with no GUI */
  192. #else
  193.         real_main(); /* a stupid idea to run on Win32 with no GUI */
  194. #endif
  195.         return TRUE;
  196.         } else {
  197.         return FALSE;
  198.         }
  199. }

  200. void real_main(
  201. #else
  202. void      main(
  203. #endif
  204. # ifndef NO_ARGS
  205. int argc, char **argv)
  206. # else
  207. void)
  208. # endif
  209. {
  210.         int listenport = LISTENPORT;
  211.         struct sockaddr_in ListenSocket;
  212.         int sockListen;
  213.         struct sigaction sa;
  214.         int opt, val;

  215. #ifndef CUSTOM_PROXY
  216.         while ((opt = getopt(argc, argv, "p:x:t:nm:")) != -1) {
  217.                 switch (opt) {
  218.                 case ':':        /* missing parameter */
  219.                 case '?':        /* unknown option */
  220.                         displaysyntax();
  221.                         exit(1);

  222.                 case 'p':        /* port */
  223.                         listenport = atoi(optarg);
  224.                         break;

  225.                 case 'x':{        /* external proxy */
  226.                                 char *p;
  227.                                 p = strchr(optarg, ':');
  228.                                 if (p == NULL) {        /* unspecified port number. let's quit */
  229.                                         fprintf(stderr, "missing port for next proxy\n");
  230.                                         displaysyntax();
  231.                                         exit(1);
  232.                                 }
  233.                                 *(p++) = 0;        /* ends hostname */
  234.                                 NextProxyPort = atoi(p);
  235.                                 strcpy(NextProxyAdr, optarg);
  236.                                 ConnectToProxy = 1;
  237.                                 break;
  238.                         }

  239.                 case 't':        /* disconnect time-out */
  240.                         timeout_out = atoi(optarg);
  241.                         break;

  242.                 case 'n':        /* no cache */
  243.                         NoCache = 1;
  244.                         break;
  245.                 case 'm':
  246.                         max_proxy_threads = atoi(optarg);
  247.                         break;
  248.                 }                /* end of switch() */
  249.         }                        /* end of while() */
  250. #else
  251.         max_proxy_threads = 500; /* God, I just want to exceed the
  252.                                     default value defined in all
  253.                                     modern Apache distributions! */
  254.         timeout_out = 30;        /* 15 secs is too short for a
  255.                                    low-bandwidth connection */
  256.         listenport = 80;        /* I just want to start at port
  257.                                    80! Sh! This is done on the
  258.                                    computer owned by my employer! */
  259. #endif

  260.         /* initialization of listen socket */

  261.         pthread_mutex_init(&free_q_mu, NULL);
  262.         pthread_mutex_init(&gethostbyname_mu, NULL);
  263.         pthread_cond_init(&free_q_cond, NULL);
  264.         free_q = NULL;

  265.         pthread_key_create(&key_alarm, NULL);

  266.         sa.sa_handler = request_alarm;
  267.         sigemptyset(&sa.sa_mask);
  268.         sa.sa_flags = SA_RESTART;
  269.         sigaction(SIGALRM, &sa, NULL);

  270.         if ((sockListen = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP)) == -1) {
  271.                 perror("Webroute(socket)");
  272.                 exit(1);
  273.         }
  274.         val = 1;
  275.         if ((setsockopt(sockListen, SOL_SOCKET, SO_REUSEADDR, &val, sizeof(val))) == -1) {
  276.                 perror("Webroute(setsockopt)");
  277.                 exit(1);
  278.         }
  279.         bzero((char *) &ListenSocket, sizeof(ListenSocket));
  280.         ListenSocket.sin_family = AF_INET;
  281.         ListenSocket.sin_addr.s_addr = htonl(INADDR_ANY);
  282.         ListenSocket.sin_port = htons(listenport);
  283.         if (bind(sockListen, (struct sockaddr *) &ListenSocket, sizeof(ListenSocket)) == -1) {
  284.                 perror("Webroute(bind)");
  285.                 exit(1);
  286.         }
  287.         if (listen(sockListen, 5) == -1) {
  288.                 perror("Webroute(listen)");
  289.                 exit(1);
  290.         }
  291.         /* the socket is ready. Let's wait for requests ... */
  292.         /* let's close stdin, stdout, stderr to prevent messages from appearing on the console */
  293. #ifndef DEBUG
  294.         close(0);
  295.         close(1);
  296.         close(2);
  297. #endif
  298.         server(sockListen, &ListenSocket);
  299. }                                /* end of main() */

  300. static struct th_proxy_struct *new_proxy_th(void)
  301. {
  302.         struct th_proxy_struct *th_proxy;
  303.         pthread_attr_t attr;

  304.         if (!(th_proxy = malloc(sizeof(struct th_proxy_struct))))
  305.                  return NULL;
  306.         memset(th_proxy, 0, sizeof(struct th_proxy_struct));
  307.         pthread_mutex_init(&th_proxy->mu, NULL);
  308.         pthread_cond_init(&th_proxy->cond, NULL);
  309.         th_proxy->next_free = NULL;
  310.         th_proxy->sock_in = -1;
  311.         pthread_attr_init(&attr);
  312.         pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED);
  313.         if (pthread_create(&th_proxy->th, &attr, (void *((*)(void *))) client, th_proxy) != 0) {
  314.                 free(th_proxy);
  315.                 return NULL;
  316.         }
  317.         return th_proxy;
  318. }

  319. static struct th_proxy_struct *alloc_proxy_th(void)
  320. {
  321.         struct th_proxy_struct *th_proxy;

  322.         pthread_mutex_lock(&free_q_mu);
  323.         do {
  324.                 th_proxy = free_q;
  325.                 if (free_q)
  326.                         free_q = free_q->next_free;
  327.                 else {
  328.                         if (thread_count < max_proxy_threads) {
  329.                                 if ((th_proxy = new_proxy_th()))
  330.                                         thread_count++;
  331.                         }
  332.                         if (!th_proxy)
  333.                                 pthread_cond_wait(&free_q_cond, &free_q_mu);
  334.                 }
  335.         } while (!th_proxy);
  336.         pthread_mutex_unlock(&free_q_mu);
  337.         return th_proxy;
  338. }

  339. void server(int sockListen, struct sockaddr_in *inputSocket)
  340. {
  341.         int lgInputSocket;
  342.         int sockIn;
  343.         struct th_proxy_struct *th_proxy;

  344.         for (;;) {                /* infinite loop */
  345.                 lgInputSocket = sizeof(*inputSocket);
  346.                 do {
  347.                         sockIn = accept(sockListen, (struct sockaddr *) inputSocket, &lgInputSocket);
  348.                 } while (sockIn == -1 && errno == EINTR);        /* retries if interrupted */
  349.                 if (sockIn == -1) {        /* if there's an error, we exit */
  350.                         exit(1);        /* don't wait when daemon is going sick ! */
  351.                 }
  352.                 /* process request, alloc thread for it */
  353.                 th_proxy = alloc_proxy_th();
  354.                 pthread_mutex_lock(&th_proxy->mu);
  355.                 th_proxy->sock_in = sockIn;
  356.                 pthread_mutex_unlock(&th_proxy->mu);
  357.                 pthread_cond_signal(&th_proxy->cond);
  358.         }
  359. }
复制代码

[ 本帖最后由 langue 于 2006-9-25 00:18 编辑 ]

论坛徽章:
0
9 [报告]
发表于 2006-09-25 00:11 |只看该作者
第2部分

  1. #define ERR_SOCKET                -5
  2. #define ERR_GETHOSTBYNAME        -6
  3. #define ERR_CONNECT                -7
  4. #define ERR_CONNECT_TIMEOUT        -8

  5. int connectto(char *hote, int port, int sockIn)
  6. {
  7. #if 1        /*
  8.          * use gethostbyname
  9.          */
  10.         struct hostent *ServerName;
  11.         struct sockaddr_in OutputSocket;        /* output socket descriptor */
  12.         int sockOut, retval;

  13.         if ((sockOut = socket(AF_INET, SOCK_STREAM, 0)) == -1) {
  14.                 return ERR_SOCKET;
  15.         }
  16.         pthread_mutex_lock(&gethostbyname_mu);
  17.         if ((ServerName = gethostbyname(hote)) == NULL) {
  18.                 pthread_mutex_unlock(&gethostbyname_mu);
  19.                 return ERR_GETHOSTBYNAME;
  20.         }
  21.         bzero((char *) &OutputSocket, sizeof(OutputSocket));
  22.         OutputSocket.sin_family = AF_INET;
  23.         OutputSocket.sin_port = htons(port);
  24.         bcopy((char *) ServerName->h_addr,
  25.               (char *) &OutputSocket.sin_addr,
  26.               ServerName->h_length);
  27.         pthread_mutex_unlock(&gethostbyname_mu);
  28. #else
  29.         /*
  30.          * use gethostbyname_r
  31.          */
  32.         struct hostent ServerName;
  33.         struct sockaddr_in OutputSocket;        /* output socket descriptor */
  34.         int sockOut, retval;
  35.         char buf[1024];
  36.         int hst_errno;

  37.         if ((sockOut = socket(AF_INET, SOCK_STREAM, 0)) == -1) {
  38.                 return ERR_SOCKET;
  39.         }
  40.         /*
  41.          * pointers used in struct hostent ServerName will be point to space
  42.          * which user give to function (the buf variable)
  43.          */
  44.         if (gethostbyname_r(hote, &ServerName, buf, sizeof(buf), &hst_errno)
  45.             == NULL) {
  46.                 if (hst_errno == ERANGE) {
  47.                         /* the buf is to short for store all informations */
  48.                 }
  49.                 return ERR_GETHOSTBYNAME;
  50.         }
  51.         bzero((char *) &OutputSocket, sizeof(OutputSocket));
  52.         OutputSocket.sin_family = AF_INET;
  53.         OutputSocket.sin_port = htons(port);
  54.         bcopy((char *) ServerName.h_addr,
  55.               (char *) &OutputSocket.sin_addr,
  56.               ServerName.h_length);
  57. #endif
  58.         alarm(timeout_out);
  59.         retval = connect(sockOut, (struct sockaddr *) &OutputSocket, sizeof(OutputSocket));
  60.         alarm(0);
  61.         if (retval == -1) {
  62.                 close(sockOut);
  63.                 return ERR_CONNECT;
  64.         }
  65.         return sockOut;                /* connection OK */
  66. }

  67. /* this function should be called only by the child */
  68. void sayerror(char *msg, int sockIn, int sockOut)
  69. {
  70.         struct linger linger;

  71.         pthread_setspecific(key_alarm, NULL);
  72.        
  73.         write(sockIn, msg, strlen(msg));
  74.        
  75.         linger.l_onoff = 1;
  76.         linger.l_linger = 4;
  77.         setsockopt(sockIn, SOL_SOCKET, SO_LINGER, &linger, sizeof(linger));

  78.         linger.l_onoff = 1;
  79.         linger.l_linger = 1;
  80.         setsockopt(sockOut, SOL_SOCKET, SO_LINGER, &linger, sizeof(linger));

  81.         close(sockOut);
  82.         close(sockIn);
  83. #ifdef DEBUG
  84.         {
  85.                 char buf[1024];
  86.                 char *p, *end;
  87.                
  88.                 p = strstr(msg, "Reason:");
  89.                 end = strstr(p, "<P>");
  90.                 if (!p || !end)
  91.                         buf[0] = 0;
  92.                 else {
  93.                         strncpy(buf, p, end - p);
  94.                         buf[end - p] = 0;
  95.                 }
  96.                 printf("%d --- request error %s\n", sockIn, buf);
  97.         }
  98. #endif
  99. }

  100. void request_alarm(int i)
  101. {
  102.         sigjmp_buf *jmp;

  103.         if ((jmp = pthread_getspecific(key_alarm))) {
  104.                 pthread_setspecific(key_alarm, NULL);
  105.                 siglongjmp(*jmp, 1);
  106.         }
  107. }

  108. #define METHOD_GET                1
  109. #define METHOD_POST                2
  110. #define METHOD_HEAD                3

  111. int process_request(int sockIn)
  112. {
  113.         char data[LDATA];
  114.         char adr[LADR], *p;
  115.         int ldata, lreq, port, req_len, req_method;
  116.         FILE *fsin;
  117.         sigjmp_buf timeout_jmp;
  118.         int sockOut = -1;
  119.         int val;
  120.        
  121.         /* let's reopen input socket as a file */
  122.         if ((fsin = fdopen(sockIn, "rw")) == NULL)
  123.                 goto serverr;

  124.         /* prepares for connection abort */
  125.         /* avoid some sockets problems ... */
  126.         val = 1;
  127.         setsockopt(sockIn, SOL_SOCKET, SO_KEEPALIVE, &val, sizeof(val));
  128. /*
  129. * here, we'll analyze the request and get rid of "http://adr:port".
  130. * The address and port willbe duplicated and used to open the connection.
  131. */
  132.         if (sigsetjmp(timeout_jmp, 1) != 0)
  133.                 goto timeout;
  134.         pthread_setspecific(key_alarm, &timeout_jmp);

  135. #ifdef DEBUG
  136.         printf("%d --- request begin\n", sockIn);
  137. #endif
  138.         if (fgets(data, LDATA, fsin) == NULL)
  139.                 goto badreq;
  140. #ifdef DEBUG
  141.         printf("%d %s", sockIn, data);
  142. #endif
  143.         /* it's easy to log all requests here */
  144.         /* fprintf(stderr,"requete recue: %s",data);   */
  145.         ldata = strlen(data);
  146.         if (strncmp(data, "GET ", 4) == 0) {
  147.                 req_len = 4;
  148.                 req_method = METHOD_GET;
  149.         } else if (strncmp(data, "POST ", 5) == 0) {
  150.                 req_len = 5;
  151.                 req_method = METHOD_POST;
  152.         } else if (strncmp(data, "HEAD ", 5) == 0) {
  153.                 req_len = 5;
  154.                 req_method = METHOD_HEAD;
  155.         } else
  156.                 goto badreq;

  157.         if (!ConnectToProxy) {        /* if proxy-to-proxy connection, we don't modify the request */
  158.                 char *str;

  159.                 str = data + req_len;
  160.                 while (*str == ' ')
  161.                         str++;
  162.                 if (!strncmp(str, "http://", 7))
  163.                         str += 7;
  164.                 if ((p = strchr(str, '/')) != NULL) {
  165.                         strncpy(adr, str, (p - str));        /* copies addresse in adr */
  166.                         adr[p - str] = 0;
  167.                         str = p;        /* points to the rest of the request (without address) */
  168.                         lreq = ldata - (str - data);
  169.                 } else
  170.                         goto badreq;        /* if no /, error */
  171.                 /* at this stage, adr contains addr[:port], and str points to the local URL with the first  '/' */
  172.                 if (adr[0] == 0)
  173.                         goto badreq;
  174.                 p = strchr(adr, ':');
  175.                 if (p == NULL)        /* unspecified port. The default one will be used */
  176.                         port = DEFAULTPORT;
  177.                 else {                /* port is available. let's read it */
  178.                         *(p++) = 0;        /* ends hostname */
  179.                         port = atoi(p);
  180.                 }
  181.                 /* end of request analysis. The hostname is in "adr", and the port in "port" */
  182.                 if ((sockOut = connectto(adr, port, sockIn)) < 0) {
  183.                         switch (sockOut) {
  184.                                 case ERR_GETHOSTBYNAME:
  185.                                         goto servdnserr;
  186.                         }
  187.                         goto servcoerr;
  188.                 }
  189.                 /* As it becomes a local URL, we only say "GET" and the end of the request. */
  190.                 alarm(timeout_out);
  191.                 switch (req_method) {
  192.                 case METHOD_GET:
  193.                         write(sockOut, "GET ", 4);
  194.                         break;
  195.                 case METHOD_POST:
  196.                         write(sockOut, "POST ", 5);
  197.                         break;
  198.                 case METHOD_HEAD:
  199.                         write(sockOut, "HEAD ", 5);
  200.                         break;
  201.                 }
  202.                 write(sockOut, str, lreq);
  203.                 alarm(0);
  204.         } else {                /* proxy-to-proxy connection ! */
  205.                 if ((sockOut = connectto(NextProxyAdr, NextProxyPort, sockIn)) < 0) {
  206.                         switch (sockOut) {
  207.                                 case ERR_GETHOSTBYNAME:
  208.                                         goto servdnserr;
  209.                         }
  210.                         goto servcoerr;
  211.                 }
  212.                 alarm(timeout_out);
  213.                 write(sockOut, data, ldata);
  214.                 alarm(0);
  215.         }
  216.         /* now, let's copy all what we don't have copied yet */
  217.         if (req_method == METHOD_POST) {
  218.                 int c_len = 0;
  219.                 char *p;

  220.                 do {
  221.                         fgets(data, LDATA, fsin);
  222. #ifdef DEBUG
  223.                         printf("%d %s", sockIn, data);
  224. #endif
  225.                         ldata = strlen(data);
  226.                         if (strncasecmp(data, "Content-Length", 14) == 0) {
  227.                                 p = data + 14;
  228.                                 while (*p != ':')
  229.                                         p++;
  230.                                 c_len = atoi(++p);
  231.                         }
  232.                         write(sockOut, data, ldata);
  233.                 } while (ldata && data[0] != '\n' && data[0] != '\r');
  234.                 if (c_len == 0)
  235.                         goto posterr;
  236. #ifdef DEBUG
  237.                 printf("%d ", sockIn);
  238. #endif
  239.                 while (c_len) {
  240.                         ldata = fread(data, 1,
  241.                                   (LDATA > c_len ? c_len : LDATA), fsin);
  242. #ifdef DEBUG
  243.                         fwrite(data, 1, ldata, stdout);
  244. #endif
  245.                         write(sockOut, data, ldata);
  246.                         c_len -= ldata;
  247.                 }
  248. #ifdef DEBUG
  249.                 printf("\n");
  250. #endif
  251.         } else { /*
  252.                   * METHOD_GET, METHOD_HEAD
  253.                   */
  254.                 do {
  255.                         fgets(data, LDATA, fsin);
  256. #ifdef DEBUG
  257.                         printf("%d %s", sockIn, data);
  258. #endif
  259.                         ldata = strlen(data);
  260.                         if (!NoCache || (strncmp(data, "If-Mod", 6)))
  261.                                 write(sockOut, data, ldata);
  262.                 } while (ldata && data[0] != '\n' && data[0] != '\r');
  263.         }
  264.         /* retrieve data from server */
  265.         do {
  266.                 int err;
  267.                 do {
  268.                         alarm(timeout_out);
  269.                         ldata = read(sockOut, data, LDATA);
  270.                         alarm(0);
  271.                 } while (ldata == -1 && errno == EINTR);        /* retry on interrupt */
  272.                 if (ldata < 0)
  273.                         goto serverr;
  274.                 if (ldata) {        /* if ldata > 0, it's not the end yet */
  275.                         do {
  276.                                 err = write(sockIn, data, ldata);
  277.                         } while (err == -1 && errno == EINTR);
  278.                         if (errno == EPIPE) {        /* other end (client) closed the conection */
  279. #ifdef DEBUG
  280.                                 printf("%d   - client closed connection\n", sockIn);
  281. #endif
  282.                                 goto end;
  283.                         }
  284.                         if (err == -1)
  285.                                 goto serverr;
  286.                 }
  287.         } while (ldata > 0);        /* loops while more data available */

  288.       end:
  289.         close(sockIn);                /* close the sockets */
  290.         close(sockOut);
  291.         pthread_setspecific(key_alarm, NULL);
  292. #ifdef DEBUG
  293.         printf("%d --- request successful\n", sockIn);
  294. #endif
  295.         return 0;                /* no error */
  296.       badreq:
  297.         sayerror(BADREQ, sockIn, sockOut);
  298.         return -1;
  299.       serverr:
  300.         sayerror(SERVERR, sockIn, sockOut);
  301.         return -2;
  302.       timeout:
  303.         sayerror(SERVTIMEOUT, sockIn, sockOut);
  304.         return -3;
  305.       servcoerr:
  306.         sayerror(SERVCOERR, sockIn, sockOut);
  307.         return -4;
  308.       servdnserr:
  309.         sayerror(SERVDNSERR, sockIn, sockOut);
  310.         return -5;
  311.       posterr:
  312.         sayerror(POSTERR, sockIn, sockOut);
  313.         return -6;
  314. }

  315. void *client(struct th_proxy_struct *th_proxy)
  316. {
  317.         struct timespec ts;
  318.         struct timeval tv;
  319.         int retval;
  320.         struct th_proxy_struct **th;

  321.         signal(SIGPIPE, SIG_IGN);
  322.         for (;;) {
  323.                 pthread_mutex_lock(&th_proxy->mu);
  324.                 while (th_proxy->sock_in < 0) {
  325. #if 0
  326.                         pthread_cond_wait(&th_proxy->cond, &th_proxy->mu);
  327. #else
  328.                         gettimeofday(&tv, NULL);
  329.                         ts.tv_sec = tv.tv_sec + TIMEOUT_THREAD_EXIT;
  330.                         ts.tv_nsec = 0;
  331.                         retval = pthread_cond_timedwait(
  332.                                     &th_proxy->cond, &th_proxy->mu, &ts);
  333.                         if (retval == ETIMEDOUT) {
  334.                                 pthread_mutex_lock(&free_q_mu);
  335.                                 th = &free_q;
  336.                                 while (*th && *th != th_proxy)
  337.                                         th = &((*th)->next_free);
  338.                                 if (*th == th_proxy) {
  339.                                         /*
  340.                                          * remove yourself from queue
  341.                                          * and exit
  342.                                          */
  343.                                         *th = th_proxy->next_free;
  344.                                         thread_count--;
  345.                                         pthread_mutex_unlock(&free_q_mu);
  346.                                         free(th_proxy);
  347.                                         pthread_exit(0);
  348.                                 }
  349.                                 pthread_mutex_unlock(&free_q_mu);
  350.                         }
  351. #endif
  352.                 }
  353.                 pthread_mutex_unlock(&th_proxy->mu);

  354.                 pthread_setspecific(key_alarm, (void *) 0);
  355.                 process_request(th_proxy->sock_in);

  356.                 pthread_mutex_lock(&th_proxy->mu);
  357.                 th_proxy->sock_in = -1;
  358.                 pthread_mutex_unlock(&th_proxy->mu);

  359.                 pthread_mutex_lock(&free_q_mu);
  360.                 th_proxy->next_free = free_q;
  361.                 free_q = th_proxy;
  362.                 pthread_mutex_unlock(&free_q_mu);
  363.                 pthread_cond_signal(&free_q_cond);
  364.         }
  365. }

  366. /* displays the right syntax to call Webroute */
  367. void displaysyntax(void)
  368. {
  369.         fprintf(stderr, "Syntax:\n");
  370.         fprintf(stderr, "webroute [ -p port ] [ -x h:p ] [ -t timeout ] [ -m max_threads ] [ -n ]\n");
  371.         fprintf(stderr, "Available options are:\n");
  372.         fprintf(stderr, "  -p allows you to run webroute on the port <port>.\n");
  373.         fprintf(stderr, "     If you don't have superuser privileges, you must use a port > 5000.\n");
  374.         fprintf(stderr, "     The default port is %d.\n", LISTENPORT);
  375.         fprintf(stderr, "  -x enables multi-proxy feature. This means that this instance of Webroute\n");
  376.         fprintf(stderr, "     doesn't have itself access to the internet, but the one which is running\n");
  377.         fprintf(stderr, "     on port <p> of host <h> can provide an access. It's possible to chain\n");
  378.         fprintf(stderr, "     as many instances of Webroute as you want. That depends of your network\n");
  379.         fprintf(stderr, "     topology\n");
  380.         fprintf(stderr, "  -t <timeout> specifies how many seconds the connection will stay connected (or trying to connect) when\n");
  381.         fprintf(stderr, "     no data arrives. After this time, the connection will be canceled.\n");
  382.         fprintf(stderr, "  -n prevents browsers from retrieving web pages from their own cache when the\n");
  383.         fprintf(stderr, "     user asks for a \"Reload\". The page will then always be reloaded.\n");
  384.         fprintf(stderr, "  -m max count of proxy threads allocated to serve the requests\n");
  385. }
复制代码

论坛徽章:
0
10 [报告]
发表于 2006-09-25 00:14 |只看该作者
http://fresh.t-systems-sfr.com/cgi-bin/warex?linux/src/linuxthreads-0.7.1.zip

这个是原版。里面有proxy.c
而上面贴出来的是我修改过的、为了适应cygwin做的版本

[ 本帖最后由 langue 于 2006-9-25 00:15 编辑 ]
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP