#include #include #include #include #include #include typedef void (*sighandler_t)(int sig); #include "cereal/services.h" #include "msgq/impl_msgq.h" #include "msgq/impl_zmq.h" std::atomic do_exit = false; static void set_do_exit(int sig) { do_exit = true; } void sigpipe_handler(int sig) { assert(sig == SIGPIPE); std::cout << "SIGPIPE received" << std::endl; } static std::vector get_services(std::string whitelist_str, bool zmq_to_msgq) { std::vector service_list; for (const auto& it : services) { std::string name = it.second.name; bool in_whitelist = whitelist_str.find(name) != std::string::npos; if (name == "plusFrame" || name == "uiLayoutState" || (zmq_to_msgq && !in_whitelist)) { continue; } service_list.push_back(name); } return service_list; } int main(int argc, char** argv) { signal(SIGPIPE, (sighandler_t)sigpipe_handler); signal(SIGINT, (sighandler_t)set_do_exit); signal(SIGTERM, (sighandler_t)set_do_exit); bool zmq_to_msgq = argc > 2; std::string ip = zmq_to_msgq ? argv[1] : "127.0.0.1"; std::string whitelist_str = zmq_to_msgq ? std::string(argv[2]) : ""; Poller *poller; Context *pub_context; Context *sub_context; if (zmq_to_msgq) { // republishes zmq debugging messages as msgq poller = new ZMQPoller(); pub_context = new MSGQContext(); sub_context = new ZMQContext(); } else { poller = new MSGQPoller(); pub_context = new ZMQContext(); sub_context = new MSGQContext(); } std::map sub2pub; for (auto endpoint : get_services(whitelist_str, zmq_to_msgq)) { PubSocket * pub_sock; SubSocket * sub_sock; if (zmq_to_msgq) { pub_sock = new MSGQPubSocket(); sub_sock = new ZMQSubSocket(); } else { pub_sock = new ZMQPubSocket(); sub_sock = new MSGQSubSocket(); } pub_sock->connect(pub_context, endpoint); sub_sock->connect(sub_context, endpoint, ip, false); poller->registerSocket(sub_sock); sub2pub[sub_sock] = pub_sock; } while (!do_exit) { for (auto sub_sock : poller->poll(100)) { Message * msg = sub_sock->receive(); if (msg == NULL) continue; int ret; do { ret = sub2pub[sub_sock]->sendMessage(msg); } while (ret == -1 && errno == EINTR && !do_exit); assert(ret >= 0 || do_exit); delete msg; if (do_exit) break; } } return 0; }