aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/gpu/drm/amd/amdgpu/amdgpu_acp.c
diff options
context:
space:
mode:
authorAkshu Agrawal <akshu.agrawal@amd.com>2017-09-18 02:56:07 -0400
committerAlex Deucher <alexander.deucher@amd.com>2017-11-03 15:44:46 -0400
commit37c5f2c99adf63adf13f1ca309a1ffce25c5589a (patch)
treebcd946fc22f5eeafbf717fe30a1c323763bea586 /drivers/gpu/drm/amd/amdgpu/amdgpu_acp.c
parente477e940dad1836c6f6d23353e424665b9316b6e (diff)
drm/amd/amdgpu: Enabling ACP clock in hw_init (v2)
Enabling of ACP in hw_init does away with requirement of order of probe on designware_i2s and acp dma driver. designware_i2s reads i2s registers and this use to fail if acp dma driver was not probed prior to it. BUG=:b:62103837 TEST=modprobe snd-soc-acp-pcm modprobe snd-soc-acp-rt5645-mach aplay -l **** List of PLAYBACK Hardware Devices **** card 0: acprt5650 [acprt5650], device 0: RT5645_AIF1 rt5645-aif1-0 [] Subdevices: 1/1 Subdevice #0: subdevice #0 v2: use proper device in dev_err to fix warnings (Alex) Signed-off-by: Akshu Agrawal <akshu.agrawal@amd.com> Reviewed-on: https://chromium-review.googlesource.com/670207 Reviewed-by: Jason Clinton <jclinton@chromium.org> Reviewed-on: https://chromium-review.googlesource.com/676628 Signed-off-by: Alex Deucher <alexander.deucher@amd.com>
Diffstat (limited to 'drivers/gpu/drm/amd/amdgpu/amdgpu_acp.c')
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_acp.c159
1 files changed, 124 insertions, 35 deletions
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_acp.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_acp.c
index a52795d9b458..023bfdb3e63f 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_acp.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_acp.c
@@ -35,41 +35,50 @@
35 35
36#include "acp_gfx_if.h" 36#include "acp_gfx_if.h"
37 37
38#define ACP_TILE_ON_MASK 0x03 38#define ACP_TILE_ON_MASK 0x03
39#define ACP_TILE_OFF_MASK 0x02 39#define ACP_TILE_OFF_MASK 0x02
40#define ACP_TILE_ON_RETAIN_REG_MASK 0x1f 40#define ACP_TILE_ON_RETAIN_REG_MASK 0x1f
41#define ACP_TILE_OFF_RETAIN_REG_MASK 0x20 41#define ACP_TILE_OFF_RETAIN_REG_MASK 0x20
42 42
43#define ACP_TILE_P1_MASK 0x3e 43#define ACP_TILE_P1_MASK 0x3e
44#define ACP_TILE_P2_MASK 0x3d 44#define ACP_TILE_P2_MASK 0x3d
45#define ACP_TILE_DSP0_MASK 0x3b 45#define ACP_TILE_DSP0_MASK 0x3b
46#define ACP_TILE_DSP1_MASK 0x37 46#define ACP_TILE_DSP1_MASK 0x37
47 47
48#define ACP_TILE_DSP2_MASK 0x2f 48#define ACP_TILE_DSP2_MASK 0x2f
49 49
50#define ACP_DMA_REGS_END 0x146c0 50#define ACP_DMA_REGS_END 0x146c0
51#define ACP_I2S_PLAY_REGS_START 0x14840 51#define ACP_I2S_PLAY_REGS_START 0x14840
52#define ACP_I2S_PLAY_REGS_END 0x148b4 52#define ACP_I2S_PLAY_REGS_END 0x148b4
53#define ACP_I2S_CAP_REGS_START 0x148b8 53#define ACP_I2S_CAP_REGS_START 0x148b8
54#define ACP_I2S_CAP_REGS_END 0x1496c 54#define ACP_I2S_CAP_REGS_END 0x1496c
55 55
56#define ACP_I2S_COMP1_CAP_REG_OFFSET 0xac 56#define ACP_I2S_COMP1_CAP_REG_OFFSET 0xac
57#define ACP_I2S_COMP2_CAP_REG_OFFSET 0xa8 57#define ACP_I2S_COMP2_CAP_REG_OFFSET 0xa8
58#define ACP_I2S_COMP1_PLAY_REG_OFFSET 0x6c 58#define ACP_I2S_COMP1_PLAY_REG_OFFSET 0x6c
59#define ACP_I2S_COMP2_PLAY_REG_OFFSET 0x68 59#define ACP_I2S_COMP2_PLAY_REG_OFFSET 0x68
60 60
61#define mmACP_PGFSM_RETAIN_REG 0x51c9 61#define mmACP_PGFSM_RETAIN_REG 0x51c9
62#define mmACP_PGFSM_CONFIG_REG 0x51ca 62#define mmACP_PGFSM_CONFIG_REG 0x51ca
63#define mmACP_PGFSM_READ_REG_0 0x51cc 63#define mmACP_PGFSM_READ_REG_0 0x51cc
64 64
65#define mmACP_MEM_SHUT_DOWN_REQ_LO 0x51f8 65#define mmACP_MEM_SHUT_DOWN_REQ_LO 0x51f8
66#define mmACP_MEM_SHUT_DOWN_REQ_HI 0x51f9 66#define mmACP_MEM_SHUT_DOWN_REQ_HI 0x51f9
67#define mmACP_MEM_SHUT_DOWN_STS_LO 0x51fa 67#define mmACP_MEM_SHUT_DOWN_STS_LO 0x51fa
68#define mmACP_MEM_SHUT_DOWN_STS_HI 0x51fb 68#define mmACP_MEM_SHUT_DOWN_STS_HI 0x51fb
69 69
70#define ACP_TIMEOUT_LOOP 0x000000FF 70#define mmACP_CONTROL 0x5131
71#define ACP_DEVS 3 71#define mmACP_STATUS 0x5133
72#define ACP_SRC_ID 162 72#define mmACP_SOFT_RESET 0x5134
73#define ACP_CONTROL__ClkEn_MASK 0x1
74#define ACP_SOFT_RESET__SoftResetAud_MASK 0x100
75#define ACP_SOFT_RESET__SoftResetAudDone_MASK 0x1000000
76#define ACP_CLOCK_EN_TIME_OUT_VALUE 0x000000FF
77#define ACP_SOFT_RESET_DONE_TIME_OUT_VALUE 0x000000FF
78
79#define ACP_TIMEOUT_LOOP 0x000000FF
80#define ACP_DEVS 3
81#define ACP_SRC_ID 162
73 82
74enum { 83enum {
75 ACP_TILE_P1 = 0, 84 ACP_TILE_P1 = 0,
@@ -260,6 +269,8 @@ static int acp_hw_init(void *handle)
260{ 269{
261 int r, i; 270 int r, i;
262 uint64_t acp_base; 271 uint64_t acp_base;
272 u32 val = 0;
273 u32 count = 0;
263 struct device *dev; 274 struct device *dev;
264 struct i2s_platform_data *i2s_pdata; 275 struct i2s_platform_data *i2s_pdata;
265 276
@@ -400,6 +411,46 @@ static int acp_hw_init(void *handle)
400 } 411 }
401 } 412 }
402 413
414 /* Assert Soft reset of ACP */
415 val = cgs_read_register(adev->acp.cgs_device, mmACP_SOFT_RESET);
416
417 val |= ACP_SOFT_RESET__SoftResetAud_MASK;
418 cgs_write_register(adev->acp.cgs_device, mmACP_SOFT_RESET, val);
419
420 count = ACP_SOFT_RESET_DONE_TIME_OUT_VALUE;
421 while (true) {
422 val = cgs_read_register(adev->acp.cgs_device, mmACP_SOFT_RESET);
423 if (ACP_SOFT_RESET__SoftResetAudDone_MASK ==
424 (val & ACP_SOFT_RESET__SoftResetAudDone_MASK))
425 break;
426 if (--count == 0) {
427 dev_err(&adev->pdev->dev, "Failed to reset ACP\n");
428 return -ETIMEDOUT;
429 }
430 udelay(100);
431 }
432 /* Enable clock to ACP and wait until the clock is enabled */
433 val = cgs_read_register(adev->acp.cgs_device, mmACP_CONTROL);
434 val = val | ACP_CONTROL__ClkEn_MASK;
435 cgs_write_register(adev->acp.cgs_device, mmACP_CONTROL, val);
436
437 count = ACP_CLOCK_EN_TIME_OUT_VALUE;
438
439 while (true) {
440 val = cgs_read_register(adev->acp.cgs_device, mmACP_STATUS);
441 if (val & (u32) 0x1)
442 break;
443 if (--count == 0) {
444 dev_err(&adev->pdev->dev, "Failed to reset ACP\n");
445 return -ETIMEDOUT;
446 }
447 udelay(100);
448 }
449 /* Deassert the SOFT RESET flags */
450 val = cgs_read_register(adev->acp.cgs_device, mmACP_SOFT_RESET);
451 val &= ~ACP_SOFT_RESET__SoftResetAud_MASK;
452 cgs_write_register(adev->acp.cgs_device, mmACP_SOFT_RESET, val);
453
403 return 0; 454 return 0;
404} 455}
405 456
@@ -412,6 +463,8 @@ static int acp_hw_init(void *handle)
412static int acp_hw_fini(void *handle) 463static int acp_hw_fini(void *handle)
413{ 464{
414 int i, ret; 465 int i, ret;
466 u32 val = 0;
467 u32 count = 0;
415 struct device *dev; 468 struct device *dev;
416 struct amdgpu_device *adev = (struct amdgpu_device *)handle; 469 struct amdgpu_device *adev = (struct amdgpu_device *)handle;
417 470
@@ -419,6 +472,42 @@ static int acp_hw_fini(void *handle)
419 if (!adev->acp.acp_cell) 472 if (!adev->acp.acp_cell)
420 return 0; 473 return 0;
421 474
475 /* Assert Soft reset of ACP */
476 val = cgs_read_register(adev->acp.cgs_device, mmACP_SOFT_RESET);
477
478 val |= ACP_SOFT_RESET__SoftResetAud_MASK;
479 cgs_write_register(adev->acp.cgs_device, mmACP_SOFT_RESET, val);
480
481 count = ACP_SOFT_RESET_DONE_TIME_OUT_VALUE;
482 while (true) {
483 val = cgs_read_register(adev->acp.cgs_device, mmACP_SOFT_RESET);
484 if (ACP_SOFT_RESET__SoftResetAudDone_MASK ==
485 (val & ACP_SOFT_RESET__SoftResetAudDone_MASK))
486 break;
487 if (--count == 0) {
488 dev_err(&adev->pdev->dev, "Failed to reset ACP\n");
489 return -ETIMEDOUT;
490 }
491 udelay(100);
492 }
493 /* Disable ACP clock */
494 val = cgs_read_register(adev->acp.cgs_device, mmACP_CONTROL);
495 val &= ~ACP_CONTROL__ClkEn_MASK;
496 cgs_write_register(adev->acp.cgs_device, mmACP_CONTROL, val);
497
498 count = ACP_CLOCK_EN_TIME_OUT_VALUE;
499
500 while (true) {
501 val = cgs_read_register(adev->acp.cgs_device, mmACP_STATUS);
502 if (val & (u32) 0x1)
503 break;
504 if (--count == 0) {
505 dev_err(&adev->pdev->dev, "Failed to reset ACP\n");
506 return -ETIMEDOUT;
507 }
508 udelay(100);
509 }
510
422 if (adev->acp.acp_genpd) { 511 if (adev->acp.acp_genpd) {
423 for (i = 0; i < ACP_DEVS ; i++) { 512 for (i = 0; i < ACP_DEVS ; i++) {
424 dev = get_mfd_cell_dev(adev->acp.acp_cell[i].name, i); 513 dev = get_mfd_cell_dev(adev->acp.acp_cell[i].name, i);