summaryrefslogtreecommitdiffstats
path: root/drivers/clk
diff options
context:
space:
mode:
authorSean Anderson <sean.anderson@seco.com>2021-08-09 18:38:13 -0400
committerStephen Boyd <sboyd@kernel.org>2021-08-28 23:46:21 -0700
commitd83e561d43bc71e5404e277b0263774ecd1d1f40 (patch)
tree218e57eb558ee4bfd2596092a7d5a912e8c06672 /drivers/clk
parent2ef162548a53085499c08485228daa968d66dc5a (diff)
downloadlinux-d83e561d43bc71e5404e277b0263774ecd1d1f40.tar.bz2
clk: vc5: Add properties for configuring SD/OE behavior
The SD/OE pin may be configured to enable output when high or low, and to shutdown the device when high. This behavior is controller by the SH and SP bits of the Primary Source and Shutdown Register (and to a lesser extent the OS and OE bits). By default, both bits are 0 (unless set by OTP memory), but they may need to be configured differently, depending on the external circuitry controlling the SD/OE pin. Signed-off-by: Sean Anderson <sean.anderson@seco.com> Link: https://lore.kernel.org/r/20210809223813.3766204-3-sean.anderson@seco.com Reviewed-by: Geert Uytterhoeven <geert+renesas@glider.be> Signed-off-by: Stephen Boyd <sboyd@kernel.org>
Diffstat (limited to 'drivers/clk')
-rw-r--r--drivers/clk/clk-versaclock5.c24
1 files changed, 24 insertions, 0 deletions
diff --git a/drivers/clk/clk-versaclock5.c b/drivers/clk/clk-versaclock5.c
index a430128a4573..c6d3b1ab3d55 100644
--- a/drivers/clk/clk-versaclock5.c
+++ b/drivers/clk/clk-versaclock5.c
@@ -907,6 +907,7 @@ static const struct of_device_id clk_vc5_of_match[];
static int vc5_probe(struct i2c_client *client, const struct i2c_device_id *id)
{
+ unsigned int oe, sd, src_mask = 0, src_val = 0;
struct vc5_driver_data *vc5;
struct clk_init_data init;
const char *parent_names[2];
@@ -934,6 +935,29 @@ static int vc5_probe(struct i2c_client *client, const struct i2c_device_id *id)
return dev_err_probe(&client->dev, PTR_ERR(vc5->regmap),
"failed to allocate register map\n");
+ ret = of_property_read_u32(client->dev.of_node, "idt,shutdown", &sd);
+ if (!ret) {
+ src_mask |= VC5_PRIM_SRC_SHDN_EN_GBL_SHDN;
+ if (sd)
+ src_val |= VC5_PRIM_SRC_SHDN_EN_GBL_SHDN;
+ } else if (ret != -EINVAL) {
+ return dev_err_probe(&client->dev, ret,
+ "could not read idt,shutdown\n");
+ }
+
+ ret = of_property_read_u32(client->dev.of_node,
+ "idt,output-enable-active", &oe);
+ if (!ret) {
+ src_mask |= VC5_PRIM_SRC_SHDN_SP;
+ if (oe)
+ src_val |= VC5_PRIM_SRC_SHDN_SP;
+ } else if (ret != -EINVAL) {
+ return dev_err_probe(&client->dev, ret,
+ "could not read idt,output-enable-active\n");
+ }
+
+ regmap_update_bits(vc5->regmap, VC5_PRIM_SRC_SHDN, src_mask, src_val);
+
/* Register clock input mux */
memset(&init, 0, sizeof(init));