From: bert hubert Date: Wed, 9 Dec 2015 11:13:58 +0000 (+0100) Subject: split out console code from dnsdist.cc, plus move some generic stuff to misc.cc X-Git-Tag: dnsdist-1.0.0-alpha1~93 X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=ffb071581fe6ad2b20545bb88c688db263588a89;p=pdns split out console code from dnsdist.cc, plus move some generic stuff to misc.cc --- diff --git a/pdns/Makefile.am b/pdns/Makefile.am index 6876dc30c..98c6b7925 100644 --- a/pdns/Makefile.am +++ b/pdns/Makefile.am @@ -604,6 +604,7 @@ dnsdist_SOURCES = \ ednssubnet.cc ednssubnet.hh \ dnsdist.cc \ dnsdist-carbon.cc \ + dnsdist-console.cc \ dnsdist-ecs.cc dnsdist-ecs.hh \ dnsdist-lua.cc \ dnsdist-lua2.cc \ diff --git a/pdns/dnsdist-console.cc b/pdns/dnsdist-console.cc new file mode 100644 index 000000000..31bf6f5df --- /dev/null +++ b/pdns/dnsdist-console.cc @@ -0,0 +1,266 @@ +#include "dnsdist.hh" +#include "sodcrypto.hh" +#include +#include +#include +#include "dolog.hh" + +void doClient(ComboAddress server, const std::string& command) +{ + cout<<"Connecting to "< resp(new char[len]); + readn2(fd, resp.get(), len); + msg.assign(resp.get(), len); + msg=sodDecryptSym(msg, g_key, theirs); + cout< dupper; + { + ifstream history(".dnsdist_history"); + string line; + while(getline(history, line)) + add_history(line.c_str()); + } + ofstream history(".dnsdist_history", std::ios_base::app); + string lastline; + for(;;) { + char* sline = readline("> "); + rl_bind_key('\t',rl_complete); + if(!sline) + break; + + string line(sline); + if(!line.empty() && line != lastline) { + add_history(sline); + history << sline < resp(new char[len]); + readn2(fd, resp.get(), len); + msg.assign(resp.get(), len); + msg=sodDecryptSym(msg, g_key, theirs); + cout< dupper; + { + ifstream history(".dnsdist_history"); + string line; + while(getline(history, line)) + add_history(line.c_str()); + } + ofstream history(".dnsdist_history", std::ios_base::app); + string lastline; + for(;;) { + char* sline = readline("> "); + rl_bind_key('\t',rl_complete); + if(!sline) + break; + + string line(sline); + if(!line.empty() && line != lastline) { + add_history(sline); + history << sline < lock(g_luamutex); + g_outputBuffer.clear(); + auto ret=g_lua.executeCode< + boost::optional< + boost::variant< + string, + shared_ptr + > + > + >(line); + + if(ret) { + if (const auto strValue = boost::get>(&*ret)) { + cout<<(*strValue)->getName()<(&*ret)) { + cout<<*strValue< words{"showRules()", "shutdown()", "rmRule(", "mvRule(", "addACL(", "addLocal(", "setServerPolicy(", "setServerPolicyLua(", + "newServer(", "rmServer(", "showServers()", "show(", "newDNSName(", "newSuffixMatchNode(", "controlSocket(", "topClients(", "showResponseLatency()", + "newQPSLimiter(", "makeKey()", "setKey(", "testCrypto()", "addAnyTCRule()", "showServerPolicy()", "setACL(", "showACL()", "addDomainBlock(", + "addPoolRule(", "addQPSLimit(", "topResponses(", "topQueries(", "topRule()", "setDNSSECPool(", "setECSOverride(", "setECSSourcePrefixV4(", + "setECSSourcePrefixV6(", "addDelay(", "setTCPRecvTimeout(", "setTCPSendTimeout(", "setMaxTCPClientThreads(", "setMaxUDPOutstanding(" }; + static int s_counter=0; + int counter=0; + if(!state) + s_counter=0; + + for(auto w : words) { + if(boost::starts_with(w, t) && counter++ == s_counter) { + s_counter++; + return strdup(w.c_str()); + } + } + return 0; +} + +char** my_completion( const char * text , int start, int end) +{ + char **matches=0; + if (start == 0) + matches = rl_completion_matches ((char*)text, &my_generator); + else + rl_bind_key('\t',rl_abort); + + if(!matches) + rl_bind_key('\t', rl_abort); + return matches; +} +} + +void controlClientThread(int fd, ComboAddress client) +try +{ + SodiumNonce theirs; + readn2(fd, (char*)theirs.value, sizeof(theirs.value)); + SodiumNonce ours; + ours.init(); + writen2(fd, (char*)ours.value, sizeof(ours.value)); + + for(;;) { + uint32_t len; + if(!getMsgLen32(fd, &len)) + break; + boost::scoped_array msg(new char[len]); + readn2(fd, msg.get(), len); + + string line(msg.get(), len); + line = sodDecryptSym(line, g_key, theirs); + // cerr<<"Have decrypted line: "< lock(g_luamutex); + g_outputBuffer.clear(); + auto ret=g_lua.executeCode< + boost::optional< + boost::variant< + string, + shared_ptr + > + > + >(line); + + if(ret) { + if (const auto strValue = boost::get>(&*ret)) { + response=(*strValue)->getName(); + } + else if (const auto strValue = boost::get(&*ret)) { + response=*strValue; + } + } + else + response=g_outputBuffer; + + } + catch(const LuaContext::ExecutionErrorException& e) { + response = "Error: " + string(e.what()) + ": "; + try { + std::rethrow_if_nested(e); + } catch(const std::exception& e) { + // e is the exception that was thrown from inside the lambda + response+= string(e.what()); + } + catch(const PDNSException& e) { + // e is the exception that was thrown from inside the lambda + response += string(e.reason); + } + } + catch(const LuaContext::SyntaxErrorException& e) { + response = "Error: " + string(e.what()) + ": "; + } + response = sodEncryptSym(response, g_key, ours); + putMsgLen32(fd, response.length()); + writen2(fd, response.c_str(), response.length()); + } + infolog("Closed control connection from %s", client.toStringWithPort()); + close(fd); + fd=-1; +} +catch(std::exception& e) +{ + errlog("Got an exception in client connection from %s: %s", client.toStringWithPort(), e.what()); + if(fd >= 0) + close(fd); +} + diff --git a/pdns/dnsdist.cc b/pdns/dnsdist.cc index 0dc0771d4..3695b54c4 100644 --- a/pdns/dnsdist.cc +++ b/pdns/dnsdist.cc @@ -766,81 +766,6 @@ void* maintThread() string g_key; -static void controlClientThread(int fd, ComboAddress client) -try -{ - SodiumNonce theirs; - readn2(fd, (char*)theirs.value, sizeof(theirs.value)); - SodiumNonce ours; - ours.init(); - writen2(fd, (char*)ours.value, sizeof(ours.value)); - - for(;;) { - uint32_t len; - if(!getMsgLen32(fd, &len)) - break; - boost::scoped_array msg(new char[len]); - readn2(fd, msg.get(), len); - - string line(msg.get(), len); - line = sodDecryptSym(line, g_key, theirs); - // cerr<<"Have decrypted line: "< lock(g_luamutex); - g_outputBuffer.clear(); - auto ret=g_lua.executeCode< - boost::optional< - boost::variant< - string, - shared_ptr - > - > - >(line); - - if(ret) { - if (const auto strValue = boost::get>(&*ret)) { - response=(*strValue)->getName(); - } - else if (const auto strValue = boost::get(&*ret)) { - response=*strValue; - } - } - else - response=g_outputBuffer; - - } - catch(const LuaContext::ExecutionErrorException& e) { - response = "Error: " + string(e.what()) + ": "; - try { - std::rethrow_if_nested(e); - } catch(const std::exception& e) { - // e is the exception that was thrown from inside the lambda - response+= string(e.what()); - } - catch(const PDNSException& e) { - // e is the exception that was thrown from inside the lambda - response += string(e.reason); - } - } - catch(const LuaContext::SyntaxErrorException& e) { - response = "Error: " + string(e.what()) + ": "; - } - response = sodEncryptSym(response, g_key, ours); - putMsgLen32(fd, response.length()); - writen2(fd, response.c_str(), response.length()); - } - infolog("Closed control connection from %s", client.toStringWithPort()); - close(fd); - fd=-1; -} -catch(std::exception& e) -{ - errlog("Got an exception in client connection from %s: %s", client.toStringWithPort(), e.what()); - if(fd >= 0) - close(fd); -} - void controlThread(int fd, ComboAddress local) try @@ -862,153 +787,6 @@ catch(std::exception& e) -static void doClient(ComboAddress server, const std::string& command) -{ - cout<<"Connecting to "< resp(new char[len]); - readn2(fd, resp.get(), len); - msg.assign(resp.get(), len); - msg=sodDecryptSym(msg, g_key, theirs); - cout< dupper; - { - ifstream history(".dnsdist_history"); - string line; - while(getline(history, line)) - add_history(line.c_str()); - } - ofstream history(".dnsdist_history", std::ios_base::app); - string lastline; - for(;;) { - char* sline = readline("> "); - rl_bind_key('\t',rl_complete); - if(!sline) - break; - - string line(sline); - if(!line.empty() && line != lastline) { - add_history(sline); - history << sline < resp(new char[len]); - readn2(fd, resp.get(), len); - msg.assign(resp.get(), len); - msg=sodDecryptSym(msg, g_key, theirs); - cout< dupper; - { - ifstream history(".dnsdist_history"); - string line; - while(getline(history, line)) - add_history(line.c_str()); - } - ofstream history(".dnsdist_history", std::ios_base::app); - string lastline; - for(;;) { - char* sline = readline("> "); - rl_bind_key('\t',rl_complete); - if(!sline) - break; - - string line(sline); - if(!line.empty() && line != lastline) { - add_history(sline); - history << sline < lock(g_luamutex); - g_outputBuffer.clear(); - auto ret=g_lua.executeCode< - boost::optional< - boost::variant< - string, - shared_ptr - > - > - >(line); - - if(ret) { - if (const auto strValue = boost::get>(&*ret)) { - cout<<(*strValue)->getName()<(&*ret)) { - cout<<*strValue<pw_uid; - } - - return result; -} - -static gid_t strToGID(const string &str) -{ - gid_t result = 0; - const char * cstr = str.c_str(); - struct group * grp = getgrnam(cstr); - - if (grp == NULL) { - char * endptr = 0; - long int val = strtol(cstr, &endptr, 10); - - if (((val == LONG_MAX || val == LLONG_MIN) && errno == ERANGE) || endptr == cstr || val <= 0) { - warnlog("Warning: Unable to parse group ID %s", cstr); - } - else { - result = val; - } - } - else { - result = grp->gr_gid; - } - - return result; -} - -/**** CARGO CULT CODE AHEAD ****/ -extern "C" { -char* my_generator(const char* text, int state) -{ - string t(text); - vector words{"showRules()", "shutdown()", "rmRule(", "mvRule(", "addACL(", "addLocal(", "setServerPolicy(", "setServerPolicyLua(", - "newServer(", "rmServer(", "showServers()", "show(", "newDNSName(", "newSuffixMatchNode(", "controlSocket(", "topClients(", "showResponseLatency()", - "newQPSLimiter(", "makeKey()", "setKey(", "testCrypto()", "addAnyTCRule()", "showServerPolicy()", "setACL(", "showACL()", "addDomainBlock(", - "addPoolRule(", "addQPSLimit(", "topResponses(", "topQueries(", "topRule()", "setDNSSECPool(", "setECSOverride(", "setECSSourcePrefixV4(", - "setECSSourcePrefixV6(", "addDelay(", "setTCPRecvTimeout(", "setTCPSendTimeout(", "setMaxTCPClientThreads(", "setMaxUDPOutstanding(" }; - static int s_counter=0; - int counter=0; - if(!state) - s_counter=0; - - for(auto w : words) { - if(boost::starts_with(w, t) && counter++ == s_counter) { - s_counter++; - return strdup(w.c_str()); - } - } - return 0; -} - -static char** my_completion( const char * text , int start, int end) -{ - char **matches=0; - if (start == 0) - matches = rl_completion_matches ((char*)text, &my_generator); - else - rl_bind_key('\t',rl_abort); - - if(!matches) - rl_bind_key('\t', rl_abort); - return matches; -} -} struct { diff --git a/pdns/dnsdist.hh b/pdns/dnsdist.hh index fe2867f6e..444dc910b 100644 --- a/pdns/dnsdist.hh +++ b/pdns/dnsdist.hh @@ -427,3 +427,9 @@ bool putMsgLen32(int fd, uint32_t len); void* tcpAcceptorThread(void* p); void moreLua(); +void doClient(ComboAddress server, const std::string& command); +void doConsole(); +void controlClientThread(int fd, ComboAddress client); +extern "C" { +char** my_completion( const char * text , int start, int end); +} diff --git a/pdns/dnsdistdist/Makefile.am b/pdns/dnsdistdist/Makefile.am index 6433a7adb..9def85c0e 100644 --- a/pdns/dnsdistdist/Makefile.am +++ b/pdns/dnsdistdist/Makefile.am @@ -34,6 +34,7 @@ dnsdist_SOURCES = \ dns.cc dns.hh \ dnsdist.cc dnsdist.hh \ dnsdist-carbon.cc \ + dnsdist-console.cc \ dnsdist-ecs.cc dnsdist-ecs.hh \ dnsdist-lua.cc \ dnsdist-lua2.cc \ diff --git a/pdns/dnsdistdist/dnsdist-console.cc b/pdns/dnsdistdist/dnsdist-console.cc new file mode 120000 index 000000000..402fcdc9d --- /dev/null +++ b/pdns/dnsdistdist/dnsdist-console.cc @@ -0,0 +1 @@ +../dnsdist-console.cc \ No newline at end of file diff --git a/pdns/misc.cc b/pdns/misc.cc index b2ee147ba..25b2f5105 100644 --- a/pdns/misc.cc +++ b/pdns/misc.cc @@ -54,6 +54,10 @@ #include #include "iputils.hh" #include "dnsparser.hh" +#include +#include +#include + bool g_singleThreaded; @@ -1232,3 +1236,53 @@ double DiffTime(const struct timeval& first, const struct timeval& second) } return seconds + useconds/1000000.0; } + + +uid_t strToUID(const string &str) +{ + uid_t result = 0; + const char * cstr = str.c_str(); + struct passwd * pwd = getpwnam(cstr); + + if (pwd == NULL) { + char * endptr = 0; + long int val = strtol(cstr, &endptr, 10); + + if (((val == LONG_MAX || val == LLONG_MIN) && errno == ERANGE) || endptr == cstr || val <= 0) { + throw runtime_error((boost::format("Warning: Unable to parse user ID %s") % cstr).str() ); + } + else { + result = val; + } + } + else { + result = pwd->pw_uid; + } + + return result; +} + +gid_t strToGID(const string &str) +{ + gid_t result = 0; + const char * cstr = str.c_str(); + struct group * grp = getgrnam(cstr); + + if (grp == NULL) { + char * endptr = 0; + long int val = strtol(cstr, &endptr, 10); + + if (((val == LONG_MAX || val == LLONG_MIN) && errno == ERANGE) || endptr == cstr || val <= 0) { + throw runtime_error((boost::format("Warning: Unable to parse group ID %s") % cstr).str() ); + } + else { + result = val; + } + } + else { + result = grp->gr_gid; + } + + return result; +} + diff --git a/pdns/misc.hh b/pdns/misc.hh index 9036bb2d6..71895e5ea 100644 --- a/pdns/misc.hh +++ b/pdns/misc.hh @@ -647,3 +647,5 @@ const char* addS(const C& c, typename std::enable_if::value>::t double DiffTime(const struct timespec& first, const struct timespec& second); double DiffTime(const struct timeval& first, const struct timeval& second); +uid_t strToUID(const string &str); +gid_t strToGID(const string &str);