29 CHServer::~CHServer() {
33 string servd, serverCntrlFileNm;
34 static bool isSSLEnabled =
false,isThreadprq =
false,processforcekilled =
false,processgendone =
false,sessatserv =
false,isCompileEnabled =
false;
35 static long sessionTimeout;
38 static char *ciphers=0;
41 void *dlib = NULL, *ddlib = NULL;
42 typedef map<string,string> sessionMap;
43 static Mutex m_mutex,p_mutex;
48 void sigchld_handler(
int s)
50 while(waitpid(-1, NULL, WNOHANG) > 0);
54 void *get_in_addr(
struct sockaddr *sa)
56 if (sa->sa_family == AF_INET) {
57 return &(((
struct sockaddr_in*)sa)->sin_addr);
59 return &(((
struct sockaddr_in6*)sa)->sin6_addr);
63 int send_connection(
int fd,
int descriptor)
72 iov [0].iov_base = (
void *)
"x";
82 msg.msg_control = NULL;
83 msg.msg_controllen = 0;
91 char control [CMSG_SPACE (
sizeof (
int))];
95 msg.msg_control = &msg_control;
96 msg.msg_controllen =
sizeof (msg_control);
98 cmsg = CMSG_FIRSTHDR (&msg);
100 cmsg->cmsg_len = CMSG_LEN (
sizeof (
int));
101 cmsg->cmsg_level = SOL_SOCKET;
102 cmsg->cmsg_type = SCM_RIGHTS;
104 *((
int *) CMSG_DATA (cmsg)) = descriptor;
107 if((n= sendmsg(fd, &msg, 0)) < 0 )
116 int receive_fd(
int fd)
121 char control [CMSG_SPACE (
sizeof (
int))];
125 struct iovec iov [1];
126 struct cmsghdr *cmsg;
130 iov [0].iov_base = buf;
131 iov [0].iov_len =
sizeof (buf);
138 msg.msg_control = &msg_control;
139 msg.msg_controllen =
sizeof (msg_control);
142 n = recvmsg (fd, &msg, 0);
145 for (cmsg = CMSG_FIRSTHDR (&msg); cmsg; cmsg = CMSG_NXTHDR (&msg, cmsg))
149 if (cmsg->cmsg_len != CMSG_LEN (
sizeof (
int)) ||
150 cmsg->cmsg_level != SOL_SOCKET ||
151 cmsg->cmsg_type != SCM_RIGHTS)
154 descriptor = *((
int *) CMSG_DATA (cmsg));
161 void signalSIGSEGV(
int dummy)
163 signal(SIGSEGV,signalSIGSEGV);
169 filename.append(
".cntrl");
170 remove(filename.c_str());
182 logger <<
"Segmentation fault occurred for process" << getpid() <<
"\n" << tempo << endl;
185 void signalSIGCHLD(
int dummy)
187 signal(SIGCHLD,signalSIGCHLD);
193 filename.append(
".cntrl");
194 remove(filename.c_str());
206 logger <<
"Child process got killed " << getpid() <<
"\n" << tempo << endl;
209 void signalSIGABRT(
int dummy)
211 signal(SIGABRT,signalSIGABRT);
217 filename.append(
".cntrl");
218 remove(filename.c_str());
230 logger <<
"Abort signal occurred for process" << getpid() <<
"\n" << tempo << endl;
233 void signalSIGTERM(
int dummy)
235 signal(SIGKILL,signalSIGTERM);
241 filename.append(
".cntrl");
242 remove(filename.c_str());
254 logger <<
"Termination signal occurred for process" << getpid() <<
"\n" << tempo << endl;
258 void signalSIGKILL(
int dummy)
260 signal(SIGKILL,signalSIGKILL);
266 filename.append(
".cntrl");
267 remove(filename.c_str());
279 logger <<
"Kill signal occurred for process" << getpid() <<
"\n" << tempo << endl;
283 void signalSIGINT(
int dummy)
285 signal(SIGINT,signalSIGINT);
291 filename.append(
".cntrl");
292 remove(filename.c_str());
304 logger <<
"Interrupt signal occurred for process" << getpid() <<
"\n" << tempo << endl;
308 void signalSIGFPE(
int dummy)
310 signal(SIGFPE,signalSIGFPE);
316 filename.append(
".cntrl");
317 remove(filename.c_str());
329 logger <<
"Floating point Exception occurred for process" << getpid() <<
"\n" << tempo << endl;
332 void signalSIGPIPE(
int dummy)
334 signal(SIGPIPE,signalSIGPIPE);
353 logger <<
"Broken pipe ignore it" << getpid() <<
"\n" << tempo << endl;
357 void signalSIGILL(
int dummy)
359 signal(SIGILL,signalSIGILL);
365 filename.append(
".cntrl");
366 remove(filename.c_str());
378 logger <<
"Floating point Exception occurred for process" << getpid() <<
"\n" << tempo << endl;
382 void* service(
void* arg)
384 logger <<
"service method " << endl;
391 pid_t createChildProcess(
string serverRootDirectory,
int sp[],
int sockfd)
394 if (socketpair(AF_UNIX, SOCK_DGRAM, 0, sp) == -1)
396 perror(
"socketpair");
402 dlib = dlopen(Constants::INTER_LIB_FILE.c_str(), RTLD_NOW);
406 logger << dlerror() << endl;
407 logger.info(
"Could not load Library");
411 logger.info(
"Library loaded successfully");
413 ddlib = dlopen(Constants::DINTER_LIB_FILE.c_str(), RTLD_NOW);
417 logger << dlerror() << endl;
418 logger.info(
"Could not load dynamic Library");
422 logger.info(
"Dynamic Library loaded successfully");
428 ctx = sSLHandler.initialize_ctx((
char*)configurationData.key_file.c_str(),(
char*)configurationData.sec_password.c_str(),
429 configurationData.ca_list);
430 sSLHandler.load_dh_params(ctx,(
char*)configurationData.dh_file.c_str());
432 SSL_CTX_set_session_id_context(ctx,
433 (
const unsigned char*)&SSLHandler::s_server_session_id_context,
434 sizeof SSLHandler::s_server_session_id_context);
438 SSL_CTX_set_cipher_list(ctx,ciphers);
445 servd = serverRootDirectory;
448 ss << serverRootDirectory;
451 filename.append(
".cntrl");
452 logger << (
"generated file " + filename) << endl;
454 cntrlfile.open(filename.c_str());
455 cntrlfile <<
"Process Running" << endl;
461 selEpolKqEvPrtHandler.initialize(sp[1]);
465 pool.init(thrdpsiz,30,
true);
468 propMap params = pread.getProperties(serverRootDirectory+
"resources/security.prop");
472 ofstream serverCntrlFile;
473 serverCntrlFile.open(serverCntrlFileNm.c_str());
474 while(serverCntrlFile.is_open())
476 serverCntrlFile.close();
478 int nfds = selEpolKqEvPrtHandler.getEvents();
481 perror(
"poller wait child process");
482 logger <<
"\n----------poller child process----" << endl;
486 int fd = receive_fd(sp[1]);
487 selEpolKqEvPrtHandler.reRegisterServerSock();
488 fcntl(fd, F_SETFL,O_SYNC);
492 if((err=recv(fd,buf,10,MSG_PEEK))==0)
495 logger <<
"Socket conn closed before being serviced" << endl;
502 isSSLEnabled, ctx, sSLHandler, configurationData, dlib, ddlib);
503 Thread pthread(&service, task);
509 isSSLEnabled, ctx, sSLHandler, configurationData, dlib, ddlib);
510 task->setCleanUp(
true);
514 serverCntrlFile.open(serverCntrlFileNm.c_str());
562 void* dynamic_page_monitor(
void* arg)
564 string serverRootDirectory = *(
string*)arg;
566 strVec dcpsss = configurationData.dcpsss;
567 strVec tpes = configurationData.tpes;
568 strVec dcspstpes = dcpsss;
569 dcspstpes.insert(dcspstpes.end(), tpes.begin(), tpes.end());
570 map<string,long> statsinf;
571 for(
int i=0;i<(int)dcspstpes.size();i++)
573 stat(dcspstpes.at(i).c_str(), &statbuf);
574 time_t tm = statbuf.st_mtime;
575 long tim = (uintmax_t)tm;
576 statsinf[dcspstpes.at(i)] = tim;
584 for(
int i=0;i<(int)dcspstpes.size();i++)
586 stat(dcspstpes.at(i).c_str(), &statbuf);
587 time_t tm = statbuf.st_mtime;
588 long tim = (uintmax_t)tm;
589 if(tim!=statsinf[dcspstpes.at(i)])
591 string rtdcfpath = serverRootDirectory +
"rtdcf/";
592 string respath = serverRootDirectory +
"resources/";
594 logger <<
"started generating dcp code" <<endl;
595 string ret = DCPGenerator::generateDCPAll(dcpsss);
596 AfcUtil::writeTofile(rtdcfpath+
"DCPInterface.cpp",ret,
true);
597 logger <<
"done generating dcp code" <<endl;
598 logger <<
"started generating template code" <<endl;
599 ret = TemplateGenerator::generateTempCdAll(tpes);
600 AfcUtil::writeTofile(rtdcfpath+
"TemplateInterface.cpp",ret,
true);
601 logger <<
"done generating template code" <<endl;
603 string compres = respath+
"rundyn_dinter.sh";
604 int i=system(compres.c_str());
607 logger <<
"regenerating intermediate code-----Done" << endl;
608 logger.info(
"Done generating intermediate code");
611 if(Constants::IS_FILE_DESC_PASSING_AVAIL)
613 map<int,pid_t>::iterator it;
614 for(it=pds.begin();it!=pds.end();it++)
623 for (
int var = 0; var < 100; ++var) {
624 if(dlclose(ddlib)!=0)
629 ddlib = dlopen(Constants::DINTER_LIB_FILE.c_str(), RTLD_NOW);
633 logger << dlerror() << endl;
634 logger.info(
"Could not re-load Dynamic Library");
637 logger.info(
"Dynamic Library re-loaded successfully");
640 processforcekilled =
true;
647 for(
int ii=0;ii<(int)dcspstpes.size();ii++)
649 stat(dcspstpes.at(ii).c_str(), &statbuf);
650 time_t tm = statbuf.st_mtime;
651 long tim = (uintmax_t)tm;
652 statsinf[dcspstpes.at(ii)] = tim;
660 int main(
int argc,
char* argv[])
663 signal(SIGSEGV,signalSIGSEGV);
664 signal(SIGFPE,signalSIGFPE);
667 signal(SIGPIPE,signalSIGPIPE);
669 struct sockaddr_storage their_addr;
673 int nfds,preForked=5;
674 string serverRootDirectory = argv[1];
676 serverRootDirectory +=
"/";
677 string incpath = serverRootDirectory +
"include/";
678 string rtdcfpath = serverRootDirectory +
"rtdcf/";
679 string pubpath = serverRootDirectory +
"public/";
680 string respath = serverRootDirectory +
"resources/";
681 string webpath = serverRootDirectory +
"web/";
682 string resourcePath = respath;
684 servd = serverRootDirectory;
685 string logp = respath+
"/log.prop";
688 serverCntrlFileNm = serverRootDirectory +
"ffead.cntrl";
690 logger = Logger::getLogger(
"CHServer");
693 propMap srprps = pread.getProperties(respath+
"server.prop");
694 if(srprps[
"NUM_PROC"]!=
"")
698 preForked = CastUtil::lexical_cast<
int>(srprps[
"NUM_PROC"]);
702 logger <<
"\nInvalid number for worker processes defined" << endl;
706 string sslEnabled = srprps[
"SSL_ENAB"];
707 if(sslEnabled==
"true" || sslEnabled==
"TRUE")
709 string thrdpreq = srprps[
"THRD_PREQ"];
710 if(thrdpreq==
"true" || thrdpreq==
"TRUE")
714 thrdpreq = srprps[
"THRD_PSIZ"];
721 thrdpsiz = CastUtil::lexical_cast<
int>(thrdpreq);
725 logger <<
"\nInvalid thread pool size defined" << endl;
730 string compileEnabled = srprps[
"DEV_MODE"];
731 if(compileEnabled==
"true" || compileEnabled==
"TRUE")
732 isCompileEnabled =
true;
734 if(srprps[
"SCRIPT_ERRS"]==
"true" || srprps[
"SCRIPT_ERRS"]==
"TRUE")
736 Constants::SCRIPT_EXEC_SHOW_ERRS =
true;
738 if(srprps[
"SESS_STATE"]==
"server")
740 if(srprps[
"SESS_TIME_OUT"]!=
"")
743 sessionTimeout = CastUtil::lexical_cast<
long>(srprps[
"SESS_TIME_OUT"]);
745 sessionTimeout = 3600;
746 logger <<
"\nInvalid session timeout value defined, defaulting to 1hour/3600sec" << endl;
750 string PORT = srprps[
"PORT_NO"];
751 string IP_ADDRES = srprps[
"IP_ADDR"];
755 IP_ADDRESS = IP_ADDRES +
":" + PORT;
757 IP_ADDRESS =
"localhost:" + PORT;
759 sockfd = Server::createListener(IP_ADDRES, PORT,
false);
761 strVec webdirs,webdirs1,pubfiles;
762 ConfigurationHandler::listi(webpath,
"/",
true,webdirs);
763 ConfigurationHandler::listi(webpath,
"/",
false,webdirs1);
764 ConfigurationHandler::listi(pubpath,
".js",
false,pubfiles);
770 configurationData = ConfigurationHandler::handle(webdirs, webdirs1, incpath, rtdcfpath, pubpath, respath, isSSLEnabled);
774 logger << p.getMessage() << endl;
776 catch(
const char* msg)
778 logger << msg << endl;
780 configurationData.sessionTimeout = sessionTimeout;
781 configurationData.ip_address = IP_ADDRESS;
782 configurationData.sessatserv = sessatserv;
783 for(
unsigned int var=0;var<pubfiles.size();var++)
785 configurationData.pubMap[pubfiles.at(var)] =
"true";
787 bool libpresent =
true;
788 void *dlibtemp = dlopen(Constants::INTER_LIB_FILE.c_str(), RTLD_NOW);
793 logger << dlerror() << endl;
794 logger.info(
"Could not load Library");
801 configurationData.props = pread.getProperties(respath+
"mime-types.prop");
802 configurationData.lprops = pread.getProperties(respath+
"locale.prop");
803 string compres = respath+
"rundyn.sh";
806 string output = ScriptHandler::execute(compres,
true);
807 logger <<
"Intermediate code generation task\n\n" << endl;
808 logger << output << endl;
811 void* checkdlib = dlopen(Constants::INTER_LIB_FILE.c_str(), RTLD_NOW);
814 logger << dlerror() << endl;
815 logger.info(
"Could not load Library");
821 logger.info(
"Library generated successfully");
824 for (
unsigned int var1 = 0;var1<configurationData.cmpnames.size();var1++)
826 string name = configurationData.cmpnames.at(var1);
827 StringUtil::replaceFirst(name,
"Component_",
"");
828 ComponentHandler::registerComponent(name);
829 AppContext::registerComponent(name);
831 if(srprps[
"CMP_PORT"]==
"")
833 srprps[
"CMP_PORT"] =
"7001";
835 ComponentHandler::trigger(srprps[
"CMP_PORT"]);
836 if(srprps[
"MESS_PORT"]==
"")
838 srprps[
"MESS_PORT"] =
"7002";
840 MessageHandler::trigger(srprps[
"MESS_PORT"],resourcePath);
841 if(srprps[
"MI_PORT"]==
"")
843 srprps[
"MI_PORT"] =
"7003";
845 MethodInvoc::trigger(srprps[
"MI_PORT"]);
848 logger.info(
"Server: waiting for connections on port "+PORT);
850 ofstream serverCntrlFile;
851 serverCntrlFile.open(serverCntrlFileNm.c_str());
852 serverCntrlFile <<
"Server Running" << endl;
853 serverCntrlFile.close();
855 vector<string> files;
856 int sp[preForked][2];
860 if(Constants::IS_FILE_DESC_PASSING_AVAIL)
862 for(
int j=0;j<preForked;j++)
864 pid_t pid = createChildProcess(serverRootDirectory,sp[j],sockfd);
868 ss << serverRootDirectory;
871 filename.append(
".cntrl");
872 files.push_back(filename);
877 propMap params = pread.getProperties(serverRootDirectory+
"resources/security.prop");
884 ctx = sSLHandler.initialize_ctx((
char*)configurationData.key_file.c_str(),(
char*)configurationData.sec_password.c_str(),
885 configurationData.ca_list);
886 sSLHandler.load_dh_params(ctx,(
char*)configurationData.dh_file.c_str());
888 SSL_CTX_set_session_id_context(ctx,
889 (
const unsigned char*)&SSLHandler::s_server_session_id_context,
890 sizeof SSLHandler::s_server_session_id_context);
894 SSL_CTX_set_cipher_list(ctx,ciphers);
901 dlib = dlopen(Constants::INTER_LIB_FILE.c_str(), RTLD_NOW);
905 logger << dlerror() << endl;
906 logger.info(
"Could not load Library");
910 logger.info(
"Library loaded successfully");
911 ddlib = dlopen(Constants::DINTER_LIB_FILE.c_str(), RTLD_NOW);
915 logger << dlerror() << endl;
916 logger.info(
"Could not load dynamic Library");
920 logger.info(
"Dynamic Library loaded successfully");
923 pool =
new ThreadPool(thrdpsiz,thrdpsiz+30,
true);
930 Thread pthread(&dynamic_page_monitor, &serverRootDirectory);
935 selEpolKqEvPrtHandler.initialize(sockfd);
943 serverCntrlFile.open(serverCntrlFileNm.c_str());
944 while(serverCntrlFile.is_open())
946 serverCntrlFile.close();
948 if(childNo>=preForked)
950 nfds = selEpolKqEvPrtHandler.getEvents();
953 perror(
"poll_wait main process");
954 logger.info(
"Interruption Signal Received\n");
956 logger <<
"\nInavlid fd" <<endl;
957 else if(errno==EFAULT)
958 logger <<
"\nThe memory area pointed to by events is not accessible" <<endl;
959 else if(errno==EINTR)
960 logger <<
"\ncall was interrupted by a signal handler before any of the requested events occurred" <<endl;
961 else if(errno==EINVAL)
962 logger <<
"not a poll file descriptor, or maxevents is less than or equal to zero" << endl;
964 logger <<
"\nnot an epoll file descriptor" <<endl;
966 processgendone =
false;
967 if(processforcekilled)
969 if(Constants::IS_FILE_DESC_PASSING_AVAIL)
972 for(
int j=0;j<preForked;j++)
974 pid_t pid = createChildProcess(serverRootDirectory,sp[j],sockfd);
978 ss << serverRootDirectory;
981 filename.append(
".cntrl");
982 files.push_back(filename);
989 pool->init(thrdpsiz,thrdpsiz+30,
true);
991 processforcekilled =
false;
992 processgendone =
true;
994 for(
int n=0;n<nfds;n++)
996 if(childNo>=preForked)
998 int descriptor = selEpolKqEvPrtHandler.getDescriptor(n);
999 if (descriptor == sockfd)
1002 sin_size =
sizeof their_addr;
1003 new_fd = accept(sockfd, (
struct sockaddr *)&their_addr, &sin_size);
1011 selEpolKqEvPrtHandler.reRegisterServerSock();
1012 selEpolKqEvPrtHandler.registerForEvent(new_fd);
1015 else if (descriptor != -1)
1017 logger << (
"got new connection " + CastUtil::lexical_cast<
string>(descriptor)) << endl;
1018 selEpolKqEvPrtHandler.unRegisterForEvent(descriptor);
1019 if(Constants::IS_FILE_DESC_PASSING_AVAIL)
1022 cntrlfile.open(files.at(childNo).c_str());
1023 if(cntrlfile.is_open())
1025 send_connection(sp[childNo][0], descriptor);
1026 string cno = CastUtil::lexical_cast<
string>(childNo);
1032 for(
int o=0;o<preForked;o++)
1034 ifstream cntrlfileT;
1035 cntrlfileT.open(files.at(o).c_str());
1036 if(cntrlfileT.is_open())
1038 send_connection(sp[childNo][0], descriptor);
1039 string cno = CastUtil::lexical_cast<
string>(o);
1047 logger <<
"Process got killed" << endl;
1048 pid_t pid = createChildProcess(serverRootDirectory,sp[tcn],sockfd);
1052 ss << serverRootDirectory;
1055 filename.append(
".cntrl");
1056 files[tcn] = filename;
1057 logger <<
"created a new Process" << endl;
1058 logger.info(
"Process got killed hence created a new Process\n");
1064 fcntl(descriptor, F_SETFL,O_SYNC);
1068 isSSLEnabled, ctx, sSLHandler, configurationData, dlib, ddlib);
1069 Thread pthread(&service, task);
1075 isSSLEnabled, ctx, sSLHandler, configurationData, dlib, ddlib);
1076 task->setCleanUp(
true);
1077 pool->execute(*task);
1082 serverCntrlFile.open(serverCntrlFileNm.c_str());
1084 ComponentHandler::stop();
1085 MessageHandler::stop();
1086 MethodInvoc::stop();
1088 ConfigurationHandler::destroyCibernate();