xref: /openbmc/linux/drivers/gpu/drm/amd/amdgpu/soc21.c (revision fa2df4aa)
171199aa4SStanley.Yang /*
271199aa4SStanley.Yang  * Copyright 2021 Advanced Micro Devices, Inc.
371199aa4SStanley.Yang  *
471199aa4SStanley.Yang  * Permission is hereby granted, free of charge, to any person obtaining a
571199aa4SStanley.Yang  * copy of this software and associated documentation files (the "Software"),
671199aa4SStanley.Yang  * to deal in the Software without restriction, including without limitation
771199aa4SStanley.Yang  * the rights to use, copy, modify, merge, publish, distribute, sublicense,
871199aa4SStanley.Yang  * and/or sell copies of the Software, and to permit persons to whom the
971199aa4SStanley.Yang  * Software is furnished to do so, subject to the following conditions:
1071199aa4SStanley.Yang  *
1171199aa4SStanley.Yang  * The above copyright notice and this permission notice shall be included in
1271199aa4SStanley.Yang  * all copies or substantial portions of the Software.
1371199aa4SStanley.Yang  *
1471199aa4SStanley.Yang  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
1571199aa4SStanley.Yang  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
1671199aa4SStanley.Yang  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
1771199aa4SStanley.Yang  * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR
1871199aa4SStanley.Yang  * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
1971199aa4SStanley.Yang  * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
2071199aa4SStanley.Yang  * OTHER DEALINGS IN THE SOFTWARE.
2171199aa4SStanley.Yang  *
2271199aa4SStanley.Yang  */
2371199aa4SStanley.Yang #include <linux/firmware.h>
2471199aa4SStanley.Yang #include <linux/slab.h>
2571199aa4SStanley.Yang #include <linux/module.h>
2671199aa4SStanley.Yang #include <linux/pci.h>
2771199aa4SStanley.Yang 
2871199aa4SStanley.Yang #include "amdgpu.h"
2971199aa4SStanley.Yang #include "amdgpu_atombios.h"
3071199aa4SStanley.Yang #include "amdgpu_ih.h"
3171199aa4SStanley.Yang #include "amdgpu_uvd.h"
3271199aa4SStanley.Yang #include "amdgpu_vce.h"
3371199aa4SStanley.Yang #include "amdgpu_ucode.h"
3471199aa4SStanley.Yang #include "amdgpu_psp.h"
3571199aa4SStanley.Yang #include "amdgpu_smu.h"
3671199aa4SStanley.Yang #include "atom.h"
3771199aa4SStanley.Yang #include "amd_pcie.h"
3871199aa4SStanley.Yang 
3971199aa4SStanley.Yang #include "gc/gc_11_0_0_offset.h"
4071199aa4SStanley.Yang #include "gc/gc_11_0_0_sh_mask.h"
4171199aa4SStanley.Yang #include "mp/mp_13_0_0_offset.h"
4271199aa4SStanley.Yang 
4371199aa4SStanley.Yang #include "soc15.h"
4471199aa4SStanley.Yang #include "soc15_common.h"
45caa5eadcSEvan Quan #include "soc21.h"
4639dd895dSYuBiao Wang #include "mxgpu_nv.h"
4771199aa4SStanley.Yang 
4871199aa4SStanley.Yang static const struct amd_ip_funcs soc21_common_ip_funcs;
4971199aa4SStanley.Yang 
509ac0edaaSJames Zhu /* SOC21 */
5106d82d87SRan Sun static const struct amdgpu_video_codec_info vcn_4_0_0_video_codecs_encode_array_vcn0[] = {
529ac0edaaSJames Zhu 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_MPEG4_AVC, 4096, 2304, 0)},
53b476ae1dSThong 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_HEVC, 8192, 4352, 0)},
54f732e2b3SAlex Deucher 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_AV1, 8192, 4352, 0)},
559ac0edaaSJames Zhu };
569ac0edaaSJames Zhu 
5706d82d87SRan Sun static const struct amdgpu_video_codec_info vcn_4_0_0_video_codecs_encode_array_vcn1[] = {
58a6de636eSAlex Deucher 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_MPEG4_AVC, 4096, 2304, 0)},
59b476ae1dSThong 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_HEVC, 8192, 4352, 0)},
609ac0edaaSJames Zhu };
619ac0edaaSJames Zhu 
6206d82d87SRan Sun static const struct amdgpu_video_codecs vcn_4_0_0_video_codecs_encode_vcn0 = {
63a6de636eSAlex Deucher 	.codec_count = ARRAY_SIZE(vcn_4_0_0_video_codecs_encode_array_vcn0),
64a6de636eSAlex Deucher 	.codec_array = vcn_4_0_0_video_codecs_encode_array_vcn0,
65a6de636eSAlex Deucher };
66a6de636eSAlex Deucher 
6706d82d87SRan Sun static const struct amdgpu_video_codecs vcn_4_0_0_video_codecs_encode_vcn1 = {
68a6de636eSAlex Deucher 	.codec_count = ARRAY_SIZE(vcn_4_0_0_video_codecs_encode_array_vcn1),
69a6de636eSAlex Deucher 	.codec_array = vcn_4_0_0_video_codecs_encode_array_vcn1,
70a6de636eSAlex Deucher };
71a6de636eSAlex Deucher 
7206d82d87SRan Sun static const struct amdgpu_video_codec_info vcn_4_0_0_video_codecs_decode_array_vcn0[] = {
7365009bf2SVeerabadhran Gopalakrishnan 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_MPEG4_AVC, 4096, 4096, 52)},
749ac0edaaSJames Zhu 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_HEVC, 8192, 4352, 186)},
759ac0edaaSJames Zhu 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_JPEG, 4096, 4096, 0)},
769ac0edaaSJames Zhu 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_VP9, 8192, 4352, 0)},
779ac0edaaSJames Zhu 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_AV1, 8192, 4352, 0)},
789ac0edaaSJames Zhu };
799ac0edaaSJames Zhu 
8006d82d87SRan Sun static const struct amdgpu_video_codec_info vcn_4_0_0_video_codecs_decode_array_vcn1[] = {
81a6de636eSAlex Deucher 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_MPEG4_AVC, 4096, 4096, 52)},
82a6de636eSAlex Deucher 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_HEVC, 8192, 4352, 186)},
83a6de636eSAlex Deucher 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_JPEG, 4096, 4096, 0)},
84a6de636eSAlex Deucher 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_VP9, 8192, 4352, 0)},
85a6de636eSAlex Deucher };
86a6de636eSAlex Deucher 
8706d82d87SRan Sun static const struct amdgpu_video_codecs vcn_4_0_0_video_codecs_decode_vcn0 = {
88a6de636eSAlex Deucher 	.codec_count = ARRAY_SIZE(vcn_4_0_0_video_codecs_decode_array_vcn0),
89a6de636eSAlex Deucher 	.codec_array = vcn_4_0_0_video_codecs_decode_array_vcn0,
90a6de636eSAlex Deucher };
91a6de636eSAlex Deucher 
9206d82d87SRan Sun static const struct amdgpu_video_codecs vcn_4_0_0_video_codecs_decode_vcn1 = {
93a6de636eSAlex Deucher 	.codec_count = ARRAY_SIZE(vcn_4_0_0_video_codecs_decode_array_vcn1),
94a6de636eSAlex Deucher 	.codec_array = vcn_4_0_0_video_codecs_decode_array_vcn1,
959ac0edaaSJames Zhu };
969ac0edaaSJames Zhu 
97dcaf5000SJane Jian /* SRIOV SOC21, not const since data is controlled by host */
98dcaf5000SJane Jian static struct amdgpu_video_codec_info sriov_vcn_4_0_0_video_codecs_encode_array_vcn0[] = {
99dcaf5000SJane Jian 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_MPEG4_AVC, 4096, 2304, 0)},
100dcaf5000SJane Jian 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_HEVC, 4096, 2304, 0)},
101dcaf5000SJane Jian 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_AV1, 8192, 4352, 0)},
102dcaf5000SJane Jian };
103dcaf5000SJane Jian 
104dcaf5000SJane Jian static struct amdgpu_video_codec_info sriov_vcn_4_0_0_video_codecs_encode_array_vcn1[] = {
105dcaf5000SJane Jian 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_MPEG4_AVC, 4096, 2304, 0)},
106dcaf5000SJane Jian 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_HEVC, 4096, 2304, 0)},
107dcaf5000SJane Jian };
108dcaf5000SJane Jian 
109dcaf5000SJane Jian static struct amdgpu_video_codecs sriov_vcn_4_0_0_video_codecs_encode_vcn0 = {
110dcaf5000SJane Jian 	.codec_count = ARRAY_SIZE(sriov_vcn_4_0_0_video_codecs_encode_array_vcn0),
111dcaf5000SJane Jian 	.codec_array = sriov_vcn_4_0_0_video_codecs_encode_array_vcn0,
112dcaf5000SJane Jian };
113dcaf5000SJane Jian 
114dcaf5000SJane Jian static struct amdgpu_video_codecs sriov_vcn_4_0_0_video_codecs_encode_vcn1 = {
115dcaf5000SJane Jian 	.codec_count = ARRAY_SIZE(sriov_vcn_4_0_0_video_codecs_encode_array_vcn1),
116dcaf5000SJane Jian 	.codec_array = sriov_vcn_4_0_0_video_codecs_encode_array_vcn1,
117dcaf5000SJane Jian };
118dcaf5000SJane Jian 
119dcaf5000SJane Jian static struct amdgpu_video_codec_info sriov_vcn_4_0_0_video_codecs_decode_array_vcn0[] = {
120dcaf5000SJane Jian 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_MPEG2, 4096, 4096, 3)},
121dcaf5000SJane Jian 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_MPEG4, 4096, 4096, 5)},
122dcaf5000SJane Jian 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_MPEG4_AVC, 4096, 4096, 52)},
123dcaf5000SJane Jian 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_VC1, 4096, 4096, 4)},
124dcaf5000SJane Jian 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_HEVC, 8192, 4352, 186)},
125dcaf5000SJane Jian 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_JPEG, 4096, 4096, 0)},
126dcaf5000SJane Jian 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_VP9, 8192, 4352, 0)},
127dcaf5000SJane Jian 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_AV1, 8192, 4352, 0)},
128dcaf5000SJane Jian };
129dcaf5000SJane Jian 
130dcaf5000SJane Jian static struct amdgpu_video_codec_info sriov_vcn_4_0_0_video_codecs_decode_array_vcn1[] = {
131dcaf5000SJane Jian 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_MPEG2, 4096, 4096, 3)},
132dcaf5000SJane Jian 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_MPEG4, 4096, 4096, 5)},
133dcaf5000SJane Jian 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_MPEG4_AVC, 4096, 4096, 52)},
134dcaf5000SJane Jian 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_VC1, 4096, 4096, 4)},
135dcaf5000SJane Jian 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_HEVC, 8192, 4352, 186)},
136dcaf5000SJane Jian 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_JPEG, 4096, 4096, 0)},
137dcaf5000SJane Jian 	{codec_info_build(AMDGPU_INFO_VIDEO_CAPS_CODEC_IDX_VP9, 8192, 4352, 0)},
138dcaf5000SJane Jian };
139dcaf5000SJane Jian 
140dcaf5000SJane Jian static struct amdgpu_video_codecs sriov_vcn_4_0_0_video_codecs_decode_vcn0 = {
141dcaf5000SJane Jian 	.codec_count = ARRAY_SIZE(sriov_vcn_4_0_0_video_codecs_decode_array_vcn0),
142dcaf5000SJane Jian 	.codec_array = sriov_vcn_4_0_0_video_codecs_decode_array_vcn0,
143dcaf5000SJane Jian };
144dcaf5000SJane Jian 
145dcaf5000SJane Jian static struct amdgpu_video_codecs sriov_vcn_4_0_0_video_codecs_decode_vcn1 = {
146dcaf5000SJane Jian 	.codec_count = ARRAY_SIZE(sriov_vcn_4_0_0_video_codecs_decode_array_vcn1),
147dcaf5000SJane Jian 	.codec_array = sriov_vcn_4_0_0_video_codecs_decode_array_vcn1,
148dcaf5000SJane Jian };
149dcaf5000SJane Jian 
soc21_query_video_codecs(struct amdgpu_device * adev,bool encode,const struct amdgpu_video_codecs ** codecs)1509ac0edaaSJames Zhu static int soc21_query_video_codecs(struct amdgpu_device *adev, bool encode,
1519ac0edaaSJames Zhu 				 const struct amdgpu_video_codecs **codecs)
1529ac0edaaSJames Zhu {
153a6de636eSAlex Deucher 	if (adev->vcn.num_vcn_inst == hweight8(adev->vcn.harvest_config))
154a6de636eSAlex Deucher 		return -EINVAL;
1559ac0edaaSJames Zhu 
156a6de636eSAlex Deucher 	switch (adev->ip_versions[UVD_HWIP][0]) {
1579ac0edaaSJames Zhu 	case IP_VERSION(4, 0, 0):
1581c0a9036SSonny Jiang 	case IP_VERSION(4, 0, 2):
159d068b700SVeerabadhran Gopalakrishnan 	case IP_VERSION(4, 0, 4):
160dcaf5000SJane Jian 		if (amdgpu_sriov_vf(adev)) {
161dcaf5000SJane Jian 			if ((adev->vcn.harvest_config & AMDGPU_VCN_HARVEST_VCN0) ||
162dcaf5000SJane Jian 			!amdgpu_sriov_is_av1_support(adev)) {
163dcaf5000SJane Jian 				if (encode)
164dcaf5000SJane Jian 					*codecs = &sriov_vcn_4_0_0_video_codecs_encode_vcn1;
165dcaf5000SJane Jian 				else
166dcaf5000SJane Jian 					*codecs = &sriov_vcn_4_0_0_video_codecs_decode_vcn1;
167dcaf5000SJane Jian 			} else {
168dcaf5000SJane Jian 				if (encode)
169dcaf5000SJane Jian 					*codecs = &sriov_vcn_4_0_0_video_codecs_encode_vcn0;
170dcaf5000SJane Jian 				else
171dcaf5000SJane Jian 					*codecs = &sriov_vcn_4_0_0_video_codecs_decode_vcn0;
172dcaf5000SJane Jian 			}
173dcaf5000SJane Jian 		} else {
174dcaf5000SJane Jian 			if ((adev->vcn.harvest_config & AMDGPU_VCN_HARVEST_VCN0)) {
1759ac0edaaSJames Zhu 				if (encode)
176a6de636eSAlex Deucher 					*codecs = &vcn_4_0_0_video_codecs_encode_vcn1;
1779ac0edaaSJames Zhu 				else
178a6de636eSAlex Deucher 					*codecs = &vcn_4_0_0_video_codecs_decode_vcn1;
179a6de636eSAlex Deucher 			} else {
180a6de636eSAlex Deucher 				if (encode)
181a6de636eSAlex Deucher 					*codecs = &vcn_4_0_0_video_codecs_encode_vcn0;
182a6de636eSAlex Deucher 				else
183a6de636eSAlex Deucher 					*codecs = &vcn_4_0_0_video_codecs_decode_vcn0;
184a6de636eSAlex Deucher 			}
185dcaf5000SJane Jian 		}
1869ac0edaaSJames Zhu 		return 0;
1879ac0edaaSJames Zhu 	default:
1889ac0edaaSJames Zhu 		return -EINVAL;
1899ac0edaaSJames Zhu 	}
1909ac0edaaSJames Zhu }
19171199aa4SStanley.Yang 
soc21_didt_rreg(struct amdgpu_device * adev,u32 reg)19271199aa4SStanley.Yang static u32 soc21_didt_rreg(struct amdgpu_device *adev, u32 reg)
19371199aa4SStanley.Yang {
19471199aa4SStanley.Yang 	unsigned long flags, address, data;
19571199aa4SStanley.Yang 	u32 r;
19671199aa4SStanley.Yang 
19771199aa4SStanley.Yang 	address = SOC15_REG_OFFSET(GC, 0, regDIDT_IND_INDEX);
19871199aa4SStanley.Yang 	data = SOC15_REG_OFFSET(GC, 0, regDIDT_IND_DATA);
19971199aa4SStanley.Yang 
20071199aa4SStanley.Yang 	spin_lock_irqsave(&adev->didt_idx_lock, flags);
20171199aa4SStanley.Yang 	WREG32(address, (reg));
20271199aa4SStanley.Yang 	r = RREG32(data);
20371199aa4SStanley.Yang 	spin_unlock_irqrestore(&adev->didt_idx_lock, flags);
20471199aa4SStanley.Yang 	return r;
20571199aa4SStanley.Yang }
20671199aa4SStanley.Yang 
soc21_didt_wreg(struct amdgpu_device * adev,u32 reg,u32 v)20771199aa4SStanley.Yang static void soc21_didt_wreg(struct amdgpu_device *adev, u32 reg, u32 v)
20871199aa4SStanley.Yang {
20971199aa4SStanley.Yang 	unsigned long flags, address, data;
21071199aa4SStanley.Yang 
21171199aa4SStanley.Yang 	address = SOC15_REG_OFFSET(GC, 0, regDIDT_IND_INDEX);
21271199aa4SStanley.Yang 	data = SOC15_REG_OFFSET(GC, 0, regDIDT_IND_DATA);
21371199aa4SStanley.Yang 
21471199aa4SStanley.Yang 	spin_lock_irqsave(&adev->didt_idx_lock, flags);
21571199aa4SStanley.Yang 	WREG32(address, (reg));
21671199aa4SStanley.Yang 	WREG32(data, (v));
21771199aa4SStanley.Yang 	spin_unlock_irqrestore(&adev->didt_idx_lock, flags);
21871199aa4SStanley.Yang }
21971199aa4SStanley.Yang 
soc21_get_config_memsize(struct amdgpu_device * adev)22071199aa4SStanley.Yang static u32 soc21_get_config_memsize(struct amdgpu_device *adev)
22171199aa4SStanley.Yang {
22271199aa4SStanley.Yang 	return adev->nbio.funcs->get_memsize(adev);
22371199aa4SStanley.Yang }
22471199aa4SStanley.Yang 
soc21_get_xclk(struct amdgpu_device * adev)22571199aa4SStanley.Yang static u32 soc21_get_xclk(struct amdgpu_device *adev)
22671199aa4SStanley.Yang {
22771199aa4SStanley.Yang 	return adev->clock.spll.reference_freq;
22871199aa4SStanley.Yang }
22971199aa4SStanley.Yang 
23071199aa4SStanley.Yang 
soc21_grbm_select(struct amdgpu_device * adev,u32 me,u32 pipe,u32 queue,u32 vmid)23171199aa4SStanley.Yang void soc21_grbm_select(struct amdgpu_device *adev,
23271199aa4SStanley.Yang 		     u32 me, u32 pipe, u32 queue, u32 vmid)
23371199aa4SStanley.Yang {
23471199aa4SStanley.Yang 	u32 grbm_gfx_cntl = 0;
23571199aa4SStanley.Yang 	grbm_gfx_cntl = REG_SET_FIELD(grbm_gfx_cntl, GRBM_GFX_CNTL, PIPEID, pipe);
23671199aa4SStanley.Yang 	grbm_gfx_cntl = REG_SET_FIELD(grbm_gfx_cntl, GRBM_GFX_CNTL, MEID, me);
23771199aa4SStanley.Yang 	grbm_gfx_cntl = REG_SET_FIELD(grbm_gfx_cntl, GRBM_GFX_CNTL, VMID, vmid);
23871199aa4SStanley.Yang 	grbm_gfx_cntl = REG_SET_FIELD(grbm_gfx_cntl, GRBM_GFX_CNTL, QUEUEID, queue);
23971199aa4SStanley.Yang 
240bbb860d4SYifan Zha 	WREG32_SOC15(GC, 0, regGRBM_GFX_CNTL, grbm_gfx_cntl);
24171199aa4SStanley.Yang }
24271199aa4SStanley.Yang 
soc21_read_disabled_bios(struct amdgpu_device * adev)24371199aa4SStanley.Yang static bool soc21_read_disabled_bios(struct amdgpu_device *adev)
24471199aa4SStanley.Yang {
24571199aa4SStanley.Yang 	/* todo */
24671199aa4SStanley.Yang 	return false;
24771199aa4SStanley.Yang }
24871199aa4SStanley.Yang 
24971199aa4SStanley.Yang static struct soc15_allowed_register_entry soc21_allowed_read_registers[] = {
25071199aa4SStanley.Yang 	{ SOC15_REG_ENTRY(GC, 0, regGRBM_STATUS)},
25171199aa4SStanley.Yang 	{ SOC15_REG_ENTRY(GC, 0, regGRBM_STATUS2)},
25271199aa4SStanley.Yang 	{ SOC15_REG_ENTRY(GC, 0, regGRBM_STATUS_SE0)},
25371199aa4SStanley.Yang 	{ SOC15_REG_ENTRY(GC, 0, regGRBM_STATUS_SE1)},
25471199aa4SStanley.Yang 	{ SOC15_REG_ENTRY(GC, 0, regGRBM_STATUS_SE2)},
25571199aa4SStanley.Yang 	{ SOC15_REG_ENTRY(GC, 0, regGRBM_STATUS_SE3)},
25671199aa4SStanley.Yang 	{ SOC15_REG_ENTRY(SDMA0, 0, regSDMA0_STATUS_REG)},
25771199aa4SStanley.Yang 	{ SOC15_REG_ENTRY(SDMA1, 0, regSDMA1_STATUS_REG)},
25871199aa4SStanley.Yang 	{ SOC15_REG_ENTRY(GC, 0, regCP_STAT)},
25971199aa4SStanley.Yang 	{ SOC15_REG_ENTRY(GC, 0, regCP_STALLED_STAT1)},
26071199aa4SStanley.Yang 	{ SOC15_REG_ENTRY(GC, 0, regCP_STALLED_STAT2)},
26171199aa4SStanley.Yang 	{ SOC15_REG_ENTRY(GC, 0, regCP_STALLED_STAT3)},
26271199aa4SStanley.Yang 	{ SOC15_REG_ENTRY(GC, 0, regCP_CPF_BUSY_STAT)},
26371199aa4SStanley.Yang 	{ SOC15_REG_ENTRY(GC, 0, regCP_CPF_STALLED_STAT1)},
26471199aa4SStanley.Yang 	{ SOC15_REG_ENTRY(GC, 0, regCP_CPF_STATUS)},
26571199aa4SStanley.Yang 	{ SOC15_REG_ENTRY(GC, 0, regCP_CPC_BUSY_STAT)},
26671199aa4SStanley.Yang 	{ SOC15_REG_ENTRY(GC, 0, regCP_CPC_STALLED_STAT1)},
26771199aa4SStanley.Yang 	{ SOC15_REG_ENTRY(GC, 0, regCP_CPC_STATUS)},
26871199aa4SStanley.Yang 	{ SOC15_REG_ENTRY(GC, 0, regGB_ADDR_CONFIG)},
26971199aa4SStanley.Yang };
27071199aa4SStanley.Yang 
soc21_read_indexed_register(struct amdgpu_device * adev,u32 se_num,u32 sh_num,u32 reg_offset)27171199aa4SStanley.Yang static uint32_t soc21_read_indexed_register(struct amdgpu_device *adev, u32 se_num,
27271199aa4SStanley.Yang 					 u32 sh_num, u32 reg_offset)
27371199aa4SStanley.Yang {
27471199aa4SStanley.Yang 	uint32_t val;
27571199aa4SStanley.Yang 
27671199aa4SStanley.Yang 	mutex_lock(&adev->grbm_idx_mutex);
27771199aa4SStanley.Yang 	if (se_num != 0xffffffff || sh_num != 0xffffffff)
278d51ac6d0SLe Ma 		amdgpu_gfx_select_se_sh(adev, se_num, sh_num, 0xffffffff, 0);
27971199aa4SStanley.Yang 
28071199aa4SStanley.Yang 	val = RREG32(reg_offset);
28171199aa4SStanley.Yang 
28271199aa4SStanley.Yang 	if (se_num != 0xffffffff || sh_num != 0xffffffff)
283d51ac6d0SLe Ma 		amdgpu_gfx_select_se_sh(adev, 0xffffffff, 0xffffffff, 0xffffffff, 0);
28471199aa4SStanley.Yang 	mutex_unlock(&adev->grbm_idx_mutex);
28571199aa4SStanley.Yang 	return val;
28671199aa4SStanley.Yang }
28771199aa4SStanley.Yang 
soc21_get_register_value(struct amdgpu_device * adev,bool indexed,u32 se_num,u32 sh_num,u32 reg_offset)28871199aa4SStanley.Yang static uint32_t soc21_get_register_value(struct amdgpu_device *adev,
28971199aa4SStanley.Yang 				      bool indexed, u32 se_num,
29071199aa4SStanley.Yang 				      u32 sh_num, u32 reg_offset)
29171199aa4SStanley.Yang {
29271199aa4SStanley.Yang 	if (indexed) {
29371199aa4SStanley.Yang 		return soc21_read_indexed_register(adev, se_num, sh_num, reg_offset);
29471199aa4SStanley.Yang 	} else {
29571199aa4SStanley.Yang 		if (reg_offset == SOC15_REG_OFFSET(GC, 0, regGB_ADDR_CONFIG) && adev->gfx.config.gb_addr_config)
29671199aa4SStanley.Yang 			return adev->gfx.config.gb_addr_config;
29771199aa4SStanley.Yang 		return RREG32(reg_offset);
29871199aa4SStanley.Yang 	}
29971199aa4SStanley.Yang }
30071199aa4SStanley.Yang 
soc21_read_register(struct amdgpu_device * adev,u32 se_num,u32 sh_num,u32 reg_offset,u32 * value)30171199aa4SStanley.Yang static int soc21_read_register(struct amdgpu_device *adev, u32 se_num,
30271199aa4SStanley.Yang 			    u32 sh_num, u32 reg_offset, u32 *value)
30371199aa4SStanley.Yang {
30471199aa4SStanley.Yang 	uint32_t i;
30571199aa4SStanley.Yang 	struct soc15_allowed_register_entry  *en;
30671199aa4SStanley.Yang 
30771199aa4SStanley.Yang 	*value = 0;
30871199aa4SStanley.Yang 	for (i = 0; i < ARRAY_SIZE(soc21_allowed_read_registers); i++) {
30971199aa4SStanley.Yang 		en = &soc21_allowed_read_registers[i];
310ba137e64SAlex Deucher 		if (!adev->reg_offset[en->hwip][en->inst])
311ba137e64SAlex Deucher 			continue;
312ba137e64SAlex Deucher 		else if (reg_offset != (adev->reg_offset[en->hwip][en->inst][en->seg]
313bf1781e1SAlex Deucher 					+ en->reg_offset))
31471199aa4SStanley.Yang 			continue;
31571199aa4SStanley.Yang 
31671199aa4SStanley.Yang 		*value = soc21_get_register_value(adev,
31771199aa4SStanley.Yang 					       soc21_allowed_read_registers[i].grbm_indexed,
31871199aa4SStanley.Yang 					       se_num, sh_num, reg_offset);
31971199aa4SStanley.Yang 		return 0;
32071199aa4SStanley.Yang 	}
32171199aa4SStanley.Yang 	return -EINVAL;
32271199aa4SStanley.Yang }
32371199aa4SStanley.Yang 
32471199aa4SStanley.Yang #if 0
32571199aa4SStanley.Yang static int soc21_asic_mode1_reset(struct amdgpu_device *adev)
32671199aa4SStanley.Yang {
32771199aa4SStanley.Yang 	u32 i;
32871199aa4SStanley.Yang 	int ret = 0;
32971199aa4SStanley.Yang 
33071199aa4SStanley.Yang 	amdgpu_atombios_scratch_regs_engine_hung(adev, true);
33171199aa4SStanley.Yang 
33271199aa4SStanley.Yang 	/* disable BM */
33371199aa4SStanley.Yang 	pci_clear_master(adev->pdev);
33471199aa4SStanley.Yang 
33571199aa4SStanley.Yang 	amdgpu_device_cache_pci_state(adev->pdev);
33671199aa4SStanley.Yang 
33771199aa4SStanley.Yang 	if (amdgpu_dpm_is_mode1_reset_supported(adev)) {
33871199aa4SStanley.Yang 		dev_info(adev->dev, "GPU smu mode1 reset\n");
33971199aa4SStanley.Yang 		ret = amdgpu_dpm_mode1_reset(adev);
34071199aa4SStanley.Yang 	} else {
34171199aa4SStanley.Yang 		dev_info(adev->dev, "GPU psp mode1 reset\n");
34271199aa4SStanley.Yang 		ret = psp_gpu_reset(adev);
34371199aa4SStanley.Yang 	}
34471199aa4SStanley.Yang 
34571199aa4SStanley.Yang 	if (ret)
34671199aa4SStanley.Yang 		dev_err(adev->dev, "GPU mode1 reset failed\n");
34771199aa4SStanley.Yang 	amdgpu_device_load_pci_state(adev->pdev);
34871199aa4SStanley.Yang 
34971199aa4SStanley.Yang 	/* wait for asic to come out of reset */
35071199aa4SStanley.Yang 	for (i = 0; i < adev->usec_timeout; i++) {
35171199aa4SStanley.Yang 		u32 memsize = adev->nbio.funcs->get_memsize(adev);
35271199aa4SStanley.Yang 
35371199aa4SStanley.Yang 		if (memsize != 0xffffffff)
35471199aa4SStanley.Yang 			break;
35571199aa4SStanley.Yang 		udelay(1);
35671199aa4SStanley.Yang 	}
35771199aa4SStanley.Yang 
35871199aa4SStanley.Yang 	amdgpu_atombios_scratch_regs_engine_hung(adev, false);
35971199aa4SStanley.Yang 
36071199aa4SStanley.Yang 	return ret;
36171199aa4SStanley.Yang }
36271199aa4SStanley.Yang #endif
36371199aa4SStanley.Yang 
36471199aa4SStanley.Yang static enum amd_reset_method
soc21_asic_reset_method(struct amdgpu_device * adev)36571199aa4SStanley.Yang soc21_asic_reset_method(struct amdgpu_device *adev)
36671199aa4SStanley.Yang {
36771199aa4SStanley.Yang 	if (amdgpu_reset_method == AMD_RESET_METHOD_MODE1 ||
368ea64228dSAlex Deucher 	    amdgpu_reset_method == AMD_RESET_METHOD_MODE2 ||
36971199aa4SStanley.Yang 	    amdgpu_reset_method == AMD_RESET_METHOD_BACO)
37071199aa4SStanley.Yang 		return amdgpu_reset_method;
37171199aa4SStanley.Yang 
37271199aa4SStanley.Yang 	if (amdgpu_reset_method != -1)
37371199aa4SStanley.Yang 		dev_warn(adev->dev, "Specified reset method:%d isn't supported, using AUTO instead.\n",
37471199aa4SStanley.Yang 				  amdgpu_reset_method);
37571199aa4SStanley.Yang 
37671199aa4SStanley.Yang 	switch (adev->ip_versions[MP1_HWIP][0]) {
37771199aa4SStanley.Yang 	case IP_VERSION(13, 0, 0):
378a53bc321SKenneth Feng 	case IP_VERSION(13, 0, 7):
37960cfad32SKenneth Feng 	case IP_VERSION(13, 0, 10):
38071199aa4SStanley.Yang 		return AMD_RESET_METHOD_MODE1;
381ea64228dSAlex Deucher 	case IP_VERSION(13, 0, 4):
38218ad1885STim Huang 	case IP_VERSION(13, 0, 11):
383ea64228dSAlex Deucher 		return AMD_RESET_METHOD_MODE2;
38471199aa4SStanley.Yang 	default:
38571199aa4SStanley.Yang 		if (amdgpu_dpm_is_baco_supported(adev))
38671199aa4SStanley.Yang 			return AMD_RESET_METHOD_BACO;
38771199aa4SStanley.Yang 		else
38871199aa4SStanley.Yang 			return AMD_RESET_METHOD_MODE1;
38971199aa4SStanley.Yang 	}
39071199aa4SStanley.Yang }
39171199aa4SStanley.Yang 
soc21_asic_reset(struct amdgpu_device * adev)39271199aa4SStanley.Yang static int soc21_asic_reset(struct amdgpu_device *adev)
39371199aa4SStanley.Yang {
39471199aa4SStanley.Yang 	int ret = 0;
39571199aa4SStanley.Yang 
39671199aa4SStanley.Yang 	switch (soc21_asic_reset_method(adev)) {
39771199aa4SStanley.Yang 	case AMD_RESET_METHOD_PCI:
39871199aa4SStanley.Yang 		dev_info(adev->dev, "PCI reset\n");
39971199aa4SStanley.Yang 		ret = amdgpu_device_pci_reset(adev);
40071199aa4SStanley.Yang 		break;
40171199aa4SStanley.Yang 	case AMD_RESET_METHOD_BACO:
40271199aa4SStanley.Yang 		dev_info(adev->dev, "BACO reset\n");
40371199aa4SStanley.Yang 		ret = amdgpu_dpm_baco_reset(adev);
40471199aa4SStanley.Yang 		break;
405ea64228dSAlex Deucher 	case AMD_RESET_METHOD_MODE2:
406ea64228dSAlex Deucher 		dev_info(adev->dev, "MODE2 reset\n");
407ea64228dSAlex Deucher 		ret = amdgpu_dpm_mode2_reset(adev);
408ea64228dSAlex Deucher 		break;
40971199aa4SStanley.Yang 	default:
41071199aa4SStanley.Yang 		dev_info(adev->dev, "MODE1 reset\n");
41171199aa4SStanley.Yang 		ret = amdgpu_device_mode1_reset(adev);
41271199aa4SStanley.Yang 		break;
41371199aa4SStanley.Yang 	}
41471199aa4SStanley.Yang 
41571199aa4SStanley.Yang 	return ret;
41671199aa4SStanley.Yang }
41771199aa4SStanley.Yang 
soc21_set_uvd_clocks(struct amdgpu_device * adev,u32 vclk,u32 dclk)41871199aa4SStanley.Yang static int soc21_set_uvd_clocks(struct amdgpu_device *adev, u32 vclk, u32 dclk)
41971199aa4SStanley.Yang {
42071199aa4SStanley.Yang 	/* todo */
42171199aa4SStanley.Yang 	return 0;
42271199aa4SStanley.Yang }
42371199aa4SStanley.Yang 
soc21_set_vce_clocks(struct amdgpu_device * adev,u32 evclk,u32 ecclk)42471199aa4SStanley.Yang static int soc21_set_vce_clocks(struct amdgpu_device *adev, u32 evclk, u32 ecclk)
42571199aa4SStanley.Yang {
42671199aa4SStanley.Yang 	/* todo */
42771199aa4SStanley.Yang 	return 0;
42871199aa4SStanley.Yang }
42971199aa4SStanley.Yang 
soc21_program_aspm(struct amdgpu_device * adev)43071199aa4SStanley.Yang static void soc21_program_aspm(struct amdgpu_device *adev)
43171199aa4SStanley.Yang {
43262f8f5c3SEvan Quan 	if (!amdgpu_device_should_use_aspm(adev))
43371199aa4SStanley.Yang 		return;
43471199aa4SStanley.Yang 
43562f8f5c3SEvan Quan 	if (!(adev->flags & AMD_IS_APU) &&
43662f8f5c3SEvan Quan 	    (adev->nbio.funcs->program_aspm))
43762f8f5c3SEvan Quan 		adev->nbio.funcs->program_aspm(adev);
43871199aa4SStanley.Yang }
43971199aa4SStanley.Yang 
44006d82d87SRan Sun const struct amdgpu_ip_block_version soc21_common_ip_block = {
44171199aa4SStanley.Yang 	.type = AMD_IP_BLOCK_TYPE_COMMON,
44271199aa4SStanley.Yang 	.major = 1,
44371199aa4SStanley.Yang 	.minor = 0,
44471199aa4SStanley.Yang 	.rev = 0,
44571199aa4SStanley.Yang 	.funcs = &soc21_common_ip_funcs,
44671199aa4SStanley.Yang };
44771199aa4SStanley.Yang 
soc21_need_full_reset(struct amdgpu_device * adev)44871199aa4SStanley.Yang static bool soc21_need_full_reset(struct amdgpu_device *adev)
44971199aa4SStanley.Yang {
450c0ff84cbSLikun Gao 	switch (adev->ip_versions[GC_HWIP][0]) {
451c0ff84cbSLikun Gao 	case IP_VERSION(11, 0, 0):
452c0ff84cbSLikun Gao 	case IP_VERSION(11, 0, 2):
4532e26bf1eSYiPeng Chai 	case IP_VERSION(11, 0, 3):
454c0ff84cbSLikun Gao 	default:
45571199aa4SStanley.Yang 		return true;
45671199aa4SStanley.Yang 	}
457c0ff84cbSLikun Gao }
45871199aa4SStanley.Yang 
soc21_need_reset_on_init(struct amdgpu_device * adev)45971199aa4SStanley.Yang static bool soc21_need_reset_on_init(struct amdgpu_device *adev)
46071199aa4SStanley.Yang {
46171199aa4SStanley.Yang 	u32 sol_reg;
46271199aa4SStanley.Yang 
46371199aa4SStanley.Yang 	if (adev->flags & AMD_IS_APU)
46471199aa4SStanley.Yang 		return false;
46571199aa4SStanley.Yang 
46671199aa4SStanley.Yang 	/* Check sOS sign of life register to confirm sys driver and sOS
46771199aa4SStanley.Yang 	 * are already been loaded.
46871199aa4SStanley.Yang 	 */
46971199aa4SStanley.Yang 	sol_reg = RREG32_SOC15(MP0, 0, regMP0_SMN_C2PMSG_81);
47071199aa4SStanley.Yang 	if (sol_reg)
47171199aa4SStanley.Yang 		return true;
47271199aa4SStanley.Yang 
47371199aa4SStanley.Yang 	return false;
47471199aa4SStanley.Yang }
47571199aa4SStanley.Yang 
soc21_init_doorbell_index(struct amdgpu_device * adev)47671199aa4SStanley.Yang static void soc21_init_doorbell_index(struct amdgpu_device *adev)
47771199aa4SStanley.Yang {
47871199aa4SStanley.Yang 	adev->doorbell_index.kiq = AMDGPU_NAVI10_DOORBELL_KIQ;
47971199aa4SStanley.Yang 	adev->doorbell_index.mec_ring0 = AMDGPU_NAVI10_DOORBELL_MEC_RING0;
48071199aa4SStanley.Yang 	adev->doorbell_index.mec_ring1 = AMDGPU_NAVI10_DOORBELL_MEC_RING1;
48171199aa4SStanley.Yang 	adev->doorbell_index.mec_ring2 = AMDGPU_NAVI10_DOORBELL_MEC_RING2;
48271199aa4SStanley.Yang 	adev->doorbell_index.mec_ring3 = AMDGPU_NAVI10_DOORBELL_MEC_RING3;
48371199aa4SStanley.Yang 	adev->doorbell_index.mec_ring4 = AMDGPU_NAVI10_DOORBELL_MEC_RING4;
48471199aa4SStanley.Yang 	adev->doorbell_index.mec_ring5 = AMDGPU_NAVI10_DOORBELL_MEC_RING5;
48571199aa4SStanley.Yang 	adev->doorbell_index.mec_ring6 = AMDGPU_NAVI10_DOORBELL_MEC_RING6;
48671199aa4SStanley.Yang 	adev->doorbell_index.mec_ring7 = AMDGPU_NAVI10_DOORBELL_MEC_RING7;
48771199aa4SStanley.Yang 	adev->doorbell_index.userqueue_start = AMDGPU_NAVI10_DOORBELL_USERQUEUE_START;
48871199aa4SStanley.Yang 	adev->doorbell_index.userqueue_end = AMDGPU_NAVI10_DOORBELL_USERQUEUE_END;
48971199aa4SStanley.Yang 	adev->doorbell_index.gfx_ring0 = AMDGPU_NAVI10_DOORBELL_GFX_RING0;
49071199aa4SStanley.Yang 	adev->doorbell_index.gfx_ring1 = AMDGPU_NAVI10_DOORBELL_GFX_RING1;
491fd0ed91aSJack Xiao 	adev->doorbell_index.gfx_userqueue_start =
492fd0ed91aSJack Xiao 		AMDGPU_NAVI10_DOORBELL_GFX_USERQUEUE_START;
493fd0ed91aSJack Xiao 	adev->doorbell_index.gfx_userqueue_end =
494fd0ed91aSJack Xiao 		AMDGPU_NAVI10_DOORBELL_GFX_USERQUEUE_END;
495b608e785SJack Xiao 	adev->doorbell_index.mes_ring0 = AMDGPU_NAVI10_DOORBELL_MES_RING0;
496b608e785SJack Xiao 	adev->doorbell_index.mes_ring1 = AMDGPU_NAVI10_DOORBELL_MES_RING1;
49771199aa4SStanley.Yang 	adev->doorbell_index.sdma_engine[0] = AMDGPU_NAVI10_DOORBELL_sDMA_ENGINE0;
49871199aa4SStanley.Yang 	adev->doorbell_index.sdma_engine[1] = AMDGPU_NAVI10_DOORBELL_sDMA_ENGINE1;
49971199aa4SStanley.Yang 	adev->doorbell_index.ih = AMDGPU_NAVI10_DOORBELL_IH;
50071199aa4SStanley.Yang 	adev->doorbell_index.vcn.vcn_ring0_1 = AMDGPU_NAVI10_DOORBELL64_VCN0_1;
50171199aa4SStanley.Yang 	adev->doorbell_index.vcn.vcn_ring2_3 = AMDGPU_NAVI10_DOORBELL64_VCN2_3;
50271199aa4SStanley.Yang 	adev->doorbell_index.vcn.vcn_ring4_5 = AMDGPU_NAVI10_DOORBELL64_VCN4_5;
50371199aa4SStanley.Yang 	adev->doorbell_index.vcn.vcn_ring6_7 = AMDGPU_NAVI10_DOORBELL64_VCN6_7;
50471199aa4SStanley.Yang 	adev->doorbell_index.first_non_cp = AMDGPU_NAVI10_DOORBELL64_FIRST_NON_CP;
50571199aa4SStanley.Yang 	adev->doorbell_index.last_non_cp = AMDGPU_NAVI10_DOORBELL64_LAST_NON_CP;
50671199aa4SStanley.Yang 
50771199aa4SStanley.Yang 	adev->doorbell_index.max_assignment = AMDGPU_NAVI10_DOORBELL_MAX_ASSIGNMENT << 1;
50871199aa4SStanley.Yang 	adev->doorbell_index.sdma_doorbell_range = 20;
50971199aa4SStanley.Yang }
51071199aa4SStanley.Yang 
soc21_pre_asic_init(struct amdgpu_device * adev)51171199aa4SStanley.Yang static void soc21_pre_asic_init(struct amdgpu_device *adev)
51271199aa4SStanley.Yang {
51371199aa4SStanley.Yang }
51471199aa4SStanley.Yang 
soc21_update_umd_stable_pstate(struct amdgpu_device * adev,bool enter)51572010239SLikun Gao static int soc21_update_umd_stable_pstate(struct amdgpu_device *adev,
51672010239SLikun Gao 					  bool enter)
51772010239SLikun Gao {
51872010239SLikun Gao 	if (enter)
51986b20703SLe Ma 		amdgpu_gfx_rlc_enter_safe_mode(adev, 0);
52072010239SLikun Gao 	else
52186b20703SLe Ma 		amdgpu_gfx_rlc_exit_safe_mode(adev, 0);
52272010239SLikun Gao 
52372010239SLikun Gao 	if (adev->gfx.funcs->update_perfmon_mgcg)
52472010239SLikun Gao 		adev->gfx.funcs->update_perfmon_mgcg(adev, !enter);
52572010239SLikun Gao 
52672010239SLikun Gao 	return 0;
52772010239SLikun Gao }
52872010239SLikun Gao 
52906d82d87SRan Sun static const struct amdgpu_asic_funcs soc21_asic_funcs = {
53071199aa4SStanley.Yang 	.read_disabled_bios = &soc21_read_disabled_bios,
53171199aa4SStanley.Yang 	.read_bios_from_rom = &amdgpu_soc15_read_bios_from_rom,
53271199aa4SStanley.Yang 	.read_register = &soc21_read_register,
53371199aa4SStanley.Yang 	.reset = &soc21_asic_reset,
53471199aa4SStanley.Yang 	.reset_method = &soc21_asic_reset_method,
53571199aa4SStanley.Yang 	.get_xclk = &soc21_get_xclk,
53671199aa4SStanley.Yang 	.set_uvd_clocks = &soc21_set_uvd_clocks,
53771199aa4SStanley.Yang 	.set_vce_clocks = &soc21_set_vce_clocks,
53871199aa4SStanley.Yang 	.get_config_memsize = &soc21_get_config_memsize,
53971199aa4SStanley.Yang 	.init_doorbell_index = &soc21_init_doorbell_index,
54071199aa4SStanley.Yang 	.need_full_reset = &soc21_need_full_reset,
54171199aa4SStanley.Yang 	.need_reset_on_init = &soc21_need_reset_on_init,
54236f3f375SLijo Lazar 	.get_pcie_replay_count = &amdgpu_nbio_get_pcie_replay_count,
54371199aa4SStanley.Yang 	.supports_baco = &amdgpu_dpm_is_baco_supported,
54471199aa4SStanley.Yang 	.pre_asic_init = &soc21_pre_asic_init,
5459ac0edaaSJames Zhu 	.query_video_codecs = &soc21_query_video_codecs,
54672010239SLikun Gao 	.update_umd_stable_pstate = &soc21_update_umd_stable_pstate,
54771199aa4SStanley.Yang };
54871199aa4SStanley.Yang 
soc21_common_early_init(void * handle)54971199aa4SStanley.Yang static int soc21_common_early_init(void *handle)
55071199aa4SStanley.Yang {
55171199aa4SStanley.Yang #define MMIO_REG_HOLE_OFFSET (0x80000 - PAGE_SIZE)
55271199aa4SStanley.Yang 	struct amdgpu_device *adev = (struct amdgpu_device *)handle;
55371199aa4SStanley.Yang 
55471199aa4SStanley.Yang 	adev->rmmio_remap.reg_offset = MMIO_REG_HOLE_OFFSET;
55571199aa4SStanley.Yang 	adev->rmmio_remap.bus_addr = adev->rmmio_base + MMIO_REG_HOLE_OFFSET;
55671199aa4SStanley.Yang 	adev->smc_rreg = NULL;
55771199aa4SStanley.Yang 	adev->smc_wreg = NULL;
55865ba96e9SHawking Zhang 	adev->pcie_rreg = &amdgpu_device_indirect_rreg;
55965ba96e9SHawking Zhang 	adev->pcie_wreg = &amdgpu_device_indirect_wreg;
56065ba96e9SHawking Zhang 	adev->pcie_rreg64 = &amdgpu_device_indirect_rreg64;
56165ba96e9SHawking Zhang 	adev->pcie_wreg64 = &amdgpu_device_indirect_wreg64;
562bafd6cbeSXiaojian Du 	adev->pciep_rreg = amdgpu_device_pcie_port_rreg;
563bafd6cbeSXiaojian Du 	adev->pciep_wreg = amdgpu_device_pcie_port_wreg;
56471199aa4SStanley.Yang 
56571199aa4SStanley.Yang 	/* TODO: will add them during VCN v2 implementation */
56671199aa4SStanley.Yang 	adev->uvd_ctx_rreg = NULL;
56771199aa4SStanley.Yang 	adev->uvd_ctx_wreg = NULL;
56871199aa4SStanley.Yang 
56971199aa4SStanley.Yang 	adev->didt_rreg = &soc21_didt_rreg;
57071199aa4SStanley.Yang 	adev->didt_wreg = &soc21_didt_wreg;
57171199aa4SStanley.Yang 
57271199aa4SStanley.Yang 	adev->asic_funcs = &soc21_asic_funcs;
57371199aa4SStanley.Yang 
574dabc114eSHawking Zhang 	adev->rev_id = amdgpu_device_get_rev_id(adev);
57571199aa4SStanley.Yang 	adev->external_rev_id = 0xff;
57671199aa4SStanley.Yang 	switch (adev->ip_versions[GC_HWIP][0]) {
57771199aa4SStanley.Yang 	case IP_VERSION(11, 0, 0):
578390db4b8SEvan Quan 		adev->cg_flags = AMD_CG_SUPPORT_GFX_CGCG |
579b21348a2SEvan Quan 			AMD_CG_SUPPORT_GFX_CGLS |
5801b586595SEvan Quan #if 0
581915b5ce7SEvan Quan 			AMD_CG_SUPPORT_GFX_3D_CGCG |
582915b5ce7SEvan Quan 			AMD_CG_SUPPORT_GFX_3D_CGLS |
5831b586595SEvan Quan #endif
584915b5ce7SEvan Quan 			AMD_CG_SUPPORT_GFX_MGCG |
5858b719b96SLeo Liu 			AMD_CG_SUPPORT_REPEATER_FGCG |
586915b5ce7SEvan Quan 			AMD_CG_SUPPORT_GFX_FGCG |
587915b5ce7SEvan Quan 			AMD_CG_SUPPORT_GFX_PERF_CLK |
5887c507d35SJames Zhu 			AMD_CG_SUPPORT_VCN_MGCG |
589c649ed05SEvan Quan 			AMD_CG_SUPPORT_JPEG_MGCG |
590c649ed05SEvan Quan 			AMD_CG_SUPPORT_ATHUB_MGCG |
5917ccf6eb0SEvan Quan 			AMD_CG_SUPPORT_ATHUB_LS |
5927ccf6eb0SEvan Quan 			AMD_CG_SUPPORT_MC_MGCG |
59320139069SEvan Quan 			AMD_CG_SUPPORT_MC_LS |
594d386f645SEvan Quan 			AMD_CG_SUPPORT_IH_CG |
595d386f645SEvan Quan 			AMD_CG_SUPPORT_HDP_SD;
5968b719b96SLeo Liu 		adev->pg_flags = AMD_PG_SUPPORT_VCN |
59704270390SJames Zhu 			AMD_PG_SUPPORT_VCN_DPG |
5987c507d35SJames Zhu 			AMD_PG_SUPPORT_JPEG |
5998b719b96SLeo Liu 			AMD_PG_SUPPORT_ATHUB |
600a6dec868SEvan Quan 			AMD_PG_SUPPORT_MMHUB;
60171199aa4SStanley.Yang 		adev->external_rev_id = adev->rev_id + 0x1; // TODO: need update
60271199aa4SStanley.Yang 		break;
60392fd2153SFlora Cui 	case IP_VERSION(11, 0, 2):
60471dae221SJames Zhu 		adev->cg_flags =
6059503a944SLikun Gao 			AMD_CG_SUPPORT_GFX_CGCG |
6069503a944SLikun Gao 			AMD_CG_SUPPORT_GFX_CGLS |
60749401d3aSKenneth Feng 			AMD_CG_SUPPORT_REPEATER_FGCG |
6087ece9314SJames Zhu 			AMD_CG_SUPPORT_VCN_MGCG |
60949401d3aSKenneth Feng 			AMD_CG_SUPPORT_JPEG_MGCG |
61049401d3aSKenneth Feng 			AMD_CG_SUPPORT_ATHUB_MGCG |
611b4ddb27dSKenneth Feng 			AMD_CG_SUPPORT_ATHUB_LS |
612b4ddb27dSKenneth Feng 			AMD_CG_SUPPORT_IH_CG |
613b4ddb27dSKenneth Feng 			AMD_CG_SUPPORT_HDP_SD;
614ebac66a3SJames Zhu 		adev->pg_flags =
615143a34a0SJames Zhu 			AMD_PG_SUPPORT_VCN |
616ec9db74eSJames Zhu 			AMD_PG_SUPPORT_VCN_DPG |
61727e3911cSKenneth Feng 			AMD_PG_SUPPORT_JPEG |
61827e3911cSKenneth Feng 			AMD_PG_SUPPORT_ATHUB |
61927e3911cSKenneth Feng 			AMD_PG_SUPPORT_MMHUB;
62092fd2153SFlora Cui 		adev->external_rev_id = adev->rev_id + 0x10;
62192fd2153SFlora Cui 		break;
62211417a92SHuang Rui 	case IP_VERSION(11, 0, 1):
62347231d5eSSonny Jiang 		adev->cg_flags =
6248df436d5STim Huang 			AMD_CG_SUPPORT_GFX_CGCG |
6258df436d5STim Huang 			AMD_CG_SUPPORT_GFX_CGLS |
6268df436d5STim Huang 			AMD_CG_SUPPORT_GFX_MGCG |
6278df436d5STim Huang 			AMD_CG_SUPPORT_GFX_FGCG |
6288df436d5STim Huang 			AMD_CG_SUPPORT_REPEATER_FGCG |
6298df436d5STim Huang 			AMD_CG_SUPPORT_GFX_PERF_CLK |
630adcd15dcSTim Huang 			AMD_CG_SUPPORT_MC_MGCG |
631adcd15dcSTim Huang 			AMD_CG_SUPPORT_MC_LS |
6327e4a77deSTim Huang 			AMD_CG_SUPPORT_HDP_MGCG |
6337e4a77deSTim Huang 			AMD_CG_SUPPORT_HDP_LS |
6348e78c7c4STim Huang 			AMD_CG_SUPPORT_ATHUB_MGCG |
6358e78c7c4STim Huang 			AMD_CG_SUPPORT_ATHUB_LS |
636fa0bbd3bSTim Huang 			AMD_CG_SUPPORT_IH_CG |
6379407feacSTim Huang 			AMD_CG_SUPPORT_BIF_MGCG |
6389407feacSTim Huang 			AMD_CG_SUPPORT_BIF_LS |
63947231d5eSSonny Jiang 			AMD_CG_SUPPORT_VCN_MGCG |
64047231d5eSSonny Jiang 			AMD_CG_SUPPORT_JPEG_MGCG;
64147231d5eSSonny Jiang 		adev->pg_flags =
642dc0a096bSTim Huang 			AMD_PG_SUPPORT_GFX_PG |
643e626d9b9SSonny Jiang 			AMD_PG_SUPPORT_VCN |
6440b37f474SSonny Jiang 			AMD_PG_SUPPORT_VCN_DPG |
64547231d5eSSonny Jiang 			AMD_PG_SUPPORT_JPEG;
64611417a92SHuang Rui 		adev->external_rev_id = adev->rev_id + 0x1;
64711417a92SHuang Rui 		break;
6486b46251cSHawking Zhang 	case IP_VERSION(11, 0, 3):
6490f05a2e5SSonny Jiang 		adev->cg_flags = AMD_CG_SUPPORT_VCN_MGCG |
6504ecdb30eSKenneth Feng 			AMD_CG_SUPPORT_JPEG_MGCG |
6514ecdb30eSKenneth Feng 			AMD_CG_SUPPORT_GFX_CGCG |
6524ecdb30eSKenneth Feng 			AMD_CG_SUPPORT_GFX_CGLS |
6534ecdb30eSKenneth Feng 			AMD_CG_SUPPORT_REPEATER_FGCG |
65420e6220bSEvan Quan 			AMD_CG_SUPPORT_GFX_MGCG |
655ad1cebb6SKenneth Feng 			AMD_CG_SUPPORT_HDP_SD |
656ad1cebb6SKenneth Feng 			AMD_CG_SUPPORT_ATHUB_MGCG |
657ad1cebb6SKenneth Feng 			AMD_CG_SUPPORT_ATHUB_LS;
6580f05a2e5SSonny Jiang 		adev->pg_flags = AMD_PG_SUPPORT_VCN |
6590f05a2e5SSonny Jiang 			AMD_PG_SUPPORT_VCN_DPG |
6600f05a2e5SSonny Jiang 			AMD_PG_SUPPORT_JPEG;
6616b46251cSHawking Zhang 		adev->external_rev_id = adev->rev_id + 0x20;
6626b46251cSHawking Zhang 		break;
663311d5236SYifan Zhang 	case IP_VERSION(11, 0, 4):
664f2b91e5aSTim Huang 		adev->cg_flags =
665f2b91e5aSTim Huang 			AMD_CG_SUPPORT_GFX_CGCG |
666f2b91e5aSTim Huang 			AMD_CG_SUPPORT_GFX_CGLS |
667f2b91e5aSTim Huang 			AMD_CG_SUPPORT_GFX_MGCG |
668f2b91e5aSTim Huang 			AMD_CG_SUPPORT_GFX_FGCG |
669f2b91e5aSTim Huang 			AMD_CG_SUPPORT_REPEATER_FGCG |
670f2b91e5aSTim Huang 			AMD_CG_SUPPORT_GFX_PERF_CLK |
671f2b91e5aSTim Huang 			AMD_CG_SUPPORT_MC_MGCG |
672f2b91e5aSTim Huang 			AMD_CG_SUPPORT_MC_LS |
673f2b91e5aSTim Huang 			AMD_CG_SUPPORT_HDP_MGCG |
674f2b91e5aSTim Huang 			AMD_CG_SUPPORT_HDP_LS |
675f2b91e5aSTim Huang 			AMD_CG_SUPPORT_ATHUB_MGCG |
676f2b91e5aSTim Huang 			AMD_CG_SUPPORT_ATHUB_LS |
677f2b91e5aSTim Huang 			AMD_CG_SUPPORT_IH_CG |
678f2b91e5aSTim Huang 			AMD_CG_SUPPORT_BIF_MGCG |
679f2b91e5aSTim Huang 			AMD_CG_SUPPORT_BIF_LS |
680f2b91e5aSTim Huang 			AMD_CG_SUPPORT_VCN_MGCG |
6812a0fe2caSSaleemkhan Jamadar 			AMD_CG_SUPPORT_JPEG_MGCG;
6822a0fe2caSSaleemkhan Jamadar 		adev->pg_flags = AMD_PG_SUPPORT_VCN |
6839c705b96SSaleemkhan Jamadar 			AMD_PG_SUPPORT_VCN_DPG |
6842a0fe2caSSaleemkhan Jamadar 			AMD_PG_SUPPORT_GFX_PG |
6852a0fe2caSSaleemkhan Jamadar 			AMD_PG_SUPPORT_JPEG;
6866d99f3f4SYifan Zhang 		adev->external_rev_id = adev->rev_id + 0x80;
687311d5236SYifan Zhang 		break;
688311d5236SYifan Zhang 
68971199aa4SStanley.Yang 	default:
69071199aa4SStanley.Yang 		/* FIXME: not supported yet */
69171199aa4SStanley.Yang 		return -EINVAL;
69271199aa4SStanley.Yang 	}
69371199aa4SStanley.Yang 
69439dd895dSYuBiao Wang 	if (amdgpu_sriov_vf(adev)) {
6950cfce240SYiqing Yao 		amdgpu_virt_init_setting(adev);
69639dd895dSYuBiao Wang 		xgpu_nv_mailbox_set_irq_funcs(adev);
69739dd895dSYuBiao Wang 	}
6980cfce240SYiqing Yao 
69971199aa4SStanley.Yang 	return 0;
70071199aa4SStanley.Yang }
70171199aa4SStanley.Yang 
soc21_common_late_init(void * handle)70271199aa4SStanley.Yang static int soc21_common_late_init(void *handle)
70371199aa4SStanley.Yang {
70439dd895dSYuBiao Wang 	struct amdgpu_device *adev = (struct amdgpu_device *)handle;
70539dd895dSYuBiao Wang 
706dcaf5000SJane Jian 	if (amdgpu_sriov_vf(adev)) {
70739dd895dSYuBiao Wang 		xgpu_nv_mailbox_get_irq(adev);
708dcaf5000SJane Jian 		if ((adev->vcn.harvest_config & AMDGPU_VCN_HARVEST_VCN0) ||
709dcaf5000SJane Jian 		!amdgpu_sriov_is_av1_support(adev)) {
710dcaf5000SJane Jian 			amdgpu_virt_update_sriov_video_codec(adev,
711dcaf5000SJane Jian 							     sriov_vcn_4_0_0_video_codecs_encode_array_vcn1,
712dcaf5000SJane Jian 							     ARRAY_SIZE(sriov_vcn_4_0_0_video_codecs_encode_array_vcn1),
713dcaf5000SJane Jian 							     sriov_vcn_4_0_0_video_codecs_decode_array_vcn1,
714dcaf5000SJane Jian 							     ARRAY_SIZE(sriov_vcn_4_0_0_video_codecs_decode_array_vcn1));
715dcaf5000SJane Jian 		} else {
716dcaf5000SJane Jian 			amdgpu_virt_update_sriov_video_codec(adev,
717dcaf5000SJane Jian 							     sriov_vcn_4_0_0_video_codecs_encode_array_vcn0,
718dcaf5000SJane Jian 							     ARRAY_SIZE(sriov_vcn_4_0_0_video_codecs_encode_array_vcn0),
719dcaf5000SJane Jian 							     sriov_vcn_4_0_0_video_codecs_decode_array_vcn0,
720dcaf5000SJane Jian 							     ARRAY_SIZE(sriov_vcn_4_0_0_video_codecs_decode_array_vcn0));
721dcaf5000SJane Jian 		}
7229af357bcSHawking Zhang 	} else {
7239af357bcSHawking Zhang 		if (adev->nbio.ras &&
7249af357bcSHawking Zhang 		    adev->nbio.ras_err_event_athub_irq.funcs)
7259af357bcSHawking Zhang 			/* don't need to fail gpu late init
7269af357bcSHawking Zhang 			 * if enabling athub_err_event interrupt failed
7279af357bcSHawking Zhang 			 * nbio v4_3 only support fatal error hanlding
7289af357bcSHawking Zhang 			 * just enable the interrupt directly */
7299af357bcSHawking Zhang 			amdgpu_irq_get(adev, &adev->nbio.ras_err_event_athub_irq, 0);
730dcaf5000SJane Jian 	}
73139dd895dSYuBiao Wang 
7321c312e81SShane Xiao 	/* Enable selfring doorbell aperture late because doorbell BAR
7331c312e81SShane Xiao 	 * aperture will change if resize BAR successfully in gmc sw_init.
7341c312e81SShane Xiao 	 */
7351c312e81SShane Xiao 	adev->nbio.funcs->enable_doorbell_selfring_aperture(adev, true);
7361c312e81SShane Xiao 
73771199aa4SStanley.Yang 	return 0;
73871199aa4SStanley.Yang }
73971199aa4SStanley.Yang 
soc21_common_sw_init(void * handle)74071199aa4SStanley.Yang static int soc21_common_sw_init(void *handle)
74171199aa4SStanley.Yang {
74239dd895dSYuBiao Wang 	struct amdgpu_device *adev = (struct amdgpu_device *)handle;
74339dd895dSYuBiao Wang 
74439dd895dSYuBiao Wang 	if (amdgpu_sriov_vf(adev))
74539dd895dSYuBiao Wang 		xgpu_nv_mailbox_add_irq_id(adev);
74639dd895dSYuBiao Wang 
74771199aa4SStanley.Yang 	return 0;
74871199aa4SStanley.Yang }
74971199aa4SStanley.Yang 
soc21_common_sw_fini(void * handle)75071199aa4SStanley.Yang static int soc21_common_sw_fini(void *handle)
75171199aa4SStanley.Yang {
75271199aa4SStanley.Yang 	return 0;
75371199aa4SStanley.Yang }
75471199aa4SStanley.Yang 
soc21_common_hw_init(void * handle)75571199aa4SStanley.Yang static int soc21_common_hw_init(void *handle)
75671199aa4SStanley.Yang {
75771199aa4SStanley.Yang 	struct amdgpu_device *adev = (struct amdgpu_device *)handle;
75871199aa4SStanley.Yang 
75971199aa4SStanley.Yang 	/* enable aspm */
76071199aa4SStanley.Yang 	soc21_program_aspm(adev);
76171199aa4SStanley.Yang 	/* setup nbio registers */
76271199aa4SStanley.Yang 	adev->nbio.funcs->init_registers(adev);
76371199aa4SStanley.Yang 	/* remap HDP registers to a hole in mmio space,
76471199aa4SStanley.Yang 	 * for the purpose of expose those registers
76571199aa4SStanley.Yang 	 * to process space
76671199aa4SStanley.Yang 	 */
7671832403cSAlex Deucher 	if (adev->nbio.funcs->remap_hdp_registers && !amdgpu_sriov_vf(adev))
76871199aa4SStanley.Yang 		adev->nbio.funcs->remap_hdp_registers(adev);
76971199aa4SStanley.Yang 	/* enable the doorbell aperture */
7701c312e81SShane Xiao 	adev->nbio.funcs->enable_doorbell_aperture(adev, true);
77171199aa4SStanley.Yang 
77271199aa4SStanley.Yang 	return 0;
77371199aa4SStanley.Yang }
77471199aa4SStanley.Yang 
soc21_common_hw_fini(void * handle)77571199aa4SStanley.Yang static int soc21_common_hw_fini(void *handle)
77671199aa4SStanley.Yang {
77771199aa4SStanley.Yang 	struct amdgpu_device *adev = (struct amdgpu_device *)handle;
77871199aa4SStanley.Yang 
7791c312e81SShane Xiao 	/* Disable the doorbell aperture and selfring doorbell aperture
7801c312e81SShane Xiao 	 * separately in hw_fini because soc21_enable_doorbell_aperture
7811c312e81SShane Xiao 	 * has been removed and there is no need to delay disabling
7821c312e81SShane Xiao 	 * selfring doorbell.
7831c312e81SShane Xiao 	 */
7841c312e81SShane Xiao 	adev->nbio.funcs->enable_doorbell_aperture(adev, false);
7851c312e81SShane Xiao 	adev->nbio.funcs->enable_doorbell_selfring_aperture(adev, false);
78671199aa4SStanley.Yang 
7879af357bcSHawking Zhang 	if (amdgpu_sriov_vf(adev)) {
78839dd895dSYuBiao Wang 		xgpu_nv_mailbox_put_irq(adev);
7899af357bcSHawking Zhang 	} else {
7909af357bcSHawking Zhang 		if (adev->nbio.ras &&
7919af357bcSHawking Zhang 		    adev->nbio.ras_err_event_athub_irq.funcs)
7929af357bcSHawking Zhang 			amdgpu_irq_put(adev, &adev->nbio.ras_err_event_athub_irq, 0);
7939af357bcSHawking Zhang 	}
79439dd895dSYuBiao Wang 
79571199aa4SStanley.Yang 	return 0;
79671199aa4SStanley.Yang }
79771199aa4SStanley.Yang 
soc21_common_suspend(void * handle)79871199aa4SStanley.Yang static int soc21_common_suspend(void *handle)
79971199aa4SStanley.Yang {
80071199aa4SStanley.Yang 	struct amdgpu_device *adev = (struct amdgpu_device *)handle;
80171199aa4SStanley.Yang 
80271199aa4SStanley.Yang 	return soc21_common_hw_fini(adev);
80371199aa4SStanley.Yang }
80471199aa4SStanley.Yang 
soc21_need_reset_on_resume(struct amdgpu_device * adev)8051520bf60SLijo Lazar static bool soc21_need_reset_on_resume(struct amdgpu_device *adev)
8061520bf60SLijo Lazar {
8071520bf60SLijo Lazar 	u32 sol_reg1, sol_reg2;
8081520bf60SLijo Lazar 
8091520bf60SLijo Lazar 	/* Will reset for the following suspend abort cases.
8101520bf60SLijo Lazar 	 * 1) Only reset dGPU side.
8111520bf60SLijo Lazar 	 * 2) S3 suspend got aborted and TOS is active.
8121520bf60SLijo Lazar 	 */
8131520bf60SLijo Lazar 	if (!(adev->flags & AMD_IS_APU) && adev->in_s3 &&
8141520bf60SLijo Lazar 	    !adev->suspend_complete) {
8151520bf60SLijo Lazar 		sol_reg1 = RREG32_SOC15(MP0, 0, regMP0_SMN_C2PMSG_81);
8161520bf60SLijo Lazar 		msleep(100);
8171520bf60SLijo Lazar 		sol_reg2 = RREG32_SOC15(MP0, 0, regMP0_SMN_C2PMSG_81);
8181520bf60SLijo Lazar 
8191520bf60SLijo Lazar 		return (sol_reg1 != sol_reg2);
8201520bf60SLijo Lazar 	}
8211520bf60SLijo Lazar 
8221520bf60SLijo Lazar 	return false;
8231520bf60SLijo Lazar }
8241520bf60SLijo Lazar 
soc21_common_resume(void * handle)82571199aa4SStanley.Yang static int soc21_common_resume(void *handle)
82671199aa4SStanley.Yang {
82771199aa4SStanley.Yang 	struct amdgpu_device *adev = (struct amdgpu_device *)handle;
82871199aa4SStanley.Yang 
8291520bf60SLijo Lazar 	if (soc21_need_reset_on_resume(adev)) {
8301520bf60SLijo Lazar 		dev_info(adev->dev, "S3 suspend aborted, resetting...");
8311520bf60SLijo Lazar 		soc21_asic_reset(adev);
8321520bf60SLijo Lazar 	}
8331520bf60SLijo Lazar 
83471199aa4SStanley.Yang 	return soc21_common_hw_init(adev);
83571199aa4SStanley.Yang }
83671199aa4SStanley.Yang 
soc21_common_is_idle(void * handle)83771199aa4SStanley.Yang static bool soc21_common_is_idle(void *handle)
83871199aa4SStanley.Yang {
83971199aa4SStanley.Yang 	return true;
84071199aa4SStanley.Yang }
84171199aa4SStanley.Yang 
soc21_common_wait_for_idle(void * handle)84271199aa4SStanley.Yang static int soc21_common_wait_for_idle(void *handle)
84371199aa4SStanley.Yang {
84471199aa4SStanley.Yang 	return 0;
84571199aa4SStanley.Yang }
84671199aa4SStanley.Yang 
soc21_common_soft_reset(void * handle)84771199aa4SStanley.Yang static int soc21_common_soft_reset(void *handle)
84871199aa4SStanley.Yang {
84971199aa4SStanley.Yang 	return 0;
85071199aa4SStanley.Yang }
85171199aa4SStanley.Yang 
soc21_common_set_clockgating_state(void * handle,enum amd_clockgating_state state)85271199aa4SStanley.Yang static int soc21_common_set_clockgating_state(void *handle,
85371199aa4SStanley.Yang 					   enum amd_clockgating_state state)
85471199aa4SStanley.Yang {
85571199aa4SStanley.Yang 	struct amdgpu_device *adev = (struct amdgpu_device *)handle;
85671199aa4SStanley.Yang 
85771199aa4SStanley.Yang 	switch (adev->ip_versions[NBIO_HWIP][0]) {
85871199aa4SStanley.Yang 	case IP_VERSION(4, 3, 0):
859b4ddb27dSKenneth Feng 	case IP_VERSION(4, 3, 1):
8609407feacSTim Huang 	case IP_VERSION(7, 7, 0):
86171199aa4SStanley.Yang 		adev->nbio.funcs->update_medium_grain_clock_gating(adev,
86271199aa4SStanley.Yang 				state == AMD_CG_STATE_GATE);
86371199aa4SStanley.Yang 		adev->nbio.funcs->update_medium_grain_light_sleep(adev,
86471199aa4SStanley.Yang 				state == AMD_CG_STATE_GATE);
86571199aa4SStanley.Yang 		adev->hdp.funcs->update_clock_gating(adev,
86671199aa4SStanley.Yang 				state == AMD_CG_STATE_GATE);
86771199aa4SStanley.Yang 		break;
86871199aa4SStanley.Yang 	default:
86971199aa4SStanley.Yang 		break;
87071199aa4SStanley.Yang 	}
87171199aa4SStanley.Yang 	return 0;
87271199aa4SStanley.Yang }
87371199aa4SStanley.Yang 
soc21_common_set_powergating_state(void * handle,enum amd_powergating_state state)87471199aa4SStanley.Yang static int soc21_common_set_powergating_state(void *handle,
87571199aa4SStanley.Yang 					   enum amd_powergating_state state)
87671199aa4SStanley.Yang {
87741967850SLikun Gao 	struct amdgpu_device *adev = (struct amdgpu_device *)handle;
87841967850SLikun Gao 
87941967850SLikun Gao 	switch (adev->ip_versions[LSDMA_HWIP][0]) {
88041967850SLikun Gao 	case IP_VERSION(6, 0, 0):
881362c3c70SLikun Gao 	case IP_VERSION(6, 0, 2):
88241967850SLikun Gao 		adev->lsdma.funcs->update_memory_power_gating(adev,
88341967850SLikun Gao 				state == AMD_PG_STATE_GATE);
88441967850SLikun Gao 		break;
88541967850SLikun Gao 	default:
88641967850SLikun Gao 		break;
88741967850SLikun Gao 	}
88841967850SLikun Gao 
88971199aa4SStanley.Yang 	return 0;
89071199aa4SStanley.Yang }
89171199aa4SStanley.Yang 
soc21_common_get_clockgating_state(void * handle,u64 * flags)89271199aa4SStanley.Yang static void soc21_common_get_clockgating_state(void *handle, u64 *flags)
89371199aa4SStanley.Yang {
89471199aa4SStanley.Yang 	struct amdgpu_device *adev = (struct amdgpu_device *)handle;
89571199aa4SStanley.Yang 
89671199aa4SStanley.Yang 	adev->nbio.funcs->get_clockgating_state(adev, flags);
89771199aa4SStanley.Yang 
89871199aa4SStanley.Yang 	adev->hdp.funcs->get_clock_gating_state(adev, flags);
89971199aa4SStanley.Yang 
90071199aa4SStanley.Yang 	return;
90171199aa4SStanley.Yang }
90271199aa4SStanley.Yang 
90371199aa4SStanley.Yang static const struct amd_ip_funcs soc21_common_ip_funcs = {
90471199aa4SStanley.Yang 	.name = "soc21_common",
90571199aa4SStanley.Yang 	.early_init = soc21_common_early_init,
90671199aa4SStanley.Yang 	.late_init = soc21_common_late_init,
90771199aa4SStanley.Yang 	.sw_init = soc21_common_sw_init,
90871199aa4SStanley.Yang 	.sw_fini = soc21_common_sw_fini,
90971199aa4SStanley.Yang 	.hw_init = soc21_common_hw_init,
91071199aa4SStanley.Yang 	.hw_fini = soc21_common_hw_fini,
91171199aa4SStanley.Yang 	.suspend = soc21_common_suspend,
91271199aa4SStanley.Yang 	.resume = soc21_common_resume,
91371199aa4SStanley.Yang 	.is_idle = soc21_common_is_idle,
91471199aa4SStanley.Yang 	.wait_for_idle = soc21_common_wait_for_idle,
91571199aa4SStanley.Yang 	.soft_reset = soc21_common_soft_reset,
91671199aa4SStanley.Yang 	.set_clockgating_state = soc21_common_set_clockgating_state,
91771199aa4SStanley.Yang 	.set_powergating_state = soc21_common_set_powergating_state,
91871199aa4SStanley.Yang 	.get_clockgating_state = soc21_common_get_clockgating_state,
91971199aa4SStanley.Yang };
920