From f96a45e3a2ca8f92e01e0a1d901f8b5c7cea130b Mon Sep 17 00:00:00 2001 From: JDierkse Date: Fri, 26 Apr 2019 11:56:54 +0200 Subject: [PATCH] Remove Boost Link Dependency --- Application/PresenceDetection.cc | 94 +++------ Application/Test.cc | 315 +++++++++---------------------- Libraries/INIh/INIReader.h | 1 + Libraries/clipp | 1 + Makefile.conf.base | 2 +- Util/HttpClient.cpp | 1 + Util/HttpClientHelpers.h | 9 +- Util/INIh.h | 15 ++ Util/clipp.h | 15 ++ 9 files changed, 157 insertions(+), 296 deletions(-) create mode 120000 Libraries/INIh/INIReader.h create mode 120000 Libraries/clipp create mode 100644 Util/INIh.h create mode 100644 Util/clipp.h diff --git a/Application/PresenceDetection.cc b/Application/PresenceDetection.cc index 7785b22..5b444f5 100644 --- a/Application/PresenceDetection.cc +++ b/Application/PresenceDetection.cc @@ -2,12 +2,11 @@ #include #include #include +#include #include #include -#include -#include -#include -#include +#include "Util/clipp.h" +#include "Util/INIh.h" #include "UniFi/Device.h" #include "Bluetooth/Device.h" @@ -19,27 +18,23 @@ int main(int argc, char** argv) setlogmask(LOG_UPTO(LOG_INFO)); openlog("PresenceDetection", LOG_CONS | LOG_NDELAY | LOG_PERROR | LOG_PID, LOG_USER); - boost::program_options::options_description description("Options"); - description.add_options() - ("help,h", "Provide Help Message") - ("daemon,d", "Run the process as Daemon"); + bool daemon = false; + PresenceDetection::Util::group cli { + PresenceDetection::Util::option("-d", "--daemon").set(daemon).doc("Run the process as Daemon") + }; - boost::program_options::variables_map vm; - boost::program_options::store(boost::program_options::parse_command_line(argc, argv, description), vm); - boost::program_options::notify(vm); - - if (vm.count("help")) + if (!PresenceDetection::Util::parse(argc, argv, cli)) { - std::cerr << description << std::endl; + std::cout << PresenceDetection::Util::make_man_page(cli, argv[0]) << std::endl; return 1; } - bool daemon = false; - if (vm.count("daemon")) - daemon = true; - - boost::property_tree::ptree pt; - boost::property_tree::ini_parser::read_ini("PresenceDetection.ini", pt); + PresenceDetection::Util::INIReader iniReader("PresenceDetection.ini"); + if (iniReader.ParseError() != 0) + { + std::cerr << "Can't read PresenceDetection.ini" << std::endl; + return 1; + } if (daemon) { @@ -65,59 +60,35 @@ int main(int argc, char** argv) close(STDERR_FILENO); } - std::string target; - boost::optional presenceDetectionTarget = pt.get_child_optional("PresenceDetection.Target"); - if (presenceDetectionTarget) - target = pt.get("PresenceDetection.Target"); - else + std::string target = iniReader.Get("PresenceDetection", "Target", ""); + if (target.empty()) throw std::runtime_error("Target directive missing in ini file."); - bool unifi = false; - boost::optional presenceDetectionUniFi = pt.get_child_optional("PresenceDetection.UniFi"); - if (presenceDetectionUniFi) - unifi = (pt.get("PresenceDetection.UniFi") == "On"); + bool unifi = iniReader.GetBoolean("PresenceDetection", "UniFi", false); - bool bluetooth = false; - boost::optional presenceDetectionBluetooth = pt.get_child_optional("PresenceDetection.Bluetooth"); - if (presenceDetectionBluetooth) - bluetooth = (pt.get("PresenceDetection.Bluetooth") == "On"); + bool bluetooth = iniReader.GetBoolean("PresenceDetection", "Bluetooth", false); std::shared_ptr pUniFiDevice; if (unifi) { - std::string hostname; - boost::optional unifiHostname = pt.get_child_optional("UniFi.Hostname"); - if (unifiHostname) - hostname = pt.get("UniFi.Hostname"); - else + std::string hostname = iniReader.Get("UniFi", "Hostname", ""); + if (hostname.empty()) throw std::runtime_error("UniFi Hostname directive missing in ini file."); - std::string username; - boost::optional unifiUsername = pt.get_child_optional("UniFi.Username"); - if (unifiUsername) - username = pt.get("UniFi.Username"); - else + std::string username = iniReader.Get("UniFi", "Username", ""); + if (username.empty()) throw std::runtime_error("UniFi Username directive missing in ini file."); - std::string password; - boost::optional unifiPassword = pt.get_child_optional("UniFi.Password"); - if (unifiPassword) - password = pt.get("UniFi.Password"); - else + std::string password = iniReader.Get("UniFi", "Password", ""); + if (password.empty()) throw std::runtime_error("UniFi Password directive missing in ini file."); - std::string cookiefile; - boost::optional unifiCookieFile = pt.get_child_optional("UniFi.CookieFile"); - if (unifiCookieFile) - cookiefile = pt.get("UniFi.CookieFile"); - else + std::string cookiefile = iniReader.Get("UniFi", "CookieFile", ""); + if (cookiefile.empty()) throw std::runtime_error("UniFi CookieFile directive missing in ini file."); - std::string inventoryURL; - boost::optional bluetoothInventoryURL = pt.get_child_optional("UniFi.Inventory"); - if (bluetoothInventoryURL) - inventoryURL = pt.get("UniFi.Inventory"); - else + std::string inventoryURL = iniReader.Get("UniFi", "Inventory", ""); + if (inventoryURL.empty()) throw std::runtime_error("UniFi Inventory directive missing in ini file."); pUniFiDevice = std::make_shared(hostname, username, password, cookiefile, inventoryURL, target); @@ -126,11 +97,8 @@ int main(int argc, char** argv) std::shared_ptr pBluetoothDevice; if (bluetooth) { - std::string inventoryURL; - boost::optional bluetoothInventoryURL = pt.get_child_optional("Bluetooth.Inventory"); - if (bluetoothInventoryURL) - inventoryURL = pt.get("Bluetooth.Inventory"); - else + std::string inventoryURL = iniReader.Get("Bluetooth", "Inventory", ""); + if (inventoryURL.empty()) throw std::runtime_error("Bluetooth Inventory directive missing in ini file."); pBluetoothDevice = std::make_shared(inventoryURL, target); diff --git a/Application/Test.cc b/Application/Test.cc index a0bfb65..b49d7a3 100644 --- a/Application/Test.cc +++ b/Application/Test.cc @@ -1,266 +1,125 @@ #include #include -#include -#include +#include +#include #include -#include -#include -#include -#include -#include -#include -#include - -#include -#include -#include -#include +#include +#include #include "Util/Timer.h" +#include "Util/INIh.h" -/* Defaults */ -static bdaddr_t bdaddr; -static int size = 44; -static int ident = 200; -static int delay = 1; -static int count = -1; -static int timeout = 10; -static int reverse = 0; -static int verify = 0; - -/* Stats */ -static int sent_pkt = 0; -static int recv_pkt = 0; - -static float tv2fl(struct timeval tv) -{ - return (float)(tv.tv_sec*1000.0) + (float)(tv.tv_usec/1000.0); -} - -static void stat(int /*sig*/) -{ - int loss = sent_pkt ? (float)((sent_pkt-recv_pkt)/(sent_pkt/100.0)) : 0; - printf("%d sent, %d received, %d%% loss\n", sent_pkt, recv_pkt, loss); - exit(0); -} - -static void ping(const char* svr) -{ - struct sigaction sa; - struct sockaddr_l2 addr; - socklen_t optlen; - unsigned char *send_buf; - unsigned char *recv_buf; - char str[18]; - int i, sk, lost; - uint8_t id; - - memset(&sa, 0, sizeof(sa)); - sa.sa_handler = stat; - sigaction(SIGINT, &sa, NULL); - - send_buf = static_cast(malloc(L2CAP_CMD_HDR_SIZE + size)); - recv_buf = static_cast(malloc(L2CAP_CMD_HDR_SIZE + size)); - if (!send_buf || !recv_buf) { - perror("Can't allocate buffer"); - exit(1); - } - - /* Create socket */ - sk = socket(PF_BLUETOOTH, SOCK_RAW, BTPROTO_L2CAP); - if (sk < 0) { - perror("Can't create socket"); - goto error; - } - - /* Bind to local address */ - memset(&addr, 0, sizeof(addr)); - addr.l2_family = AF_BLUETOOTH; - bacpy(&addr.l2_bdaddr, &bdaddr); - - if (bind(sk, (struct sockaddr *) &addr, sizeof(addr)) < 0) { - perror("Can't bind socket"); - goto error; - } - - /* Connect to remote device */ - memset(&addr, 0, sizeof(addr)); - addr.l2_family = AF_BLUETOOTH; - str2ba(svr, &addr.l2_bdaddr); - - if (connect(sk, (struct sockaddr *) &addr, sizeof(addr)) < 0) { - perror("Can't connect"); - goto error; - } - - /* Get local address */ - memset(&addr, 0, sizeof(addr)); - optlen = sizeof(addr); - - if (getsockname(sk, (struct sockaddr *) &addr, &optlen) < 0) { - perror("Can't get local address"); - goto error; - } - - ba2str(&addr.l2_bdaddr, str); - printf("Ping: %s from %s (data size %d) ...\n", svr, str, size); - - /* Initialize send buffer */ - for (i = 0; i < size; i++) - send_buf[L2CAP_CMD_HDR_SIZE + i] = (i % 40) + 'A'; - - id = ident; - - while (count == -1 || count-- > 0) { - struct timeval tv_send, tv_recv, tv_diff; - l2cap_cmd_hdr *send_cmd = (l2cap_cmd_hdr *) send_buf; - l2cap_cmd_hdr *recv_cmd = (l2cap_cmd_hdr *) recv_buf; - - /* Build command header */ - send_cmd->ident = id; - send_cmd->len = htobs(size); - - if (reverse) - send_cmd->code = L2CAP_ECHO_RSP; - else - send_cmd->code = L2CAP_ECHO_REQ; - - gettimeofday(&tv_send, NULL); - - /* Send Echo Command */ - if (send(sk, send_buf, L2CAP_CMD_HDR_SIZE + size, 0) <= 0) { - perror("Send failed"); - goto error; - } - - /* Wait for Echo Response */ - lost = 0; - while (1) { - struct pollfd pf[1]; - int err; - - pf[0].fd = sk; - pf[0].events = POLLIN; - - if ((err = poll(pf, 1, timeout * 1000)) < 0) { - perror("Poll failed"); - goto error; - } - - if (!err) { - lost = 1; - break; - } - - if ((err = recv(sk, recv_buf, L2CAP_CMD_HDR_SIZE + size, 0)) < 0) { - perror("Recv failed"); - goto error; - } - - if (!err){ - printf("Disconnected\n"); - goto error; - } - - recv_cmd->len = btohs(recv_cmd->len); - - /* Check for our id */ - if (recv_cmd->ident != id) - continue; - - /* Check type */ - if (!reverse && recv_cmd->code == L2CAP_ECHO_RSP) - break; - - if (recv_cmd->code == L2CAP_COMMAND_REJ) { - printf("Peer doesn't support Echo packets\n"); - goto error; - } - - } - sent_pkt++; - - if (!lost) { - recv_pkt++; - - gettimeofday(&tv_recv, NULL); - timersub(&tv_recv, &tv_send, &tv_diff); - - if (verify) { - /* Check payload length */ - if (recv_cmd->len != size) { - fprintf(stderr, "Received %d bytes, expected %d\n", - recv_cmd->len, size); - goto error; - } - - /* Check payload */ - if (memcmp(&send_buf[L2CAP_CMD_HDR_SIZE], - &recv_buf[L2CAP_CMD_HDR_SIZE], size)) { - fprintf(stderr, "Response payload different.\n"); - goto error; - } - } - - printf("%d bytes from %s id %d time %.2fms\n", recv_cmd->len, svr, - id - ident, tv2fl(tv_diff)); - - if (delay) - sleep(delay); - } else { - printf("no response from %s: id %d\n", svr, id - ident); - } - - if (++id > 254) - id = ident; - } - stat(0); - free(send_buf); - free(recv_buf); - return; - -error: - close(sk); - free(send_buf); - free(recv_buf); - exit(1); -} void print() { std::cout << "Print" << std::endl; } -int main(int /*argc*/, char** /*argv[]*/) +void TestTimerAbort() { - //std::string address = "48:4B:AA:85:30:C5"; - //ping(address.c_str()); - - //address = "d0:c5:f3:84:99:de"; - //ping(address.c_str()); - PresenceDetection::Util::Timer timer; std::function f_print = print; std::cout << "---" << std::endl; + auto start = std::chrono::steady_clock::now(); + std::clock_t begin = std::clock(); timer.StartContinuous(1000, f_print); timer.Stop(); timer.Wait(); + auto elapsed = std::chrono::duration_cast(std::chrono::steady_clock::now() - start); + std::cout << "Elapsed: " << elapsed.count() << std::endl; std::cout << "---" << std::endl << std::endl; std::cout << "---" << std::endl; + start = std::chrono::steady_clock::now(); timer.StartContinuous(3000, f_print); timer.Abort(); timer.Wait(); + elapsed = std::chrono::duration_cast(std::chrono::steady_clock::now() - start); + std::cout << "Elapsed: " << elapsed.count() << std::endl; std::cout << "---" << std::endl << std::endl; std::cout << "---" << std::endl; + start = std::chrono::steady_clock::now(); timer.StartContinuous(3000, f_print); sleep(1); timer.Abort(); timer.Wait(); + elapsed = std::chrono::duration_cast(std::chrono::steady_clock::now() - start); + std::cout << "Elapsed: " << elapsed.count() << std::endl; std::cout << "---" << std::endl << std::endl; +} + +typedef std::unique_ptr Pointer; + +template +std::unique_ptr make_unique(Args&&... args) { + return std::unique_ptr(new T(std::forward(args)...)); +} + +void OnTimerEnd(const std::string& type, int id) +{ + std::cout << "OnTimerEnd() " << type << " " << id <& timers) +{ + int delay(2000); + std::string identifier("Blabla"); + int id(10); + + // Protect! + auto timer = make_unique(); + timer->StartSingle(delay, static_cast>(std::bind(&OnTimerEnd, std::placeholders::_1, std::placeholders::_2)), identifier, id); + timers.push_back(std::move(timer)); +} + +void Cleanup(std::deque& timers) +{ + timers.erase(std::remove_if(timers.begin(), timers.end(), [](Pointer& t){return !t->IsRunning();}), timers.end()); +} + +void TestTimerDeque() +{ + std::deque timers; + StartNewTimer(timers); + std::cout << "Count: " << timers.size() << std::endl; + StartNewTimer(timers); + std::cout << "Count: " << timers.size() << std::endl; + + sleep(5); + + std::cout << "Count: " << timers.size() << std::endl; + Cleanup(timers); + std::cout << "Count: " << timers.size() << std::endl; +} + +void TestINIReader() +{ + PresenceDetection::Util::INIReader reader("PresenceDetection.ini"); + + std::string target = reader.Get("PresenceDetection", "Target", ""); + if (!target.empty()) + std::cout << "Error" << std::endl; + std::cout << target.size() << " " << target << std::endl; + + bool unifi = reader.GetBoolean("PresenceDetection", "UniFi", false); + if (unifi) + std::cout << "UniFi On" << std::endl; + else + std::cout << "UniFi Off" << std::endl; + + bool test = reader.GetBoolean("PresenceDetection", "Test", false); + if (test) + std::cout << "Test On" << std::endl; + else + std::cout << "Test Off" << std::endl; +} + +int main(int /*argc*/, char** /*argv[]*/) +{ + TestINIReader(); return 0; } diff --git a/Libraries/INIh/INIReader.h b/Libraries/INIh/INIReader.h new file mode 120000 index 0000000..17148ff --- /dev/null +++ b/Libraries/INIh/INIReader.h @@ -0,0 +1 @@ +../../../Libraries/inih/INIReader.h \ No newline at end of file diff --git a/Libraries/clipp b/Libraries/clipp new file mode 120000 index 0000000..e67602a --- /dev/null +++ b/Libraries/clipp @@ -0,0 +1 @@ +../../Libraries/clipp/include \ No newline at end of file diff --git a/Makefile.conf.base b/Makefile.conf.base index e4a679c..7a63a0d 100644 --- a/Makefile.conf.base +++ b/Makefile.conf.base @@ -5,7 +5,7 @@ CFLAGS += -g3 -O3 -fPIC -std=c++11 CFLAGS += -Wall -Wextra -Wstrict-aliasing -fmax-errors=5 -Werror -Wunreachable-code -Wdisabled-optimization -Wformat=2 -Winit-self -Wlogical-op -Wmissing-include-dirs -Wnoexcept -Woverloaded-virtual -Wsign-promo -Wstrict-null-sentinel -Wswitch-default -Wno-unused -Wno-variadic-macros -Wno-parentheses -fdiagnostics-show-option # CFLAGS += -Wold-style-cast -pedantic -Wcast-qual -Wundef -Wshadow -Wctor-dtor-privacy -Wredundant-decls -Wstrict-overflow=5 -Wcast-align -LFLAGS += -lpthread -lm -lboost_system -lboost_thread -lboost_program_options -lboost_date_time -lssl -lcrypto -lcurl -lz -ldl -lbluetooth +LFLAGS += -lpthread -lm -lssl -lcrypto -lcurl -lz -ldl -lbluetooth CFLAGS += -fpermissive CFLAGS += -I$(ROOTPATH) -I$(ROOTPATH)/Libraries/JSON diff --git a/Util/HttpClient.cpp b/Util/HttpClient.cpp index eae67e4..df925a5 100644 --- a/Util/HttpClient.cpp +++ b/Util/HttpClient.cpp @@ -1,4 +1,5 @@ #include +#include #include #include #include diff --git a/Util/HttpClientHelpers.h b/Util/HttpClientHelpers.h index d7c809b..c2dd04c 100644 --- a/Util/HttpClientHelpers.h +++ b/Util/HttpClientHelpers.h @@ -1,15 +1,16 @@ #ifndef UTIL_HTTPCLIENTHELPERS_H #define UTIL_HTTPCLIENTHELPERS_H -#include -#include +#include +#include +#include #include namespace PresenceDetection { namespace Util { -static std::vector > g_mutexes; +static std::vector > g_mutexes; static void LockCallback(int mode, int type, const char* /*file*/, int /*line*/) { @@ -28,7 +29,7 @@ static void InitializeLocks(void) { g_mutexes.resize(CRYPTO_num_locks()); for (int i = 0; i < CRYPTO_num_locks(); ++i) - g_mutexes[i] = boost::shared_ptr(new boost::mutex()); + g_mutexes[i] = std::shared_ptr(new std::mutex()); CRYPTO_set_id_callback(ThreadId); CRYPTO_set_locking_callback(LockCallback); diff --git a/Util/INIh.h b/Util/INIh.h new file mode 100644 index 0000000..7a0b754 --- /dev/null +++ b/Util/INIh.h @@ -0,0 +1,15 @@ +#ifndef UTIL_INIH_H +#define UTIL_INIH_H + +#include "Libraries/INIh/INIReader.h" + + +namespace PresenceDetection { +namespace Util { + +using ::INIReader; + +} // namespace Util +} // namespace DomoticaServer + +#endif // UTIL_INIH_H diff --git a/Util/clipp.h b/Util/clipp.h new file mode 100644 index 0000000..c0874a1 --- /dev/null +++ b/Util/clipp.h @@ -0,0 +1,15 @@ +#ifndef UTIL_CLIPP_H +#define UTIL_CLIPP_H + +#include "Libraries/clipp/clipp.h" + + +namespace PresenceDetection { +namespace Util { + +using namespace clipp; + +} // namespace Util +} // namespace DomoticaServer + +#endif // UTIL_CLIPP_H