View | Details | Raw Unified | Return to bug 116029
Collapse All | Expand All

(-)Makefile (-1 / +1 lines)
Lines 7-13 Link Here
7
7
8
PORTNAME=	powerdns-recursor
8
PORTNAME=	powerdns-recursor
9
PORTVERSION=	3.1.4
9
PORTVERSION=	3.1.4
10
PORTREVISION=	5
10
PORTREVISION=	6
11
CATEGORIES=	dns ipv6
11
CATEGORIES=	dns ipv6
12
MASTER_SITES=	http://downloads.powerdns.com/releases/ \
12
MASTER_SITES=	http://downloads.powerdns.com/releases/ \
13
		http://mirrors.evolva.ro/powerdns.com/releases/
13
		http://mirrors.evolva.ro/powerdns.com/releases/
(-)files/patch-multiline_txt_records (+398 lines)
Line 0 Link Here
1
Index: dnswriter.hh
2
===================================================================
3
--- dnswriter.hh (revision 962)
4
+++ dnswriter.hh (revision 996)
5
@@ -84,5 +84,5 @@
6
 
7
   void xfrLabel(const string& label, bool compress=false);
8
-  void xfrText(const string& text);
9
+  void xfrText(const string& text, bool multi=false);
10
   void xfrBlob(const string& blob);
11
   void xfrHexBlob(const string& blob);
12
Index: dnsparser.hh
13
===================================================================
14
--- dnsparser.hh (revision 972)
15
+++ dnsparser.hh (revision 996)
16
@@ -110,7 +110,7 @@
17
   }
18
 
19
-  void xfrText(string &text)
20
-  {
21
-    text=getText();
22
+  void xfrText(string &text, bool multi=false)
23
+  {
24
+    text=getText(multi);
25
   }
26
 
27
@@ -126,5 +126,5 @@
28
 
29
   string getLabel(unsigned int recurs=0);
30
-  string getText();
31
+  string getText(bool multi);
32
 
33
   uint16_t d_pos;
34
Index: zoneparser-tng.cc
35
===================================================================
36
--- zoneparser-tng.cc (revision 989)
37
+++ zoneparser-tng.cc (revision 996)
38
@@ -281,6 +281,5 @@
39
     }
40
     catch(...) {
41
-      cerr<<"Oops, this doesn't look like a qtype, stopping loop\n";
42
-      break;
43
+      throw runtime_error("Parsing zone content line: '"+nextpart+"' doesn't look like a qtype, stopping loop");
44
     }
45
   }
46
Index: dnswriter.cc
47
===================================================================
48
--- dnswriter.cc (revision 962)
49
+++ dnswriter.cc (revision 996)
50
@@ -2,4 +2,5 @@
51
 #include "misc.hh"
52
 #include "dnsparser.hh"
53
+#include <boost/tokenizer.hpp>
54
 
55
 DNSPacketWriter::DNSPacketWriter(vector<uint8_t>& content, const string& qname, uint16_t  qtype, uint16_t qclass, uint8_t opcode)
56
@@ -116,9 +117,20 @@
57
 }
58
 
59
-void DNSPacketWriter::xfrText(const string& text)
60
-{
61
-  d_record.push_back(text.length());
62
-  const uint8_t* ptr=(uint8_t*)(text.c_str());
63
-  d_record.insert(d_record.end(), ptr, ptr+text.size());
64
+void DNSPacketWriter::xfrText(const string& text, bool)
65
+{
66
+  escaped_list_separator<char> sep('\\', ' ' , '"');
67
+  tokenizer<escaped_list_separator<char> > tok(text, sep);
68
+
69
+  tokenizer<escaped_list_separator<char> >::iterator beg=tok.begin();
70
+
71
+  if(beg==tok.end()) {
72
+    d_record.push_back(0);
73
+  }
74
+  else 
75
+    for(; beg!=tok.end(); ++beg){
76
+      d_record.push_back(beg->length());
77
+      const uint8_t* ptr=(uint8_t*)(beg->c_str());
78
+      d_record.insert(d_record.end(), ptr, ptr+beg->length());
79
+    }
80
 }
81
 
82
Index: dnsparser.cc
83
===================================================================
84
--- dnsparser.cc (revision 972)
85
+++ dnsparser.cc (revision 996)
86
@@ -359,14 +359,42 @@
87
 }
88
 
89
-string PacketReader::getText()
90
+static string txtEscape(const string &name)
91
+{
92
+  string ret;
93
+
94
+  for(string::const_iterator i=name.begin();i!=name.end();++i)
95
+    if(*i=='"' || *i=='\\'){
96
+      ret += '\\';
97
+      ret += *i;
98
+    }
99
+    else
100
+      ret += *i;
101
+  return ret;
102
+}
103
+
104
+// exceptions thrown here do not result in logging in the main pdns auth server - just so you know!
105
+string PacketReader::getText(bool multi)
106
 {
107
   string ret;
108
   ret.reserve(40);
109
-
110
-  unsigned char labellen=d_content.at(d_pos++);
111
-  ret.append(&d_content.at(d_pos), &d_content.at(d_pos+labellen-1)+1); // the end is one beyond the packet
112
-  d_pos+=labellen;
113
-  return ret;
114
-}
115
+  while(d_pos < d_startrecordpos + d_recordlen ) {
116
+    if(!ret.empty()) {
117
+      ret.append(1,' ');
118
+    }
119
+    unsigned char labellen=d_content.at(d_pos++);
120
+    
121
+    ret.append(1,'"');
122
+    string val(&d_content.at(d_pos), &d_content.at(d_pos+labellen-1)+1);
123
+    
124
+    ret.append(txtEscape(val)); // the end is one beyond the packet
125
+    ret.append(1,'"');
126
+    d_pos+=labellen;
127
+    if(!multi)
128
+      break;
129
+  }
130
+
131
+  return ret;
132
+}
133
+
134
 
135
 void PacketReader::getLabelFromContent(const vector<uint8_t>& content, uint16_t& frompos, string& ret, int recurs) 
136
Index: rcpgenerator.hh
137
===================================================================
138
--- rcpgenerator.hh (revision 802)
139
+++ rcpgenerator.hh (revision 996)
140
@@ -51,5 +51,5 @@
141
 
142
   void xfrLabel(string& val, bool compress=false);
143
-  void xfrText(string& val);
144
+  void xfrText(string& val, bool multi=false);
145
   void xfrHexBlob(string& val);
146
   void xfrBlob(string& val);
147
@@ -76,5 +76,5 @@
148
   void xfrType(const uint16_t& val);
149
   void xfrLabel(const string& val, bool compress=false);
150
-  void xfrText(const string& val);
151
+  void xfrText(const string& val, bool multi=false);
152
   void xfrBlob(const string& val);
153
   void xfrHexBlob(const string& val);
154
Index: dnsrecords.cc
155
===================================================================
156
--- dnsrecords.cc (revision 823)
157
+++ dnsrecords.cc (revision 996)
158
@@ -1,5 +1,5 @@
159
 /*
160
     PowerDNS Versatile Database Driven Nameserver
161
-    Copyright (C) 2005 - 2006  PowerDNS.COM BV
162
+    Copyright (C) 2005 - 2007  PowerDNS.COM BV
163
 
164
     This program is free software; you can redistribute it and/or modify
165
@@ -178,6 +178,6 @@
166
 boilerplate_conv(PTR, ns_t_ptr, conv.xfrLabel(d_content, true));
167
 boilerplate_conv(CNAME, ns_t_cname, conv.xfrLabel(d_content, true));
168
-boilerplate_conv(TXT, ns_t_txt, conv.xfrText(d_text));
169
-boilerplate_conv(SPF, 99, conv.xfrText(d_text));
170
+boilerplate_conv(TXT, ns_t_txt, conv.xfrText(d_text, true));
171
+boilerplate_conv(SPF, 99, conv.xfrText(d_text, true));
172
 boilerplate_conv(HINFO, ns_t_hinfo,  conv.xfrText(d_cpu);   conv.xfrText(d_host));
173
 
174
@@ -199,4 +199,9 @@
175
 		 conv.xfr16BitInt(d_preference);
176
 		 conv.xfrLabel(d_mxname, true);
177
+		 )
178
+
179
+boilerplate_conv(AFSDB, ns_t_afsdb, 
180
+		 conv.xfr16BitInt(d_subtype);
181
+		 conv.xfrLabel(d_hostname);
182
 		 )
183
 
184
@@ -235,4 +240,11 @@
185
 		 conv.xfr32BitInt(d_st.expire);
186
 		 conv.xfr32BitInt(d_st.minimum);
187
+		 );
188
+#undef KEY
189
+boilerplate_conv(KEY, ns_t_key, 
190
+		 conv.xfr16BitInt(d_flags); 
191
+		 conv.xfr8BitInt(d_protocol); 
192
+		 conv.xfr8BitInt(d_algorithm); 
193
+		 conv.xfrBlob(d_certificate);
194
 		 );
195
 
196
@@ -294,7 +306,9 @@
197
 void reportOtherTypes()
198
 {
199
+   AFSDBRecordContent::report();
200
    SPFRecordContent::report();
201
    NAPTRRecordContent::report();
202
    RPRecordContent::report();
203
+   KEYRecordContent::report();
204
    DNSKEYRecordContent::report();
205
    RRSIGRecordContent::report();
206
Index: dnsrecords.hh
207
===================================================================
208
--- dnsrecords.hh (revision 823)
209
+++ dnsrecords.hh (revision 978)
210
@@ -196,4 +196,26 @@
211
   string d_fingerprint;
212
 };
213
+
214
+class KEYRecordContent : public DNSRecordContent
215
+{
216
+public:
217
+  includeboilerplate(KEY)
218
+
219
+private:
220
+  uint16_t d_flags;
221
+  uint8_t d_protocol, d_algorithm;
222
+  string d_certificate;
223
+};
224
+
225
+class AFSDBRecordContent : public DNSRecordContent
226
+{
227
+public:
228
+  includeboilerplate(AFSDB)
229
+
230
+private:
231
+  uint16_t d_subtype;
232
+  string d_hostname;
233
+};
234
+
235
 
236
 class CERTRecordContent : public DNSRecordContent
237
Index: rcpgenerator.cc
238
===================================================================
239
--- rcpgenerator.cc (revision 850)
240
+++ rcpgenerator.cc (revision 996)
241
@@ -67,9 +67,38 @@
242
   if(!isdigit(d_string.at(d_pos)))
243
     throw RecordTextException("while parsing IP address, expected digits at position "+lexical_cast<string>(d_pos)+" in '"+d_string+"'");
244
-  
245
-  string ip;
246
-  xfrLabel(ip);
247
-  if(!IpToU32(ip, &val))
248
-    throw RecordTextException("unable to parse IP address '"+ip+"'");
249
+
250
+  uint32_t octet=0;
251
+  val=0;
252
+  char count=0;
253
+  
254
+  for(;;) {
255
+    if(d_string.at(d_pos)=='.') {
256
+      val<<=8;
257
+      val+=octet;
258
+      octet=0;
259
+      count++;
260
+      if(count > 3)
261
+	break;
262
+    }
263
+    else if(isdigit(d_string.at(d_pos))) {
264
+      octet*=10;
265
+      octet+=d_string.at(d_pos) - '0';
266
+      if(octet > 255)
267
+	throw RecordTextException("unable to parse IP address");
268
+    }
269
+    else if(dns_isspace(d_string.at(d_pos))) 
270
+      break;
271
+    else
272
+      throw RecordTextException("unable to parse IP address, strange character: "+d_string.at(d_pos));
273
+
274
+    d_pos++;
275
+    if(d_pos == d_string.length())
276
+      break;
277
+  }
278
+  if(count<=3) {
279
+    val<<=8;
280
+    val+=octet;
281
+  }
282
+  val=ntohl(val);
283
 }
284
 
285
@@ -178,23 +207,31 @@
286
 }
287
 
288
-
289
-void RecordTextReader::xfrText(string& val)
290
-{
291
-  skipSpaces();
292
-  if(d_string[d_pos]!='"')
293
-    throw RecordTextException("Data field in DNS should start with quote (\") at position "+lexical_cast<string>(d_pos)+" of '"+d_string+"'");
294
-
295
+void RecordTextReader::xfrText(string& val, bool multi)
296
+{
297
   val.clear();
298
   val.reserve(d_end - d_pos);
299
-  
300
-  while(++d_pos < d_end && d_string[d_pos]!='"') {
301
-    if(d_string[d_pos]=='\\' && d_pos+1!=d_end) {
302
-      ++d_pos;
303
+
304
+  while(d_pos != d_end) {
305
+    if(!val.empty())
306
+      val.append(1, ' ');
307
+
308
+    skipSpaces();
309
+    if(d_string[d_pos]!='"')
310
+      throw RecordTextException("Data field in DNS should start with quote (\") at position "+lexical_cast<string>(d_pos)+" of '"+d_string+"'");
311
+
312
+    val.append(1, '"');
313
+    while(++d_pos < d_end && d_string[d_pos]!='"') {
314
+      if(d_string[d_pos]=='\\' && d_pos+1!=d_end) {
315
+	val.append(1, d_string[d_pos++]);
316
+      }
317
+      val.append(1, d_string[d_pos]);
318
     }
319
-    val.append(1, d_string[d_pos]);
320
-  }
321
-  if(d_pos == d_end)
322
-    throw RecordTextException("Data field in DNS should end on a quote (\") in '"+d_string+"'");
323
-  d_pos++;
324
+    val.append(1,'"');
325
+    if(d_pos == d_end)
326
+      throw RecordTextException("Data field in DNS should end on a quote (\") in '"+d_string+"'");
327
+    d_pos++;
328
+    if(!multi)
329
+      break;
330
+  }
331
 }
332
 
333
@@ -251,11 +288,28 @@
334
 
335
   char tmp[17];
336
-  snprintf(tmp, sizeof(tmp)-1, "%u.%u.%u.%u", 
337
-	   (val >> 24)&0xff,
338
-	   (val >> 16)&0xff,
339
-	   (val >>  8)&0xff,
340
-	   (val      )&0xff);
341
-  
342
-  d_string+=tmp;
343
+  uint32_t ip=htonl(val);
344
+  uint8_t vals[4];
345
+
346
+  memcpy(&vals[0], &ip, sizeof(ip));
347
+
348
+  char *pos=tmp;
349
+
350
+  for(int n=0; n < 4; ++n) {
351
+    if(vals[n]<10) {
352
+      *(pos++)=vals[n]+'0';
353
+    } else if(vals[n] < 100) {
354
+      *(pos++)=(vals[n]/10) +'0';
355
+      *(pos++)=(vals[n]%10) +'0';
356
+    } else {
357
+      *(pos++)=(vals[n]/100) +'0';
358
+      vals[n]%=100;
359
+      *(pos++)=(vals[n]/10) +'0';
360
+      *(pos++)=(vals[n]%10) +'0';
361
+    }
362
+    if(n!=3)
363
+      *(pos++)='.';
364
+  }
365
+  *pos=0;
366
+  d_string.append(tmp, pos);
367
 }
368
 
369
@@ -338,23 +392,10 @@
370
 }
371
 
372
-void RecordTextWriter::xfrText(const string& val)
373
-{
374
-  if(!d_string.empty())
375
-    d_string.append(1,' ');
376
-  d_string.append(1,'"');
377
-
378
-  if(val.find_first_of("\\\"") == string::npos)
379
-    d_string+=val;
380
-  else {
381
-    string::size_type end=val.size();
382
-    
383
-    for(string::size_type pos=0; pos < end; ++pos) {
384
-      if(val[pos]=='\'' || val[pos]=='"')
385
-	d_string.append(1,'\\');
386
-      d_string.append(1, val[pos]);
387
-    }
388
-  }
389
-
390
-  d_string.append(1,'"');
391
+void RecordTextWriter::xfrText(const string& val, bool multi)
392
+{
393
+  if(!d_string.empty())
394
+    d_string.append(1,' ');
395
+
396
+  d_string.append(val);
397
 }
398

Return to bug 116029