diff --git a/CHANGES b/CHANGES index 09ff3a5bc1..f53b39ccdd 100644 --- a/CHANGES +++ b/CHANGES @@ -1,3 +1,6 @@ +6384. [bug] Remove infinite loop when including a directory in a + zone file. [GL #4357] + 6383. [bug] Address an infinite loop in $GENERATE when a negative value was converted in nibble mode. [GL #4353] diff --git a/bin/tests/system/checkzone/zones/bad-include-directory.db b/bin/tests/system/checkzone/zones/bad-include-directory.db new file mode 100644 index 0000000000..3ccf700960 --- /dev/null +++ b/bin/tests/system/checkzone/zones/bad-include-directory.db @@ -0,0 +1,13 @@ +; Copyright (C) Internet Systems Consortium, Inc. ("ISC") +; +; SPDX-License-Identifier: MPL-2.0 +; +; This Source Code Form is subject to the terms of the Mozilla Public +; License, v. 2.0. If a copy of the MPL was not distributed with this +; file, you can obtain one at https://mozilla.org/MPL/2.0/. +; +; See the COPYRIGHT file distributed with this work for additional +; information regarding copyright ownership. + +$INCLUDE . +$INCLUDE .. diff --git a/lib/dns/master.c b/lib/dns/master.c index eab1d00364..e56fa4f12f 100644 --- a/lib/dns/master.c +++ b/lib/dns/master.c @@ -214,33 +214,52 @@ task_send(dns_loadctx_t *lctx); static void loadctx_destroy(dns_loadctx_t *lctx); -#define GETTOKENERR(lexer, options, token, eol, err) \ - do { \ - result = gettoken(lexer, options, token, eol, callbacks); \ - switch (result) { \ - case ISC_R_SUCCESS: \ - break; \ - case ISC_R_UNEXPECTED: \ - goto insist_and_cleanup; \ - default: \ - if (MANYERRS(lctx, result)) { \ - SETRESULT(lctx, result); \ - LOGIT(result); \ - read_till_eol = true; \ - err goto next_line; \ - } else \ - goto log_and_cleanup; \ - } \ - if ((token)->type == isc_tokentype_special) { \ - result = DNS_R_SYNTAX; \ - if (MANYERRS(lctx, result)) { \ - SETRESULT(lctx, result); \ - LOGIT(result); \ - read_till_eol = true; \ - goto next_line; \ - } else \ - goto log_and_cleanup; \ - } \ +#define LCTX_MANYERRORS(lctx) (((lctx)->options & DNS_MASTER_MANYERRORS) != 0) + +#define GETTOKENERR(lexer, options, token, eol, err) \ + do { \ + result = gettoken(lexer, options, token, eol, callbacks); \ + switch (result) { \ + case ISC_R_SUCCESS: \ + break; \ + case ISC_R_NOTFILE: \ + /* Treat "bad" $INCLUDE as eof. */ \ + if (ictx->parent != NULL && LCTX_MANYERRORS(lctx)) { \ + SETRESULT(lctx, result); \ + COMMITALL; \ + lctx->inc = ictx->parent; \ + ictx->parent = NULL; \ + incctx_destroy(lctx->mctx, ictx); \ + RUNTIME_CHECK(isc_lex_close(lctx->lex) == \ + ISC_R_SUCCESS); \ + line = isc_lex_getsourceline(lctx->lex); \ + POST(line); \ + source = isc_lex_getsourcename(lctx->lex); \ + ictx = lctx->inc; \ + continue; \ + } \ + goto insist_and_cleanup; \ + case ISC_R_UNEXPECTED: \ + goto insist_and_cleanup; \ + default: \ + if (MANYERRS(lctx, result)) { \ + SETRESULT(lctx, result); \ + LOGIT(result); \ + read_till_eol = true; \ + err goto next_line; \ + } else \ + goto log_and_cleanup; \ + } \ + if ((token)->type == isc_tokentype_special) { \ + result = DNS_R_SYNTAX; \ + if (MANYERRS(lctx, result)) { \ + SETRESULT(lctx, result); \ + LOGIT(result); \ + read_till_eol = true; \ + goto next_line; \ + } else \ + goto log_and_cleanup; \ + } \ } while (0) #define GETTOKEN(lexer, options, token, eol) \ GETTOKENERR(lexer, options, token, eol, {}) @@ -293,7 +312,7 @@ loadctx_destroy(dns_loadctx_t *lctx); #define MANYERRS(lctx, result) \ ((result != ISC_R_SUCCESS) && (result != ISC_R_IOERROR) && \ - ((lctx)->options & DNS_MASTER_MANYERRORS) != 0) + LCTX_MANYERRORS(lctx)) #define SETRESULT(lctx, r) \ do { \