1 /* 2 * Copyright 2023 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 */ 23 24 #include "amdgpu.h" 25 #include "amdgpu_jpeg.h" 26 #include "amdgpu_pm.h" 27 #include "soc15.h" 28 #include "soc15d.h" 29 #include "jpeg_v2_0.h" 30 #include "jpeg_v4_0_5.h" 31 #include "mmsch_v4_0.h" 32 33 #include "vcn/vcn_4_0_5_offset.h" 34 #include "vcn/vcn_4_0_5_sh_mask.h" 35 #include "ivsrcid/vcn/irqsrcs_vcn_4_0.h" 36 37 #define mmUVD_DPG_LMA_CTL regUVD_DPG_LMA_CTL 38 #define mmUVD_DPG_LMA_CTL_BASE_IDX regUVD_DPG_LMA_CTL_BASE_IDX 39 #define mmUVD_DPG_LMA_DATA regUVD_DPG_LMA_DATA 40 #define mmUVD_DPG_LMA_DATA_BASE_IDX regUVD_DPG_LMA_DATA_BASE_IDX 41 42 #define regUVD_JPEG_PITCH_INTERNAL_OFFSET 0x401f 43 #define regJPEG_DEC_GFX10_ADDR_CONFIG_INTERNAL_OFFSET 0x4026 44 #define regJPEG_SYS_INT_EN_INTERNAL_OFFSET 0x4141 45 #define regJPEG_CGC_CTRL_INTERNAL_OFFSET 0x4161 46 #define regJPEG_CGC_GATE_INTERNAL_OFFSET 0x4160 47 #define regUVD_NO_OP_INTERNAL_OFFSET 0x0029 48 49 static const struct amdgpu_hwip_reg_entry jpeg_reg_list_4_0_5[] = { 50 SOC15_REG_ENTRY_STR(JPEG, 0, regUVD_JPEG_POWER_STATUS), 51 SOC15_REG_ENTRY_STR(JPEG, 0, regUVD_JPEG_INT_STAT), 52 SOC15_REG_ENTRY_STR(JPEG, 0, regUVD_JRBC_RB_RPTR), 53 SOC15_REG_ENTRY_STR(JPEG, 0, regUVD_JRBC_RB_WPTR), 54 SOC15_REG_ENTRY_STR(JPEG, 0, regUVD_JRBC_RB_CNTL), 55 SOC15_REG_ENTRY_STR(JPEG, 0, regUVD_JRBC_RB_SIZE), 56 SOC15_REG_ENTRY_STR(JPEG, 0, regUVD_JRBC_STATUS), 57 SOC15_REG_ENTRY_STR(JPEG, 0, regJPEG_DEC_ADDR_MODE), 58 SOC15_REG_ENTRY_STR(JPEG, 0, regJPEG_DEC_GFX10_ADDR_CONFIG), 59 SOC15_REG_ENTRY_STR(JPEG, 0, regJPEG_DEC_Y_GFX10_TILING_SURFACE), 60 SOC15_REG_ENTRY_STR(JPEG, 0, regJPEG_DEC_UV_GFX10_TILING_SURFACE), 61 SOC15_REG_ENTRY_STR(JPEG, 0, regUVD_JPEG_PITCH), 62 SOC15_REG_ENTRY_STR(JPEG, 0, regUVD_JPEG_UV_PITCH), 63 }; 64 65 static void jpeg_v4_0_5_set_dec_ring_funcs(struct amdgpu_device *adev); 66 static void jpeg_v4_0_5_set_irq_funcs(struct amdgpu_device *adev); 67 static int jpeg_v4_0_5_set_powergating_state(struct amdgpu_ip_block *ip_block, 68 enum amd_powergating_state state); 69 static void jpeg_v4_0_5_dec_ring_set_wptr(struct amdgpu_ring *ring); 70 71 static int amdgpu_ih_clientid_jpeg[] = { 72 SOC15_IH_CLIENTID_VCN, 73 SOC15_IH_CLIENTID_VCN1 74 }; 75 76 77 78 /** 79 * jpeg_v4_0_5_early_init - set function pointers 80 * 81 * @ip_block: Pointer to the amdgpu_ip_block for this hw instance. 82 * 83 * Set ring and irq function pointers 84 */ 85 static int jpeg_v4_0_5_early_init(struct amdgpu_ip_block *ip_block) 86 { 87 struct amdgpu_device *adev = ip_block->adev; 88 89 switch (amdgpu_ip_version(adev, UVD_HWIP, 0)) { 90 case IP_VERSION(4, 0, 5): 91 adev->jpeg.num_jpeg_inst = 1; 92 break; 93 case IP_VERSION(4, 0, 6): 94 adev->jpeg.num_jpeg_inst = 2; 95 break; 96 default: 97 DRM_DEV_ERROR(adev->dev, 98 "Failed to init vcn ip block(UVD_HWIP:0x%x)\n", 99 amdgpu_ip_version(adev, UVD_HWIP, 0)); 100 return -EINVAL; 101 } 102 103 adev->jpeg.num_jpeg_rings = 1; 104 105 jpeg_v4_0_5_set_dec_ring_funcs(adev); 106 jpeg_v4_0_5_set_irq_funcs(adev); 107 108 return 0; 109 } 110 111 /** 112 * jpeg_v4_0_5_sw_init - sw init for JPEG block 113 * 114 * @ip_block: Pointer to the amdgpu_ip_block for this hw instance. 115 * 116 * Load firmware and sw initialization 117 */ 118 static int jpeg_v4_0_5_sw_init(struct amdgpu_ip_block *ip_block) 119 { 120 struct amdgpu_device *adev = ip_block->adev; 121 struct amdgpu_ring *ring; 122 int r, i; 123 124 for (i = 0; i < adev->jpeg.num_jpeg_inst; ++i) { 125 if (adev->jpeg.harvest_config & (1 << i)) 126 continue; 127 128 /* JPEG TRAP */ 129 r = amdgpu_irq_add_id(adev, amdgpu_ih_clientid_jpeg[i], 130 VCN_4_0__SRCID__JPEG_DECODE, &adev->jpeg.inst[i].irq); 131 if (r) 132 return r; 133 134 /* JPEG DJPEG POISON EVENT */ 135 r = amdgpu_irq_add_id(adev, amdgpu_ih_clientid_jpeg[i], 136 VCN_4_0__SRCID_DJPEG0_POISON, &adev->jpeg.inst[i].irq); 137 if (r) 138 return r; 139 140 /* JPEG EJPEG POISON EVENT */ 141 r = amdgpu_irq_add_id(adev, amdgpu_ih_clientid_jpeg[i], 142 VCN_4_0__SRCID_EJPEG0_POISON, &adev->jpeg.inst[i].irq); 143 if (r) 144 return r; 145 } 146 147 r = amdgpu_jpeg_sw_init(adev); 148 if (r) 149 return r; 150 151 r = amdgpu_jpeg_resume(adev); 152 if (r) 153 return r; 154 155 for (i = 0; i < adev->jpeg.num_jpeg_inst; ++i) { 156 if (adev->jpeg.harvest_config & (1 << i)) 157 continue; 158 159 ring = adev->jpeg.inst[i].ring_dec; 160 ring->use_doorbell = true; 161 ring->vm_hub = AMDGPU_MMHUB0(0); 162 ring->doorbell_index = (adev->doorbell_index.vcn.vcn_ring0_1 << 1) + 1 + 8 * i; 163 sprintf(ring->name, "jpeg_dec_%d", i); 164 r = amdgpu_ring_init(adev, ring, 512, &adev->jpeg.inst[i].irq, 165 0, AMDGPU_RING_PRIO_DEFAULT, NULL); 166 if (r) 167 return r; 168 169 adev->jpeg.internal.jpeg_pitch[0] = regUVD_JPEG_PITCH_INTERNAL_OFFSET; 170 adev->jpeg.inst[i].external.jpeg_pitch[0] = SOC15_REG_OFFSET(JPEG, i, regUVD_JPEG_PITCH); 171 } 172 173 r = amdgpu_jpeg_reg_dump_init(adev, jpeg_reg_list_4_0_5, ARRAY_SIZE(jpeg_reg_list_4_0_5)); 174 if (r) 175 return r; 176 177 adev->jpeg.supported_reset = 178 amdgpu_get_soft_full_reset_mask(&adev->jpeg.inst[0].ring_dec[0]); 179 if (!amdgpu_sriov_vf(adev)) 180 adev->jpeg.supported_reset |= AMDGPU_RESET_TYPE_PER_QUEUE; 181 r = amdgpu_jpeg_sysfs_reset_mask_init(adev); 182 if (r) 183 return r; 184 185 return 0; 186 } 187 188 /** 189 * jpeg_v4_0_5_sw_fini - sw fini for JPEG block 190 * 191 * @ip_block: Pointer to the amdgpu_ip_block for this hw instance. 192 * 193 * JPEG suspend and free up sw allocation 194 */ 195 static int jpeg_v4_0_5_sw_fini(struct amdgpu_ip_block *ip_block) 196 { 197 struct amdgpu_device *adev = ip_block->adev; 198 int r; 199 200 r = amdgpu_jpeg_suspend(adev); 201 if (r) 202 return r; 203 204 amdgpu_jpeg_sysfs_reset_mask_fini(adev); 205 r = amdgpu_jpeg_sw_fini(adev); 206 207 return r; 208 } 209 210 /** 211 * jpeg_v4_0_5_hw_init - start and test JPEG block 212 * 213 * @ip_block: Pointer to the amdgpu_ip_block for this hw instance. 214 * 215 */ 216 static int jpeg_v4_0_5_hw_init(struct amdgpu_ip_block *ip_block) 217 { 218 struct amdgpu_device *adev = ip_block->adev; 219 struct amdgpu_ring *ring; 220 int i, r = 0; 221 222 // TODO: Enable ring test with DPG support 223 if (adev->pg_flags & AMD_PG_SUPPORT_JPEG_DPG) { 224 return 0; 225 } 226 227 for (i = 0; i < adev->jpeg.num_jpeg_inst; ++i) { 228 if (adev->jpeg.harvest_config & (1 << i)) 229 continue; 230 231 ring = adev->jpeg.inst[i].ring_dec; 232 r = amdgpu_ring_test_helper(ring); 233 if (r) 234 return r; 235 } 236 237 return 0; 238 } 239 240 /** 241 * jpeg_v4_0_5_hw_fini - stop the hardware block 242 * 243 * @ip_block: Pointer to the amdgpu_ip_block for this hw instance. 244 * 245 * Stop the JPEG block, mark ring as not ready any more 246 */ 247 static int jpeg_v4_0_5_hw_fini(struct amdgpu_ip_block *ip_block) 248 { 249 struct amdgpu_device *adev = ip_block->adev; 250 int i; 251 252 cancel_delayed_work_sync(&adev->jpeg.idle_work); 253 254 for (i = 0; i < adev->jpeg.num_jpeg_inst; ++i) { 255 if (adev->jpeg.harvest_config & (1 << i)) 256 continue; 257 258 if (!amdgpu_sriov_vf(adev)) { 259 if (adev->jpeg.cur_state != AMD_PG_STATE_GATE && 260 RREG32_SOC15(JPEG, i, regUVD_JRBC_STATUS)) 261 jpeg_v4_0_5_set_powergating_state(ip_block, AMD_PG_STATE_GATE); 262 } 263 } 264 return 0; 265 } 266 267 /** 268 * jpeg_v4_0_5_suspend - suspend JPEG block 269 * 270 * @ip_block: Pointer to the amdgpu_ip_block for this hw instance. 271 * 272 * HW fini and suspend JPEG block 273 */ 274 static int jpeg_v4_0_5_suspend(struct amdgpu_ip_block *ip_block) 275 { 276 int r; 277 278 r = jpeg_v4_0_5_hw_fini(ip_block); 279 if (r) 280 return r; 281 282 r = amdgpu_jpeg_suspend(ip_block->adev); 283 284 return r; 285 } 286 287 /** 288 * jpeg_v4_0_5_resume - resume JPEG block 289 * 290 * @ip_block: Pointer to the amdgpu_ip_block for this hw instance. 291 * 292 * Resume firmware and hw init JPEG block 293 */ 294 static int jpeg_v4_0_5_resume(struct amdgpu_ip_block *ip_block) 295 { 296 int r; 297 298 r = amdgpu_jpeg_resume(ip_block->adev); 299 if (r) 300 return r; 301 302 r = jpeg_v4_0_5_hw_init(ip_block); 303 304 return r; 305 } 306 307 static void jpeg_v4_0_5_disable_clock_gating(struct amdgpu_device *adev, int inst) 308 { 309 uint32_t data = 0; 310 311 data = RREG32_SOC15(JPEG, inst, regJPEG_CGC_CTRL); 312 if (adev->cg_flags & AMD_CG_SUPPORT_JPEG_MGCG) { 313 data |= 1 << JPEG_CGC_CTRL__DYN_CLOCK_MODE__SHIFT; 314 data &= (~JPEG_CGC_CTRL__JPEG_DEC_MODE_MASK); 315 } else { 316 data &= ~JPEG_CGC_CTRL__DYN_CLOCK_MODE__SHIFT; 317 } 318 319 data |= 1 << JPEG_CGC_CTRL__CLK_GATE_DLY_TIMER__SHIFT; 320 data |= 4 << JPEG_CGC_CTRL__CLK_OFF_DELAY__SHIFT; 321 WREG32_SOC15(JPEG, inst, regJPEG_CGC_CTRL, data); 322 323 data = RREG32_SOC15(JPEG, inst, regJPEG_CGC_GATE); 324 data &= ~(JPEG_CGC_GATE__JPEG_DEC_MASK 325 | JPEG_CGC_GATE__JPEG2_DEC_MASK 326 | JPEG_CGC_GATE__JMCIF_MASK 327 | JPEG_CGC_GATE__JRBBM_MASK); 328 WREG32_SOC15(JPEG, inst, regJPEG_CGC_GATE, data); 329 } 330 331 static void jpeg_v4_0_5_enable_clock_gating(struct amdgpu_device *adev, int inst) 332 { 333 uint32_t data = 0; 334 335 data = RREG32_SOC15(JPEG, inst, regJPEG_CGC_CTRL); 336 if (adev->cg_flags & AMD_CG_SUPPORT_JPEG_MGCG) { 337 data |= 1 << JPEG_CGC_CTRL__DYN_CLOCK_MODE__SHIFT; 338 data |= JPEG_CGC_CTRL__JPEG_DEC_MODE_MASK; 339 } else { 340 data &= ~JPEG_CGC_CTRL__DYN_CLOCK_MODE__SHIFT; 341 } 342 343 data |= 1 << JPEG_CGC_CTRL__CLK_GATE_DLY_TIMER__SHIFT; 344 data |= 4 << JPEG_CGC_CTRL__CLK_OFF_DELAY__SHIFT; 345 WREG32_SOC15(JPEG, inst, regJPEG_CGC_CTRL, data); 346 347 data = RREG32_SOC15(JPEG, inst, regJPEG_CGC_GATE); 348 data |= (JPEG_CGC_GATE__JPEG_DEC_MASK 349 |JPEG_CGC_GATE__JPEG2_DEC_MASK 350 |JPEG_CGC_GATE__JMCIF_MASK 351 |JPEG_CGC_GATE__JRBBM_MASK); 352 WREG32_SOC15(JPEG, inst, regJPEG_CGC_GATE, data); 353 } 354 355 static void jpeg_engine_4_0_5_dpg_clock_gating_mode(struct amdgpu_device *adev, 356 int inst_idx, uint8_t indirect) 357 { 358 uint32_t data = 0; 359 360 if (adev->cg_flags & AMD_CG_SUPPORT_JPEG_MGCG) 361 data |= 1 << JPEG_CGC_CTRL__DYN_CLOCK_MODE__SHIFT; 362 else 363 data |= 0 << JPEG_CGC_CTRL__DYN_CLOCK_MODE__SHIFT; 364 365 data |= 1 << JPEG_CGC_CTRL__CLK_GATE_DLY_TIMER__SHIFT; 366 data |= 4 << JPEG_CGC_CTRL__CLK_OFF_DELAY__SHIFT; 367 WREG32_SOC15_JPEG_DPG_MODE(inst_idx, regJPEG_CGC_CTRL_INTERNAL_OFFSET, data, indirect); 368 369 data = 0; 370 WREG32_SOC15_JPEG_DPG_MODE(inst_idx, regJPEG_CGC_GATE_INTERNAL_OFFSET, 371 data, indirect); 372 } 373 374 static int jpeg_v4_0_5_disable_static_power_gating(struct amdgpu_device *adev, int inst) 375 { 376 if (adev->pg_flags & AMD_PG_SUPPORT_JPEG) { 377 WREG32(SOC15_REG_OFFSET(JPEG, inst, regUVD_IPX_DLDO_CONFIG), 378 1 << UVD_IPX_DLDO_CONFIG__ONO1_PWR_CONFIG__SHIFT); 379 SOC15_WAIT_ON_RREG(JPEG, inst, regUVD_IPX_DLDO_STATUS, 380 0, UVD_IPX_DLDO_STATUS__ONO1_PWR_STATUS_MASK); 381 } 382 383 /* disable anti hang mechanism */ 384 WREG32_P(SOC15_REG_OFFSET(JPEG, inst, regUVD_JPEG_POWER_STATUS), 0, 385 ~UVD_JPEG_POWER_STATUS__JPEG_POWER_STATUS_MASK); 386 387 /* keep the JPEG in static PG mode */ 388 WREG32_P(SOC15_REG_OFFSET(JPEG, inst, regUVD_JPEG_POWER_STATUS), 0, 389 ~UVD_JPEG_POWER_STATUS__JPEG_PG_MODE_MASK); 390 391 return 0; 392 } 393 394 static int jpeg_v4_0_5_enable_static_power_gating(struct amdgpu_device *adev, int inst) 395 { 396 /* enable anti hang mechanism */ 397 WREG32_P(SOC15_REG_OFFSET(JPEG, inst, regUVD_JPEG_POWER_STATUS), 398 UVD_JPEG_POWER_STATUS__JPEG_POWER_STATUS_MASK, 399 ~UVD_JPEG_POWER_STATUS__JPEG_POWER_STATUS_MASK); 400 401 if (adev->pg_flags & AMD_PG_SUPPORT_JPEG) { 402 WREG32(SOC15_REG_OFFSET(JPEG, inst, regUVD_IPX_DLDO_CONFIG), 403 2 << UVD_IPX_DLDO_CONFIG__ONO1_PWR_CONFIG__SHIFT); 404 SOC15_WAIT_ON_RREG(JPEG, inst, regUVD_IPX_DLDO_STATUS, 405 1 << UVD_IPX_DLDO_STATUS__ONO1_PWR_STATUS__SHIFT, 406 UVD_IPX_DLDO_STATUS__ONO1_PWR_STATUS_MASK); 407 } 408 409 return 0; 410 } 411 412 /** 413 * jpeg_v4_0_5_start_dpg_mode - Jpeg start with dpg mode 414 * 415 * @adev: amdgpu_device pointer 416 * @inst_idx: instance number index 417 * @indirect: indirectly write sram 418 * 419 * Start JPEG block with dpg mode 420 */ 421 static void jpeg_v4_0_5_start_dpg_mode(struct amdgpu_device *adev, int inst_idx, bool indirect) 422 { 423 struct amdgpu_ring *ring = adev->jpeg.inst[inst_idx].ring_dec; 424 uint32_t reg_data = 0; 425 426 /* enable anti hang mechanism */ 427 reg_data = RREG32_SOC15(JPEG, inst_idx, regUVD_JPEG_POWER_STATUS); 428 reg_data &= ~UVD_JPEG_POWER_STATUS__JPEG_POWER_STATUS_MASK; 429 reg_data |= 0x1; 430 WREG32_SOC15(JPEG, inst_idx, regUVD_JPEG_POWER_STATUS, reg_data); 431 432 if (adev->pg_flags & AMD_PG_SUPPORT_JPEG) { 433 WREG32(SOC15_REG_OFFSET(JPEG, inst_idx, regUVD_IPX_DLDO_CONFIG), 434 2 << UVD_IPX_DLDO_CONFIG__ONO1_PWR_CONFIG__SHIFT); 435 SOC15_WAIT_ON_RREG(JPEG, inst_idx, regUVD_IPX_DLDO_STATUS, 436 1 << UVD_IPX_DLDO_STATUS__ONO1_PWR_STATUS__SHIFT, 437 UVD_IPX_DLDO_STATUS__ONO1_PWR_STATUS_MASK); 438 } 439 440 reg_data = RREG32_SOC15(JPEG, inst_idx, regUVD_JPEG_POWER_STATUS); 441 reg_data |= UVD_JPEG_POWER_STATUS__JPEG_PG_MODE_MASK; 442 WREG32_SOC15(JPEG, inst_idx, regUVD_JPEG_POWER_STATUS, reg_data); 443 444 if (indirect) 445 adev->jpeg.inst[inst_idx].dpg_sram_curr_addr = 446 (uint32_t *)adev->jpeg.inst[inst_idx].dpg_sram_cpu_addr; 447 448 jpeg_engine_4_0_5_dpg_clock_gating_mode(adev, inst_idx, indirect); 449 450 /* MJPEG global tiling registers */ 451 WREG32_SOC15_JPEG_DPG_MODE(inst_idx, regJPEG_DEC_GFX10_ADDR_CONFIG_INTERNAL_OFFSET, 452 adev->gfx.config.gb_addr_config, indirect); 453 /* enable System Interrupt for JRBC */ 454 WREG32_SOC15_JPEG_DPG_MODE(inst_idx, regJPEG_SYS_INT_EN_INTERNAL_OFFSET, 455 JPEG_SYS_INT_EN__DJRBC_MASK, indirect); 456 457 /* add nop to workaround PSP size check */ 458 WREG32_SOC15_JPEG_DPG_MODE(inst_idx, regUVD_NO_OP_INTERNAL_OFFSET, 0, indirect); 459 460 if (indirect) 461 amdgpu_jpeg_psp_update_sram(adev, inst_idx, 0); 462 463 WREG32_SOC15(JPEG, inst_idx, regUVD_LMI_JRBC_RB_VMID, 0); 464 WREG32_SOC15(JPEG, inst_idx, regUVD_JRBC_RB_CNTL, (0x00000001L | 0x00000002L)); 465 WREG32_SOC15(JPEG, inst_idx, regUVD_LMI_JRBC_RB_64BIT_BAR_LOW, 466 lower_32_bits(ring->gpu_addr)); 467 WREG32_SOC15(JPEG, inst_idx, regUVD_LMI_JRBC_RB_64BIT_BAR_HIGH, 468 upper_32_bits(ring->gpu_addr)); 469 WREG32_SOC15(JPEG, inst_idx, regUVD_JRBC_RB_RPTR, 0); 470 WREG32_SOC15(JPEG, inst_idx, regUVD_JRBC_RB_WPTR, 0); 471 WREG32_SOC15(JPEG, inst_idx, regUVD_JRBC_RB_CNTL, 0x00000002L); 472 WREG32_SOC15(JPEG, inst_idx, regUVD_JRBC_RB_SIZE, ring->ring_size / 4); 473 ring->wptr = RREG32_SOC15(JPEG, inst_idx, regUVD_JRBC_RB_WPTR); 474 } 475 476 /** 477 * jpeg_v4_0_5_stop_dpg_mode - Jpeg stop with dpg mode 478 * 479 * @adev: amdgpu_device pointer 480 * @inst_idx: instance number index 481 * 482 * Stop JPEG block with dpg mode 483 */ 484 static void jpeg_v4_0_5_stop_dpg_mode(struct amdgpu_device *adev, int inst_idx) 485 { 486 uint32_t reg_data = 0; 487 488 reg_data = RREG32_SOC15(JPEG, inst_idx, regUVD_JPEG_POWER_STATUS); 489 reg_data &= ~UVD_JPEG_POWER_STATUS__JPEG_PG_MODE_MASK; 490 WREG32_SOC15(JPEG, inst_idx, regUVD_JPEG_POWER_STATUS, reg_data); 491 492 } 493 494 /** 495 * jpeg_v4_0_5_start - start JPEG block 496 * 497 * @adev: amdgpu_device pointer 498 * 499 * Setup and start the JPEG block 500 */ 501 static int jpeg_v4_0_5_start(struct amdgpu_device *adev) 502 { 503 struct amdgpu_ring *ring; 504 int r, i; 505 506 if (adev->pm.dpm_enabled) 507 amdgpu_dpm_enable_jpeg(adev, true); 508 509 for (i = 0; i < adev->jpeg.num_jpeg_inst; ++i) { 510 if (adev->jpeg.harvest_config & (1 << i)) 511 continue; 512 513 ring = adev->jpeg.inst[i].ring_dec; 514 /* doorbell programming is done for every playback */ 515 adev->nbio.funcs->vcn_doorbell_range(adev, ring->use_doorbell, 516 (adev->doorbell_index.vcn.vcn_ring0_1 << 1) + 8 * i, i); 517 518 WREG32_SOC15(VCN, i, regVCN_JPEG_DB_CTRL, 519 ring->doorbell_index << VCN_JPEG_DB_CTRL__OFFSET__SHIFT | 520 VCN_JPEG_DB_CTRL__EN_MASK); 521 522 if (adev->pg_flags & AMD_PG_SUPPORT_JPEG_DPG) { 523 jpeg_v4_0_5_start_dpg_mode(adev, i, adev->jpeg.indirect_sram); 524 continue; 525 } 526 527 /* disable power gating */ 528 r = jpeg_v4_0_5_disable_static_power_gating(adev, i); 529 if (r) 530 return r; 531 532 /* JPEG disable CGC */ 533 jpeg_v4_0_5_disable_clock_gating(adev, i); 534 535 /* MJPEG global tiling registers */ 536 WREG32_SOC15(JPEG, i, regJPEG_DEC_GFX10_ADDR_CONFIG, 537 adev->gfx.config.gb_addr_config); 538 539 /* enable JMI channel */ 540 WREG32_P(SOC15_REG_OFFSET(JPEG, i, regUVD_JMI_CNTL), 0, 541 ~UVD_JMI_CNTL__SOFT_RESET_MASK); 542 543 /* enable System Interrupt for JRBC */ 544 WREG32_P(SOC15_REG_OFFSET(JPEG, i, regJPEG_SYS_INT_EN), 545 JPEG_SYS_INT_EN__DJRBC_MASK, 546 ~JPEG_SYS_INT_EN__DJRBC_MASK); 547 548 WREG32_SOC15(JPEG, i, regUVD_LMI_JRBC_RB_VMID, 0); 549 WREG32_SOC15(JPEG, i, regUVD_JRBC_RB_CNTL, (0x00000001L | 0x00000002L)); 550 WREG32_SOC15(JPEG, i, regUVD_LMI_JRBC_RB_64BIT_BAR_LOW, 551 lower_32_bits(ring->gpu_addr)); 552 WREG32_SOC15(JPEG, i, regUVD_LMI_JRBC_RB_64BIT_BAR_HIGH, 553 upper_32_bits(ring->gpu_addr)); 554 WREG32_SOC15(JPEG, i, regUVD_JRBC_RB_RPTR, 0); 555 WREG32_SOC15(JPEG, i, regUVD_JRBC_RB_WPTR, 0); 556 WREG32_SOC15(JPEG, i, regUVD_JRBC_RB_CNTL, 0x00000002L); 557 WREG32_SOC15(JPEG, i, regUVD_JRBC_RB_SIZE, ring->ring_size / 4); 558 ring->wptr = RREG32_SOC15(JPEG, i, regUVD_JRBC_RB_WPTR); 559 } 560 561 return 0; 562 } 563 564 /** 565 * jpeg_v4_0_5_stop - stop JPEG block 566 * 567 * @adev: amdgpu_device pointer 568 * 569 * stop the JPEG block 570 */ 571 static int jpeg_v4_0_5_stop(struct amdgpu_device *adev) 572 { 573 int r, i; 574 575 for (i = 0; i < adev->jpeg.num_jpeg_inst; ++i) { 576 if (adev->jpeg.harvest_config & (1 << i)) 577 continue; 578 579 if (adev->pg_flags & AMD_PG_SUPPORT_JPEG_DPG) { 580 jpeg_v4_0_5_stop_dpg_mode(adev, i); 581 continue; 582 } 583 584 /* reset JMI */ 585 WREG32_P(SOC15_REG_OFFSET(JPEG, i, regUVD_JMI_CNTL), 586 UVD_JMI_CNTL__SOFT_RESET_MASK, 587 ~UVD_JMI_CNTL__SOFT_RESET_MASK); 588 589 jpeg_v4_0_5_enable_clock_gating(adev, i); 590 591 /* enable power gating */ 592 r = jpeg_v4_0_5_enable_static_power_gating(adev, i); 593 if (r) 594 return r; 595 } 596 if (adev->pm.dpm_enabled) 597 amdgpu_dpm_enable_jpeg(adev, false); 598 599 return 0; 600 } 601 602 /** 603 * jpeg_v4_0_5_dec_ring_get_rptr - get read pointer 604 * 605 * @ring: amdgpu_ring pointer 606 * 607 * Returns the current hardware read pointer 608 */ 609 static uint64_t jpeg_v4_0_5_dec_ring_get_rptr(struct amdgpu_ring *ring) 610 { 611 struct amdgpu_device *adev = ring->adev; 612 613 return RREG32_SOC15(JPEG, ring->me, regUVD_JRBC_RB_RPTR); 614 } 615 616 /** 617 * jpeg_v4_0_5_dec_ring_get_wptr - get write pointer 618 * 619 * @ring: amdgpu_ring pointer 620 * 621 * Returns the current hardware write pointer 622 */ 623 static uint64_t jpeg_v4_0_5_dec_ring_get_wptr(struct amdgpu_ring *ring) 624 { 625 struct amdgpu_device *adev = ring->adev; 626 627 if (ring->use_doorbell) 628 return *ring->wptr_cpu_addr; 629 else 630 return RREG32_SOC15(JPEG, ring->me, regUVD_JRBC_RB_WPTR); 631 } 632 633 /** 634 * jpeg_v4_0_5_dec_ring_set_wptr - set write pointer 635 * 636 * @ring: amdgpu_ring pointer 637 * 638 * Commits the write pointer to the hardware 639 */ 640 static void jpeg_v4_0_5_dec_ring_set_wptr(struct amdgpu_ring *ring) 641 { 642 struct amdgpu_device *adev = ring->adev; 643 644 if (ring->use_doorbell) { 645 *ring->wptr_cpu_addr = lower_32_bits(ring->wptr); 646 WDOORBELL32(ring->doorbell_index, lower_32_bits(ring->wptr)); 647 } else { 648 WREG32_SOC15(JPEG, ring->me, regUVD_JRBC_RB_WPTR, lower_32_bits(ring->wptr)); 649 } 650 } 651 652 static bool jpeg_v4_0_5_is_idle(struct amdgpu_ip_block *ip_block) 653 { 654 struct amdgpu_device *adev = ip_block->adev; 655 int i, ret = 1; 656 657 for (i = 0; i < adev->jpeg.num_jpeg_inst; ++i) { 658 if (adev->jpeg.harvest_config & (1 << i)) 659 continue; 660 661 ret &= (((RREG32_SOC15(JPEG, i, regUVD_JRBC_STATUS) & 662 UVD_JRBC_STATUS__RB_JOB_DONE_MASK) == 663 UVD_JRBC_STATUS__RB_JOB_DONE_MASK)); 664 } 665 return ret; 666 } 667 668 static int jpeg_v4_0_5_wait_for_idle(struct amdgpu_ip_block *ip_block) 669 { 670 struct amdgpu_device *adev = ip_block->adev; 671 int i; 672 673 for (i = 0; i < adev->jpeg.num_jpeg_inst; ++i) { 674 if (adev->jpeg.harvest_config & (1 << i)) 675 continue; 676 677 return SOC15_WAIT_ON_RREG(JPEG, i, regUVD_JRBC_STATUS, 678 UVD_JRBC_STATUS__RB_JOB_DONE_MASK, 679 UVD_JRBC_STATUS__RB_JOB_DONE_MASK); 680 } 681 682 return 0; 683 } 684 685 static int jpeg_v4_0_5_set_clockgating_state(struct amdgpu_ip_block *ip_block, 686 enum amd_clockgating_state state) 687 { 688 struct amdgpu_device *adev = ip_block->adev; 689 bool enable = (state == AMD_CG_STATE_GATE) ? true : false; 690 int i; 691 692 for (i = 0; i < adev->jpeg.num_jpeg_inst; ++i) { 693 if (adev->jpeg.harvest_config & (1 << i)) 694 continue; 695 696 if (enable) { 697 if (!jpeg_v4_0_5_is_idle(ip_block)) 698 return -EBUSY; 699 700 jpeg_v4_0_5_enable_clock_gating(adev, i); 701 } else { 702 jpeg_v4_0_5_disable_clock_gating(adev, i); 703 } 704 } 705 706 return 0; 707 } 708 709 static int jpeg_v4_0_5_set_powergating_state(struct amdgpu_ip_block *ip_block, 710 enum amd_powergating_state state) 711 { 712 struct amdgpu_device *adev = ip_block->adev; 713 int ret; 714 715 if (amdgpu_sriov_vf(adev)) { 716 adev->jpeg.cur_state = AMD_PG_STATE_UNGATE; 717 return 0; 718 } 719 720 if (state == adev->jpeg.cur_state) 721 return 0; 722 723 if (state == AMD_PG_STATE_GATE) 724 ret = jpeg_v4_0_5_stop(adev); 725 else 726 ret = jpeg_v4_0_5_start(adev); 727 728 if (!ret) 729 adev->jpeg.cur_state = state; 730 731 return ret; 732 } 733 734 static int jpeg_v4_0_5_process_interrupt(struct amdgpu_device *adev, 735 struct amdgpu_irq_src *source, 736 struct amdgpu_iv_entry *entry) 737 { 738 uint32_t ip_instance; 739 740 DRM_DEBUG("IH: JPEG TRAP\n"); 741 742 switch (entry->client_id) { 743 case SOC15_IH_CLIENTID_VCN: 744 ip_instance = 0; 745 break; 746 case SOC15_IH_CLIENTID_VCN1: 747 ip_instance = 1; 748 break; 749 default: 750 DRM_ERROR("Unhandled client id: %d\n", entry->client_id); 751 return 0; 752 } 753 754 switch (entry->src_id) { 755 case VCN_4_0__SRCID__JPEG_DECODE: 756 amdgpu_fence_process(adev->jpeg.inst[ip_instance].ring_dec); 757 break; 758 case VCN_4_0__SRCID_DJPEG0_POISON: 759 case VCN_4_0__SRCID_EJPEG0_POISON: 760 amdgpu_jpeg_process_poison_irq(adev, source, entry); 761 break; 762 default: 763 DRM_DEV_ERROR(adev->dev, "Unhandled interrupt: %d %d\n", 764 entry->src_id, entry->src_data[0]); 765 break; 766 } 767 768 return 0; 769 } 770 771 static int jpeg_v4_0_5_ring_reset(struct amdgpu_ring *ring, 772 unsigned int vmid, 773 struct amdgpu_fence *timedout_fence) 774 { 775 int r; 776 777 amdgpu_ring_reset_helper_begin(ring, timedout_fence); 778 r = jpeg_v4_0_5_stop(ring->adev); 779 if (r) 780 return r; 781 r = jpeg_v4_0_5_start(ring->adev); 782 if (r) 783 return r; 784 return amdgpu_ring_reset_helper_end(ring, timedout_fence); 785 } 786 787 static const struct amd_ip_funcs jpeg_v4_0_5_ip_funcs = { 788 .name = "jpeg_v4_0_5", 789 .early_init = jpeg_v4_0_5_early_init, 790 .sw_init = jpeg_v4_0_5_sw_init, 791 .sw_fini = jpeg_v4_0_5_sw_fini, 792 .hw_init = jpeg_v4_0_5_hw_init, 793 .hw_fini = jpeg_v4_0_5_hw_fini, 794 .suspend = jpeg_v4_0_5_suspend, 795 .resume = jpeg_v4_0_5_resume, 796 .is_idle = jpeg_v4_0_5_is_idle, 797 .wait_for_idle = jpeg_v4_0_5_wait_for_idle, 798 .set_clockgating_state = jpeg_v4_0_5_set_clockgating_state, 799 .set_powergating_state = jpeg_v4_0_5_set_powergating_state, 800 .dump_ip_state = amdgpu_jpeg_dump_ip_state, 801 .print_ip_state = amdgpu_jpeg_print_ip_state, 802 }; 803 804 static const struct amdgpu_ring_funcs jpeg_v4_0_5_dec_ring_vm_funcs = { 805 .type = AMDGPU_RING_TYPE_VCN_JPEG, 806 .align_mask = 0xf, 807 .get_rptr = jpeg_v4_0_5_dec_ring_get_rptr, 808 .get_wptr = jpeg_v4_0_5_dec_ring_get_wptr, 809 .set_wptr = jpeg_v4_0_5_dec_ring_set_wptr, 810 .parse_cs = jpeg_v2_dec_ring_parse_cs, 811 .emit_frame_size = 812 SOC15_FLUSH_GPU_TLB_NUM_WREG * 6 + 813 SOC15_FLUSH_GPU_TLB_NUM_REG_WAIT * 8 + 814 8 + /* jpeg_v4_0_5_dec_ring_emit_vm_flush */ 815 18 + 18 + /* jpeg_v4_0_5_dec_ring_emit_fence x2 vm fence */ 816 8 + 16, 817 .emit_ib_size = 22, /* jpeg_v4_0_5_dec_ring_emit_ib */ 818 .emit_ib = jpeg_v2_0_dec_ring_emit_ib, 819 .emit_fence = jpeg_v2_0_dec_ring_emit_fence, 820 .emit_vm_flush = jpeg_v2_0_dec_ring_emit_vm_flush, 821 .test_ring = amdgpu_jpeg_dec_ring_test_ring, 822 .test_ib = amdgpu_jpeg_dec_ring_test_ib, 823 .insert_nop = jpeg_v2_0_dec_ring_nop, 824 .insert_start = jpeg_v2_0_dec_ring_insert_start, 825 .insert_end = jpeg_v2_0_dec_ring_insert_end, 826 .pad_ib = amdgpu_ring_generic_pad_ib, 827 .begin_use = amdgpu_jpeg_ring_begin_use, 828 .end_use = amdgpu_jpeg_ring_end_use, 829 .emit_wreg = jpeg_v2_0_dec_ring_emit_wreg, 830 .emit_reg_wait = jpeg_v2_0_dec_ring_emit_reg_wait, 831 .emit_reg_write_reg_wait = amdgpu_ring_emit_reg_write_reg_wait_helper, 832 .reset = jpeg_v4_0_5_ring_reset, 833 }; 834 835 static void jpeg_v4_0_5_set_dec_ring_funcs(struct amdgpu_device *adev) 836 { 837 int i; 838 839 for (i = 0; i < adev->jpeg.num_jpeg_inst; ++i) { 840 if (adev->jpeg.harvest_config & (1 << i)) 841 continue; 842 843 adev->jpeg.inst[i].ring_dec->funcs = &jpeg_v4_0_5_dec_ring_vm_funcs; 844 adev->jpeg.inst[i].ring_dec->me = i; 845 } 846 } 847 848 static const struct amdgpu_irq_src_funcs jpeg_v4_0_5_irq_funcs = { 849 .process = jpeg_v4_0_5_process_interrupt, 850 }; 851 852 static void jpeg_v4_0_5_set_irq_funcs(struct amdgpu_device *adev) 853 { 854 int i; 855 856 for (i = 0; i < adev->jpeg.num_jpeg_inst; ++i) { 857 if (adev->jpeg.harvest_config & (1 << i)) 858 continue; 859 860 adev->jpeg.inst[i].irq.num_types = 1; 861 adev->jpeg.inst[i].irq.funcs = &jpeg_v4_0_5_irq_funcs; 862 } 863 } 864 865 const struct amdgpu_ip_block_version jpeg_v4_0_5_ip_block = { 866 .type = AMD_IP_BLOCK_TYPE_JPEG, 867 .major = 4, 868 .minor = 0, 869 .rev = 5, 870 .funcs = &jpeg_v4_0_5_ip_funcs, 871 }; 872 873