2 * The Shibboleth License, Version 1.
4 * University Corporation for Advanced Internet Development, Inc.
8 * Redistribution and use in source and binary forms, with or without
9 * modification, are permitted provided that the following conditions are met:
11 * Redistributions of source code must retain the above copyright notice, this
12 * list of conditions and the following disclaimer.
14 * Redistributions in binary form must reproduce the above copyright notice,
15 * this list of conditions and the following disclaimer in the documentation
16 * and/or other materials provided with the distribution, if any, must include
17 * the following acknowledgment: "This product includes software developed by
18 * the University Corporation for Advanced Internet Development
19 * <http://www.ucaid.edu>Internet2 Project. Alternately, this acknowledegement
20 * may appear in the software itself, if and wherever such third-party
21 * acknowledgments normally appear.
23 * Neither the name of Shibboleth nor the names of its contributors, nor
24 * Internet2, nor the University Corporation for Advanced Internet Development,
25 * Inc., nor UCAID may be used to endorse or promote products derived from this
26 * software without specific prior written permission. For written permission,
27 * please contact shibboleth@shibboleth.org
29 * Products derived from this software may not be called Shibboleth, Internet2,
30 * UCAID, or the University Corporation for Advanced Internet Development, nor
31 * may Shibboleth appear in their name, without prior written permission of the
32 * University Corporation for Advanced Internet Development.
35 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
36 * AND WITH ALL FAULTS. ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
37 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS FOR A
38 * PARTICULAR PURPOSE, AND NON-INFRINGEMENT ARE DISCLAIMED AND THE ENTIRE RISK
39 * OF SATISFACTORY QUALITY, PERFORMANCE, ACCURACY, AND EFFORT IS WITH LICENSEE.
40 * IN NO EVENT SHALL THE COPYRIGHT OWNER, CONTRIBUTORS OR THE UNIVERSITY
41 * CORPORATION FOR ADVANCED INTERNET DEVELOPMENT, INC. BE LIABLE FOR ANY DIRECT,
42 * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
43 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
44 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
45 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
46 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
47 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
51 * shib-config.cpp -- ShibTarget initialization and finalization routines
53 * Created By: Derek Atkins <derek@ihtfp.com>
60 #include <shib/shib-threads.h>
62 #include <log4cpp/PropertyConfigurator.hh>
63 #include <log4cpp/Category.hh>
65 #ifndef SHIBTARGET_INIFILE
66 #define SHIBTARGET_INIFILE "/opt/shibboleth/etc/shibboleth/shibboleth.ini"
69 class STConfig : public ShibTargetConfig
72 STConfig(const char* app_name, const char* inifile);
76 ShibINI& getINI() { return *ini; }
78 Iterator<const XMLCh*> getPolicies() { return Iterator<const XMLCh*>(policies); }
87 vector<const XMLCh*> policies;
90 vector<string> m_SocketACL;
92 friend ShibSockName shib_target_sockname();
93 friend ShibSockName shib_target_sockacl(unsigned int);
97 STConfig * g_Config = NULL;
98 Mutex * g_lock = NULL;
101 CCache* shibtarget::g_shibTargetCCache = NULL;
103 /****************************************************************************/
104 // External Interface
107 void ShibTargetConfig::preinit()
110 g_lock = Mutex::create();
113 ShibTargetConfig& ShibTargetConfig::init(const char* app_name, const char* inifile)
116 throw runtime_error ("ShibTargetConfig not pre-initialized");
119 throw runtime_error ("No Application name");
127 g_Config = new STConfig(app_name, inifile);
132 ShibTargetConfig& ShibTargetConfig::getConfig()
135 throw SAMLException("ShibTargetConfig::getConfig() called with NULL configuration");
139 /****************************************************************************/
142 STConfig::STConfig(const char* app_name, const char* inifile)
143 : samlConf(SAMLConfig::getConfig()), shibConf(ShibConfig::getConfig()),
147 ini = new ShibINI((inifile ? inifile : SHIBTARGET_INIFILE));
149 cerr << "Unable to load the INI file: " <<
150 (inifile ? inifile : SHIBTARGET_INIFILE) << endl;
155 void STConfig::init()
157 string app = m_app_name;
160 // Initialize Log4cpp
161 if (ini->get_tag (app, SHIBTARGET_TAG_LOGGER, true, &tag)) {
162 cerr << "Trying to load logger configuration: " << tag << "\n";
164 PropertyConfigurator::configure(tag);
165 } catch (ConfigureFailure& e) {
166 cerr << "Error reading configuration: " << e.what() << "\n";
169 Category& category = Category::getRoot();
170 category.setPriority(log4cpp::Priority::DEBUG);
171 cerr << "No logger configuration found\n";
174 Category& log = Category::getInstance("shibtarget.STConfig");
176 saml::NDC ndc("STConfig::init");
178 // Init SAML Configuration
179 if (ini->get_tag (app, SHIBTARGET_TAG_SAMLCOMPAT, true, &tag))
180 samlConf.compatibility_mode = ShibINI::boolean(tag);
181 if (ini->get_tag (app, SHIBTARGET_TAG_SCHEMAS, true, &tag))
182 samlConf.schema_dir = tag;
184 // Init SAML Binding Configuration
185 if (ini->get_tag (app, SHIBTARGET_TAG_AATIMEOUT, true, &tag))
186 samlConf.binding_defaults.timeout = atoi(tag.c_str());
187 if (ini->get_tag (app, SHIBTARGET_TAG_AACONNECTTO, true, &tag))
188 samlConf.binding_defaults.conn_timeout = atoi(tag.c_str());
189 if (ini->get_tag (app, SHIBTARGET_TAG_CERTFILE, true, &tag))
190 samlConf.binding_defaults.ssl_certfile = tag;
191 if (ini->get_tag (app, SHIBTARGET_TAG_KEYFILE, true, &tag))
192 samlConf.binding_defaults.ssl_keyfile = tag;
193 if (ini->get_tag (app, SHIBTARGET_TAG_KEYPASS, true, &tag))
194 samlConf.binding_defaults.ssl_keypass = tag;
195 if (ini->get_tag (app, SHIBTARGET_TAG_CALIST, true, &tag))
196 samlConf.binding_defaults.ssl_calist = tag;
199 if (!samlConf.init()) {
200 log.fatal ("Failed to initialize SAML Library");
201 throw runtime_error ("Failed to initialize SAML Library");
203 log.debug ("SAML Initialized");
205 log.crit ("Died initializing SAML Library");
211 if (!shibConf.init()) {
212 log.fatal ("Failed to initialize Shib library");
213 throw runtime_error ("Failed to initialize Shib Library");
215 log.debug ("Shib Initialized");
217 log.crit ("Failed initializing Shib library.");
221 // Load any SAML extensions
222 string ext = "extensions:saml";
223 if (ini->exists(ext)) {
224 saml::NDC ndc("load_extensions");
225 ShibINI::Iterator* iter = ini->tag_iterator(ext);
227 for (const string* str = iter->begin(); str; str = iter->next()) {
228 string file = ini->get(ext, *str);
231 samlConf.saml_register_extension(file.c_str(),ini);
232 log.debug("%s: loading %s", str->c_str(), file.c_str());
234 catch (SAMLException& e)
236 log.crit("%s: %s", str->c_str(), e.what());
242 // Load the specified metadata.
243 if (ini->get_tag(app, SHIBTARGET_TAG_METADATA, true, &tag) && ini->exists(tag))
245 ShibINI::Iterator* iter=ini->tag_iterator(tag);
246 for (const string* prov=iter->begin(); prov; prov=iter->next())
248 const string source=ini->get(tag,*prov);
249 log.info("registering metadata provider: type=%s, source=%s",prov->c_str(),source.c_str());
250 if (!shibConf.addMetadata(prov->c_str(),source.c_str()))
252 log.crit("error adding metadata provider: type=%s, source=%s",prov->c_str(),source.c_str());
253 if (!strcmp(app.c_str(), SHIBTARGET_SHAR))
254 throw runtime_error("error adding metadata provider");
260 // Load SAML policies.
261 if (ini->exists(SHIBTARGET_POLICIES)) {
262 log.info("loading SAML policies");
263 ShibINI::Iterator* iter = ini->tag_iterator(SHIBTARGET_POLICIES);
265 for (const string* str = iter->begin(); str; str = iter->next()) {
266 policies.push_back(XMLString::transcode(ini->get(SHIBTARGET_POLICIES, *str).c_str()));
271 // Initialize the SHAR Cache
272 if (!strcmp (app.c_str(), SHIBTARGET_SHAR)) {
273 const char * cache_type = NULL;
274 if (ini->get_tag (app, SHIBTARGET_TAG_CACHETYPE, true, &tag))
275 cache_type = tag.c_str();
277 g_shibTargetCCache = CCache::getInstance(cache_type);
280 // Process socket settings.
281 m_SocketName=ini->get(SHIBTARGET_GENERAL, "sharsocket");
282 if (m_SocketName.empty())
283 m_SocketName=SHIB_SHAR_SOCKET;
286 string sockacl=ini->get(SHIBTARGET_SHAR, "sharacl");
287 if (sockacl.length()>0)
290 for (int i = 0; i < sockacl.length(); i++)
292 if (sockacl.at(i)==' ')
294 string addr=sockacl.substr(j, i-j);
296 m_SocketACL.push_back(addr);
299 string addr=sockacl.substr(j, sockacl.length()-j);
300 m_SocketACL.push_back(addr);
303 m_SocketACL.push_back("127.0.0.1");
307 log.debug("finished");
310 STConfig::~STConfig()
312 for (vector<const XMLCh*>::iterator i=policies.begin(); i!=policies.end(); i++)
313 delete const_cast<XMLCh*>(*i);
317 if (g_shibTargetCCache)
318 delete g_shibTargetCCache;
329 void STConfig::shutdown()
338 extern "C" ShibSockName shib_target_sockname(void)
340 return (g_Config ? g_Config->m_SocketName.c_str() : (ShibSockName)0);
343 extern "C" ShibSockName shib_target_sockacl(unsigned int index)
346 if (g_Config && index<g_Config->m_SocketACL.size())
347 return g_Config->m_SocketACL[index].c_str();
349 return (ShibSockName)0;