diff --git pdns/rfc2136handler.cc pdns/rfc2136handler.cc index 3e6577e35..e7f204a3f 100644 --- pdns/rfc2136handler.cc +++ pdns/rfc2136handler.cc @@ -538,10 +538,25 @@ uint PacketHandler::performUpdate(const string &msgPrefix, const DNSRecord *rr, } return changedRecords; } +static void socketCleaner(int* sock) +{ + if (*sock < 0) { + return; // nothing to do + } + + try { + closesocket(*sock); + *sock = -1; + } + catch (const PDNSException& e) { + g_log << Logger::Error << "Error closing primary forwarding socket: " << e.reason << endl; + } +} + int PacketHandler::forwardPacket(const string &msgPrefix, const DNSPacket& p, const DomainInfo& di) { vector forward; B.getDomainMetadata(p.qdomain, "FORWARD-DNSUPDATE", forward); if (forward.size() == 0 && ! ::arg().mustDo("forward-dnsupdate")) { @@ -560,93 +575,61 @@ int PacketHandler::forwardPacket(const string &msgPrefix, const DNSPacket& p, co if(sock < 0) { g_log< guard(&sock, socketCleaner); - DNSPacket l_forwardPacket(p); - l_forwardPacket.setID(dns_random_uint16()); - l_forwardPacket.setRemote(&remote); - uint16_t len=htons(l_forwardPacket.getString().length()); - string buffer((const char*)&len, 2); - buffer.append(l_forwardPacket.getString()); - if(write(sock, buffer.c_str(), buffer.length()) < 0) { - g_log<(recvRes) < sizeof(lenBuf)) { - g_log << Logger::Error << msgPrefix << "Could not receive data (length) from primary at " << remote.toStringWithPort() << ", error:" << stringerror() << endl; - try { - closesocket(sock); - } - catch(const PDNSException& e) { - g_log << Logger::Error << "Error closing primary forwarding socket after recv() failed: " << e.reason << endl; + std::array lenBuf{}; + recvRes = recv(sock, lenBuf.data(), lenBuf.size(), 0); + if (recvRes < 0 || static_cast(recvRes) < lenBuf.size()) { + g_log << Logger::Error << msgPrefix << "Could not receive data (length) from primary at " << remote.toStringWithPort() << ", error:" << stringerror() << endl; + continue; } - continue; - } - size_t packetLen = lenBuf[0]*256+lenBuf[1]; - - buffer.resize(packetLen); - recvRes = recv(sock, &buffer.at(0), packetLen, 0); - if (recvRes < 0) { - g_log << Logger::Error << msgPrefix << "Could not receive data (dnspacket) from primary at " << remote.toStringWithPort() << ", error:" << stringerror() << endl; - try { - closesocket(sock); + size_t packetLen = lenBuf[0]*256+lenBuf[1]; + + if (packetLen == 0) { + g_log << Logger::Warning << msgPrefix << "Empty update sent by primary at " << remote.toStringWithPort() << endl; + continue; } - catch(const PDNSException& e) { - g_log << Logger::Error << "Error closing primary forwarding socket after recv() failed: " << e.reason << endl; + + buffer.resize(packetLen); + recvRes = recv(sock, &buffer.at(0), packetLen, 0); + if (recvRes < 0) { + g_log << Logger::Error << msgPrefix << "Could not receive data (dnspacket) from primary at " << remote.toStringWithPort() << ", error:" << stringerror() << endl; + continue; } - continue; - } - try { - closesocket(sock); - } - catch(const PDNSException& e) { - g_log << Logger::Error << "Error closing primary forwarding socket: " << e.reason << endl; - } + } // socketCleaner scope try { MOADNSParser mdp(false, buffer.data(), static_cast(recvRes)); g_log<