xref: /aosp_15_r20/external/arm-trusted-firmware/drivers/arm/fvp/fvp_pwrc.c (revision 54fd6939e177f8ff529b10183254802c76df6d08)
1*54fd6939SJiyong Park /*
2*54fd6939SJiyong Park  * Copyright (c) 2013-2018, ARM Limited and Contributors. All rights reserved.
3*54fd6939SJiyong Park  *
4*54fd6939SJiyong Park  * SPDX-License-Identifier: BSD-3-Clause
5*54fd6939SJiyong Park  */
6*54fd6939SJiyong Park 
7*54fd6939SJiyong Park #include <drivers/arm/fvp/fvp_pwrc.h>
8*54fd6939SJiyong Park #include <lib/bakery_lock.h>
9*54fd6939SJiyong Park #include <lib/mmio.h>
10*54fd6939SJiyong Park #include <plat/arm/common/plat_arm.h>
11*54fd6939SJiyong Park #include <platform_def.h>
12*54fd6939SJiyong Park 
13*54fd6939SJiyong Park /*
14*54fd6939SJiyong Park  * TODO: Someday there will be a generic power controller api. At the moment
15*54fd6939SJiyong Park  * each platform has its own pwrc so just exporting functions is fine.
16*54fd6939SJiyong Park  */
17*54fd6939SJiyong Park ARM_INSTANTIATE_LOCK;
18*54fd6939SJiyong Park 
fvp_pwrc_get_cpu_wkr(u_register_t mpidr)19*54fd6939SJiyong Park unsigned int fvp_pwrc_get_cpu_wkr(u_register_t mpidr)
20*54fd6939SJiyong Park {
21*54fd6939SJiyong Park 	return PSYSR_WK(fvp_pwrc_read_psysr(mpidr));
22*54fd6939SJiyong Park }
23*54fd6939SJiyong Park 
fvp_pwrc_read_psysr(u_register_t mpidr)24*54fd6939SJiyong Park unsigned int fvp_pwrc_read_psysr(u_register_t mpidr)
25*54fd6939SJiyong Park {
26*54fd6939SJiyong Park 	unsigned int rc;
27*54fd6939SJiyong Park 	arm_lock_get();
28*54fd6939SJiyong Park 	mmio_write_32(PWRC_BASE + PSYSR_OFF, (unsigned int) mpidr);
29*54fd6939SJiyong Park 	rc = mmio_read_32(PWRC_BASE + PSYSR_OFF);
30*54fd6939SJiyong Park 	arm_lock_release();
31*54fd6939SJiyong Park 	return rc;
32*54fd6939SJiyong Park }
33*54fd6939SJiyong Park 
fvp_pwrc_write_pponr(u_register_t mpidr)34*54fd6939SJiyong Park void fvp_pwrc_write_pponr(u_register_t mpidr)
35*54fd6939SJiyong Park {
36*54fd6939SJiyong Park 	arm_lock_get();
37*54fd6939SJiyong Park 	mmio_write_32(PWRC_BASE + PPONR_OFF, (unsigned int) mpidr);
38*54fd6939SJiyong Park 	arm_lock_release();
39*54fd6939SJiyong Park }
40*54fd6939SJiyong Park 
fvp_pwrc_write_ppoffr(u_register_t mpidr)41*54fd6939SJiyong Park void fvp_pwrc_write_ppoffr(u_register_t mpidr)
42*54fd6939SJiyong Park {
43*54fd6939SJiyong Park 	arm_lock_get();
44*54fd6939SJiyong Park 	mmio_write_32(PWRC_BASE + PPOFFR_OFF, (unsigned int) mpidr);
45*54fd6939SJiyong Park 	arm_lock_release();
46*54fd6939SJiyong Park }
47*54fd6939SJiyong Park 
fvp_pwrc_set_wen(u_register_t mpidr)48*54fd6939SJiyong Park void fvp_pwrc_set_wen(u_register_t mpidr)
49*54fd6939SJiyong Park {
50*54fd6939SJiyong Park 	arm_lock_get();
51*54fd6939SJiyong Park 	mmio_write_32(PWRC_BASE + PWKUPR_OFF,
52*54fd6939SJiyong Park 		      (unsigned int) (PWKUPR_WEN | mpidr));
53*54fd6939SJiyong Park 	arm_lock_release();
54*54fd6939SJiyong Park }
55*54fd6939SJiyong Park 
fvp_pwrc_clr_wen(u_register_t mpidr)56*54fd6939SJiyong Park void fvp_pwrc_clr_wen(u_register_t mpidr)
57*54fd6939SJiyong Park {
58*54fd6939SJiyong Park 	arm_lock_get();
59*54fd6939SJiyong Park 	mmio_write_32(PWRC_BASE + PWKUPR_OFF,
60*54fd6939SJiyong Park 		      (unsigned int) mpidr);
61*54fd6939SJiyong Park 	arm_lock_release();
62*54fd6939SJiyong Park }
63*54fd6939SJiyong Park 
fvp_pwrc_write_pcoffr(u_register_t mpidr)64*54fd6939SJiyong Park void fvp_pwrc_write_pcoffr(u_register_t mpidr)
65*54fd6939SJiyong Park {
66*54fd6939SJiyong Park 	arm_lock_get();
67*54fd6939SJiyong Park 	mmio_write_32(PWRC_BASE + PCOFFR_OFF, (unsigned int) mpidr);
68*54fd6939SJiyong Park 	arm_lock_release();
69*54fd6939SJiyong Park }
70*54fd6939SJiyong Park 
71*54fd6939SJiyong Park /* Nothing else to do here apart from initializing the lock */
plat_arm_pwrc_setup(void)72*54fd6939SJiyong Park void __init plat_arm_pwrc_setup(void)
73*54fd6939SJiyong Park {
74*54fd6939SJiyong Park 	arm_lock_init();
75*54fd6939SJiyong Park }
76*54fd6939SJiyong Park 
77*54fd6939SJiyong Park 
78*54fd6939SJiyong Park 
79