Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP
Browse files

added stability on fcgi accept failed

git-svn-id: https://svn.opensource.yandex.net/xscript/trunk@663 b01ef89b-65f2-463d-9415-e8412542ae63
  • Loading branch information...
commit dc22d96240e48ae9f851bf15e34f98afa7efafd1 1 parent f227caa
compwolf authored
Showing with 62 additions and 21 deletions.
  1. +50 −21 daemon/fcgi_server.cpp
  2. +12 −0 daemon/fcgi_server.h
View
71 daemon/fcgi_server.cpp
@@ -47,6 +47,19 @@
namespace xscript {
+class FCGIServer::RequestAcceptor {
+ public:
+ explicit RequestAcceptor(FCGX_Request *req);
+ ~RequestAcceptor();
+
+ bool accepted() const { return NULL != req_; }
+
+ private:
+ FCGX_Request *req_;
+};
+
+
+
FCGIServer::FCGIServer(Config *config) :
Server(config), socket_(-1), inbuf_size_(0), outbuf_size_(0), alternate_port_(0),
workerCounter_(SimpleCounterFactory::instance()->createCounter("fcgi-workers", true)),
@@ -110,9 +123,10 @@ FCGIServer::handle() {
}
XmlUtils::registerReporters();
-
- while (true) {
- if (-1 != FCGX_Accept_r(&req)) {
+
+ for (;;) {
+ RequestAcceptor request_acceptor(&req);
+ if (request_acceptor.accepted()) {
try {
SimpleCounter::ScopedCount c(workerCounter_.get());
@@ -123,42 +137,30 @@ FCGIServer::handle() {
std::ostream os(&outbuf);
boost::shared_ptr<RequestResponse> request(new ServerRequest());
- ServerRequest* server_request = dynamic_cast<ServerRequest*>(request.get());
+ ServerRequest *server_request = dynamic_cast<ServerRequest*>(request.get());
+ RequestDetacher request_detacher(server_request);
- bool attach_error = false;
+ bool attach_success = false;
try {
- try {
- server_request->attach(&is, &os, req.envp);
- }
- catch (const std::exception &e) {
- attach_error = true;
- throw;
- }
+ server_request->attach(&is, &os, req.envp);
+ attach_success = true;
boost::shared_ptr<RequestData> data(
new RequestData(request, boost::shared_ptr<State>(new State())));
handleRequest(data);
-
- server_request->detach();
- FCGX_Finish_r(&req);
}
catch (const std::exception &e) {
- if (attach_error) {
+ if (!attach_success) {
OperationMode::instance()->sendError(server_request, 400, e.what());
}
- server_request->detach();
throw;
}
}
catch (const std::exception &e) {
- FCGX_Finish_r(&req);
log()->error("caught exception while handling request: %s", e.what());
}
}
- else {
- log()->error("failed to accept fastcgi request");
- }
}
FCGX_Free(&req, 1);
}
@@ -187,4 +189,31 @@ FCGIServer::needApplyPerblockStylesheet(Request *request) const {
return (request->getServerPort() != noxslt_port_);
}
+
+FCGIServer::RequestAcceptor::RequestAcceptor(FCGX_Request *req) : req_(NULL) {
+ int result = FCGX_Accept_r(req);
+ if (0 == result) {
+ req_ = req;
+ }
+ else {
+ log()->error("failed to accept fastcgi request, result: %d", result);
+ }
+}
+
+FCGIServer::RequestAcceptor::~RequestAcceptor() {
+ if (NULL != req_) {
+ FCGX_Finish_r(req_);
+ }
+}
+
+
+FCGIServer::RequestDetacher::RequestDetacher(ServerRequest *req) : req_(req) {
+ assert(NULL != req);
+}
+
+FCGIServer::RequestDetacher::~RequestDetacher() {
+ req_->detach();
+}
+
+
} // namespace xscript
View
12 daemon/fcgi_server.h
@@ -13,6 +13,7 @@ namespace xscript {
class Config;
class Request;
+class ServerRequest;
class FCGIServer : public Server, private boost::thread_group {
public:
@@ -28,6 +29,17 @@ class FCGIServer : public Server, private boost::thread_group {
void pid(const std::string &file);
private:
+ class RequestAcceptor;
+
+ class RequestDetacher {
+ public:
+ explicit RequestDetacher(ServerRequest *req);
+ ~RequestDetacher();
+
+ private:
+ ServerRequest *req_;
+ };
+
int socket_;
int inbuf_size_, outbuf_size_;
unsigned short alternate_port_, noxslt_port_;
Please sign in to comment.
Something went wrong with that request. Please try again.