linux/drivers/clk/qcom/clk-rcg.h
<<
>>
Prefs
   1/* SPDX-License-Identifier: GPL-2.0 */
   2/* Copyright (c) 2013, 2018, The Linux Foundation. All rights reserved. */
   3
   4#ifndef __QCOM_CLK_RCG_H__
   5#define __QCOM_CLK_RCG_H__
   6
   7#include <linux/clk-provider.h>
   8#include "clk-regmap.h"
   9
  10#define F(f, s, h, m, n) { (f), (s), (2 * (h) - 1), (m), (n) }
  11
  12struct freq_tbl {
  13        unsigned long freq;
  14        u8 src;
  15        u8 pre_div;
  16        u16 m;
  17        u16 n;
  18};
  19
  20/**
  21 * struct mn - M/N:D counter
  22 * @mnctr_en_bit: bit to enable mn counter
  23 * @mnctr_reset_bit: bit to assert mn counter reset
  24 * @mnctr_mode_shift: lowest bit of mn counter mode field
  25 * @n_val_shift: lowest bit of n value field
  26 * @m_val_shift: lowest bit of m value field
  27 * @width: number of bits in m/n/d values
  28 * @reset_in_cc: true if the mnctr_reset_bit is in the CC register
  29 */
  30struct mn {
  31        u8              mnctr_en_bit;
  32        u8              mnctr_reset_bit;
  33        u8              mnctr_mode_shift;
  34#define MNCTR_MODE_DUAL 0x2
  35#define MNCTR_MODE_MASK 0x3
  36        u8              n_val_shift;
  37        u8              m_val_shift;
  38        u8              width;
  39        bool            reset_in_cc;
  40};
  41
  42/**
  43 * struct pre_div - pre-divider
  44 * @pre_div_shift: lowest bit of pre divider field
  45 * @pre_div_width: number of bits in predivider
  46 */
  47struct pre_div {
  48        u8              pre_div_shift;
  49        u8              pre_div_width;
  50};
  51
  52/**
  53 * struct src_sel - source selector
  54 * @src_sel_shift: lowest bit of source selection field
  55 * @parent_map: map from software's parent index to hardware's src_sel field
  56 */
  57struct src_sel {
  58        u8              src_sel_shift;
  59#define SRC_SEL_MASK    0x7
  60        const struct parent_map *parent_map;
  61};
  62
  63/**
  64 * struct clk_rcg - root clock generator
  65 *
  66 * @ns_reg: NS register
  67 * @md_reg: MD register
  68 * @mn: mn counter
  69 * @p: pre divider
  70 * @s: source selector
  71 * @freq_tbl: frequency table
  72 * @clkr: regmap clock handle
  73 * @lock: register lock
  74 */
  75struct clk_rcg {
  76        u32             ns_reg;
  77        u32             md_reg;
  78
  79        struct mn       mn;
  80        struct pre_div  p;
  81        struct src_sel  s;
  82
  83        const struct freq_tbl   *freq_tbl;
  84
  85        struct clk_regmap       clkr;
  86};
  87
  88extern const struct clk_ops clk_rcg_ops;
  89extern const struct clk_ops clk_rcg_bypass_ops;
  90extern const struct clk_ops clk_rcg_bypass2_ops;
  91extern const struct clk_ops clk_rcg_pixel_ops;
  92extern const struct clk_ops clk_rcg_esc_ops;
  93extern const struct clk_ops clk_rcg_lcc_ops;
  94
  95#define to_clk_rcg(_hw) container_of(to_clk_regmap(_hw), struct clk_rcg, clkr)
  96
  97/**
  98 * struct clk_dyn_rcg - root clock generator with glitch free mux
  99 *
 100 * @mux_sel_bit: bit to switch glitch free mux
 101 * @ns_reg: NS0 and NS1 register
 102 * @md_reg: MD0 and MD1 register
 103 * @bank_reg: register to XOR @mux_sel_bit into to switch glitch free mux
 104 * @mn: mn counter (banked)
 105 * @s: source selector (banked)
 106 * @freq_tbl: frequency table
 107 * @clkr: regmap clock handle
 108 * @lock: register lock
 109 */
 110struct clk_dyn_rcg {
 111        u32     ns_reg[2];
 112        u32     md_reg[2];
 113        u32     bank_reg;
 114
 115        u8      mux_sel_bit;
 116
 117        struct mn       mn[2];
 118        struct pre_div  p[2];
 119        struct src_sel  s[2];
 120
 121        const struct freq_tbl *freq_tbl;
 122
 123        struct clk_regmap clkr;
 124};
 125
 126extern const struct clk_ops clk_dyn_rcg_ops;
 127
 128#define to_clk_dyn_rcg(_hw) \
 129        container_of(to_clk_regmap(_hw), struct clk_dyn_rcg, clkr)
 130
 131/**
 132 * struct clk_rcg2 - root clock generator
 133 *
 134 * @cmd_rcgr: corresponds to *_CMD_RCGR
 135 * @mnd_width: number of bits in m/n/d values
 136 * @hid_width: number of bits in half integer divider
 137 * @safe_src_index: safe src index value
 138 * @parent_map: map from software's parent index to hardware's src_sel field
 139 * @freq_tbl: frequency table
 140 * @clkr: regmap clock handle
 141 * @cfg_off: defines the cfg register offset from the CMD_RCGR + CFG_REG
 142 */
 143struct clk_rcg2 {
 144        u32                     cmd_rcgr;
 145        u8                      mnd_width;
 146        u8                      hid_width;
 147        u8                      safe_src_index;
 148        const struct parent_map *parent_map;
 149        const struct freq_tbl   *freq_tbl;
 150        struct clk_regmap       clkr;
 151        u8                      cfg_off;
 152};
 153
 154#define to_clk_rcg2(_hw) container_of(to_clk_regmap(_hw), struct clk_rcg2, clkr)
 155
 156struct clk_rcg2_gfx3d {
 157        u8 div;
 158        struct clk_rcg2 rcg;
 159        struct clk_hw **hws;
 160};
 161
 162#define to_clk_rcg2_gfx3d(_hw) \
 163        container_of(to_clk_rcg2(_hw), struct clk_rcg2_gfx3d, rcg)
 164
 165extern const struct clk_ops clk_rcg2_ops;
 166extern const struct clk_ops clk_rcg2_floor_ops;
 167extern const struct clk_ops clk_edp_pixel_ops;
 168extern const struct clk_ops clk_byte_ops;
 169extern const struct clk_ops clk_byte2_ops;
 170extern const struct clk_ops clk_pixel_ops;
 171extern const struct clk_ops clk_gfx3d_ops;
 172extern const struct clk_ops clk_rcg2_shared_ops;
 173extern const struct clk_ops clk_dp_ops;
 174
 175struct clk_rcg_dfs_data {
 176        struct clk_rcg2 *rcg;
 177        struct clk_init_data *init;
 178};
 179
 180#define DEFINE_RCG_DFS(r) \
 181        { .rcg = &r, .init = &r##_init }
 182
 183extern int qcom_cc_register_rcg_dfs(struct regmap *regmap,
 184                                    const struct clk_rcg_dfs_data *rcgs,
 185                                    size_t len);
 186#endif
 187