////////////////////////////////////////////////////////////////////// // Dump Black Listed DNS entries // Written by Jonathan A. Foster // Started Ocotber 27th, 2021 // Copyright JF Possibilities, Inc. All rights reserved. // // Read the "dns" table and dump all black listed host names as // entries for a "hosts" file. This could also be easily done with a // script but I want to be able to use the same config file as every- // thing else and parsing in SH is clumsy at best. ////////////////////////////////////////////////////////////////////// #include #include #include #include #include #include "../strutil.h" #include "appbase.h" using namespace std; ////////////////////////////////////////////////////////////////////// // Class to manage and test hoset names agains bad domains ////////////////////////////////////////////////////////////////////// struct DomainList: public StringList { bool operator==(const std::string host) { DomainList::const_iterator i; int dl, hl = host.size(); for(i=begin(); i!=end(); i++) { if(*i==host) return true; dl = i->size()+1; if(hl>dl && host.substr(hl-dl)=="."+*i) return true; } return false; } inline bool operator!=(const std::string host) { return !(*this==host); } }; namespace cppdb { session &operator>>(cppdb::session &db, DomainList &doms) { cppdb::result qry; std::string s; doms.clear(); qry = db << "SELECT name FROM dns_wild WHERE status=2"; while(qry.next()) { qry >> s; doms.push_back(s); } return db; } } // cppdb ////////////////////////////////////////////////////////////////////// // Connection Report Generator Application Class ////////////////////////////////////////////////////////////////////// struct DNSblackList: BlackListBaseApp { bool all; unsigned do_switch(const char *arg) { if(*arg=='a' && !arg[1]) { all=1; return 0; } return BlackListBaseApp::do_switch(arg); } int help() { std::cerr << " FORMAT: " << basename(command_args[0]) << " -c {config} [-a] [-4 {address}] [-6 {address}]\n" << '\n' << "The config file must have a [Traffic Mon] section with the database\n" << "credentials in it. -4 & -6 set the addresses to pin blocked names to.\n" << "They default to the 'localhost' address in the respective family. Set\n" << "to '' to turn off output of that family. -a dumps all blocked host\n" << "names otherwise host names that are covered by a domain block will\n" << "not be shown." << std::endl; return ExitCode = 1; } int main() { DomainList baddoms; cppdb::result qry; string s; int x; /// SETUP & VALIDATE CLI /// all = false; if(x=BlackListBaseApp::main()) return x; // Parse CLI args, open conf & db if(ipv6!="" && ipv6.size()<8) ipv6+='\t'; // an extra \t to line up columns. :-) /// Load list of bad domains /// // These should be excluded from the list below since they should be // blocked by other means and the point of domain wide blocking is to // relieve the burden on the blocking tools (dnsmasq). if(!all) db >> baddoms; /// Query & load data /// qry = db << "SELECT name " "FROM dns " "WHERE status=2 " // 2 = blocked... need this doc'd somewhere... "ORDER BY name"; while(qry.next()) { qry >> s; if(all || baddoms!=s) { // exclude blocked domains if(ipv4!="") cout << ipv4 << '\t' << s << '\n'; if(ipv6!="") cout << ipv6 << '\t' << s << '\n'; } } return 0; } }; ////////////////////////////////////////////////////////////////////// // Lets run the report and dump it out ////////////////////////////////////////////////////////////////////// MAIN(DNSblackList)