]> git.ipfire.org Git - thirdparty/pdns.git/blame - pdns/toysdig.cc
Merge pull request #9073 from pieterlexis/runtime-dirs-virtual-hosting
[thirdparty/pdns.git] / pdns / toysdig.cc
CommitLineData
870a0fe4
AT
1#ifdef HAVE_CONFIG_H
2#include "config.h"
3#endif
181fcd29 4#include "dnsparser.hh"
12475222 5#include "rec-lua-conf.hh"
181fcd29
BH
6#include "sstuff.hh"
7#include "misc.hh"
8#include "dnswriter.hh"
9#include "dnsrecords.hh"
10#include "statbag.hh"
af7d3ea6 11#include "ednssubnet.hh"
5bb846fe 12#include "dnssecinfra.hh"
13#include "recursor_cache.hh"
14#include "base32.hh"
f2234140 15#include "root-dnssec.hh"
243f4780 16
17#include "validate.hh"
181fcd29
BH
18StatBag S;
19
5bb846fe 20class TCPResolver : public boost::noncopyable
21{
22public:
23 TCPResolver(ComboAddress addr) : d_rsock(AF_INET, SOCK_STREAM)
24 {
25 d_rsock.connect(addr);
26 }
27
28 string query(const DNSName& qname, uint16_t qtype)
29 {
30 cerr<<"Q "<<qname<<"/"<<DNSRecordContent::NumberToType(qtype)<<endl;
31 vector<uint8_t> packet;
32 DNSPacketWriter pw(packet, qname, qtype);
33
34 // recurse
35 pw.getHeader()->rd=true;
36
37 // we'll do the validation
38 pw.getHeader()->cd=true;
39 pw.getHeader()->ad=true;
40
41 // we do require DNSSEC records to do that!
42 pw.addOpt(2800, 0, EDNSOpts::DNSSECOK);
43 pw.commit();
44
45 uint16_t len;
46 len = htons(packet.size());
47 if(d_rsock.write((char *) &len, 2) != 2)
48 throw PDNSException("tcp write failed");
49
16657041 50 d_rsock.writen(string(packet.begin(), packet.end()));
5bb846fe 51
2cb98b9a 52 int bread=d_rsock.read((char *) &len, 2);
53 if( bread <0)
a702a96c 54 throw PDNSException("tcp read failed: "+stringerror());
2cb98b9a 55 if(bread != 2)
56 throw PDNSException("EOF on TCP read");
5bb846fe 57
58 len=ntohs(len);
c2826d2e 59 std::unique_ptr<char[]> creply(new char[len]);
5bb846fe 60 int n=0;
61 int numread;
62 while(n<len) {
c2826d2e 63 numread=d_rsock.read(creply.get()+n, len-n);
34c513f9 64 if(numread<0) {
a702a96c 65 throw PDNSException("tcp read failed: "+stringerror());
34c513f9 66 }
5bb846fe 67 n+=numread;
68 }
69
c2826d2e 70 string reply(creply.get(), len);
5bb846fe 71
72 return reply;
73 }
74
75 Socket d_rsock;
76};
77
5bb846fe 78
243f4780 79class TCPRecordOracle : public DNSRecordOracle
5bb846fe 80{
243f4780 81public:
82 TCPRecordOracle(const ComboAddress& dest) : d_dest(dest) {}
83 vector<DNSRecord> get(const DNSName& qname, uint16_t qtype) override
5bb846fe 84 {
243f4780 85 TCPResolver tr(d_dest);
86 string resp=tr.query(qname, qtype);
27c0050c 87 MOADNSParser mdp(false, resp);
243f4780 88 vector<DNSRecord> ret;
89 ret.reserve(mdp.d_answers.size());
90 for(const auto& a : mdp.d_answers) {
91 ret.push_back(a.first);
5bb846fe 92 }
243f4780 93 return ret;
5bb846fe 94 }
243f4780 95private:
96 ComboAddress d_dest;
97};
5bb846fe 98
12475222 99GlobalStateHolder<LuaConfigItems> g_luaconfs;
100LuaConfigItems::LuaConfigItems()
101{
f2234140 102 for (const auto &dsRecord : rootDSs) {
32122aab 103 auto ds=std::dynamic_pointer_cast<DSRecordContent>(DSRecordContent::make(dsRecord));
12c06211 104 dsAnchors[g_rootdnsname].insert(*ds);
f2234140 105 }
12475222 106}
5bb846fe 107
12475222 108DNSFilterEngine::DNSFilterEngine() {}
5bb846fe 109
181fcd29
BH
110int main(int argc, char** argv)
111try
112{
113 reportAllTypes();
12475222 114// g_rootDS = "19036 8 2 49aac11d7b6f6446702e54a1607371607a1a41855200fd2ce1cdde32f24e8fb5";
7492e4b3 115
12475222 116// if(argv[5])
117// g_rootDS = argv[5];
118
2cb98b9a 119 // g_anchors.insert(DSRecordContent("19036 8 2 49aac11d7b6f6446702e54a1607371607a1a41855200fd2ce1cdde32f24e8fb5"));
181fcd29 120 if(argc < 4) {
2cb98b9a 121 cerr<<"Syntax: toysdig IP-address port question question-type [rootDS]\n";
181fcd29
BH
122 exit(EXIT_FAILURE);
123 }
5bb846fe 124 ComboAddress dest(argv[1] + (*argv[1]=='@'), atoi(argv[2]));
243f4780 125 TCPRecordOracle tro(dest);
5bb846fe 126 DNSName qname(argv[3]);
127 uint16_t qtype=DNSRecordContent::TypeToNumber(argv[4]);
5bb846fe 128 cout<<"digraph oneshot {"<<endl;
af7d3ea6 129
243f4780 130 auto recs=tro.get(qname, qtype);
181fcd29 131
243f4780 132 cspmap_t cspmap=harvestCSPFromRecs(recs);
9c3caa79 133 cerr<<"Got "<<cspmap.size()<<" RRSETs: ";
134 int numsigs=0;
135 for(const auto& csp : cspmap) {
136 cerr<<" "<<csp.first.first<<'/'<<DNSRecordContent::NumberToType(csp.first.second)<<": "<<csp.second.signatures.size()<<" sigs for "<<csp.second.records.size()<<" records"<<endl;
137 numsigs+= csp.second.signatures.size();
5bb846fe 138 }
9c3caa79 139
647544dc 140 skeyset_t keys;
9c3caa79 141 cspmap_t validrrsets;
142
143 if(numsigs) {
144 for(const auto& csp : cspmap) {
145 for(const auto& sig : csp.second.signatures) {
146 cerr<<"got rrsig "<<sig->d_signer<<"/"<<sig->d_tag<<endl;
243f4780 147 vState state = getKeysFor(tro, sig->d_signer, keys);
9c3caa79 148 cerr<<"! state = "<<vStates[state]<<", now have "<<keys.size()<<" keys at "<<qname<<endl;
5bb846fe 149 // dsmap.insert(make_pair(dsrc.d_tag, dsrc));
150 }
151 }
9c3caa79 152
153 validateWithKeySet(cspmap, validrrsets, keys);
92011b8f 154 }
5bb846fe 155 else {
156 cerr<<"no sigs, hoping for Insecure"<<endl;
243f4780 157 vState state = getKeysFor(tro, qname, keys);
5bb846fe 158 cerr<<"! state = "<<vStates[state]<<", now have "<<keys.size()<<" keys at "<<qname<<endl;
159 }
9c3caa79 160 cerr<<"! validated "<<validrrsets.size()<<" RRsets out of "<<cspmap.size()<<endl;
5bb846fe 161
162 cerr<<"% validated RRs:"<<endl;
9c3caa79 163 for(auto i=validrrsets.begin(); i!=validrrsets.end(); i++) {
5bb846fe 164 cerr<<"% "<<i->first.first<<"/"<<DNSRecordContent::NumberToType(i->first.second)<<endl;
9c3caa79 165 for(auto j=i->second.records.begin(); j!=i->second.records.end(); j++) {
2cb98b9a 166 cerr<<"\t% > "<<(*j)->getZoneRepresentation()<<endl;
5bb846fe 167 }
168 }
169
170 cout<<"}"<<endl;
171 exit(0);
181fcd29
BH
172}
173catch(std::exception &e)
174{
175 cerr<<"Fatal: "<<e.what()<<endl;
176}
2cb98b9a 177catch(PDNSException &pe)
178{
179 cerr<<"Fatal: "<<pe.reason<<endl;
180}
181