| 518 | } |
| 519 | |
| 520 | void THttpServer::flush() { |
| 521 | // Fetch the contents of the write buffer |
| 522 | uint8_t* buf; |
| 523 | uint32_t len; |
| 524 | writeBuffer_.getBuffer(&buf, &len); |
| 525 | |
| 526 | // Construct the HTTP header |
| 527 | std::ostringstream h; |
| 528 | h << "HTTP/1.1 200 OK" << CRLF << "Date: " << getTimeRFC1123() << CRLF |
| 529 | << "Server: Thrift/" << PACKAGE_VERSION << CRLF |
| 530 | << "Access-Control-Allow-Origin: *" << CRLF |
| 531 | << "Content-Type: application/x-thrift" << CRLF << "Content-Length: " << len << CRLF |
| 532 | << "Connection: Keep-Alive" << CRLF; |
| 533 | vector<string> return_headers = callbacks_.return_headers_fn(); |
| 534 | for (const string& header : return_headers) { |
| 535 | h << header << CRLF; |
| 536 | } |
| 537 | h << CRLF; |
| 538 | string header = h.str(); |
| 539 | |
| 540 | // Write the header, then the data, then flush |
| 541 | // cast should be fine, because none of "header" is under attacker control |
| 542 | transport_->write((const uint8_t*)header.c_str(), static_cast<uint32_t>(header.size())); |
| 543 | transport_->write(buf, len); |
| 544 | transport_->flush(); |
| 545 | |
| 546 | // Reset the buffer and header variables |
| 547 | writeBuffer_.resetBuffer(); |
| 548 | readHeaders_ = true; |
| 549 | } |
| 550 | |
| 551 | std::string THttpServer::getTimeRFC1123() { |
| 552 | static const char* Days[] = {"Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"}; |
no test coverage detected