From patchwork Tue Aug 29 17:11:24 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: andrey.konovalov@linux.dev X-Patchwork-Id: 13369247 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from kanga.kvack.org (kanga.kvack.org [205.233.56.17]) by smtp.lore.kernel.org (Postfix) with ESMTP id 3EF5CC83F1E for ; Tue, 29 Aug 2023 17:13:50 +0000 (UTC) Received: by kanga.kvack.org (Postfix) id 4A16E8E0036; Tue, 29 Aug 2023 13:13:48 -0400 (EDT) Received: by kanga.kvack.org (Postfix, from userid 40) id 429F18E003B; Tue, 29 Aug 2023 13:13:48 -0400 (EDT) X-Delivered-To: int-list-linux-mm@kvack.org Received: by kanga.kvack.org (Postfix, from userid 63042) id 2A4878E0036; Tue, 29 Aug 2023 13:13:48 -0400 (EDT) X-Delivered-To: linux-mm@kvack.org Received: from relay.hostedemail.com (smtprelay0012.hostedemail.com [216.40.44.12]) by kanga.kvack.org (Postfix) with ESMTP id EFA498E003B for ; Tue, 29 Aug 2023 13:13:47 -0400 (EDT) Received: from smtpin09.hostedemail.com (a10.router.float.18 [10.200.18.1]) by unirelay08.hostedemail.com (Postfix) with ESMTP id CD965140260 for ; Tue, 29 Aug 2023 17:13:47 +0000 (UTC) X-FDA: 81177789294.09.945D546 Received: from out-252.mta1.migadu.com (out-252.mta1.migadu.com [95.215.58.252]) by imf14.hostedemail.com (Postfix) with ESMTP id 22B6F100039 for ; Tue, 29 Aug 2023 17:13:45 +0000 (UTC) Authentication-Results: imf14.hostedemail.com; dkim=pass header.d=linux.dev header.s=key1 header.b=T1iG7qQW; dmarc=pass (policy=none) header.from=linux.dev; spf=pass (imf14.hostedemail.com: domain of andrey.konovalov@linux.dev designates 95.215.58.252 as permitted sender) smtp.mailfrom=andrey.konovalov@linux.dev ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=hostedemail.com; s=arc-20220608; t=1693329226; h=from:from:sender:reply-to:subject:subject:date:date: message-id:message-id:to:to:cc:cc:mime-version:mime-version: content-type:content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references:dkim-signature; bh=c+OqyPrsOPGHg5XrLPNZBNE7kZ+J8BEkGBD6zb/JuYQ=; b=TZ5YbBhYXVZyq9KoRd5bNLQg5FzQhGgCMmp5RddvokH0I5L5TXJ71oiTPv9qhdAWTR3FeG ZyLUtgbwSXoI7HTeU2ypskm5erAut8/Zkt3lO73yMe9EQtj4p2rgfjtPdP7WTKSH9KWyyX 49cY0Rkfv6sK1j8DQqqZXnMSNTrYSpM= ARC-Authentication-Results: i=1; imf14.hostedemail.com; dkim=pass header.d=linux.dev header.s=key1 header.b=T1iG7qQW; dmarc=pass (policy=none) header.from=linux.dev; spf=pass (imf14.hostedemail.com: domain of andrey.konovalov@linux.dev designates 95.215.58.252 as permitted sender) smtp.mailfrom=andrey.konovalov@linux.dev ARC-Seal: i=1; s=arc-20220608; d=hostedemail.com; t=1693329226; a=rsa-sha256; cv=none; b=jcxcX9909/AjIxgv0sK6gD58gPFt6wmJJwqCjK1rSUd9Il34B+w/cxZVd2Xjm7Fatqd6Ge lSlV5/XauWigF8NEFayLI4xU68qjqfIEQlxPEzwUfb/vwyO09lm3J9nRY2TFTozl1XBkZ/ iAPNNve3tq3//NQ1ozheF9+uFAX1ejE= X-Report-Abuse: Please report any abuse attempt to abuse@migadu.com and include these headers. DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linux.dev; s=key1; t=1693329224; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=c+OqyPrsOPGHg5XrLPNZBNE7kZ+J8BEkGBD6zb/JuYQ=; b=T1iG7qQWFqXknvW3oxV4ppqhlGJ2B4GzTHDs5oEMMGMfeCMjQjH9IJfBalbYfv0NVvUDzy EwkpyMnG6Nxt+AMl/9tnMXZ4f/nw+qGm5hpPJdpaKfCfaWqaErDfKrIusJZnN6iT+BpvCJ ObS/4jb3NCEUDuj8JPJ9Tc91Spi4dxo= From: andrey.konovalov@linux.dev To: Marco Elver , Alexander Potapenko Cc: Andrey Konovalov , Dmitry Vyukov , Vlastimil Babka , kasan-dev@googlegroups.com, Evgenii Stepanov , Andrew Morton , linux-mm@kvack.org, linux-kernel@vger.kernel.org, Andrey Konovalov Subject: [PATCH 14/15] stackdepot: allow users to evict stack traces Date: Tue, 29 Aug 2023 19:11:24 +0200 Message-Id: <99cd7ac4a312e86c768b933332364272b9e3fb40.1693328501.git.andreyknvl@google.com> In-Reply-To: References: MIME-Version: 1.0 X-Migadu-Flow: FLOW_OUT X-Rspamd-Queue-Id: 22B6F100039 X-Rspam-User: X-Rspamd-Server: rspam02 X-Stat-Signature: hsqwoum64ou764gjki6fac56yf91u8qj X-HE-Tag: 1693329225-558056 X-HE-Meta: U2FsdGVkX18Xh6d6N6GAcV0Sq+bCyRbWFucXxNzLj/UJzNMrZiQA3A6uswm8DHDXiBjiCSTNXPRnR4Mz8CCqRN1YEDAk+UMsXIrVou7N0ssIJUGaqovz6Hv1cJHL6V0o7sAkE3gMN65E1NdekncnyAuuJoawCjmW1e2Jl6HBpPDIenGzqjgWViSSKVE8bz+6Tj6ulEQVdqhvckl1GiJ5sPoVfwhyQM02bV8bmieBnznWyWcU4ukbaOPXp1sUBhqQN1V1GIQIvK+PGFfqhvgtAA9FWxPip6OiFYvy58Lbwp+wTojrlSSV1h2NE2lkSSnAnzareuIGH6MSBuJT24q8feikHlBvy0WDimhCEADEZAia9UwgpimkM0UAkpsNNvo7V7T6e7icmNrhQC6/FzE8OnNff7mjHZ/V4rxKd78ZZCgnAMJ8SkZ5iYVPLs7nw+UXc2scWjN8CRoRUZbG/QxmT7Czrc8qqhVhsqZoL3mjy+cAwSgLay6KxuUX3wBzL51lQjAd0rajgRdfm+Jk8zcKvNtZba3UEfbZM1VXbQJwFAjBXW5mmVNLzh2viPZoDRrLoURR7GvFUWMuuan6xv1+jbX5QXM2Jc6RoS21ZKNNcvW9Xl5IunhGoay2avVHiNLzG13Su6p4XAUMbv92bC4gEWrcnxEzlcL8Qj4duHQGNteL74aGVvGKv6D3HEOqOVCu5xlJAxAmbtUOadANF2NkFptzp29lQggnLGxdRbWM9LWjDpPCVDDOaBJsxO2SHrO+S4WcHMTv8oFMLCswU+YQtp18NUidxV5iC/bjpszNLV8xRvMj1NUkKmV54IvXUnJxEV7XhOz9k6SIJAPWavhpk3QHAUgaQibRLVMtaLygYGJLpFwl4RPJ3wPWQCtMNSXDZuqsIhfz3kg1DdRYr+AQJrakuvIt+geuI2xe65gq2AqPzprPV5kVpGRF/oIzOocChN9i7qI5DJUOiLhuxCi EeyWY0F+ VJpRF5to4bvk19zGsHOgdHrC3qjLuRbdfTjikPPnyDjYxRRg0/di5Ku9hksSFmAad+GqsyVJzjvFcnFBxC1XAvxCyGkb8ST+I2sR7 X-Bogosity: Ham, tests=bogofilter, spamicity=0.000000, version=1.2.4 Sender: owner-linux-mm@kvack.org Precedence: bulk X-Loop: owner-majordomo@kvack.org List-ID: From: Andrey Konovalov Add stack_depot_evict, a function that decrements a reference counter on a stack record and removes it from the stack depot once the counter reaches 0. Internally, when removing a stack record, the function unlinks it from the hash table bucket and returns to the freelist. With this change, the users of stack depot can call stack_depot_evict when keeping a stack trace in the stack depot is not needed anymore. This allows avoiding polluting the stack depot with irrelevant stack traces and thus have more space to store the relevant ones before the stack depot reaches its capacity. Signed-off-by: Andrey Konovalov --- include/linux/stackdepot.h | 11 ++++++++++ lib/stackdepot.c | 43 ++++++++++++++++++++++++++++++++++++++ 2 files changed, 54 insertions(+) diff --git a/include/linux/stackdepot.h b/include/linux/stackdepot.h index e58306783d8e..b14da6797714 100644 --- a/include/linux/stackdepot.h +++ b/include/linux/stackdepot.h @@ -121,6 +121,17 @@ depot_stack_handle_t stack_depot_save(unsigned long *entries, unsigned int stack_depot_fetch(depot_stack_handle_t handle, unsigned long **entries); +/** + * stack_depot_evict - Drop a reference to a stack trace from stack depot + * + * @handle: Stack depot handle returned from stack_depot_save() + * + * The stack trace gets fully removed from stack depot once all references + * to it has been dropped (once the number of stack_depot_evict calls matches + * the number of stack_depot_save calls for this stack trace). + */ +void stack_depot_evict(depot_stack_handle_t handle); + /** * stack_depot_print - Print a stack trace from stack depot * diff --git a/lib/stackdepot.c b/lib/stackdepot.c index 641db97d8c7c..cf28720b842d 100644 --- a/lib/stackdepot.c +++ b/lib/stackdepot.c @@ -384,6 +384,13 @@ static struct stack_record *depot_fetch_stack(depot_stack_handle_t handle) return stack; } +/* Frees stack into the freelist. */ +static void depot_free_stack(struct stack_record *stack) +{ + stack->next = next_stack; + next_stack = stack; +} + /* Calculates the hash for a stack. */ static inline u32 hash_stack(unsigned long *entries, unsigned int size) { @@ -555,6 +562,42 @@ unsigned int stack_depot_fetch(depot_stack_handle_t handle, } EXPORT_SYMBOL_GPL(stack_depot_fetch); +void stack_depot_evict(depot_stack_handle_t handle) +{ + struct stack_record *stack, **bucket; + unsigned long flags; + + if (!handle || stack_depot_disabled) + return; + + write_lock_irqsave(&pool_rwlock, flags); + + stack = depot_fetch_stack(handle); + if (WARN_ON(!stack)) + goto out; + + if (refcount_dec_and_test(&stack->count)) { + /* Drop stack from the hash table. */ + if (stack->next) + stack->next->prev = stack->prev; + if (stack->prev) + stack->prev->next = stack->next; + else { + bucket = &stack_table[stack->hash & stack_hash_mask]; + *bucket = stack->next; + } + stack->next = NULL; + stack->prev = NULL; + + /* Free stack. */ + depot_free_stack(stack); + } + +out: + write_unlock_irqrestore(&pool_rwlock, flags); +} +EXPORT_SYMBOL_GPL(stack_depot_evict); + void stack_depot_print(depot_stack_handle_t stack) { unsigned long *entries;