2
0
mirror of https://gitlab.isc.org/isc-projects/bind9 synced 2025-09-03 08:05:21 +00:00

Reset the TCP connection when garbage is received

When invalid DNS message is received, there was a handling mechanism for
DoH that would be called to return proper HTTP response.

Reuse this mechanism and reset the TCP connection when the client is
blackholed, DNS message is completely bogus or the ns_client receives
response instead of query.
This commit is contained in:
Ondřej Surý
2022-02-15 14:41:15 +01:00
parent 0697288b9d
commit 4716c56ebb
3 changed files with 49 additions and 18 deletions

View File

@@ -1247,6 +1247,12 @@ isc__nmsocket_shutdown(isc_nmsocket_t *sock);
* callbacks.
*/
void
isc__nmsocket_reset(isc_nmsocket_t *sock);
/*%<
* Reset and close the socket.
*/
bool
isc__nmsocket_active(isc_nmsocket_t *sock);
/*%<

View File

@@ -1835,9 +1835,6 @@ isc__nmhandle_detach(isc_nmhandle_t **handlep FLARG) {
}
}
void
isc__nmsocket_shutdown(isc_nmsocket_t *sock);
static void
nmhandle_detach_cb(isc_nmhandle_t **handlep FLARG) {
isc_nmsocket_t *sock = NULL;
@@ -2085,11 +2082,7 @@ isc__nmsocket_writetimeout_cb(uv_timer_t *timer) {
int r = uv_timer_stop(&sock->write_timer);
UV_RUNTIME_CHECK(uv_timer_stop, r);
/* The shutdown will be handled in the respective close functions */
r = uv_tcp_close_reset(&sock->uv_handle.tcp, NULL);
UV_RUNTIME_CHECK(uv_tcp_close_reset, r);
isc__nmsocket_shutdown(sock);
isc__nmsocket_reset(sock);
}
void
@@ -2902,6 +2895,32 @@ isc__nm_async_detach(isc__networker_t *worker, isc__netievent_t *ev0) {
nmhandle_detach_cb(&ievent->handle FLARG_PASS);
}
void
isc__nmsocket_reset(isc_nmsocket_t *sock) {
REQUIRE(VALID_NMSOCK(sock));
switch (sock->type) {
case isc_nm_tcpdnssocket:
case isc_nm_tlsdnssocket:
REQUIRE(sock->parent == NULL);
break;
default:
INSIST(0);
ISC_UNREACHABLE();
break;
}
if (!uv_is_closing(&sock->uv_handle.handle)) {
/*
* The real shutdown will be handled in the respective
* close functions.
*/
int r = uv_tcp_close_reset(&sock->uv_handle.tcp, NULL);
UV_RUNTIME_CHECK(uv_tcp_close_reset, r);
}
isc__nmsocket_shutdown(sock);
}
void
isc__nmsocket_shutdown(isc_nmsocket_t *sock) {
REQUIRE(VALID_NMSOCK(sock));
@@ -3467,25 +3486,26 @@ isc_nm_sequential(isc_nmhandle_t *handle) {
void
isc_nm_bad_request(isc_nmhandle_t *handle) {
isc_nmsocket_t *sock;
isc_nmsocket_t *sock = NULL;
REQUIRE(VALID_NMHANDLE(handle));
REQUIRE(VALID_NMSOCK(handle->sock));
sock = handle->sock;
switch (sock->type) {
case isc_nm_udpsocket:
return;
case isc_nm_tcpdnssocket:
case isc_nm_tlsdnssocket:
REQUIRE(sock->parent == NULL);
isc__nmsocket_reset(sock);
return;
#if HAVE_LIBNGHTTP2
case isc_nm_httpsocket:
isc__nm_http_bad_request(handle);
break;
#endif /* HAVE_LIBNGHTTP2 */
case isc_nm_udpsocket:
case isc_nm_tcpdnssocket:
case isc_nm_tlsdnssocket:
return;
break;
#endif /* HAVE_LIBNGHTTP2 */
case isc_nm_tcpsocket:
#if HAVE_LIBNGHTTP2
case isc_nm_tlssocket:

View File

@@ -1822,6 +1822,9 @@ ns__client_request(isc_nmhandle_t *handle, isc_result_t eresult,
* There isn't enough header to determine whether
* this was a request or a response. Drop it.
*/
ns_client_log(client, DNS_LOGCATEGORY_SECURITY,
NS_LOGMODULE_CLIENT, ISC_LOG_DEBUG(10),
"dropped request: invalid message header");
isc_nm_bad_request(handle);
return;
}
@@ -1838,7 +1841,9 @@ ns__client_request(isc_nmhandle_t *handle, isc_result_t eresult,
* If it's a TCP response, discard it here.
*/
if ((flags & DNS_MESSAGEFLAG_QR) != 0) {
CTRACE("unexpected response");
ns_client_log(client, DNS_LOGCATEGORY_SECURITY,
NS_LOGMODULE_CLIENT, ISC_LOG_DEBUG(10),
"dropped request: unexpected response");
isc_nm_bad_request(handle);
return;
}