From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: by sourceware.org (Postfix, from userid 1962) id 85C503857BB2; Thu, 11 Jan 2024 15:39:24 +0000 (GMT) DKIM-Filter: OpenDKIM Filter v2.11.0 sourceware.org 85C503857BB2 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=sourceware.org; s=default; t=1704987564; bh=3CS2F2KCRrrGC7JI+uVWuvnb6Jbl6O6XYMGkMk98aM4=; h=From:To:Subject:Date:From; b=DPLsbuyZgzcNEuxoGzm3XrjHTCMIX7PCy7A3uNI6ZLKfoHfNdeKyM8iNpuM24X5WH N96niJ3ftqfONgm8zHmdl2v7hMMCHZ4j0ftmHfo2lVUVH4sybOqP5jN/xIPHNUxBIX qJjiQ0SLDleLvsvWC/48O6rtUNJM83gR5P4YaHDA= Content-Type: text/plain; charset="us-ascii" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit From: Stefan Liebler To: glibc-cvs@sourceware.org Subject: [glibc] resolv: Fix endless loop in __res_context_query X-Act-Checkin: glibc X-Git-Author: Stefan Liebler X-Git-Refname: refs/heads/master X-Git-Oldrev: c0c259c3bde3b76722d717b4372233b488c8d3ff X-Git-Newrev: 0aabf15a3515a996bd415ff37e29326286c8007e Message-Id: <20240111153924.85C503857BB2@sourceware.org> Date: Thu, 11 Jan 2024 15:39:24 +0000 (GMT) List-Id: https://sourceware.org/git/gitweb.cgi?p=glibc.git;h=0aabf15a3515a996bd415ff37e29326286c8007e commit 0aabf15a3515a996bd415ff37e29326286c8007e Author: Stefan Liebler Date: Thu Jan 11 14:01:18 2024 +0100 resolv: Fix endless loop in __res_context_query Starting with commit 40c0add7d48739f5d89ebba255c1df26629a76e2 "resolve: Remove __res_context_query alloca usage" there is an endless loop in __res_context_query if __res_context_mkquery fails e.g. if type is invalid. Then the scratch buffer is resized to MAXPACKET size and it is retried again. Before the mentioned commit, it was retried only once and with the mentioned commit, there is no check and it retries in an endless loop. This is observable with xtest resolv/tst-resolv-qtypes which times out after 300s. This patch retries mkquery only once as before the mentioned commit. Furthermore, scratch_buffer_set_array_size is now only called with nelem=2 if type is T_QUERY_A_AND_AAAA (also see mentioned commit). The test tst-resolv-qtypes is also adjusted to verify that is really returning with -1 in case of an invalid type. Reviewed-by: Adhemerval Zanella Diff: --- resolv/res_query.c | 8 ++++++-- resolv/tst-resolv-qtypes.c | 4 ++-- 2 files changed, 8 insertions(+), 4 deletions(-) diff --git a/resolv/res_query.c b/resolv/res_query.c index 1b148a2a05..bd55453552 100644 --- a/resolv/res_query.c +++ b/resolv/res_query.c @@ -81,6 +81,7 @@ #include #include #include +#include #if PACKETSZ > 65536 #define MAXPACKET PACKETSZ @@ -116,6 +117,7 @@ __res_context_query (struct resolv_context *ctx, const char *name, UHEADER *hp = (UHEADER *) answer; UHEADER *hp2; int n; + bool retried = false; /* It requires 2 times QUERYSIZE for type == T_QUERY_A_AND_AAAA. */ struct scratch_buffer buf; @@ -182,13 +184,15 @@ __res_context_query (struct resolv_context *ctx, const char *name, nquery1 = n; } - if (__glibc_unlikely (n <= 0)) { + if (__glibc_unlikely (n <= 0) && !retried) { /* Retry just in case res_nmkquery failed because of too short buffer. Shouldn't happen. */ if (scratch_buffer_set_array_size (&buf, - T_QUERY_A_AND_AAAA ? 2 : 1, + (type == T_QUERY_A_AND_AAAA) + ? 2 : 1, MAXPACKET)) { query1 = buf.data; + retried = true; goto again; } } diff --git a/resolv/tst-resolv-qtypes.c b/resolv/tst-resolv-qtypes.c index 3fa566c7ea..973c4e15d3 100644 --- a/resolv/tst-resolv-qtypes.c +++ b/resolv/tst-resolv-qtypes.c @@ -154,8 +154,8 @@ test_function (const char *fname, } } - TEST_VERIFY (func (-1, buf, sizeof (buf) == -1)); - TEST_VERIFY (func (65536, buf, sizeof (buf) == -1)); + TEST_VERIFY (func (-1, buf, sizeof (buf)) == -1); + TEST_VERIFY (func (65536, buf, sizeof (buf)) == -1); } static int