aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDave Airlie <airlied@redhat.com>2015-02-23 18:23:58 -0500
committerAlex Deucher <alexander.deucher@amd.com>2015-03-19 12:26:47 -0400
commit47f2467fffc4e1a070b141bc9d1319dc2c0acea5 (patch)
tree51d3b0c26ef8e3403db16ad05e452bbc5573c90e
parent2bc67b4d9e9f2c8d13782387bbdbb6e1b5e12d30 (diff)
radeon/si: add support for short HPD irqs
This adds support to process short HPD irqs on SI gpus. Signed-off-by: Dave Airlie <airlied@redhat.com> Signed-off-by: Alex Deucher <alexander.deucher@amd.com>
-rw-r--r--drivers/gpu/drm/radeon/si.c100
1 files changed, 88 insertions, 12 deletions
diff --git a/drivers/gpu/drm/radeon/si.c b/drivers/gpu/drm/radeon/si.c
index 0d2295fd2844..86e75798320f 100644
--- a/drivers/gpu/drm/radeon/si.c
+++ b/drivers/gpu/drm/radeon/si.c
@@ -6085,12 +6085,12 @@ int si_irq_set(struct radeon_device *rdev)
6085 (CNTX_BUSY_INT_ENABLE | CNTX_EMPTY_INT_ENABLE); 6085 (CNTX_BUSY_INT_ENABLE | CNTX_EMPTY_INT_ENABLE);
6086 6086
6087 if (!ASIC_IS_NODCE(rdev)) { 6087 if (!ASIC_IS_NODCE(rdev)) {
6088 hpd1 = RREG32(DC_HPD1_INT_CONTROL) & ~DC_HPDx_INT_EN; 6088 hpd1 = RREG32(DC_HPD1_INT_CONTROL) & ~(DC_HPDx_INT_EN | DC_HPDx_RX_INT_EN);
6089 hpd2 = RREG32(DC_HPD2_INT_CONTROL) & ~DC_HPDx_INT_EN; 6089 hpd2 = RREG32(DC_HPD2_INT_CONTROL) & ~(DC_HPDx_INT_EN | DC_HPDx_RX_INT_EN);
6090 hpd3 = RREG32(DC_HPD3_INT_CONTROL) & ~DC_HPDx_INT_EN; 6090 hpd3 = RREG32(DC_HPD3_INT_CONTROL) & ~(DC_HPDx_INT_EN | DC_HPDx_RX_INT_EN);
6091 hpd4 = RREG32(DC_HPD4_INT_CONTROL) & ~DC_HPDx_INT_EN; 6091 hpd4 = RREG32(DC_HPD4_INT_CONTROL) & ~(DC_HPDx_INT_EN | DC_HPDx_RX_INT_EN);
6092 hpd5 = RREG32(DC_HPD5_INT_CONTROL) & ~DC_HPDx_INT_EN; 6092 hpd5 = RREG32(DC_HPD5_INT_CONTROL) & ~(DC_HPDx_INT_EN | DC_HPDx_RX_INT_EN);
6093 hpd6 = RREG32(DC_HPD6_INT_CONTROL) & ~DC_HPDx_INT_EN; 6093 hpd6 = RREG32(DC_HPD6_INT_CONTROL) & ~(DC_HPDx_INT_EN | DC_HPDx_RX_INT_EN);
6094 } 6094 }
6095 6095
6096 dma_cntl = RREG32(DMA_CNTL + DMA0_REGISTER_OFFSET) & ~TRAP_ENABLE; 6096 dma_cntl = RREG32(DMA_CNTL + DMA0_REGISTER_OFFSET) & ~TRAP_ENABLE;
@@ -6153,27 +6153,27 @@ int si_irq_set(struct radeon_device *rdev)
6153 } 6153 }
6154 if (rdev->irq.hpd[0]) { 6154 if (rdev->irq.hpd[0]) {
6155 DRM_DEBUG("si_irq_set: hpd 1\n"); 6155 DRM_DEBUG("si_irq_set: hpd 1\n");
6156 hpd1 |= DC_HPDx_INT_EN; 6156 hpd1 |= DC_HPDx_INT_EN | DC_HPDx_RX_INT_EN;
6157 } 6157 }
6158 if (rdev->irq.hpd[1]) { 6158 if (rdev->irq.hpd[1]) {
6159 DRM_DEBUG("si_irq_set: hpd 2\n"); 6159 DRM_DEBUG("si_irq_set: hpd 2\n");
6160 hpd2 |= DC_HPDx_INT_EN; 6160 hpd2 |= DC_HPDx_INT_EN | DC_HPDx_RX_INT_EN;
6161 } 6161 }
6162 if (rdev->irq.hpd[2]) { 6162 if (rdev->irq.hpd[2]) {
6163 DRM_DEBUG("si_irq_set: hpd 3\n"); 6163 DRM_DEBUG("si_irq_set: hpd 3\n");
6164 hpd3 |= DC_HPDx_INT_EN; 6164 hpd3 |= DC_HPDx_INT_EN | DC_HPDx_RX_INT_EN;
6165 } 6165 }
6166 if (rdev->irq.hpd[3]) { 6166 if (rdev->irq.hpd[3]) {
6167 DRM_DEBUG("si_irq_set: hpd 4\n"); 6167 DRM_DEBUG("si_irq_set: hpd 4\n");
6168 hpd4 |= DC_HPDx_INT_EN; 6168 hpd4 |= DC_HPDx_INT_EN | DC_HPDx_RX_INT_EN;
6169 } 6169 }
6170 if (rdev->irq.hpd[4]) { 6170 if (rdev->irq.hpd[4]) {
6171 DRM_DEBUG("si_irq_set: hpd 5\n"); 6171 DRM_DEBUG("si_irq_set: hpd 5\n");
6172 hpd5 |= DC_HPDx_INT_EN; 6172 hpd5 |= DC_HPDx_INT_EN | DC_HPDx_RX_INT_EN;
6173 } 6173 }
6174 if (rdev->irq.hpd[5]) { 6174 if (rdev->irq.hpd[5]) {
6175 DRM_DEBUG("si_irq_set: hpd 6\n"); 6175 DRM_DEBUG("si_irq_set: hpd 6\n");
6176 hpd6 |= DC_HPDx_INT_EN; 6176 hpd6 |= DC_HPDx_INT_EN | DC_HPDx_RX_INT_EN;
6177 } 6177 }
6178 6178
6179 WREG32(CP_INT_CNTL_RING0, cp_int_cntl); 6179 WREG32(CP_INT_CNTL_RING0, cp_int_cntl);
@@ -6336,6 +6336,37 @@ static inline void si_irq_ack(struct radeon_device *rdev)
6336 tmp |= DC_HPDx_INT_ACK; 6336 tmp |= DC_HPDx_INT_ACK;
6337 WREG32(DC_HPD6_INT_CONTROL, tmp); 6337 WREG32(DC_HPD6_INT_CONTROL, tmp);
6338 } 6338 }
6339
6340 if (rdev->irq.stat_regs.evergreen.disp_int & DC_HPD1_RX_INTERRUPT) {
6341 tmp = RREG32(DC_HPD1_INT_CONTROL);
6342 tmp |= DC_HPDx_RX_INT_ACK;
6343 WREG32(DC_HPD1_INT_CONTROL, tmp);
6344 }
6345 if (rdev->irq.stat_regs.evergreen.disp_int_cont & DC_HPD2_RX_INTERRUPT) {
6346 tmp = RREG32(DC_HPD2_INT_CONTROL);
6347 tmp |= DC_HPDx_RX_INT_ACK;
6348 WREG32(DC_HPD2_INT_CONTROL, tmp);
6349 }
6350 if (rdev->irq.stat_regs.evergreen.disp_int_cont2 & DC_HPD3_RX_INTERRUPT) {
6351 tmp = RREG32(DC_HPD3_INT_CONTROL);
6352 tmp |= DC_HPDx_RX_INT_ACK;
6353 WREG32(DC_HPD3_INT_CONTROL, tmp);
6354 }
6355 if (rdev->irq.stat_regs.evergreen.disp_int_cont3 & DC_HPD4_RX_INTERRUPT) {
6356 tmp = RREG32(DC_HPD4_INT_CONTROL);
6357 tmp |= DC_HPDx_RX_INT_ACK;
6358 WREG32(DC_HPD4_INT_CONTROL, tmp);
6359 }
6360 if (rdev->irq.stat_regs.evergreen.disp_int_cont4 & DC_HPD5_RX_INTERRUPT) {
6361 tmp = RREG32(DC_HPD5_INT_CONTROL);
6362 tmp |= DC_HPDx_RX_INT_ACK;
6363 WREG32(DC_HPD5_INT_CONTROL, tmp);
6364 }
6365 if (rdev->irq.stat_regs.evergreen.disp_int_cont5 & DC_HPD6_RX_INTERRUPT) {
6366 tmp = RREG32(DC_HPD5_INT_CONTROL);
6367 tmp |= DC_HPDx_RX_INT_ACK;
6368 WREG32(DC_HPD6_INT_CONTROL, tmp);
6369 }
6339} 6370}
6340 6371
6341static void si_irq_disable(struct radeon_device *rdev) 6372static void si_irq_disable(struct radeon_device *rdev)
@@ -6401,6 +6432,7 @@ int si_irq_process(struct radeon_device *rdev)
6401 u32 src_id, src_data, ring_id; 6432 u32 src_id, src_data, ring_id;
6402 u32 ring_index; 6433 u32 ring_index;
6403 bool queue_hotplug = false; 6434 bool queue_hotplug = false;
6435 bool queue_dp = false;
6404 bool queue_thermal = false; 6436 bool queue_thermal = false;
6405 u32 status, addr; 6437 u32 status, addr;
6406 6438
@@ -6641,6 +6673,48 @@ restart_ih:
6641 DRM_DEBUG("IH: HPD6\n"); 6673 DRM_DEBUG("IH: HPD6\n");
6642 } 6674 }
6643 break; 6675 break;
6676 case 6:
6677 if (rdev->irq.stat_regs.evergreen.disp_int & DC_HPD1_RX_INTERRUPT) {
6678 rdev->irq.stat_regs.evergreen.disp_int &= ~DC_HPD1_RX_INTERRUPT;
6679 queue_dp = true;
6680 DRM_DEBUG("IH: HPD_RX 1\n");
6681 }
6682 break;
6683 case 7:
6684 if (rdev->irq.stat_regs.evergreen.disp_int_cont & DC_HPD2_RX_INTERRUPT) {
6685 rdev->irq.stat_regs.evergreen.disp_int_cont &= ~DC_HPD2_RX_INTERRUPT;
6686 queue_dp = true;
6687 DRM_DEBUG("IH: HPD_RX 2\n");
6688 }
6689 break;
6690 case 8:
6691 if (rdev->irq.stat_regs.evergreen.disp_int_cont2 & DC_HPD3_RX_INTERRUPT) {
6692 rdev->irq.stat_regs.evergreen.disp_int_cont2 &= ~DC_HPD3_RX_INTERRUPT;
6693 queue_dp = true;
6694 DRM_DEBUG("IH: HPD_RX 3\n");
6695 }
6696 break;
6697 case 9:
6698 if (rdev->irq.stat_regs.evergreen.disp_int_cont3 & DC_HPD4_RX_INTERRUPT) {
6699 rdev->irq.stat_regs.evergreen.disp_int_cont3 &= ~DC_HPD4_RX_INTERRUPT;
6700 queue_dp = true;
6701 DRM_DEBUG("IH: HPD_RX 4\n");
6702 }
6703 break;
6704 case 10:
6705 if (rdev->irq.stat_regs.evergreen.disp_int_cont4 & DC_HPD5_RX_INTERRUPT) {
6706 rdev->irq.stat_regs.evergreen.disp_int_cont4 &= ~DC_HPD5_RX_INTERRUPT;
6707 queue_dp = true;
6708 DRM_DEBUG("IH: HPD_RX 5\n");
6709 }
6710 break;
6711 case 11:
6712 if (rdev->irq.stat_regs.evergreen.disp_int_cont5 & DC_HPD6_RX_INTERRUPT) {
6713 rdev->irq.stat_regs.evergreen.disp_int_cont5 &= ~DC_HPD6_RX_INTERRUPT;
6714 queue_dp = true;
6715 DRM_DEBUG("IH: HPD_RX 6\n");
6716 }
6717 break;
6644 default: 6718 default:
6645 DRM_DEBUG("Unhandled interrupt: %d %d\n", src_id, src_data); 6719 DRM_DEBUG("Unhandled interrupt: %d %d\n", src_id, src_data);
6646 break; 6720 break;
@@ -6723,6 +6797,8 @@ restart_ih:
6723 rptr &= rdev->ih.ptr_mask; 6797 rptr &= rdev->ih.ptr_mask;
6724 WREG32(IH_RB_RPTR, rptr); 6798 WREG32(IH_RB_RPTR, rptr);
6725 } 6799 }
6800 if (queue_dp)
6801 schedule_work(&rdev->dp_work);
6726 if (queue_hotplug) 6802 if (queue_hotplug)
6727 schedule_work(&rdev->hotplug_work); 6803 schedule_work(&rdev->hotplug_work);
6728 if (queue_thermal && rdev->pm.dpm_enabled) 6804 if (queue_thermal && rdev->pm.dpm_enabled)