xref: /rk3399_ARM-atf/plat/mediatek/mt8183/plat_dcm.c (revision 7352f329e8db1ee655ef1a062ef6fc6dabb3bec2)
1*7352f329Skenny liang /*
2*7352f329Skenny liang  * Copyright (c) 2019, MediaTek Inc. All rights reserved.
3*7352f329Skenny liang  *
4*7352f329Skenny liang  * SPDX-License-Identifier: BSD-3-Clause
5*7352f329Skenny liang  */
6*7352f329Skenny liang 
7*7352f329Skenny liang #include <arch.h>
8*7352f329Skenny liang #include <lib/bakery_lock.h>
9*7352f329Skenny liang #include <drivers/console.h>
10*7352f329Skenny liang #include <common/debug.h>
11*7352f329Skenny liang #include <lib/mmio.h>
12*7352f329Skenny liang #include <plat_dcm.h>
13*7352f329Skenny liang #include <plat_private.h>
14*7352f329Skenny liang #include <plat_dcm.h>
15*7352f329Skenny liang #include <plat/common/platform.h>
16*7352f329Skenny liang #include <platform_def.h>
17*7352f329Skenny liang #include <mtk_plat_common.h>
18*7352f329Skenny liang 
19*7352f329Skenny liang #define PWR_STATUS                     (SPM_BASE + 0x180)
20*7352f329Skenny liang 
21*7352f329Skenny liang uint64_t plat_dcm_mcsi_a_addr;
22*7352f329Skenny liang uint32_t plat_dcm_mcsi_a_val;
23*7352f329Skenny liang static int plat_dcm_init_type;
24*7352f329Skenny liang static unsigned int dcm_big_core_cnt;
25*7352f329Skenny liang int plat_dcm_initiated;
26*7352f329Skenny liang 
27*7352f329Skenny liang #define PWR_STA_BIG_MP_MASK	(0x1 << 15)
28*7352f329Skenny liang 
29*7352f329Skenny liang DEFINE_BAKERY_LOCK(dcm_lock);
30*7352f329Skenny liang 
31*7352f329Skenny liang void dcm_lock_init(void)
32*7352f329Skenny liang {
33*7352f329Skenny liang 	bakery_lock_init(&dcm_lock);
34*7352f329Skenny liang }
35*7352f329Skenny liang 
36*7352f329Skenny liang void dcm_lock_get(void)
37*7352f329Skenny liang {
38*7352f329Skenny liang 	bakery_lock_get(&dcm_lock);
39*7352f329Skenny liang }
40*7352f329Skenny liang 
41*7352f329Skenny liang void dcm_lock_release(void)
42*7352f329Skenny liang {
43*7352f329Skenny liang 	bakery_lock_release(&dcm_lock);
44*7352f329Skenny liang }
45*7352f329Skenny liang 
46*7352f329Skenny liang void plat_dcm_mcsi_a_backup(void)
47*7352f329Skenny liang {
48*7352f329Skenny liang }
49*7352f329Skenny liang 
50*7352f329Skenny liang void plat_dcm_mcsi_a_restore(void)
51*7352f329Skenny liang {
52*7352f329Skenny liang }
53*7352f329Skenny liang 
54*7352f329Skenny liang void plat_dcm_rgu_enable(void)
55*7352f329Skenny liang {
56*7352f329Skenny liang }
57*7352f329Skenny liang 
58*7352f329Skenny liang void plat_dcm_big_core_sync(short on)
59*7352f329Skenny liang {
60*7352f329Skenny liang 	/* Check if Big cluster power is existed */
61*7352f329Skenny liang 	if (!(mmio_read_32(PWR_STATUS) & PWR_STA_BIG_MP_MASK))
62*7352f329Skenny liang 		return;
63*7352f329Skenny liang 
64*7352f329Skenny liang 	if (on) {
65*7352f329Skenny liang 		mmio_write_32(MP2_SYNC_DCM,
66*7352f329Skenny liang 			      (mmio_read_32(MP2_SYNC_DCM) & ~MP2_SYNC_DCM_MASK)
67*7352f329Skenny liang 			      | MP2_SYNC_DCM_ON);
68*7352f329Skenny liang 		dcm_big_core_cnt++;
69*7352f329Skenny liang 	} else
70*7352f329Skenny liang 		mmio_write_32(MP2_SYNC_DCM,
71*7352f329Skenny liang 			      (mmio_read_32(MP2_SYNC_DCM) & ~MP2_SYNC_DCM_MASK)
72*7352f329Skenny liang 			      | MP2_SYNC_DCM_OFF);
73*7352f329Skenny liang }
74*7352f329Skenny liang 
75*7352f329Skenny liang void plat_dcm_restore_cluster_on(unsigned long mpidr)
76*7352f329Skenny liang {
77*7352f329Skenny liang 	unsigned long cluster_id =
78*7352f329Skenny liang 		(mpidr & MPIDR_CLUSTER_MASK) >> MPIDR_AFFINITY_BITS;
79*7352f329Skenny liang 
80*7352f329Skenny liang 	switch (cluster_id) {
81*7352f329Skenny liang 	case 0x1:
82*7352f329Skenny liang 		dcm_lock_get();
83*7352f329Skenny liang 		if (plat_dcm_init_type & BIG_CORE_DCM_TYPE)
84*7352f329Skenny liang 			plat_dcm_big_core_sync(1);
85*7352f329Skenny liang 		else
86*7352f329Skenny liang 			plat_dcm_big_core_sync(0);
87*7352f329Skenny liang 		dcm_lock_release();
88*7352f329Skenny liang 		break;
89*7352f329Skenny liang 	default:
90*7352f329Skenny liang 		break;
91*7352f329Skenny liang 	}
92*7352f329Skenny liang }
93*7352f329Skenny liang 
94*7352f329Skenny liang void plat_dcm_msg_handler(uint64_t x1)
95*7352f329Skenny liang {
96*7352f329Skenny liang 	plat_dcm_init_type = x1 & ALL_DCM_TYPE;
97*7352f329Skenny liang }
98*7352f329Skenny liang 
99*7352f329Skenny liang unsigned long plat_dcm_get_enabled_cnt(uint64_t type)
100*7352f329Skenny liang {
101*7352f329Skenny liang 	switch (type) {
102*7352f329Skenny liang 	case BIG_CORE_DCM_TYPE:
103*7352f329Skenny liang 		return dcm_big_core_cnt;
104*7352f329Skenny liang 	default:
105*7352f329Skenny liang 		return 0;
106*7352f329Skenny liang 	}
107*7352f329Skenny liang }
108*7352f329Skenny liang 
109*7352f329Skenny liang void plat_dcm_init(void)
110*7352f329Skenny liang {
111*7352f329Skenny liang 	dcm_lock_init();
112*7352f329Skenny liang }
113