root/drivers/clk/st/clkgen-mux.c

/* [<][>][^][v][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. clkgen_mux_get_parents
  2. st_of_clkgen_mux_setup
  3. st_of_clkgen_a9_mux_setup

   1 // SPDX-License-Identifier: GPL-2.0-or-later
   2 /*
   3  * clkgen-mux.c: ST GEN-MUX Clock driver
   4  *
   5  * Copyright (C) 2014 STMicroelectronics (R&D) Limited
   6  *
   7  * Authors: Stephen Gallimore <stephen.gallimore@st.com>
   8  *          Pankaj Dev <pankaj.dev@st.com>
   9  */
  10 
  11 #include <linux/slab.h>
  12 #include <linux/io.h>
  13 #include <linux/of_address.h>
  14 #include <linux/clk.h>
  15 #include <linux/clk-provider.h>
  16 #include "clkgen.h"
  17 
  18 static const char ** __init clkgen_mux_get_parents(struct device_node *np,
  19                                                        int *num_parents)
  20 {
  21         const char **parents;
  22         unsigned int nparents;
  23 
  24         nparents = of_clk_get_parent_count(np);
  25         if (WARN_ON(!nparents))
  26                 return ERR_PTR(-EINVAL);
  27 
  28         parents = kcalloc(nparents, sizeof(const char *), GFP_KERNEL);
  29         if (!parents)
  30                 return ERR_PTR(-ENOMEM);
  31 
  32         *num_parents = of_clk_parent_fill(np, parents, nparents);
  33         return parents;
  34 }
  35 
  36 struct clkgen_mux_data {
  37         u32 offset;
  38         u8 shift;
  39         u8 width;
  40         spinlock_t *lock;
  41         unsigned long clk_flags;
  42         u8 mux_flags;
  43 };
  44 
  45 static struct clkgen_mux_data stih407_a9_mux_data = {
  46         .offset = 0x1a4,
  47         .shift = 0,
  48         .width = 2,
  49         .lock = &clkgen_a9_lock,
  50 };
  51 
  52 static void __init st_of_clkgen_mux_setup(struct device_node *np,
  53                 struct clkgen_mux_data *data)
  54 {
  55         struct clk *clk;
  56         void __iomem *reg;
  57         const char **parents;
  58         int num_parents = 0;
  59 
  60         reg = of_iomap(np, 0);
  61         if (!reg) {
  62                 pr_err("%s: Failed to get base address\n", __func__);
  63                 return;
  64         }
  65 
  66         parents = clkgen_mux_get_parents(np, &num_parents);
  67         if (IS_ERR(parents)) {
  68                 pr_err("%s: Failed to get parents (%ld)\n",
  69                                 __func__, PTR_ERR(parents));
  70                 goto err_parents;
  71         }
  72 
  73         clk = clk_register_mux(NULL, np->name, parents, num_parents,
  74                                 data->clk_flags | CLK_SET_RATE_PARENT,
  75                                 reg + data->offset,
  76                                 data->shift, data->width, data->mux_flags,
  77                                 data->lock);
  78         if (IS_ERR(clk))
  79                 goto err;
  80 
  81         pr_debug("%s: parent %s rate %u\n",
  82                         __clk_get_name(clk),
  83                         __clk_get_name(clk_get_parent(clk)),
  84                         (unsigned int)clk_get_rate(clk));
  85 
  86         kfree(parents);
  87         of_clk_add_provider(np, of_clk_src_simple_get, clk);
  88         return;
  89 
  90 err:
  91         kfree(parents);
  92 err_parents:
  93         iounmap(reg);
  94 }
  95 
  96 static void __init st_of_clkgen_a9_mux_setup(struct device_node *np)
  97 {
  98         st_of_clkgen_mux_setup(np, &stih407_a9_mux_data);
  99 }
 100 CLK_OF_DECLARE(clkgen_a9mux, "st,stih407-clkgen-a9-mux",
 101                 st_of_clkgen_a9_mux_setup);

/* [<][>][^][v][top][bottom][index][help] */