From patchwork Mon Nov 19 18:55:17 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Waiman Long X-Patchwork-Id: 10689317 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id D1AB213AD for ; Mon, 19 Nov 2018 18:57:38 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id C3EC82A46F for ; Mon, 19 Nov 2018 18:57:38 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id AFD1F2A45B; Mon, 19 Nov 2018 18:57:38 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-2.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_NONE autolearn=ham version=3.3.1 Received: from kanga.kvack.org (kanga.kvack.org [205.233.56.17]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 28AFA2A46C for ; Mon, 19 Nov 2018 18:57:38 +0000 (UTC) Received: by kanga.kvack.org (Postfix) id 4DC176B1BEE; Mon, 19 Nov 2018 13:57:37 -0500 (EST) Delivered-To: linux-mm-outgoing@kvack.org Received: by kanga.kvack.org (Postfix, from userid 40) id 48BDD6B1BEF; Mon, 19 Nov 2018 13:57:37 -0500 (EST) X-Original-To: int-list-linux-mm@kvack.org X-Delivered-To: int-list-linux-mm@kvack.org Received: by kanga.kvack.org (Postfix, from userid 63042) id 3A3AF6B1BF0; Mon, 19 Nov 2018 13:57:37 -0500 (EST) X-Original-To: linux-mm@kvack.org X-Delivered-To: linux-mm@kvack.org Received: from mail-qk1-f199.google.com (mail-qk1-f199.google.com [209.85.222.199]) by kanga.kvack.org (Postfix) with ESMTP id 12C996B1BEE for ; Mon, 19 Nov 2018 13:57:37 -0500 (EST) Received: by mail-qk1-f199.google.com with SMTP id c84so71564028qkb.13 for ; Mon, 19 Nov 2018 10:57:37 -0800 (PST) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-original-authentication-results:x-gm-message-state:from:to:cc :subject:date:message-id:in-reply-to:references; bh=80nYVpjORCReHIj2uz46o7n7SFyAOvH/JNuXPKW8n38=; b=i7zQTM1jclGzWV9u0Y9EhbTFlLtN4ghGVf4k2boW2D5FZdIrXeKTnje2L61HWzlakk bsQ7p0sfW9JTCF8pefgqYrz3Yj+0915vBwz2NMMhZhl7ku9RnIzDhBAcJ+n9qXlPWmKw AGsuKaYOdgbQlaUgyBlJYfg+4c3+taG2A9jJkdnUELNu3eBfGNxTtk+nEhnlPMMnOPpQ f6OQiwvyQU3u1L43UpDXBPkaamobJiOa5xo9EUhGzsHiRcF3SdgogL/GVYjs/pNDHUWj xOzIlDknegeL629gyCDW+NUDm8AjG/q1Une+FFF8ynywqIKs0nHiiJQLMzEenK20TW/M J5RA== X-Original-Authentication-Results: mx.google.com; spf=pass (google.com: domain of longman@redhat.com designates 209.132.183.28 as permitted sender) smtp.mailfrom=longman@redhat.com; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=redhat.com X-Gm-Message-State: AGRZ1gKdmqCSHMsDzJ9S7O1/8TsxLpAr7HtcyZBSZP+D+KwwBPD4BYv7 bk7a2eTJ2C8X5qbqkv0qMhXUdinHuS4YJ8dVrPwfGLsycEyF+HNTACKQFcF9b+cre6ihs4hipId PtnYnnsG4k7MYSGNoFJzA0sqXmm0mFrXN3Q69jsMrvvA8zH8VtkuZCMZlB0U4UCIutg== X-Received: by 2002:ac8:3ae5:: with SMTP id x92mr22736007qte.370.1542653855506; Mon, 19 Nov 2018 10:57:35 -0800 (PST) X-Google-Smtp-Source: AJdET5e8Zk2f2Mhy8HNW2NBRi99RMV4kwqVirLg8IviVlViH5F6aqpeadiX0NDcWdRVCCOFT72PA X-Received: by 2002:ac8:3ae5:: with SMTP id x92mr22735976qte.370.1542653854771; Mon, 19 Nov 2018 10:57:34 -0800 (PST) ARC-Seal: i=1; a=rsa-sha256; t=1542653854; cv=none; d=google.com; s=arc-20160816; b=nz7mzhX/ogftxQMBC+kofEZ/hPSuGV4mLPC0iIBB2xXOElwkbmf8GvLb2pYqWfBIFQ OtXwaQ/mU/mJqMHMgerGfOQ104TWOYdNVIFGEFMJKwhSIwbcEYh+3sPO1venmNh0Aii5 MhyIi9nGSVCvOXY1vF/NJP6D2RXfzTWS9C1AuJEfZEgaMkFZB2kWAUJ1lwX/5i0i/UK8 YJ3QkrM7HBuZkoM3WcuPIt7BLxQg16JIbWoeRKxolLDXZRRXDz4k+UclGG2OQjbdhZhM xU9tfai8Xp2j9C0eUZEuaAJOG5XzM9zVed/mxAoXFU/z9bIvmEEFFCDIaRcOn0xRkCcM 2Qiw== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=references:in-reply-to:message-id:date:subject:cc:to:from; bh=80nYVpjORCReHIj2uz46o7n7SFyAOvH/JNuXPKW8n38=; b=ixIAtRsfVQ+6ITjWqqAQVFEip5MH/xKJOYy0lybSTQ1JipBiYdc3rLw8nkffSXHdJl y/64DjxTP9Mk+3IqZDA512g4/VSFbWohjamcxqlZFvITMLL+nj3tf+1qfXpm37IXom1o zniRAH1uK4pQbM5/3Cp2W+auJkOWIkGjo15dwh9ntKYrQ+WUiyvfr2mkV+mpXDzPIq8q Fhc2cS59lQG/35lJY0KBhPzvBlHaIaxd+ajNauLRR71YKEvnDTlkDj3BsM1f037lul7s mhnnsLkvyDkUKONEQ/cGO4stFVl+O2QhiYDrALwU1OsLdbh1qld3/AFURVmk+vUyS+8K 50+g== ARC-Authentication-Results: i=1; mx.google.com; spf=pass (google.com: domain of longman@redhat.com designates 209.132.183.28 as permitted sender) smtp.mailfrom=longman@redhat.com; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=redhat.com Received: from mx1.redhat.com (mx1.redhat.com. [209.132.183.28]) by mx.google.com with ESMTPS id f42si4122289qkh.191.2018.11.19.10.57.34 for (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Mon, 19 Nov 2018 10:57:34 -0800 (PST) Received-SPF: pass (google.com: domain of longman@redhat.com designates 209.132.183.28 as permitted sender) client-ip=209.132.183.28; Authentication-Results: mx.google.com; spf=pass (google.com: domain of longman@redhat.com designates 209.132.183.28 as permitted sender) smtp.mailfrom=longman@redhat.com; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=redhat.com Received: from smtp.corp.redhat.com (int-mx03.intmail.prod.int.phx2.redhat.com [10.5.11.13]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id C3BAC3154866; Mon, 19 Nov 2018 18:57:33 +0000 (UTC) Received: from llong.com (dhcp-17-55.bos.redhat.com [10.18.17.55]) by smtp.corp.redhat.com (Postfix) with ESMTP id 7EFA4608E7; Mon, 19 Nov 2018 18:57:25 +0000 (UTC) From: Waiman Long To: Peter Zijlstra , Ingo Molnar , Will Deacon , Thomas Gleixner Cc: linux-kernel@vger.kernel.org, kasan-dev@googlegroups.com, linux-mm@kvack.org, iommu@lists.linux-foundation.org, Petr Mladek , Sergey Senozhatsky , Andrey Ryabinin , Tejun Heo , Andrew Morton , Waiman Long Subject: [PATCH v2 08/17] locking/lockdep: Add support for nestable terminal locks Date: Mon, 19 Nov 2018 13:55:17 -0500 Message-Id: <1542653726-5655-9-git-send-email-longman@redhat.com> In-Reply-To: <1542653726-5655-1-git-send-email-longman@redhat.com> References: <1542653726-5655-1-git-send-email-longman@redhat.com> X-Scanned-By: MIMEDefang 2.79 on 10.5.11.13 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.5.110.41]); Mon, 19 Nov 2018 18:57:33 +0000 (UTC) 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: X-Virus-Scanned: ClamAV using ClamSMTP There are use cases where we want to allow nesting of one terminal lock underneath another terminal-like lock. That new lock type is called nestable terminal lock which can optionally allow the acquisition of no more than one regular (non-nestable) terminal lock underneath it. Signed-off-by: Waiman Long --- include/linux/lockdep.h | 9 ++++++++- kernel/locking/lockdep.c | 15 +++++++++++++-- kernel/locking/lockdep_internals.h | 2 +- 3 files changed, 22 insertions(+), 4 deletions(-) diff --git a/include/linux/lockdep.h b/include/linux/lockdep.h index a146bca..b9435fb 100644 --- a/include/linux/lockdep.h +++ b/include/linux/lockdep.h @@ -148,16 +148,20 @@ struct lock_class_stats { * 1) LOCKDEP_FLAG_NOVALIDATE: No full validation, just simple checks. * 2) LOCKDEP_FLAG_TERMINAL: This is a terminal lock where lock/unlock on * another lock within its critical section is not allowed. + * 3) LOCKDEP_FLAG_TERMINAL_NESTABLE: This is a terminal lock that can + * allow one more regular terminal lock to be nested underneath it. * * Only the least significant 4 bits of the flags will be copied to the * held_lock structure. */ #define LOCKDEP_FLAG_TERMINAL (1 << 0) +#define LOCKDEP_FLAG_TERMINAL_NESTABLE (1 << 1) #define LOCKDEP_FLAG_NOVALIDATE (1 << 4) #define LOCKDEP_HLOCK_FLAGS_MASK 0x0f #define LOCKDEP_NOCHECK_FLAGS (LOCKDEP_FLAG_NOVALIDATE |\ - LOCKDEP_FLAG_TERMINAL) + LOCKDEP_FLAG_TERMINAL |\ + LOCKDEP_FLAG_TERMINAL_NESTABLE) /* * Map the lock object (the lock instance) to the lock-class object. @@ -327,6 +331,8 @@ extern void lockdep_init_map(struct lockdep_map *lock, const char *name, do { (lock)->dep_map.flags |= LOCKDEP_FLAG_NOVALIDATE; } while (0) #define lockdep_set_terminal_class(lock) \ do { (lock)->dep_map.flags |= LOCKDEP_FLAG_TERMINAL; } while (0) +#define lockdep_set_terminal_nestable_class(lock) \ + do { (lock)->dep_map.flags |= LOCKDEP_FLAG_TERMINAL_NESTABLE; } while (0) /* * Compare locking classes @@ -444,6 +450,7 @@ static inline void lockdep_on(void) #define lockdep_set_novalidate_class(lock) do { } while (0) #define lockdep_set_terminal_class(lock) do { } while (0) +#define lockdep_set_terminal_nestable_class(lock) do { } while (0) /* * We don't define lockdep_match_class() and lockdep_match_key() for !LOCKDEP diff --git a/kernel/locking/lockdep.c b/kernel/locking/lockdep.c index 40894c1..5a853a6 100644 --- a/kernel/locking/lockdep.c +++ b/kernel/locking/lockdep.c @@ -3263,13 +3263,24 @@ static int __lock_acquire(struct lockdep_map *lock, unsigned int subclass, class_idx = class - lock_classes + 1; if (depth) { + int prev_type; + hlock = curr->held_locks + depth - 1; /* - * Warn if the previous lock is a terminal lock. + * Warn if the previous lock is a terminal lock or the + * previous lock is a nestable terminal lock and the current + * one isn't a regular terminal lock. */ - if (DEBUG_LOCKS_WARN_ON(hlock_is_terminal(hlock))) + prev_type = hlock_is_terminal(hlock); + if (DEBUG_LOCKS_WARN_ON((prev_type == LOCKDEP_FLAG_TERMINAL) || + ((prev_type == LOCKDEP_FLAG_TERMINAL_NESTABLE) && + (flags_is_terminal(class->flags) != + LOCKDEP_FLAG_TERMINAL)))) { + pr_warn("Terminal lock error: prev lock = %s, curr lock = %s\n", + hlock->instance->name, class->name); return 0; + } if (hlock->class_idx == class_idx && nest_lock) { if (hlock->references) { diff --git a/kernel/locking/lockdep_internals.h b/kernel/locking/lockdep_internals.h index 271fba8..51fa141 100644 --- a/kernel/locking/lockdep_internals.h +++ b/kernel/locking/lockdep_internals.h @@ -215,5 +215,5 @@ static inline unsigned long debug_class_ops_read(struct lock_class *class) static inline unsigned int flags_is_terminal(unsigned int flags) { - return flags & LOCKDEP_FLAG_TERMINAL; + return flags & (LOCKDEP_FLAG_TERMINAL|LOCKDEP_FLAG_TERMINAL_NESTABLE); }