File Index
Files and directories
Sign in
FILE

dce80_resource.c

File preview with syntax highlighting.

linux-6.19.14/drivers/gpu/drm/amd/display/dc/resource/dce80/dce80_resource.c C
   1/*
   2 * Copyright 2012-15 Advanced Micro Devices, Inc.
   3 *
   4 * Permission is hereby granted, free of charge, to any person obtaining a
   5 * copy of this software and associated documentation files (the "Software"),
   6 * to deal in the Software without restriction, including without limitation
   7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
   8 * and/or sell copies of the Software, and to permit persons to whom the
   9 * Software is furnished to do so, subject to the following conditions:
  10 *
  11 * The above copyright notice and this permission notice shall be included in
  12 * all copies or substantial portions of the Software.
  13 *
  14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
  17 * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR
  18 * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
  19 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
  20 * OTHER DEALINGS IN THE SOFTWARE.
  21 *
  22 * Authors: AMD
  23 *
  24 */
  25
  26#include "dce/dce_8_0_d.h"
  27#include "dce/dce_8_0_sh_mask.h"
  28
  29#include "dm_services.h"
  30
  31#include "link_encoder.h"
  32#include "stream_encoder.h"
  33
  34#include "resource.h"
  35#include "clk_mgr.h"
  36#include "include/irq_service_interface.h"
  37#include "irq/dce80/irq_service_dce80.h"
  38#include "dce110/dce110_timing_generator.h"
  39#include "dce110/dce110_resource.h"
  40#include "dce80/dce80_timing_generator.h"
  41#include "dce/dce_mem_input.h"
  42#include "dce/dce_link_encoder.h"
  43#include "dce/dce_stream_encoder.h"
  44#include "dce/dce_ipp.h"
  45#include "dce/dce_transform.h"
  46#include "dce/dce_opp.h"
  47#include "dce/dce_clock_source.h"
  48#include "dce/dce_audio.h"
  49#include "dce/dce_hwseq.h"
  50#include "dce80/dce80_hwseq.h"
  51#include "dce100/dce100_resource.h"
  52#include "dce/dce_panel_cntl.h"
  53
  54#include "reg_helper.h"
  55
  56#include "dce/dce_dmcu.h"
  57#include "dce/dce_aux.h"
  58#include "dce/dce_abm.h"
  59#include "dce/dce_i2c.h"
  60
  61#ifndef mmMC_HUB_RDREQ_DMIF_LIMIT
  62#include "gmc/gmc_7_1_d.h"
  63#include "gmc/gmc_7_1_sh_mask.h"
  64#endif
  65
  66#include "dce80/dce80_resource.h"
  67
  68#ifndef mmDP_DPHY_INTERNAL_CTRL
  69#define mmDP_DPHY_INTERNAL_CTRL                         0x1CDE
  70#define mmDP0_DP_DPHY_INTERNAL_CTRL                     0x1CDE
  71#define mmDP1_DP_DPHY_INTERNAL_CTRL                     0x1FDE
  72#define mmDP2_DP_DPHY_INTERNAL_CTRL                     0x42DE
  73#define mmDP3_DP_DPHY_INTERNAL_CTRL                     0x45DE
  74#define mmDP4_DP_DPHY_INTERNAL_CTRL                     0x48DE
  75#define mmDP5_DP_DPHY_INTERNAL_CTRL                     0x4BDE
  76#define mmDP6_DP_DPHY_INTERNAL_CTRL                     0x4EDE
  77#endif
  78
  79
  80#ifndef mmBIOS_SCRATCH_2
  81	#define mmBIOS_SCRATCH_0 0x05C9
  82	#define mmBIOS_SCRATCH_2 0x05CB
  83	#define mmBIOS_SCRATCH_3 0x05CC
  84	#define mmBIOS_SCRATCH_6 0x05CF
  85#endif
  86
  87#ifndef mmDP_DPHY_FAST_TRAINING
  88	#define mmDP_DPHY_FAST_TRAINING                         0x1CCE
  89	#define mmDP0_DP_DPHY_FAST_TRAINING                     0x1CCE
  90	#define mmDP1_DP_DPHY_FAST_TRAINING                     0x1FCE
  91	#define mmDP2_DP_DPHY_FAST_TRAINING                     0x42CE
  92	#define mmDP3_DP_DPHY_FAST_TRAINING                     0x45CE
  93	#define mmDP4_DP_DPHY_FAST_TRAINING                     0x48CE
  94	#define mmDP5_DP_DPHY_FAST_TRAINING                     0x4BCE
  95	#define mmDP6_DP_DPHY_FAST_TRAINING                     0x4ECE
  96#endif
  97
  98
  99#ifndef mmHPD_DC_HPD_CONTROL
 100	#define mmHPD_DC_HPD_CONTROL                            0x189A
 101	#define mmHPD0_DC_HPD_CONTROL                           0x189A
 102	#define mmHPD1_DC_HPD_CONTROL                           0x18A2
 103	#define mmHPD2_DC_HPD_CONTROL                           0x18AA
 104	#define mmHPD3_DC_HPD_CONTROL                           0x18B2
 105	#define mmHPD4_DC_HPD_CONTROL                           0x18BA
 106	#define mmHPD5_DC_HPD_CONTROL                           0x18C2
 107#endif
 108
 109#define DCE11_DIG_FE_CNTL 0x4a00
 110#define DCE11_DIG_BE_CNTL 0x4a47
 111#define DCE11_DP_SEC 0x4ac3
 112
 113static const struct dce110_timing_generator_offsets dce80_tg_offsets[] = {
 114		{
 115			.crtc = (mmCRTC0_CRTC_CONTROL - mmCRTC_CONTROL),
 116			.dcp =  (mmGRPH_CONTROL - mmGRPH_CONTROL),
 117			.dmif = (mmDMIF_PG0_DPG_WATERMARK_MASK_CONTROL
 118					- mmDPG_WATERMARK_MASK_CONTROL),
 119		},
 120		{
 121			.crtc = (mmCRTC1_CRTC_CONTROL - mmCRTC_CONTROL),
 122			.dcp = (mmDCP1_GRPH_CONTROL - mmGRPH_CONTROL),
 123			.dmif = (mmDMIF_PG1_DPG_WATERMARK_MASK_CONTROL
 124					- mmDPG_WATERMARK_MASK_CONTROL),
 125		},
 126		{
 127			.crtc = (mmCRTC2_CRTC_CONTROL - mmCRTC_CONTROL),
 128			.dcp = (mmDCP2_GRPH_CONTROL - mmGRPH_CONTROL),
 129			.dmif = (mmDMIF_PG2_DPG_WATERMARK_MASK_CONTROL
 130					- mmDPG_WATERMARK_MASK_CONTROL),
 131		},
 132		{
 133			.crtc = (mmCRTC3_CRTC_CONTROL - mmCRTC_CONTROL),
 134			.dcp = (mmDCP3_GRPH_CONTROL - mmGRPH_CONTROL),
 135			.dmif = (mmDMIF_PG3_DPG_WATERMARK_MASK_CONTROL
 136					- mmDPG_WATERMARK_MASK_CONTROL),
 137		},
 138		{
 139			.crtc = (mmCRTC4_CRTC_CONTROL - mmCRTC_CONTROL),
 140			.dcp = (mmDCP4_GRPH_CONTROL - mmGRPH_CONTROL),
 141			.dmif = (mmDMIF_PG4_DPG_WATERMARK_MASK_CONTROL
 142					- mmDPG_WATERMARK_MASK_CONTROL),
 143		},
 144		{
 145			.crtc = (mmCRTC5_CRTC_CONTROL - mmCRTC_CONTROL),
 146			.dcp = (mmDCP5_GRPH_CONTROL - mmGRPH_CONTROL),
 147			.dmif = (mmDMIF_PG5_DPG_WATERMARK_MASK_CONTROL
 148					- mmDPG_WATERMARK_MASK_CONTROL),
 149		}
 150};
 151
 152/* set register offset */
 153#define SR(reg_name)\
 154	.reg_name = mm ## reg_name
 155
 156/* set register offset with instance */
 157#define SRI(reg_name, block, id)\
 158	.reg_name = mm ## block ## id ## _ ## reg_name
 159
 160#define ipp_regs(id)\
 161[id] = {\
 162		IPP_COMMON_REG_LIST_DCE_BASE(id)\
 163}
 164
 165static const struct dce_ipp_registers ipp_regs[] = {
 166		ipp_regs(0),
 167		ipp_regs(1),
 168		ipp_regs(2),
 169		ipp_regs(3),
 170		ipp_regs(4),
 171		ipp_regs(5)
 172};
 173
 174static const struct dce_ipp_shift ipp_shift = {
 175		IPP_COMMON_MASK_SH_LIST_DCE_COMMON_BASE(__SHIFT)
 176};
 177
 178static const struct dce_ipp_mask ipp_mask = {
 179		IPP_COMMON_MASK_SH_LIST_DCE_COMMON_BASE(_MASK)
 180};
 181
 182#define transform_regs(id)\
 183[id] = {\
 184		XFM_COMMON_REG_LIST_DCE80(id)\
 185}
 186
 187static const struct dce_transform_registers xfm_regs[] = {
 188		transform_regs(0),
 189		transform_regs(1),
 190		transform_regs(2),
 191		transform_regs(3),
 192		transform_regs(4),
 193		transform_regs(5)
 194};
 195
 196static const struct dce_transform_shift xfm_shift = {
 197		XFM_COMMON_MASK_SH_LIST_DCE80(__SHIFT)
 198};
 199
 200static const struct dce_transform_mask xfm_mask = {
 201		XFM_COMMON_MASK_SH_LIST_DCE80(_MASK)
 202};
 203
 204#define aux_regs(id)\
 205[id] = {\
 206	AUX_REG_LIST(id)\
 207}
 208
 209static const struct dce110_link_enc_aux_registers link_enc_aux_regs[] = {
 210	aux_regs(0),
 211	aux_regs(1),
 212	aux_regs(2),
 213	aux_regs(3),
 214	aux_regs(4),
 215	aux_regs(5)
 216};
 217
 218#define hpd_regs(id)\
 219[id] = {\
 220	HPD_REG_LIST(id)\
 221}
 222
 223static const struct dce110_link_enc_hpd_registers link_enc_hpd_regs[] = {
 224		hpd_regs(0),
 225		hpd_regs(1),
 226		hpd_regs(2),
 227		hpd_regs(3),
 228		hpd_regs(4),
 229		hpd_regs(5)
 230};
 231
 232#define link_regs(id)\
 233[id] = {\
 234	LE_DCE80_REG_LIST(id)\
 235}
 236
 237static const struct dce110_link_enc_registers link_enc_regs[] = {
 238	link_regs(0),
 239	link_regs(1),
 240	link_regs(2),
 241	link_regs(3),
 242	link_regs(4),
 243	link_regs(5),
 244	link_regs(6),
 245	{ .DAC_ENABLE = mmDAC_ENABLE },
 246};
 247
 248#define stream_enc_regs(id)\
 249[id] = {\
 250	SE_COMMON_REG_LIST_DCE_BASE(id),\
 251	.AFMT_CNTL = 0,\
 252}
 253
 254static const struct dce110_stream_enc_registers stream_enc_regs[] = {
 255	stream_enc_regs(0),
 256	stream_enc_regs(1),
 257	stream_enc_regs(2),
 258	stream_enc_regs(3),
 259	stream_enc_regs(4),
 260	stream_enc_regs(5),
 261	stream_enc_regs(6),
 262	{SR(DAC_SOURCE_SELECT),} /* DACA */
 263};
 264
 265static const struct dce_stream_encoder_shift se_shift = {
 266		SE_COMMON_MASK_SH_LIST_DCE80_100(__SHIFT)
 267};
 268
 269static const struct dce_stream_encoder_mask se_mask = {
 270		SE_COMMON_MASK_SH_LIST_DCE80_100(_MASK)
 271};
 272
 273static const struct dce_panel_cntl_registers panel_cntl_regs[] = {
 274	{ DCE_PANEL_CNTL_REG_LIST() }
 275};
 276
 277static const struct dce_panel_cntl_shift panel_cntl_shift = {
 278	DCE_PANEL_CNTL_MASK_SH_LIST(__SHIFT)
 279};
 280
 281static const struct dce_panel_cntl_mask panel_cntl_mask = {
 282	DCE_PANEL_CNTL_MASK_SH_LIST(_MASK)
 283};
 284
 285#define opp_regs(id)\
 286[id] = {\
 287	OPP_DCE_80_REG_LIST(id),\
 288}
 289
 290static const struct dce_opp_registers opp_regs[] = {
 291	opp_regs(0),
 292	opp_regs(1),
 293	opp_regs(2),
 294	opp_regs(3),
 295	opp_regs(4),
 296	opp_regs(5)
 297};
 298
 299static const struct dce_opp_shift opp_shift = {
 300	OPP_COMMON_MASK_SH_LIST_DCE_80(__SHIFT)
 301};
 302
 303static const struct dce_opp_mask opp_mask = {
 304	OPP_COMMON_MASK_SH_LIST_DCE_80(_MASK)
 305};
 306
 307static const struct dce110_aux_registers_shift aux_shift = {
 308	DCE10_AUX_MASK_SH_LIST(__SHIFT)
 309};
 310
 311static const struct dce110_aux_registers_mask aux_mask = {
 312	DCE10_AUX_MASK_SH_LIST(_MASK)
 313};
 314
 315#define aux_engine_regs(id)\
 316[id] = {\
 317	AUX_COMMON_REG_LIST(id), \
 318	.AUX_RESET_MASK = 0 \
 319}
 320
 321static const struct dce110_aux_registers aux_engine_regs[] = {
 322		aux_engine_regs(0),
 323		aux_engine_regs(1),
 324		aux_engine_regs(2),
 325		aux_engine_regs(3),
 326		aux_engine_regs(4),
 327		aux_engine_regs(5)
 328};
 329
 330#define audio_regs(id)\
 331[id] = {\
 332	AUD_COMMON_REG_LIST(id)\
 333}
 334
 335static const struct dce_audio_registers audio_regs[] = {
 336	audio_regs(0),
 337	audio_regs(1),
 338	audio_regs(2),
 339	audio_regs(3),
 340	audio_regs(4),
 341	audio_regs(5),
 342	audio_regs(6),
 343};
 344
 345static const struct dce_audio_shift audio_shift = {
 346		AUD_COMMON_MASK_SH_LIST(__SHIFT)
 347};
 348
 349static const struct dce_audio_mask audio_mask = {
 350		AUD_COMMON_MASK_SH_LIST(_MASK)
 351};
 352
 353#define clk_src_regs(id)\
 354[id] = {\
 355	CS_COMMON_REG_LIST_DCE_80(id),\
 356}
 357
 358
 359static const struct dce110_clk_src_regs clk_src_regs[] = {
 360	clk_src_regs(0),
 361	clk_src_regs(1),
 362	clk_src_regs(2)
 363};
 364
 365static const struct dce110_clk_src_shift cs_shift = {
 366		CS_COMMON_MASK_SH_LIST_DCE_COMMON_BASE(__SHIFT)
 367};
 368
 369static const struct dce110_clk_src_mask cs_mask = {
 370		CS_COMMON_MASK_SH_LIST_DCE_COMMON_BASE(_MASK)
 371};
 372
 373static const struct bios_registers bios_regs = {
 374	.BIOS_SCRATCH_0 = mmBIOS_SCRATCH_0,
 375	.BIOS_SCRATCH_3 = mmBIOS_SCRATCH_3,
 376	.BIOS_SCRATCH_6 = mmBIOS_SCRATCH_6
 377};
 378
 379static const struct resource_caps res_cap = {
 380		.num_timing_generator = 6,
 381		.num_audio = 6,
 382		.num_analog_stream_encoder = 1,
 383		.num_stream_encoder = 6,
 384		.num_pll = 3,
 385		.num_ddc = 6,
 386};
 387
 388static const struct resource_caps res_cap_81 = {
 389		.num_timing_generator = 4,
 390		.num_audio = 7,
 391		.num_analog_stream_encoder = 1,
 392		.num_stream_encoder = 7,
 393		.num_pll = 3,
 394		.num_ddc = 6,
 395};
 396
 397static const struct resource_caps res_cap_83 = {
 398		.num_timing_generator = 2,
 399		.num_audio = 6,
 400		.num_analog_stream_encoder = 1,
 401		.num_stream_encoder = 6,
 402		.num_pll = 2,
 403		.num_ddc = 2,
 404};
 405
 406static const struct dc_plane_cap plane_cap = {
 407	.type = DC_PLANE_TYPE_DCE_RGB,
 408
 409	.pixel_format_support = {
 410			.argb8888 = true,
 411			.nv12 = false,
 412			.fp16 = true
 413	},
 414
 415	.max_upscale_factor = {
 416			.argb8888 = 16000,
 417			.nv12 = 1,
 418			.fp16 = 1
 419	},
 420
 421	.max_downscale_factor = {
 422			.argb8888 = 250,
 423			.nv12 = 1,
 424			.fp16 = 1
 425	}
 426};
 427
 428static const struct dc_debug_options debug_defaults = { 0 };
 429
 430static const struct dc_check_config config_defaults = {
 431	.enable_legacy_fast_update = true,
 432};
 433
 434static const struct dce_dmcu_registers dmcu_regs = {
 435		DMCU_DCE80_REG_LIST()
 436};
 437
 438static const struct dce_dmcu_shift dmcu_shift = {
 439		DMCU_MASK_SH_LIST_DCE80(__SHIFT)
 440};
 441
 442static const struct dce_dmcu_mask dmcu_mask = {
 443		DMCU_MASK_SH_LIST_DCE80(_MASK)
 444};
 445static const struct dce_abm_registers abm_regs = {
 446		ABM_DCE110_COMMON_REG_LIST()
 447};
 448
 449static const struct dce_abm_shift abm_shift = {
 450		ABM_MASK_SH_LIST_DCE110(__SHIFT)
 451};
 452
 453static const struct dce_abm_mask abm_mask = {
 454		ABM_MASK_SH_LIST_DCE110(_MASK)
 455};
 456
 457#define CTX  ctx
 458#define REG(reg) mm ## reg
 459
 460#ifndef mmCC_DC_HDMI_STRAPS
 461#define mmCC_DC_HDMI_STRAPS 0x1918
 462#define CC_DC_HDMI_STRAPS__HDMI_DISABLE_MASK 0x40
 463#define CC_DC_HDMI_STRAPS__HDMI_DISABLE__SHIFT 0x6
 464#define CC_DC_HDMI_STRAPS__AUDIO_STREAM_NUMBER_MASK 0x700
 465#define CC_DC_HDMI_STRAPS__AUDIO_STREAM_NUMBER__SHIFT 0x8
 466#endif
 467
 468static int map_transmitter_id_to_phy_instance(
 469	enum transmitter transmitter)
 470{
 471	switch (transmitter) {
 472	case TRANSMITTER_UNIPHY_A:
 473		return 0;
 474	case TRANSMITTER_UNIPHY_B:
 475		return 1;
 476	case TRANSMITTER_UNIPHY_C:
 477		return 2;
 478	case TRANSMITTER_UNIPHY_D:
 479		return 3;
 480	case TRANSMITTER_UNIPHY_E:
 481		return 4;
 482	case TRANSMITTER_UNIPHY_F:
 483		return 5;
 484	case TRANSMITTER_UNIPHY_G:
 485		return 6;
 486	default:
 487		ASSERT(0);
 488		return 0;
 489	}
 490}
 491
 492static void read_dce_straps(
 493	struct dc_context *ctx,
 494	struct resource_straps *straps)
 495{
 496	REG_GET_2(CC_DC_HDMI_STRAPS,
 497			HDMI_DISABLE, &straps->hdmi_disable,
 498			AUDIO_STREAM_NUMBER, &straps->audio_stream_number);
 499
 500	REG_GET(DC_PINSTRAPS, DC_PINSTRAPS_AUDIO, &straps->dc_pinstraps_audio);
 501}
 502
 503static struct audio *create_audio(
 504		struct dc_context *ctx, unsigned int inst)
 505{
 506	return dce_audio_create(ctx, inst,
 507			&audio_regs[inst], &audio_shift, &audio_mask);
 508}
 509
 510static struct timing_generator *dce80_timing_generator_create(
 511		struct dc_context *ctx,
 512		uint32_t instance,
 513		const struct dce110_timing_generator_offsets *offsets)
 514{
 515	struct dce110_timing_generator *tg110 =
 516		kzalloc(sizeof(struct dce110_timing_generator), GFP_KERNEL);
 517
 518	if (!tg110)
 519		return NULL;
 520
 521	dce80_timing_generator_construct(tg110, ctx, instance, offsets);
 522	return &tg110->base;
 523}
 524
 525static struct output_pixel_processor *dce80_opp_create(
 526	struct dc_context *ctx,
 527	uint32_t inst)
 528{
 529	struct dce110_opp *opp =
 530		kzalloc(sizeof(struct dce110_opp), GFP_KERNEL);
 531
 532	if (!opp)
 533		return NULL;
 534
 535	dce110_opp_construct(opp,
 536			     ctx, inst, &opp_regs[inst], &opp_shift, &opp_mask);
 537	return &opp->base;
 538}
 539
 540static struct dce_aux *dce80_aux_engine_create(
 541	struct dc_context *ctx,
 542	uint32_t inst)
 543{
 544	struct aux_engine_dce110 *aux_engine =
 545		kzalloc(sizeof(struct aux_engine_dce110), GFP_KERNEL);
 546
 547	if (!aux_engine)
 548		return NULL;
 549
 550	dce110_aux_engine_construct(aux_engine, ctx, inst,
 551				    SW_AUX_TIMEOUT_PERIOD_MULTIPLIER * AUX_TIMEOUT_PERIOD,
 552				    &aux_engine_regs[inst],
 553					&aux_mask,
 554					&aux_shift,
 555					ctx->dc->caps.extended_aux_timeout_support);
 556
 557	return &aux_engine->base;
 558}
 559#define i2c_inst_regs(id) { I2C_HW_ENGINE_COMMON_REG_LIST(id) }
 560
 561static const struct dce_i2c_registers i2c_hw_regs[] = {
 562		i2c_inst_regs(1),
 563		i2c_inst_regs(2),
 564		i2c_inst_regs(3),
 565		i2c_inst_regs(4),
 566		i2c_inst_regs(5),
 567		i2c_inst_regs(6),
 568};
 569
 570static const struct dce_i2c_shift i2c_shifts = {
 571		I2C_COMMON_MASK_SH_LIST_DCE_COMMON_BASE(__SHIFT)
 572};
 573
 574static const struct dce_i2c_mask i2c_masks = {
 575		I2C_COMMON_MASK_SH_LIST_DCE_COMMON_BASE(_MASK)
 576};
 577
 578static struct dce_i2c_hw *dce80_i2c_hw_create(
 579	struct dc_context *ctx,
 580	uint32_t inst)
 581{
 582	struct dce_i2c_hw *dce_i2c_hw =
 583		kzalloc(sizeof(struct dce_i2c_hw), GFP_KERNEL);
 584
 585	if (!dce_i2c_hw)
 586		return NULL;
 587
 588	dce_i2c_hw_construct(dce_i2c_hw, ctx, inst,
 589				    &i2c_hw_regs[inst], &i2c_shifts, &i2c_masks);
 590
 591	return dce_i2c_hw;
 592}
 593
 594static struct dce_i2c_sw *dce80_i2c_sw_create(
 595	struct dc_context *ctx)
 596{
 597	struct dce_i2c_sw *dce_i2c_sw =
 598		kzalloc(sizeof(struct dce_i2c_sw), GFP_KERNEL);
 599
 600	if (!dce_i2c_sw)
 601		return NULL;
 602
 603	dce_i2c_sw_construct(dce_i2c_sw, ctx);
 604
 605	return dce_i2c_sw;
 606}
 607static struct stream_encoder *dce80_stream_encoder_create(
 608	enum engine_id eng_id,
 609	struct dc_context *ctx)
 610{
 611	struct dce110_stream_encoder *enc110 =
 612		kzalloc(sizeof(struct dce110_stream_encoder), GFP_KERNEL);
 613
 614	if (!enc110)
 615		return NULL;
 616
 617	if (eng_id == ENGINE_ID_DACA || eng_id == ENGINE_ID_DACB) {
 618		dce110_analog_stream_encoder_construct(enc110, ctx, ctx->dc_bios, eng_id,
 619			&stream_enc_regs[eng_id], &se_shift, &se_mask);
 620		return &enc110->base;
 621	}
 622
 623	dce110_stream_encoder_construct(enc110, ctx, ctx->dc_bios, eng_id,
 624					&stream_enc_regs[eng_id],
 625					&se_shift, &se_mask);
 626	return &enc110->base;
 627}
 628
 629#define SRII(reg_name, block, id)\
 630	.reg_name[id] = mm ## block ## id ## _ ## reg_name
 631
 632static const struct dce_hwseq_registers hwseq_reg = {
 633		HWSEQ_DCE8_REG_LIST()
 634};
 635
 636static const struct dce_hwseq_shift hwseq_shift = {
 637		HWSEQ_DCE8_MASK_SH_LIST(__SHIFT)
 638};
 639
 640static const struct dce_hwseq_mask hwseq_mask = {
 641		HWSEQ_DCE8_MASK_SH_LIST(_MASK)
 642};
 643
 644static struct dce_hwseq *dce80_hwseq_create(
 645	struct dc_context *ctx)
 646{
 647	struct dce_hwseq *hws = kzalloc(sizeof(struct dce_hwseq), GFP_KERNEL);
 648
 649	if (hws) {
 650		hws->ctx = ctx;
 651		hws->regs = &hwseq_reg;
 652		hws->shifts = &hwseq_shift;
 653		hws->masks = &hwseq_mask;
 654	}
 655	return hws;
 656}
 657
 658static const struct resource_create_funcs res_create_funcs = {
 659	.read_dce_straps = read_dce_straps,
 660	.create_audio = create_audio,
 661	.create_stream_encoder = dce80_stream_encoder_create,
 662	.create_hwseq = dce80_hwseq_create,
 663};
 664
 665#define mi_inst_regs(id) { \
 666	MI_DCE8_REG_LIST(id), \
 667	.MC_HUB_RDREQ_DMIF_LIMIT = mmMC_HUB_RDREQ_DMIF_LIMIT \
 668}
 669static const struct dce_mem_input_registers mi_regs[] = {
 670		mi_inst_regs(0),
 671		mi_inst_regs(1),
 672		mi_inst_regs(2),
 673		mi_inst_regs(3),
 674		mi_inst_regs(4),
 675		mi_inst_regs(5),
 676};
 677
 678static const struct dce_mem_input_shift mi_shifts = {
 679		MI_DCE8_MASK_SH_LIST(__SHIFT),
 680		.ENABLE = MC_HUB_RDREQ_DMIF_LIMIT__ENABLE__SHIFT
 681};
 682
 683static const struct dce_mem_input_mask mi_masks = {
 684		MI_DCE8_MASK_SH_LIST(_MASK),
 685		.ENABLE = MC_HUB_RDREQ_DMIF_LIMIT__ENABLE_MASK
 686};
 687
 688static struct mem_input *dce80_mem_input_create(
 689	struct dc_context *ctx,
 690	uint32_t inst)
 691{
 692	struct dce_mem_input *dce_mi = kzalloc(sizeof(struct dce_mem_input),
 693					       GFP_KERNEL);
 694
 695	if (!dce_mi) {
 696		BREAK_TO_DEBUGGER();
 697		return NULL;
 698	}
 699
 700	dce_mem_input_construct(dce_mi, ctx, inst, &mi_regs[inst], &mi_shifts, &mi_masks);
 701	dce_mi->wa.single_head_rdreq_dmif_limit = 2;
 702	return &dce_mi->base;
 703}
 704
 705static void dce80_transform_destroy(struct transform **xfm)
 706{
 707	kfree(TO_DCE_TRANSFORM(*xfm));
 708	*xfm = NULL;
 709}
 710
 711static struct transform *dce80_transform_create(
 712	struct dc_context *ctx,
 713	uint32_t inst)
 714{
 715	struct dce_transform *transform =
 716		kzalloc(sizeof(struct dce_transform), GFP_KERNEL);
 717
 718	if (!transform)
 719		return NULL;
 720
 721	dce_transform_construct(transform, ctx, inst,
 722				&xfm_regs[inst], &xfm_shift, &xfm_mask);
 723	transform->prescaler_on = false;
 724	return &transform->base;
 725}
 726
 727static const struct encoder_feature_support link_enc_feature = {
 728		.max_hdmi_deep_color = COLOR_DEPTH_121212,
 729		.max_hdmi_pixel_clock = 297000,
 730		.flags.bits.IS_HBR2_CAPABLE = true,
 731		.flags.bits.IS_TPS3_CAPABLE = true
 732};
 733
 734static struct link_encoder *dce80_link_encoder_create(
 735	struct dc_context *ctx,
 736	const struct encoder_init_data *enc_init_data)
 737{
 738	struct dce110_link_encoder *enc110 =
 739		kzalloc(sizeof(struct dce110_link_encoder), GFP_KERNEL);
 740	int link_regs_id;
 741
 742	if (!enc110)
 743		return NULL;
 744
 745	if (enc_init_data->connector.id == CONNECTOR_ID_VGA &&
 746	    enc_init_data->analog_engine != ENGINE_ID_UNKNOWN) {
 747		dce110_link_encoder_construct(enc110,
 748			enc_init_data,
 749			&link_enc_feature,
 750			&link_enc_regs[ENGINE_ID_DACA],
 751			NULL,
 752			NULL);
 753		return &enc110->base;
 754	}
 755
 756	link_regs_id =
 757		map_transmitter_id_to_phy_instance(enc_init_data->transmitter);
 758
 759	dce110_link_encoder_construct(enc110,
 760				      enc_init_data,
 761				      &link_enc_feature,
 762				      &link_enc_regs[link_regs_id],
 763				      &link_enc_aux_regs[enc_init_data->channel - 1],
 764				      enc_init_data->hpd_source >= ARRAY_SIZE(link_enc_hpd_regs) ?
 765				      NULL : &link_enc_hpd_regs[enc_init_data->hpd_source]);
 766	return &enc110->base;
 767}
 768
 769static struct panel_cntl *dce80_panel_cntl_create(const struct panel_cntl_init_data *init_data)
 770{
 771	struct dce_panel_cntl *panel_cntl =
 772		kzalloc(sizeof(struct dce_panel_cntl), GFP_KERNEL);
 773
 774	if (!panel_cntl)
 775		return NULL;
 776
 777	dce_panel_cntl_construct(panel_cntl,
 778			init_data,
 779			&panel_cntl_regs[init_data->inst],
 780			&panel_cntl_shift,
 781			&panel_cntl_mask);
 782
 783	return &panel_cntl->base;
 784}
 785
 786static struct clock_source *dce80_clock_source_create(
 787	struct dc_context *ctx,
 788	struct dc_bios *bios,
 789	enum clock_source_id id,
 790	const struct dce110_clk_src_regs *regs,
 791	bool dp_clk_src)
 792{
 793	struct dce110_clk_src *clk_src =
 794		kzalloc(sizeof(struct dce110_clk_src), GFP_KERNEL);
 795
 796	if (!clk_src)
 797		return NULL;
 798
 799	if (dce110_clk_src_construct(clk_src, ctx, bios, id,
 800			regs, &cs_shift, &cs_mask)) {
 801		clk_src->base.dp_clk_src = dp_clk_src;
 802		return &clk_src->base;
 803	}
 804
 805	kfree(clk_src);
 806	BREAK_TO_DEBUGGER();
 807	return NULL;
 808}
 809
 810static void dce80_clock_source_destroy(struct clock_source **clk_src)
 811{
 812	kfree(TO_DCE110_CLK_SRC(*clk_src));
 813	*clk_src = NULL;
 814}
 815
 816static struct input_pixel_processor *dce80_ipp_create(
 817	struct dc_context *ctx, uint32_t inst)
 818{
 819	struct dce_ipp *ipp = kzalloc(sizeof(struct dce_ipp), GFP_KERNEL);
 820
 821	if (!ipp) {
 822		BREAK_TO_DEBUGGER();
 823		return NULL;
 824	}
 825
 826	dce_ipp_construct(ipp, ctx, inst,
 827			&ipp_regs[inst], &ipp_shift, &ipp_mask);
 828	return &ipp->base;
 829}
 830
 831static void dce80_resource_destruct(struct dce110_resource_pool *pool)
 832{
 833	unsigned int i;
 834
 835	for (i = 0; i < pool->base.pipe_count; i++) {
 836		if (pool->base.opps[i] != NULL)
 837			dce110_opp_destroy(&pool->base.opps[i]);
 838
 839		if (pool->base.transforms[i] != NULL)
 840			dce80_transform_destroy(&pool->base.transforms[i]);
 841
 842		if (pool->base.ipps[i] != NULL)
 843			dce_ipp_destroy(&pool->base.ipps[i]);
 844
 845		if (pool->base.mis[i] != NULL) {
 846			kfree(TO_DCE_MEM_INPUT(pool->base.mis[i]));
 847			pool->base.mis[i] = NULL;
 848		}
 849
 850		if (pool->base.timing_generators[i] != NULL)	{
 851			kfree(DCE110TG_FROM_TG(pool->base.timing_generators[i]));
 852			pool->base.timing_generators[i] = NULL;
 853		}
 854	}
 855
 856	for (i = 0; i < pool->base.res_cap->num_ddc; i++) {
 857		if (pool->base.engines[i] != NULL)
 858			dce110_engine_destroy(&pool->base.engines[i]);
 859		if (pool->base.hw_i2cs[i] != NULL) {
 860			kfree(pool->base.hw_i2cs[i]);
 861			pool->base.hw_i2cs[i] = NULL;
 862		}
 863		if (pool->base.sw_i2cs[i] != NULL) {
 864			kfree(pool->base.sw_i2cs[i]);
 865			pool->base.sw_i2cs[i] = NULL;
 866		}
 867	}
 868
 869	for (i = 0; i < pool->base.stream_enc_count; i++) {
 870		if (pool->base.stream_enc[i] != NULL)
 871			kfree(DCE110STRENC_FROM_STRENC(pool->base.stream_enc[i]));
 872	}
 873
 874	for (i = 0; i < pool->base.clk_src_count; i++) {
 875		if (pool->base.clock_sources[i] != NULL) {
 876			dce80_clock_source_destroy(&pool->base.clock_sources[i]);
 877		}
 878	}
 879
 880	if (pool->base.abm != NULL)
 881			dce_abm_destroy(&pool->base.abm);
 882
 883	if (pool->base.dmcu != NULL)
 884			dce_dmcu_destroy(&pool->base.dmcu);
 885
 886	if (pool->base.dp_clock_source != NULL)
 887		dce80_clock_source_destroy(&pool->base.dp_clock_source);
 888
 889	for (i = 0; i < pool->base.audio_count; i++)	{
 890		if (pool->base.audios[i] != NULL) {
 891			dce_aud_destroy(&pool->base.audios[i]);
 892		}
 893	}
 894
 895	if (pool->base.irqs != NULL) {
 896		dal_irq_service_destroy(&pool->base.irqs);
 897	}
 898}
 899
 900static void dce80_destroy_resource_pool(struct resource_pool **pool)
 901{
 902	struct dce110_resource_pool *dce110_pool = TO_DCE110_RES_POOL(*pool);
 903
 904	dce80_resource_destruct(dce110_pool);
 905	kfree(dce110_pool);
 906	*pool = NULL;
 907}
 908
 909static const struct resource_funcs dce80_res_pool_funcs = {
 910	.destroy = dce80_destroy_resource_pool,
 911	.link_enc_create = dce80_link_encoder_create,
 912	.panel_cntl_create = dce80_panel_cntl_create,
 913	.validate_bandwidth = dce100_validate_bandwidth,
 914	.validate_plane = dce100_validate_plane,
 915	.add_stream_to_ctx = dce100_add_stream_to_ctx,
 916	.validate_global = dce100_validate_global,
 917	.find_first_free_match_stream_enc_for_link = dce100_find_first_free_match_stream_enc_for_link
 918};
 919
 920static bool dce80_construct(
 921	uint8_t num_virtual_links,
 922	struct dc *dc,
 923	struct dce110_resource_pool *pool)
 924{
 925	unsigned int i;
 926	struct dc_context *ctx = dc->ctx;
 927	struct dc_bios *bp;
 928
 929	ctx->dc_bios->regs = &bios_regs;
 930
 931	pool->base.res_cap = &res_cap;
 932	pool->base.funcs = &dce80_res_pool_funcs;
 933
 934
 935	/*************************************************
 936	 *  Resource + asic cap harcoding                *
 937	 *************************************************/
 938	pool->base.underlay_pipe_index = NO_UNDERLAY_PIPE;
 939	pool->base.pipe_count = res_cap.num_timing_generator;
 940	pool->base.timing_generator_count = res_cap.num_timing_generator;
 941	dc->caps.max_downscale_ratio = 200;
 942	dc->caps.i2c_speed_in_khz = 40;
 943	dc->caps.i2c_speed_in_khz_hdcp = 40;
 944	dc->caps.max_cursor_size = 128;
 945	dc->caps.min_horizontal_blanking_period = 80;
 946	dc->caps.dual_link_dvi = true;
 947	dc->caps.extended_aux_timeout_support = false;
 948	dc->debug = debug_defaults;
 949	dc->check_config = config_defaults;
 950
 951	/*************************************************
 952	 *  Create resources                             *
 953	 *************************************************/
 954
 955	bp = ctx->dc_bios;
 956
 957	if (bp->fw_info_valid && bp->fw_info.external_clock_source_frequency_for_dp != 0) {
 958		pool->base.dp_clock_source =
 959				dce80_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_EXTERNAL, NULL, true);
 960
 961		pool->base.clock_sources[0] =
 962				dce80_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL0, &clk_src_regs[0], false);
 963		pool->base.clock_sources[1] =
 964				dce80_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL1, &clk_src_regs[1], false);
 965		pool->base.clock_sources[2] =
 966				dce80_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL2, &clk_src_regs[2], false);
 967		pool->base.clk_src_count = 3;
 968
 969	} else {
 970		pool->base.dp_clock_source =
 971				dce80_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL0, &clk_src_regs[0], true);
 972
 973		pool->base.clock_sources[0] =
 974				dce80_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL1, &clk_src_regs[1], false);
 975		pool->base.clock_sources[1] =
 976				dce80_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL2, &clk_src_regs[2], false);
 977		pool->base.clk_src_count = 2;
 978	}
 979
 980	if (pool->base.dp_clock_source == NULL) {
 981		dm_error("DC: failed to create dp clock source!\n");
 982		BREAK_TO_DEBUGGER();
 983		goto res_create_fail;
 984	}
 985
 986	for (i = 0; i < pool->base.clk_src_count; i++) {
 987		if (pool->base.clock_sources[i] == NULL) {
 988			dm_error("DC: failed to create clock sources!\n");
 989			BREAK_TO_DEBUGGER();
 990			goto res_create_fail;
 991		}
 992	}
 993
 994	pool->base.dmcu = dce_dmcu_create(ctx,
 995			&dmcu_regs,
 996			&dmcu_shift,
 997			&dmcu_mask);
 998	if (pool->base.dmcu == NULL) {
 999		dm_error("DC: failed to create dmcu!\n");
1000		BREAK_TO_DEBUGGER();
1001		goto res_create_fail;
1002	}
1003
1004	pool->base.abm = dce_abm_create(ctx,
1005			&abm_regs,
1006			&abm_shift,
1007			&abm_mask);
1008	if (pool->base.abm == NULL) {
1009		dm_error("DC: failed to create abm!\n");
1010		BREAK_TO_DEBUGGER();
1011		goto res_create_fail;
1012	}
1013
1014	{
1015		struct irq_service_init_data init_data;
1016		init_data.ctx = dc->ctx;
1017		pool->base.irqs = dal_irq_service_dce80_create(&init_data);
1018		if (!pool->base.irqs)
1019			goto res_create_fail;
1020	}
1021
1022	for (i = 0; i < pool->base.pipe_count; i++) {
1023		pool->base.timing_generators[i] = dce80_timing_generator_create(
1024				ctx, i, &dce80_tg_offsets[i]);
1025		if (pool->base.timing_generators[i] == NULL) {
1026			BREAK_TO_DEBUGGER();
1027			dm_error("DC: failed to create tg!\n");
1028			goto res_create_fail;
1029		}
1030
1031		pool->base.mis[i] = dce80_mem_input_create(ctx, i);
1032		if (pool->base.mis[i] == NULL) {
1033			BREAK_TO_DEBUGGER();
1034			dm_error("DC: failed to create memory input!\n");
1035			goto res_create_fail;
1036		}
1037
1038		pool->base.ipps[i] = dce80_ipp_create(ctx, i);
1039		if (pool->base.ipps[i] == NULL) {
1040			BREAK_TO_DEBUGGER();
1041			dm_error("DC: failed to create input pixel processor!\n");
1042			goto res_create_fail;
1043		}
1044
1045		pool->base.transforms[i] = dce80_transform_create(ctx, i);
1046		if (pool->base.transforms[i] == NULL) {
1047			BREAK_TO_DEBUGGER();
1048			dm_error("DC: failed to create transform!\n");
1049			goto res_create_fail;
1050		}
1051
1052		pool->base.opps[i] = dce80_opp_create(ctx, i);
1053		if (pool->base.opps[i] == NULL) {
1054			BREAK_TO_DEBUGGER();
1055			dm_error("DC: failed to create output pixel processor!\n");
1056			goto res_create_fail;
1057		}
1058	}
1059
1060	for (i = 0; i < pool->base.res_cap->num_ddc; i++) {
1061		pool->base.engines[i] = dce80_aux_engine_create(ctx, i);
1062		if (pool->base.engines[i] == NULL) {
1063			BREAK_TO_DEBUGGER();
1064			dm_error(
1065				"DC:failed to create aux engine!!\n");
1066			goto res_create_fail;
1067		}
1068		pool->base.hw_i2cs[i] = dce80_i2c_hw_create(ctx, i);
1069		if (pool->base.hw_i2cs[i] == NULL) {
1070			BREAK_TO_DEBUGGER();
1071			dm_error(
1072				"DC:failed to create i2c engine!!\n");
1073			goto res_create_fail;
1074		}
1075		pool->base.sw_i2cs[i] = dce80_i2c_sw_create(ctx);
1076		if (pool->base.sw_i2cs[i] == NULL) {
1077			BREAK_TO_DEBUGGER();
1078			dm_error(
1079				"DC:failed to create sw i2c!!\n");
1080			goto res_create_fail;
1081		}
1082	}
1083
1084	dc->caps.max_planes =  pool->base.pipe_count;
1085
1086	for (i = 0; i < dc->caps.max_planes; ++i)
1087		dc->caps.planes[i] = plane_cap;
1088
1089	dc->caps.disable_dp_clk_share = true;
1090
1091	if (!resource_construct(num_virtual_links, dc, &pool->base,
1092			&res_create_funcs))
1093		goto res_create_fail;
1094
1095	/* Create hardware sequencer */
1096	dce80_hw_sequencer_construct(dc);
1097
1098	return true;
1099
1100res_create_fail:
1101	dce80_resource_destruct(pool);
1102	return false;
1103}
1104
1105struct resource_pool *dce80_create_resource_pool(
1106	uint8_t num_virtual_links,
1107	struct dc *dc)
1108{
1109	struct dce110_resource_pool *pool =
1110		kzalloc(sizeof(struct dce110_resource_pool), GFP_KERNEL);
1111
1112	if (!pool)
1113		return NULL;
1114
1115	if (dce80_construct(num_virtual_links, dc, pool))
1116		return &pool->base;
1117
1118	kfree(pool);
1119	BREAK_TO_DEBUGGER();
1120	return NULL;
1121}
1122
1123static bool dce81_construct(
1124	uint8_t num_virtual_links,
1125	struct dc *dc,
1126	struct dce110_resource_pool *pool)
1127{
1128	unsigned int i;
1129	struct dc_context *ctx = dc->ctx;
1130	struct dc_bios *bp;
1131
1132	ctx->dc_bios->regs = &bios_regs;
1133
1134	pool->base.res_cap = &res_cap_81;
1135	pool->base.funcs = &dce80_res_pool_funcs;
1136
1137
1138	/*************************************************
1139	 *  Resource + asic cap harcoding                *
1140	 *************************************************/
1141	pool->base.underlay_pipe_index = NO_UNDERLAY_PIPE;
1142	pool->base.pipe_count = res_cap_81.num_timing_generator;
1143	pool->base.timing_generator_count = res_cap_81.num_timing_generator;
1144	dc->caps.max_downscale_ratio = 200;
1145	dc->caps.i2c_speed_in_khz = 40;
1146	dc->caps.i2c_speed_in_khz_hdcp = 40;
1147	dc->caps.max_cursor_size = 128;
1148	dc->caps.min_horizontal_blanking_period = 80;
1149	dc->caps.is_apu = true;
1150
1151	/*************************************************
1152	 *  Create resources                             *
1153	 *************************************************/
1154
1155	bp = ctx->dc_bios;
1156
1157	if (bp->fw_info_valid && bp->fw_info.external_clock_source_frequency_for_dp != 0) {
1158		pool->base.dp_clock_source =
1159				dce80_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_EXTERNAL, NULL, true);
1160
1161		pool->base.clock_sources[0] =
1162				dce80_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL0, &clk_src_regs[0], false);
1163		pool->base.clock_sources[1] =
1164				dce80_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL1, &clk_src_regs[1], false);
1165		pool->base.clock_sources[2] =
1166				dce80_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL2, &clk_src_regs[2], false);
1167		pool->base.clk_src_count = 3;
1168
1169	} else {
1170		pool->base.dp_clock_source =
1171				dce80_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL0, &clk_src_regs[0], true);
1172
1173		pool->base.clock_sources[0] =
1174				dce80_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL1, &clk_src_regs[1], false);
1175		pool->base.clock_sources[1] =
1176				dce80_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL2, &clk_src_regs[2], false);
1177		pool->base.clk_src_count = 2;
1178	}
1179
1180	if (pool->base.dp_clock_source == NULL) {
1181		dm_error("DC: failed to create dp clock source!\n");
1182		BREAK_TO_DEBUGGER();
1183		goto res_create_fail;
1184	}
1185
1186	for (i = 0; i < pool->base.clk_src_count; i++) {
1187		if (pool->base.clock_sources[i] == NULL) {
1188			dm_error("DC: failed to create clock sources!\n");
1189			BREAK_TO_DEBUGGER();
1190			goto res_create_fail;
1191		}
1192	}
1193
1194	pool->base.dmcu = dce_dmcu_create(ctx,
1195			&dmcu_regs,
1196			&dmcu_shift,
1197			&dmcu_mask);
1198	if (pool->base.dmcu == NULL) {
1199		dm_error("DC: failed to create dmcu!\n");
1200		BREAK_TO_DEBUGGER();
1201		goto res_create_fail;
1202	}
1203
1204	pool->base.abm = dce_abm_create(ctx,
1205			&abm_regs,
1206			&abm_shift,
1207			&abm_mask);
1208	if (pool->base.abm == NULL) {
1209		dm_error("DC: failed to create abm!\n");
1210		BREAK_TO_DEBUGGER();
1211		goto res_create_fail;
1212	}
1213
1214	{
1215		struct irq_service_init_data init_data;
1216		init_data.ctx = dc->ctx;
1217		pool->base.irqs = dal_irq_service_dce80_create(&init_data);
1218		if (!pool->base.irqs)
1219			goto res_create_fail;
1220	}
1221
1222	for (i = 0; i < pool->base.pipe_count; i++) {
1223		pool->base.timing_generators[i] = dce80_timing_generator_create(
1224				ctx, i, &dce80_tg_offsets[i]);
1225		if (pool->base.timing_generators[i] == NULL) {
1226			BREAK_TO_DEBUGGER();
1227			dm_error("DC: failed to create tg!\n");
1228			goto res_create_fail;
1229		}
1230
1231		pool->base.mis[i] = dce80_mem_input_create(ctx, i);
1232		if (pool->base.mis[i] == NULL) {
1233			BREAK_TO_DEBUGGER();
1234			dm_error("DC: failed to create memory input!\n");
1235			goto res_create_fail;
1236		}
1237
1238		pool->base.ipps[i] = dce80_ipp_create(ctx, i);
1239		if (pool->base.ipps[i] == NULL) {
1240			BREAK_TO_DEBUGGER();
1241			dm_error("DC: failed to create input pixel processor!\n");
1242			goto res_create_fail;
1243		}
1244
1245		pool->base.transforms[i] = dce80_transform_create(ctx, i);
1246		if (pool->base.transforms[i] == NULL) {
1247			BREAK_TO_DEBUGGER();
1248			dm_error("DC: failed to create transform!\n");
1249			goto res_create_fail;
1250		}
1251
1252		pool->base.opps[i] = dce80_opp_create(ctx, i);
1253		if (pool->base.opps[i] == NULL) {
1254			BREAK_TO_DEBUGGER();
1255			dm_error("DC: failed to create output pixel processor!\n");
1256			goto res_create_fail;
1257		}
1258	}
1259
1260	for (i = 0; i < pool->base.res_cap->num_ddc; i++) {
1261		pool->base.engines[i] = dce80_aux_engine_create(ctx, i);
1262		if (pool->base.engines[i] == NULL) {
1263			BREAK_TO_DEBUGGER();
1264			dm_error(
1265				"DC:failed to create aux engine!!\n");
1266			goto res_create_fail;
1267		}
1268		pool->base.hw_i2cs[i] = dce80_i2c_hw_create(ctx, i);
1269		if (pool->base.hw_i2cs[i] == NULL) {
1270			BREAK_TO_DEBUGGER();
1271			dm_error(
1272				"DC:failed to create i2c engine!!\n");
1273			goto res_create_fail;
1274		}
1275		pool->base.sw_i2cs[i] = dce80_i2c_sw_create(ctx);
1276		if (pool->base.sw_i2cs[i] == NULL) {
1277			BREAK_TO_DEBUGGER();
1278			dm_error(
1279				"DC:failed to create sw i2c!!\n");
1280			goto res_create_fail;
1281		}
1282	}
1283
1284	dc->caps.max_planes =  pool->base.pipe_count;
1285
1286	for (i = 0; i < dc->caps.max_planes; ++i)
1287		dc->caps.planes[i] = plane_cap;
1288
1289	dc->caps.disable_dp_clk_share = true;
1290
1291	if (!resource_construct(num_virtual_links, dc, &pool->base,
1292			&res_create_funcs))
1293		goto res_create_fail;
1294
1295	/* Create hardware sequencer */
1296	dce80_hw_sequencer_construct(dc);
1297
1298	return true;
1299
1300res_create_fail:
1301	dce80_resource_destruct(pool);
1302	return false;
1303}
1304
1305struct resource_pool *dce81_create_resource_pool(
1306	uint8_t num_virtual_links,
1307	struct dc *dc)
1308{
1309	struct dce110_resource_pool *pool =
1310		kzalloc(sizeof(struct dce110_resource_pool), GFP_KERNEL);
1311
1312	if (!pool)
1313		return NULL;
1314
1315	if (dce81_construct(num_virtual_links, dc, pool))
1316		return &pool->base;
1317
1318	kfree(pool);
1319	BREAK_TO_DEBUGGER();
1320	return NULL;
1321}
1322
1323static bool dce83_construct(
1324	uint8_t num_virtual_links,
1325	struct dc *dc,
1326	struct dce110_resource_pool *pool)
1327{
1328	unsigned int i;
1329	struct dc_context *ctx = dc->ctx;
1330	struct dc_bios *bp;
1331
1332	ctx->dc_bios->regs = &bios_regs;
1333
1334	pool->base.res_cap = &res_cap_83;
1335	pool->base.funcs = &dce80_res_pool_funcs;
1336
1337
1338	/*************************************************
1339	 *  Resource + asic cap harcoding                *
1340	 *************************************************/
1341	pool->base.underlay_pipe_index = NO_UNDERLAY_PIPE;
1342	pool->base.pipe_count = res_cap_83.num_timing_generator;
1343	pool->base.timing_generator_count = res_cap_83.num_timing_generator;
1344	dc->caps.max_downscale_ratio = 200;
1345	dc->caps.i2c_speed_in_khz = 40;
1346	dc->caps.i2c_speed_in_khz_hdcp = 40;
1347	dc->caps.max_cursor_size = 128;
1348	dc->caps.min_horizontal_blanking_period = 80;
1349	dc->caps.is_apu = true;
1350	dc->debug = debug_defaults;
1351	dc->check_config = config_defaults;
1352
1353	/*************************************************
1354	 *  Create resources                             *
1355	 *************************************************/
1356
1357	bp = ctx->dc_bios;
1358
1359	if (bp->fw_info_valid && bp->fw_info.external_clock_source_frequency_for_dp != 0) {
1360		pool->base.dp_clock_source =
1361				dce80_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_EXTERNAL, NULL, true);
1362
1363		pool->base.clock_sources[0] =
1364				dce80_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL1, &clk_src_regs[0], false);
1365		pool->base.clock_sources[1] =
1366				dce80_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL2, &clk_src_regs[1], false);
1367		pool->base.clk_src_count = 2;
1368
1369	} else {
1370		pool->base.dp_clock_source =
1371				dce80_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL1, &clk_src_regs[0], true);
1372
1373		pool->base.clock_sources[0] =
1374				dce80_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL2, &clk_src_regs[1], false);
1375		pool->base.clk_src_count = 1;
1376	}
1377
1378	if (pool->base.dp_clock_source == NULL) {
1379		dm_error("DC: failed to create dp clock source!\n");
1380		BREAK_TO_DEBUGGER();
1381		goto res_create_fail;
1382	}
1383
1384	for (i = 0; i < pool->base.clk_src_count; i++) {
1385		if (pool->base.clock_sources[i] == NULL) {
1386			dm_error("DC: failed to create clock sources!\n");
1387			BREAK_TO_DEBUGGER();
1388			goto res_create_fail;
1389		}
1390	}
1391
1392	pool->base.dmcu = dce_dmcu_create(ctx,
1393			&dmcu_regs,
1394			&dmcu_shift,
1395			&dmcu_mask);
1396	if (pool->base.dmcu == NULL) {
1397		dm_error("DC: failed to create dmcu!\n");
1398		BREAK_TO_DEBUGGER();
1399		goto res_create_fail;
1400	}
1401
1402	pool->base.abm = dce_abm_create(ctx,
1403			&abm_regs,
1404			&abm_shift,
1405			&abm_mask);
1406	if (pool->base.abm == NULL) {
1407		dm_error("DC: failed to create abm!\n");
1408		BREAK_TO_DEBUGGER();
1409		goto res_create_fail;
1410	}
1411
1412	{
1413		struct irq_service_init_data init_data;
1414		init_data.ctx = dc->ctx;
1415		pool->base.irqs = dal_irq_service_dce80_create(&init_data);
1416		if (!pool->base.irqs)
1417			goto res_create_fail;
1418	}
1419
1420	for (i = 0; i < pool->base.pipe_count; i++) {
1421		pool->base.timing_generators[i] = dce80_timing_generator_create(
1422				ctx, i, &dce80_tg_offsets[i]);
1423		if (pool->base.timing_generators[i] == NULL) {
1424			BREAK_TO_DEBUGGER();
1425			dm_error("DC: failed to create tg!\n");
1426			goto res_create_fail;
1427		}
1428
1429		pool->base.mis[i] = dce80_mem_input_create(ctx, i);
1430		if (pool->base.mis[i] == NULL) {
1431			BREAK_TO_DEBUGGER();
1432			dm_error("DC: failed to create memory input!\n");
1433			goto res_create_fail;
1434		}
1435
1436		pool->base.ipps[i] = dce80_ipp_create(ctx, i);
1437		if (pool->base.ipps[i] == NULL) {
1438			BREAK_TO_DEBUGGER();
1439			dm_error("DC: failed to create input pixel processor!\n");
1440			goto res_create_fail;
1441		}
1442
1443		pool->base.transforms[i] = dce80_transform_create(ctx, i);
1444		if (pool->base.transforms[i] == NULL) {
1445			BREAK_TO_DEBUGGER();
1446			dm_error("DC: failed to create transform!\n");
1447			goto res_create_fail;
1448		}
1449
1450		pool->base.opps[i] = dce80_opp_create(ctx, i);
1451		if (pool->base.opps[i] == NULL) {
1452			BREAK_TO_DEBUGGER();
1453			dm_error("DC: failed to create output pixel processor!\n");
1454			goto res_create_fail;
1455		}
1456	}
1457
1458	for (i = 0; i < pool->base.res_cap->num_ddc; i++) {
1459		pool->base.engines[i] = dce80_aux_engine_create(ctx, i);
1460		if (pool->base.engines[i] == NULL) {
1461			BREAK_TO_DEBUGGER();
1462			dm_error(
1463				"DC:failed to create aux engine!!\n");
1464			goto res_create_fail;
1465		}
1466		pool->base.hw_i2cs[i] = dce80_i2c_hw_create(ctx, i);
1467		if (pool->base.hw_i2cs[i] == NULL) {
1468			BREAK_TO_DEBUGGER();
1469			dm_error(
1470				"DC:failed to create i2c engine!!\n");
1471			goto res_create_fail;
1472		}
1473		pool->base.sw_i2cs[i] = dce80_i2c_sw_create(ctx);
1474		if (pool->base.sw_i2cs[i] == NULL) {
1475			BREAK_TO_DEBUGGER();
1476			dm_error(
1477				"DC:failed to create sw i2c!!\n");
1478			goto res_create_fail;
1479		}
1480	}
1481
1482	dc->caps.max_planes =  pool->base.pipe_count;
1483
1484	for (i = 0; i < dc->caps.max_planes; ++i)
1485		dc->caps.planes[i] = plane_cap;
1486
1487	dc->caps.disable_dp_clk_share = true;
1488
1489	if (!resource_construct(num_virtual_links, dc, &pool->base,
1490			&res_create_funcs))
1491		goto res_create_fail;
1492
1493	/* Create hardware sequencer */
1494	dce80_hw_sequencer_construct(dc);
1495
1496	return true;
1497
1498res_create_fail:
1499	dce80_resource_destruct(pool);
1500	return false;
1501}
1502
1503struct resource_pool *dce83_create_resource_pool(
1504	uint8_t num_virtual_links,
1505	struct dc *dc)
1506{
1507	struct dce110_resource_pool *pool =
1508		kzalloc(sizeof(struct dce110_resource_pool), GFP_KERNEL);
1509
1510	if (!pool)
1511		return NULL;
1512
1513	if (dce83_construct(num_virtual_links, dc, pool))
1514		return &pool->base;
1515
1516	kfree(pool);
1517	BREAK_TO_DEBUGGER();
1518	return NULL;
1519}
~/ Read-only file preview.