void Transport::replaceHeader(CStrRef header) { String name; const char *value; if (splitHeader(header, name, value)) { replaceHeader(name.data(), value); } }
void Transport::prepareHeaders(bool compressed, const void *data, int size) { FiberReadLock lock(this); for (HeaderMap::const_iterator iter = m_responseHeaders.begin(); iter != m_responseHeaders.end(); ++iter) { const vector<string> &values = iter->second; for (unsigned int i = 0; i < values.size(); i++) { addHeaderImpl(iter->first.c_str(), values[i].c_str()); } } for (CookieMap::const_iterator iter = m_responseCookies.begin(); iter != m_responseCookies.end(); ++iter) { addHeaderImpl("Set-Cookie", iter->second.c_str()); } if (compressed) { addHeaderImpl("Content-Encoding", "gzip"); removeHeaderImpl("Content-Length"); if (m_responseHeaders.find("Content-MD5") != m_responseHeaders.end()) { String response((const char *)data, size, AttachLiteral); replaceHeader("Content-MD5", StringUtil::Base64Encode( StringUtil::MD5(response, true)).c_str()); } } if (m_responseHeaders.find("Content-Type") == m_responseHeaders.end() && m_responseCode != 304) { addHeaderImpl("Content-Type", "text/html; charset=utf-8"); } // shutting down servers, so need to terminate all Keep-Alive connections if (!RuntimeOption::EnableKeepAlive || isServerStopping()) { addHeaderImpl("Connection", "close"); removeHeaderImpl("Keep-Alive"); // so lower level transports can ignore incoming "Connection: keep-alive" removeRequestHeaderImpl("Connection"); } }
int COneServerHttpProxyThread::start() { try { char peername[256]; int port = m_client->peer_name(peername, 256); if(http_tracelevel >= 5) fprintf(m_ofile, "\n>>receivd request from %s:%d\n", peername, port); StringBuffer requestbuf; Owned<IByteOutputStream> reqstream = createOutputStream(requestbuf); bool isRoxie; Http::receiveData(m_client, reqstream.get(), false, isRoxie); if(http_tracelevel >= 10) fprintf(m_ofile, "%s%s%s", sepstr, requestbuf.str(), sepstr); else if(http_tracelevel >= 5) { const char* endofline = strstr(requestbuf.str(), "\n"); if(endofline) { StringBuffer firstline; firstline.append((endofline - requestbuf.str()), requestbuf.str()); fprintf(m_ofile, "%s", firstline.str()); } else fprintf(m_ofile, "%s\n", requestbuf.str()); } if (0 != stricmp(m_url_prefix, "/")) { int url_offset; if (!strnicmp(requestbuf.str(), "GET ", 4)) url_offset = 4; else if (!strnicmp(requestbuf.str(), "POST ", 5)) url_offset = 5; else url_offset = -1; if (url_offset > 0) { const int prefix_len = strlen(m_url_prefix); if (0 != strnicmp(requestbuf.str()+url_offset, m_url_prefix, prefix_len)) { const char* endofline = strstr(requestbuf.str(), "\n"); if(endofline) { StringBuffer firstline; firstline.append((endofline - requestbuf.str()), requestbuf.str()); fprintf(m_ofile, "INVALID request: %s", firstline.str()); } else fprintf(m_ofile, "INVALID request:\n%s\n", requestbuf.str()); StringBuffer respbuf; respbuf.append("HTTP/1.1 404 Not Found\n") .append("Content-Type: text/xml; charset=UTF-8\n") .append("Connection: close\n"); m_client->write(respbuf.str(), respbuf.length()); if(http_tracelevel >= 5) fprintf(m_ofile, ">>sent the response back to %s:%d:\n", peername, port); if(http_tracelevel >= 10) fprintf(m_ofile, "%s%s%s", sepstr, respbuf.str(), sepstr); fflush(m_ofile); m_client->shutdown(); m_client->close(); return -1; } else { //we want to map /x to / and /x/y to /y as follows: //if m_url_prefix is /x and url is /x/y then remove x //to result in //y requestbuf.remove(++url_offset, prefix_len-1); //now, if we have //y then change it to /y if (*(requestbuf.str()+url_offset) == '/') requestbuf.remove(url_offset, 1); } } } SocketEndpoint ep; Owned<ISocket> socket2; ep.set(m_host.str(), m_port); socket2.setown(ISocket::connect(ep)); if(m_use_ssl && m_ssctx != NULL) { Owned<ISecureSocket> securesocket = m_ssctx->createSecureSocket(socket2.getLink()); int res = securesocket->secure_connect(); if(res >= 0) { socket2.set(securesocket.get()); } } if(socket2.get() == NULL) { StringBuffer urlstr; DBGLOG(">>Can't connect to %s", ep.getUrlStr(urlstr).str()); return -1; } char newhost[1024]; sprintf(newhost, "%s:%d", m_host.str(), m_port); replaceHeader(requestbuf, "Host", newhost); //checkContentLength(requestbuf); if(http_tracelevel >= 5) fprintf(m_ofile, "\n>>sending request to %s:%d\n", m_host.str(), m_port); if(http_tracelevel >= 10) fprintf(m_ofile, "%s%s%s", sepstr, requestbuf.str(), sepstr); socket2->write(requestbuf.str(), requestbuf.length()); StringBuffer respbuf; Owned<IByteOutputStream> respstream = createOutputStream(respbuf); isRoxie; Http::receiveData(socket2.get(), respstream.get(), true, isRoxie); if(http_tracelevel >= 5) fprintf(m_ofile, ">>received response from %s:%d:\n", m_host.str(), m_port); if(http_tracelevel >= 10) fprintf(m_ofile, "%s%s%s", sepstr, respbuf.str(), sepstr); m_client->write(respbuf.str(), respbuf.length()); fflush(m_ofile); if(http_tracelevel >= 5) fprintf(m_ofile, ">>sent the response back to %s:%d:\n", peername, port); if(http_tracelevel >= 10) fprintf(m_ofile, "%s%s%s", sepstr, respbuf.str(), sepstr); socket2->shutdown(); socket2->close(); m_client->shutdown(); m_client->close(); } catch(IException *excpt) { StringBuffer errMsg; DBGLOG("%s", excpt->errorMessage(errMsg).str()); return -1; } catch(...) { DBGLOG("unknown exception"); return -1; } return 0; }
int COneServerHttpProxyThread::start() { try { char peername[256]; int port = m_client->peer_name(peername, 256); if(httptest_tracelevel > 5) fprintf(m_ofile, "\n>>receivd request from %s:%d\n", peername, port); StringBuffer requestbuf; Owned<IByteOutputStream> reqstream = createOutputStream(requestbuf); receiveData(m_client, reqstream.get(), false); if(httptest_tracelevel > 10) fprintf(m_ofile, "%s%s%s", sepstr, requestbuf.str(), sepstr); SocketEndpoint ep; Owned<ISocket> socket2; ep.set(m_host.str(), m_port); socket2.setown(ISocket::connect(ep)); if(m_use_ssl && m_ssctx != NULL) { Owned<ISecureSocket> securesocket = m_ssctx->createSecureSocket(socket2.getLink()); int res = securesocket->secure_connect(); if(res >= 0) { socket2.set(securesocket.get()); } } if(socket2.get() == NULL) { StringBuffer urlstr; DBGLOG(">>Can't connect to %s", ep.getUrlStr(urlstr).str()); return -1; } char newhost[1024]; sprintf(newhost, "%s:%d", m_host.str(), m_port); replaceHeader(requestbuf, "Host", newhost); //checkContentLength(requestbuf); if(httptest_tracelevel > 5) fprintf(m_ofile, "\n>>sending request to %s:%d\n", m_host.str(), m_port); if(httptest_tracelevel > 10) fprintf(m_ofile, "%s%s%s", sepstr, requestbuf.str(), sepstr); socket2->write(requestbuf.str(), requestbuf.length()); StringBuffer respbuf; Owned<IByteOutputStream> respstream = createOutputStream(respbuf); receiveData(socket2.get(), respstream.get(), true); if(httptest_tracelevel > 5) fprintf(m_ofile, ">>received response from %s:%d:\n", m_host.str(), m_port); if(httptest_tracelevel > 10) fprintf(m_ofile, "%s%s%s", sepstr, respbuf.str(), sepstr); m_client->write(respbuf.str(), respbuf.length()); fflush(m_ofile); if(httptest_tracelevel > 5) fprintf(m_ofile, ">>sent the response back to %s:%d:\n", peername, port); socket2->shutdown(); socket2->close(); m_client->shutdown(); m_client->close(); } catch(IException *excpt) { StringBuffer errMsg; DBGLOG("%s", excpt->errorMessage(errMsg).str()); return -1; } catch(...) { DBGLOG("unknown exception"); return -1; } return 0; }