From patchwork Fri Sep 8 15:45:13 2017 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Peter Rosin X-Patchwork-Id: 112094 Delivered-To: patch@linaro.org Received: by 10.37.128.210 with SMTP id c18csp1806605ybm; Fri, 8 Sep 2017 08:46:36 -0700 (PDT) X-Google-Smtp-Source: ADKCNb4zRkxjXAV3jsmOUbqtZTtXG3L+A0MoyW2ce5FvNojpEelLu+M+6N3mDqmVnc6hpuXKQbp8 X-Received: by 10.98.54.70 with SMTP id d67mr3464536pfa.287.1504885596615; Fri, 08 Sep 2017 08:46:36 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1504885596; cv=none; d=google.com; s=arc-20160816; b=tixUJ0OxUtbdq9bd9LX87R7UCL3ENIKWuCaYwzF7tpCe4zHy+GhqDu30XdpLHi4by5 fcV96XVcx+kCXMKZjE7k/uZaBrBre+zIXnIrDa8F16/yzmLGkmH7yKNUXdtJ5EWcfSEA 3bLviB3vQ6/OozMhrnSqa6JW/rCYbGx5JMGMYXOY0BzEzsA+1Kn45tqzRiYHCKsD7CUC 9suKMkjuK98ysQnkSc+DZVloqYMi5HzWl3YRaoAW6lY7S981QHPXj75UYP0lY6X2hbWX LopQBjcVd/pVjr+cT6MfFRaw4x7jfprJHaSgpH2RT7Ijwp5Yqaqzl6IhVKniyrruymKL 5jXA== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:sender:spamdiagnosticmetadata :spamdiagnosticoutput:mime-version:references:in-reply-to:message-id :date:subject:cc:to:from:dkim-signature:arc-authentication-results; bh=YvZksExKduyPWMDBzetzb8qNCvYesgCjgiU7+h5JutA=; b=xxrklIO/1JV2dzUEd102r4EOPcgTULth55vLTrD3cKmwv4gRh4gZF/skdIqbYAp87u pcmcxd0pKDDAyCRYxJo9JcU55KQ5l9aRB1QyTaQp8FNyzZTKXZoNKq/+hZb9AxvR3ctN SFKYp+hS7W1oUVjMsm8Whgb7JmmneKPOf0sK/Oa/BGrsSdoYrmNoFbVDotx/6eDHBnBI c0CoygwOHhgZx/B2APMG2s7Lx0/dRsuQxdKJjNFpwkqDvX3NGDh2sc58h2YW841dkO4H wxHvJ59Ps9ibysaAsLKDw2qPEtGH4yawfjejp4dSt3RK4ylZuy+fw6FSdTgTDf3briiE 3B2g== ARC-Authentication-Results: i=1; mx.google.com; dkim=pass header.i=@axentiatech.onmicrosoft.com header.s=selector1-axentia-se header.b=CAbUvH5F; 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 Return-Path: Received: from vger.kernel.org (vger.kernel.org. [209.132.180.67]) by mx.google.com with ESMTP id j88si1776978pfe.519.2017.09.08.08.46.36; Fri, 08 Sep 2017 08:46:36 -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=@axentiatech.onmicrosoft.com header.s=selector1-axentia-se header.b=CAbUvH5F; 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 Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1753522AbdIHPqd (ORCPT + 26 others); Fri, 8 Sep 2017 11:46:33 -0400 Received: from mail-ve1eur01on0119.outbound.protection.outlook.com ([104.47.1.119]:29792 "EHLO EUR01-VE1-obe.outbound.protection.outlook.com" rhost-flags-OK-OK-OK-FAIL) by vger.kernel.org with ESMTP id S1751548AbdIHPqa (ORCPT ); Fri, 8 Sep 2017 11:46:30 -0400 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=axentiatech.onmicrosoft.com; s=selector1-axentia-se; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version; bh=YvZksExKduyPWMDBzetzb8qNCvYesgCjgiU7+h5JutA=; b=CAbUvH5F+wYr+W+dNyJPP4l+uPQFC+au86L1IuSAUZr6jtUyhExB6cN7FUQCScHDDuinSaFm57VVh3Oh548IybpI178UhvNxsmYQBzcKM/GoYXnmZdmkOLX9hDx63juQgYrljckGxz8OaOXPFjglMAwjRFY/NadHT41H2tsRLPM= Authentication-Results: spf=none (sender IP is ) smtp.mailfrom=peda@axentia.se; Received: from orc.pedanet (81.224.168.30) by VI1PR0202MB2557.eurprd02.prod.outlook.com (2603:10a6:801:6::8) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384_P256) id 15.20.13.10; Fri, 8 Sep 2017 15:46:24 +0000 From: Peter Rosin To: Hans de Goede Cc: Stephen Boyd , MyungJoo Ham , Chanwoo Choi , Guenter Roeck , Heikki Krogerus , Darren Hart , Andy Shevchenko , Mathias Nyman , linux-kernel@vger.kernel.org, platform-driver-x86@vger.kernel.org, devel@driverdev.osuosl.org, Kuppuswamy Sathyanarayanan , Sathyanarayanan Kuppuswamy Natarajan , Greg Kroah-Hartman , linux-usb@vger.kernel.org, Peter Rosin Subject: [PATCH 1/2] mux: add mux_control_get_optional() API Date: Fri, 8 Sep 2017 17:45:13 +0200 Message-Id: <20170908154514.4463-2-peda@axentia.se> X-Mailer: git-send-email 2.11.0 In-Reply-To: <20170908154514.4463-1-peda@axentia.se> References: <20170905164221.11266-6-hdegoede@redhat.com> <20170908154514.4463-1-peda@axentia.se> MIME-Version: 1.0 X-Originating-IP: [81.224.168.30] X-ClientProxiedBy: HE1PR0301CA0017.eurprd03.prod.outlook.com (2603:10a6:3:76::27) To VI1PR0202MB2557.eurprd02.prod.outlook.com (2603:10a6:801:6::8) X-MS-PublicTrafficType: Email X-MS-Office365-Filtering-Correlation-Id: a05a6cd1-c116-4a1d-4eca-08d4f6d0c40c X-Microsoft-Antispam: UriScan:; BCL:0; PCL:0; RULEID:(300000500095)(300135000095)(300000501095)(300135300095)(22001)(300000502095)(300135100095)(2017030254152)(2017082002075)(300000503095)(300135400095)(201703131423075)(201702281549075)(300000504095)(300135200095)(300000505095)(300135600095)(300000506095)(300135500095); SRVR:VI1PR0202MB2557; X-Microsoft-Exchange-Diagnostics: 1; VI1PR0202MB2557; 3:YDidEb+Hjynbczky2lIceQk//9d2mgNrcHXV3P3rm8VpacyH5FwrbePChVuzLG4+iT2CIsXoH5/TzqipCJYPC880Z2lMA4EivWWcZa9XUWmSEQaeIo1xC5IndPb6xN1j4buJ1KmFQwapuRbDZGfE69NTwvyRLhxNgBrx3Y4A3QOKYuw4V+s3COCGktyWfviNo20hle29SDKwtx5Ls7KrTS/NAEmmEVQCc7IeBr1uNsXX9mKU1fdyTO8ZQNN6Rzlm; 25:qVTUDQaN+92d2KmhQ0U6jj+wG0rVTezbXJmR4kVDa0nTP+us1H5h2mfEi54WB+JTXwDJ8vJ9OpU3QPiQWXm/5Zo+OSVnuxs8oDYeq53n1gktebSleaZd9NcUi+HjMGJdbLB7Ypa2AsGbcKaJ7Da3vF9ccFb50UVTvaS9tAUSXubE+YXWJCKzD7SP8yCAE0H2Tq12POghrVXs0AhGaOdwEHFARzQd6AL+Hb7AY4rrxrB//duAsXbAtVRJnmc5ldeOiTmvV8dVwMSdk6joHc8nHnpy4LRvVbUMIB0Dt0oSWQZw1HlSGlUTv0vyU8Rz3QGtWcRJm6xcGi9IMXCwdLWxNg==; 31:PPolN9irltq+D92mCvwzemXa/+rQ8fak54X07LrZ93CytKsG5bO9Bx+ebYefnFGTFje6XI9dL5oXiktxyGUUDbumtAbqoIE0iPtFRhIFx4pIU0BhxWf8QQgbrlpbKxBHMFGqt7eXOEwuMgy18QKVhOs2hbJKbOwpL+FlVS9NHTS05FMAYtqLl+VVvqkTDHPPmnc+H6QrEliXNJLMU3exs1+ZggNSmN5pLOglFNfaoCc= X-MS-TrafficTypeDiagnostic: VI1PR0202MB2557: X-Exchange-Antispam-Report-Test: UriScan:; X-Microsoft-Antispam-PRVS: X-Exchange-Antispam-Report-CFA-Test: BCL:0; PCL:0; RULEID:(100000700101)(100105000095)(100000701101)(100105300095)(100000702101)(100105100095)(6040450)(2401047)(8121501046)(5005006)(93006095)(93001095)(3002001)(10201501046)(100000703101)(100105400095)(6041248)(20161123558100)(20161123560025)(20161123555025)(2016111802025)(20161123564025)(201703131423075)(201703061421075)(20161123562025)(6042181)(6043046)(6072148)(201708071742011)(100000704101)(100105200095)(100000705101)(100105500095); SRVR:VI1PR0202MB2557; BCL:0; PCL:0; RULEID:(100000800101)(100110000095)(100000801101)(100110300095)(100000802101)(100110100095)(100000803101)(100110400095)(100000804101)(100110200095)(100000805101)(100110500095); SRVR:VI1PR0202MB2557; X-Microsoft-Exchange-Diagnostics: 1; VI1PR0202MB2557; 4:E/No935IwpCsiqhCisYTH3qY7NXQmAahiDp9QEebfCgwNHY2lBLMQxGeGIddsXYeiC01azL4Qq/oPkD+k/AewmJqKzu7jZjPgCZh0iQY51Zummz40nw4jeQQoLrIuoyZlzGWZLusbwpT4y7VfW2plrU4yhYjDLyd3R10SRwqFUl8jt6L/Rt7pAMkUPRO/LOxbQcQoq1ks6lL5l8smwJtALAEgAD2S7Oo529KwnGLlOVanvkOIj/rQeP4hFtKNcls X-Forefront-PRVS: 04244E0DC5 X-Forefront-Antispam-Report: SFV:NSPM; SFS:(10019020)(4630300001)(7370300001)(6009001)(199003)(189002)(575784001)(6116002)(68736007)(86362001)(189998001)(3846002)(2906002)(6916009)(6666003)(2950100002)(107886003)(50986999)(1076002)(110136004)(76176999)(4326008)(53936002)(36756003)(54906002)(7350300001)(97736004)(6512007)(5003940100001)(81156014)(81166006)(8676002)(7736002)(66066001)(6506006)(305945005)(50226002)(508600001)(50466002)(7416002)(101416001)(74482002)(105586002)(47776003)(48376002)(42186005)(5660300001)(33646002)(106356001)(25786009)(6486002)(42262002); DIR:OUT; SFP:1102; SCL:1; SRVR:VI1PR0202MB2557; H:orc.pedanet; FPR:; SPF:None; PTR:InfoNoRecords; A:1; MX:1; LANG:en; Received-SPF: None (protection.outlook.com: axentia.se does not designate permitted sender hosts) X-Microsoft-Exchange-Diagnostics: 1; VI1PR0202MB2557; 23:gGYGO+jSXPOXQxMX+Ub+3k9OcCKJbIrnMUTZXH9jikvVl2gTFL2R7X/VWUz0GTQFB5QHtkNsu8GXzGepSrEekGrE+3D/Xd8isy4yyWE/JOMbWCs4FxqRhDNmjyoZNgFriVcMBb07Yhqz459LdnZXBl8Ox3b75p7GIfAKGjdfYEOzPM30XudH11IkmrWNcjAdT6dxkLcJM4P3+Baxm/xkx3wR7AcR45cecNZXR6nqQuOklYzfqbOZjU0FUVynCNDQyjTqgjmkvsLXVCFUVLVgt6hFgoHf1su9XnTxUsG6gPfLQJUXVJziYyQaX8s6/H2g8DV7c/JzG+w1Mh6gH6P4RRxjtPpeJlCYgqEqqzFgMzbW7S7Z5USAe4dlEDPHK1343yWRvdGpU+SXTb+uD5ymnp1HQDnxYkZrKCKVIuPw7A/omBdTz2uNaY/fXHyxmO2WlhCcfvDUqk8XGHUxG8pEmvzscsyV8/LCkTgXOjo8mTwzpwI3Ggyz5SQClro2AkP3ZhcCzTJzbXkjtoPbHWtzu5Fv1yEZ7CMiqYeU9lVQHO/P0I1OPsOaZ0B0fe7Hc9wh78FfZXQTCuugz8xKpXvlmZtEAx/yL0Sz0jTUzIQYnmZ6EGirn2ksqxs4muD3AzD8xX/k1usaZFbKBhop10UoIwhqLgG64ziM5DYZrlvJPrfqMkvZXtLygHyqj49m5r+MNZ8LlIyLYhdWIiU9+Kq2CUkhmDzllU+jKUU+3h4xCPYnvSDs/IP1CCj7tFR706es3mOpLFii1EsBXNEph5a154upYTYUrIkwMAvJ3Q4ZxpY/Z3EoeYH+AAU5sguXyb8JLeEihDTEeMiMjJ+hukzfMKD01EqLo1plxNL/TsMikBxQPFJjhIluFvQOa1x3tdWSJn45k8UDZz29sZfU2Nuk1M1pVe3tIBGU+oDkoNxX5e0xgWc9UZE1xYXzoWin2tX/8bfD/C3p5lXsOI+ivBPqN1HpwIarUl07VslIjPSmwaC7bmHH7sdmxeDblAMOAx+aPcOZNkn/laPta6y4qSp9X2rucZ0ZPFsYRbDA+E4hNVShM2n15OD/5JEl1oKPpokLRg33JTdZOkrPUR/xz7ywi3g6gU8ECVLt9Ux4Kg5VbRD/BdzJ2D4zTZJPnIR3K4l0Cpt0t2j3SnZ/uopEiJRHFksVoT00yeH3GRLgA+4Gj3sgfz3H9T9N39buJczi1qYetepTeSitZqbvcWr1oEUqbw== X-Microsoft-Exchange-Diagnostics: 1; VI1PR0202MB2557; 6:8iXctzpxXdbwGl5coZCiacGHdi2wM7xS+miJCn46tPNv9QoU1kOzW9pe1Cbn+uO3tg3zoBnGLOk0zOPQlBiw3JyG/5NOrBOvOauLopH0y1ZkqyFNZHEdX074SflMPUAU0lSAzkAokqwAgL6bjJ2429DO6j4y83z47jKwhWwxxdiBnecuwcJrY353KCk9sWF4Blz3CZW5gCFkP640hj9xG9tsAydFHb5e7fmnMwN3nAce3jDQnZPQRT+dsOcbNou9MHXW/x7uZ7guhz5/cNkW8Se2BZECJlsUOF06NTwBWLUJnMzQuasb0JFWAR0KhghfCbnCpYxgKlMEpA+X/aoMWA==; 5:Oy7gFmp5pvJHPzI1Q84PrE989VjT6l9EOsjW9lHg/xKvWtrJSPNG0xa4IKnOdnsOExkCGGzc3XI4r95Ud++ASPzTG92jUcQaOw02iiUVY+j70dccJGlryhK1iaIDoF92aZGSJwBDRZz7CDerXt+V4A==; 24:SzqUsRR73t6AYJAM8TULVCpGsYkMhrCftQSOZtUSk4j1qmvoBKelL9lPUWnkkFIaK3U4wJakNl82sVMl1atS5gDyzyVekVCBf6fl0MPNnYY=; 7:7eHTBDQe5D2+cFBcCaQiPrPtSLTi6n6cZb7xOEl9RZAVfGtm3jKdVq99K/w83yRK5VVYKmFpnowPO0kbSJp8Tk4aBHyA6deSkK4ivWDc1Ku11AtP4sYoOXTZECpnPYk+G2en53gvd9gjekuhpcM47bdQOMNQeNlYSGz4EDlK/vY/Xs7RXYQhG9n/g9ejmwknMvtBRdE8xvVxLFKILKqIN4LsjLQ+3o6fChGcVMQ+ZRE= SpamDiagnosticOutput: 1:99 SpamDiagnosticMetadata: NSPM X-OriginatorOrg: axentia.se X-MS-Exchange-CrossTenant-OriginalArrivalTime: 08 Sep 2017 15:46:24.9166 (UTC) X-MS-Exchange-CrossTenant-FromEntityHeader: Hosted X-MS-Exchange-Transport-CrossTenantHeadersStamped: VI1PR0202MB2557 Sender: linux-kernel-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org From: Stephen Boyd Sometimes drivers only use muxes under certain scenarios. For example, the chipidea usb controller may be connected to a usb switch on some platforms, and connected directly to a usb port on others. The driver won't know one way or the other though, so add a mux_control_get_optional() API that allows the driver to differentiate errors getting the mux from there not being a mux for the driver to use at all. --- Documentation/driver-model/devres.txt | 1 + drivers/mux/core.c | 104 +++++++++++++++++++++++++++------- include/linux/mux/consumer.h | 4 ++ 3 files changed, 89 insertions(+), 20 deletions(-) I haven't tested this patch, and hence I have not signed it and I also removed the sign-off from Stephen... Cheers, peda -- 2.11.0 Signed-off-by: Stephen Boyd diff --git a/Documentation/driver-model/devres.txt b/Documentation/driver-model/devres.txt index 30e04f7a690d..4fdd3e63ff8b 100644 --- a/Documentation/driver-model/devres.txt +++ b/Documentation/driver-model/devres.txt @@ -342,6 +342,7 @@ MUX devm_mux_chip_alloc() devm_mux_chip_register() devm_mux_control_get() + devm_mux_control_get_optional() PER-CPU MEM devm_alloc_percpu() diff --git a/drivers/mux/core.c b/drivers/mux/core.c index 2260063b0ea8..2eb234300669 100644 --- a/drivers/mux/core.c +++ b/drivers/mux/core.c @@ -289,6 +289,9 @@ EXPORT_SYMBOL_GPL(devm_mux_chip_register); */ unsigned int mux_control_states(struct mux_control *mux) { + if (!mux) + return 0; + return mux->states; } EXPORT_SYMBOL_GPL(mux_control_states); @@ -338,6 +341,9 @@ int mux_control_select(struct mux_control *mux, unsigned int state) { int ret; + if (!mux) + return 0; + ret = down_killable(&mux->lock); if (ret < 0) return ret; @@ -370,6 +376,9 @@ int mux_control_try_select(struct mux_control *mux, unsigned int state) { int ret; + if (!mux) + return 0; + if (down_trylock(&mux->lock)) return -EBUSY; @@ -398,6 +407,9 @@ int mux_control_deselect(struct mux_control *mux) { int ret = 0; + if (!mux) + return 0; + if (mux->idle_state != MUX_IDLE_AS_IS && mux->idle_state != mux->cached_state) ret = mux_control_set(mux, mux->idle_state); @@ -422,14 +434,8 @@ static struct mux_chip *of_find_mux_chip_by_node(struct device_node *np) return dev ? to_mux_chip(dev) : NULL; } -/** - * mux_control_get() - Get the mux-control for a device. - * @dev: The device that needs a mux-control. - * @mux_name: The name identifying the mux-control. - * - * Return: A pointer to the mux-control, or an ERR_PTR with a negative errno. - */ -struct mux_control *mux_control_get(struct device *dev, const char *mux_name) +static struct mux_control * +__mux_control_get(struct device *dev, const char *mux_name, bool optional) { struct device_node *np = dev->of_node; struct of_phandle_args args; @@ -441,16 +447,22 @@ struct mux_control *mux_control_get(struct device *dev, const char *mux_name) if (mux_name) { index = of_property_match_string(np, "mux-control-names", mux_name); + if ((index == -EINVAL || index == -ENODATA) && optional) + return NULL; if (index < 0) { dev_err(dev, "mux controller '%s' not found\n", mux_name); return ERR_PTR(index); } + /* OF does point to a mux, so it's no longer optional */ + optional = false; } ret = of_parse_phandle_with_args(np, "mux-controls", "#mux-control-cells", index, &args); + if (ret == -ENOENT && optional) + return NULL; if (ret) { dev_err(dev, "%pOF: failed to get mux-control %s(%i)\n", np, mux_name ?: "", index); @@ -482,9 +494,36 @@ struct mux_control *mux_control_get(struct device *dev, const char *mux_name) get_device(&mux_chip->dev); return &mux_chip->mux[controller]; } + +/** + * mux_control_get() - Get the mux-control for a device. + * @dev: The device that needs a mux-control. + * @mux_name: The name identifying the mux-control. + * + * Return: A pointer to the mux-control, or an ERR_PTR with a negative errno. + */ +struct mux_control *mux_control_get(struct device *dev, const char *mux_name) +{ + return __mux_control_get(dev, mux_name, false); +} EXPORT_SYMBOL_GPL(mux_control_get); /** + * mux_control_get_optional() - Get the optional mux-control for a device. + * @dev: The device that needs a mux-control. + * @mux_name: The name identifying the mux-control. + * + * Return: NULL if no mux with the provided name is found, a pointer to + * the named mux-control or an ERR_PTR with a negative errno. + */ +struct mux_control * +mux_control_get_optional(struct device *dev, const char *mux_name) +{ + return __mux_control_get(dev, mux_name, true); +} +EXPORT_SYMBOL_GPL(mux_control_get_optional); + +/** * mux_control_put() - Put away the mux-control for good. * @mux: The mux-control to put away. * @@ -492,6 +531,9 @@ EXPORT_SYMBOL_GPL(mux_control_get); */ void mux_control_put(struct mux_control *mux) { + if (!mux) + return; + put_device(&mux->chip->dev); } EXPORT_SYMBOL_GPL(mux_control_put); @@ -503,16 +545,8 @@ static void devm_mux_control_release(struct device *dev, void *res) mux_control_put(mux); } -/** - * devm_mux_control_get() - Get the mux-control for a device, with resource - * management. - * @dev: The device that needs a mux-control. - * @mux_name: The name identifying the mux-control. - * - * Return: Pointer to the mux-control, or an ERR_PTR with a negative errno. - */ -struct mux_control *devm_mux_control_get(struct device *dev, - const char *mux_name) +static struct mux_control * +__devm_mux_control_get(struct device *dev, const char *mux_name, bool optional) { struct mux_control **ptr, *mux; @@ -520,8 +554,8 @@ struct mux_control *devm_mux_control_get(struct device *dev, if (!ptr) return ERR_PTR(-ENOMEM); - mux = mux_control_get(dev, mux_name); - if (IS_ERR(mux)) { + mux = __mux_control_get(dev, mux_name, optional); + if (IS_ERR_OR_NULL(mux)) { devres_free(ptr); return mux; } @@ -531,8 +565,38 @@ struct mux_control *devm_mux_control_get(struct device *dev, return mux; } + +/** + * devm_mux_control_get() - Get the mux-control for a device, with resource + * management. + * @dev: The device that needs a mux-control. + * @mux_name: The name identifying the mux-control. + * + * Return: Pointer to the mux-control, or an ERR_PTR with a negative errno. + */ +struct mux_control * +devm_mux_control_get(struct device *dev, const char *mux_name) +{ + return __devm_mux_control_get(dev, mux_name, false); +} EXPORT_SYMBOL_GPL(devm_mux_control_get); +/** + * devm_mux_control_get_optional() - Get the optional mux-control for a device, + * with resource management. + * @dev: The device that needs a mux-control. + * @mux_name: The name identifying the mux-control. + * + * Return: NULL if no mux with the provided name is found, a pointer to + * the named mux-control or an ERR_PTR with a negative errno. + */ +struct mux_control * +devm_mux_control_get_optional(struct device *dev, const char *mux_name) +{ + return __devm_mux_control_get(dev, mux_name, true); +} +EXPORT_SYMBOL_GPL(devm_mux_control_get_optional); + /* * Using subsys_initcall instead of module_init here to try to ensure - for * the non-modular case - that the subsystem is initialized when mux consumers diff --git a/include/linux/mux/consumer.h b/include/linux/mux/consumer.h index ea96d4c82be7..fc98547bf494 100644 --- a/include/linux/mux/consumer.h +++ b/include/linux/mux/consumer.h @@ -26,9 +26,13 @@ int __must_check mux_control_try_select(struct mux_control *mux, int mux_control_deselect(struct mux_control *mux); struct mux_control *mux_control_get(struct device *dev, const char *mux_name); +struct mux_control *mux_control_get_optional(struct device *dev, + const char *mux_name); void mux_control_put(struct mux_control *mux); struct mux_control *devm_mux_control_get(struct device *dev, const char *mux_name); +struct mux_control *devm_mux_control_get_optional(struct device *dev, + const char *mux_name); #endif /* _LINUX_MUX_CONSUMER_H */