]> git.ipfire.org Git - thirdparty/pdns.git/blame - pdns/dynhandler.cc
Added qtype statistics to recursor and rec_control (get-qtypelist)
[thirdparty/pdns.git] / pdns / dynhandler.cc
CommitLineData
12c86877
BH
1/*
2 PowerDNS Versatile Database Driven Nameserver
379ab445 3 Copyright (C) 2002 - 2008 PowerDNS.COM BV
12c86877
BH
4
5 This program is free software; you can redistribute it and/or modify
ea44d9d3
BH
6 it under the terms of the GNU General Public License version 2 as
7 published by the Free Software Foundation.
12c86877 8
f782fe38
MH
9 Additionally, the license of this program contains a special
10 exception which allows to distribute the program in binary form when
11 it is linked against OpenSSL.
12
12c86877
BH
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
17
18 You should have received a copy of the GNU General Public License
19 along with this program; if not, write to the Free Software
06bd9ccf 20 Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
12c86877 21*/
379ab445 22#include "packetcache.hh"
bd11bd1d 23#include "utility.hh"
12c86877
BH
24#include "dynhandler.hh"
25#include "statbag.hh"
26#include "logger.hh"
27#include "dns.hh"
28#include "arguments.hh"
29#include <signal.h>
bd11bd1d 30#include "misc.hh"
12c86877 31#include "communicator.hh"
627d2ca2 32#include "dnsseckeeper.hh"
ba7244a5 33#include "nameserver.hh"
12c86877
BH
34
35static bool s_pleasequit;
64bcb6be 36static string d_status;
12c86877
BH
37
38bool DLQuitPlease()
39{
40 return s_pleasequit;
41}
42
43string DLQuitHandler(const vector<string>&parts, Utility::pid_t ppid)
44{
45 string ret="No return value";
46 if(parts[0]=="QUIT") {
47 s_pleasequit=true;
48 ret="Scheduling exit";
49 L<<Logger::Error<<"Scheduling exit on remote request"<<endl;
50 }
51 return ret;
52
53}
54
55static void dokill(int)
56{
57 exit(1);
58}
59
64bcb6be
RA
60string DLCurrentConfigHandler(const vector<string>&parts, Utility::pid_t ppid)
61{
62 return ::arg().configstring(true);
63}
64
12c86877
BH
65string DLRQuitHandler(const vector<string>&parts, Utility::pid_t ppid)
66{
12c86877 67 signal(SIGALRM, dokill);
12c86877 68 alarm(1);
12c86877
BH
69 return "Exiting";
70}
71
72string DLPingHandler(const vector<string>&parts, Utility::pid_t ppid)
73{
74 return "PONG";
75}
76
77string DLShowHandler(const vector<string>&parts, Utility::pid_t ppid)
78{
79 extern StatBag S;
80 string ret("Wrong number of parameters");
81 if(parts.size()==2) {
82 if(parts[1]=="*")
83 ret=S.directory();
84 else
85 ret=S.getValueStr(parts[1]);
86 }
87
88 return ret;
89}
90
12c86877
BH
91
92void setStatus(const string &str)
93{
94 d_status=str;
95}
96
97string DLStatusHandler(const vector<string>&parts, Utility::pid_t ppid)
98{
99 ostringstream os;
100 os<<ppid<<": "<<d_status;
101 return os.str();
102}
103
104string DLUptimeHandler(const vector<string>&parts, Utility::pid_t ppid)
105{
106 ostringstream os;
107 os<<humanDuration(time(0)-s_starttime);
108 return os.str();
109}
110
111string DLPurgeHandler(const vector<string>&parts, Utility::pid_t ppid)
112{
113 extern PacketCache PC;
627d2ca2 114 DNSSECKeeper dk;
12c86877 115 ostringstream os;
27fdc3fc 116 int ret=0;
12c86877 117
27fdc3fc
BH
118 if(parts.size()>1) {
119 for (vector<string>::const_iterator i=++parts.begin();i<parts.end();++i) {
120 ret+=PC.purge(*i);
627d2ca2 121 dk.clearCaches(*i);
27fdc3fc
BH
122 }
123 }
627d2ca2 124 else {
12c86877 125 ret=PC.purge();
627d2ca2
PD
126 dk.clearAllCaches();
127 }
128
12c86877
BH
129 os<<ret;
130 return os.str();
131}
132
133string DLCCHandler(const vector<string>&parts, Utility::pid_t ppid)
134{
135 extern PacketCache PC;
136 map<char,int> counts=PC.getCounts();
137 ostringstream os;
138 bool first=true;
139 for(map<char,int>::const_iterator i=counts.begin();i!=counts.end();++i) {
140 if(!first)
141 os<<", ";
142 first=false;
143
144 if(i->first=='!')
145 os<<"negative queries: ";
146 else if(i->first=='Q')
147 os<<"queries: ";
148 else if(i->first=='n')
149 os<<"non-recursive packets: ";
150 else if(i->first=='r')
151 os<<"recursive packets: ";
152 else
153 os<<"unknown: ";
154
155 os<<i->second;
156 }
157
158 return os.str();
159}
160
ba7244a5
PD
161string DLQTypesHandler(const vector<string>&parts, Utility::pid_t ppid)
162{
93698ef3
PD
163 typedef map<uint16_t, uint64_t> qtypenums_t;
164 qtypenums_t qtypenums = g_rs.getQTypeResponseCounts();
ba7244a5 165 ostringstream os;
879efdb9 166 boost::format fmt("%s\t%d\n");
93698ef3
PD
167 BOOST_FOREACH(const qtypenums_t::value_type& val, qtypenums) {
168 os << (fmt %DNSRecordContent::NumberToType( val.first) % val.second).str();
ba7244a5 169 }
ba7244a5
PD
170 return os.str();
171}
12c86877 172
93698ef3
PD
173string DLRSizesHandler(const vector<string>&parts, Utility::pid_t ppid)
174{
175 typedef map<uint16_t, uint64_t> respsizes_t;
176 respsizes_t respsizes = g_rs.getSizeResponseCounts();
177 ostringstream os;
178 boost::format fmt("%d\t%d\n");
179 BOOST_FOREACH(const respsizes_t::value_type& val, respsizes) {
180 os << (fmt % val.first % val.second).str();
181 }
182 return os.str();
183}
184
185string DLRemotesHandler(const vector<string>&parts, Utility::pid_t ppid)
186{
187 extern StatBag S;
188 typedef vector<pair<string, unsigned int> > totals_t;
189 totals_t totals = S.getRing("remotes");
190 string ret;
191 boost::format fmt("%s\t%d\n");
192 BOOST_FOREACH(totals_t::value_type& val, totals) {
193 ret += (fmt % val.first % val.second).str();
194 }
195 return ret;
196}
197
12c86877
BH
198string DLSettingsHandler(const vector<string>&parts, Utility::pid_t ppid)
199{
200 static const char *whitelist[]={"query-logging",0};
201 const char **p;
202
203 if(parts.size()!=3) {
204 return "Syntax: set variable value";
205 }
206
207 for(p=whitelist;*p;p++)
208 if(*p==parts[1])
209 break;
3120733f 210 if(*p) {
379ab445 211 ::arg().set(parts[1])=parts[2];
12c86877
BH
212 return "done";
213 }
214 else
3120733f 215 return "This setting cannot be changed at runtime, or no such setting";
12c86877
BH
216
217}
218
12c86877
BH
219string DLVersionHandler(const vector<string>&parts, Utility::pid_t ppid)
220{
12c86877
BH
221 return VERSION;
222}
223
ef1d2f44
BH
224string DLNotifyRetrieveHandler(const vector<string>&parts, Utility::pid_t ppid)
225{
226 extern CommunicatorClass Communicator;
227 ostringstream os;
228 if(parts.size()!=2)
229 return "syntax: retrieve domain";
230
231 const string& domain=parts[1];
232 DomainInfo di;
233 PacketHandler P;
234 if(!P.getBackend()->getDomainInfo(domain, di))
235 return "Domain '"+domain+"' unknown";
236
e5b11b2f 237 if(di.masters.empty())
f2c11a48
BH
238 return "Domain '"+domain+"' is not a slave domain (or has no master defined)";
239
e5b11b2f
BH
240 random_shuffle(di.masters.begin(), di.masters.end());
241 Communicator.addSuckRequest(domain, di.masters.front());
242 return "Added retrieval request for '"+domain+"' from master "+di.masters.front();
ef1d2f44 243}
12c86877
BH
244
245string DLNotifyHostHandler(const vector<string>&parts, Utility::pid_t ppid)
246{
247 extern CommunicatorClass Communicator;
248 ostringstream os;
249 if(parts.size()!=3)
ea44d9d3 250 return "syntax: notify-host domain ip";
2685008f
PD
251 if(!::arg().mustDo("master"))
252 return "PowerDNS not configured as master";
5762f14e 253
c069c1f2
BH
254 try {
255 ComboAddress ca(parts[2]);
256 } catch(...)
257 {
5762f14e 258 return "Unable to convert '"+parts[2]+"' to an IP address";
c069c1f2
BH
259 }
260
12c86877
BH
261 L<<Logger::Warning<<"Notification request to host "<<parts[2]<<" for domain '"<<parts[1]<<"' received"<<endl;
262 Communicator.notify(parts[1],parts[2]);
263 return "Added to queue";
264}
265
266string DLNotifyHandler(const vector<string>&parts, Utility::pid_t ppid)
267{
268 extern CommunicatorClass Communicator;
269 ostringstream os;
270 if(parts.size()!=2)
271 return "syntax: notify domain";
2685008f
PD
272 if(!::arg().mustDo("master"))
273 return "PowerDNS not configured as master";
11a45617 274 L<<Logger::Warning<<"Notification request for domain '"<<parts[1]<<"' received from operator"<<endl;
12c86877
BH
275 if(!Communicator.notifyDomain(parts[1]))
276 return "Failed to add to the queue - see log";
277 return "Added to queue";
278}
279
280string DLRediscoverHandler(const vector<string>&parts, Utility::pid_t ppid)
281{
85a41ee7
MZ
282 UeberBackend::rediscover_all();
283 return "Ok";
12c86877
BH
284}
285
286string DLReloadHandler(const vector<string>&parts, Utility::pid_t ppid)
287{
85a41ee7 288 UeberBackend::reload_all();
12c86877
BH
289 L<<Logger::Error<<"Reload was requested"<<endl;
290 return "Ok";
291}
64bcb6be 292