From aa94eeda65bcb48a177dea4c5c5086560fbeeca4 Mon Sep 17 00:00:00 2001 From: /jdi/ Date: Sun, 18 Oct 2015 10:16:03 +0200 Subject: [PATCH] Timeout option added --- README.md | 4 ++++ src/File.cpp | 11 ++++----- src/File.h | 6 +++-- src/Options.h | 4 ++-- src/Program.cpp | 22 +++++++++--------- src/Socket.cpp | 55 ++++++++++++++++++++++++++++----------------- src/Socket.h | 18 +++++++-------- src/Types.h | 2 +- src/jsonNode.cpp | 10 +++++---- src/lookupTable.cpp | 1 + 10 files changed, 79 insertions(+), 54 deletions(-) diff --git a/README.md b/README.md index 5e735b0..dc75c35 100644 --- a/README.md +++ b/README.md @@ -1,3 +1,7 @@ # smrtlink Command-Line Tool which might in the future be able to configure TP-Link Easy Smart Switches. The usage is loosely based on the swconfig utility. + +##dependencys + libboost-filesystem-dev + libboost-system-dev \ No newline at end of file diff --git a/src/File.cpp b/src/File.cpp index 6bd7b8d..654bca2 100644 --- a/src/File.cpp +++ b/src/File.cpp @@ -7,13 +7,14 @@ #include #include "File.h" +#include "Options.h" -std::string File::read(std::string path) { +std::string File::read() { if (!fs::exists(home)) { fs::create_directory(home); } - fs::ifstream in((home / path), std::ios::in | std::ios::binary); + fs::ifstream in(((options.file=="")?home / DEFAULT_FILE:options.file), std::ios::in | std::ios::binary); if (in) { std::string contents; in.seekg(0, std::ios::end); @@ -26,13 +27,13 @@ std::string File::read(std::string path) { return ""; } -int File::write(std::string path, std::string content) { +int File::write(std::string content) { if (!fs::exists(home)) { fs::create_directory(home); } - fs::path p = home / path; + fs::path p = (options.file=="")?home / DEFAULT_FILE:options.file; fs::ofstream file(p); - file << content; + file << content<<"\n"; file.close(); return 0; } diff --git a/src/File.h b/src/File.h index 955a2bd..5a39bc0 100644 --- a/src/File.h +++ b/src/File.h @@ -14,13 +14,15 @@ namespace fs = boost::filesystem; #include +#define DEFAULT_FILE "config.json" + class File { public: File() { home = fs::path(getenv("HOME")) / ".smrtlink"; } - std::string read(std::string); - int write(std::string, std::string); + std::string read(); + int write(std::string); private: fs::path home; }; diff --git a/src/Options.h b/src/Options.h index af207ce..6f4ddc8 100644 --- a/src/Options.h +++ b/src/Options.h @@ -25,8 +25,8 @@ -u --user <[password:]username>\n\ -p --password \n\ Login with Username and Password\n\ - -f --file choose a settings file\n\ - -t --timeout Not yet implemented\n\ + -f --file choose a settings file\n\n\ + -t --timeout Timeout in milliseconds. Default: 180\n\ -w --wait Not yet implemented: blocking until operation is completed\n\ -s --permanent Not yet implemented: make changes immediately permanent\n\n\ Command Summary:\n\ diff --git a/src/Program.cpp b/src/Program.cpp index fd9e7f5..40d2955 100644 --- a/src/Program.cpp +++ b/src/Program.cpp @@ -22,11 +22,11 @@ int Program::list() { Packet p = Packet(Packet::DISCOVERY); p.setHostMac(host.getMac()); p.setPayload( { }); - bytes a = p.getBytes(); - p.encode(a); + bytes b = p.getBytes(); + p.encode(b); try { - asio::io_service io_service; + boost::asio::io_service io_service; Socket s(io_service); s.setHostIp(host.getIp()); s.init(DST_PORT, SRC_PORT); @@ -47,12 +47,12 @@ int Program::list() { Switch s = Switch(); s.parse(d); File f; - f.write("config.json", s.toString()); + f.write(s.toString()); std::cout <<"Devices:\n\t"< #include #include -#include #include "Socket.h" #include "Packet.h" #include "Options.h" #include "Host.h" #include "Types.h" -Socket::Socket(asio::io_service& io_service) : - send_socket_(io_service), receive_socket_(io_service) { +Socket::Socket(boost::asio::io_service& io_service) : + send_socket_(io_service), receive_socket_(io_service), timer(io_service) { } //, resolver( io_service) void Socket::init(short dst_port, short src_port) { @@ -29,23 +28,35 @@ void Socket::init(short dst_port, short src_port) { if (options.flags & FLAG_DEBUG) std::cout << "Local IP:\t" << local_ip << "\n"; - wildcard_endpoint_ = asio::ip::udp::endpoint( - asio::ip::address_v4::from_string("0.0.0.0"), src_port); - local_endpoint_ = asio::ip::udp::endpoint(asio::ip::address_v4(local_ip), - src_port); - broadcast_endpoint_ = asio::ip::udp::endpoint( - asio::ip::address_v4::from_string("255.255.255.255"), dst_port); + wildcard_endpoint_ = boost::asio::ip::udp::endpoint( + boost::asio::ip::address_v4::from_string("0.0.0.0"), src_port); + local_endpoint_ = boost::asio::ip::udp::endpoint( + boost::asio::ip::address_v4(local_ip), src_port); + broadcast_endpoint_ = boost::asio::ip::udp::endpoint( + boost::asio::ip::address_v4::from_string("255.255.255.255"), + dst_port); - send_socket_.open(asio::ip::udp::v4()); - send_socket_.set_option(asio::socket_base::broadcast(true)); - send_socket_.set_option(asio::socket_base::reuse_address(true)); + send_socket_.open(boost::asio::ip::udp::v4()); + send_socket_.set_option(boost::asio::socket_base::broadcast(true)); + send_socket_.set_option(boost::asio::socket_base::reuse_address(true)); send_socket_.bind(local_endpoint_); - receive_socket_.open(asio::ip::udp::v4()); - receive_socket_.set_option(asio::socket_base::broadcast(true)); - receive_socket_.set_option(asio::socket_base::reuse_address(true)); + receive_socket_.open(boost::asio::ip::udp::v4()); + receive_socket_.set_option(boost::asio::socket_base::broadcast(true)); + receive_socket_.set_option(boost::asio::socket_base::reuse_address(true)); receive_socket_.bind(wildcard_endpoint_); + if (options.timeout != 0) { + timer.expires_from_now( + boost::posix_time::milliseconds(options.timeout)); + timer.async_wait([this](const boost::system::error_code& error) + { + if (!error) + { + receive_socket_.close(); + } + }); + } } void Socket::setHostIp(ipAddr ip) { @@ -54,9 +65,9 @@ void Socket::setHostIp(ipAddr ip) { void Socket::send(bytes data) { unsigned char * a = &data[0]; - send_socket_.async_send_to(asio::buffer(a, data.size()), + send_socket_.async_send_to(boost::asio::buffer(a, data.size()), broadcast_endpoint_, - [this](asio::error_code ec, std::size_t bytes_sent) + [this](boost::system::error_code ec, std::size_t bytes_sent) { listen(); }); @@ -64,12 +75,13 @@ void Socket::send(bytes data) { void Socket::listen() { data.resize(MAX_LENGTH); - receive_socket_.async_receive_from(asio::buffer(data, MAX_LENGTH), + receive_socket_.async_receive_from(boost::asio::buffer(data, MAX_LENGTH), remote_endpoint_, - [this](asio::error_code ec, std::size_t bytes_recvd) + [this](boost::system::error_code ec, std::size_t bytes_recvd) { if (ec || bytes_recvd == 0) { - listen(); + //listen(); + // TODO distinguish error codes } else { data.resize(bytes_recvd); Packet p = Packet(Packet::RETURN); @@ -77,8 +89,9 @@ void Socket::listen() { p.parse(data); datasets l = p.getPayload(); if(!callback(p)) { - listen(); + //TODO do something } + listen(); } }); } diff --git a/src/Socket.h b/src/Socket.h index eed3bb1..bab3998 100644 --- a/src/Socket.h +++ b/src/Socket.h @@ -8,7 +8,7 @@ #ifndef SOCKET_H_ #define SOCKET_H_ -#include +#include #include "Packet.h" #include "Types.h" @@ -19,7 +19,7 @@ class Socket { public: - Socket(asio::io_service&); + Socket(boost::asio::io_service&); virtual ~Socket() { } void init(short, short); @@ -31,13 +31,13 @@ public: }; private: - asio::ip::udp::socket send_socket_; - asio::ip::udp::socket receive_socket_; - //asio::ip::udp::resolver resolver; - asio::ip::udp::endpoint broadcast_endpoint_; - asio::ip::udp::endpoint remote_endpoint_; - asio::ip::udp::endpoint wildcard_endpoint_; - asio::ip::udp::endpoint local_endpoint_; + boost::asio::ip::udp::socket send_socket_; + boost::asio::ip::udp::socket receive_socket_; + boost::asio::ip::udp::endpoint broadcast_endpoint_; + boost::asio::ip::udp::endpoint remote_endpoint_; + boost::asio::ip::udp::endpoint wildcard_endpoint_; + boost::asio::ip::udp::endpoint local_endpoint_; + boost::asio::deadline_timer timer; bytes data = bytes(MAX_LENGTH); ipAddr local_ip; diff --git a/src/Types.h b/src/Types.h index 1a45092..87f5f52 100644 --- a/src/Types.h +++ b/src/Types.h @@ -118,7 +118,7 @@ struct Options { std::string interface; std::string file; int debug_level=0; - long timeout; + long timeout = 180U; }; #endif /* TYPES_H_ */ diff --git a/src/jsonNode.cpp b/src/jsonNode.cpp index a617402..1ac0ea5 100644 --- a/src/jsonNode.cpp +++ b/src/jsonNode.cpp @@ -5,6 +5,9 @@ * Author: jdi */ +#include "../include/rapidjson/document.h" +#include "../include/rapidjson/prettywriter.h" + #include "jsonNode.h" jsonNode::jsonNode(const std::string &x, doc &root) { @@ -18,8 +21,7 @@ jsonNode::jsonNode(const std::string &x, doc &root) { jsonNode::jsonNode(const ipAddr &x, doc &root) { super(rapidjson::kStringType); char buffer[16]; - int len = sprintf(buffer, "%d.%d.%d.%d", x[0], x[1], - x[2], x[3]); + int len = sprintf(buffer, "%d.%d.%d.%d", x[0], x[1], x[2], x[3]); this->SetString(buffer, static_cast(len), root.GetAllocator()); memset(buffer, 0, sizeof(buffer)); } @@ -27,8 +29,8 @@ jsonNode::jsonNode(const ipAddr &x, doc &root) { jsonNode::jsonNode(const macAddr &x, doc &root) { super(rapidjson::kStringType); char buffer[18]; - int len = sprintf(buffer, "%02x:%02x:%02x:%02x:%02x:%02x", x[0], x[1], - x[2], x[3], x[4], x[5]); + int len = sprintf(buffer, "%02x:%02x:%02x:%02x:%02x:%02x", x[0], x[1], x[2], + x[3], x[4], x[5]); this->SetString(buffer, static_cast(len), root.GetAllocator()); memset(buffer, 0, sizeof(buffer)); } diff --git a/src/lookupTable.cpp b/src/lookupTable.cpp index 389ef3c..c4def39 100644 --- a/src/lookupTable.cpp +++ b/src/lookupTable.cpp @@ -5,6 +5,7 @@ * Author: jdi */ +#include #include "lookupTable.h" lookupTable::lookupTable(std::initializer_list l) {