Changeset 514 for trunk/pdns/pdns/pdns_recursor.cc
- Timestamp:
- 10/10/05 21:42:06 (8 years ago)
- Files:
-
- 1 modified
-
trunk/pdns/pdns/pdns_recursor.cc (modified) (13 diffs)
Legend:
- Unmodified
- Added
- Removed
-
trunk/pdns/pdns/pdns_recursor.cc
r508 r514 41 41 #include <boost/tuple/tuple_comparison.hpp> 42 42 #include <boost/shared_array.hpp> 43 43 #include <boost/lexical_cast.hpp> 44 #include "dnsparser.hh" 45 #include "dnswriter.hh" 46 #include "dnsrecords.hh" 44 47 using namespace boost; 45 48 … … 54 57 55 58 string s_programname="pdns_recursor"; 59 60 struct DNSComboWriter { 61 DNSComboWriter(const char* data, uint16_t len) : d_mdp(data, len), d_tcp(false), d_socket(-1) 62 {} 63 MOADNSParser d_mdp; 64 void setRemote(struct sockaddr* sa, socklen_t len) 65 { 66 memcpy((void *)d_remote, (void *)sa, len); 67 d_socklen=len; 68 } 69 70 void setSocket(int sock) 71 { 72 d_socket=sock; 73 } 74 char d_remote[sizeof(sockaddr_in6)]; 75 socklen_t d_socklen; 76 bool d_tcp; 77 int d_socket; 78 }; 79 56 80 57 81 #if 0 … … 206 230 arr.qname=nsrr.content=templ; 207 231 arr.content=ips[c-'a']; 208 set<DNSResourceRecord> aset;232 set<DNSResourceRecord> aset; 209 233 aset.insert(arr); 210 RC.replace(string(templ), QType(QType::A),aset);234 RC.replace(string(templ), QType(QType::A), aset); 211 235 212 236 nsset.insert(nsrr); … … 219 243 try { 220 244 bool quiet=arg().mustDo("quiet"); 221 DNSPacket P=*(DNSPacket *)p; 222 223 delete (DNSPacket *)p; 224 225 vector<DNSResourceRecord>ret; 226 DNSPacket *R=P.replyPacket(); 227 R->setA(false); 228 R->setRA(true); 245 DNSComboWriter* dc=(DNSComboWriter *)p; 246 247 vector<DNSResourceRecord> ret; 248 249 vector<uint8_t> packet; 250 DNSPacketWriter pw(packet, dc->d_mdp.d_qname, dc->d_mdp.d_qtype, dc->d_mdp.d_qclass); 251 252 pw.getHeader()->aa=0; 253 pw.getHeader()->ra=1; 254 pw.getHeader()->id=dc->d_mdp.d_header.id; 255 229 256 // MT->setTitle("udp question for "+P.qdomain+"|"+P.qtype.getName()); 230 257 SyncRes sr; 231 258 if(!quiet) 232 L<<Logger::Error<<"["<<MT->getTid()<<"] " << ( R->d_tcp ? "TCP " : "") << "question for '"<<P.qdomain<<"|"<<P.qtype.getName()<<"' from "<<P.getRemote()<<endl;259 L<<Logger::Error<<"["<<MT->getTid()<<"] " << (dc->d_tcp ? "TCP " : "") << "question for '"<<dc->d_mdp.d_qname<<"|"<<dc->d_mdp.d_qtype<<"' from "<<"1.2.3.4"<<endl; 233 260 234 261 sr.setId(MT->getTid()); 235 if(! P.d.rd)262 if(!dc->d_mdp.d_header.rd) 236 263 sr.setCacheOnly(); 237 264 238 int res=sr.beginResolve( P.qdomain, P.qtype, ret);265 int res=sr.beginResolve(dc->d_mdp.d_qname, QType(dc->d_mdp.d_qtype), ret); 239 266 if(res<0) 240 R->setRcode(RCode::ServFail);267 pw.getHeader()->rcode=RCode::ServFail; 241 268 else { 242 R->setRcode(res); 243 for(vector<DNSResourceRecord>::const_iterator i=ret.begin();i!=ret.end();++i) 244 R->addRecord(*i); 269 pw.getHeader()->rcode=res; 270 for(vector<DNSResourceRecord>::const_iterator i=ret.begin();i!=ret.end();++i) { 271 pw.startRecord(i->qname, i->qtype.getCode()); 272 shared_ptr<DNSRecordContent> drc(DNSRecordContent::mastermake(i->qtype.getCode(), 1, i->content)); 273 drc->toPacket(pw); 274 } 275 pw.commit(); 245 276 } 246 277 247 const char *buffer=R->getData(); 248 249 if(!R->d_tcp) { 278 if(!dc->d_tcp) { 279 /* 250 280 if(R->len > 512) { 251 281 R->truncate(512); 252 282 } 253 254 sendto(R->getSocket(),buffer,R->len,0,(struct sockaddr *)(R->remote),R->d_socklen); 283 */ 284 285 sendto(dc->d_socket, &*packet.begin(), packet.size(), 0, (struct sockaddr *)(dc->d_remote), dc->d_socklen); 255 286 } 256 287 else { 257 288 char buf[2]; 258 buf[0]= R->len/256;259 buf[1]= R->len%256;289 buf[0]=packet.size()/256; 290 buf[1]=packet.size()%256; 260 291 261 292 struct iovec iov[2]; 262 293 263 iov[0].iov_base=(void*)buf; iov[0].iov_len=2;264 iov[1].iov_base=(void*) buffer; iov[1].iov_len = R->len;265 266 int ret=writev( R->getSocket(), iov, 2);294 iov[0].iov_base=(void*)buf; iov[0].iov_len=2; 295 iov[1].iov_base=(void*)&*packet.begin(); iov[1].iov_len = packet.size(); 296 297 int ret=writev(dc->d_socket, iov, 2); 267 298 268 299 if(ret <= 0 ) 269 L<<Logger::Error<<"Error writing TCP answer to "<< P.getRemote()<<": "<< (ret ? strerror(errno) : "EOF") <<endl;270 else if( ret != 2 + R->len)271 L<<Logger::Error<<"Oops, partial answer sent to "<< P.getRemote()<<" - probably would have trouble receiving our answer anyhow (size="<<R->len<<")"<<endl;300 L<<Logger::Error<<"Error writing TCP answer to "<<"1.2.3.4"<<": "<< (ret ? strerror(errno) : "EOF") <<endl; 301 else if((unsigned int)ret != 2 + packet.size()) 302 L<<Logger::Error<<"Oops, partial answer sent to "<<"1.2.3.4"<<" - probably would have trouble receiving our answer anyhow (size="<<packet.size()<<")"<<endl; 272 303 273 304 // if(write(R->getSocket(),buf,2)!=2 || write(R->getSocket(),buffer,R->len)!=R->len) … … 277 308 // MT->setTitle("DONE! udp question for "+P.qdomain+"|"+P.qtype.getName()); 278 309 if(!quiet) { 279 L<<Logger::Error<<"["<<MT->getTid()<<"] answer to "<<( P.d.rd?"":"non-rd ")<<"question '"<<P.qdomain<<"|"<<P.qtype.getName();280 L<<"': "<<ntohs( R->d.ancount)<<" answers, "<<ntohs(R->d.arcount)<<" additional, took "<<sr.d_outqueries<<" packets, "<<310 L<<Logger::Error<<"["<<MT->getTid()<<"] answer to "<<(dc->d_mdp.d_header.rd?"":"non-rd ")<<"question '"<<dc->d_mdp.d_qname<<"|"<<dc->d_mdp.d_qtype; 311 L<<"': "<<ntohs(pw.getHeader()->ancount)<<" answers, "<<ntohs(pw.getHeader()->arcount)<<" additional, took "<<sr.d_outqueries<<" packets, "<< 281 312 sr.d_throttledqueries<<" throttled, "<<sr.d_timeouts<<" timeouts, "<<sr.d_tcpoutqueries<<" tcp connections, rcode="<<res<<endl; 282 313 } 283 314 284 315 sr.d_outqueries ? RC.cacheMisses++ : RC.cacheHits++; 285 286 delete R; 316 delete dc; 287 317 } 288 318 catch(AhuException &ae) { … … 410 440 close(1); 411 441 close(2); 412 413 442 } 414 443 #endif … … 426 455 SyncRes::setLog(true); 427 456 } 428 429 430 457 431 458 void doStats(void) … … 459 486 if(now -last_rootupdate>7200) { 460 487 SyncRes sr; 461 vector<DNSResourceRecord> ret;488 vector<DNSResourceRecord> ret; 462 489 463 490 sr.setNoCache(); … … 515 542 int main(int argc, char **argv) 516 543 { 544 ARecordContent::report(); 545 // AAAARecordContent::report(); // will be needed once we do ipv6 transport 546 NSRecordContent::report(); 547 CNAMERecordContent::report(); 548 MXRecordContent::report(); 549 SOARecordContent::report(); 550 517 551 int ret = EXIT_SUCCESS; 518 552 #ifdef WIN32 … … 636 670 Utility::socklen_t addrlen=sizeof(fromaddr); 637 671 int d_len; 638 DNSPacket P;639 672 640 673 struct timeval tv; … … 699 732 if(d_len<0) 700 733 continue; 701 702 P.setRemote((struct sockaddr *)&fromaddr, addrlen); 703 if(P.parse(data,d_len)<0) { 704 L<<Logger::Error<<"Unparseable packet from remote server "<<P.getRemote()<<endl; 705 } 706 else { 707 if(P.d.qr) { 734 735 try { 736 DNSComboWriter dc(data, d_len); 737 dc.setRemote((struct sockaddr *)&fromaddr, addrlen); 738 739 if(dc.d_mdp.d_header.qr) { 708 740 pident.remote=fromaddr; 709 pident.id= P.d.id;741 pident.id=dc.d_mdp.d_header.id; 710 742 string packet; 711 packet.assign(data, d_len);712 MT->sendEvent(pident, &packet);743 packet.assign(data, d_len); 744 MT->sendEvent(pident, &packet); 713 745 } 714 746 else 715 L<<Logger::Warning<<"Ignoring question on outgoing socket from "<<P.getRemote()<<endl; 716 } 747 L<<Logger::Warning<<"Ignoring question on outgoing socket from "<<"1.2.3.4"<<endl; 748 } 749 catch(MOADNSException& mde) { 750 L<<Logger::Error<<"Unparseable packet from remote server "<<"1.2.3.4"<<": "<<mde.what()<<endl; 751 } 752 717 753 } 718 754 … … 722 758 if(d_len<0) 723 759 continue; 724 P.setRemote((struct sockaddr *)&fromaddr, addrlen); 725 if(P.parse(data,d_len)<0) { 726 L<<Logger::Error<<"Unparseable packet from remote client "<<P.getRemote()<<endl; 727 } 728 else { 729 if(P.d.qr) 730 L<<Logger::Error<<"Ignoring answer on server socket!"<<endl; 731 else { 732 ++qcounter; 733 P.setSocket(*i); 734 P.d_tcp=false; 735 MT->makeThread(startDoResolve,(void*)new DNSPacket(P), "udp"); 736 } 760 761 DNSComboWriter*dc = new DNSComboWriter(data, d_len); 762 763 dc->setRemote((struct sockaddr *)&fromaddr, addrlen); 764 765 if(dc->d_mdp.d_header.qr) 766 L<<Logger::Error<<"Ignoring answer on server socket!"<<endl; 767 else { 768 ++qcounter; 769 dc->setSocket(*i); 770 dc->d_tcp=false; 771 MT->makeThread(startDoResolve, (void*) dc, "udp"); 737 772 } 738 773 } … … 859 894 if(i->bytesread==i->qlen) { 860 895 i->state=TCPConnection::BYTE0; 861 862 if(P.parse(i->data,i->qlen)<0) { 863 L<<Logger::Error<<"Unparseable packet from remote client "<<P.getRemote()<<endl; 896 DNSComboWriter* dc; 897 try { 898 dc=new DNSComboWriter(i->data, i->qlen); 899 } 900 catch(MOADNSException &mde) { 901 L<<Logger::Error<<"Unparseable packet from remote client "<<"1.2.3.4"<<endl; 864 902 close(i->fd); 865 903 tcpconnections.erase(i); 866 904 break; 867 905 } 868 else { 869 P.setSocket(i->fd); 870 P.d_tcp=true; 871 P.setRemote((struct sockaddr *)&i->remote,sizeof(i->remote)); 872 if(P.d.qr) 873 L<<Logger::Error<<"Ignoring answer on server socket!"<<endl; 874 else { 875 ++qcounter; 876 MT->makeThread(startDoResolve,(void*)new DNSPacket(P), "tcp"); 877 } 906 907 dc->setSocket(i->fd); 908 dc->d_tcp=true; 909 dc->setRemote((struct sockaddr *)&i->remote,sizeof(i->remote)); 910 if(dc->d_mdp.d_header.qr) 911 L<<Logger::Error<<"Ignoring answer on server socket!"<<endl; 912 else { 913 ++qcounter; 914 MT->makeThread(startDoResolve, dc, "tcp"); 878 915 } 879 916 }