xref: /openbmc/linux/arch/arm/mach-omap2/prm3xxx.c (revision d2999e1b)
1 /*
2  * OMAP3xxx PRM module functions
3  *
4  * Copyright (C) 2010-2012 Texas Instruments, Inc.
5  * Copyright (C) 2010 Nokia Corporation
6  * Benoît Cousson
7  * Paul Walmsley
8  * Rajendra Nayak <rnayak@ti.com>
9  *
10  * This program is free software; you can redistribute it and/or modify
11  * it under the terms of the GNU General Public License version 2 as
12  * published by the Free Software Foundation.
13  */
14 
15 #include <linux/kernel.h>
16 #include <linux/errno.h>
17 #include <linux/err.h>
18 #include <linux/io.h>
19 #include <linux/irq.h>
20 
21 #include "soc.h"
22 #include "common.h"
23 #include "vp.h"
24 #include "powerdomain.h"
25 #include "prm3xxx.h"
26 #include "prm2xxx_3xxx.h"
27 #include "cm2xxx_3xxx.h"
28 #include "prm-regbits-34xx.h"
29 
30 static const struct omap_prcm_irq omap3_prcm_irqs[] = {
31 	OMAP_PRCM_IRQ("wkup",	0,	0),
32 	OMAP_PRCM_IRQ("io",	9,	1),
33 };
34 
35 static struct omap_prcm_irq_setup omap3_prcm_irq_setup = {
36 	.ack			= OMAP3_PRM_IRQSTATUS_MPU_OFFSET,
37 	.mask			= OMAP3_PRM_IRQENABLE_MPU_OFFSET,
38 	.nr_regs		= 1,
39 	.irqs			= omap3_prcm_irqs,
40 	.nr_irqs		= ARRAY_SIZE(omap3_prcm_irqs),
41 	.irq			= 11 + OMAP_INTC_START,
42 	.read_pending_irqs	= &omap3xxx_prm_read_pending_irqs,
43 	.ocp_barrier		= &omap3xxx_prm_ocp_barrier,
44 	.save_and_clear_irqen	= &omap3xxx_prm_save_and_clear_irqen,
45 	.restore_irqen		= &omap3xxx_prm_restore_irqen,
46 	.reconfigure_io_chain	= &omap3xxx_prm_reconfigure_io_chain,
47 };
48 
49 /*
50  * omap3_prm_reset_src_map - map from bits in the PRM_RSTST hardware
51  *   register (which are specific to OMAP3xxx SoCs) to reset source ID
52  *   bit shifts (which is an OMAP SoC-independent enumeration)
53  */
54 static struct prm_reset_src_map omap3xxx_prm_reset_src_map[] = {
55 	{ OMAP3430_GLOBAL_COLD_RST_SHIFT, OMAP_GLOBAL_COLD_RST_SRC_ID_SHIFT },
56 	{ OMAP3430_GLOBAL_SW_RST_SHIFT, OMAP_GLOBAL_WARM_RST_SRC_ID_SHIFT },
57 	{ OMAP3430_SECURITY_VIOL_RST_SHIFT, OMAP_SECU_VIOL_RST_SRC_ID_SHIFT },
58 	{ OMAP3430_MPU_WD_RST_SHIFT, OMAP_MPU_WD_RST_SRC_ID_SHIFT },
59 	{ OMAP3430_SECURE_WD_RST_SHIFT, OMAP_MPU_WD_RST_SRC_ID_SHIFT },
60 	{ OMAP3430_EXTERNAL_WARM_RST_SHIFT, OMAP_EXTWARM_RST_SRC_ID_SHIFT },
61 	{ OMAP3430_VDD1_VOLTAGE_MANAGER_RST_SHIFT,
62 	  OMAP_VDD_MPU_VM_RST_SRC_ID_SHIFT },
63 	{ OMAP3430_VDD2_VOLTAGE_MANAGER_RST_SHIFT,
64 	  OMAP_VDD_CORE_VM_RST_SRC_ID_SHIFT },
65 	{ OMAP3430_ICEPICK_RST_SHIFT, OMAP_ICEPICK_RST_SRC_ID_SHIFT },
66 	{ OMAP3430_ICECRUSHER_RST_SHIFT, OMAP_ICECRUSHER_RST_SRC_ID_SHIFT },
67 	{ -1, -1 },
68 };
69 
70 /* PRM VP */
71 
72 /*
73  * struct omap3_vp - OMAP3 VP register access description.
74  * @tranxdone_status: VP_TRANXDONE_ST bitmask in PRM_IRQSTATUS_MPU reg
75  */
76 struct omap3_vp {
77 	u32 tranxdone_status;
78 };
79 
80 static struct omap3_vp omap3_vp[] = {
81 	[OMAP3_VP_VDD_MPU_ID] = {
82 		.tranxdone_status = OMAP3430_VP1_TRANXDONE_ST_MASK,
83 	},
84 	[OMAP3_VP_VDD_CORE_ID] = {
85 		.tranxdone_status = OMAP3430_VP2_TRANXDONE_ST_MASK,
86 	},
87 };
88 
89 #define MAX_VP_ID ARRAY_SIZE(omap3_vp);
90 
91 u32 omap3_prm_vp_check_txdone(u8 vp_id)
92 {
93 	struct omap3_vp *vp = &omap3_vp[vp_id];
94 	u32 irqstatus;
95 
96 	irqstatus = omap2_prm_read_mod_reg(OCP_MOD,
97 					   OMAP3_PRM_IRQSTATUS_MPU_OFFSET);
98 	return irqstatus & vp->tranxdone_status;
99 }
100 
101 void omap3_prm_vp_clear_txdone(u8 vp_id)
102 {
103 	struct omap3_vp *vp = &omap3_vp[vp_id];
104 
105 	omap2_prm_write_mod_reg(vp->tranxdone_status,
106 				OCP_MOD, OMAP3_PRM_IRQSTATUS_MPU_OFFSET);
107 }
108 
109 u32 omap3_prm_vcvp_read(u8 offset)
110 {
111 	return omap2_prm_read_mod_reg(OMAP3430_GR_MOD, offset);
112 }
113 
114 void omap3_prm_vcvp_write(u32 val, u8 offset)
115 {
116 	omap2_prm_write_mod_reg(val, OMAP3430_GR_MOD, offset);
117 }
118 
119 u32 omap3_prm_vcvp_rmw(u32 mask, u32 bits, u8 offset)
120 {
121 	return omap2_prm_rmw_mod_reg_bits(mask, bits, OMAP3430_GR_MOD, offset);
122 }
123 
124 /**
125  * omap3xxx_prm_dpll3_reset - use DPLL3 reset to reboot the OMAP SoC
126  *
127  * Set the DPLL3 reset bit, which should reboot the SoC.  This is the
128  * recommended way to restart the SoC, considering Errata i520.  No
129  * return value.
130  */
131 void omap3xxx_prm_dpll3_reset(void)
132 {
133 	omap2_prm_set_mod_reg_bits(OMAP_RST_DPLL3_MASK, OMAP3430_GR_MOD,
134 				   OMAP2_RM_RSTCTRL);
135 	/* OCP barrier */
136 	omap2_prm_read_mod_reg(OMAP3430_GR_MOD, OMAP2_RM_RSTCTRL);
137 }
138 
139 /**
140  * omap3xxx_prm_read_pending_irqs - read pending PRM MPU IRQs into @events
141  * @events: ptr to a u32, preallocated by caller
142  *
143  * Read PRM_IRQSTATUS_MPU bits, AND'ed with the currently-enabled PRM
144  * MPU IRQs, and store the result into the u32 pointed to by @events.
145  * No return value.
146  */
147 void omap3xxx_prm_read_pending_irqs(unsigned long *events)
148 {
149 	u32 mask, st;
150 
151 	/* XXX Can the mask read be avoided (e.g., can it come from RAM?) */
152 	mask = omap2_prm_read_mod_reg(OCP_MOD, OMAP3_PRM_IRQENABLE_MPU_OFFSET);
153 	st = omap2_prm_read_mod_reg(OCP_MOD, OMAP3_PRM_IRQSTATUS_MPU_OFFSET);
154 
155 	events[0] = mask & st;
156 }
157 
158 /**
159  * omap3xxx_prm_ocp_barrier - force buffered MPU writes to the PRM to complete
160  *
161  * Force any buffered writes to the PRM IP block to complete.  Needed
162  * by the PRM IRQ handler, which reads and writes directly to the IP
163  * block, to avoid race conditions after acknowledging or clearing IRQ
164  * bits.  No return value.
165  */
166 void omap3xxx_prm_ocp_barrier(void)
167 {
168 	omap2_prm_read_mod_reg(OCP_MOD, OMAP3_PRM_REVISION_OFFSET);
169 }
170 
171 /**
172  * omap3xxx_prm_save_and_clear_irqen - save/clear PRM_IRQENABLE_MPU reg
173  * @saved_mask: ptr to a u32 array to save IRQENABLE bits
174  *
175  * Save the PRM_IRQENABLE_MPU register to @saved_mask.  @saved_mask
176  * must be allocated by the caller.  Intended to be used in the PRM
177  * interrupt handler suspend callback.  The OCP barrier is needed to
178  * ensure the write to disable PRM interrupts reaches the PRM before
179  * returning; otherwise, spurious interrupts might occur.  No return
180  * value.
181  */
182 void omap3xxx_prm_save_and_clear_irqen(u32 *saved_mask)
183 {
184 	saved_mask[0] = omap2_prm_read_mod_reg(OCP_MOD,
185 					       OMAP3_PRM_IRQENABLE_MPU_OFFSET);
186 	omap2_prm_write_mod_reg(0, OCP_MOD, OMAP3_PRM_IRQENABLE_MPU_OFFSET);
187 
188 	/* OCP barrier */
189 	omap2_prm_read_mod_reg(OCP_MOD, OMAP3_PRM_REVISION_OFFSET);
190 }
191 
192 /**
193  * omap3xxx_prm_restore_irqen - set PRM_IRQENABLE_MPU register from args
194  * @saved_mask: ptr to a u32 array of IRQENABLE bits saved previously
195  *
196  * Restore the PRM_IRQENABLE_MPU register from @saved_mask.  Intended
197  * to be used in the PRM interrupt handler resume callback to restore
198  * values saved by omap3xxx_prm_save_and_clear_irqen().  No OCP
199  * barrier should be needed here; any pending PRM interrupts will fire
200  * once the writes reach the PRM.  No return value.
201  */
202 void omap3xxx_prm_restore_irqen(u32 *saved_mask)
203 {
204 	omap2_prm_write_mod_reg(saved_mask[0], OCP_MOD,
205 				OMAP3_PRM_IRQENABLE_MPU_OFFSET);
206 }
207 
208 /**
209  * omap3xxx_prm_reconfigure_io_chain - clear latches and reconfigure I/O chain
210  *
211  * Clear any previously-latched I/O wakeup events and ensure that the
212  * I/O wakeup gates are aligned with the current mux settings.  Works
213  * by asserting WUCLKIN, waiting for WUCLKOUT to be asserted, and then
214  * deasserting WUCLKIN and clearing the ST_IO_CHAIN WKST bit.  No
215  * return value.
216  */
217 void omap3xxx_prm_reconfigure_io_chain(void)
218 {
219 	int i = 0;
220 
221 	omap2_prm_set_mod_reg_bits(OMAP3430_EN_IO_CHAIN_MASK, WKUP_MOD,
222 				   PM_WKEN);
223 
224 	omap_test_timeout(omap2_prm_read_mod_reg(WKUP_MOD, PM_WKST) &
225 			  OMAP3430_ST_IO_CHAIN_MASK,
226 			  MAX_IOPAD_LATCH_TIME, i);
227 	if (i == MAX_IOPAD_LATCH_TIME)
228 		pr_warn("PRM: I/O chain clock line assertion timed out\n");
229 
230 	omap2_prm_clear_mod_reg_bits(OMAP3430_EN_IO_CHAIN_MASK, WKUP_MOD,
231 				     PM_WKEN);
232 
233 	omap2_prm_set_mod_reg_bits(OMAP3430_ST_IO_CHAIN_MASK, WKUP_MOD,
234 				   PM_WKST);
235 
236 	omap2_prm_read_mod_reg(WKUP_MOD, PM_WKST);
237 }
238 
239 /**
240  * omap3xxx_prm_enable_io_wakeup - enable wakeup events from I/O wakeup latches
241  *
242  * Activates the I/O wakeup event latches and allows events logged by
243  * those latches to signal a wakeup event to the PRCM.  For I/O
244  * wakeups to occur, WAKEUPENABLE bits must be set in the pad mux
245  * registers, and omap3xxx_prm_reconfigure_io_chain() must be called.
246  * No return value.
247  */
248 static void __init omap3xxx_prm_enable_io_wakeup(void)
249 {
250 	if (prm_features & PRM_HAS_IO_WAKEUP)
251 		omap2_prm_set_mod_reg_bits(OMAP3430_EN_IO_MASK, WKUP_MOD,
252 					   PM_WKEN);
253 }
254 
255 /**
256  * omap3xxx_prm_read_reset_sources - return the last SoC reset source
257  *
258  * Return a u32 representing the last reset sources of the SoC.  The
259  * returned reset source bits are standardized across OMAP SoCs.
260  */
261 static u32 omap3xxx_prm_read_reset_sources(void)
262 {
263 	struct prm_reset_src_map *p;
264 	u32 r = 0;
265 	u32 v;
266 
267 	v = omap2_prm_read_mod_reg(WKUP_MOD, OMAP2_RM_RSTST);
268 
269 	p = omap3xxx_prm_reset_src_map;
270 	while (p->reg_shift >= 0 && p->std_shift >= 0) {
271 		if (v & (1 << p->reg_shift))
272 			r |= 1 << p->std_shift;
273 		p++;
274 	}
275 
276 	return r;
277 }
278 
279 /* Powerdomain low-level functions */
280 
281 static int omap3_pwrdm_set_next_pwrst(struct powerdomain *pwrdm, u8 pwrst)
282 {
283 	omap2_prm_rmw_mod_reg_bits(OMAP_POWERSTATE_MASK,
284 				   (pwrst << OMAP_POWERSTATE_SHIFT),
285 				   pwrdm->prcm_offs, OMAP2_PM_PWSTCTRL);
286 	return 0;
287 }
288 
289 static int omap3_pwrdm_read_next_pwrst(struct powerdomain *pwrdm)
290 {
291 	return omap2_prm_read_mod_bits_shift(pwrdm->prcm_offs,
292 					     OMAP2_PM_PWSTCTRL,
293 					     OMAP_POWERSTATE_MASK);
294 }
295 
296 static int omap3_pwrdm_read_pwrst(struct powerdomain *pwrdm)
297 {
298 	return omap2_prm_read_mod_bits_shift(pwrdm->prcm_offs,
299 					     OMAP2_PM_PWSTST,
300 					     OMAP_POWERSTATEST_MASK);
301 }
302 
303 /* Applicable only for OMAP3. Not supported on OMAP2 */
304 static int omap3_pwrdm_read_prev_pwrst(struct powerdomain *pwrdm)
305 {
306 	return omap2_prm_read_mod_bits_shift(pwrdm->prcm_offs,
307 					     OMAP3430_PM_PREPWSTST,
308 					     OMAP3430_LASTPOWERSTATEENTERED_MASK);
309 }
310 
311 static int omap3_pwrdm_read_logic_pwrst(struct powerdomain *pwrdm)
312 {
313 	return omap2_prm_read_mod_bits_shift(pwrdm->prcm_offs,
314 					     OMAP2_PM_PWSTST,
315 					     OMAP3430_LOGICSTATEST_MASK);
316 }
317 
318 static int omap3_pwrdm_read_logic_retst(struct powerdomain *pwrdm)
319 {
320 	return omap2_prm_read_mod_bits_shift(pwrdm->prcm_offs,
321 					     OMAP2_PM_PWSTCTRL,
322 					     OMAP3430_LOGICSTATEST_MASK);
323 }
324 
325 static int omap3_pwrdm_read_prev_logic_pwrst(struct powerdomain *pwrdm)
326 {
327 	return omap2_prm_read_mod_bits_shift(pwrdm->prcm_offs,
328 					     OMAP3430_PM_PREPWSTST,
329 					     OMAP3430_LASTLOGICSTATEENTERED_MASK);
330 }
331 
332 static int omap3_get_mem_bank_lastmemst_mask(u8 bank)
333 {
334 	switch (bank) {
335 	case 0:
336 		return OMAP3430_LASTMEM1STATEENTERED_MASK;
337 	case 1:
338 		return OMAP3430_LASTMEM2STATEENTERED_MASK;
339 	case 2:
340 		return OMAP3430_LASTSHAREDL2CACHEFLATSTATEENTERED_MASK;
341 	case 3:
342 		return OMAP3430_LASTL2FLATMEMSTATEENTERED_MASK;
343 	default:
344 		WARN_ON(1); /* should never happen */
345 		return -EEXIST;
346 	}
347 	return 0;
348 }
349 
350 static int omap3_pwrdm_read_prev_mem_pwrst(struct powerdomain *pwrdm, u8 bank)
351 {
352 	u32 m;
353 
354 	m = omap3_get_mem_bank_lastmemst_mask(bank);
355 
356 	return omap2_prm_read_mod_bits_shift(pwrdm->prcm_offs,
357 				OMAP3430_PM_PREPWSTST, m);
358 }
359 
360 static int omap3_pwrdm_clear_all_prev_pwrst(struct powerdomain *pwrdm)
361 {
362 	omap2_prm_write_mod_reg(0, pwrdm->prcm_offs, OMAP3430_PM_PREPWSTST);
363 	return 0;
364 }
365 
366 static int omap3_pwrdm_enable_hdwr_sar(struct powerdomain *pwrdm)
367 {
368 	return omap2_prm_rmw_mod_reg_bits(0,
369 					  1 << OMAP3430ES2_SAVEANDRESTORE_SHIFT,
370 					  pwrdm->prcm_offs, OMAP2_PM_PWSTCTRL);
371 }
372 
373 static int omap3_pwrdm_disable_hdwr_sar(struct powerdomain *pwrdm)
374 {
375 	return omap2_prm_rmw_mod_reg_bits(1 << OMAP3430ES2_SAVEANDRESTORE_SHIFT,
376 					  0, pwrdm->prcm_offs,
377 					  OMAP2_PM_PWSTCTRL);
378 }
379 
380 struct pwrdm_ops omap3_pwrdm_operations = {
381 	.pwrdm_set_next_pwrst	= omap3_pwrdm_set_next_pwrst,
382 	.pwrdm_read_next_pwrst	= omap3_pwrdm_read_next_pwrst,
383 	.pwrdm_read_pwrst	= omap3_pwrdm_read_pwrst,
384 	.pwrdm_read_prev_pwrst	= omap3_pwrdm_read_prev_pwrst,
385 	.pwrdm_set_logic_retst	= omap2_pwrdm_set_logic_retst,
386 	.pwrdm_read_logic_pwrst	= omap3_pwrdm_read_logic_pwrst,
387 	.pwrdm_read_logic_retst	= omap3_pwrdm_read_logic_retst,
388 	.pwrdm_read_prev_logic_pwrst	= omap3_pwrdm_read_prev_logic_pwrst,
389 	.pwrdm_set_mem_onst	= omap2_pwrdm_set_mem_onst,
390 	.pwrdm_set_mem_retst	= omap2_pwrdm_set_mem_retst,
391 	.pwrdm_read_mem_pwrst	= omap2_pwrdm_read_mem_pwrst,
392 	.pwrdm_read_mem_retst	= omap2_pwrdm_read_mem_retst,
393 	.pwrdm_read_prev_mem_pwrst	= omap3_pwrdm_read_prev_mem_pwrst,
394 	.pwrdm_clear_all_prev_pwrst	= omap3_pwrdm_clear_all_prev_pwrst,
395 	.pwrdm_enable_hdwr_sar	= omap3_pwrdm_enable_hdwr_sar,
396 	.pwrdm_disable_hdwr_sar	= omap3_pwrdm_disable_hdwr_sar,
397 	.pwrdm_wait_transition	= omap2_pwrdm_wait_transition,
398 };
399 
400 /*
401  *
402  */
403 
404 static int omap3xxx_prm_late_init(void);
405 
406 static struct prm_ll_data omap3xxx_prm_ll_data = {
407 	.read_reset_sources = &omap3xxx_prm_read_reset_sources,
408 	.late_init = &omap3xxx_prm_late_init,
409 };
410 
411 int __init omap3xxx_prm_init(void)
412 {
413 	if (omap3_has_io_wakeup())
414 		prm_features |= PRM_HAS_IO_WAKEUP;
415 
416 	return prm_register(&omap3xxx_prm_ll_data);
417 }
418 
419 static int omap3xxx_prm_late_init(void)
420 {
421 	int ret;
422 
423 	if (!(prm_features & PRM_HAS_IO_WAKEUP))
424 		return 0;
425 
426 	omap3xxx_prm_enable_io_wakeup();
427 	ret = omap_prcm_register_chain_handler(&omap3_prcm_irq_setup);
428 	if (!ret)
429 		irq_set_status_flags(omap_prcm_event_to_irq("io"),
430 				     IRQ_NOAUTOEN);
431 
432 	return ret;
433 }
434 
435 static void __exit omap3xxx_prm_exit(void)
436 {
437 	prm_unregister(&omap3xxx_prm_ll_data);
438 }
439 __exitcall(omap3xxx_prm_exit);
440