/*############################################################################## Copyright (C) 2011 HPCC Systems. All rights reserved. This program is free software: you can redistribute it and/or modify it under the terms of the GNU Affero General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for more details. You should have received a copy of the GNU Affero General Public License along with this program. If not, see . ############################################################################## */ #pragma warning (disable : 4786) #ifdef _WIN32 #ifdef ESPHTTP_EXPORTS #define esp_http_decl __declspec(dllexport) #endif #endif //Jlib #include "jliball.hpp" //CRT / OS #ifdef _WIN32 #define WIN32_LEAN_AND_MEAN #include #include #include #include #include #else #include #include #include #include #include #include #include #endif //SCM Interfaces //#include "IAEsp.hpp" //#include "IAEsc.hpp" //ESP Core #include "espthread.hpp" CEspProtocolThread::CEspProtocolThread(const char *name) : Thread("CEspProtocolThread"), m_name(name) { terminating = false; } CEspProtocolThread::CEspProtocolThread(ISocket *sock, const char *name) : Thread("CEspProtocolThread"), m_name(name) { terminating = false; setSocket(sock); } CEspProtocolThread::~CEspProtocolThread() { } void CEspProtocolThread::start() { Thread::start(); } const char *CEspProtocolThread::getServiceName() { return m_name.get(); } bool CEspProtocolThread::onRequest() { return false; } void CEspProtocolThread::setSocket(ISocket *sock) { CriticalBlock block(sect); m_socket.setown(sock); //DBGLOG("%s -- serving socket(%d):", this->getServiceName(), sock->OShandle()); char xname[256]={0}; m_socket->name(xname, 256); //DBGLOG("... on net address(%s)", xname); m_socket->peer_name(xname, 256); //DBGLOG("... from net address(%s)", xname); ticksem.signal(); } void CEspProtocolThread::stop(bool wait) { terminating = true; ticksem.signal(); //if (wait) // join(); } //Unused code cause Linker warning LNK4089: // all references to 'dynamic-link library' discarded by /OPT:REF #if 0 bool wait_to_exit(bool can_continue, ISocket* sock, int timeoutsecs) { if(sock == NULL) return false; int sockid = sock->OShandle(); fd_set rdfds; timeval selecttimeout; FD_ZERO(&rdfds); FD_SET(sockid, &rdfds); selecttimeout.tv_sec = timeoutsecs; selecttimeout.tv_usec = 0; int availread = 0; int n = select(sockid + 1, &rdfds, NULL, NULL, &selecttimeout); if (n < 0) { if (errno != EINTR) { DBGLOG("error selecting in wait_to_exit() error %d\n", errno); return false; } } else if(n > 0) { DBGLOG("Select on socket %d returns before timeout", sockid); availread = sock->avail_read(); if(availread > 0) { // This is the only place that can possibly return true. return can_continue; } else { DBGLOG("The remote side of the socket %d has been closed.", sockid); return false; } } else { DBGLOG("Select returns after timeout"); return false; } return false; } #endif int CEspProtocolThread::run() { Link(); try { bool can_continue = false; do { can_continue = onRequest(); } while (can_continue); } catch (IException *e) { StringBuffer estr; ERRLOG("Exception(%d, %s) in CEspProtocolThread::run while processing request.", e->errorCode(), e->errorMessage(estr).str()); e->Release(); } catch(...) { ERRLOG("Unknown Exception in CEspProtocolThread::run while processing request."); } try { m_socket->shutdown(); m_socket->close(); } catch (IException *e) { StringBuffer estr; DBGLOG("Exception(%d, %s) - in CEspProtocolThread::run while closing socket.", e->errorCode(), e->errorMessage(estr).str()); e->Release(); } catch(...) { DBGLOG("General Exception - in CEspProtocolThread::run while closing socket."); } Release(); return 0; }