blob: fb77f77c725d2fe0b149cd47b0c3af2043475b9b [file] [log] [blame]
Achin Gupta4f6ad662013-10-25 09:08:21 +01001/*
Madhukar Pappireddy15926e72023-07-31 23:22:02 -05002 * Copyright (c) 2013-2023, Arm Limited and Contributors. All rights reserved.
Achin Gupta4f6ad662013-10-25 09:08:21 +01003 *
dp-armfa3cf0b2017-05-03 09:38:09 +01004 * SPDX-License-Identifier: BSD-3-Clause
Achin Gupta4f6ad662013-10-25 09:08:21 +01005 */
6
Antonio Nino Diazf13d09a2019-01-23 21:50:09 +00007#include <drivers/arm/fvp/fvp_pwrc.h>
Antonio Nino Diaze0f90632018-12-14 00:18:21 +00008#include <lib/bakery_lock.h>
9#include <lib/mmio.h>
Antonio Nino Diazbd7b7402019-01-25 14:30:04 +000010#include <plat/arm/common/plat_arm.h>
Antonio Nino Diaza320ecd2019-01-15 14:19:50 +000011#include <platform_def.h>
Antonio Nino Diaze0f90632018-12-14 00:18:21 +000012
Madhukar Pappireddy15926e72023-07-31 23:22:02 -050013#define FVP_PWRC_ID_MASK U(0x00FFFFFF)
14
Achin Gupta4f6ad662013-10-25 09:08:21 +010015/*
16 * TODO: Someday there will be a generic power controller api. At the moment
17 * each platform has its own pwrc so just exporting functions is fine.
18 */
Jeenu Viswambharan749d25b2017-08-23 14:12:59 +010019ARM_INSTANTIATE_LOCK;
Achin Gupta4f6ad662013-10-25 09:08:21 +010020
Madhukar Pappireddy15926e72023-07-31 23:22:02 -050021/*
22 * Core ID field is 24 bits wide and extracted from MPIDR.
23 * Bits[23:16] represent Affinity Level 2
24 * Bits[15:8] represent Affinity Level 1
25 * Bits[7:0] represent Affinity Level 0
26 */
27static unsigned int fvp_pwrc_core_id(u_register_t mpidr)
28{
29 return (unsigned int)(mpidr & FVP_PWRC_ID_MASK);
30}
31
Soby Mathewa0fedc42016-06-16 14:52:04 +010032unsigned int fvp_pwrc_get_cpu_wkr(u_register_t mpidr)
Achin Gupta4f6ad662013-10-25 09:08:21 +010033{
Madhukar Pappireddy15926e72023-07-31 23:22:02 -050034 unsigned int id = fvp_pwrc_core_id(mpidr);
35
36 return PSYSR_WK(fvp_pwrc_read_psysr(id));
Achin Gupta4f6ad662013-10-25 09:08:21 +010037}
38
Soby Mathewa0fedc42016-06-16 14:52:04 +010039unsigned int fvp_pwrc_read_psysr(u_register_t mpidr)
Achin Gupta4f6ad662013-10-25 09:08:21 +010040{
Andrew Thoelke958cc022014-06-09 12:54:15 +010041 unsigned int rc;
Madhukar Pappireddy15926e72023-07-31 23:22:02 -050042 unsigned int id = fvp_pwrc_core_id(mpidr);
43
Dan Handley2b6b5742015-03-19 19:17:53 +000044 arm_lock_get();
Madhukar Pappireddy15926e72023-07-31 23:22:02 -050045 mmio_write_32(PWRC_BASE + PSYSR_OFF, id);
Achin Gupta4f6ad662013-10-25 09:08:21 +010046 rc = mmio_read_32(PWRC_BASE + PSYSR_OFF);
Dan Handley2b6b5742015-03-19 19:17:53 +000047 arm_lock_release();
Achin Gupta4f6ad662013-10-25 09:08:21 +010048 return rc;
49}
50
Soby Mathewa0fedc42016-06-16 14:52:04 +010051void fvp_pwrc_write_pponr(u_register_t mpidr)
Achin Gupta4f6ad662013-10-25 09:08:21 +010052{
Madhukar Pappireddy15926e72023-07-31 23:22:02 -050053 unsigned int id = fvp_pwrc_core_id(mpidr);
54
Dan Handley2b6b5742015-03-19 19:17:53 +000055 arm_lock_get();
Madhukar Pappireddy15926e72023-07-31 23:22:02 -050056 mmio_write_32(PWRC_BASE + PPONR_OFF, id);
Dan Handley2b6b5742015-03-19 19:17:53 +000057 arm_lock_release();
Achin Gupta4f6ad662013-10-25 09:08:21 +010058}
59
Soby Mathewa0fedc42016-06-16 14:52:04 +010060void fvp_pwrc_write_ppoffr(u_register_t mpidr)
Achin Gupta4f6ad662013-10-25 09:08:21 +010061{
Madhukar Pappireddy15926e72023-07-31 23:22:02 -050062 unsigned int id = fvp_pwrc_core_id(mpidr);
63
Dan Handley2b6b5742015-03-19 19:17:53 +000064 arm_lock_get();
Madhukar Pappireddy15926e72023-07-31 23:22:02 -050065 mmio_write_32(PWRC_BASE + PPOFFR_OFF, id);
Dan Handley2b6b5742015-03-19 19:17:53 +000066 arm_lock_release();
Achin Gupta4f6ad662013-10-25 09:08:21 +010067}
68
Soby Mathewa0fedc42016-06-16 14:52:04 +010069void fvp_pwrc_set_wen(u_register_t mpidr)
Achin Gupta4f6ad662013-10-25 09:08:21 +010070{
Madhukar Pappireddy15926e72023-07-31 23:22:02 -050071 unsigned int id = fvp_pwrc_core_id(mpidr);
72
Dan Handley2b6b5742015-03-19 19:17:53 +000073 arm_lock_get();
Achin Gupta4f6ad662013-10-25 09:08:21 +010074 mmio_write_32(PWRC_BASE + PWKUPR_OFF,
Madhukar Pappireddy15926e72023-07-31 23:22:02 -050075 (unsigned int) (PWKUPR_WEN | id));
Dan Handley2b6b5742015-03-19 19:17:53 +000076 arm_lock_release();
Achin Gupta4f6ad662013-10-25 09:08:21 +010077}
78
Soby Mathewa0fedc42016-06-16 14:52:04 +010079void fvp_pwrc_clr_wen(u_register_t mpidr)
Achin Guptab127cdb2013-11-12 16:40:00 +000080{
Madhukar Pappireddy15926e72023-07-31 23:22:02 -050081 unsigned int id = fvp_pwrc_core_id(mpidr);
82
Dan Handley2b6b5742015-03-19 19:17:53 +000083 arm_lock_get();
Madhukar Pappireddy15926e72023-07-31 23:22:02 -050084 mmio_write_32(PWRC_BASE + PWKUPR_OFF, id);
Dan Handley2b6b5742015-03-19 19:17:53 +000085 arm_lock_release();
Achin Guptab127cdb2013-11-12 16:40:00 +000086}
87
Soby Mathewa0fedc42016-06-16 14:52:04 +010088void fvp_pwrc_write_pcoffr(u_register_t mpidr)
Achin Gupta4f6ad662013-10-25 09:08:21 +010089{
Madhukar Pappireddy15926e72023-07-31 23:22:02 -050090 unsigned int id = fvp_pwrc_core_id(mpidr);
91
Dan Handley2b6b5742015-03-19 19:17:53 +000092 arm_lock_get();
Madhukar Pappireddy15926e72023-07-31 23:22:02 -050093 mmio_write_32(PWRC_BASE + PCOFFR_OFF, id);
Dan Handley2b6b5742015-03-19 19:17:53 +000094 arm_lock_release();
Achin Gupta4f6ad662013-10-25 09:08:21 +010095}
96
97/* Nothing else to do here apart from initializing the lock */
Daniel Boulbyf45a4bb2018-09-18 13:26:03 +010098void __init plat_arm_pwrc_setup(void)
Achin Gupta4f6ad662013-10-25 09:08:21 +010099{
Dan Handley2b6b5742015-03-19 19:17:53 +0000100 arm_lock_init();
Achin Gupta4f6ad662013-10-25 09:08:21 +0100101}
102
103
104