Received: by 2002:ac0:a581:0:0:0:0:0 with SMTP id m1-v6csp567204imm; Fri, 22 Jun 2018 01:16:52 -0700 (PDT) X-Google-Smtp-Source: ADUXVKJ9QShFCwFB2LiCufuvuRbLLi+XqPdgPQZKoj1JrJ6gdMvN87Nbp73DopG8eME4s5KRzPXl X-Received: by 2002:a65:64cf:: with SMTP id t15-v6mr508443pgv.79.1529655412117; Fri, 22 Jun 2018 01:16:52 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1529655412; cv=none; d=google.com; s=arc-20160816; b=0vVEBXeP1ULVPH4xjf6pBk1RlVDGxi79XxTkcpG8LdX0XqS0YHwhzLow7UXgG0+7ZL At4IFtoMA9EB8SzFL0D5y65ljciJNpSYnSM2h/woLWPVWiJ5GbnqRWNRd19qC1InzmID gETuFmHOC1Pb4EysUo67V9DWsaRPkSJBq319JY2yL34zywObaGHCnMxirPgNhHFa7Esg h7yk/WbO3MpP1vhSjD9batSW5nZYACbLfOXsV6Mle5kNeqToa866hmC5ctjdosTItMRF dR5qfq4+ke+zW9PJLM33FDboWC9a9hxzLIfYBWuw7wxCkZ5+GSDMIAiR6hsEhWxrrOOl fK4g== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:sender:references:in-reply-to:references :in-reply-to:message-id:date:subject:cc:to:from:dkim-signature :arc-authentication-results; bh=EvEb9AghybtdnkxHfKvMzouMMdmNPOMDUDXqyHf1hyQ=; b=HWjX7Zs5jyYI/io55GTGNxD9Ke1sknoUO7eCKlehERzBCJd05lcAyNxpgqtFSuilyC iP2YAiXbcGpZiiOh2jwenCHvyhRHsHTjU9xGWUmnvQoI2krE/G7r9QOLiwHvSNv6O5MM mE6DmFWBb+T1vb9qAkMOcCAjZFGPxfWdmo5fMYUz5F0sbn6W8IFeb4k0xxRjeozTj0Qf SS4vo+XkeD2TMU6OwaJQgIJmRQwKr5IW2Vtq1I2g+92ChbQIoJbrBnK8MWR9X28UvzX4 xo1wFr0IKR7yweIKRRW+8DcGQhVry50UxmuqKBlrSencv9LMrEqPiUo0Djce1KmklGSq wWLw== ARC-Authentication-Results: i=1; mx.google.com; dkim=pass header.i=@linaro.org header.s=google header.b=QGn5hNib; spf=pass (google.com: best guess record for domain of linux-kernel-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=linaro.org Return-Path: Received: from vger.kernel.org (vger.kernel.org. [209.132.180.67]) by mx.google.com with ESMTP id y127-v6si3276553pgb.96.2018.06.22.01.16.34; Fri, 22 Jun 2018 01:16:52 -0700 (PDT) Received-SPF: pass (google.com: best guess record for domain of linux-kernel-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) client-ip=209.132.180.67; Authentication-Results: mx.google.com; dkim=pass header.i=@linaro.org header.s=google header.b=QGn5hNib; spf=pass (google.com: best guess record for domain of linux-kernel-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=linaro.org Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1754280AbeFVIOG (ORCPT + 99 others); Fri, 22 Jun 2018 04:14:06 -0400 Received: from mail-pl0-f68.google.com ([209.85.160.68]:41368 "EHLO mail-pl0-f68.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1751289AbeFVIJ4 (ORCPT ); Fri, 22 Jun 2018 04:09:56 -0400 Received: by mail-pl0-f68.google.com with SMTP id w8-v6so3108290ply.8 for ; Fri, 22 Jun 2018 01:09:56 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; h=from:to:cc:subject:date:message-id:in-reply-to:references :in-reply-to:references; bh=EvEb9AghybtdnkxHfKvMzouMMdmNPOMDUDXqyHf1hyQ=; b=QGn5hNibPxZvcY+B8cCrU5jZegOWBsI956F5lIQd0q/RYra2/LPc3P3vKd0X+NluHy KZTAe8xCyRJ2WMB1dhZRc9RbFoVXeOcqJLyuEctmn8SZWc3HzEahke5m+2vuneWhUvsx md4VioeOYEhWs6eyTgyvTih1QRbzRA2P2mVdY= X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:in-reply-to:references; bh=EvEb9AghybtdnkxHfKvMzouMMdmNPOMDUDXqyHf1hyQ=; b=Ge6oe4K86ObbzxjGkPL5Qd0VSgL9lPtNesNcftIgA7TZeHso6XDeKQdDVAzS8pa6L0 lrbej6+Og7qpQzlcvyttS7V3r/Xx2JjGxpbbRzPTTcoIE45P/+Zdd8UvaXgRhMVpUQMk WXaDcbTVI9PO3g/zz+Mocb598wHXPfWwMzKiVheFQ+Uil0prm0h6m4T6238fqA70Yu8Z 0aX54hV3cxvJw5qvo1PpqGNgf73xWApVNBE6U57qNaoxKWuwBL0jhAY73U27ymmwY4A5 X2nSnUmxD1phJO4NrgY7KkvgCgtO4R/wyuPuX7dihlNmFyoavFGWJnPh990Dic2i7hEK 7E7g== X-Gm-Message-State: APt69E0TdFE4KmE7mGnFXlYDqnpa00FdzUrSSESM+Y6XAzx/Blgkjqns r0JGiOqgUk7O6J7vcFGJaozDnw== X-Received: by 2002:a17:902:6bc7:: with SMTP id m7-v6mr633780plt.162.1529654996417; Fri, 22 Jun 2018 01:09:56 -0700 (PDT) Received: from baolinwangubtpc.spreadtrum.com ([117.18.48.102]) by smtp.gmail.com with ESMTPSA id i65-v6sm22656131pfd.17.2018.06.22.01.09.54 (version=TLS1 cipher=ECDHE-RSA-AES128-SHA bits=128/128); Fri, 22 Jun 2018 01:09:55 -0700 (PDT) From: Baolin Wang To: ohad@wizery.com, bjorn.andersson@linaro.org, broonie@kernel.org Cc: baolin.wang@linaro.org, linux-spi@vger.kernel.org, linux-remoteproc@vger.kernel.org, linux-kernel@vger.kernel.org Subject: [PATCH 2/8] hwspinlock: Add devm_xxx() APIs to request/free hwlock Date: Fri, 22 Jun 2018 16:08:59 +0800 Message-Id: X-Mailer: git-send-email 1.7.9.5 In-Reply-To: References: In-Reply-To: References: Sender: linux-kernel-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org This patch introduces some devm_xxx() APIs to help to request or free the hwlocks, which will help to simplify the cleanup code for drivers requesting one hwlock, ensuring that the hwlock is automatically freed whenever the device is unbound. Signed-off-by: Baolin Wang --- drivers/hwspinlock/hwspinlock_core.c | 110 ++++++++++++++++++++++++++++++++++ include/linux/hwspinlock.h | 22 +++++++ 2 files changed, 132 insertions(+) diff --git a/drivers/hwspinlock/hwspinlock_core.c b/drivers/hwspinlock/hwspinlock_core.c index bea3586..d542b6f 100644 --- a/drivers/hwspinlock/hwspinlock_core.c +++ b/drivers/hwspinlock/hwspinlock_core.c @@ -735,6 +735,116 @@ int hwspin_lock_free(struct hwspinlock *hwlock) } EXPORT_SYMBOL_GPL(hwspin_lock_free); +static int devm_hwspin_lock_match(struct device *dev, void *res, void *data) +{ + struct hwspinlock **hwlock = res; + + if (WARN_ON(!hwlock || !*hwlock)) + return 0; + + return *hwlock == data; +} + +static void devm_hwspin_lock_release(struct device *dev, void *res) +{ + hwspin_lock_free(*(struct hwspinlock **)res); +} + +/** + * devm_hwspin_lock_free() - free a specific hwspinlock for a managed device + * @dev: the device to free the specific hwspinlock + * @hwlock: the specific hwspinlock to free + * + * This function mark @hwlock as free again. + * Should only be called with an @hwlock that was retrieved from + * an earlier call to hwspin_lock_request{_specific}. + * + * Should be called from a process context (might sleep) + * + * Returns 0 on success, or an appropriate error code on failure + */ +int devm_hwspin_lock_free(struct device *dev, struct hwspinlock *hwlock) +{ + int ret; + + ret = devres_release(dev, devm_hwspin_lock_release, + devm_hwspin_lock_match, hwlock); + WARN_ON(ret); + + return ret; +} +EXPORT_SYMBOL_GPL(devm_hwspin_lock_free); + +/** + * devm_hwspin_lock_request() - request an hwspinlock for a managed device + * @dev: the device to request an hwspinlock + * + * This function should be called by users of the hwspinlock device, + * in order to dynamically assign them an unused hwspinlock. + * Usually the user of this lock will then have to communicate the lock's id + * to the remote core before it can be used for synchronization (to get the + * id of a given hwlock, use hwspin_lock_get_id()). + * + * Should be called from a process context (might sleep) + * + * Returns the address of the assigned hwspinlock, or NULL on error + */ +struct hwspinlock *devm_hwspin_lock_request(struct device *dev) +{ + struct hwspinlock **ptr, *hwlock; + + ptr = devres_alloc(devm_hwspin_lock_release, sizeof(*ptr), GFP_KERNEL); + if (!ptr) + return ERR_PTR(-ENOMEM); + + hwlock = hwspin_lock_request(); + if (!IS_ERR(hwlock)) { + *ptr = hwlock; + devres_add(dev, ptr); + } else { + devres_free(ptr); + } + + return hwlock; +} +EXPORT_SYMBOL_GPL(devm_hwspin_lock_request); + +/** + * devm_hwspin_lock_request_specific() - request for a specific hwspinlock for + * a managed device + * @dev: the device to request the specific hwspinlock + * @id: index of the specific hwspinlock that is requested + * + * This function should be called by users of the hwspinlock module, + * in order to assign them a specific hwspinlock. + * Usually early board code will be calling this function in order to + * reserve specific hwspinlock ids for predefined purposes. + * + * Should be called from a process context (might sleep) + * + * Returns the address of the assigned hwspinlock, or NULL on error + */ +struct hwspinlock *devm_hwspin_lock_request_specific(struct device *dev, + unsigned int id) +{ + struct hwspinlock **ptr, *hwlock; + + ptr = devres_alloc(devm_hwspin_lock_release, sizeof(*ptr), GFP_KERNEL); + if (!ptr) + return ERR_PTR(-ENOMEM); + + hwlock = hwspin_lock_request_specific(id); + if (!IS_ERR(hwlock)) { + *ptr = hwlock; + devres_add(dev, ptr); + } else { + devres_free(ptr); + } + + return hwlock; +} +EXPORT_SYMBOL_GPL(devm_hwspin_lock_request_specific); + MODULE_LICENSE("GPL v2"); MODULE_DESCRIPTION("Hardware spinlock interface"); MODULE_AUTHOR("Ohad Ben-Cohen "); diff --git a/include/linux/hwspinlock.h b/include/linux/hwspinlock.h index 2b6f389..dfd0593 100644 --- a/include/linux/hwspinlock.h +++ b/include/linux/hwspinlock.h @@ -67,6 +67,10 @@ int __hwspin_lock_timeout(struct hwspinlock *, unsigned int, int, int __hwspin_trylock(struct hwspinlock *, int, unsigned long *); void __hwspin_unlock(struct hwspinlock *, int, unsigned long *); int of_hwspin_lock_get_id_byname(struct device_node *np, const char *name); +int devm_hwspin_lock_free(struct device *dev, struct hwspinlock *hwlock); +struct hwspinlock *devm_hwspin_lock_request(struct device *dev); +struct hwspinlock *devm_hwspin_lock_request_specific(struct device *dev, + unsigned int id); #else /* !CONFIG_HWSPINLOCK */ @@ -132,6 +136,24 @@ int of_hwspin_lock_get_id_byname(struct device_node *np, const char *name) return 0; } +static inline +int devm_hwspin_lock_free(struct device *dev, struct hwspinlock *hwlock) +{ + return 0; +} + +static inline struct hwspinlock *devm_hwspin_lock_request(struct device *dev) +{ + return ERR_PTR(-ENODEV); +} + +static inline +struct hwspinlock *devm_hwspin_lock_request_specific(struct device *dev, + unsigned int id) +{ + return ERR_PTR(-ENODEV); +} + #endif /* !CONFIG_HWSPINLOCK */ /** -- 1.7.9.5