From patchwork Sat Sep 26 01:34:21 2026 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: DJ Delorie X-Patchwork-Id: 144692 Return-Path: X-Original-To: patchwork@sourceware.org Delivered-To: patchwork@sourceware.org Received: from vm01.sourceware.org (localhost [IPv6:::1]) by sourceware.org (Postfix) with ESMTP id E4B3B4B920C8 for ; Sat, 26 Sep 2026 01:35:47 +0000 (GMT) DKIM-Filter: OpenDKIM Filter v2.11.0 sourceware.org E4B3B4B920C8 Authentication-Results: sourceware.org; dkim=pass (1024-bit key, unprotected) header.d=redhat.com header.i=@redhat.com header.a=rsa-sha256 header.s=mimecast20190719 header.b=INbR22yS X-Original-To: libc-alpha@sourceware.org Delivered-To: libc-alpha@sourceware.org Received: from us-smtp-delivery-124.mimecast.com (us-smtp-delivery-124.mimecast.com [170.10.133.124]) by sourceware.org (Postfix) with ESMTP id 7C4C14BB58ED for ; Sat, 26 Sep 2026 01:35:13 +0000 (GMT) DMARC-Filter: OpenDMARC Filter v1.4.2 sourceware.org 7C4C14BB58ED Authentication-Results: sourceware.org; dmarc=pass (p=quarantine dis=none) header.from=redhat.com Authentication-Results: sourceware.org; spf=pass smtp.mailfrom=redhat.com ARC-Filter: OpenARC Filter v1.0.0 sourceware.org 7C4C14BB58ED Authentication-Results: sourceware.org; arc=none smtp.remote-ip=170.10.133.124 ARC-Seal: i=1; a=rsa-sha256; d=sourceware.org; s=key; t=1790386514; cv=none; b=KxVM7vCc0GO+5LZP5PKck+mRED9YihOoOuYHgnhu04r1FsgDSxxPbhNbkyoYOE4kEWcxDajctZvxtJ1zTPimdb4tpz47aoEAQf/OxDRSZPtrjXYtkAumu/7qm2cpv1QsP8lIhwri0lXOYHg+nKOUEYa5RuRLWxFat0tNgWSjuSk= ARC-Message-Signature: i=1; a=rsa-sha256; d=sourceware.org; s=key; t=1790386514; c=relaxed/simple; bh=1P+E9gIQgcr6kev/ra5C5gzXRL6ng4WR33jts0xKt2w=; h=DKIM-Signature:MIME-Version:From:Date:Message-ID:Subject:To; b=BOPXezU47BoV7BTUgT+albRkJD8BCthqM2HZ3hDLtJgjXWIHPyPGlCef2PQBLdhITziFfbRsRHhOkiOtmRHxP4R9ttj12GbjP4tcwI3HEplcG9OK9ZX+JGJHYfiaFeLSFE9FYXvQJ/z4ee8T4/XSV5sFn3AmeJPRmKtS/+cRMz8= ARC-Authentication-Results: i=1; sourceware.org; dkim=pass (1024-bit key, unprotected) header.d=redhat.com header.i=@redhat.com header.a=rsa-sha256 header.s=mimecast20190719 header.b=INbR22yS DKIM-Filter: OpenDKIM Filter v2.11.0 sourceware.org 7C4C14BB58ED DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=redhat.com; s=mimecast20190719; t=1790386513; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:mime-version:mime-version:content-type:content-type; bh=mzJTmBpBihgNGvBPUHTlMfM04pTIkkq+uLK5uwKbXoY=; b=INbR22ySseF7IbhLtEi3RiB5AJ8rqdGObbj0JwTuudff3xct/bbGgBD9uDaYkyVuRN5sYv 1iwDJVLldcikFvbTRgLhcHNecd0C9JZDiCVjoUlJv6b8ie0soF4NknUQ8fh8p/lh3sg7ay gyrMiZR+V20YLH+adUcYYmUrLEJDYvE= Received: from mail-yx1-f69.google.com (mail-yx1-f69.google.com [74.125.224.69]) by relay.mimecast.com with ESMTP with STARTTLS (version=TLSv1.3, cipher=TLS_AES_256_GCM_SHA384) id us-mta-280-O2DlLDL_P6um41gM2qIX_g-1; Fri, 25 Sep 2026 21:35:11 -0400 X-MC-Unique: O2DlLDL_P6um41gM2qIX_g-1 X-Mimecast-MFC-AGG-ID: O2DlLDL_P6um41gM2qIX_g_1790386510 Received: by mail-yx1-f69.google.com with SMTP id 956f58d0204a3-6752fcf311cso47647d50.3 for ; Fri, 25 Sep 2026 18:35:11 -0700 (PDT) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20260707; t=1790386510; x=1790991310; h=content-type:to:subject:message-id:date:from:mime-version:x-gm-gg :x-gm-message-state:from:to:cc:subject:date:message-id:reply-to :content-type; bh=mzJTmBpBihgNGvBPUHTlMfM04pTIkkq+uLK5uwKbXoY=; b=HldGWQPEHGxRkrXJCf/vib/zamTNPy5ecXcWBGAykQVOO0uN05ACWoP1R5gFe/xkVN TClu9V2rIH/9zRNKW1t9lD+Xy9x7M1YhUQxBfgm1b2uBOiorE7nJLgbupmLZgYvuf883 kwo2cgBaKNsbdiWyNznvsxXZCKo8rgZyxQMGC98S7UzU6D5J52laKQfXofL/+NAdCU8i EnjvBtP+O7UetnGb902RWSovjyw4xTWSVLB6dDwTkX6SGqVupBkZLTc5FYQG21lBhaLK Z0+hmtk+TFj2PQiPS5hfzNffIsbVWHJWigMI0Lh9GTGfmgUpMpkwc8chjde2WK74hSza weyA== X-Gm-Message-State: AFq9FYKoXwPqMKev1bkmTZzJ0N/K/w4dcxMdDwR8nvg1yWKoQpQNlX1g 1XNfyetL+pSIuhH/zwvduNs5jCedvvTiL/MjX5aOWWGeFGDZlzaRfmyYZti4C9aUoAtA61BlK+z adiYJ7DmgELuFdoL1bvAMnUCW2mUKYtOANmU0WAtmxB1kMOKCDrMkbnWZq/KSmghYkLYPaa3OWi EZ34uFdZ3nQLnLDoUNi8XpfmziCyKyrJl2cYNSYtSdLqlcJMA= X-Gm-Gg: AYBFou1pwBTMNzzOniUiXGgIgIaCbbYJD836mvvkJmjwLjqszyvEiYZJ2u8kJLtuJhB oBIFyMdziEz4S9vltSJzt0ip5MwlTVREhwoHjmGQlNnFT/c0Q2iZHgQzPfgqb0vgDFDQsCg2YW5 wsYdX/jGJ6JcCThtf+P2TGP1KHN/KJcOSpjgzemGNT4qaTzXXKaY1ZpReu X-Received: by 2002:a05:690e:80b:10b0:671:2eb:c2a3 with SMTP id 956f58d0204a3-672ed2274cbmr2634335d50.9.1790386510282; Fri, 25 Sep 2026 18:35:10 -0700 (PDT) X-Received: by 2002:a05:690e:80b:10b0:671:2eb:c2a3 with SMTP id 956f58d0204a3-672ed2274cbmr2634330d50.9.1790386509609; Fri, 25 Sep 2026 18:35:09 -0700 (PDT) MIME-Version: 1.0 From: DJ Delorie Date: Fri, 25 Sep 2026 21:34:21 -0400 X-Gm-Features: AclHuK-4vsk_7eoHvMxI43Wd25lwXuQUBF5cAe_m9AtWat-68cnY9vAVgSAfik4 Message-ID: Subject: [PATCH v3 1/1] nscd: replace alloca with malloc in aicache, hstcache [BZ #34624] To: libc-alpha X-Mimecast-Spam-Score: 0 X-Mimecast-MFC-PROC-ID: cylj8R0prBu3mFThz3rwlCpDBlG3_zwlGnVWFdXuRK0_1790386510 X-Mimecast-Originator: redhat.com X-Spam-Status: No, score=-10.6 required=5.0 tests=BAYES_00, DKIMWL_WL_HIGH, DKIM_SIGNED, DKIM_VALID, DKIM_VALID_AU, DKIM_VALID_EF, GIT_PATCH_0, RCVD_IN_DNSWL_NONE, RCVD_IN_MSPIKE_H3, RCVD_IN_MSPIKE_WL, SPF_HELO_PASS, SPF_NONE, TXREP shortcircuit=no autolearn=ham autolearn_force=no version=3.4.6 X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on sourceware.org X-BeenThere: libc-alpha@sourceware.org X-Mailman-Version: 2.1.30 Precedence: list List-Id: Libc-alpha mailing list List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: libc-alpha-bounces~patchwork=sourceware.org@sourceware.org This changes the alloca fallback to a malloc fallback in the addrinfo and host cache code. --- v3: Simplify error returns. Add h_aliases_len. v2: Florian suggested storing the malloc'd pointer and using *that* as the "flag", which simplified the code. nscd/aicache.c | 24 +++++++++++++++++------- nscd/hstcache.c | 34 ++++++++++++++++++++++++++-------- 2 files changed, 43 insertions(+), 15 deletions(-) { @@ -216,8 +218,11 @@ cache_addhst (struct database_dyn *db, int fd, request_header *req, ++h_addr_list_cnt; if (h_addr_list_cnt == 0) - /* Invalid entry. */ - return MAX_TIMEOUT_VALUE; + { + /* Invalid entry. */ + free (h_aliases_len); + return MAX_TIMEOUT_VALUE; + } total += (sizeof (struct dataset) + h_name_len @@ -228,8 +233,10 @@ cache_addhst (struct database_dyn *db, int fd, request_header *req, change. Allocate memory on the cache since it is likely discarded anyway. If it turns out to be necessary to have a new record we can still allocate real memory. */ - bool alloca_used = false; dataset = NULL; + /* If not NULL, dataset is a temporary dataset not inserted into + the database, and needs to be free'd. */ + void *dataset_alloc = NULL; /* If the record contains more than one IP address (used for load balancing etc) don't cache the entry. This is something @@ -245,10 +252,15 @@ cache_addhst (struct database_dyn *db, int fd, request_header *req, /* We cannot permanently add the result in the moment. But we can provide the result as is. Store the data in some temporary memory. */ - dataset = (struct dataset *) alloca (total + req->key_len); + dataset = (struct dataset *) malloc (total + req->key_len); + if (dataset == NULL) + { + free (h_aliases_len); + return MAX_TIMEOUT_VALUE; + } /* We cannot add this record to the permanent database. */ - alloca_used = true; + dataset_alloc = dataset; } timeout = datahead_init_pos (&dataset->head, total + req->key_len, @@ -283,6 +295,8 @@ cache_addhst (struct database_dyn *db, int fd, request_header *req, for (cnt = 0; cnt < h_aliases_cnt; ++cnt) cp = mempcpy (cp, hst->h_aliases[cnt], h_aliases_len[cnt]); + free (h_aliases_len); + assert (cp == dataset->strdata + total - offsetof (struct dataset, strdata)); @@ -335,7 +349,9 @@ cache_addhst (struct database_dyn *db, int fd, request_header *req, key_copy = (char *) newp + (key_copy - (char *) dataset); dataset = memcpy (newp, dataset, total + req->key_len); - alloca_used = false; + + free (dataset_alloc); + dataset_alloc = NULL; } } @@ -363,7 +379,7 @@ cache_addhst (struct database_dyn *db, int fd, request_header *req, the current cache handling cannot handle and it is more than questionable whether it is worthwhile complicating the cache handling just for handling such a special case. */ - if (! alloca_used) + if (dataset_alloc == NULL) { /* If necessary, we also propagate the data to disk. */ if (db->persistent) @@ -394,6 +410,8 @@ cache_addhst (struct database_dyn *db, int fd, request_header *req, pthread_rwlock_unlock (&db->lock); } + free (dataset_alloc); + dataset_alloc = NULL; } if (__builtin_expect (!all_written, 0) && debug_level > 0) diff --git a/nscd/aicache.c b/nscd/aicache.c index ef15c373f5..46d05065f9 100644 --- a/nscd/aicache.c +++ b/nscd/aicache.c @@ -102,7 +102,9 @@ addhstaiX (struct database_dyn *db, int fd, request_header *req, int32_t ttl = INT32_MAX; ssize_t total = 0; char *key_copy = NULL; - bool alloca_used = false; + /* If not NULL, dataset is a temporary dataset not inserted into the + database, and needs to be free'd. */ + void *dataset_alloc = NULL; time_t timeout = MAX_TIMEOUT_VALUE; while (!no_more) @@ -173,10 +175,12 @@ addhstaiX (struct database_dyn *db, int fd, request_header *req, /* We cannot permanently add the result in the moment. But we can provide the result as is. Store the data in some temporary memory. */ - dataset = (struct dataset *) alloca (total + req->key_len); + dataset = (struct dataset *) malloc (total + req->key_len); + if (dataset == NULL) + goto out; /* We cannot add this record to the permanent database. */ - alloca_used = true; + dataset_alloc = dataset; } /* Fill in the address and address families. */ @@ -345,10 +349,12 @@ addhstaiX (struct database_dyn *db, int fd, request_header *req, /* We cannot permanently add the result in the moment. But we can provide the result as is. Store the data in some temporary memory. */ - dataset = (struct dataset *) alloca (total + req->key_len); + dataset = (struct dataset *) malloc (total + req->key_len); + if (dataset == NULL) + goto out; /* We cannot add this record to the permanent database. */ - alloca_used = true; + dataset_alloc = dataset; } /* Fill in the address and address families. */ @@ -419,7 +425,9 @@ addhstaiX (struct database_dyn *db, int fd, request_header *req, key_copy = (char *) newp + (key_copy - (char *) dataset); dataset = memcpy (newp, dataset, total + req->key_len); - alloca_used = false; + + free (dataset_alloc); + dataset_alloc = NULL; } /* Mark the old record as obsolete. */ @@ -502,7 +510,7 @@ next_nip: out: __resolv_context_put (ctx); - if (dataset != NULL && !alloca_used) + if (dataset != NULL && dataset_alloc == NULL) { /* If necessary, we also propagate the data to disk. */ if (db->persistent) @@ -528,6 +536,8 @@ next_nip: scratch_buffer_free (&tmpbuf4); scratch_buffer_free (&canonbuf); + free (dataset_alloc); + return timeout; } diff --git a/nscd/hstcache.c b/nscd/hstcache.c index fe91818640..ea00d741bc 100644 --- a/nscd/hstcache.c +++ b/nscd/hstcache.c @@ -202,7 +202,9 @@ cache_addhst (struct database_dyn *db, int fd, request_header *req, for (cnt = 0; hst->h_aliases[cnt] != NULL; ++cnt) ++h_aliases_cnt; /* Determine the length of all aliases. */ - h_aliases_len = (uint32_t *) alloca (h_aliases_cnt * sizeof (uint32_t)); + h_aliases_len = (uint32_t *) malloc (h_aliases_cnt * sizeof (uint32_t)); + if (h_aliases_len == NULL) + return MAX_TIMEOUT_VALUE; total = 0; for (cnt = 0; cnt < h_aliases_cnt; ++cnt)