uboot/arch/arm/include/asm/arch-tegra/clock.h
<<
>>
Prefs
   1/* SPDX-License-Identifier: GPL-2.0+ */
   2/*
   3 * Copyright (c) 2011 The Chromium OS Authors.
   4 */
   5
   6/* Tegra clock control functions */
   7
   8#ifndef _TEGRA_CLOCK_H_
   9#define _TEGRA_CLOCK_H_
  10
  11/* Set of oscillator frequencies supported in the internal API. */
  12enum clock_osc_freq {
  13        /* All in MHz, so 13_0 is 13.0MHz */
  14        CLOCK_OSC_FREQ_13_0,
  15        CLOCK_OSC_FREQ_19_2,
  16        CLOCK_OSC_FREQ_12_0,
  17        CLOCK_OSC_FREQ_26_0,
  18        CLOCK_OSC_FREQ_38_4,
  19        CLOCK_OSC_FREQ_48_0,
  20
  21        CLOCK_OSC_FREQ_COUNT,
  22};
  23
  24/*
  25 * Note that no Tegra clock register actually uses all of bits 31:28 as
  26 * the mux field. Rather, bits 30:28, 29:28, or 28 are used. However, in
  27 * those cases, nothing is stored in the bits about the mux field, so it's
  28 * safe to pretend that the mux field extends all the way to the end of the
  29 * register. As such, the U-Boot clock driver is currently a bit lazy, and
  30 * doesn't distinguish between 31:28, 30:28, 29:28 and 28; it just lumps
  31 * them all together and pretends they're all 31:28.
  32 */
  33enum {
  34        MASK_BITS_31_30,
  35        MASK_BITS_31_29,
  36        MASK_BITS_31_28,
  37};
  38
  39#include <asm/arch/clock-tables.h>
  40/* PLL stabilization delay in usec */
  41#define CLOCK_PLL_STABLE_DELAY_US 300
  42
  43/* return the current oscillator clock frequency */
  44enum clock_osc_freq clock_get_osc_freq(void);
  45
  46/* return the clk_m frequency */
  47unsigned int clk_m_get_rate(unsigned int parent_rate);
  48
  49/**
  50 * Start PLL using the provided configuration parameters.
  51 *
  52 * @param id    clock id
  53 * @param divm  input divider
  54 * @param divn  feedback divider
  55 * @param divp  post divider 2^n
  56 * @param cpcon charge pump setup control
  57 * @param lfcon loop filter setup control
  58 *
  59 * @returns monotonic time in us that the PLL will be stable
  60 */
  61unsigned long clock_start_pll(enum clock_id id, u32 divm, u32 divn,
  62                u32 divp, u32 cpcon, u32 lfcon);
  63
  64/**
  65 * Set PLL output frequency
  66 *
  67 * @param clkid clock id
  68 * @param pllout        pll output id
  69 * @param rate          desired output rate
  70 *
  71 * @return 0 if ok, -1 on error (invalid clock id or no suitable divider)
  72 */
  73int clock_set_pllout(enum clock_id clkid, enum pll_out_id pllout,
  74                unsigned rate);
  75
  76/**
  77 * Read low-level parameters of a PLL.
  78 *
  79 * @param id    clock id to read (note: USB is not supported)
  80 * @param divm  returns input divider
  81 * @param divn  returns feedback divider
  82 * @param divp  returns post divider 2^n
  83 * @param cpcon returns charge pump setup control
  84 * @param lfcon returns loop filter setup control
  85 *
  86 * @returns 0 if ok, -1 on error (invalid clock id)
  87 */
  88int clock_ll_read_pll(enum clock_id clkid, u32 *divm, u32 *divn,
  89                u32 *divp, u32 *cpcon, u32 *lfcon);
  90
  91/*
  92 * Enable a clock
  93 *
  94 * @param id    clock id
  95 */
  96void clock_enable(enum periph_id clkid);
  97
  98/*
  99 * Disable a clock
 100 *
 101 * @param id    clock id
 102 */
 103void clock_disable(enum periph_id clkid);
 104
 105/*
 106 * Set whether a clock is enabled or disabled.
 107 *
 108 * @param id            clock id
 109 * @param enable        1 to enable, 0 to disable
 110 */
 111void clock_set_enable(enum periph_id clkid, int enable);
 112
 113/**
 114 * Reset a peripheral. This puts it in reset, waits for a delay, then takes
 115 * it out of reset and waits for th delay again.
 116 *
 117 * @param periph_id     peripheral to reset
 118 * @param us_delay      time to delay in microseconds
 119 */
 120void reset_periph(enum periph_id periph_id, int us_delay);
 121
 122/**
 123 * Put a peripheral into or out of reset.
 124 *
 125 * @param periph_id     peripheral to reset
 126 * @param enable        1 to put into reset, 0 to take out of reset
 127 */
 128void reset_set_enable(enum periph_id periph_id, int enable);
 129
 130
 131/* CLK_RST_CONTROLLER_RST_CPU_CMPLX_SET/CLR_0 */
 132enum crc_reset_id {
 133        /* Things we can hold in reset for each CPU */
 134        crc_rst_cpu = 1,
 135        crc_rst_de = 1 << 4,    /* What is de? */
 136        crc_rst_watchdog = 1 << 8,
 137        crc_rst_debug = 1 << 12,
 138};
 139
 140/**
 141 * Put parts of the CPU complex into or out of reset.\
 142 *
 143 * @param cpu           cpu number (0 or 1 on Tegra2, 0-3 on Tegra3)
 144 * @param which         which parts of the complex to affect (OR of crc_reset_id)
 145 * @param reset         1 to assert reset, 0 to de-assert
 146 */
 147void reset_cmplx_set_enable(int cpu, int which, int reset);
 148
 149/**
 150 * Set the source for a peripheral clock. This plus the divisor sets the
 151 * clock rate. You need to look up the datasheet to see the meaning of the
 152 * source parameter as it changes for each peripheral.
 153 *
 154 * Warning: This function is only for use pre-relocation. Please use
 155 * clock_start_periph_pll() instead.
 156 *
 157 * @param periph_id     peripheral to adjust
 158 * @param source        source clock (0, 1, 2 or 3)
 159 */
 160void clock_ll_set_source(enum periph_id periph_id, unsigned source);
 161
 162/**
 163 * This function is similar to clock_ll_set_source() except that it can be
 164 * used for clocks with more than 2 mux bits.
 165 *
 166 * @param periph_id     peripheral to adjust
 167 * @param mux_bits      number of mux bits for the clock
 168 * @param source        source clock (0-15 depending on mux_bits)
 169 */
 170int clock_ll_set_source_bits(enum periph_id periph_id, int mux_bits,
 171                             unsigned source);
 172
 173/**
 174 * Set the source and divisor for a peripheral clock. This sets the
 175 * clock rate. You need to look up the datasheet to see the meaning of the
 176 * source parameter as it changes for each peripheral.
 177 *
 178 * Warning: This function is only for use pre-relocation. Please use
 179 * clock_start_periph_pll() instead.
 180 *
 181 * @param periph_id     peripheral to adjust
 182 * @param source        source clock (0, 1, 2 or 3)
 183 * @param divisor       divisor value to use
 184 */
 185void clock_ll_set_source_divisor(enum periph_id periph_id, unsigned source,
 186                unsigned divisor);
 187
 188/**
 189 * Returns the current parent clock ID of a given peripheral. This can be
 190 * useful in order to call clock_*_periph_*() from generic code that has no
 191 * specific knowledge of system-level clock tree structure.
 192 *
 193 * @param periph_id     peripheral to query
 194 * @return clock ID of the peripheral's current parent clock
 195 */
 196enum clock_id clock_get_periph_parent(enum periph_id periph_id);
 197
 198/**
 199 * Start a peripheral PLL clock at the given rate. This also resets the
 200 * peripheral.
 201 *
 202 * @param periph_id     peripheral to start
 203 * @param parent        PLL id of required parent clock
 204 * @param rate          Required clock rate in Hz
 205 * @return rate selected in Hz, or -1U if something went wrong
 206 */
 207unsigned clock_start_periph_pll(enum periph_id periph_id,
 208                enum clock_id parent, unsigned rate);
 209
 210/**
 211 * Returns the rate of a peripheral clock in Hz. Since the caller almost
 212 * certainly knows the parent clock (having just set it) we require that
 213 * this be passed in so we don't need to work it out.
 214 *
 215 * @param periph_id     peripheral to start
 216 * @param parent        PLL id of parent clock (used to calculate rate, you
 217 *                      must know this!)
 218 * @return clock rate of peripheral in Hz
 219 */
 220unsigned long clock_get_periph_rate(enum periph_id periph_id,
 221                enum clock_id parent);
 222
 223/**
 224 * Adjust peripheral PLL clock to the given rate. This does not reset the
 225 * peripheral. If a second stage divisor is not available, pass NULL for
 226 * extra_div. If it is available, then this parameter will return the
 227 * divisor selected (which will be a power of 2 from 1 to 256).
 228 *
 229 * @param periph_id     peripheral to start
 230 * @param parent        PLL id of required parent clock
 231 * @param rate          Required clock rate in Hz
 232 * @param extra_div     value for the second-stage divisor (NULL if one is
 233                        not available)
 234 * @return rate selected in Hz, or -1U if something went wrong
 235 */
 236unsigned clock_adjust_periph_pll_div(enum periph_id periph_id,
 237                enum clock_id parent, unsigned rate, int *extra_div);
 238
 239/**
 240 * Returns the clock rate of a specified clock, in Hz.
 241 *
 242 * @param parent        PLL id of clock to check
 243 * @return rate of clock in Hz
 244 */
 245unsigned clock_get_rate(enum clock_id clkid);
 246
 247/**
 248 * Start up a UART using low-level calls
 249 *
 250 * Prior to relocation clock_start_periph_pll() cannot be called. This
 251 * function provides a way to set up a UART using low-level calls which
 252 * do not require BSS.
 253 *
 254 * @param periph_id     Peripheral ID of UART to enable (e,g, PERIPH_ID_UART1)
 255 */
 256void clock_ll_start_uart(enum periph_id periph_id);
 257
 258/**
 259 * Decode a peripheral ID from a device tree node.
 260 *
 261 * This works by looking up the peripheral's 'clocks' node and reading out
 262 * the second cell, which is the clock number / peripheral ID.
 263 *
 264 * @param blob          FDT blob to use
 265 * @param node          Node to look at
 266 * @return peripheral ID, or PERIPH_ID_NONE if none
 267 */
 268int clock_decode_periph_id(struct udevice *dev);
 269
 270/**
 271 * Checks if the oscillator bypass is enabled (XOBP bit)
 272 *
 273 * @return 1 if bypass is enabled, 0 if not
 274 */
 275int clock_get_osc_bypass(void);
 276
 277/*
 278 * Checks that clocks are valid and prints a warning if not
 279 *
 280 * @return 0 if ok, -1 on error
 281 */
 282int clock_verify(void);
 283
 284/* Initialize the clocks */
 285void clock_init(void);
 286
 287/* Initialize the PLLs */
 288void clock_early_init(void);
 289
 290/* @return true if hardware indicates that clock_early_init() was called */
 291bool clock_early_init_done(void);
 292
 293/* Returns a pointer to the clock source register for a peripheral */
 294u32 *get_periph_source_reg(enum periph_id periph_id);
 295
 296/* Returns a pointer to the given 'simple' PLL */
 297struct clk_pll_simple *clock_get_simple_pll(enum clock_id clkid);
 298
 299/*
 300 * Given a peripheral ID, determine where the mux bits are in the peripheral
 301 * clock's register, the number of divider bits the clock has, and the SoC-
 302 * specific clock type.
 303 *
 304 * This is an internal API between the core Tegra clock code and the SoC-
 305 * specific clock code.
 306 *
 307 * @param periph_id     peripheral to query
 308 * @param mux_bits      Set to number of bits in mux register
 309 * @param divider_bits  Set to the relevant MASK_BITS_* value
 310 * @param type          Set to the SoC-specific clock type
 311 * @return 0 on success, -1 on error
 312 */
 313int get_periph_clock_info(enum periph_id periph_id, int *mux_bits,
 314                          int *divider_bits, int *type);
 315
 316/*
 317 * Given a peripheral ID and clock source mux value, determine the clock_id
 318 * of that peripheral's parent.
 319 *
 320 * This is an internal API between the core Tegra clock code and the SoC-
 321 * specific clock code.
 322 *
 323 * @param periph_id     peripheral to query
 324 * @param source        raw clock source mux value
 325 * @return the CLOCK_ID_* value @source represents
 326 */
 327enum clock_id get_periph_clock_id(enum periph_id periph_id, int source);
 328
 329/**
 330 * Given a peripheral ID and the required source clock, this returns which
 331 * value should be programmed into the source mux for that peripheral.
 332 *
 333 * There is special code here to handle the one source type with 5 sources.
 334 *
 335 * @param periph_id     peripheral to start
 336 * @param source        PLL id of required parent clock
 337 * @param mux_bits      Set to number of bits in mux register: 2 or 4
 338 * @param divider_bits  Set to number of divider bits (8 or 16)
 339 * @return mux value (0-4, or -1 if not found)
 340 */
 341int get_periph_clock_source(enum periph_id periph_id,
 342                enum clock_id parent, int *mux_bits, int *divider_bits);
 343
 344/*
 345 * Convert a device tree clock ID to our peripheral ID. They are mostly
 346 * the same but we are very cautious so we check that a valid clock ID is
 347 * provided.
 348 *
 349 * @param clk_id        Clock ID according to tegra30 device tree binding
 350 * @return peripheral ID, or PERIPH_ID_NONE if the clock ID is invalid
 351 */
 352enum periph_id clk_id_to_periph_id(int clk_id);
 353
 354/**
 355 * Set the output frequency you want for each PLL clock.
 356 * PLL output frequencies are programmed by setting their N, M and P values.
 357 * The governing equations are:
 358 *     VCO = (Fi / m) * n, Fo = VCO / (2^p)
 359 *     where Fo is the output frequency from the PLL.
 360 * Example: Set the output frequency to 216Mhz(Fo) with 12Mhz OSC(Fi)
 361 *     216Mhz = ((12Mhz / m) * n) / (2^p) so n=432,m=12,p=1
 362 * Please see Tegra TRM section 5.3 to get the detail for PLL Programming
 363 *
 364 * @param n PLL feedback divider(DIVN)
 365 * @param m PLL input divider(DIVN)
 366 * @param p post divider(DIVP)
 367 * @param cpcon base PLL charge pump(CPCON)
 368 * @return 0 if ok, -1 on error (the requested PLL is incorrect and cannot
 369 *              be overridden), 1 if PLL is already correct
 370 */
 371int clock_set_rate(enum clock_id clkid, u32 n, u32 m, u32 p, u32 cpcon);
 372
 373/* return 1 if a peripheral ID is in range */
 374#define clock_type_id_isvalid(id) ((id) >= 0 && \
 375                (id) < CLOCK_TYPE_COUNT)
 376
 377/* return 1 if a periphc_internal_id is in range */
 378#define periphc_internal_id_isvalid(id) ((id) >= 0 && \
 379                (id) < PERIPHC_COUNT)
 380
 381/* SoC-specific TSC init */
 382void arch_timer_init(void);
 383
 384void tegra30_set_up_pllp(void);
 385
 386/* Number of PLL-based clocks (i.e. not OSC, MCLK or 32KHz) */
 387#define CLOCK_ID_PLL_COUNT      (CLOCK_ID_COUNT - 3)
 388
 389struct clk_pll_info {
 390        u32     m_shift:5;      /* DIVM_SHIFT */
 391        u32     n_shift:5;      /* DIVN_SHIFT */
 392        u32     p_shift:5;      /* DIVP_SHIFT */
 393        u32     kcp_shift:5;    /* KCP/cpcon SHIFT */
 394        u32     kvco_shift:5;   /* KVCO/lfcon SHIFT */
 395        u32     lock_ena:6;     /* LOCK_ENABLE/EN_LOCKDET shift */
 396        u32     rsvd:1;
 397        u32     m_mask:10;      /* DIVM_MASK */
 398        u32     n_mask:12;      /* DIVN_MASK */
 399        u32     p_mask:10;      /* DIVP_MASK or VCO_MASK */
 400        u32     kcp_mask:10;    /* KCP/CPCON MASK */
 401        u32     kvco_mask:10;   /* KVCO/LFCON MASK */
 402        u32     lock_det:6;     /* LOCK_DETECT/LOCKED shift */
 403        u32     rsvd2:6;
 404};
 405extern struct clk_pll_info tegra_pll_info_table[CLOCK_ID_PLL_COUNT];
 406
 407struct periph_clk_init {
 408        enum periph_id periph_id;
 409        enum clock_id parent_clock_id;
 410};
 411extern struct periph_clk_init periph_clk_init_table[];
 412
 413/**
 414 * Enable output clock for external peripherals
 415 *
 416 * @param clk_id        Clock ID to output (1, 2 or 3)
 417 * @return 0 if OK. -ve on error
 418 */
 419int clock_external_output(int clk_id);
 420
 421#endif  /* _TEGRA_CLOCK_H_ */
 422