Shell of new SP object interface to replace old IConfig layer.
[shibboleth/cpp-sp.git] / shibsp / ListenerService.cpp
1 /*
2  *  Copyright 2001-2006 Internet2
3  * 
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *     http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16
17 /**
18  * ListenerService.cpp
19  * 
20  * Interprocess remoting engine.
21  */
22
23 #include "internal.h"
24 #include "exceptions.h"
25 #include "ListenerService.h"
26
27 #include <log4cpp/Category.hh>
28 #include <xercesc/dom/DOM.hpp>
29
30 using namespace shibsp;
31 using namespace xmltooling;
32 using namespace log4cpp;
33 using namespace xercesc;
34 using namespace std;
35
36 namespace shibsp {
37     //SHIBSP_DLLLOCAL PluginManager<ListenerService,const DOMElement*>::Factory MemoryListenerServiceFactory;
38     SHIBSP_DLLLOCAL PluginManager<ListenerService,const DOMElement*>::Factory TCPListenerServiceFactory;
39 #ifndef WIN32
40     SHIBSP_DLLLOCAL PluginManager<ListenerService,const DOMElement*>::Factory UnixListenerServiceFactory;
41 #endif
42 };
43
44 void SHIBSP_API shibsp::registerListenerServices()
45 {
46     SPConfig& conf=SPConfig::getConfig();
47     //conf.ListenerServiceManager.registerFactory(MEMORY_LISTENER_SERVICE, MemoryListenerServiceFactory);
48     conf.ListenerServiceManager.registerFactory(TCP_LISTENER_SERVICE, TCPListenerServiceFactory);
49 #ifndef WIN32
50     conf.ListenerServiceManager.registerFactory(UNIX_LISTENER_SERVICE, UnixListenerServiceFactory);
51 #endif
52 }
53
54 Remoted* ListenerService::regListener(const char* address, Remoted* listener)
55 {
56     Remoted* ret=NULL;
57     map<string,Remoted*>::const_iterator i=m_listenerMap.find(address);
58     if (i!=m_listenerMap.end())
59         ret=i->second;
60     m_listenerMap[address]=listener;
61     Category::getInstance(SHIBSP_LOGCAT".Listener").info("registered remoted message endpoint (%s)",address);
62     return ret;
63 }
64
65 bool ListenerService::unregListener(const char* address, Remoted* current, Remoted* restore)
66 {
67     map<string,Remoted*>::const_iterator i=m_listenerMap.find(address);
68     if (i!=m_listenerMap.end() && i->second==current) {
69         if (restore)
70             m_listenerMap[address]=restore;
71         else
72             m_listenerMap.erase(address);
73         Category::getInstance(SHIBSP_LOGCAT".Listener").info("unregistered remoted message endpoint (%s)",address);
74         return true;
75     }
76     return false;
77 }
78
79 Remoted* ListenerService::lookup(const char *address) const
80 {
81     map<string,Remoted*>::const_iterator i=m_listenerMap.find(address);
82     return (i==m_listenerMap.end()) ? NULL : i->second;
83 }
84
85 DDF ListenerService::receive(const DDF &in)
86 {
87     if (!in.name())
88         throw ListenerException("Incoming message with no destination address rejected.");
89     else if (!strcmp("ping",in.name())) {
90         DDF out=DDF(NULL).integer(in.integer() + 1);
91         return out;
92     }
93
94     Remoted* dest=lookup(in.name());
95     if (!dest)
96         throw ListenerException("No destination registered for incoming message addressed to ($1).",params(1,in.name()));
97     
98     return dest->receive(in);
99 }