master
c 74 lines 1.75 KB
Raw
1 /*
2 * IMX31 Clock Control Module
3 *
4 * Copyright (C) 2012 NICTA
5 * Updated by Jean-Christophe Dubois <jcd@tribudubois.net>
6 *
7 * This work is licensed under the terms of the GNU GPL, version 2 or later.
8 * See the COPYING file in the top-level directory.
9 *
10 * This is an abstract base class used to get a common interface to
11 * retrieve the CCM frequencies from the various i.MX SOC.
12 */
13
14 #include "qemu/osdep.h"
15 #include "hw/misc/imx_ccm.h"
16 #include "qemu/module.h"
17 #include "trace.h"
18
19
20 uint32_t imx_ccm_get_clock_frequency(IMXCCMState *dev, IMXClk clock)
21 {
22 uint32_t freq = 0;
23 IMXCCMClass *klass = IMX_CCM_GET_CLASS(dev);
24
25 if (klass->get_clock_frequency) {
26 freq = klass->get_clock_frequency(dev, clock);
27 }
28
29 trace_imx_ccm_get_clock_frequency(clock, freq);
30
31 return freq;
32 }
33
34 /*
35 * Calculate PLL output frequency
36 */
37 uint32_t imx_ccm_calc_pll(uint32_t pllreg, uint32_t base_freq)
38 {
39 int32_t freq;
40 int32_t mfn = MFN(pllreg); /* Numerator */
41 uint32_t mfi = MFI(pllreg); /* Integer part */
42 uint32_t mfd = 1 + MFD(pllreg); /* Denominator */
43 uint32_t pd = 1 + PD(pllreg); /* Pre-divider */
44
45 if (mfi < 5) {
46 mfi = 5;
47 }
48
49 /* mfn is 10-bit signed twos-complement */
50 mfn <<= 32 - 10;
51 mfn >>= 32 - 10;
52
53 freq = ((2 * (base_freq >> 10) * (mfi * mfd + mfn)) /
54 (mfd * pd)) << 10;
55
56 trace_imx_ccm_calc_pll(pllreg, base_freq, freq);
57
58 return freq;
59 }
60
61 static const TypeInfo imx_ccm_info = {
62 .name = TYPE_IMX_CCM,
63 .parent = TYPE_SYS_BUS_DEVICE,
64 .instance_size = sizeof(IMXCCMState),
65 .class_size = sizeof(IMXCCMClass),
66 .abstract = true,
67 };
68
69 static void imx_ccm_register_types(void)
70 {
71 type_register_static(&imx_ccm_info);
72 }
73
74 type_init(imx_ccm_register_types)