Advertisement
Guest User

Havenard

a guest
Aug 19th, 2009
2,309
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 10.38 KB | None | 0 0
  1.  
  2. /*
  3. * Simple HTTP Proxy Daemon by Havenard <havenard@hotmail.com>
  4. *
  5. * Compile: gcc proxy.c -o proxy
  6. * Use: ./proxy
  7. * Or: ./proxy port
  8. * Exemple: ./proxy 1337
  9. *
  10. */
  11.  
  12. #include <stdio.h>
  13. #include <time.h>
  14. #include <signal.h>
  15. #include <sys/socket.h>
  16. #include <netinet/in.h>
  17. #include <netdb.h>
  18.  
  19. #define INVALID_SOCKET -1
  20. typedef int SOCKET;
  21.  
  22. typedef struct complete_socket { /* < 0x0001.txt */
  23. SOCKET handle;
  24. struct sockaddr_in addr;
  25. char *buffer;
  26. } complete_socket; /* > 0x0001.txt */
  27.  
  28. const char http_foot[] = "\x0d\x0a\x0d\x0a";
  29. const char http_vers[] = " HTTP/1.";
  30. const char http_200[] = "HTTP/1.0 200 OK\x0d\x0a\x0d\x0a";
  31.  
  32. long int strpos(const char *m, const char *s);
  33. int resolve(char *host);
  34.  
  35. int main(int argc, char **argv) {
  36. complete_socket s_receiver, s_client, s_remote; /* < 0x0002.txt */
  37. struct timeval tv;
  38. fd_set fdsets;
  39. int i, size;
  40. int port, s_port; /* > 0x0002.txt */
  41.  
  42. if (!((argc > 1) && ((port = atoi(argv[1])) > 0)))
  43. port = 6589; /* Se nao foi especificada porta ou a porta e' invalida, usa-se a porta padrao 6589 */
  44. bzero((char *)&s_receiver, sizeof(complete_socket));
  45. bzero((char *)&s_client, sizeof(complete_socket));
  46. bzero((char *)&s_remote, sizeof(complete_socket));
  47. s_client.buffer = (char *)malloc(8193); /* < 0x0003.txt */
  48. s_remote.buffer = (char *)malloc(8193);
  49. if ((s_client.buffer < 0) || (s_remote.buffer < 0)) {
  50. printf("[-] Unable to alloc memory.\n");
  51. exit(-1);
  52. } /* > 0x0003.txt */
  53. if ((s_receiver.handle = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP)) < 0) { /* < 0x0004.txt */
  54. printf("[-] Unable to create a socket.\n");
  55. exit(-1);
  56. } /* > 0x0004.txt */
  57.  
  58. bzero(s_client.buffer, 8193); /* Zerar a memoria dos buffers e' importante porque o programa precisara' */
  59. bzero(s_remote.buffer, 8193); /* saber quanta informacao ja' foi armazenada neles. */
  60.  
  61. s_receiver.addr.sin_family = AF_INET; /* < 0x0005.txt */
  62. s_receiver.addr.sin_addr.s_addr = htonl(INADDR_ANY);
  63. s_receiver.addr.sin_port = htons(port);
  64.  
  65. if (bind(s_receiver.handle, (struct sockaddr *)&s_receiver.addr, sizeof(struct sockaddr_in)) < 0) {
  66. printf("[-] Unable to bind socket to port %d, it may being used by another program.\n", port);
  67. exit(-1);
  68. }
  69. if (listen(s_receiver.handle, 10) < 0) {
  70. printf("[-] Unable to listen to port %d.\n", port);
  71. exit(-1);
  72. } /* > 0x0005.txt */
  73. printf("[+] Service activated successfully on port %d.\n", port);
  74. setsid(); /* < 0x0006.txt */
  75. signal(SIGCHLD, SIG_IGN);
  76. if (fork()) exit(0); /* > 0x0006.txt */
  77. while (1) { /* < 0x0007.txt */
  78. size = sizeof(struct sockaddr_in);
  79. if ((s_client.handle = accept(s_receiver.handle, (struct sockaddr *)&s_client.addr, &size)) != INVALID_SOCKET)
  80. if (!fork()) {
  81. close(s_receiver.handle); /* > 0x0007.txt */
  82. while (1) { /* < 0x0008.txt */
  83. tv.tv_sec = 1;
  84. tv.tv_usec = 0;
  85. FD_ZERO(&fdsets);
  86. FD_SET(s_client.handle, &fdsets);
  87. if (s_remote.handle > 0)
  88. FD_SET(s_remote.handle, &fdsets);
  89. if (select((s_client.handle > s_remote.handle ? s_client.handle : s_remote.handle) +1, &fdsets, NULL, NULL, &tv) < 0) {
  90. close(s_client.handle);
  91. if (s_remote.handle > 0)
  92. close(s_remote.handle);
  93. exit(0);
  94. } /* > 0x0008.txt */
  95. if (FD_ISSET(s_client.handle, &fdsets)) {
  96. if (s_remote.handle == 0) {
  97. size = strlen(s_client.buffer);
  98. size = recv(s_client.handle, &s_client.buffer[size], 8192-size, 0);
  99. if (size < 1) {
  100. close(s_client.handle);
  101. exit(0);
  102. }
  103. if (strpos(http_foot, s_client.buffer) >= 0) {
  104. if (!strncasecmp("CONNECT ", s_client.buffer, 8)) {
  105. memcpy(s_remote.buffer, &s_client.buffer[8], 8192-8);
  106. if ((i = strpos(http_vers, s_remote.buffer)) < 0) {
  107. close(s_client.handle);
  108. exit(0);
  109. }
  110. s_remote.buffer[i] = '\x00';
  111. for (i = 0; i < 512; i++)
  112. if ((s_remote.buffer[i] == '\x0d') || (s_remote.buffer[i] == '\x0a')) {
  113. s_remote.buffer[i] = '\x00';
  114. break;
  115. }
  116. for (i = strlen(s_remote.buffer); i >= 0; i--)
  117. if (s_remote.buffer[i] == '\\')
  118. s_remote.buffer[i] = '/';
  119. if (strpos("/", s_remote.buffer) >= 0) {
  120. close(s_client.handle);
  121. exit(0);
  122. }
  123. s_port = 80;
  124. if ((i = strpos(":", s_remote.buffer)) >= 0) {
  125. s_remote.buffer[i] = '\x00';
  126. i++;
  127. if ((s_port = atoi(&s_remote.buffer[i])) <= 0) {
  128. close(s_client.handle);
  129. exit(0);
  130. }
  131. }
  132. s_remote.addr.sin_family = AF_INET;
  133. s_remote.addr.sin_port = htons(s_port);
  134. s_remote.addr.sin_addr.s_addr = resolve(s_remote.buffer);
  135. if (s_remote.addr.sin_addr.s_addr <= 0) {
  136. close(s_client.handle);
  137. exit(0);
  138. }
  139. if ((s_remote.handle = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP)) < 0) {
  140. close(s_client.handle);
  141. exit(0);
  142. }
  143. if (connect(s_remote.handle, (struct sockaddr *)&s_remote.addr, sizeof(struct sockaddr_in)) < 0) {
  144. close(s_client.handle);
  145. close(s_remote.handle);
  146. exit(0);
  147. }
  148. send(s_client.handle, http_200, strlen(http_200), 0);
  149. bzero(s_client.buffer, 8192);
  150. bzero(s_remote.buffer, 8192);
  151. }
  152. else if (!strncasecmp("GET ", s_client.buffer, 4) || !strncasecmp("POST ", s_client.buffer, 5)) {
  153. if (!strncasecmp("GET ", s_client.buffer, 4))
  154. memcpy(s_remote.buffer, &s_client.buffer[4], 8192-4);
  155. else
  156. memcpy(s_remote.buffer, &s_client.buffer[5], 8192-5);
  157. if ((i = strpos(http_vers, s_remote.buffer)) < 0) {
  158. close(s_client.handle);
  159. exit(0);
  160. }
  161. s_remote.buffer[i] = '\x00';
  162. for (i = 0; i < 512; i++)
  163. if ((s_remote.buffer[i] == '\x0d') || (s_remote.buffer[i] == '\x0a')) {
  164. s_remote.buffer[i] = '\x00';
  165. break;
  166. }
  167. for (i = strlen(s_remote.buffer); i >= 0; i--)
  168. if (s_remote.buffer[i] == '\\')
  169. s_remote.buffer[i] = '/';
  170. if (s_remote.buffer[0] == '/') {
  171. close(s_client.handle);
  172. exit(0);
  173. }
  174. if (strncasecmp("http://", s_remote.buffer, 7)) {
  175. close(s_client.handle);
  176. exit(0);
  177. }
  178. for (i = strlen(s_remote.buffer); i >= 0; i--)
  179. if (s_remote.buffer[i] == '/')
  180. s_remote.buffer[i] = '\x00';
  181. s_port = 80;
  182. if ((i = strpos(":", &s_remote.buffer[7])) >= 0) {
  183. i += 7;
  184. s_remote.buffer[i] = '\x00';
  185. i++;
  186. if ((s_port = atoi(&s_remote.buffer[i])) <= 0) {
  187. close(s_client.handle);
  188. exit(0);
  189. }
  190. }
  191. s_remote.addr.sin_family = AF_INET;
  192. s_remote.addr.sin_port = htons(s_port);
  193. s_remote.addr.sin_addr.s_addr = resolve(&s_remote.buffer[7]);
  194. if (s_remote.addr.sin_addr.s_addr <= 0) {
  195. close(s_client.handle);
  196. exit(0);
  197. }
  198. size = (toupper(s_client.buffer[0]) == 'G' ? 11 : 12);
  199. i = strpos("/", &s_client.buffer[size]);
  200. if (i < 0) {
  201. close(s_client.handle);
  202. exit(0);
  203. }
  204. if ((s_remote.handle = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP)) < 0) {
  205. close(s_client.handle);
  206. exit(0);
  207. }
  208. if (connect(s_remote.handle, (struct sockaddr *)&s_remote.addr, sizeof(struct sockaddr_in)) < 0) {
  209. close(s_client.handle);
  210. close(s_remote.handle);
  211. exit(0);
  212. }
  213. memcpy(s_remote.buffer, s_client.buffer, (size == 11 ? 4 : 5));
  214. memcpy(&s_remote.buffer[(size == 11 ? 4 : 5)], &s_client.buffer[i+size], 8192-(i+size));
  215. send(s_remote.handle, s_remote.buffer, strlen(s_remote.buffer), 0);
  216. }
  217. else {
  218. close(s_client.handle);
  219. exit(0);
  220. }
  221. }
  222. else if (s_client.buffer[8191] != '\x00') {
  223. close(s_client.handle);
  224. exit(0);
  225. }
  226. }
  227. else {
  228. size = recv(s_client.handle, s_client.buffer, 8192, 0);
  229. if (size > 0)
  230. send(s_remote.handle, s_client.buffer, size, 0);
  231. else {
  232. close(s_client.handle);
  233. close(s_remote.handle);
  234. exit(0);
  235. }
  236. }
  237. }
  238. if ((s_remote.handle > 0) && FD_ISSET(s_remote.handle, &fdsets)) {
  239. size = recv(s_remote.handle, s_remote.buffer, 8192, 0);
  240. if (size > 0)
  241. send(s_client.handle, s_remote.buffer, size, 0);
  242. else {
  243. close(s_client.handle);
  244. close(s_remote.handle);
  245. exit(0);
  246. }
  247. }
  248. }
  249. exit(0);
  250. }
  251. close(s_client.handle);
  252. }
  253. }
  254.  
  255. int resolve(char *host) {
  256. int result;
  257. struct hostent *dnslook;
  258. if ((result = inet_addr(host)) == INADDR_NONE) {
  259. if ((dnslook = gethostbyname(host)) == NULL)
  260. return 0;
  261. return ((struct in_addr *)(dnslook->h_addr))->s_addr;
  262. }
  263. return result;
  264. }
  265.  
  266. long int strpos(const char *m, const char *s) {
  267. long int i, len, end;
  268. len = strlen(m);
  269. end = strlen(s) - len +1;
  270. if (end >= len)
  271. for (i = 0; i < end; i++)
  272. if (!strncmp(m, &s[i], len))
  273. return i;
  274. return -1;
  275. }
  276.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement