2 * Copyright 2001-2007 Internet2
\r
4 * Licensed under the Apache License, Version 2.0 (the "License");
\r
5 * you may not use this file except in compliance with the License.
\r
6 * You may obtain a copy of the License at
\r
8 * http://www.apache.org/licenses/LICENSE-2.0
\r
10 * Unless required by applicable law or agreed to in writing, software
\r
11 * distributed under the License is distributed on an "AS IS" BASIS,
\r
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
\r
13 * See the License for the specific language governing permissions and
\r
14 * limitations under the License.
\r
18 * shar.cpp -- the shibd "main" code. All the functionality is elsewhere
\r
20 * Created By: Derek Atkins <derek@ihtfp.com>
\r
22 * $Id: shar.cpp 2164 2007-02-11 05:26:18 +0000 (Sun, 11 Feb 2007) cantor $
\r
26 // eventually we might be able to support autoconf via cygwin...
\r
27 #if defined (_MSC_VER) || defined(__BORLANDC__)
\r
28 # include "config_win32.h"
\r
30 # include "config.h"
\r
34 # define _CRT_NONSTDC_NO_DEPRECATE 1
\r
35 # define _CRT_SECURE_NO_DEPRECATE 1
\r
38 #include <shibsp/SPConfig.h>
\r
40 #ifdef HAVE_UNISTD_H
\r
42 #include <sys/select.h>
\r
47 #include <log4cpp/Category.hh>
\r
48 #include <shibsp/ServiceProvider.h>
\r
49 #include <shibsp/remoting/ListenerService.h>
\r
50 #include <xercesc/util/XMLUniDefs.hpp>
\r
51 #include <xmltooling/XMLToolingConfig.h>
\r
52 #include <xmltooling/util/XMLConstants.h>
\r
53 #include <xmltooling/util/XMLHelper.h>
\r
55 using namespace shibsp;
\r
56 using namespace log4cpp;
\r
57 using namespace xmltooling;
\r
58 using namespace std;
\r
60 bool shibd_shutdown = false;
\r
61 const char* shar_config = NULL;
\r
62 const char* shar_schemadir = NULL;
\r
63 bool shar_checkonly = false;
\r
64 static int unlink_socket = 0;
\r
65 const char* pidfile = NULL;
\r
69 //#include <CRTDBG.H>
\r
71 #define nNoMansLandSize 4
\r
72 typedef struct _CrtMemBlockHeader
\r
74 struct _CrtMemBlockHeader * pBlockHeaderNext;
\r
75 struct _CrtMemBlockHeader * pBlockHeaderPrev;
\r
81 unsigned char gap[nNoMansLandSize];
\r
83 * unsigned char data[nDataSize];
\r
84 * unsigned char anotherGap[nNoMansLandSize];
\r
86 } _CrtMemBlockHeader;
\r
89 int MyAllocHook(int nAllocType, void *pvData,
\r
90 size_t nSize, int nBlockUse, long lRequest,
\r
91 const unsigned char * szFileName, int nLine)
\r
93 if ( nBlockUse == _CRT_BLOCK )
\r
95 if (nAllocType == _HOOK_FREE) {
\r
96 _CrtMemBlockHeader* ptr = (_CrtMemBlockHeader*)(((_CrtMemBlockHeader *)pvData)-1);
\r
97 if (ptr->nDataSize == 8192)
\r
98 fprintf(stderr,"free request %u size %u\n", ptr->lRequest, ptr->nDataSize);
\r
100 else if (nAllocType == _HOOK_ALLOC && nSize == 8192)
\r
101 fprintf(stderr,"%s request %u size %u\n", ((nAllocType == _HOOK_ALLOC) ? "alloc" : "realloc"), lRequest, nSize);
\r
106 int real_main(int preinit)
\r
108 SPConfig& conf=SPConfig::getConfig();
\r
111 // Initialize the SP library.
\r
113 SPConfig::Listener |
\r
114 SPConfig::Caching |
\r
115 SPConfig::Metadata |
\r
117 SPConfig::Credentials |
\r
118 SPConfig::AttributeResolution |
\r
119 SPConfig::OutOfProcess |
\r
120 (shar_checkonly ? (SPConfig::InProcess | SPConfig::RequestMapping) : SPConfig::Logging)
\r
123 shar_config=getenv("SHIBSP_CONFIG");
\r
124 if (!shar_schemadir)
\r
125 shar_schemadir=getenv("SHIBSP_SCHEMAS");
\r
126 if (!shar_schemadir)
\r
127 shar_schemadir=SHIBSP_SCHEMAS;
\r
129 shar_config=SHIBSP_CONFIG;
\r
130 if (!conf.init(shar_schemadir)) {
\r
131 fprintf(stderr, "configuration is invalid, see console for specific problems\n");
\r
136 fprintf(stderr, "loading configuration file: %s\n", shar_config);
\r
137 static const XMLCh path[] = UNICODE_LITERAL_4(p,a,t,h);
\r
138 static const XMLCh validate[] = UNICODE_LITERAL_8(v,a,l,i,d,a,t,e);
\r
139 xercesc::DOMDocument* dummydoc=XMLToolingConfig::getConfig().getParser().newDocument();
\r
140 XercesJanitor<xercesc::DOMDocument> docjanitor(dummydoc);
\r
141 xercesc::DOMElement* dummy = dummydoc->createElementNS(NULL,path);
\r
142 auto_ptr_XMLCh src(shar_config);
\r
143 dummy->setAttributeNS(NULL,path,src.get());
\r
144 dummy->setAttributeNS(NULL,validate,xmlconstants::XML_ONE);
\r
146 conf.setServiceProvider(conf.ServiceProviderManager.newPlugin(XML_SERVICE_PROVIDER,dummy));
\r
147 conf.getServiceProvider()->init();
\r
149 catch (exception& ex) {
\r
150 fprintf(stderr, "caught exception while loading configuration: %s\n", ex.what());
\r
155 // If just a test run, bail.
\r
156 if (shar_checkonly) {
\r
157 fprintf(stdout, "overall configuration is loadable, check console for non-fatal problems\n");
\r
163 //_CrtSetAllocHook(MyAllocHook);
\r
165 // Run the listener
\r
166 if (!shar_checkonly) {
\r
168 // Run the listener.
\r
169 if (!conf.getServiceProvider()->getListenerService()->run(&shibd_shutdown)) {
\r
170 fprintf(stderr, "listener failed to enter listen loop\n");
\r
182 static void term_handler(int arg)
\r
184 shibd_shutdown = true;
\r
187 static int setup_signals(void)
\r
189 struct sigaction sa;
\r
190 memset(&sa, 0, sizeof (sa));
\r
191 sa.sa_handler = SIG_IGN;
\r
192 sa.sa_flags = SA_RESTART;
\r
194 if (sigaction(SIGPIPE, &sa, NULL) < 0) {
\r
198 memset(&sa, 0, sizeof (sa));
\r
199 sa.sa_handler = term_handler;
\r
200 sa.sa_flags = SA_RESTART;
\r
202 if (sigaction(SIGHUP, &sa, NULL) < 0) {
\r
205 if (sigaction(SIGINT, &sa, NULL) < 0) {
\r
208 if (sigaction(SIGQUIT, &sa, NULL) < 0) {
\r
211 if (sigaction(SIGTERM, &sa, NULL) < 0) {
\r
217 static void usage(char* whoami)
\r
219 fprintf(stderr, "usage: %s [-fcdt]\n", whoami);
\r
220 fprintf(stderr, " -c\tconfig file to use.\n");
\r
221 fprintf(stderr, " -d\tschema directory to use.\n");
\r
222 fprintf(stderr, " -t\tcheck configuration file for problems.\n");
\r
223 fprintf(stderr, " -f\tforce removal of listener socket.\n");
\r
224 fprintf(stderr, " -p\tpid file to use.\n");
\r
225 fprintf(stderr, " -h\tprint this help message.\n");
\r
229 static int parse_args(int argc, char* argv[])
\r
233 while ((opt = getopt(argc, argv, "c:d:p:fth")) > 0) {
\r
236 shar_config=optarg;
\r
239 shar_schemadir=optarg;
\r
245 shar_checkonly=true;
\r
257 int main(int argc, char *argv[])
\r
259 if (setup_signals() != 0)
\r
262 if (parse_args(argc, argv) != 0)
\r
266 shar_config=getenv("SHIBSP_CONFIG");
\r
267 if (!shar_schemadir)
\r
268 shar_schemadir=getenv("SHIBSP_SCHEMAS");
\r
269 if (!shar_schemadir)
\r
270 shar_schemadir=SHIBSP_SCHEMAS;
\r
272 shar_config=SHIBSP_CONFIG;
\r
274 // initialize the shib-target library
\r
275 SPConfig& conf=SPConfig::getConfig();
\r
277 SPConfig::Listener |
\r
278 SPConfig::Caching |
\r
279 SPConfig::Metadata |
\r
281 SPConfig::Credentials |
\r
282 SPConfig::AttributeResolution |
\r
283 SPConfig::OutOfProcess |
\r
284 (shar_checkonly ? (SPConfig::InProcess | SPConfig::RequestMapping) : SPConfig::Logging)
\r
286 if (!conf.init(shar_schemadir)) {
\r
287 fprintf(stderr, "configuration is invalid, check console for specific problems\n");
\r
292 fprintf(stderr, "loading configuration file: %s\n", shar_config);
\r
293 static const XMLCh path[] = UNICODE_LITERAL_4(p,a,t,h);
\r
294 static const XMLCh validate[] = UNICODE_LITERAL_8(v,a,l,i,d,a,t,e);
\r
295 xercesc::DOMDocument* dummydoc=XMLToolingConfig::getConfig().getParser().newDocument();
\r
296 XercesJanitor<xercesc::DOMDocument> docjanitor(dummydoc);
\r
297 xercesc::DOMElement* dummy = dummydoc->createElementNS(NULL,path);
\r
298 auto_ptr_XMLCh src(shar_config);
\r
299 dummy->setAttributeNS(NULL,path,src.get());
\r
300 dummy->setAttributeNS(NULL,validate,xmlconstants::XML_ONE);
\r
302 conf.setServiceProvider(conf.ServiceProviderManager.newPlugin(XML_SERVICE_PROVIDER,dummy));
\r
303 conf.getServiceProvider()->init();
\r
305 catch (exception& ex) {
\r
306 fprintf(stderr, "caught exception while loading configuration: %s\n", ex.what());
\r
311 if (shar_checkonly)
\r
312 fprintf(stderr, "overall configuration is loadable, check console for non-fatal problems\n");
\r
315 // Write the pid file
\r
317 FILE* pidf = fopen(pidfile, "w");
\r
319 fprintf(pidf, "%d\n", getpid());
\r
322 perror(pidfile); // keep running though
\r
326 // Run the listener
\r
327 if (!conf.getServiceProvider()->getListenerService()->run(&shibd_shutdown)) {
\r
328 fprintf(stderr, "listener failed to enter listen loop\n");
\r