ARM: cpu topology: Add debugfs interface for cpu_power
[cmplus.git] / arch / arm / mach-omap2 / omap4_trim_quirks.c
blobbb1c88e741a143a8f466e5df9740126aaebfa5fa
1 /*
2 * OMAP LDO control and configuration
4 * Copyright (C) 2011 Texas Instruments Incorporated - http://www.ti.com/
5 * Nishanth Menon
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License version 2 as
9 * published by the Free Software Foundation.
12 #include <linux/init.h>
13 #include <linux/kernel.h>
14 #include <linux/cpu.h>
16 #include "control.h"
17 #include "pm.h"
18 #include <mach/ctrl_module_core_44xx.h>
20 #define OMAP4_DPLL_MPU_TRIMMED_VAL_2P4 (0x1 << 18)
21 #define OMAP4_DPLL_MPU_TRIMMED_VAL_3P0 (0x3 << 18)
22 #define OMAP4_DPLL_MPU_TRIMMED_MASK (BIT(19) | BIT(18))
24 * Trim value has to be written to CONTROL_EFUSE_2 according to
25 * OMAP4430 errata i684 (version B)
26 * OMAP4430 units with ProdID[51:50]=11 are not affected
28 #define OMAP4_LPDDR2_I684_FIX_VALUE 0x004E4000
29 #define OMAP4_PROD_ID_I684_MASK 0x000C0000
32 static bool bgap_trim_sw_overide;
33 static bool dpll_trim_override;
34 static bool ddr_io_trim_override;
36 /**
37 * omap4_ldo_trim_configure() - Handle device trim variance
39 * Few of the silicon out of the fab come out without trim parameters
40 * efused in. These need some software support to allow the device to
41 * function normally. Handle these silicon quirks here.
43 int omap4_ldo_trim_configure(void)
45 u32 val;
47 /* if not trimmed, we set force overide, insted of efuse. */
48 if (bgap_trim_sw_overide) {
49 /* Fill in recommended values */
50 val = 0x0f << OMAP4_LDOSRAMCORE_ACTMODE_VSET_OUT_SHIFT;
51 val |= OMAP4_LDOSRAMCORE_ACTMODE_MUX_CTRL_MASK;
52 val |= 0x1 << OMAP4_LDOSRAMCORE_RETMODE_VSET_OUT_SHIFT;
53 val |= OMAP4_LDOSRAMCORE_RETMODE_MUX_CTRL_MASK;
55 omap_ctrl_writel(val,
56 OMAP4_CTRL_MODULE_CORE_LDOSRAM_MPU_VOLTAGE_CTRL);
57 omap_ctrl_writel(val,
58 OMAP4_CTRL_MODULE_CORE_LDOSRAM_CORE_VOLTAGE_CTRL);
59 omap_ctrl_writel(val,
60 OMAP4_CTRL_MODULE_CORE_LDOSRAM_IVA_VOLTAGE_CTRL);
63 /* For all trimmed and untrimmed write value as per recomendation */
64 val = 0x10 << OMAP4_AVDAC_TRIM_BYTE0_SHIFT;
65 val |= 0x01 << OMAP4_AVDAC_TRIM_BYTE1_SHIFT;
66 val |= 0x4d << OMAP4_AVDAC_TRIM_BYTE2_SHIFT;
67 val |= 0x1C << OMAP4_AVDAC_TRIM_BYTE3_SHIFT;
68 omap4_ctrl_pad_writel(val,
69 OMAP4_CTRL_MODULE_PAD_CORE_CONTROL_EFUSE_1);
71 /* DDR I/O Trim override as per erratum i684 */
72 if (ddr_io_trim_override) {
73 omap4_ctrl_pad_writel(OMAP4_LPDDR2_I684_FIX_VALUE,
74 OMAP4_CTRL_MODULE_PAD_CORE_CONTROL_EFUSE_2);
77 /* Required for DPLL_MPU to lock at 2.4 GHz */
78 // if (dpll_trim_override)
79 omap_ctrl_writel(0x29, OMAP4_CTRL_MODULE_CORE_DPLL_NWELL_TRIM_0);
81 return 0;
84 /**
85 * omap4460_mpu_dpll_trim_override() - provide a selective s/w trim overide
87 static __init void omap4460_mpu_dpll_trim_override(void)
89 u32 val;
91 val = omap_ctrl_readl(OMAP4_CTRL_MODULE_CORE_STD_FUSE_OPP_DPLL_1) &
92 OMAP4_DPLL_MPU_TRIMMED_MASK;
93 switch (val) {
94 case OMAP4_DPLL_MPU_TRIMMED_VAL_3P0:
95 /* all ok.. */
96 break;
97 case OMAP4_DPLL_MPU_TRIMMED_VAL_2P4:
98 /* Cross check! */
99 if (omap4_has_mpu_1_5ghz()) {
100 WARN(1, "%s: OMAP is 1.5GHz capable, trimmed=1.2GHz!\n",
101 __func__);
103 break;
104 default:
105 WARN(1, "%s: UNKNOWN TRIM:0x%08x, using s/w override\n",
106 __func__, val);
107 /* fall through and use override */
108 case 0:
110 * For PRE_RTP devices: Not trimmed, use s/w override!
111 * We only support unto 1.2GHz with s/w override,
112 * so just give a gentle warning if higher opp is attempted
114 dpll_trim_override = true;
115 /* Confirm */
116 if (omap4_has_mpu_1_5ghz()) {
117 pr_err("%s: OMAP is 1.5GHz capable, s/w trim=1.2GHz!\n",
118 __func__);
120 break;
124 static __init int omap4_ldo_trim_init(void)
126 u32 bgap_trimmed = 0;
128 /* Applicable only for OMAP4 */
129 if (!cpu_is_omap44xx())
130 return 0;
133 * Some ES2.2 efuse values for BGAP and SLDO trim
134 * are not programmed. For these units
135 * 1. we can set overide mode for SLDO trim,
136 * and program the max multiplication factor, to ensure
137 * high enough voltage on SLDO output.
138 * 2. trim VDAC value for TV output as per recomendation
140 if (omap_rev() >= CHIP_IS_OMAP4430ES2_2)
141 bgap_trimmed = omap_ctrl_readl(
142 OMAP4_CTRL_MODULE_CORE_STD_FUSE_OPP_BGAP);
144 bgap_trimmed &= OMAP4_STD_FUSE_OPP_BGAP_MASK_LSB;
146 /* if not trimmed, we set force overide, insted of efuse. */
147 if (!bgap_trimmed)
148 bgap_trim_sw_overide = true;
150 /* If not already trimmed, use s/w override */
151 if (cpu_is_omap446x())
152 omap4460_mpu_dpll_trim_override();
155 * Errata i684 (revision B)
156 * Impacts all OMAP4430ESx.y trimmed and untrimmed excluding units
157 * with with ProdID[51:50]=11
158 * OMAP4460/70 are not impacted.
160 * ProdID:
161 * 51 50
162 * 0 0 Incorrect trim, SW WA needed.
163 * 0 1 Fixed test program issue of overlapping of LPDDR & SmartIO
164 * efuse fields, SW WA needed for LPDDR.
165 * 1 1 New LPDDR trim formula to compensate for vertical vs horizontal
166 * cell layout. No overwrite required.
168 if (cpu_is_omap443x()) {
169 u32 prod_id;
171 prod_id = omap_ctrl_readl(
172 OMAP4_CTRL_MODULE_CORE_STD_FUSE_PROD_ID_1);
173 prod_id &= OMAP4_PROD_ID_I684_MASK;
174 if (prod_id != OMAP4_PROD_ID_I684_MASK)
175 ddr_io_trim_override = true;
178 return omap4_ldo_trim_configure();
180 arch_initcall(omap4_ldo_trim_init);