IPC: Support older glib
[platform/core/security/vasum.git] / common / ipc / service.hpp
1 /*
2 *  Copyright (c) 2015 Samsung Electronics Co., Ltd All Rights Reserved
3 *
4 *  Contact: Jan Olszak <j.olszak@samsung.com>
5 *
6 *  Licensed under the Apache License, Version 2.0 (the "License");
7 *  you may not use this file except in compliance with the License.
8 *  You may obtain a copy of the License at
9 *
10 *      http://www.apache.org/licenses/LICENSE-2.0
11 *
12 *  Unless required by applicable law or agreed to in writing, software
13 *  distributed under the License is distributed on an "AS IS" BASIS,
14 *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 *  See the License for the specific language governing permissions and
16 *  limitations under the License
17 */
18
19 /**
20  * @file
21  * @author  Jan Olszak (j.olszak@samsung.com)
22  * @brief   Declaration of the IPC handling class
23  */
24
25 #ifndef COMMON_IPC_SERVICE_HPP
26 #define COMMON_IPC_SERVICE_HPP
27
28 #include "ipc/internals/processor.hpp"
29 #include "ipc/internals/acceptor.hpp"
30 #include "ipc/ipc-gsource.hpp"
31 #include "ipc/types.hpp"
32 #include "logger/logger.hpp"
33
34 #include <string>
35
36 namespace vasum {
37 namespace ipc {
38
39
40 /**
41  * This class wraps communication via UX sockets.
42  * It uses serialization mechanism from libConfig.
43  *
44  * There are two working threads:
45  * - ACCEPTOR accepts incoming connections and passes them to PROCESSOR
46  * - PROCESSOR is responsible for the communication and calling the callbacks
47  *
48  * For message format @see ipc::Processor
49  */
50 class Service {
51 public:
52     /**
53      * @param path path to the socket
54      */
55     Service(const std::string& path,
56             const PeerCallback& addPeerCallback = nullptr,
57             const PeerCallback& removePeerCallback = nullptr);
58     ~Service();
59
60     Service(const Service&) = delete;
61     Service& operator=(const Service&) = delete;
62
63     /**
64      * Starts the worker and acceptor threads
65      *
66      * @param usesExternalPolling internal or external polling is used
67      */
68     void start(const bool usesExternalPolling = false);
69
70     /**
71     * @return is the communication thread running
72     */
73     bool isStarted();
74
75     /**
76      * Stops all working threads
77      */
78     void stop();
79
80     /**
81      * Used with an external polling loop.
82      * Handles one event from the file descriptor.
83      *
84      * @param fd file descriptor
85      * @param pollEvent event on the fd. Defined in poll.h
86      *
87      */
88     void handle(const FileDescriptor fd, const short pollEvent);
89
90     /**
91     * Set the callback called for each new connection to a peer
92     *
93     * @param newPeerCallback the callback
94     */
95     void setNewPeerCallback(const PeerCallback& newPeerCallback);
96
97     /**
98      * Set the callback called when connection to a peer is lost
99      *
100      * @param removedPeerCallback the callback
101      */
102     void setRemovedPeerCallback(const PeerCallback& removedPeerCallback);
103
104     /**
105      * Saves the callback connected to the method id.
106      * When a message with the given method id is received
107      * the data will be parsed and passed to this callback.
108      *
109      * @param methodID API dependent id of the method
110      * @param method method handling implementation
111      */
112     template<typename SentDataType, typename ReceivedDataType>
113     void setMethodHandler(const MethodID methodID,
114                           const typename MethodHandler<SentDataType, ReceivedDataType>::type& method);
115
116     /**
117      * Saves the callback connected to the method id.
118      * When a message with the given method id is received
119      * the data will be parsed and passed to this callback.
120      *
121      * @param methodID API dependent id of the method
122      * @param handler handling implementation
123      * @tparam ReceivedDataType data type to serialize
124      */
125     template<typename ReceivedDataType>
126     void setSignalHandler(const MethodID methodID,
127                           const typename SignalHandler<ReceivedDataType>::type& handler);
128
129     /**
130      * Removes the callback
131      *
132      * @param methodID API dependent id of the method
133      */
134     void removeMethod(const MethodID methodID);
135
136     /**
137      * Synchronous method call.
138      *
139      * @param methodID API dependent id of the method
140      * @param data data to send
141      * @return result data
142      */
143     template<typename SentDataType, typename ReceivedDataType>
144     std::shared_ptr<ReceivedDataType> callSync(const MethodID methodID,
145                                                const FileDescriptor peerFD,
146                                                const std::shared_ptr<SentDataType>& data,
147                                                unsigned int timeoutMS = 500);
148
149     /**
150      * Asynchronous method call. The return callback will be called on
151      * return data arrival. It will be run in the PROCESSOR thread.
152      *
153      *
154      * @param methodID API dependent id of the method
155      * @param data data to send
156      * @param resultCallback callback for result serialization and handling
157      */
158     template<typename SentDataType, typename ReceivedDataType>
159     void callAsync(const MethodID methodID,
160                    const FileDescriptor peerFD,
161                    const std::shared_ptr<SentDataType>& data,
162                    const typename ResultHandler<ReceivedDataType>::type& resultCallback);
163
164     /**
165     * Send a signal to the peer.
166     * There is no return value from the peer
167     * Sends any data only if a peer registered this a signal
168     *
169     * @param methodID API dependent id of the method
170     * @param data data to sent
171     * @tparam SentDataType data type to send
172     */
173     template<typename SentDataType>
174     void signal(const MethodID methodID,
175                 const std::shared_ptr<SentDataType>& data);
176 private:
177
178     void startPoll();
179     void stopPoll();
180
181     typedef std::lock_guard<std::mutex> Lock;
182     Processor mProcessor;
183     Acceptor mAcceptor;
184     IPCGSource::Pointer mIPCGSourcePtr;
185 };
186
187
188 template<typename SentDataType, typename ReceivedDataType>
189 void Service::setMethodHandler(const MethodID methodID,
190                                const typename MethodHandler<SentDataType, ReceivedDataType>::type& method)
191 {
192     LOGS("Service setMethodHandler, methodID " << methodID);
193     mProcessor.setMethodHandler<SentDataType, ReceivedDataType>(methodID, method);
194 }
195
196 template<typename ReceivedDataType>
197 void Service::setSignalHandler(const MethodID methodID,
198                                const typename SignalHandler<ReceivedDataType>::type& handler)
199 {
200     LOGS("Service setSignalHandler, methodID " << methodID);
201     mProcessor.setSignalHandler<ReceivedDataType>(methodID, handler);
202 }
203
204 template<typename SentDataType, typename ReceivedDataType>
205 std::shared_ptr<ReceivedDataType> Service::callSync(const MethodID methodID,
206                                                     const FileDescriptor peerFD,
207                                                     const std::shared_ptr<SentDataType>& data,
208                                                     unsigned int timeoutMS)
209 {
210     LOGS("Service callSync, methodID: " << methodID
211          << ", peerFD: " << peerFD
212          << ", timeoutMS: " << timeoutMS);
213     return mProcessor.callSync<SentDataType, ReceivedDataType>(methodID, peerFD, data, timeoutMS);
214 }
215
216 template<typename SentDataType, typename ReceivedDataType>
217 void Service::callAsync(const MethodID methodID,
218                         const FileDescriptor peerFD,
219                         const std::shared_ptr<SentDataType>& data,
220                         const typename ResultHandler<ReceivedDataType>::type& resultCallback)
221 {
222     LOGS("Service callAsync, methodID: " << methodID << ", peerFD: " << peerFD);
223     mProcessor.callAsync<SentDataType,
224                          ReceivedDataType>(methodID,
225                                            peerFD,
226                                            data,
227                                            resultCallback);
228 }
229
230 template<typename SentDataType>
231 void Service::signal(const MethodID methodID,
232                      const std::shared_ptr<SentDataType>& data)
233 {
234     LOGS("Service signal, methodID: " << methodID);
235     mProcessor.signal<SentDataType>(methodID, data);
236 }
237
238 } // namespace ipc
239 } // namespace vasum
240
241 #endif // COMMON_IPC_SERVICE_HPP