Received: by 2002:ac0:a5b6:0:0:0:0:0 with SMTP id m51-v6csp716679imm; Thu, 31 May 2018 08:12:24 -0700 (PDT) X-Google-Smtp-Source: ADUXVKIsKObH30Q9i9ByiqCbmCS4WYzcnKkgTTOWAkpgXeJ6LIvmbhvr4Vvj2oG9tvtxouVHy8Sg X-Received: by 2002:a63:6ac6:: with SMTP id f189-v6mr5922102pgc.308.1527779544431; Thu, 31 May 2018 08:12:24 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1527779544; cv=none; d=google.com; s=arc-20160816; b=hwpOMWgGV125kjII7Z+Iwsbxee+aYCr+vZmmQG6a8hxxcb/64fvqHRd3MbKTQ3T/s8 pDaF4a5mzqdASCFLDXYKZpETRRHYgyGlTyBycHfJgbKZmZw8KHK+13B6S7Y+a3cHM+Z4 H9kYQ2n146WbphYsoqhF4sCYt3sPtTlj4WZyIxgojKVVT9hBX5e6pyFzC6vrbG0J28td /mI0rWrVphmYOslw8hLBXHndl4vKyTLZnhE3S3f5g9AKXYIN+qGmUoExhrjaaMrzE6hv iD5zP5sIak2LmIarmoUbs6ajWEaseYexTpEvfLYmnGK+2leLFZphMABnNcjf+X7Og+ha Kn9g== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:sender:date:subject:user-agent:message-id :references:cc:in-reply-to:from:to:content-transfer-encoding :mime-version:dkim-signature:arc-authentication-results; bh=JH1UP4ndZX/2MTBi1svtqUcDSpCv9l4FWtyayyuV1e8=; b=mNYUYezaP0Pw7FUgMq0PbsorxEFkjKfPw7fZmHxKm6i81HYMWfnULOo9umkHy/Ak7I /IUEkMKZayypbQcuh6dqg0R3DFKVvc4xXumuw4USPQ30/OlcnRG/2zlzP7x2QkBB4BiF f5n4DPzMzUoE1laZLqD3BEwaVfO0nl9U71MnlH5Xap5e14J8EcEON82Z7cEDf/0SOtoF EdZD15QyXpJy50zyKN6ZBUdimRcoIV/0BcM3HTkbAiBPZlKEn+PxRKKbsc70XCNhjBiH jxY0RUxAA1tU16iDf/OCLO33TYi1LvdIsiiZ5bFekr9jiL0MDEbQmkW/KQ7XWCzekd3j vaEA== ARC-Authentication-Results: i=1; mx.google.com; dkim=pass header.i=@kernel.org header.s=default header.b=HuuwIYd6; 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=kernel.org Return-Path: Received: from vger.kernel.org (vger.kernel.org. [209.132.180.67]) by mx.google.com with ESMTP id e5-v6si6004562pgp.105.2018.05.31.08.12.10; Thu, 31 May 2018 08:12:24 -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=@kernel.org header.s=default header.b=HuuwIYd6; 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=kernel.org Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1755528AbeEaPKn (ORCPT + 99 others); Thu, 31 May 2018 11:10:43 -0400 Received: from mail.kernel.org ([198.145.29.99]:46156 "EHLO mail.kernel.org" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1755484AbeEaPKl (ORCPT ); Thu, 31 May 2018 11:10:41 -0400 Received: from localhost (unknown [104.132.1.75]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by mail.kernel.org (Postfix) with ESMTPSA id 7A06C2087D; Thu, 31 May 2018 15:10:40 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=kernel.org; s=default; t=1527779440; bh=dd+CxCyeYMoEa2aEGrf8DY0RMy+V73C3tLph1+cSwkA=; h=To:From:In-Reply-To:Cc:References:Subject:Date:From; b=HuuwIYd6cfr6ABZmQ60aa6eIpOQFLiJ8kMJfhiogvmZY3+X3ikEqsr4u+jQVY7tl/ jJ/MqWRPJIgUTmkqueAmkUieyWd3hFxFcTFuL9jDsUg7y23pqarMxj2NPcZ4+enVod J/uJx9MbJzPWGTSdo3MMvju1550vbwkzt5aB69Sg= Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable To: Matti Vaittinen , broonie@kernel.org, lee.jones@linaro.org, lgirdwood@gmail.com, mark.rutland@arm.com, mazziesaccount@gmail.com, mturquette@baylibre.com, robh+dt@kernel.org From: Stephen Boyd In-Reply-To: <3d9d7239331c30826a237ae55db28d918155d504.1527669443.git.matti.vaittinen@fi.rohmeurope.com> Cc: linux-clk@vger.kernel.org, devicetree@vger.kernel.org, linux-kernel@vger.kernel.org, mikko.mutanen@fi.rohmeurope.com, heikki.haikola@fi.rohmeurope.com References: <3d9d7239331c30826a237ae55db28d918155d504.1527669443.git.matti.vaittinen@fi.rohmeurope.com> Message-ID: <152777943977.144038.10971658990200651749@swboyd.mtv.corp.google.com> User-Agent: alot/0.7 Subject: Re: [PATCH v4 5/6] clk: bd71837: Add driver for BD71837 PMIC clock Date: Thu, 31 May 2018 08:10:39 -0700 Sender: linux-kernel-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Quoting Matti Vaittinen (2018-05-30 01:43:19) > diff --git a/drivers/clk/Kconfig b/drivers/clk/Kconfig > index 41492e980ef4..4b045699bb5e 100644 > --- a/drivers/clk/Kconfig > +++ b/drivers/clk/Kconfig > @@ -279,6 +279,15 @@ config COMMON_CLK_STM32H7 > ---help--- > Support for stm32h7 SoC family clocks > = > +config COMMON_CLK_BD71837 > + tristate "Clock driver for ROHM BD71837 PMIC MFD" > + depends on MFD_BD71837 > + depends on I2C=3Dy Why depend on I2C=3Dy? > + depends on OF Why depend on OF? > + help > + This driver supports ROHM BD71837 PMIC clock. > + > + > source "drivers/clk/bcm/Kconfig" > source "drivers/clk/hisilicon/Kconfig" > source "drivers/clk/imgtec/Kconfig" > diff --git a/drivers/clk/clk-bd71837.c b/drivers/clk/clk-bd71837.c > new file mode 100644 > index 000000000000..91456d1077ac > --- /dev/null > +++ b/drivers/clk/clk-bd71837.c > @@ -0,0 +1,151 @@ > +// SPDX-License-Identifier: GPL-2.0 > +// Copyright (C) 2018 ROHM Semiconductors > +// bd71837.c -- ROHM BD71837MWV clock driver > + > +#include > +#include > +#include > +#include > +#include > +#include > +#include > +#include > +#include > + > +static int bd71837_clk_enable(struct clk_hw *hw); > +static void bd71837_clk_disable(struct clk_hw *hw); > +static int bd71837_clk_is_enabled(struct clk_hw *hw); > + > +struct bd71837_clk { > + struct clk_hw hw; > + uint8_t reg; > + uint8_t mask; > + unsigned long rate; > + struct platform_device *pdev; > + struct bd71837 *mfd; > +}; > + > +static unsigned long bd71837_clk_recalc_rate(struct clk_hw *hw, > + unsigned long parent_rate); > + > +static const struct clk_ops bd71837_clk_ops =3D { > + .recalc_rate =3D &bd71837_clk_recalc_rate, > + .prepare =3D &bd71837_clk_enable, > + .unprepare =3D &bd71837_clk_disable, > + .is_prepared =3D &bd71837_clk_is_enabled, > +}; Move this structure after the function definitions. And drop the forward declared functions. > + > +static int bd71837_clk_set(struct clk_hw *hw, int status) > +{ > + struct bd71837_clk *c =3D container_of(hw, struct bd71837_clk, hw= ); > + > + return bd71837_update_bits(c->mfd, c->reg, c->mask, status); > +} > + > +static void bd71837_clk_disable(struct clk_hw *hw) > +{ > + int rv; > + struct bd71837_clk *c =3D container_of(hw, struct bd71837_clk, hw= ); > + > + rv =3D bd71837_clk_set(hw, 0); > + if (rv) > + dev_err(&c->pdev->dev, "Failed to disable 32K clk (%d)\n"= , rv); Why is a disable error message more important than an enable error message? Please drop this message and rely on callers to indicate if enabling their clk didn't work for some reason. > +} > + > +static int bd71837_clk_enable(struct clk_hw *hw) > +{ > + return bd71837_clk_set(hw, 1); > +} > + > +static int bd71837_clk_is_enabled(struct clk_hw *hw) > +{ > + struct bd71837_clk *c =3D container_of(hw, struct bd71837_clk, hw= ); > + > + return c->mask & bd71837_reg_read(c->mfd, c->reg); Please put this on two or more lines so we know what the type of bd71837_reg_read() returns: u32 reg =3D bd71837_reg_read(....) return c->mask & reg; > +} > + > +static unsigned long bd71837_clk_recalc_rate(struct clk_hw *hw, > + unsigned long parent_rate) > +{ > + struct bd71837_clk *c =3D container_of(hw, struct bd71837_clk, hw= ); > + > + return c->rate; Recalc rate should read the hardware instead of returning a cached rate unless it can't actually read hardware. > +} > + > +static int bd71837_clk_probe(struct platform_device *pdev) > +{ > + struct bd71837_clk *c; > + int rval =3D -ENOMEM; > + struct bd71837 *mfd =3D dev_get_drvdata(pdev->dev.parent); > + const char *errstr =3D "memory allocation for bd71837 data failed= "; We don't need allocation error messages. > + struct clk_init_data init =3D { > + .name =3D "bd71837-32k-out", > + .ops =3D &bd71837_clk_ops, > + }; > + > + c =3D kzalloc(sizeof(struct bd71837_clk), GFP_KERNEL); Use sizeof(*c) instead so we don't have to worry about type mismatches. > + if (!c) > + goto err_out; > + > + c->reg =3D BD71837_REG_OUT32K; > + c->mask =3D BD71837_OUT32K_EN; > + c->rate =3D BD71837_CLK_RATE; Is the plan to have more clks supported by this driver in the future? Because right now it seems to make a structure up and then hardcode the members for a single clk so I'm not sure why those registers aren't just hardcoded in the clk_ops functions that use them. > + c->mfd =3D mfd; > + c->pdev =3D pdev; > + > + if (pdev->dev.of_node) If there isn't an of_node it would be NULL, and then calling the function below would cause it to not update the init name? Seems like it could be called unconditionally. > + of_property_read_string_index(pdev->dev.of_node, > + "clock-output-names", 0, > + &init.name); > + > + c->hw.init =3D &init; > + > + errstr =3D "failed to register 32K clk"; The 'errstr' thing is not standard. Please just call dev_err() directly with the string you want to print. And consider not printing anything at all. > + rval =3D clk_hw_register(&pdev->dev, &c->hw); > + if (rval) > + goto err_free; > + > + errstr =3D "failed to register clkdev for bd71837"; > + rval =3D clk_hw_register_clkdev(&c->hw, init.name, NULL); Are you using the clkdev lookup? Or this is just added for backup purposes? If this is a mostly DT driver then please drop this part of the patch and rely on of_clk_hw_add_provider() to handle the lookup instead. > + if (rval) > + goto err_unregister; > + > + platform_set_drvdata(pdev, c); > + dev_dbg(&pdev->dev, "bd71837_clk successfully probed\n"); There's a pr_debug() in really_probe() for this. > + > + return 0; > + > +err_unregister: > + clk_hw_unregister(&c->hw); > +err_free: > + kfree(c); > +err_out: > + dev_err(&pdev->dev, "%s\n", errstr); > + return rval; > +} > + > +static int bd71837_clk_remove(struct platform_device *pdev) > +{ > + struct bd71837_clk *c =3D platform_get_drvdata(pdev); > + > + if (c) { > + clk_hw_unregister(&c->hw); Use devm to register clks. > + kfree(c); and devm_kzalloc() > + platform_set_drvdata(pdev, NULL); This doesn't need to be done. Drop it. > + } > + return 0; > +} > +