From: Lukasz Wojciechowski Date: Mon, 16 Jun 2014 19:46:23 +0000 (+0200) Subject: Add early cynara service implementation X-Git-Tag: v0.1.0~106 X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=760facd6b8ef1559937bae850979f5f4d737a5c2;p=platform%2Fcore%2Fsecurity%2Fcynara.git Add early cynara service implementation Change-Id: I3007944f08f9c29cab6e6b755c4996f38db3ab0d --- diff --git a/src/common/common.h b/src/common/common.h index f69a5b31..8637231f 100644 --- a/src/common/common.h +++ b/src/common/common.h @@ -27,6 +27,9 @@ #include "attributes/attributes.h" #include "attributes/debug_attributes.h" +#include "containers/BinaryQueue.h" +#include "containers/RawBuffer.h" + #include "result/Result.h" #include "types/PolicyTypeExtension.h" diff --git a/src/common/containers/RawBuffer.h b/src/common/containers/RawBuffer.h new file mode 100644 index 00000000..1e320de2 --- /dev/null +++ b/src/common/containers/RawBuffer.h @@ -0,0 +1,34 @@ +/* + * Copyright (c) 2014 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/* + * @file RawBuffer.h + * @author Lukasz Wojciechowski + * @version 1.0 + * @brief This file defines binary raw buffer type + */ + +#ifndef SRC_COMMON_CONTAINERS_RAWBUFFER_H_ +#define SRC_COMMON_CONTAINERS_RAWBUFFER_H_ + +#include + +namespace Cynara { + +typedef std::vector RawBuffer; + +} // namespace Cynara + +#endif /* SRC_COMMON_CONTAINERS_RAWBUFFER_H_ */ diff --git a/src/common/exceptions/InitException.h b/src/common/exceptions/InitException.h new file mode 100644 index 00000000..f3f69fa8 --- /dev/null +++ b/src/common/exceptions/InitException.h @@ -0,0 +1,40 @@ +/* + * Copyright (c) 2014 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/* + * @file UnexpectedErrorException.h + * @author Lukasz Wojciechowski + * @version 1.0 + * @brief Implementation of InitException + */ + +#ifndef SRC_COMMON_EXCEPTIONS_INITEXCEPTION_H_ +#define SRC_COMMON_EXCEPTIONS_INITEXCEPTION_H_ + +#include "Exception.h" + +#include + +namespace Cynara { + +class InitException : public Exception { +public: + InitException() = default; + virtual ~InitException() = default; +}; + +} /* namespace Cynara */ + +#endif /* SRC_COMMON_EXCEPTIONS_INITEXCEPTION_H_ */ diff --git a/src/common/exceptions/UnexpectedErrorException.h b/src/common/exceptions/UnexpectedErrorException.h new file mode 100644 index 00000000..9d858f40 --- /dev/null +++ b/src/common/exceptions/UnexpectedErrorException.h @@ -0,0 +1,55 @@ +/* + * Copyright (c) 2014 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/* + * @file UnexpectedErrorException.h + * @author Lukasz Wojciechowski + * @version 1.0 + * @brief Implementation of UnexpectedErrorException + */ + +#ifndef SRC_COMMON_EXCEPTIONS_UNEXPECTEDERROREXCEPTION_H_ +#define SRC_COMMON_EXCEPTIONS_UNEXPECTEDERROREXCEPTION_H_ + +#include +#include + +#include "Exception.h" + +namespace Cynara { + +class UnexpectedErrorException : public Exception { +private: + std::string m_whatMessage; + +public: + UnexpectedErrorException() = delete; + UnexpectedErrorException(int errorCode, const char *errorMsg) { + std::ostringstream stream; + stream << "UnexpectedErrorException with errorCode =[" << errorCode << "] and message <"; + stream << errorMsg << ">"; + m_whatMessage = stream.str(); + } + + virtual ~UnexpectedErrorException() = default; + + virtual const char* what() const noexcept { + return m_whatMessage.c_str(); + } +}; + +} // namespace Cynara + +#endif /* SRC_COMMON_EXCEPTIONS_UNEXPECTEDERROREXCEPTION_H_ */ diff --git a/src/service/CMakeLists.txt b/src/service/CMakeLists.txt index a5805547..206b64de 100644 --- a/src/service/CMakeLists.txt +++ b/src/service/CMakeLists.txt @@ -19,7 +19,17 @@ SET(CYNARA_SERVICE_PATH ${CYNARA_PATH}/service) SET(CYNARA_SOURCES + ${CYNARA_SERVICE_PATH}/logic/Logic.cpp + ${CYNARA_SERVICE_PATH}/main/Cynara.cpp ${CYNARA_SERVICE_PATH}/main/main.cpp + ${CYNARA_SERVICE_PATH}/protocol/Protocol.cpp + ${CYNARA_SERVICE_PATH}/protocol/ProtocolAdmin.cpp + ${CYNARA_SERVICE_PATH}/protocol/ProtocolClient.cpp + ${CYNARA_SERVICE_PATH}/protocol/ProtocolSignal.cpp + ${CYNARA_SERVICE_PATH}/request/Request.cpp + ${CYNARA_SERVICE_PATH}/request/RequestContext.cpp + ${CYNARA_SERVICE_PATH}/sockets/Descriptor.cpp + ${CYNARA_SERVICE_PATH}/sockets/SocketManager.cpp ${CYNARA_SERVICE_PATH}/storage/Storage.cpp ) @@ -29,7 +39,7 @@ SET_SOURCE_FILES_PROPERTIES( COMPILE_FLAGS "-D_GNU_SOURCE -fvisibility=hidden") INCLUDE_DIRECTORIES( - ${CYNARA_SERVICE_PATH}/main + ${CYNARA_SERVICE_PATH} ) ADD_EXECUTABLE(${TARGET_CYNARA} ${CYNARA_SOURCES}) diff --git a/src/service/logic/Logic.cpp b/src/service/logic/Logic.cpp new file mode 100644 index 00000000..0556c4fe --- /dev/null +++ b/src/service/logic/Logic.cpp @@ -0,0 +1,31 @@ +/* + * Copyright (c) 2014 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/* + * @file Logic.cpp + * @author Lukasz Wojciechowski + * @version 1.0 + * @brief This file implements main class of logic layer in cynara service + */ + +#include "Logic.h" + +namespace Cynara { +Logic::Logic() { +} + +Logic::~Logic() { +} +} // namespace Cynara diff --git a/src/service/logic/Logic.h b/src/service/logic/Logic.h new file mode 100644 index 00000000..e957196f --- /dev/null +++ b/src/service/logic/Logic.h @@ -0,0 +1,36 @@ +/* + * Copyright (c) 2014 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/* + * @file Logic.h + * @author Lukasz Wojciechowski + * @version 1.0 + * @brief This file defines main class of logic layer in cynara service + */ + +#ifndef SRC_SERVICE_LOGIC_LOGIC_H_ +#define SRC_SERVICE_LOGIC_LOGIC_H_ + +namespace Cynara { + +class Logic { +public: + Logic(); + ~Logic(); +}; + +} // namespace Cynara + +#endif /* SRC_SERVICE_LOGIC_LOGIC_H_ */ diff --git a/src/service/main/Cynara.cpp b/src/service/main/Cynara.cpp new file mode 100644 index 00000000..2d4b1b93 --- /dev/null +++ b/src/service/main/Cynara.cpp @@ -0,0 +1,61 @@ +/* + * Copyright (c) 2014 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/* + * @file Cynara.cpp + * @author Lukasz Wojciechowski + * @version 1.0 + * @brief This file implements main class of cynara service + */ + +#include +#include "Cynara.h" + +namespace Cynara { + +Cynara::Cynara() : m_logic(nullptr), m_socketManager(nullptr) { +} + +Cynara* Cynara::getInstance(void) { + static Cynara instance; + return &instance; +} + +Cynara::~Cynara() { +} + +void Cynara::init(void) { + getInstance()->m_logic = new Logic(); + getInstance()->m_socketManager = new SocketManager(); +} + +void Cynara::run(void) { + getInstance()->m_socketManager->run(); +} + +void Cynara::finalize(void) { + delete getInstance()->m_socketManager; + delete getInstance()->m_logic; +} + +Logic* Cynara::getLogic(void) { + return getInstance()->m_logic; +} + +SocketManager* Cynara::getSocketManager(void) { + return getInstance()->m_socketManager; +} + +} // namespace Cynara diff --git a/src/service/main/Cynara.h b/src/service/main/Cynara.h new file mode 100644 index 00000000..0d335ac8 --- /dev/null +++ b/src/service/main/Cynara.h @@ -0,0 +1,54 @@ +/* + * Copyright (c) 2014 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/* + * @file Cynara.h + * @author Lukasz Wojciechowski + * @version 1.0 + * @brief This file defines main class of cynara service + */ + +#ifndef SRC_SERVICE_MAIN_CYNARA_H_ +#define SRC_SERVICE_MAIN_CYNARA_H_ + +#include +#include + +namespace Cynara { + +class Cynara { +private: + Logic *m_logic; + SocketManager *m_socketManager; + + Cynara(); + + static Cynara* getInstance(void); + +public: + ~Cynara(); + + static void init(void); + static void run(void); + static void finalize(void); + + static Logic* getLogic(void); + static SocketManager* getSocketManager(void); + +}; + +} // namespace Cynara + +#endif /* SRC_SERVICE_MAIN_CYNARA_H_ */ diff --git a/src/service/main/main.cpp b/src/service/main/main.cpp index 7a6ffaca..cfe17e7f 100644 --- a/src/service/main/main.cpp +++ b/src/service/main/main.cpp @@ -23,75 +23,57 @@ * @brief Main Cynara daemon file */ -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include +//#include +#include +//#include +//#include +//#include +#include +//#include +//#include +//#include +//#include +//#include #include #include -// Temporary "exit tool" -// After implementing the real main we must provide better way to inform daemon -// about our will. -static int goodbye = 0; - -// Handle kill message from systemd -// Typically signal SIGTERM is used - depends on configuration in service file -void kill_handler(int sig) { - (void) sig; - LOGD("Cynara service is going down now"); - // As said above, this exitting way should be changed - goodbye = 1; -} +#include +#include +#include "Cynara.h" -int main(int argc, char **argv) { - (void) argc; - (void) argv; +using namespace Cynara; +int main(int argc UNUSED, char **argv UNUSED) { int ret; - struct sigaction act; - int it = 0; // TODO: remove me soon - - LOGI("Cynara service is started"); - - // Install kill handler - TERM signal will be delivered form systemd to kill this service - memset(&act, 0, sizeof(act)); - act.sa_handler = &kill_handler; - if ((ret = sigaction(SIGTERM, &act, NULL)) < 0) { - LOGE("sigaction failed [%d]", ret); - return 1; - } init_log(); - // Do some initialization here - // Now notify systemd that cynara is ready to fulfil its destiny - ret = sd_notify(0, "READY=1"); - if (ret == 0) { - LOGW("Cynara was not configured to notify its status"); - } else if (ret < 0) { - LOGE("sd_notify failed [%d]", ret); + try { + LOGI("Cynara service is starting ..."); + Cynara::Cynara::init(); + LOGI("Cynara service is started"); + + ret = sd_notify(0, "READY=1"); + if (ret == 0) { + LOGW("Cynara was not configured to notify its status"); + } else if (ret < 0) { + LOGE("sd_notify failed [%d]", ret); + } + + LOGD("Starting the real job"); + Cynara::Cynara::run(); + + LOGD("Time to clean up."); + Cynara::Cynara::finalize(); + LOGD("Cynara service is stopped"); + } catch (std::exception &e) { + LOGC("Cynara stoped because of unhandled exception: %s", e.what()); + return EXIT_FAILURE; + } catch (...) { + LOGC("Cynara stoped because of unknown unhanndled exception."); + return EXIT_FAILURE; } - LOGD("Starting the real job"); - - while (!goodbye) { - TEMP_FAILURE_RETRY(sleep(1)); - - LOGD("Iteration: % 5d", it++); - // TODO: remove me soon - } - - LOGD("Cynara service is stopped"); - - return 0; + return EXIT_SUCCESS; } - diff --git a/src/service/protocol/Protocol.cpp b/src/service/protocol/Protocol.cpp new file mode 100644 index 00000000..657dd7b8 --- /dev/null +++ b/src/service/protocol/Protocol.cpp @@ -0,0 +1,33 @@ +/* + * Copyright (c) 2014 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/* + * @file Protocol.cpp + * @author Lukasz Wojciechowski + * @version 1.0 + * @brief This file implements protocol base class + */ + +#include "Protocol.h" + +namespace Cynara { + +Protocol::Protocol() { +} + +Protocol::~Protocol() { +} + +} // namespace Cynara diff --git a/src/service/protocol/Protocol.h b/src/service/protocol/Protocol.h new file mode 100644 index 00000000..e0fa8efe --- /dev/null +++ b/src/service/protocol/Protocol.h @@ -0,0 +1,41 @@ +/* + * Copyright (c) 2014 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/* + * @file Protocol.h + * @author Lukasz Wojciechowski + * @version 1.0 + * @brief This file defines protocol base class + */ + +#ifndef SRC_SERVICE_PROTOCOL_PROTOCOL_H_ +#define SRC_SERVICE_PROTOCOL_PROTOCOL_H_ + +#include +#include + +namespace Cynara { + +class Protocol { +public: + Protocol(); + virtual ~Protocol(); + + virtual Request *extractRequestFromBuffer(BinaryQueue &bufferQueue) = 0; +}; + +} // namespace Cynara + +#endif /* SRC_SERVICE_PROTOCOL_PROTOCOL_H_ */ diff --git a/src/service/protocol/ProtocolAdmin.cpp b/src/service/protocol/ProtocolAdmin.cpp new file mode 100644 index 00000000..c130d8c4 --- /dev/null +++ b/src/service/protocol/ProtocolAdmin.cpp @@ -0,0 +1,38 @@ +/* + * Copyright (c) 2014 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/* + * @file ProtocolAdmin.cpp + * @author Lukasz Wojciechowski + * @version 1.0 + * @brief This file implements protocol class for administration + */ + +#include +#include "ProtocolAdmin.h" + +namespace Cynara { + +ProtocolAdmin::ProtocolAdmin() { +} + +ProtocolAdmin::~ProtocolAdmin() { +} + +Request *ProtocolAdmin::extractRequestFromBuffer(BinaryQueue& bufferQueue) { + TODO_USE_ME(bufferQueue); + return nullptr; +} +} // namespace Cynara diff --git a/src/service/protocol/ProtocolAdmin.h b/src/service/protocol/ProtocolAdmin.h new file mode 100644 index 00000000..3ca0769f --- /dev/null +++ b/src/service/protocol/ProtocolAdmin.h @@ -0,0 +1,40 @@ +/* + * Copyright (c) 2014 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/* + * @file ProtocolAdmin.h + * @author Lukasz Wojciechowski + * @version 1.0 + * @brief This file defines protocol class for administration + */ + +#ifndef SRC_SERVICE_PROTOCOL_PROTOCOLADMIN_H_ +#define SRC_SERVICE_PROTOCOL_PROTOCOLADMIN_H_ + +#include "Protocol.h" + +namespace Cynara { + +class ProtocolAdmin : public Protocol { +public: + ProtocolAdmin(); + virtual ~ProtocolAdmin(); + + virtual Request *extractRequestFromBuffer(BinaryQueue &bufferQueue); +}; + +} // namespace Cynara + +#endif /* SRC_SERVICE_PROTOCOL_PROTOCOLADMIN_H_ */ diff --git a/src/service/protocol/ProtocolClient.cpp b/src/service/protocol/ProtocolClient.cpp new file mode 100644 index 00000000..12dd34f2 --- /dev/null +++ b/src/service/protocol/ProtocolClient.cpp @@ -0,0 +1,39 @@ +/* + * Copyright (c) 2014 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/* + * @file ProtocolClient.cpp + * @author Lukasz Wojciechowski + * @version 1.0 + * @brief This file implements protocol class for communication with client + */ + +#include +#include "ProtocolClient.h" + +namespace Cynara { + +ProtocolClient::ProtocolClient() { +} + +ProtocolClient::~ProtocolClient() { +} + +Request *ProtocolClient::extractRequestFromBuffer(BinaryQueue& bufferQueue) { + TODO_USE_ME(bufferQueue); + return nullptr; +} + +} // namespace Cynara diff --git a/src/service/protocol/ProtocolClient.h b/src/service/protocol/ProtocolClient.h new file mode 100644 index 00000000..f4deae37 --- /dev/null +++ b/src/service/protocol/ProtocolClient.h @@ -0,0 +1,40 @@ +/* + * Copyright (c) 2014 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/* + * @file ProtocolClient.h + * @author Lukasz Wojciechowski + * @version 1.0 + * @brief This file defines protocol class for communication with client + */ + +#ifndef SRC_SERVICE_PROTOCOL_PROTOCOLCLIENT_H_ +#define SRC_SERVICE_PROTOCOL_PROTOCOLCLIENT_H_ + +#include "Protocol.h" + +namespace Cynara { + +class ProtocolClient : public Protocol { +public: + ProtocolClient(); + virtual ~ProtocolClient(); + + virtual Request *extractRequestFromBuffer(BinaryQueue &bufferQueue); +}; + +} // namespace Cynara + +#endif /* SRC_SERVICE_PROTOCOL_PROTOCOLCLIENT_H_ */ diff --git a/src/service/protocol/ProtocolSignal.cpp b/src/service/protocol/ProtocolSignal.cpp new file mode 100644 index 00000000..e20d13fc --- /dev/null +++ b/src/service/protocol/ProtocolSignal.cpp @@ -0,0 +1,39 @@ +/* + * Copyright (c) 2014 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/* + * @file ProtocolSignal.cpp + * @author Lukasz Wojciechowski + * @version 1.0 + * @brief This file implements protocol class for signals + */ + +#include +#include "ProtocolSignal.h" + +namespace Cynara { + +ProtocolSignal::ProtocolSignal() { +} + +ProtocolSignal::~ProtocolSignal() { +} + +Request *ProtocolSignal::extractRequestFromBuffer(BinaryQueue& bufferQueue) { + TODO_USE_ME(bufferQueue); + return nullptr; +} + +} // namespace Cynara diff --git a/src/service/protocol/ProtocolSignal.h b/src/service/protocol/ProtocolSignal.h new file mode 100644 index 00000000..a5400523 --- /dev/null +++ b/src/service/protocol/ProtocolSignal.h @@ -0,0 +1,40 @@ +/* + * Copyright (c) 2014 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/* + * @file ProtocolSignal.h + * @author Lukasz Wojciechowski + * @version 1.0 + * @brief This file defines protocol class for signals + */ + +#ifndef SRC_SERVICE_PROTOCOL_PROTOCOLSIGNAL_H_ +#define SRC_SERVICE_PROTOCOL_PROTOCOLSIGNAL_H_ + +#include "Protocol.h" + +namespace Cynara { + +class ProtocolSignal : public Protocol { +public: + ProtocolSignal(); + virtual ~ProtocolSignal(); + + virtual Request *extractRequestFromBuffer(BinaryQueue &bufferQueue); +}; + +} // namespace Cynara + +#endif /* SRC_SERVICE_PROTOCOL_PROTOCOLSIGNAL_H_ */ diff --git a/src/service/request/Request.cpp b/src/service/request/Request.cpp new file mode 100644 index 00000000..152447fa --- /dev/null +++ b/src/service/request/Request.cpp @@ -0,0 +1,33 @@ +/* + * Copyright (c) 2014 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/* + * @file Request.cpp + * @author Lukasz Wojciechowski + * @version 1.0 + * @brief This file implements request base class + */ + +#include "Request.h" + +namespace Cynara { + +Request::Request() { +} + +Request::~Request() { +} + +} // namespace Cynara diff --git a/src/service/request/Request.h b/src/service/request/Request.h new file mode 100644 index 00000000..e0f44658 --- /dev/null +++ b/src/service/request/Request.h @@ -0,0 +1,41 @@ +/* + * Copyright (c) 2014 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/* + * @file Request.h + * @author Lukasz Wojciechowski + * @version 1.0 + * @brief This file defines request base class + */ + +#ifndef SRC_SERVICE_REQUEST_REQUEST_H_ +#define SRC_SERVICE_REQUEST_REQUEST_H_ + +#include +#include "RequestContext.h" + +namespace Cynara { + +class Request { +public: + Request(); + virtual ~Request(); + + virtual void execute(Logic *logic, const RequestContext &context) = 0; +}; + +} // namespace Cynara + +#endif /* SRC_SERVICE_REQUEST_REQUEST_H_ */ diff --git a/src/service/request/RequestContext.cpp b/src/service/request/RequestContext.cpp new file mode 100644 index 00000000..38361ac0 --- /dev/null +++ b/src/service/request/RequestContext.cpp @@ -0,0 +1,30 @@ +/* + * Copyright (c) 2014 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/* + * @file RequestContext.cpp + * @author Lukasz Wojciechowski + * @version 1.0 + * @brief This file implements request context class + */ + +#include "RequestContext.h" + +namespace Cynara { + +RequestContext::RequestContext(int fd) : m_sourceFd(fd) { +} + +} // namespace Cynara diff --git a/src/service/request/RequestContext.h b/src/service/request/RequestContext.h new file mode 100644 index 00000000..75824d23 --- /dev/null +++ b/src/service/request/RequestContext.h @@ -0,0 +1,37 @@ +/* + * Copyright (c) 2014 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/* + * @file RequestContext.h + * @author Lukasz Wojciechowski + * @version 1.0 + * @brief This file defines request context class + */ + +#ifndef SRC_SERVICE_REQUEST_REQUESTCONTEXT_H_ +#define SRC_SERVICE_REQUEST_REQUESTCONTEXT_H_ + +namespace Cynara { + +class RequestContext { +public: + RequestContext(int fd); + + int m_sourceFd; +}; + +} // namespace Cynara + +#endif /* SRC_SERVICE_REQUEST_REQUESTCONTEXT_H_ */ diff --git a/src/service/sockets/Descriptor.cpp b/src/service/sockets/Descriptor.cpp new file mode 100644 index 00000000..ca72c71a --- /dev/null +++ b/src/service/sockets/Descriptor.cpp @@ -0,0 +1,56 @@ +/* + * Copyright (c) 2014 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/* + * @file Descriptor.cpp + * @author Lukasz Wojciechowski + * @version 1.0 + * @brief This file implements descriptor class + */ + +#include "Descriptor.h" + +namespace Cynara { + +bool Descriptor::isDataToWrite(void) const { + return !(m_writeQueue.empty() && m_writeBuffer.empty()); +} + +void Descriptor::pushReadBuffer(const RawBuffer &readbuffer) { + m_readQueue.appendCopy(readbuffer.data(), readbuffer.size()); +} + +Request *Descriptor::extractRequest(void) { + return m_protocol->extractRequestFromBuffer(m_readQueue); +} + +RawBuffer &Descriptor::prepareWriteBuffer(void) { + size_t queuedDataSize = m_writeQueue.size(); + size_t bufferDataSize = m_writeBuffer.size(); + + m_writeBuffer.resize(queuedDataSize + bufferDataSize); + m_writeQueue.flattenConsume(m_writeBuffer.data() + bufferDataSize, queuedDataSize); + + return m_writeBuffer; +} + +void Descriptor::clear(void) { + m_readQueue.clear(); + m_writeQueue.clear(); + m_writeBuffer.clear(); + m_protocol = nullptr; +} + +} // namespace Cynara diff --git a/src/service/sockets/Descriptor.h b/src/service/sockets/Descriptor.h new file mode 100644 index 00000000..e3031ac0 --- /dev/null +++ b/src/service/sockets/Descriptor.h @@ -0,0 +1,73 @@ +/* + * Copyright (c) 2014 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/* + * @file Descriptor.h + * @author Lukasz Wojciechowski + * @version 1.0 + * @brief This file defines descriptor class + */ + +#ifndef SRC_SERVICE_SOCKETS_DESCRIPTOR_H_ +#define SRC_SERVICE_SOCKETS_DESCRIPTOR_H_ + +#include + +#include +#include + +namespace Cynara { + +class Descriptor { +private: + int m_fd; + bool m_listen; + + BinaryQueue m_readQueue; + BinaryQueue m_writeQueue; + RawBuffer m_writeBuffer; + + Protocol *m_protocol; + +public: + bool isListen(void) const { + return m_listen; + } + + bool isDataToWrite(void) const; + + Protocol *protocol(void) { + return m_protocol; + } + + void setProtocol(Protocol *protocol) { + m_protocol = protocol; + } + + void setListen(bool listen) { + m_listen = listen; + } + + void pushReadBuffer(const RawBuffer &readbuffer); + Request *extractRequest(void); + + RawBuffer &prepareWriteBuffer(void); + + void clear(void); +}; + +} // namespace Cynara + +#endif /* SRC_SERVICE_SOCKETS_DESCRIPTOR_H_ */ diff --git a/src/service/sockets/SocketManager.cpp b/src/service/sockets/SocketManager.cpp new file mode 100644 index 00000000..8df25861 --- /dev/null +++ b/src/service/sockets/SocketManager.cpp @@ -0,0 +1,348 @@ +/* + * Copyright (c) 2014 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/* + * @file SocketManager.cpp + * @author Lukasz Wojciechowski + * @version 1.0 + * @brief This file implements socket layer manager for cynara + */ + +#include +#include +#include +#include +#include +#include +#include +#include + +#include + +#include +#include +#include +#include + +#include +#include
+#include +#include +#include + +#include "SocketManager.h" + +namespace Cynara { + +SocketManager::SocketManager() : m_working(false), m_maxDesc(-1) { + FD_ZERO(&m_readSet); + FD_ZERO(&m_writeSet); +} + +SocketManager::~SocketManager() { +} + +void SocketManager::run(void) { + init(); + mainLoop(); +} + +void SocketManager::init(void) { + LOGI("SocketManger init start"); + const std::string clientSocketPath("/run/cynara/cynara.socket"); + const std::string adminSocketPath("/run/cynara/cynara-admin.socket"); + const mode_t clientSocketUMask(0); + const mode_t adminSocketUMask(0077); + + createDomainSocket(new ProtocolClient, clientSocketPath, clientSocketUMask); + createDomainSocket(new ProtocolAdmin, adminSocketPath, adminSocketUMask); + // todo create signal descriptor + LOGI("SocketManger init done"); +} + +void SocketManager::mainLoop(void) { + LOGI("SocketManger mainLoop start"); + m_working = true; + while (m_working) { + fd_set readSet = m_readSet; + fd_set writeSet = m_writeSet; + + int ret = select(m_maxDesc + 1, &readSet, &writeSet, nullptr, nullptr); + + if (ret < 0) { + switch (errno) { + case EINTR: + continue; + default: + int err = errno; + throw UnexpectedErrorException(err, strerror(err)); + } + } else if (ret > 0) { + for (int i = 0; i < m_maxDesc + 1 && ret; ++i) { + if (FD_ISSET(i, &readSet)) { + readyForRead(i); + --ret; + } + if (FD_ISSET(i, &writeSet)) { + readyForWrite(i); + --ret; + } + } + } + } + LOGI("SocketManger mainLoop done"); +} + +void SocketManager::mainLoopStop(void) { + m_working = false; +} + +void SocketManager::readyForRead(int fd) { + LOGD("SocketManger readyForRead on fd [%d] start", fd); + auto &desc = m_fds[fd]; + if (desc.isListen()) { + readyForAccept(fd); + return; + } + + RawBuffer readBuffer(DEFAULT_BUFFER_SIZE); + ssize_t size = read(fd, readBuffer.data(), DEFAULT_BUFFER_SIZE); + + if (size > 0) { + LOGD("read [%zd] bytes", size); + readBuffer.resize(size); + if (handleRead(fd, readBuffer)) { + LOGD("SocketManger readyForRead on fd [%d] successfully done", fd); + return; + } + LOGI("interpreting buffer read from [%d] failed", fd); + } else if (size < 0) { + int err = errno; + switch (err) { + case EAGAIN: +#if EWOULDBLOCK != EAGAIN + case EWOULDBLOCK: +#endif + case EINTR: + return; + default: + LOGW("While reading from [%d] socket, error [%d]:<%s>", + fd, err, strerror(err)); + } + } else { + LOGN("Socket [%d] closed on other end", fd); + } + closeSocket(fd); + LOGD("SocketManger readyForRead on fd [%d] done", fd); +} + +void SocketManager::readyForWrite(int fd) { + LOGD("SocketManger readyForWrite on fd [%d] start", fd); + auto &desc = m_fds[fd]; + auto &buffer = desc.prepareWriteBuffer(); + size_t size = buffer.size(); + ssize_t result = write(fd, buffer.data(), size); + if (result == -1) { + int err = errno; + switch (err) { + case EAGAIN: + case EINTR: + // select will trigger write once again, nothing to do + break; + case EPIPE: + default: + LOGD("Error during write to fd [%d]:<%s> ", fd, strerror(err)); + closeSocket(fd); + break; + } + return; // We do not want to propagate error to next layer + } + + LOGD("written [%zd] bytes", result); + buffer.erase(buffer.begin(), buffer.begin() + result); + + if (buffer.empty()) + removeWriteSocket(fd); + LOGD("SocketManger readyForWrite on fd [%d] done", fd); +} + +void SocketManager::readyForAccept(int fd) { + LOGD("SocketManger readyForAccept on fd [%d] start", fd); + struct sockaddr_un clientAddr; + unsigned int clientLen = sizeof(clientAddr); + int client = accept4(fd, (struct sockaddr*) &clientAddr, &clientLen, SOCK_NONBLOCK); + if (client == -1) { + int err = errno; + LOGW("Error in accept on socket [%d]: <%s>", fd, strerror(err)); + return; + } + LOGD("Accept on sock [%d]. New client socket opened [%d]", fd, client); + + auto &description = createDescriptor(client); + description.setListen(false); + description.setProtocol(m_fds[fd].protocol()); + addReadSocket(client); + LOGD("SocketManger readyForAccept on fd [%d] done", fd); +} + +void SocketManager::closeSocket(int fd) { + LOGD("SocketManger closeSocket fd [%d] start", fd); + removeReadSocket(fd); + removeWriteSocket(fd); + m_fds[fd].clear(); + close(fd); + LOGD("SocketManger closeSocket fd [%d] done", fd); +} + +bool SocketManager::handleRead(int fd, const RawBuffer &readbuffer) { + LOGD("SocketManger handleRead on fd [%d] start", fd); + auto &desc = m_fds[fd]; + desc.pushReadBuffer(readbuffer); + + try { + Request *req = nullptr; + for (;;) { + req = desc.extractRequest(); + if (!req) + break; + + LOGD("request extracted"); + req->execute(Cynara::getLogic(), {fd}); + delete req; + + if (desc.isDataToWrite()) + addWriteSocket(fd); + } + } catch (const Exception &ex) { + LOGE("Error handling request <%s>. Closing socket", ex.what()); + return false; + } + LOGD("SocketManger handleRead on fd [%d] done", fd); + return true; +} + +void SocketManager::createDomainSocket(Protocol *protocol, const std::string &path, mode_t mask) { + int fd = getSocketFromSystemD(path); + if (fd == -1) + fd = createDomainSocketHelp(path, mask); + + auto &desc = createDescriptor(fd); + desc.setListen(true); + desc.setProtocol(protocol); + addReadSocket(fd); + + LOGD("Domain socket: [%d] added.", fd); +} + +int SocketManager::createDomainSocketHelp(const std::string &path, mode_t mask) { + int fd; + + if ((fd = socket(AF_UNIX, SOCK_STREAM, 0)) == -1) { + int err = errno; + LOGE("Error during UNIX socket creation: <%s>", strerror(err)); + throw InitException(); + } + + int flags; + if ((flags = fcntl(fd, F_GETFL, 0)) == -1) + flags = 0; + if (fcntl(fd, F_SETFL, flags | O_NONBLOCK) == -1) { + int err = errno; + close(fd); + LOGE("Error setting \"O_NONBLOCK\" on descriptor [%d] with fcntl: <%s>", + fd, strerror(err)); + throw InitException(); + } + + sockaddr_un serverAddress; + memset(&serverAddress, 0, sizeof(serverAddress)); + serverAddress.sun_family = AF_UNIX; + if (path.length() > sizeof(serverAddress.sun_path)) { + LOGE("Path for unix domain socket <%s> is [%zu] bytes long, while it should be maximum " + "[%zu] bytes long", path.c_str(), path.length(), sizeof(serverAddress)); + throw InitException(); + } + strcpy(serverAddress.sun_path, path.c_str()); + unlink(serverAddress.sun_path); + + mode_t originalUmask; + originalUmask = umask(mask); + + if (bind(fd, (struct sockaddr*)&serverAddress, sizeof(serverAddress)) == -1) { + int err = errno; + close(fd); + LOGE("Error in bind socket descriptor [%d] to path <%s>: <%s>", + fd, path.c_str(), strerror(err)); + throw InitException(); + } + + umask(originalUmask); + + if (listen(fd, 5) == -1) { + int err = errno; + close(fd); + LOGE("Error setting listen on file descriptor [%d], path <%s>: <%s>", + fd, path.c_str(), strerror(err)); + throw InitException(); + } + + return fd; +} + +int SocketManager::getSocketFromSystemD(const std::string &path) { + int n = sd_listen_fds(0); + LOGI("sd_listen_fds returns: [%d]", n); + if (n < 0) { + LOGE("Error in sd_listend_fds"); + throw InitException(); + } + + for (int fd = SD_LISTEN_FDS_START; fd < SD_LISTEN_FDS_START + n; ++fd) { + if (sd_is_socket_unix(fd, SOCK_STREAM, 1, path.c_str(), 0) > 0) { + LOGI("Useable socket <%s> was passed by SystemD under descriptor [%d]", + path.c_str(), fd); + return fd; + } + } + LOGI("No useable sockets were passed by systemd."); + return -1; +} + +Descriptor &SocketManager::createDescriptor(int fd) { + if (fd > m_maxDesc) { + m_maxDesc = fd; + if (fd >= static_cast(m_fds.size())) + m_fds.resize(fd + 20); + } + return m_fds[fd]; +} + +void SocketManager::addReadSocket(int fd) { + FD_SET(fd, &m_readSet); +} + +void SocketManager::removeReadSocket(int fd) { + FD_CLR(fd, &m_readSet); +} + +void SocketManager::addWriteSocket(int fd) { + FD_SET(fd, &m_writeSet); +} + +void SocketManager::removeWriteSocket(int fd) { + FD_CLR(fd, &m_writeSet); +} + +} // namespace Cynara diff --git a/src/service/sockets/SocketManager.h b/src/service/sockets/SocketManager.h new file mode 100644 index 00000000..72e820ad --- /dev/null +++ b/src/service/sockets/SocketManager.h @@ -0,0 +1,78 @@ +/* + * Copyright (c) 2014 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +/* + * @file SocketManager.h + * @author Lukasz Wojciechowski + * @version 1.0 + * @brief This file defines socket layer manager for cynara + */ + +#ifndef SRC_SERVICE_SOCKETS_SOCKETMANAGER_H_ +#define SRC_SERVICE_SOCKETS_SOCKETMANAGER_H_ + +#include +#include + +#include + +#include "Descriptor.h" + +namespace Cynara { + +const size_t DEFAULT_BUFFER_SIZE = BUFSIZ; + +class SocketManager { +public: + SocketManager(); + ~SocketManager(); + + void run(void); + void mainLoopStop(void); + +private: + typedef std::vector FDVector; + FDVector m_fds; + + bool m_working; + + fd_set m_readSet; + fd_set m_writeSet; + int m_maxDesc; + + void init(void); + void mainLoop(void); + + void readyForRead(int fd); + void readyForWrite(int fd); + void readyForAccept(int fd); + void closeSocket(int fd); + bool handleRead(int fd, const RawBuffer &readbuffer); + + void createDomainSocket(Protocol *protocol, const std::string &path, mode_t mask); + int createDomainSocketHelp(const std::string &path, mode_t mask); + int getSocketFromSystemD(const std::string &path); + + Descriptor &createDescriptor(int fd); + + void addReadSocket(int fd); + void removeReadSocket(int fd); + void addWriteSocket(int fd); + void removeWriteSocket(int fd); +}; + +} // namespace Cynara + +#endif /* SRC_SERVICE_SOCKETS_SOCKETMANAGER_H_ */ diff --git a/systemd/cynara-admin.socket b/systemd/cynara-admin.socket index 050267e1..2d1aea44 100644 --- a/systemd/cynara-admin.socket +++ b/systemd/cynara-admin.socket @@ -1,5 +1,5 @@ [Socket] -ListenStream=/run/cynara/cynara-admin.sock +ListenStream=/run/cynara/cynara-admin.socket SocketMode=0700 SmackLabelIPIn=@ SmackLabelIPOut=@ diff --git a/systemd/cynara.socket b/systemd/cynara.socket index 2162102f..92f4f7f3 100644 --- a/systemd/cynara.socket +++ b/systemd/cynara.socket @@ -1,5 +1,5 @@ [Socket] -ListenStream=/run/cynara/cynara.sock +ListenStream=/run/cynara/cynara.socket SocketMode=0777 SmackLabelIPIn=@ SmackLabelIPOut=@