title: In C: Proxy HTTP requests to another server
body: <p>I'm trying to proxy HTTP requests to another HTTP server. The hostname and port number of the upstream HTTP server, respectively, are server_proxy_hostname and server_proxy_port.</p>
  
  <p><strong>The first step</strong> is to do a DNS lookup of the server_proxy_hostname.</p>
  
  <p><strong>Secondly</strong>, I create a network socket and connet it to the IP address I got from DNS.</p>
  
  <p><strong>Last step</strong>: Wait for new data on both sockets. When data arrives, I immediately read it to a buffer and then write it to the other
  socket. This maintains a 2-way communication between the HTTP client and
  the upstream HTTP server.</p>
  
  <p><strong>If any of the socket is closed</strong>, I close the other one.</p>
  
  <hr>
  
  <p>The problem right now is that it is not working. (It times out)</p>
  
  <p>I believe that the way I'm getting my IP addresses is correct, so the problem has to be in either my while loop (it never terminates?) or the part where I called connect(). I tried adding error termination for read() and select() but that didn't work either.</p>
  
  <pre><code>void handle_proxy_request(int fd) {
  
    char * targetHostName = server_proxy_hostname;
    int targetPort = server_proxy_port;
    struct hostent *info;
    info = gethostbyname(targetHostName);
    struct in_addr ** ipAddresslist;
    ipAddresslist = (struct in_addr **) (info -&gt; h_addr_list);
    struct in_addr * ipAddress = ipAddresslist[0];
    printf("ip address is %s\n", inet_ntoa(*ipAddress));
  
    /*ip for in_addr struct*/
    unsigned long ip = inet_addr(inet_ntoa(*ipAddress));
    struct in_addr addressIp = {ip};
    struct sockaddr_in address = {PF_INET, htons(targetPort), addressIp};
  
    int socket_num = socket(PF_INET, SOCK_STREAM, 0);
    connect(socket_num, (struct sockaddr *)&amp;address, sizeof(address));
  
    /*portion for select()*/
    char buf[10000];
    int nfds = (fd &gt; socket_num)?fd:socket_num;
    fd_set readSet;
    fd_set writeSet;
  
    while (1) {
  
      FD_ZERO(&amp;readSet);
      FD_ZERO(&amp;writeSet);
      FD_SET(fd, &amp;readSet);
      FD_SET(socket_num, &amp;readSet);
      FD_SET(fd, &amp;writeSet);
      FD_SET(socket_num, &amp;writeSet);
      int selectReturn = select(nfds, &amp;readSet, &amp;writeSet, NULL, NULL);
      if (selectReturn == -1){
        break;
      }
      if(FD_ISSET(fd, &amp;readSet)){
        int readStat = read(fd, buf, sizeof(buf));
        int status = write(socket_num, buf, sizeof(buf));
        if (status == -1 || readStat == -1){
          close(socket_num);
          close(fd);
          break;
        }
        /*memset(buf, 0, sizeof(buf));*/
      }
      if(FD_ISSET(socket_num, &amp;readSet)){
        int readStat2 = read(socket_num, buf, sizeof(buf));
        int status2 = write(fd, buf, sizeof(buf));
        if (status2 == -1 || readStat2 == -1){
          close(socket_num);
          close(fd);
          break;
        }
      }
  
    }
  
  }
  </code></pre>