Pull drm fixes and cleanups from Dave Airlie: "The main thing are a bunch of fixes for the new amd display code, a bunch of smatch fixes. core: - Atomic helper regression fix. - Deferred fbdev fallout regression fix. amdgpu: - New display code (dc) dpms, suspend/resume and smatch fixes, along with some others - Some regression fixes for amdkfd/radeon. - Fix a ttm regression for swiotlb disabled bridge: - A bunch of fixes for the tc358767 bridge mali-dp + hdlcd: - some fixes and internal API catchups. imx-drm: -regression fix in atomic code. omapdrm: - platform detection regression fixes" * tag 'drm-fixes-for-v4.15-rc2' of git://people.freedesktop.org/~airlied/linux: (76 commits) drm/imx: always call wait_for_flip_done in commit_tail omapdrm: hdmi4_cec: signedness bug in hdmi4_cec_init() drm: omapdrm: Fix DPI on platforms using the DSI VDDS omapdrm: hdmi4: Correct the SoC revision matching drm/omap: displays: panel-dpi: add backlight dependency drm/omap: Fix error handling path in 'omap_dmm_probe()' drm/i915: Disable THP until we have a GPU read BW W/A drm/bridge: tc358767: fix 1-lane behavior drm/bridge: tc358767: fix AUXDATAn registers access drm/bridge: tc358767: fix timing calculations drm/bridge: tc358767: fix DP0_MISC register set drm/bridge: tc358767: filter out too high modes drm/bridge: tc358767: do no fail on hi-res displays drm/bridge: Fix lvds-encoder since the panel_bridge rework. drm/bridge: synopsys/dw-hdmi: Enable cec clock drm/bridge: adv7511/33: Fix adv7511_cec_init() failure handling drm/radeon: remove init of CIK VMIDs 8-16 for amdkfd drm/ttm: fix populate_and_map() functions once more drm/fb_helper: Disable all crtc's when initial setup fails. drm/atomic: make drm_atomic_helper_wait_for_vblanks more agressive ...
Unified · Split
| @@ -717,7 +717,7 @@ int amdgpu_queue_mgr_fini(struct amdgpu_device *adev, · 716 unmodified lines | ||
| 717 | 717 | struct amdgpu_queue_mgr *mgr); |
| 718 | 718 | int amdgpu_queue_mgr_map(struct amdgpu_device *adev, |
| 719 | 719 | struct amdgpu_queue_mgr *mgr, |
| 720 | − int hw_ip, int instance, int ring, | |
| 720 | + u32 hw_ip, u32 instance, u32 ring, | |
| 721 | 721 | struct amdgpu_ring **out_ring); |
| 722 | 722 | |
| 723 | 723 | /* |
| @@ -1572,18 +1572,14 @@ struct amdgpu_device { · 848 unmodified lines | ||
| 1572 | 1572 | /* sdma */ |
| 1573 | 1573 | struct amdgpu_sdma sdma; |
| 1574 | 1574 | |
| 1575 | − union { | |
| 1576 | − struct { | |
| 1577 | − /* uvd */ | |
| 1578 | − struct amdgpu_uvd uvd; | |
| 1575 | + /* uvd */ | |
| 1576 | + struct amdgpu_uvd uvd; | |
| 1579 | 1577 | |
| 1580 | − /* vce */ | |
| 1581 | − struct amdgpu_vce vce; | |
| 1582 | − }; | |
| 1578 | + /* vce */ | |
| 1579 | + struct amdgpu_vce vce; | |
| 1583 | 1580 | |
| 1584 | − /* vcn */ | |
| 1585 | − struct amdgpu_vcn vcn; | |
| 1586 | − }; | |
| 1581 | + /* vcn */ | |
| 1582 | + struct amdgpu_vcn vcn; | |
| 1587 | 1583 | |
| 1588 | 1584 | /* firmwares */ |
| 1589 | 1585 | struct amdgpu_firmware firmware; |
| @@ -379,29 +379,50 @@ static int kgd_hqd_sdma_load(struct kgd_dev *kgd, void *mqd) · 378 unmodified lines | ||
| 379 | 379 | { |
| 380 | 380 | struct amdgpu_device *adev = get_amdgpu_device(kgd); |
| 381 | 381 | struct cik_sdma_rlc_registers *m; |
| 382 | + unsigned long end_jiffies; | |
| 382 | 383 | uint32_t sdma_base_addr; |
| 384 | + uint32_t data; | |
| 383 | 385 | |
| 384 | 386 | m = get_sdma_mqd(mqd); |
| 385 | 387 | sdma_base_addr = get_sdma_base_addr(m); |
| 386 | 388 | |
| 387 | − WREG32(sdma_base_addr + mmSDMA0_RLC0_VIRTUAL_ADDR, | |
| 388 | − m->sdma_rlc_virtual_addr); | |
| 389 | + WREG32(sdma_base_addr + mmSDMA0_RLC0_RB_CNTL, | |
| 390 | + m->sdma_rlc_rb_cntl & (~SDMA0_RLC0_RB_CNTL__RB_ENABLE_MASK)); | |
| 389 | 391 | |
| 390 | − WREG32(sdma_base_addr + mmSDMA0_RLC0_RB_BASE, | |
| 391 | − m->sdma_rlc_rb_base); | |
| 392 | + end_jiffies = msecs_to_jiffies(2000) + jiffies; | |
| 393 | + while (true) { | |
| 394 | + data = RREG32(sdma_base_addr + mmSDMA0_RLC0_CONTEXT_STATUS); | |
| 395 | + if (data & SDMA0_RLC0_CONTEXT_STATUS__IDLE_MASK) | |
| 396 | + break; | |
| 397 | + if (time_after(jiffies, end_jiffies)) | |
| 398 | + return -ETIME; | |
| 399 | + usleep_range(500, 1000); | |
| 400 | + } | |
| 401 | + if (m->sdma_engine_id) { | |
| 402 | + data = RREG32(mmSDMA1_GFX_CONTEXT_CNTL); | |
| 403 | + data = REG_SET_FIELD(data, SDMA1_GFX_CONTEXT_CNTL, | |
| 404 | + RESUME_CTX, 0); | |
| 405 | + WREG32(mmSDMA1_GFX_CONTEXT_CNTL, data); | |
| 406 | + } else { | |
| 407 | + data = RREG32(mmSDMA0_GFX_CONTEXT_CNTL); | |
| 408 | + data = REG_SET_FIELD(data, SDMA0_GFX_CONTEXT_CNTL, | |
| 409 | + RESUME_CTX, 0); | |
| 410 | + WREG32(mmSDMA0_GFX_CONTEXT_CNTL, data); | |
| 411 | + } | |
| 392 | 412 | |
| 413 | + WREG32(sdma_base_addr + mmSDMA0_RLC0_DOORBELL, | |
| 414 | + m->sdma_rlc_doorbell); | |
| 415 | + WREG32(sdma_base_addr + mmSDMA0_RLC0_RB_RPTR, 0); | |
| 416 | + WREG32(sdma_base_addr + mmSDMA0_RLC0_RB_WPTR, 0); | |
| 417 | + WREG32(sdma_base_addr + mmSDMA0_RLC0_VIRTUAL_ADDR, | |
| 418 | + m->sdma_rlc_virtual_addr); | |
| 419 | + WREG32(sdma_base_addr + mmSDMA0_RLC0_RB_BASE, m->sdma_rlc_rb_base); | |
| 393 | 420 | WREG32(sdma_base_addr + mmSDMA0_RLC0_RB_BASE_HI, |
| 394 | 421 | m->sdma_rlc_rb_base_hi); |
| 395 | − | |
| 396 | 422 | WREG32(sdma_base_addr + mmSDMA0_RLC0_RB_RPTR_ADDR_LO, |
| 397 | 423 | m->sdma_rlc_rb_rptr_addr_lo); |
| 398 | − | |
| 399 | 424 | WREG32(sdma_base_addr + mmSDMA0_RLC0_RB_RPTR_ADDR_HI, |
| 400 | 425 | m->sdma_rlc_rb_rptr_addr_hi); |
| 401 | − | |
| 402 | − WREG32(sdma_base_addr + mmSDMA0_RLC0_DOORBELL, | |
| 403 | − m->sdma_rlc_doorbell); | |
| 404 | − | |
| 405 | 426 | WREG32(sdma_base_addr + mmSDMA0_RLC0_RB_CNTL, |
| 406 | 427 | m->sdma_rlc_rb_cntl); |
| 407 | 428 | |
| @@ -574,9 +595,9 @@ static int kgd_hqd_sdma_destroy(struct kgd_dev *kgd, void *mqd, · 166 unmodified lines | ||
| 574 | 595 | } |
| 575 | 596 | |
| 576 | 597 | WREG32(sdma_base_addr + mmSDMA0_RLC0_DOORBELL, 0); |
| 577 | − WREG32(sdma_base_addr + mmSDMA0_RLC0_RB_RPTR, 0); | |
| 578 | − WREG32(sdma_base_addr + mmSDMA0_RLC0_RB_WPTR, 0); | |
| 579 | − WREG32(sdma_base_addr + mmSDMA0_RLC0_RB_BASE, 0); | |
| 598 | + WREG32(sdma_base_addr + mmSDMA0_RLC0_RB_CNTL, | |
| 599 | + RREG32(sdma_base_addr + mmSDMA0_RLC0_RB_CNTL) | | |
| 600 | + SDMA0_RLC0_RB_CNTL__RB_ENABLE_MASK); | |
| 580 | 601 | |
| 581 | 602 | return 0; |
| 582 | 603 | } |
| @@ -409,6 +409,10 @@ static bool amdgpu_cs_try_evict(struct amdgpu_cs_parser *p, · 408 unmodified lines | ||
| 409 | 409 | if (candidate->robj == validated) |
| 410 | 410 | break; |
| 411 | 411 | |
| 412 | + /* We can't move pinned BOs here */ | |
| 413 | + if (bo->pin_count) | |
| 414 | + continue; | |
| 415 | + | |
| 412 | 416 | other = amdgpu_mem_type_to_domain(bo->tbo.mem.mem_type); |
| 413 | 417 | |
| 414 | 418 | /* Check if this BO is in one of the domains we need space for */ |
| @@ -1837,9 +1837,6 @@ static int amdgpu_fini(struct amdgpu_device *adev) · 1836 unmodified lines | ||
| 1837 | 1837 | adev->ip_blocks[i].status.hw = false; |
| 1838 | 1838 | } |
| 1839 | 1839 | |
| 1840 | − if (adev->firmware.load_type == AMDGPU_FW_LOAD_SMU) | |
| 1841 | − amdgpu_ucode_fini_bo(adev); | |
| 1842 | − | |
| 1843 | 1840 | for (i = adev->num_ip_blocks - 1; i >= 0; i--) { |
| 1844 | 1841 | if (!adev->ip_blocks[i].status.sw) |
| 1845 | 1842 | continue; |
| @@ -536,7 +536,7 @@ static const struct pci_device_id pciidlist[] = { · 535 unmodified lines | ||
| 536 | 536 | {0x1002, 0x686c, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_VEGA10}, |
| 537 | 537 | {0x1002, 0x687f, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_VEGA10}, |
| 538 | 538 | /* Raven */ |
| 539 | − {0x1002, 0x15dd, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_RAVEN|AMD_IS_APU|AMD_EXP_HW_SUPPORT}, | |
| 539 | + {0x1002, 0x15dd, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_RAVEN|AMD_IS_APU}, | |
| 540 | 540 | |
| 541 | 541 | {0, 0, 0} |
| 542 | 542 | }; |
| @@ -164,6 +164,9 @@ static int amdgpu_pp_hw_fini(void *handle) · 163 unmodified lines | ||
| 164 | 164 | ret = adev->powerplay.ip_funcs->hw_fini( |
| 165 | 165 | adev->powerplay.pp_handle); |
| 166 | 166 | |
| 167 | + if (adev->firmware.load_type == AMDGPU_FW_LOAD_SMU) | |
| 168 | + amdgpu_ucode_fini_bo(adev); | |
| 169 | + | |
| 167 | 170 | return ret; |
| 168 | 171 | } |
| 169 | 172 | |
| @@ -442,6 +442,8 @@ static int psp_hw_fini(void *handle) · 441 unmodified lines | ||
| 442 | 442 | if (adev->firmware.load_type != AMDGPU_FW_LOAD_PSP) |
| 443 | 443 | return 0; |
| 444 | 444 | |
| 445 | + amdgpu_ucode_fini_bo(adev); | |
| 446 | + | |
| 445 | 447 | psp_ring_destroy(psp, PSP_RING_TYPE__KM); |
| 446 | 448 | |
| 447 | 449 | amdgpu_bo_free_kernel(&psp->tmr_bo, &psp->tmr_mc_addr, &psp->tmr_buf); |
| @@ -63,7 +63,7 @@ static int amdgpu_update_cached_map(struct amdgpu_queue_mapper *mapper, · 62 unmodified lines | ||
| 63 | 63 | |
| 64 | 64 | static int amdgpu_identity_map(struct amdgpu_device *adev, |
| 65 | 65 | struct amdgpu_queue_mapper *mapper, |
| 66 | − int ring, | |
| 66 | + u32 ring, | |
| 67 | 67 | struct amdgpu_ring **out_ring) |
| 68 | 68 | { |
| 69 | 69 | switch (mapper->hw_ip) { |
| @@ -121,7 +121,7 @@ static enum amdgpu_ring_type amdgpu_hw_ip_to_ring_type(int hw_ip) · 51 unmodified lines | ||
| 121 | 121 | |
| 122 | 122 | static int amdgpu_lru_map(struct amdgpu_device *adev, |
| 123 | 123 | struct amdgpu_queue_mapper *mapper, |
| 124 | − int user_ring, bool lru_pipe_order, | |
| 124 | + u32 user_ring, bool lru_pipe_order, | |
| 125 | 125 | struct amdgpu_ring **out_ring) |
| 126 | 126 | { |
| 127 | 127 | int r, i, j; |
| @@ -208,7 +208,7 @@ int amdgpu_queue_mgr_fini(struct amdgpu_device *adev, · 80 unmodified lines | ||
| 208 | 208 | */ |
| 209 | 209 | int amdgpu_queue_mgr_map(struct amdgpu_device *adev, |
| 210 | 210 | struct amdgpu_queue_mgr *mgr, |
| 211 | − int hw_ip, int instance, int ring, | |
| 211 | + u32 hw_ip, u32 instance, u32 ring, | |
| 212 | 212 | struct amdgpu_ring **out_ring) |
| 213 | 213 | { |
| 214 | 214 | int r, ip_num_rings; |
| @@ -1023,22 +1023,101 @@ static const struct amdgpu_allowed_register_entry cik_allowed_read_registers[] = · 1022 unmodified lines | ||
| 1023 | 1023 | {mmPA_SC_RASTER_CONFIG_1, true}, |
| 1024 | 1024 | }; |
| 1025 | 1025 | |
| 1026 | −static uint32_t cik_read_indexed_register(struct amdgpu_device *adev, | |
| 1027 | − u32 se_num, u32 sh_num, | |
| 1028 | − u32 reg_offset) | |
| 1026 | + | |
| 1027 | +static uint32_t cik_get_register_value(struct amdgpu_device *adev, | |
| 1028 | + bool indexed, u32 se_num, | |
| 1029 | + u32 sh_num, u32 reg_offset) | |
| 1029 | 1030 | { |
| 1030 | − uint32_t val; | |
| 1031 | + if (indexed) { | |
| 1032 | + uint32_t val; | |
| 1033 | + unsigned se_idx = (se_num == 0xffffffff) ? 0 : se_num; | |
| 1034 | + unsigned sh_idx = (sh_num == 0xffffffff) ? 0 : sh_num; | |
| 1035 | + | |
| 1036 | + switch (reg_offset) { | |
| 1037 | + case mmCC_RB_BACKEND_DISABLE: | |
| 1038 | + return adev->gfx.config.rb_config[se_idx][sh_idx].rb_backend_disable; | |
| 1039 | + case mmGC_USER_RB_BACKEND_DISABLE: | |
| 1040 | + return adev->gfx.config.rb_config[se_idx][sh_idx].user_rb_backend_disable; | |
| 1041 | + case mmPA_SC_RASTER_CONFIG: | |
| 1042 | + return adev->gfx.config.rb_config[se_idx][sh_idx].raster_config; | |
| 1043 | + case mmPA_SC_RASTER_CONFIG_1: | |
| 1044 | + return adev->gfx.config.rb_config[se_idx][sh_idx].raster_config_1; | |
| 1045 | + } | |
| 1031 | 1046 | |
| 1032 | − mutex_lock(&adev->grbm_idx_mutex); | |
| 1033 | − if (se_num != 0xffffffff || sh_num != 0xffffffff) | |
| 1034 | − amdgpu_gfx_select_se_sh(adev, se_num, sh_num, 0xffffffff); | |
| 1047 | + mutex_lock(&adev->grbm_idx_mutex); | |
| 1048 | + if (se_num != 0xffffffff || sh_num != 0xffffffff) | |
| 1049 | + amdgpu_gfx_select_se_sh(adev, se_num, sh_num, 0xffffffff); | |
| 1035 | 1050 | |
| 1036 | − val = RREG32(reg_offset); | |
| 1051 | + val = RREG32(reg_offset); | |
| 1037 | 1052 | |
| 1038 | − if (se_num != 0xffffffff || sh_num != 0xffffffff) | |
| 1039 | − amdgpu_gfx_select_se_sh(adev, 0xffffffff, 0xffffffff, 0xffffffff); | |
| 1040 | − mutex_unlock(&adev->grbm_idx_mutex); | |
| 1041 | − return val; | |
| 1053 | + if (se_num != 0xffffffff || sh_num != 0xffffffff) | |
| 1054 | + amdgpu_gfx_select_se_sh(adev, 0xffffffff, 0xffffffff, 0xffffffff); | |
| 1055 | + mutex_unlock(&adev->grbm_idx_mutex); | |
| 1056 | + return val; | |
| 1057 | + } else { | |
| 1058 | + unsigned idx; | |
| 1059 | + | |
| 1060 | + switch (reg_offset) { | |
| 1061 | + case mmGB_ADDR_CONFIG: | |
| 1062 | + return adev->gfx.config.gb_addr_config; | |
| 1063 | + case mmMC_ARB_RAMCFG: | |
| 1064 | + return adev->gfx.config.mc_arb_ramcfg; | |
| 1065 | + case mmGB_TILE_MODE0: | |
| 1066 | + case mmGB_TILE_MODE1: | |
| 1067 | + case mmGB_TILE_MODE2: | |
| 1068 | + case mmGB_TILE_MODE3: | |
| 1069 | + case mmGB_TILE_MODE4: | |
| 1070 | + case mmGB_TILE_MODE5: | |
| 1071 | + case mmGB_TILE_MODE6: | |
| 1072 | + case mmGB_TILE_MODE7: | |
| 1073 | + case mmGB_TILE_MODE8: | |
| 1074 | + case mmGB_TILE_MODE9: | |
| 1075 | + case mmGB_TILE_MODE10: | |
| 1076 | + case mmGB_TILE_MODE11: | |
| 1077 | + case mmGB_TILE_MODE12: | |
| 1078 | + case mmGB_TILE_MODE13: | |
| 1079 | + case mmGB_TILE_MODE14: | |
| 1080 | + case mmGB_TILE_MODE15: | |
| 1081 | + case mmGB_TILE_MODE16: | |
| 1082 | + case mmGB_TILE_MODE17: | |
| 1083 | + case mmGB_TILE_MODE18: | |
| 1084 | + case mmGB_TILE_MODE19: | |
| 1085 | + case mmGB_TILE_MODE20: | |
| 1086 | + case mmGB_TILE_MODE21: | |
| 1087 | + case mmGB_TILE_MODE22: | |
| 1088 | + case mmGB_TILE_MODE23: | |
| 1089 | + case mmGB_TILE_MODE24: | |
| 1090 | + case mmGB_TILE_MODE25: | |
| 1091 | + case mmGB_TILE_MODE26: | |
| 1092 | + case mmGB_TILE_MODE27: | |
| 1093 | + case mmGB_TILE_MODE28: | |
| 1094 | + case mmGB_TILE_MODE29: | |
| 1095 | + case mmGB_TILE_MODE30: | |
| 1096 | + case mmGB_TILE_MODE31: | |
| 1097 | + idx = (reg_offset - mmGB_TILE_MODE0); | |
| 1098 | + return adev->gfx.config.tile_mode_array[idx]; | |
| 1099 | + case mmGB_MACROTILE_MODE0: | |
| 1100 | + case mmGB_MACROTILE_MODE1: | |
| 1101 | + case mmGB_MACROTILE_MODE2: | |
| 1102 | + case mmGB_MACROTILE_MODE3: | |
| 1103 | + case mmGB_MACROTILE_MODE4: | |
| 1104 | + case mmGB_MACROTILE_MODE5: | |
| 1105 | + case mmGB_MACROTILE_MODE6: | |
| 1106 | + case mmGB_MACROTILE_MODE7: | |
| 1107 | + case mmGB_MACROTILE_MODE8: | |
| 1108 | + case mmGB_MACROTILE_MODE9: | |
| 1109 | + case mmGB_MACROTILE_MODE10: | |
| 1110 | + case mmGB_MACROTILE_MODE11: | |
| 1111 | + case mmGB_MACROTILE_MODE12: | |
| 1112 | + case mmGB_MACROTILE_MODE13: | |
| 1113 | + case mmGB_MACROTILE_MODE14: | |
| 1114 | + case mmGB_MACROTILE_MODE15: | |
| 1115 | + idx = (reg_offset - mmGB_MACROTILE_MODE0); | |
| 1116 | + return adev->gfx.config.macrotile_mode_array[idx]; | |
| 1117 | + default: | |
| 1118 | + return RREG32(reg_offset); | |
| 1119 | + } | |
| 1120 | + } | |
| 1042 | 1121 | } |
| 1043 | 1122 | |
| 1044 | 1123 | static int cik_read_register(struct amdgpu_device *adev, u32 se_num, |
| @@ -1048,13 +1127,13 @@ static int cik_read_register(struct amdgpu_device *adev, u32 se_num, · 3 unmodified lines | ||
| 1048 | 1127 | |
| 1049 | 1128 | *value = 0; |
| 1050 | 1129 | for (i = 0; i < ARRAY_SIZE(cik_allowed_read_registers); i++) { |
| 1130 | + bool indexed = cik_allowed_read_registers[i].grbm_indexed; | |
| 1131 | + | |
| 1051 | 1132 | if (reg_offset != cik_allowed_read_registers[i].reg_offset) |
| 1052 | 1133 | continue; |
| 1053 | 1134 | |
| 1054 | − *value = cik_allowed_read_registers[i].grbm_indexed ? | |
| 1055 | − cik_read_indexed_register(adev, se_num, | |
| 1056 | − sh_num, reg_offset) : | |
| 1057 | − RREG32(reg_offset); | |
| 1135 | + *value = cik_get_register_value(adev, indexed, se_num, sh_num, | |
| 1136 | + reg_offset); | |
| 1058 | 1137 | return 0; |
| 1059 | 1138 | } |
| 1060 | 1139 | return -EINVAL; |
| @@ -1819,6 +1819,22 @@ static void gfx_v7_0_setup_rb(struct amdgpu_device *adev) · 1818 unmodified lines | ||
| 1819 | 1819 | adev->gfx.config.backend_enable_mask, |
| 1820 | 1820 | num_rb_pipes); |
| 1821 | 1821 | } |
| 1822 | + | |
| 1823 | + /* cache the values for userspace */ | |
| 1824 | + for (i = 0; i < adev->gfx.config.max_shader_engines; i++) { | |
| 1825 | + for (j = 0; j < adev->gfx.config.max_sh_per_se; j++) { | |
| 1826 | + gfx_v7_0_select_se_sh(adev, i, j, 0xffffffff); | |
| 1827 | + adev->gfx.config.rb_config[i][j].rb_backend_disable = | |
| 1828 | + RREG32(mmCC_RB_BACKEND_DISABLE); | |
| 1829 | + adev->gfx.config.rb_config[i][j].user_rb_backend_disable = | |
| 1830 | + RREG32(mmGC_USER_RB_BACKEND_DISABLE); | |
| 1831 | + adev->gfx.config.rb_config[i][j].raster_config = | |
| 1832 | + RREG32(mmPA_SC_RASTER_CONFIG); | |
| 1833 | + adev->gfx.config.rb_config[i][j].raster_config_1 = | |
| 1834 | + RREG32(mmPA_SC_RASTER_CONFIG_1); | |
| 1835 | + } | |
| 1836 | + } | |
| 1837 | + gfx_v7_0_select_se_sh(adev, 0xffffffff, 0xffffffff, 0xffffffff); | |
| 1822 | 1838 | mutex_unlock(&adev->grbm_idx_mutex); |
| 1823 | 1839 | } |
| 1824 | 1840 | |
| @@ -1175,7 +1175,7 @@ static const struct amdgpu_irq_src_funcs vcn_v1_0_irq_funcs = { · 1174 unmodified lines | ||
| 1175 | 1175 | |
| 1176 | 1176 | static void vcn_v1_0_set_irq_funcs(struct amdgpu_device *adev) |
| 1177 | 1177 | { |
| 1178 | − adev->uvd.irq.num_types = adev->vcn.num_enc_rings + 1; | |
| 1178 | + adev->vcn.irq.num_types = adev->vcn.num_enc_rings + 1; | |
| 1179 | 1179 | adev->vcn.irq.funcs = &vcn_v1_0_irq_funcs; |
| 1180 | 1180 | } |
| 1181 | 1181 | |
| @@ -24,6 +24,7 @@ · 23 unmodified lines | ||
| 24 | 24 | #include <linux/sched.h> |
| 25 | 25 | #include <linux/moduleparam.h> |
| 26 | 26 | #include <linux/device.h> |
| 27 | +#include <linux/printk.h> | |
| 27 | 28 | #include "kfd_priv.h" |
| 28 | 29 | |
| 29 | 30 | #define KFD_DRIVER_AUTHOR "AMD Inc. and others" |
| @@ -132,7 +133,7 @@ static void __exit kfd_module_exit(void) · 102 unmodified lines | ||
| 132 | 133 | kfd_process_destroy_wq(); |
| 133 | 134 | kfd_topology_shutdown(); |
| 134 | 135 | kfd_chardev_exit(); |
| 135 | − dev_info(kfd_device, "Removed module\n"); | |
| 136 | + pr_info("amdkfd: Removed module\n"); | |
| 136 | 137 | } |
| 137 | 138 | |
| 138 | 139 | module_init(kfd_module_init); |
| @@ -202,8 +202,8 @@ static int update_mqd_sdma(struct mqd_manager *mm, void *mqd, · 201 unmodified lines | ||
| 202 | 202 | struct cik_sdma_rlc_registers *m; |
| 203 | 203 | |
| 204 | 204 | m = get_sdma_mqd(mqd); |
| 205 | − m->sdma_rlc_rb_cntl = ffs(q->queue_size / sizeof(unsigned int)) << | |
| 206 | − SDMA0_RLC0_RB_CNTL__RB_SIZE__SHIFT | | |
| 205 | + m->sdma_rlc_rb_cntl = (ffs(q->queue_size / sizeof(unsigned int)) - 1) | |
| 206 | + << SDMA0_RLC0_RB_CNTL__RB_SIZE__SHIFT | | |
| 207 | 207 | q->vmid << SDMA0_RLC0_RB_CNTL__RB_VMID__SHIFT | |
| 208 | 208 | 1 << SDMA0_RLC0_RB_CNTL__RPTR_WRITEBACK_ENABLE__SHIFT | |
| 209 | 209 | 6 << SDMA0_RLC0_RB_CNTL__RPTR_WRITEBACK_TIMER__SHIFT; |
| @@ -191,6 +191,24 @@ int pqm_create_queue(struct process_queue_manager *pqm, · 190 unmodified lines | ||
| 191 | 191 | |
| 192 | 192 | switch (type) { |
| 193 | 193 | case KFD_QUEUE_TYPE_SDMA: |
| 194 | + if (dev->dqm->queue_count >= | |
| 195 | + CIK_SDMA_QUEUES_PER_ENGINE * CIK_SDMA_ENGINE_NUM) { | |
| 196 | + pr_err("Over-subscription is not allowed for SDMA.\n"); | |
| 197 | + retval = -EPERM; | |
| 198 | + goto err_create_queue; | |
| 199 | + } | |
| 200 | + | |
| 201 | + retval = create_cp_queue(pqm, dev, &q, properties, f, *qid); | |
| 202 | + if (retval != 0) | |
| 203 | + goto err_create_queue; | |
| 204 | + pqn->q = q; | |
| 205 | + pqn->kq = NULL; | |
| 206 | + retval = dev->dqm->ops.create_queue(dev->dqm, q, &pdd->qpd, | |
| 207 | + &q->properties.vmid); | |
| 208 | + pr_debug("DQM returned %d for create_queue\n", retval); | |
| 209 | + print_queue(q); | |
| 210 | + break; | |
| 211 | + | |
| 194 | 212 | case KFD_QUEUE_TYPE_COMPUTE: |
| 195 | 213 | /* check if there is over subscription */ |
| 196 | 214 | if ((sched_policy == KFD_SCHED_POLICY_HWS_NO_OVERSUBSCRIPTION) && |
| @@ -520,7 +520,8 @@ static int detect_mst_link_for_all_connectors(struct drm_device *dev) · 519 unmodified lines | ||
| 520 | 520 | |
| 521 | 521 | list_for_each_entry(connector, &dev->mode_config.connector_list, head) { |
| 522 | 522 | aconnector = to_amdgpu_dm_connector(connector); |
| 523 | − if (aconnector->dc_link->type == dc_connection_mst_branch) { | |
| 523 | + if (aconnector->dc_link->type == dc_connection_mst_branch && | |
| 524 | + aconnector->mst_mgr.aux) { | |
| 524 | 525 | DRM_DEBUG_DRIVER("DM_MST: starting TM on aconnector: %p [id: %d]\n", |
| 525 | 526 | aconnector, aconnector->base.base.id); |
| 526 | 527 | |
| @@ -677,6 +678,10 @@ int amdgpu_dm_display_resume(struct amdgpu_device *adev) · 150 unmodified lines | ||
| 677 | 678 | |
| 678 | 679 | mutex_lock(&aconnector->hpd_lock); |
| 679 | 680 | dc_link_detect(aconnector->dc_link, DETECT_REASON_HPD); |
| 681 | + | |
| 682 | + if (aconnector->fake_enable && aconnector->dc_link->local_sink) | |
| 683 | + aconnector->fake_enable = false; | |
| 684 | + | |
| 680 | 685 | aconnector->dc_sink = NULL; |
| 681 | 686 | amdgpu_dm_update_connector_after_detect(aconnector); |
| 682 | 687 | mutex_unlock(&aconnector->hpd_lock); |
| @@ -711,7 +716,6 @@ int amdgpu_dm_display_resume(struct amdgpu_device *adev) · 28 unmodified lines | ||
| 711 | 716 | |
| 712 | 717 | ret = drm_atomic_helper_resume(ddev, adev->dm.cached_state); |
| 713 | 718 | |
| 714 | − drm_atomic_state_put(adev->dm.cached_state); | |
| 715 | 719 | adev->dm.cached_state = NULL; |
| 716 | 720 | |
| 717 | 721 | amdgpu_dm_irq_resume_late(adev); |
| @@ -2704,7 +2708,7 @@ static void create_eml_sink(struct amdgpu_dm_connector *aconnector) · 1986 unmodified lines | ||
| 2704 | 2708 | .link = aconnector->dc_link, |
| 2705 | 2709 | .sink_signal = SIGNAL_TYPE_VIRTUAL |
| 2706 | 2710 | }; |
| 2707 | − struct edid *edid = (struct edid *) aconnector->base.edid_blob_ptr->data; | |
| 2711 | + struct edid *edid; | |
| 2708 | 2712 | |
| 2709 | 2713 | if (!aconnector->base.edid_blob_ptr || |
| 2710 | 2714 | !aconnector->base.edid_blob_ptr->data) { |
| @@ -2716,6 +2720,8 @@ static void create_eml_sink(struct amdgpu_dm_connector *aconnector) · 5 unmodified lines | ||
| 2716 | 2720 | return; |
| 2717 | 2721 | } |
| 2718 | 2722 | |
| 2723 | + edid = (struct edid *) aconnector->base.edid_blob_ptr->data; | |
| 2724 | + | |
| 2719 | 2725 | aconnector->edid = edid; |
| 2720 | 2726 | |
| 2721 | 2727 | aconnector->dc_em_sink = dc_link_add_remote_sink( |
| @@ -4193,13 +4199,13 @@ static void amdgpu_dm_atomic_commit_tail(struct drm_atomic_state *state) · 1471 unmodified lines | ||
| 4193 | 4199 | update_stream_scaling_settings(&dm_new_con_state->base.crtc->mode, |
| 4194 | 4200 | dm_new_con_state, (struct dc_stream_state *)dm_new_crtc_state->stream); |
| 4195 | 4201 | |
| 4202 | + if (!dm_new_crtc_state->stream) | |
| 4203 | + continue; | |
| 4204 | + | |
| 4196 | 4205 | status = dc_stream_get_status(dm_new_crtc_state->stream); |
| 4197 | 4206 | WARN_ON(!status); |
| 4198 | 4207 | WARN_ON(!status->plane_count); |
| 4199 | 4208 | |
| 4200 | − if (!dm_new_crtc_state->stream) | |
| 4201 | − continue; | |
| 4202 | − | |
| 4203 | 4209 | /*TODO How it works with MPO ?*/ |
| 4204 | 4210 | if (!dc_commit_planes_to_stream( |
| 4205 | 4211 | dm->dc, |
| @@ -4253,7 +4259,7 @@ static void amdgpu_dm_atomic_commit_tail(struct drm_atomic_state *state) · 47 unmodified lines | ||
| 4253 | 4259 | drm_atomic_helper_commit_hw_done(state); |
| 4254 | 4260 | |
| 4255 | 4261 | if (wait_for_vblank) |
| 4256 | − drm_atomic_helper_wait_for_vblanks(dev, state); | |
| 4262 | + drm_atomic_helper_wait_for_flip_done(dev, state); | |
| 4257 | 4263 | |
| 4258 | 4264 | drm_atomic_helper_cleanup_planes(dev, state); |
| 4259 | 4265 | } |
| @@ -4332,9 +4338,11 @@ void dm_restore_drm_connector_state(struct drm_device *dev, · 72 unmodified lines | ||
| 4332 | 4338 | return; |
| 4333 | 4339 | |
| 4334 | 4340 | disconnected_acrtc = to_amdgpu_crtc(connector->encoder->crtc); |
| 4335 | − acrtc_state = to_dm_crtc_state(disconnected_acrtc->base.state); | |
| 4341 | + if (!disconnected_acrtc) | |
| 4342 | + return; | |
| 4336 | 4343 | |
| 4337 | − if (!disconnected_acrtc || !acrtc_state->stream) | |
| 4344 | + acrtc_state = to_dm_crtc_state(disconnected_acrtc->base.state); | |
| 4345 | + if (!acrtc_state->stream) | |
| 4338 | 4346 | return; |
| 4339 | 4347 | |
| 4340 | 4348 | /* |
| @@ -4455,7 +4463,7 @@ static int dm_update_crtcs_state(struct dc *dc, · 114 unmodified lines | ||
| 4455 | 4463 | } |
| 4456 | 4464 | } |
| 4457 | 4465 | |
| 4458 | − if (dc_is_stream_unchanged(new_stream, dm_old_crtc_state->stream) && | |
| 4466 | + if (enable && dc_is_stream_unchanged(new_stream, dm_old_crtc_state->stream) && | |
| 4459 | 4467 | dc_is_stream_scaling_unchanged(new_stream, dm_old_crtc_state->stream)) { |
| 4460 | 4468 | |
| 4461 | 4469 | new_crtc_state->mode_changed = false; |
| @@ -4709,7 +4717,8 @@ static int amdgpu_dm_atomic_check(struct drm_device *dev, · 247 unmodified lines | ||
| 4709 | 4717 | } |
| 4710 | 4718 | } else { |
| 4711 | 4719 | for_each_oldnew_crtc_in_state(state, crtc, old_crtc_state, new_crtc_state, i) { |
| 4712 | − if (!drm_atomic_crtc_needs_modeset(new_crtc_state)) | |
| 4720 | + if (!drm_atomic_crtc_needs_modeset(new_crtc_state) && | |
| 4721 | + !new_crtc_state->color_mgmt_changed) | |
| 4713 | 4722 | continue; |
| 4714 | 4723 | |
| 4715 | 4724 | if (!new_crtc_state->enable) |
| @@ -75,6 +75,9 @@ void dc_conn_log(struct dc_context *ctx, · 74 unmodified lines | ||
| 75 | 75 | if (signal == signal_type_info_tbl[i].type) |
| 76 | 76 | break; |
| 77 | 77 | |
| 78 | + if (i == NUM_ELEMENTS(signal_type_info_tbl)) | |
| 79 | + goto fail; | |
| 80 | + | |
| 78 | 81 | dm_logger_append(&entry, "[%s][ConnIdx:%d] ", |
| 79 | 82 | signal_type_info_tbl[i].name, |
| 80 | 83 | link->link_index); |
| @@ -96,6 +99,8 @@ void dc_conn_log(struct dc_context *ctx, · 15 unmodified lines | ||
| 96 | 99 | |
| 97 | 100 | dm_logger_append(&entry, "^\n"); |
| 98 | 101 | dm_helpers_dc_conn_log(ctx, &entry, event); |
| 102 | + | |
| 103 | +fail: | |
| 99 | 104 | dm_logger_close(&entry); |
| 100 | 105 | |
| 101 | 106 | va_end(args); |
| @@ -249,7 +249,7 @@ static enum bp_result bios_parser_get_dst_obj(struct dc_bios *dcb, · 248 unmodified lines | ||
| 249 | 249 | struct graphics_object_id *dest_object_id) |
| 250 | 250 | { |
| 251 | 251 | uint32_t number; |
| 252 | − uint16_t *id; | |
| 252 | + uint16_t *id = NULL; | |
| 253 | 253 | ATOM_OBJECT *object; |
| 254 | 254 | struct bios_parser *bp = BP_FROM_DCB(dcb); |
| 255 | 255 | |
| @@ -260,7 +260,7 @@ static enum bp_result bios_parser_get_dst_obj(struct dc_bios *dcb, · 4 unmodified lines | ||
| 260 | 260 | |
| 261 | 261 | number = get_dest_obj_list(bp, object, &id); |
| 262 | 262 | |
| 263 | − if (number <= index) | |
| 263 | + if (number <= index || !id) | |
| 264 | 264 | return BP_RESULT_BADINPUT; |
| 265 | 265 | |
| 266 | 266 | *dest_object_id = object_id_from_bios_object_id(id[index]); |
| @@ -121,6 +121,10 @@ static bool create_links( · 120 unmodified lines | ||
| 121 | 121 | goto failed_alloc; |
| 122 | 122 | } |
| 123 | 123 | |
| 124 | + link->link_index = dc->link_count; | |
| 125 | + dc->links[dc->link_count] = link; | |
| 126 | + dc->link_count++; | |
| 127 | + | |
| 124 | 128 | link->ctx = dc->ctx; |
| 125 | 129 | link->dc = dc; |
| 126 | 130 | link->connector_signal = SIGNAL_TYPE_VIRTUAL; |
| @@ -129,6 +133,13 @@ static bool create_links( · 2 unmodified lines | ||
| 129 | 133 | link->link_id.enum_id = ENUM_ID_1; |
| 130 | 134 | link->link_enc = kzalloc(sizeof(*link->link_enc), GFP_KERNEL); |
| 131 | 135 | |
| 136 | + if (!link->link_enc) { | |
| 137 | + BREAK_TO_DEBUGGER(); | |
| 138 | + goto failed_alloc; | |
| 139 | + } | |
| 140 | + | |
| 141 | + link->link_status.dpcd_caps = &link->dpcd_caps; | |
| 142 | + | |
| 132 | 143 | enc_init.ctx = dc->ctx; |
| 133 | 144 | enc_init.channel = CHANNEL_ID_UNKNOWN; |
| 134 | 145 | enc_init.hpd_source = HPD_SOURCEID_UNKNOWN; |
| @@ -138,10 +149,6 @@ static bool create_links( · 3 unmodified lines | ||
| 138 | 149 | enc_init.encoder.id = ENCODER_ID_INTERNAL_VIRTUAL; |
| 139 | 150 | enc_init.encoder.enum_id = ENUM_ID_1; |
| 140 | 151 | virtual_link_encoder_construct(link->link_enc, &enc_init); |
| 141 | − | |
| 142 | − link->link_index = dc->link_count; | |
| 143 | − dc->links[dc->link_count] = link; | |
| 144 | − dc->link_count++; | |
| 145 | 152 | } |
| 146 | 153 | |
| 147 | 154 | return true; |
| @@ -480,22 +480,6 @@ static void detect_dp( · 479 unmodified lines | ||
| 480 | 480 | sink_caps->signal = SIGNAL_TYPE_DISPLAY_PORT; |
| 481 | 481 | detect_dp_sink_caps(link); |
| 482 | 482 | |
| 483 | − /* DP active dongles */ | |
| 484 | − if (is_dp_active_dongle(link)) { | |
| 485 | − link->type = dc_connection_active_dongle; | |
| 486 | − if (!link->dpcd_caps.sink_count.bits.SINK_COUNT) { | |
| 487 | − /* | |
| 488 | − * active dongle unplug processing for short irq | |
| 489 | − */ | |
| 490 | − link_disconnect_sink(link); | |
| 491 | − return; | |
| 492 | − } | |
| 493 | − | |
| 494 | − if (link->dpcd_caps.dongle_type != | |
| 495 | − DISPLAY_DONGLE_DP_HDMI_CONVERTER) { | |
| 496 | − *converter_disable_audio = true; | |
| 497 | − } | |
| 498 | − } | |
| 499 | 483 | if (is_mst_supported(link)) { |
| 500 | 484 | sink_caps->signal = SIGNAL_TYPE_DISPLAY_PORT_MST; |
| 501 | 485 | link->type = dc_connection_mst_branch; |
| @@ -535,6 +519,22 @@ static void detect_dp( · 33 unmodified lines | ||
| 535 | 519 | sink_caps->signal = SIGNAL_TYPE_DISPLAY_PORT; |
| 536 | 520 | } |
| 537 | 521 | } |
| 522 | + | |
| 523 | + if (link->type != dc_connection_mst_branch && | |
| 524 | + is_dp_active_dongle(link)) { | |
| 525 | + /* DP active dongles */ | |
| 526 | + link->type = dc_connection_active_dongle; | |
| 527 | + if (!link->dpcd_caps.sink_count.bits.SINK_COUNT) { | |
| 528 | + /* | |
| 529 | + * active dongle unplug processing for short irq | |
| 530 | + */ | |
| 531 | + link_disconnect_sink(link); | |
| 532 | + return; | |
| 533 | + } | |
| 534 | + | |
| 535 | + if (link->dpcd_caps.dongle_type != DISPLAY_DONGLE_DP_HDMI_CONVERTER) | |
| 536 | + *converter_disable_audio = true; | |
| 537 | + } | |
| 538 | 538 | } else { |
| 539 | 539 | /* DP passive dongles */ |
| 540 | 540 | sink_caps->signal = dp_passive_dongle_detection(link->ddc, |
| @@ -1801,12 +1801,75 @@ static void disable_link(struct dc_link *link, enum signal_type signal) · 1260 unmodified lines | ||
| 1801 | 1801 | link->link_enc->funcs->disable_output(link->link_enc, signal, link); |
| 1802 | 1802 | } |
| 1803 | 1803 | |
| 1804 | +bool dp_active_dongle_validate_timing( | |
| 1805 | + const struct dc_crtc_timing *timing, | |
| 1806 | + const struct dc_dongle_caps *dongle_caps) | |
| 1807 | +{ | |
| 1808 | + unsigned int required_pix_clk = timing->pix_clk_khz; | |
| 1809 | + | |
| 1810 | + if (dongle_caps->dongle_type != DISPLAY_DONGLE_DP_HDMI_CONVERTER || | |
| 1811 | + dongle_caps->extendedCapValid == false) | |
| 1812 | + return true; | |
| 1813 | + | |
| 1814 | + /* Check Pixel Encoding */ | |
| 1815 | + switch (timing->pixel_encoding) { | |
| 1816 | + case PIXEL_ENCODING_RGB: | |
| 1817 | + case PIXEL_ENCODING_YCBCR444: | |
| 1818 | + break; | |
| 1819 | + case PIXEL_ENCODING_YCBCR422: | |
| 1820 | + if (!dongle_caps->is_dp_hdmi_ycbcr422_pass_through) | |
| 1821 | + return false; | |
| 1822 | + break; | |
| 1823 | + case PIXEL_ENCODING_YCBCR420: | |
| 1824 | + if (!dongle_caps->is_dp_hdmi_ycbcr420_pass_through) | |
| 1825 | + return false; | |
| 1826 | + break; | |
| 1827 | + default: | |
| 1828 | + /* Invalid Pixel Encoding*/ | |
| 1829 | + return false; | |
| 1830 | + } | |
| 1831 | + | |
| 1832 | + | |
| 1833 | + /* Check Color Depth and Pixel Clock */ | |
| 1834 | + if (timing->pixel_encoding == PIXEL_ENCODING_YCBCR420) | |
| 1835 | + required_pix_clk /= 2; | |
| 1836 | + | |
| 1837 | + switch (timing->display_color_depth) { | |
| 1838 | + case COLOR_DEPTH_666: | |
| 1839 | + case COLOR_DEPTH_888: | |
| 1840 | + /*888 and 666 should always be supported*/ | |
| 1841 | + break; | |
| 1842 | + case COLOR_DEPTH_101010: | |
| 1843 | + if (dongle_caps->dp_hdmi_max_bpc < 10) | |
| 1844 | + return false; | |
| 1845 | + required_pix_clk = required_pix_clk * 10 / 8; | |
| 1846 | + break; | |
| 1847 | + case COLOR_DEPTH_121212: | |
| 1848 | + if (dongle_caps->dp_hdmi_max_bpc < 12) | |
| 1849 | + return false; | |
| 1850 | + required_pix_clk = required_pix_clk * 12 / 8; | |
| 1851 | + break; | |
| 1852 | + | |
| 1853 | + case COLOR_DEPTH_141414: | |
| 1854 | + case COLOR_DEPTH_161616: | |
| 1855 | + default: | |
| 1856 | + /* These color depths are currently not supported */ | |
| 1857 | + return false; | |
| 1858 | + } | |
| 1859 | + | |
| 1860 | + if (required_pix_clk > dongle_caps->dp_hdmi_max_pixel_clk) | |
| 1861 | + return false; | |
| 1862 | + | |
| 1863 | + return true; | |
| 1864 | +} | |
| 1865 | + | |
| 1804 | 1866 | enum dc_status dc_link_validate_mode_timing( |
| 1805 | 1867 | const struct dc_stream_state *stream, |
| 1806 | 1868 | struct dc_link *link, |
| 1807 | 1869 | const struct dc_crtc_timing *timing) |
| 1808 | 1870 | { |
| 1809 | 1871 | uint32_t max_pix_clk = stream->sink->dongle_max_pix_clk; |
| 1872 | + struct dc_dongle_caps *dongle_caps = &link->link_status.dpcd_caps->dongle_caps; | |
| 1810 | 1873 | |
| 1811 | 1874 | /* A hack to avoid failing any modes for EDID override feature on |
| 1812 | 1875 | * topology change such as lower quality cable for DP or different dongle |
| @@ -1814,8 +1877,13 @@ enum dc_status dc_link_validate_mode_timing( · 1 unmodified line | ||
| 1814 | 1877 | if (link->remote_sinks[0]) |
| 1815 | 1878 | return DC_OK; |
| 1816 | 1879 | |
| 1880 | + /* Passive Dongle */ | |
| 1817 | 1881 | if (0 != max_pix_clk && timing->pix_clk_khz > max_pix_clk) |
| 1818 | − return DC_EXCEED_DONGLE_MAX_CLK; | |
| 1882 | + return DC_EXCEED_DONGLE_CAP; | |
| 1883 | + | |
| 1884 | + /* Active Dongle*/ | |
| 1885 | + if (!dp_active_dongle_validate_timing(timing, dongle_caps)) | |
| 1886 | + return DC_EXCEED_DONGLE_CAP; | |
| 1819 | 1887 | |
| 1820 | 1888 | switch (stream->signal) { |
| 1821 | 1889 | case SIGNAL_TYPE_EDP: |
| @@ -1512,7 +1512,7 @@ static bool hpd_rx_irq_check_link_loss_status( · 1511 unmodified lines | ||
| 1512 | 1512 | struct dc_link *link, |
| 1513 | 1513 | union hpd_irq_data *hpd_irq_dpcd_data) |
| 1514 | 1514 | { |
| 1515 | − uint8_t irq_reg_rx_power_state; | |
| 1515 | + uint8_t irq_reg_rx_power_state = 0; | |
| 1516 | 1516 | enum dc_status dpcd_result = DC_ERROR_UNEXPECTED; |
| 1517 | 1517 | union lane_status lane_status; |
| 1518 | 1518 | uint32_t lane; |
| @@ -1524,60 +1524,55 @@ static bool hpd_rx_irq_check_link_loss_status( · 5 unmodified lines | ||
| 1524 | 1524 | |
| 1525 | 1525 | if (link->cur_link_settings.lane_count == 0) |
| 1526 | 1526 | return return_code; |
| 1527 | − /*1. Check that we can handle interrupt: Not in FS DOS, | |
| 1528 | − * Not in "Display Timeout" state, Link is trained. | |
| 1529 | − */ | |
| 1530 | 1527 | |
| 1531 | − dpcd_result = core_link_read_dpcd(link, | |
| 1532 | − DP_SET_POWER, | |
| 1533 | − &irq_reg_rx_power_state, | |
| 1534 | − sizeof(irq_reg_rx_power_state)); | |
| 1528 | + /*1. Check that Link Status changed, before re-training.*/ | |
| 1535 | 1529 | |
| 1536 | − if (dpcd_result != DC_OK) { | |
| 1537 | − irq_reg_rx_power_state = DP_SET_POWER_D0; | |
| 1538 | − dm_logger_write(link->ctx->logger, LOG_HW_HPD_IRQ, | |
| 1539 | − "%s: DPCD read failed to obtain power state.\n", | |
| 1540 | − __func__); | |
| 1530 | + /*parse lane status*/ | |
| 1531 | + for (lane = 0; lane < link->cur_link_settings.lane_count; lane++) { | |
| 1532 | + /* check status of lanes 0,1 | |
| 1533 | + * changed DpcdAddress_Lane01Status (0x202) | |
| 1534 | + */ | |
| 1535 | + lane_status.raw = get_nibble_at_index( | |
| 1536 | + &hpd_irq_dpcd_data->bytes.lane01_status.raw, | |
| 1537 | + lane); | |
| 1538 | + | |
| 1539 | + if (!lane_status.bits.CHANNEL_EQ_DONE_0 || | |
| 1540 | + !lane_status.bits.CR_DONE_0 || | |
| 1541 | + !lane_status.bits.SYMBOL_LOCKED_0) { | |
| 1542 | + /* if one of the channel equalization, clock | |
| 1543 | + * recovery or symbol lock is dropped | |
| 1544 | + * consider it as (link has been | |
| 1545 | + * dropped) dp sink status has changed | |
| 1546 | + */ | |
| 1547 | + sink_status_changed = true; | |
| 1548 | + break; | |
| 1549 | + } | |
| 1541 | 1550 | } |
| 1542 | 1551 | |
| 1543 | − if (irq_reg_rx_power_state == DP_SET_POWER_D0) { | |
| 1544 | − | |
| 1545 | − /*2. Check that Link Status changed, before re-training.*/ | |
| 1546 | − | |
| 1547 | − /*parse lane status*/ | |
| 1548 | − for (lane = 0; | |
| 1549 | − lane < link->cur_link_settings.lane_count; | |
| 1550 | − lane++) { | |
| 1552 | + /* Check interlane align.*/ | |
| 1553 | + if (sink_status_changed || | |
| 1554 | + !hpd_irq_dpcd_data->bytes.lane_status_updated.bits.INTERLANE_ALIGN_DONE) { | |
| 1551 | 1555 | |
| 1552 | − /* check status of lanes 0,1 | |
| 1553 | − * changed DpcdAddress_Lane01Status (0x202)*/ | |
| 1554 | − lane_status.raw = get_nibble_at_index( | |
| 1555 | − &hpd_irq_dpcd_data->bytes.lane01_status.raw, | |
| 1556 | − lane); | |
| 1557 | − | |
| 1558 | − if (!lane_status.bits.CHANNEL_EQ_DONE_0 || | |
| 1559 | − !lane_status.bits.CR_DONE_0 || | |
| 1560 | − !lane_status.bits.SYMBOL_LOCKED_0) { | |
| 1561 | − /* if one of the channel equalization, clock | |
| 1562 | − * recovery or symbol lock is dropped | |
| 1563 | − * consider it as (link has been | |
| 1564 | − * dropped) dp sink status has changed*/ | |
| 1565 | − sink_status_changed = true; | |
| 1566 | − break; | |
| 1567 | − } | |
| 1556 | + dm_logger_write(link->ctx->logger, LOG_HW_HPD_IRQ, | |
| 1557 | + "%s: Link Status changed.\n", __func__); | |
| 1568 | 1558 | |
| 1569 | − } | |
| 1559 | + return_code = true; | |
| 1570 | 1560 | |
| 1571 | − /* Check interlane align.*/ | |
| 1572 | − if (sink_status_changed || | |
| 1573 | − !hpd_irq_dpcd_data->bytes.lane_status_updated.bits. | |
| 1574 | − INTERLANE_ALIGN_DONE) { | |
| 1561 | + /*2. Check that we can handle interrupt: Not in FS DOS, | |
| 1562 | + * Not in "Display Timeout" state, Link is trained. | |
| 1563 | + */ | |
| 1564 | + dpcd_result = core_link_read_dpcd(link, | |
| 1565 | + DP_SET_POWER, | |
| 1566 | + &irq_reg_rx_power_state, | |
| 1567 | + sizeof(irq_reg_rx_power_state)); | |
| 1575 | 1568 | |
| 1569 | + if (dpcd_result != DC_OK) { | |
| 1576 | 1570 | dm_logger_write(link->ctx->logger, LOG_HW_HPD_IRQ, |
| 1577 | − "%s: Link Status changed.\n", | |
| 1571 | + "%s: DPCD read failed to obtain power state.\n", | |
| 1578 | 1572 | __func__); |
| 1579 | − | |
| 1580 | − return_code = true; | |
| 1573 | + } else { | |
| 1574 | + if (irq_reg_rx_power_state != DP_SET_POWER_D0) | |
| 1575 | + return_code = false; | |
| 1581 | 1576 | } |
| 1582 | 1577 | } |
| 1583 | 1578 | |
| @@ -2062,6 +2057,24 @@ bool is_dp_active_dongle(const struct dc_link *link) · 478 unmodified lines | ||
| 2062 | 2057 | (dongle_type == DISPLAY_DONGLE_DP_HDMI_CONVERTER); |
| 2063 | 2058 | } |
| 2064 | 2059 | |
| 2060 | +static int translate_dpcd_max_bpc(enum dpcd_downstream_port_max_bpc bpc) | |
| 2061 | +{ | |
| 2062 | + switch (bpc) { | |
| 2063 | + case DOWN_STREAM_MAX_8BPC: | |
| 2064 | + return 8; | |
| 2065 | + case DOWN_STREAM_MAX_10BPC: | |
| 2066 | + return 10; | |
| 2067 | + case DOWN_STREAM_MAX_12BPC: | |
| 2068 | + return 12; | |
| 2069 | + case DOWN_STREAM_MAX_16BPC: | |
| 2070 | + return 16; | |
| 2071 | + default: | |
| 2072 | + break; | |
| 2073 | + } | |
| 2074 | + | |
| 2075 | + return -1; | |
| 2076 | +} | |
| 2077 | + | |
| 2065 | 2078 | static void get_active_converter_info( |
| 2066 | 2079 | uint8_t data, struct dc_link *link) |
| 2067 | 2080 | { |
| @@ -2131,7 +2144,8 @@ static void get_active_converter_info( · 63 unmodified lines | ||
| 2131 | 2144 | hdmi_caps.bits.YCrCr420_CONVERSION; |
| 2132 | 2145 | |
| 2133 | 2146 | link->dpcd_caps.dongle_caps.dp_hdmi_max_bpc = |
| 2134 | − hdmi_color_caps.bits.MAX_BITS_PER_COLOR_COMPONENT; | |
| 2147 | + translate_dpcd_max_bpc( | |
| 2148 | + hdmi_color_caps.bits.MAX_BITS_PER_COLOR_COMPONENT); | |
| 2135 | 2149 | |
| 2136 | 2150 | link->dpcd_caps.dongle_caps.extendedCapValid = true; |
| 2137 | 2151 | } |
| @@ -516,13 +516,11 @@ static void calculate_viewport(struct pipe_ctx *pipe_ctx) · 515 unmodified lines | ||
| 516 | 516 | right_view = (plane_state->rotation == ROTATION_ANGLE_270) != sec_split; |
| 517 | 517 | |
| 518 | 518 | if (right_view) { |
| 519 | − data->viewport.width /= 2; | |
| 520 | − data->viewport_c.width /= 2; | |
| 521 | − data->viewport.x += data->viewport.width; | |
| 522 | − data->viewport_c.x += data->viewport_c.width; | |
| 519 | + data->viewport.x += data->viewport.width / 2; | |
| 520 | + data->viewport_c.x += data->viewport_c.width / 2; | |
| 523 | 521 | /* Ceil offset pipe */ |
| 524 | − data->viewport.width += data->viewport.width % 2; | |
| 525 | − data->viewport_c.width += data->viewport_c.width % 2; | |
| 522 | + data->viewport.width = (data->viewport.width + 1) / 2; | |
| 523 | + data->viewport_c.width = (data->viewport_c.width + 1) / 2; | |
| 526 | 524 | } else { |
| 527 | 525 | data->viewport.width /= 2; |
| 528 | 526 | data->viewport_c.width /= 2; |
| @@ -580,14 +578,12 @@ static void calculate_recout(struct pipe_ctx *pipe_ctx, struct view *recout_skip · 51 unmodified lines | ||
| 580 | 578 | if (pipe_ctx->top_pipe && pipe_ctx->top_pipe->plane_state == |
| 581 | 579 | pipe_ctx->plane_state) { |
| 582 | 580 | if (stream->view_format == VIEW_3D_FORMAT_TOP_AND_BOTTOM) { |
| 583 | − pipe_ctx->plane_res.scl_data.recout.height /= 2; | |
| 584 | − pipe_ctx->plane_res.scl_data.recout.y += pipe_ctx->plane_res.scl_data.recout.height; | |
| 581 | + pipe_ctx->plane_res.scl_data.recout.y += pipe_ctx->plane_res.scl_data.recout.height / 2; | |
| 585 | 582 | /* Floor primary pipe, ceil 2ndary pipe */ |
| 586 | − pipe_ctx->plane_res.scl_data.recout.height += pipe_ctx->plane_res.scl_data.recout.height % 2; | |
| 583 | + pipe_ctx->plane_res.scl_data.recout.height = (pipe_ctx->plane_res.scl_data.recout.height + 1) / 2; | |
| 587 | 584 | } else { |
| 588 | − pipe_ctx->plane_res.scl_data.recout.width /= 2; | |
| 589 | − pipe_ctx->plane_res.scl_data.recout.x += pipe_ctx->plane_res.scl_data.recout.width; | |
| 590 | − pipe_ctx->plane_res.scl_data.recout.width += pipe_ctx->plane_res.scl_data.recout.width % 2; | |
| 585 | + pipe_ctx->plane_res.scl_data.recout.x += pipe_ctx->plane_res.scl_data.recout.width / 2; | |
| 586 | + pipe_ctx->plane_res.scl_data.recout.width = (pipe_ctx->plane_res.scl_data.recout.width + 1) / 2; | |
| 591 | 587 | } |
| 592 | 588 | } else if (pipe_ctx->bottom_pipe && |
| 593 | 589 | pipe_ctx->bottom_pipe->plane_state == pipe_ctx->plane_state) { |
| @@ -856,6 +852,7 @@ bool resource_build_scaling_params(struct pipe_ctx *pipe_ctx) · 262 unmodified lines | ||
| 856 | 852 | pipe_ctx->plane_res.scl_data.h_active = timing->h_addressable + timing->h_border_left + timing->h_border_right; |
| 857 | 853 | pipe_ctx->plane_res.scl_data.v_active = timing->v_addressable + timing->v_border_top + timing->v_border_bottom; |
| 858 | 854 | |
| 855 | + | |
| 859 | 856 | /* Taps calculations */ |
| 860 | 857 | if (pipe_ctx->plane_res.xfm != NULL) |
| 861 | 858 | res = pipe_ctx->plane_res.xfm->funcs->transform_get_optimal_number_of_taps( |
| @@ -864,16 +861,21 @@ bool resource_build_scaling_params(struct pipe_ctx *pipe_ctx) · 2 unmodified lines | ||
| 864 | 861 | if (pipe_ctx->plane_res.dpp != NULL) |
| 865 | 862 | res = pipe_ctx->plane_res.dpp->funcs->dpp_get_optimal_number_of_taps( |
| 866 | 863 | pipe_ctx->plane_res.dpp, &pipe_ctx->plane_res.scl_data, &plane_state->scaling_quality); |
| 867 | − | |
| 868 | 864 | if (!res) { |
| 869 | 865 | /* Try 24 bpp linebuffer */ |
| 870 | 866 | pipe_ctx->plane_res.scl_data.lb_params.depth = LB_PIXEL_DEPTH_24BPP; |
| 871 | 867 | |
| 872 | − res = pipe_ctx->plane_res.xfm->funcs->transform_get_optimal_number_of_taps( | |
| 873 | − pipe_ctx->plane_res.xfm, &pipe_ctx->plane_res.scl_data, &plane_state->scaling_quality); | |
| 868 | + if (pipe_ctx->plane_res.xfm != NULL) | |
| 869 | + res = pipe_ctx->plane_res.xfm->funcs->transform_get_optimal_number_of_taps( | |
| 870 | + pipe_ctx->plane_res.xfm, | |
| 871 | + &pipe_ctx->plane_res.scl_data, | |
| 872 | + &plane_state->scaling_quality); | |
| 874 | 873 | |
| 875 | − res = pipe_ctx->plane_res.dpp->funcs->dpp_get_optimal_number_of_taps( | |
| 876 | − pipe_ctx->plane_res.dpp, &pipe_ctx->plane_res.scl_data, &plane_state->scaling_quality); | |
| 874 | + if (pipe_ctx->plane_res.dpp != NULL) | |
| 875 | + res = pipe_ctx->plane_res.dpp->funcs->dpp_get_optimal_number_of_taps( | |
| 876 | + pipe_ctx->plane_res.dpp, | |
| 877 | + &pipe_ctx->plane_res.scl_data, | |
| 878 | + &plane_state->scaling_quality); | |
| 877 | 879 | } |
| 878 | 880 | |
| 879 | 881 | if (res) |
| @@ -991,8 +993,10 @@ static struct pipe_ctx *acquire_free_pipe_for_stream( · 111 unmodified lines | ||
| 991 | 993 | |
| 992 | 994 | head_pipe = resource_get_head_pipe_for_stream(res_ctx, stream); |
| 993 | 995 | |
| 994 | − if (!head_pipe) | |
| 996 | + if (!head_pipe) { | |
| 995 | 997 | ASSERT(0); |
| 998 | + return NULL; | |
| 999 | + } | |
| 996 | 1000 | |
| 997 | 1001 | if (!head_pipe->plane_state) |
| 998 | 1002 | return head_pipe; |
| @@ -1447,11 +1451,16 @@ static struct stream_encoder *find_first_free_match_stream_enc_for_link( · 448 unmodified lines | ||
| 1447 | 1451 | |
| 1448 | 1452 | static struct audio *find_first_free_audio( |
| 1449 | 1453 | struct resource_context *res_ctx, |
| 1450 | − const struct resource_pool *pool) | |
| 1454 | + const struct resource_pool *pool, | |
| 1455 | + enum engine_id id) | |
| 1451 | 1456 | { |
| 1452 | 1457 | int i; |
| 1453 | 1458 | for (i = 0; i < pool->audio_count; i++) { |
| 1454 | 1459 | if ((res_ctx->is_audio_acquired[i] == false) && (res_ctx->is_stream_enc_acquired[i] == true)) { |
| 1460 | + /*we have enough audio endpoint, find the matching inst*/ | |
| 1461 | + if (id != i) | |
| 1462 | + continue; | |
| 1463 | + | |
| 1455 | 1464 | return pool->audios[i]; |
| 1456 | 1465 | } |
| 1457 | 1466 | } |
| @@ -1700,7 +1709,7 @@ enum dc_status resource_map_pool_resources( · 242 unmodified lines | ||
| 1700 | 1709 | dc_is_audio_capable_signal(pipe_ctx->stream->signal) && |
| 1701 | 1710 | stream->audio_info.mode_count) { |
| 1702 | 1711 | pipe_ctx->stream_res.audio = find_first_free_audio( |
| 1703 | − &context->res_ctx, pool); | |
| 1712 | + &context->res_ctx, pool, pipe_ctx->stream_res.stream_enc->id); | |
| 1704 | 1713 | |
| 1705 | 1714 | /* |
| 1706 | 1715 | * Audio assigned in order first come first get. |
| @@ -1765,13 +1774,16 @@ enum dc_status dc_validate_global_state( · 58 unmodified lines | ||
| 1765 | 1774 | enum dc_status result = DC_ERROR_UNEXPECTED; |
| 1766 | 1775 | int i, j; |
| 1767 | 1776 | |
| 1777 | + if (!new_ctx) | |
| 1778 | + return DC_ERROR_UNEXPECTED; | |
| 1779 | + | |
| 1768 | 1780 | if (dc->res_pool->funcs->validate_global) { |
| 1769 | 1781 | result = dc->res_pool->funcs->validate_global(dc, new_ctx); |
| 1770 | 1782 | if (result != DC_OK) |
| 1771 | 1783 | return result; |
| 1772 | 1784 | } |
| 1773 | 1785 | |
| 1774 | − for (i = 0; new_ctx && i < new_ctx->stream_count; i++) { | |
| 1786 | + for (i = 0; i < new_ctx->stream_count; i++) { | |
| 1775 | 1787 | struct dc_stream_state *stream = new_ctx->streams[i]; |
| 1776 | 1788 | |
| 1777 | 1789 | for (j = 0; j < dc->res_pool->pipe_count; j++) { |
| @@ -263,7 +263,6 @@ bool dc_stream_set_cursor_position( · 262 unmodified lines | ||
| 263 | 263 | struct input_pixel_processor *ipp = pipe_ctx->plane_res.ipp; |
| 264 | 264 | struct mem_input *mi = pipe_ctx->plane_res.mi; |
| 265 | 265 | struct hubp *hubp = pipe_ctx->plane_res.hubp; |
| 266 | − struct transform *xfm = pipe_ctx->plane_res.xfm; | |
| 267 | 266 | struct dpp *dpp = pipe_ctx->plane_res.dpp; |
| 268 | 267 | struct dc_cursor_position pos_cpy = *position; |
| 269 | 268 | struct dc_cursor_mi_param param = { |
| @@ -294,11 +293,11 @@ bool dc_stream_set_cursor_position( · 24 unmodified lines | ||
| 294 | 293 | if (mi != NULL && mi->funcs->set_cursor_position != NULL) |
| 295 | 294 | mi->funcs->set_cursor_position(mi, &pos_cpy, ¶m); |
| 296 | 295 | |
| 297 | − if (hubp != NULL && hubp->funcs->set_cursor_position != NULL) | |
| 298 | − hubp->funcs->set_cursor_position(hubp, &pos_cpy, ¶m); | |
| 296 | + if (!hubp) | |
| 297 | + continue; | |
| 299 | 298 | |
| 300 | − if (xfm != NULL && xfm->funcs->set_cursor_position != NULL) | |
| 301 | − xfm->funcs->set_cursor_position(xfm, &pos_cpy, ¶m, hubp->curs_attr.width); | |
| 299 | + if (hubp->funcs->set_cursor_position != NULL) | |
| 300 | + hubp->funcs->set_cursor_position(hubp, &pos_cpy, ¶m); | |
| 302 | 301 | |
| 303 | 302 | if (dpp != NULL && dpp->funcs->set_cursor_position != NULL) |
| 304 | 303 | dpp->funcs->set_cursor_position(dpp, &pos_cpy, ¶m, hubp->curs_attr.width); |
| @@ -352,11 +352,11 @@ void dce_aud_az_enable(struct audio *audio) · 351 unmodified lines | ||
| 352 | 352 | uint32_t value = AZ_REG_READ(AZALIA_F0_CODEC_PIN_CONTROL_HOT_PLUG_CONTROL); |
| 353 | 353 | |
| 354 | 354 | set_reg_field_value(value, 1, |
| 355 | − AZALIA_F0_CODEC_PIN_CONTROL_HOT_PLUG_CONTROL, | |
| 356 | − CLOCK_GATING_DISABLE); | |
| 357 | − set_reg_field_value(value, 1, | |
| 358 | − AZALIA_F0_CODEC_PIN_CONTROL_HOT_PLUG_CONTROL, | |
| 359 | − AUDIO_ENABLED); | |
| 355 | + AZALIA_F0_CODEC_PIN_CONTROL_HOT_PLUG_CONTROL, | |
| 356 | + CLOCK_GATING_DISABLE); | |
| 357 | + set_reg_field_value(value, 1, | |
| 358 | + AZALIA_F0_CODEC_PIN_CONTROL_HOT_PLUG_CONTROL, | |
| 359 | + AUDIO_ENABLED); | |
| 360 | 360 | |
| 361 | 361 | AZ_REG_WRITE(AZALIA_F0_CODEC_PIN_CONTROL_HOT_PLUG_CONTROL, value); |
| 362 | 362 | value = AZ_REG_READ(AZALIA_F0_CODEC_PIN_CONTROL_HOT_PLUG_CONTROL); |
| @@ -87,6 +87,9 @@ static void dce110_update_generic_info_packet( · 86 unmodified lines | ||
| 87 | 87 | */ |
| 88 | 88 | uint32_t max_retries = 50; |
| 89 | 89 | |
| 90 | + /*we need turn on clock before programming AFMT block*/ | |
| 91 | + REG_UPDATE(AFMT_CNTL, AFMT_AUDIO_CLOCK_EN, 1); | |
| 92 | + | |
| 90 | 93 | if (REG(AFMT_VBI_PACKET_CONTROL1)) { |
| 91 | 94 | if (packet_index >= 8) |
| 92 | 95 | ASSERT(0); |
| @@ -991,6 +991,16 @@ void dce110_disable_stream(struct pipe_ctx *pipe_ctx, int option) · 990 unmodified lines | ||
| 991 | 991 | struct dc_link *link = stream->sink->link; |
| 992 | 992 | struct dc *dc = pipe_ctx->stream->ctx->dc; |
| 993 | 993 | |
| 994 | + if (dc_is_hdmi_signal(pipe_ctx->stream->signal)) | |
| 995 | + pipe_ctx->stream_res.stream_enc->funcs->stop_hdmi_info_packets( | |
| 996 | + pipe_ctx->stream_res.stream_enc); | |
| 997 | + | |
| 998 | + if (dc_is_dp_signal(pipe_ctx->stream->signal)) | |
| 999 | + pipe_ctx->stream_res.stream_enc->funcs->stop_dp_info_packets( | |
| 1000 | + pipe_ctx->stream_res.stream_enc); | |
| 1001 | + | |
| 1002 | + pipe_ctx->stream_res.stream_enc->funcs->audio_mute_control( | |
| 1003 | + pipe_ctx->stream_res.stream_enc, true); | |
| 994 | 1004 | if (pipe_ctx->stream_res.audio) { |
| 995 | 1005 | pipe_ctx->stream_res.audio->funcs->az_disable(pipe_ctx->stream_res.audio); |
| 996 | 1006 | |
| @@ -1015,18 +1025,6 @@ void dce110_disable_stream(struct pipe_ctx *pipe_ctx, int option) · 18 unmodified lines | ||
| 1015 | 1025 | */ |
| 1016 | 1026 | } |
| 1017 | 1027 | |
| 1018 | − if (dc_is_hdmi_signal(pipe_ctx->stream->signal)) | |
| 1019 | − pipe_ctx->stream_res.stream_enc->funcs->stop_hdmi_info_packets( | |
| 1020 | − pipe_ctx->stream_res.stream_enc); | |
| 1021 | − | |
| 1022 | − if (dc_is_dp_signal(pipe_ctx->stream->signal)) | |
| 1023 | − pipe_ctx->stream_res.stream_enc->funcs->stop_dp_info_packets( | |
| 1024 | − pipe_ctx->stream_res.stream_enc); | |
| 1025 | − | |
| 1026 | − pipe_ctx->stream_res.stream_enc->funcs->audio_mute_control( | |
| 1027 | − pipe_ctx->stream_res.stream_enc, true); | |
| 1028 | − | |
| 1029 | − | |
| 1030 | 1028 | /* blank at encoder level */ |
| 1031 | 1029 | if (dc_is_dp_signal(pipe_ctx->stream->signal)) { |
| 1032 | 1030 | if (pipe_ctx->stream->sink->link->connector_signal == SIGNAL_TYPE_EDP) |
| @@ -1774,6 +1772,10 @@ static enum dc_status validate_fbc(struct dc *dc, · 741 unmodified lines | ||
| 1774 | 1772 | if (pipe_ctx->stream->sink->link->psr_enabled) |
| 1775 | 1773 | return DC_ERROR_UNEXPECTED; |
| 1776 | 1774 | |
| 1775 | + /* Nothing to compress */ | |
| 1776 | + if (!pipe_ctx->plane_state) | |
| 1777 | + return DC_ERROR_UNEXPECTED; | |
| 1778 | + | |
| 1777 | 1779 | /* Only for non-linear tiling */ |
| 1778 | 1780 | if (pipe_ctx->plane_state->tiling_info.gfx8.array_mode == DC_ARRAY_LINEAR_GENERAL) |
| 1779 | 1781 | return DC_ERROR_UNEXPECTED; |
| @@ -1868,8 +1870,10 @@ static void dce110_reset_hw_ctx_wrap( · 88 unmodified lines | ||
| 1868 | 1870 | pipe_need_reprogram(pipe_ctx_old, pipe_ctx)) { |
| 1869 | 1871 | struct clock_source *old_clk = pipe_ctx_old->clock_source; |
| 1870 | 1872 | |
| 1871 | − /* disable already, no need to disable again */ | |
| 1872 | − if (pipe_ctx->stream && !pipe_ctx->stream->dpms_off) | |
| 1873 | + /* Disable if new stream is null. O/w, if stream is | |
| 1874 | + * disabled already, no need to disable again. | |
| 1875 | + */ | |
| 1876 | + if (!pipe_ctx->stream || !pipe_ctx->stream->dpms_off) | |
| 1873 | 1877 | core_link_disable_stream(pipe_ctx_old, FREE_ACQUIRED_RESOURCE); |
| 1874 | 1878 | |
| 1875 | 1879 | pipe_ctx_old->stream_res.tg->funcs->set_blank(pipe_ctx_old->stream_res.tg, true); |
| @@ -1037,11 +1037,13 @@ static bool underlay_create(struct dc_context *ctx, struct resource_pool *pool) · 1036 unmodified lines | ||
| 1037 | 1037 | struct dce110_opp *dce110_oppv = kzalloc(sizeof(*dce110_oppv), |
| 1038 | 1038 | GFP_KERNEL); |
| 1039 | 1039 | |
| 1040 | − if ((dce110_tgv == NULL) || | |
| 1041 | − (dce110_xfmv == NULL) || | |
| 1042 | − (dce110_miv == NULL) || | |
| 1043 | − (dce110_oppv == NULL)) | |
| 1044 | − return false; | |
| 1040 | + if (!dce110_tgv || !dce110_xfmv || !dce110_miv || !dce110_oppv) { | |
| 1041 | + kfree(dce110_tgv); | |
| 1042 | + kfree(dce110_xfmv); | |
| 1043 | + kfree(dce110_miv); | |
| 1044 | + kfree(dce110_oppv); | |
| 1045 | + return false; | |
| 1046 | + } | |
| 1045 | 1047 | |
| 1046 | 1048 | dce110_opp_v_construct(dce110_oppv, ctx); |
| 1047 | 1049 | |
| @@ -1112,10 +1112,7 @@ bool dce110_timing_generator_validate_timing( · 1111 unmodified lines | ||
| 1112 | 1112 | enum signal_type signal) |
| 1113 | 1113 | { |
| 1114 | 1114 | uint32_t h_blank; |
| 1115 | − uint32_t h_back_porch; | |
| 1116 | − uint32_t hsync_offset = timing->h_border_right + | |
| 1117 | − timing->h_front_porch; | |
| 1118 | − uint32_t h_sync_start = timing->h_addressable + hsync_offset; | |
| 1115 | + uint32_t h_back_porch, hsync_offset, h_sync_start; | |
| 1119 | 1116 | |
| 1120 | 1117 | struct dce110_timing_generator *tg110 = DCE110TG_FROM_TG(tg); |
| 1121 | 1118 | |
| @@ -1124,6 +1121,9 @@ bool dce110_timing_generator_validate_timing( · 2 unmodified lines | ||
| 1124 | 1121 | if (!timing) |
| 1125 | 1122 | return false; |
| 1126 | 1123 | |
| 1124 | + hsync_offset = timing->h_border_right + timing->h_front_porch; | |
| 1125 | + h_sync_start = timing->h_addressable + hsync_offset; | |
| 1126 | + | |
| 1127 | 1127 | /* Currently we don't support 3D, so block all 3D timings */ |
| 1128 | 1128 | if (timing->timing_3d_format != TIMING_3D_FORMAT_NONE) |
| 1129 | 1129 | return false; |
| @@ -912,11 +912,13 @@ static struct pipe_ctx *dcn10_acquire_idle_pipe_for_layer( · 911 unmodified lines | ||
| 912 | 912 | struct pipe_ctx *head_pipe = resource_get_head_pipe_for_stream(res_ctx, stream); |
| 913 | 913 | struct pipe_ctx *idle_pipe = find_idle_secondary_pipe(res_ctx, pool); |
| 914 | 914 | |
| 915 | − if (!head_pipe) | |
| 915 | + if (!head_pipe) { | |
| 916 | 916 | ASSERT(0); |
| 917 | + return NULL; | |
| 918 | + } | |
| 917 | 919 | |
| 918 | 920 | if (!idle_pipe) |
| 919 | − return false; | |
| 921 | + return NULL; | |
| 920 | 922 | |
| 921 | 923 | idle_pipe->stream = head_pipe->stream; |
| 922 | 924 | idle_pipe->stream_res.tg = head_pipe->stream_res.tg; |
| @@ -496,9 +496,6 @@ static bool tgn10_validate_timing( · 495 unmodified lines | ||
| 496 | 496 | timing->timing_3d_format != TIMING_3D_FORMAT_INBAND_FA) |
| 497 | 497 | return false; |
| 498 | 498 | |
| 499 | − if (timing->timing_3d_format != TIMING_3D_FORMAT_NONE && | |
| 500 | − tg->ctx->dc->debug.disable_stereo_support) | |
| 501 | − return false; | |
| 502 | 499 | /* Temporarily blocking interlacing mode until it's supported */ |
| 503 | 500 | if (timing->flags.INTERLACE == 1) |
| 504 | 501 | return false; |
| @@ -38,7 +38,7 @@ enum dc_status { · 37 unmodified lines | ||
| 38 | 38 | DC_FAIL_DETACH_SURFACES = 8, |
| 39 | 39 | DC_FAIL_SURFACE_VALIDATE = 9, |
| 40 | 40 | DC_NO_DP_LINK_BANDWIDTH = 10, |
| 41 | − DC_EXCEED_DONGLE_MAX_CLK = 11, | |
| 41 | + DC_EXCEED_DONGLE_CAP = 11, | |
| 42 | 42 | DC_SURFACE_PIXEL_FORMAT_UNSUPPORTED = 12, |
| 43 | 43 | DC_FAIL_BANDWIDTH_VALIDATE = 13, /* BW and Watermark validation */ |
| 44 | 44 | DC_FAIL_SCALING = 14, |
| @@ -259,13 +259,6 @@ struct transform_funcs { · 258 unmodified lines | ||
| 259 | 259 | struct transform *xfm_base, |
| 260 | 260 | const struct dc_cursor_attributes *attr); |
| 261 | 261 | |
| 262 | − void (*set_cursor_position)( | |
| 263 | − struct transform *xfm_base, | |
| 264 | − const struct dc_cursor_position *pos, | |
| 265 | − const struct dc_cursor_mi_param *param, | |
| 266 | − uint32_t width | |
| 267 | − ); | |
| 268 | − | |
| 269 | 262 | }; |
| 270 | 263 | |
| 271 | 264 | const uint16_t *get_filter_2tap_16p(void); |
| @@ -317,9 +317,8 @@ static struct drm_plane *hdlcd_plane_init(struct drm_device *drm) · 316 unmodified lines | ||
| 317 | 317 | formats, ARRAY_SIZE(formats), |
| 318 | 318 | NULL, |
| 319 | 319 | DRM_PLANE_TYPE_PRIMARY, NULL); |
| 320 | − if (ret) { | |
| 320 | + if (ret) | |
| 321 | 321 | return ERR_PTR(ret); |
| 322 | − } | |
| 323 | 322 | |
| 324 | 323 | drm_plane_helper_add(plane, &hdlcd_plane_helper_funcs); |
| 325 | 324 | hdlcd->plane = plane; |
| @@ -13,6 +13,7 @@ · 12 unmodified lines | ||
| 13 | 13 | #include <linux/spinlock.h> |
| 14 | 14 | #include <linux/clk.h> |
| 15 | 15 | #include <linux/component.h> |
| 16 | +#include <linux/console.h> | |
| 16 | 17 | #include <linux/list.h> |
| 17 | 18 | #include <linux/of_graph.h> |
| 18 | 19 | #include <linux/of_reserved_mem.h> |
| @@ -354,7 +355,7 @@ err_unload: · 335 unmodified lines | ||
| 354 | 355 | err_free: |
| 355 | 356 | drm_mode_config_cleanup(drm); |
| 356 | 357 | dev_set_drvdata(dev, NULL); |
| 357 | − drm_dev_unref(drm); | |
| 358 | + drm_dev_put(drm); | |
| 358 | 359 | |
| 359 | 360 | return ret; |
| 360 | 361 | } |
| @@ -379,7 +380,7 @@ static void hdlcd_drm_unbind(struct device *dev) · 18 unmodified lines | ||
| 379 | 380 | pm_runtime_disable(drm->dev); |
| 380 | 381 | of_reserved_mem_device_release(drm->dev); |
| 381 | 382 | drm_mode_config_cleanup(drm); |
| 382 | − drm_dev_unref(drm); | |
| 383 | + drm_dev_put(drm); | |
| 383 | 384 | drm->dev_private = NULL; |
| 384 | 385 | dev_set_drvdata(dev, NULL); |
| 385 | 386 | } |
| @@ -432,9 +433,11 @@ static int __maybe_unused hdlcd_pm_suspend(struct device *dev) · 46 unmodified lines | ||
| 432 | 433 | return 0; |
| 433 | 434 | |
| 434 | 435 | drm_kms_helper_poll_disable(drm); |
| 436 | + drm_fbdev_cma_set_suspend_unlocked(hdlcd->fbdev, 1); | |
| 435 | 437 | |
| 436 | 438 | hdlcd->state = drm_atomic_helper_suspend(drm); |
| 437 | 439 | if (IS_ERR(hdlcd->state)) { |
| 440 | + drm_fbdev_cma_set_suspend_unlocked(hdlcd->fbdev, 0); | |
| 438 | 441 | drm_kms_helper_poll_enable(drm); |
| 439 | 442 | return PTR_ERR(hdlcd->state); |
| 440 | 443 | } |
| @@ -451,8 +454,8 @@ static int __maybe_unused hdlcd_pm_resume(struct device *dev) · 10 unmodified lines | ||
| 451 | 454 | return 0; |
| 452 | 455 | |
| 453 | 456 | drm_atomic_helper_resume(drm, hdlcd->state); |
| 457 | + drm_fbdev_cma_set_suspend_unlocked(hdlcd->fbdev, 0); | |
| 454 | 458 | drm_kms_helper_poll_enable(drm); |
| 455 | − pm_runtime_set_active(dev); | |
| 456 | 459 | |
| 457 | 460 | return 0; |
| 458 | 461 | } |
| @@ -65,8 +65,8 @@ static void malidp_crtc_atomic_enable(struct drm_crtc *crtc, · 64 unmodified lines | ||
| 65 | 65 | /* We rely on firmware to set mclk to a sensible level. */ |
| 66 | 66 | clk_set_rate(hwdev->pxlclk, crtc->state->adjusted_mode.crtc_clock * 1000); |
| 67 | 67 | |
| 68 | − hwdev->modeset(hwdev, &vm); | |
| 69 | − hwdev->leave_config_mode(hwdev); | |
| 68 | + hwdev->hw->modeset(hwdev, &vm); | |
| 69 | + hwdev->hw->leave_config_mode(hwdev); | |
| 70 | 70 | drm_crtc_vblank_on(crtc); |
| 71 | 71 | } |
| 72 | 72 | |
| @@ -77,8 +77,12 @@ static void malidp_crtc_atomic_disable(struct drm_crtc *crtc, · 4 unmodified lines | ||
| 77 | 77 | struct malidp_hw_device *hwdev = malidp->dev; |
| 78 | 78 | int err; |
| 79 | 79 | |
| 80 | + /* always disable planes on the CRTC that is being turned off */ | |
| 81 | + drm_atomic_helper_disable_planes_on_crtc(old_state, false); | |
| 82 | + | |
| 80 | 83 | drm_crtc_vblank_off(crtc); |
| 81 | − hwdev->enter_config_mode(hwdev); | |
| 84 | + hwdev->hw->enter_config_mode(hwdev); | |
| 85 | + | |
| 82 | 86 | clk_disable_unprepare(hwdev->pxlclk); |
| 83 | 87 | |
| 84 | 88 | err = pm_runtime_put(crtc->dev->dev); |
| @@ -319,7 +323,7 @@ static int malidp_crtc_atomic_check_scaling(struct drm_crtc *crtc, · 234 unmodified lines | ||
| 319 | 323 | |
| 320 | 324 | mclk_calc: |
| 321 | 325 | drm_display_mode_to_videomode(&state->adjusted_mode, &vm); |
| 322 | − ret = hwdev->se_calc_mclk(hwdev, s, &vm); | |
| 326 | + ret = hwdev->hw->se_calc_mclk(hwdev, s, &vm); | |
| 323 | 327 | if (ret < 0) |
| 324 | 328 | return -EINVAL; |
| 325 | 329 | return 0; |
| @@ -475,7 +479,7 @@ static int malidp_crtc_enable_vblank(struct drm_crtc *crtc) · 149 unmodified lines | ||
| 475 | 479 | struct malidp_hw_device *hwdev = malidp->dev; |
| 476 | 480 | |
| 477 | 481 | malidp_hw_enable_irq(hwdev, MALIDP_DE_BLOCK, |
| 478 | − hwdev->map.de_irq_map.vsync_irq); | |
| 482 | + hwdev->hw->map.de_irq_map.vsync_irq); | |
| 479 | 483 | return 0; |
| 480 | 484 | } |
| 481 | 485 | |
| @@ -485,7 +489,7 @@ static void malidp_crtc_disable_vblank(struct drm_crtc *crtc) · 3 unmodified lines | ||
| 485 | 489 | struct malidp_hw_device *hwdev = malidp->dev; |
| 486 | 490 | |
| 487 | 491 | malidp_hw_disable_irq(hwdev, MALIDP_DE_BLOCK, |
| 488 | − hwdev->map.de_irq_map.vsync_irq); | |
| 492 | + hwdev->hw->map.de_irq_map.vsync_irq); | |
| 489 | 493 | } |
| 490 | 494 | |
| 491 | 495 | static const struct drm_crtc_funcs malidp_crtc_funcs = { |
| @@ -47,10 +47,10 @@ static void malidp_write_gamma_table(struct malidp_hw_device *hwdev, · 46 unmodified lines | ||
| 47 | 47 | * directly. |
| 48 | 48 | */ |
| 49 | 49 | malidp_hw_write(hwdev, gamma_write_mask, |
| 50 | − hwdev->map.coeffs_base + MALIDP_COEF_TABLE_ADDR); | |
| 50 | + hwdev->hw->map.coeffs_base + MALIDP_COEF_TABLE_ADDR); | |
| 51 | 51 | for (i = 0; i < MALIDP_COEFFTAB_NUM_COEFFS; ++i) |
| 52 | 52 | malidp_hw_write(hwdev, data[i], |
| 53 | − hwdev->map.coeffs_base + | |
| 53 | + hwdev->hw->map.coeffs_base + | |
| 54 | 54 | MALIDP_COEF_TABLE_DATA); |
| 55 | 55 | } |
| 56 | 56 | |
| @@ -103,7 +103,7 @@ void malidp_atomic_commit_update_coloradj(struct drm_crtc *crtc, · 46 unmodified lines | ||
| 103 | 103 | for (i = 0; i < MALIDP_COLORADJ_NUM_COEFFS; ++i) |
| 104 | 104 | malidp_hw_write(hwdev, |
| 105 | 105 | mc->coloradj_coeffs[i], |
| 106 | − hwdev->map.coeffs_base + | |
| 106 | + hwdev->hw->map.coeffs_base + | |
| 107 | 107 | MALIDP_COLOR_ADJ_COEF + 4 * i); |
| 108 | 108 | |
| 109 | 109 | malidp_hw_setbits(hwdev, MALIDP_DISP_FUNC_CADJ, |
| @@ -120,8 +120,8 @@ static void malidp_atomic_commit_se_config(struct drm_crtc *crtc, · 10 unmodified lines | ||
| 120 | 120 | struct malidp_hw_device *hwdev = malidp->dev; |
| 121 | 121 | struct malidp_se_config *s = &cs->scaler_config; |
| 122 | 122 | struct malidp_se_config *old_s = &old_cs->scaler_config; |
| 123 | − u32 se_control = hwdev->map.se_base + | |
| 124 | − ((hwdev->map.features & MALIDP_REGMAP_HAS_CLEARIRQ) ? | |
| 123 | + u32 se_control = hwdev->hw->map.se_base + | |
| 124 | + ((hwdev->hw->map.features & MALIDP_REGMAP_HAS_CLEARIRQ) ? | |
| 125 | 125 | 0x10 : 0xC); |
| 126 | 126 | u32 layer_control = se_control + MALIDP_SE_LAYER_CONTROL; |
| 127 | 127 | u32 scr = se_control + MALIDP_SE_SCALING_CONTROL; |
| @@ -135,7 +135,7 @@ static void malidp_atomic_commit_se_config(struct drm_crtc *crtc, · 7 unmodified lines | ||
| 135 | 135 | return; |
| 136 | 136 | } |
| 137 | 137 | |
| 138 | − hwdev->se_set_scaling_coeffs(hwdev, s, old_s); | |
| 138 | + hwdev->hw->se_set_scaling_coeffs(hwdev, s, old_s); | |
| 139 | 139 | val = malidp_hw_read(hwdev, se_control); |
| 140 | 140 | val |= MALIDP_SE_SCALING_EN | MALIDP_SE_ALPHA_EN; |
| 141 | 141 | |
| @@ -170,9 +170,9 @@ static int malidp_set_and_wait_config_valid(struct drm_device *drm) · 28 unmodified lines | ||
| 170 | 170 | int ret; |
| 171 | 171 | |
| 172 | 172 | atomic_set(&malidp->config_valid, 0); |
| 173 | − hwdev->set_config_valid(hwdev); | |
| 173 | + hwdev->hw->set_config_valid(hwdev); | |
| 174 | 174 | /* don't wait for config_valid flag if we are in config mode */ |
| 175 | − if (hwdev->in_config_mode(hwdev)) | |
| 175 | + if (hwdev->hw->in_config_mode(hwdev)) | |
| 176 | 176 | return 0; |
| 177 | 177 | |
| 178 | 178 | ret = wait_event_interruptible_timeout(malidp->wq, |
| @@ -455,7 +455,7 @@ static int malidp_runtime_pm_suspend(struct device *dev) · 276 unmodified lines | ||
| 455 | 455 | struct malidp_hw_device *hwdev = malidp->dev; |
| 456 | 456 | |
| 457 | 457 | /* we can only suspend if the hardware is in config mode */ |
| 458 | − WARN_ON(!hwdev->in_config_mode(hwdev)); | |
| 458 | + WARN_ON(!hwdev->hw->in_config_mode(hwdev)); | |
| 459 | 459 | |
| 460 | 460 | hwdev->pm_suspended = true; |
| 461 | 461 | clk_disable_unprepare(hwdev->mclk); |
| @@ -500,11 +500,7 @@ static int malidp_bind(struct device *dev) · 38 unmodified lines | ||
| 500 | 500 | if (!hwdev) |
| 501 | 501 | return -ENOMEM; |
| 502 | 502 | |
| 503 | − /* | |
| 504 | − * copy the associated data from malidp_drm_of_match to avoid | |
| 505 | − * having to keep a reference to the OF node after binding | |
| 506 | − */ | |
| 507 | − memcpy(hwdev, of_device_get_match_data(dev), sizeof(*hwdev)); | |
| 503 | + hwdev->hw = (struct malidp_hw *)of_device_get_match_data(dev); | |
| 508 | 504 | malidp->dev = hwdev; |
| 509 | 505 | |
| 510 | 506 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
| @@ -568,13 +564,13 @@ static int malidp_bind(struct device *dev) · 57 unmodified lines | ||
| 568 | 564 | goto query_hw_fail; |
| 569 | 565 | } |
| 570 | 566 | |
| 571 | − ret = hwdev->query_hw(hwdev); | |
| 567 | + ret = hwdev->hw->query_hw(hwdev); | |
| 572 | 568 | if (ret) { |
| 573 | 569 | DRM_ERROR("Invalid HW configuration\n"); |
| 574 | 570 | goto query_hw_fail; |
| 575 | 571 | } |
| 576 | 572 | |
| 577 | − version = malidp_hw_read(hwdev, hwdev->map.dc_base + MALIDP_DE_CORE_ID); | |
| 573 | + version = malidp_hw_read(hwdev, hwdev->hw->map.dc_base + MALIDP_DE_CORE_ID); | |
| 578 | 574 | DRM_INFO("found ARM Mali-DP%3x version r%dp%d\n", version >> 16, |
| 579 | 575 | (version >> 12) & 0xf, (version >> 8) & 0xf); |
| 580 | 576 | |
| @@ -589,7 +585,7 @@ static int malidp_bind(struct device *dev) · 8 unmodified lines | ||
| 589 | 585 | |
| 590 | 586 | for (i = 0; i < MAX_OUTPUT_CHANNELS; i++) |
| 591 | 587 | out_depth = (out_depth << 8) | (output_width[i] & 0xf); |
| 592 | − malidp_hw_write(hwdev, out_depth, hwdev->map.out_depth_base); | |
| 588 | + malidp_hw_write(hwdev, out_depth, hwdev->hw->map.out_depth_base); | |
| 593 | 589 | |
| 594 | 590 | atomic_set(&malidp->config_valid, 0); |
| 595 | 591 | init_waitqueue_head(&malidp->wq); |
| @@ -671,7 +667,7 @@ query_hw_fail: · 75 unmodified lines | ||
| 671 | 667 | malidp_runtime_pm_suspend(dev); |
| 672 | 668 | drm->dev_private = NULL; |
| 673 | 669 | dev_set_drvdata(dev, NULL); |
| 674 | − drm_dev_unref(drm); | |
| 670 | + drm_dev_put(drm); | |
| 675 | 671 | alloc_fail: |
| 676 | 672 | of_reserved_mem_device_release(dev); |
| 677 | 673 | |
| @@ -704,7 +700,7 @@ static void malidp_unbind(struct device *dev) · 26 unmodified lines | ||
| 704 | 700 | malidp_runtime_pm_suspend(dev); |
| 705 | 701 | drm->dev_private = NULL; |
| 706 | 702 | dev_set_drvdata(dev, NULL); |
| 707 | − drm_dev_unref(drm); | |
| 703 | + drm_dev_put(drm); | |
| 708 | 704 | of_reserved_mem_device_release(dev); |
| 709 | 705 | } |
| 710 | 706 | |
| @@ -183,7 +183,7 @@ static void malidp500_enter_config_mode(struct malidp_hw_device *hwdev) · 182 unmodified lines | ||
| 183 | 183 | |
| 184 | 184 | malidp_hw_setbits(hwdev, MALIDP500_DC_CONFIG_REQ, MALIDP500_DC_CONTROL); |
| 185 | 185 | while (count) { |
| 186 | − status = malidp_hw_read(hwdev, hwdev->map.dc_base + MALIDP_REG_STATUS); | |
| 186 | + status = malidp_hw_read(hwdev, hwdev->hw->map.dc_base + MALIDP_REG_STATUS); | |
| 187 | 187 | if ((status & MALIDP500_DC_CONFIG_REQ) == MALIDP500_DC_CONFIG_REQ) |
| 188 | 188 | break; |
| 189 | 189 | /* |
| @@ -203,7 +203,7 @@ static void malidp500_leave_config_mode(struct malidp_hw_device *hwdev) · 13 unmodified lines | ||
| 203 | 203 | malidp_hw_clearbits(hwdev, MALIDP_CFG_VALID, MALIDP500_CONFIG_VALID); |
| 204 | 204 | malidp_hw_clearbits(hwdev, MALIDP500_DC_CONFIG_REQ, MALIDP500_DC_CONTROL); |
| 205 | 205 | while (count) { |
| 206 | − status = malidp_hw_read(hwdev, hwdev->map.dc_base + MALIDP_REG_STATUS); | |
| 206 | + status = malidp_hw_read(hwdev, hwdev->hw->map.dc_base + MALIDP_REG_STATUS); | |
| 207 | 207 | if ((status & MALIDP500_DC_CONFIG_REQ) == 0) |
| 208 | 208 | break; |
| 209 | 209 | usleep_range(100, 1000); |
| @@ -216,7 +216,7 @@ static bool malidp500_in_config_mode(struct malidp_hw_device *hwdev) · 6 unmodified lines | ||
| 216 | 216 | { |
| 217 | 217 | u32 status; |
| 218 | 218 | |
| 219 | − status = malidp_hw_read(hwdev, hwdev->map.dc_base + MALIDP_REG_STATUS); | |
| 219 | + status = malidp_hw_read(hwdev, hwdev->hw->map.dc_base + MALIDP_REG_STATUS); | |
| 220 | 220 | if ((status & MALIDP500_DC_CONFIG_REQ) == MALIDP500_DC_CONFIG_REQ) |
| 221 | 221 | return true; |
| 222 | 222 | |
| @@ -407,7 +407,7 @@ static void malidp550_enter_config_mode(struct malidp_hw_device *hwdev) · 184 unmodified lines | ||
| 407 | 407 | |
| 408 | 408 | malidp_hw_setbits(hwdev, MALIDP550_DC_CONFIG_REQ, MALIDP550_DC_CONTROL); |
| 409 | 409 | while (count) { |
| 410 | − status = malidp_hw_read(hwdev, hwdev->map.dc_base + MALIDP_REG_STATUS); | |
| 410 | + status = malidp_hw_read(hwdev, hwdev->hw->map.dc_base + MALIDP_REG_STATUS); | |
| 411 | 411 | if ((status & MALIDP550_DC_CONFIG_REQ) == MALIDP550_DC_CONFIG_REQ) |
| 412 | 412 | break; |
| 413 | 413 | /* |
| @@ -427,7 +427,7 @@ static void malidp550_leave_config_mode(struct malidp_hw_device *hwdev) · 13 unmodified lines | ||
| 427 | 427 | malidp_hw_clearbits(hwdev, MALIDP_CFG_VALID, MALIDP550_CONFIG_VALID); |
| 428 | 428 | malidp_hw_clearbits(hwdev, MALIDP550_DC_CONFIG_REQ, MALIDP550_DC_CONTROL); |
| 429 | 429 | while (count) { |
| 430 | − status = malidp_hw_read(hwdev, hwdev->map.dc_base + MALIDP_REG_STATUS); | |
| 430 | + status = malidp_hw_read(hwdev, hwdev->hw->map.dc_base + MALIDP_REG_STATUS); | |
| 431 | 431 | if ((status & MALIDP550_DC_CONFIG_REQ) == 0) |
| 432 | 432 | break; |
| 433 | 433 | usleep_range(100, 1000); |
| @@ -440,7 +440,7 @@ static bool malidp550_in_config_mode(struct malidp_hw_device *hwdev) · 6 unmodified lines | ||
| 440 | 440 | { |
| 441 | 441 | u32 status; |
| 442 | 442 | |
| 443 | − status = malidp_hw_read(hwdev, hwdev->map.dc_base + MALIDP_REG_STATUS); | |
| 443 | + status = malidp_hw_read(hwdev, hwdev->hw->map.dc_base + MALIDP_REG_STATUS); | |
| 444 | 444 | if ((status & MALIDP550_DC_CONFIG_REQ) == MALIDP550_DC_CONFIG_REQ) |
| 445 | 445 | return true; |
| 446 | 446 | |
| @@ -616,7 +616,7 @@ static int malidp650_query_hw(struct malidp_hw_device *hwdev) · 169 unmodified lines | ||
| 616 | 616 | return 0; |
| 617 | 617 | } |
| 618 | 618 | |
| 619 | −const struct malidp_hw_device malidp_device[MALIDP_MAX_DEVICES] = { | |
| 619 | +const struct malidp_hw malidp_device[MALIDP_MAX_DEVICES] = { | |
| 620 | 620 | [MALIDP_500] = { |
| 621 | 621 | .map = { |
| 622 | 622 | .coeffs_base = MALIDP500_COEFFS_BASE, |
| @@ -751,7 +751,7 @@ static void malidp_hw_clear_irq(struct malidp_hw_device *hwdev, u8 block, u32 ir · 128 unmodified lines | ||
| 751 | 751 | { |
| 752 | 752 | u32 base = malidp_get_block_base(hwdev, block); |
| 753 | 753 | |
| 754 | − if (hwdev->map.features & MALIDP_REGMAP_HAS_CLEARIRQ) | |
| 754 | + if (hwdev->hw->map.features & MALIDP_REGMAP_HAS_CLEARIRQ) | |
| 755 | 755 | malidp_hw_write(hwdev, irq, base + MALIDP_REG_CLEARIRQ); |
| 756 | 756 | else |
| 757 | 757 | malidp_hw_write(hwdev, irq, base + MALIDP_REG_STATUS); |
| @@ -762,12 +762,14 @@ static irqreturn_t malidp_de_irq(int irq, void *arg) · 4 unmodified lines | ||
| 762 | 762 | struct drm_device *drm = arg; |
| 763 | 763 | struct malidp_drm *malidp = drm->dev_private; |
| 764 | 764 | struct malidp_hw_device *hwdev; |
| 765 | + struct malidp_hw *hw; | |
| 765 | 766 | const struct malidp_irq_map *de; |
| 766 | 767 | u32 status, mask, dc_status; |
| 767 | 768 | irqreturn_t ret = IRQ_NONE; |
| 768 | 769 | |
| 769 | 770 | hwdev = malidp->dev; |
| 770 | − de = &hwdev->map.de_irq_map; | |
| 771 | + hw = hwdev->hw; | |
| 772 | + de = &hw->map.de_irq_map; | |
| 771 | 773 | |
| 772 | 774 | /* |
| 773 | 775 | * if we are suspended it is likely that we were invoked because |
| @@ -778,8 +780,8 @@ static irqreturn_t malidp_de_irq(int irq, void *arg) · 4 unmodified lines | ||
| 778 | 780 | return IRQ_NONE; |
| 779 | 781 | |
| 780 | 782 | /* first handle the config valid IRQ */ |
| 781 | − dc_status = malidp_hw_read(hwdev, hwdev->map.dc_base + MALIDP_REG_STATUS); | |
| 782 | − if (dc_status & hwdev->map.dc_irq_map.vsync_irq) { | |
| 783 | + dc_status = malidp_hw_read(hwdev, hw->map.dc_base + MALIDP_REG_STATUS); | |
| 784 | + if (dc_status & hw->map.dc_irq_map.vsync_irq) { | |
| 783 | 785 | /* we have a page flip event */ |
| 784 | 786 | atomic_set(&malidp->config_valid, 1); |
| 785 | 787 | malidp_hw_clear_irq(hwdev, MALIDP_DC_BLOCK, dc_status); |
| @@ -832,11 +834,11 @@ int malidp_de_irq_init(struct drm_device *drm, int irq) · 46 unmodified lines | ||
| 832 | 834 | |
| 833 | 835 | /* first enable the DC block IRQs */ |
| 834 | 836 | malidp_hw_enable_irq(hwdev, MALIDP_DC_BLOCK, |
| 835 | − hwdev->map.dc_irq_map.irq_mask); | |
| 837 | + hwdev->hw->map.dc_irq_map.irq_mask); | |
| 836 | 838 | |
| 837 | 839 | /* now enable the DE block IRQs */ |
| 838 | 840 | malidp_hw_enable_irq(hwdev, MALIDP_DE_BLOCK, |
| 839 | − hwdev->map.de_irq_map.irq_mask); | |
| 841 | + hwdev->hw->map.de_irq_map.irq_mask); | |
| 840 | 842 | |
| 841 | 843 | return 0; |
| 842 | 844 | } |
| @@ -847,9 +849,9 @@ void malidp_de_irq_fini(struct drm_device *drm) · 4 unmodified lines | ||
| 847 | 849 | struct malidp_hw_device *hwdev = malidp->dev; |
| 848 | 850 | |
| 849 | 851 | malidp_hw_disable_irq(hwdev, MALIDP_DE_BLOCK, |
| 850 | − hwdev->map.de_irq_map.irq_mask); | |
| 852 | + hwdev->hw->map.de_irq_map.irq_mask); | |
| 851 | 853 | malidp_hw_disable_irq(hwdev, MALIDP_DC_BLOCK, |
| 852 | − hwdev->map.dc_irq_map.irq_mask); | |
| 854 | + hwdev->hw->map.dc_irq_map.irq_mask); | |
| 853 | 855 | } |
| 854 | 856 | |
| 855 | 857 | static irqreturn_t malidp_se_irq(int irq, void *arg) |
| @@ -857,6 +859,8 @@ static irqreturn_t malidp_se_irq(int irq, void *arg) · 1 unmodified line | ||
| 857 | 859 | struct drm_device *drm = arg; |
| 858 | 860 | struct malidp_drm *malidp = drm->dev_private; |
| 859 | 861 | struct malidp_hw_device *hwdev = malidp->dev; |
| 862 | + struct malidp_hw *hw = hwdev->hw; | |
| 863 | + const struct malidp_irq_map *se = &hw->map.se_irq_map; | |
| 860 | 864 | u32 status, mask; |
| 861 | 865 | |
| 862 | 866 | /* |
| @@ -867,12 +871,12 @@ static irqreturn_t malidp_se_irq(int irq, void *arg) · 4 unmodified lines | ||
| 867 | 871 | if (hwdev->pm_suspended) |
| 868 | 872 | return IRQ_NONE; |
| 869 | 873 | |
| 870 | − status = malidp_hw_read(hwdev, hwdev->map.se_base + MALIDP_REG_STATUS); | |
| 871 | − if (!(status & hwdev->map.se_irq_map.irq_mask)) | |
| 874 | + status = malidp_hw_read(hwdev, hw->map.se_base + MALIDP_REG_STATUS); | |
| 875 | + if (!(status & se->irq_mask)) | |
| 872 | 876 | return IRQ_NONE; |
| 873 | 877 | |
| 874 | − mask = malidp_hw_read(hwdev, hwdev->map.se_base + MALIDP_REG_MASKIRQ); | |
| 875 | − status = malidp_hw_read(hwdev, hwdev->map.se_base + MALIDP_REG_STATUS); | |
| 878 | + mask = malidp_hw_read(hwdev, hw->map.se_base + MALIDP_REG_MASKIRQ); | |
| 879 | + status = malidp_hw_read(hwdev, hw->map.se_base + MALIDP_REG_STATUS); | |
| 876 | 880 | status &= mask; |
| 877 | 881 | /* ToDo: status decoding and firing up of VSYNC and page flip events */ |
| 878 | 882 | |
| @@ -905,7 +909,7 @@ int malidp_se_irq_init(struct drm_device *drm, int irq) · 26 unmodified lines | ||
| 905 | 909 | } |
| 906 | 910 | |
| 907 | 911 | malidp_hw_enable_irq(hwdev, MALIDP_SE_BLOCK, |
| 908 | − hwdev->map.se_irq_map.irq_mask); | |
| 912 | + hwdev->hw->map.se_irq_map.irq_mask); | |
| 909 | 913 | |
| 910 | 914 | return 0; |
| 911 | 915 | } |
| @@ -916,5 +920,5 @@ void malidp_se_irq_fini(struct drm_device *drm) · 4 unmodified lines | ||
| 916 | 920 | struct malidp_hw_device *hwdev = malidp->dev; |
| 917 | 921 | |
| 918 | 922 | malidp_hw_disable_irq(hwdev, MALIDP_SE_BLOCK, |
| 919 | − hwdev->map.se_irq_map.irq_mask); | |
| 923 | + hwdev->hw->map.se_irq_map.irq_mask); | |
| 920 | 924 | } |
| @@ -120,18 +120,14 @@ struct malidp_hw_regmap { · 119 unmodified lines | ||
| 120 | 120 | /* Unlike DP550/650, DP500 has 3 stride registers in its video layer. */ |
| 121 | 121 | #define MALIDP_DEVICE_LV_HAS_3_STRIDES BIT(0) |
| 122 | 122 | |
| 123 | −struct malidp_hw_device { | |
| 124 | − const struct malidp_hw_regmap map; | |
| 125 | − void __iomem *regs; | |
| 123 | +struct malidp_hw_device; | |
| 126 | 124 | |
| 127 | − /* APB clock */ | |
| 128 | − struct clk *pclk; | |
| 129 | − /* AXI clock */ | |
| 130 | − struct clk *aclk; | |
| 131 | − /* main clock for display core */ | |
| 132 | − struct clk *mclk; | |
| 133 | − /* pixel clock for display core */ | |
| 134 | − struct clk *pxlclk; | |
| 125 | +/* | |
| 126 | + * Static structure containing hardware specific data and pointers to | |
| 127 | + * functions that behave differently between various versions of the IP. | |
| 128 | + */ | |
| 129 | +struct malidp_hw { | |
| 130 | + const struct malidp_hw_regmap map; | |
| 135 | 131 | |
| 136 | 132 | /* |
| 137 | 133 | * Validate the driver instance against the hardware bits |
| @@ -182,15 +178,6 @@ struct malidp_hw_device { · 44 unmodified lines | ||
| 182 | 178 | struct videomode *vm); |
| 183 | 179 | |
| 184 | 180 | u8 features; |
| 185 | − | |
| 186 | − u8 min_line_size; | |
| 187 | − u16 max_line_size; | |
| 188 | − | |
| 189 | − /* track the device PM state */ | |
| 190 | − bool pm_suspended; | |
| 191 | − | |
| 192 | − /* size of memory used for rotating layers, up to two banks available */ | |
| 193 | − u32 rotation_memory[2]; | |
| 194 | 181 | }; |
| 195 | 182 | |
| 196 | 183 | /* Supported variants of the hardware */ |
| @@ -202,7 +189,33 @@ enum { · 5 unmodified lines | ||
| 202 | 189 | MALIDP_MAX_DEVICES |
| 203 | 190 | }; |
| 204 | 191 | |
| 205 | −extern const struct malidp_hw_device malidp_device[MALIDP_MAX_DEVICES]; | |
| 192 | +extern const struct malidp_hw malidp_device[MALIDP_MAX_DEVICES]; | |
| 193 | + | |
| 194 | +/* | |
| 195 | + * Structure used by the driver during runtime operation. | |
| 196 | + */ | |
| 197 | +struct malidp_hw_device { | |
| 198 | + struct malidp_hw *hw; | |
| 199 | + void __iomem *regs; | |
| 200 | + | |
| 201 | + /* APB clock */ | |
| 202 | + struct clk *pclk; | |
| 203 | + /* AXI clock */ | |
| 204 | + struct clk *aclk; | |
| 205 | + /* main clock for display core */ | |
| 206 | + struct clk *mclk; | |
| 207 | + /* pixel clock for display core */ | |
| 208 | + struct clk *pxlclk; | |
| 209 | + | |
| 210 | + u8 min_line_size; | |
| 211 | + u16 max_line_size; | |
| 212 | + | |
| 213 | + /* track the device PM state */ | |
| 214 | + bool pm_suspended; | |
| 215 | + | |
| 216 | + /* size of memory used for rotating layers, up to two banks available */ | |
| 217 | + u32 rotation_memory[2]; | |
| 218 | +}; | |
| 206 | 219 | |
| 207 | 220 | static inline u32 malidp_hw_read(struct malidp_hw_device *hwdev, u32 reg) |
| 208 | 221 | { |
| @@ -240,9 +253,9 @@ static inline u32 malidp_get_block_base(struct malidp_hw_device *hwdev, · 31 unmodified lines | ||
| 240 | 253 | { |
| 241 | 254 | switch (block) { |
| 242 | 255 | case MALIDP_SE_BLOCK: |
| 243 | − return hwdev->map.se_base; | |
| 256 | + return hwdev->hw->map.se_base; | |
| 244 | 257 | case MALIDP_DC_BLOCK: |
| 245 | − return hwdev->map.dc_base; | |
| 258 | + return hwdev->hw->map.dc_base; | |
| 246 | 259 | } |
| 247 | 260 | |
| 248 | 261 | return 0; |
| @@ -275,7 +288,7 @@ u8 malidp_hw_get_format_id(const struct malidp_hw_regmap *map, · 26 unmodified lines | ||
| 275 | 288 | static inline bool malidp_hw_pitch_valid(struct malidp_hw_device *hwdev, |
| 276 | 289 | unsigned int pitch) |
| 277 | 290 | { |
| 278 | − return !(pitch & (hwdev->map.bus_align_bytes - 1)); | |
| 291 | + return !(pitch & (hwdev->hw->map.bus_align_bytes - 1)); | |
| 279 | 292 | } |
| 280 | 293 | |
| 281 | 294 | /* U16.16 */ |
| @@ -308,8 +321,8 @@ static inline void malidp_se_set_enh_coeffs(struct malidp_hw_device *hwdev) · 26 unmodified lines | ||
| 308 | 321 | }; |
| 309 | 322 | u32 val = MALIDP_SE_SET_ENH_LIMIT_LOW(MALIDP_SE_ENH_LOW_LEVEL) | |
| 310 | 323 | MALIDP_SE_SET_ENH_LIMIT_HIGH(MALIDP_SE_ENH_HIGH_LEVEL); |
| 311 | − u32 image_enh = hwdev->map.se_base + | |
| 312 | − ((hwdev->map.features & MALIDP_REGMAP_HAS_CLEARIRQ) ? | |
| 324 | + u32 image_enh = hwdev->hw->map.se_base + | |
| 325 | + ((hwdev->hw->map.features & MALIDP_REGMAP_HAS_CLEARIRQ) ? | |
| 313 | 326 | 0x10 : 0xC) + MALIDP_SE_IMAGE_ENH; |
| 314 | 327 | u32 enh_coeffs = image_enh + MALIDP_SE_ENH_COEFF0; |
| 315 | 328 | int i; |
| @@ -57,7 +57,7 @@ static void malidp_de_plane_destroy(struct drm_plane *plane) · 56 unmodified lines | ||
| 57 | 57 | struct malidp_plane *mp = to_malidp_plane(plane); |
| 58 | 58 | |
| 59 | 59 | if (mp->base.fb) |
| 60 | − drm_framebuffer_unreference(mp->base.fb); | |
| 60 | + drm_framebuffer_put(mp->base.fb); | |
| 61 | 61 | |
| 62 | 62 | drm_plane_helper_disable(plane); |
| 63 | 63 | drm_plane_cleanup(plane); |
| @@ -185,8 +185,9 @@ static int malidp_de_plane_check(struct drm_plane *plane, · 121 unmodified lines | ||
| 185 | 185 | |
| 186 | 186 | fb = state->fb; |
| 187 | 187 | |
| 188 | − ms->format = malidp_hw_get_format_id(&mp->hwdev->map, mp->layer->id, | |
| 189 | − fb->format->format); | |
| 188 | + ms->format = malidp_hw_get_format_id(&mp->hwdev->hw->map, | |
| 189 | + mp->layer->id, | |
| 190 | + fb->format->format); | |
| 190 | 191 | if (ms->format == MALIDP_INVALID_FORMAT_ID) |
| 191 | 192 | return -EINVAL; |
| 192 | 193 | |
| @@ -211,7 +212,7 @@ static int malidp_de_plane_check(struct drm_plane *plane, · 18 unmodified lines | ||
| 211 | 212 | * third plane stride register. |
| 212 | 213 | */ |
| 213 | 214 | if (ms->n_planes == 3 && |
| 214 | − !(mp->hwdev->features & MALIDP_DEVICE_LV_HAS_3_STRIDES) && | |
| 215 | + !(mp->hwdev->hw->features & MALIDP_DEVICE_LV_HAS_3_STRIDES) && | |
| 215 | 216 | (state->fb->pitches[1] != state->fb->pitches[2])) |
| 216 | 217 | return -EINVAL; |
| 217 | 218 | |
| @@ -229,9 +230,9 @@ static int malidp_de_plane_check(struct drm_plane *plane, · 11 unmodified lines | ||
| 229 | 230 | if (state->rotation & MALIDP_ROTATED_MASK) { |
| 230 | 231 | int val; |
| 231 | 232 | |
| 232 | − val = mp->hwdev->rotmem_required(mp->hwdev, state->crtc_h, | |
| 233 | − state->crtc_w, | |
| 234 | − fb->format->format); | |
| 233 | + val = mp->hwdev->hw->rotmem_required(mp->hwdev, state->crtc_h, | |
| 234 | + state->crtc_w, | |
| 235 | + fb->format->format); | |
| 235 | 236 | if (val < 0) |
| 236 | 237 | return val; |
| 237 | 238 | |
| @@ -251,7 +252,7 @@ static void malidp_de_set_plane_pitches(struct malidp_plane *mp, · 13 unmodified lines | ||
| 251 | 252 | return; |
| 252 | 253 | |
| 253 | 254 | if (num_planes == 3) |
| 254 | − num_strides = (mp->hwdev->features & | |
| 255 | + num_strides = (mp->hwdev->hw->features & | |
| 255 | 256 | MALIDP_DEVICE_LV_HAS_3_STRIDES) ? 3 : 2; |
| 256 | 257 | |
| 257 | 258 | for (i = 0; i < num_strides; ++i) |
| @@ -264,13 +265,11 @@ static void malidp_de_plane_update(struct drm_plane *plane, · 6 unmodified lines | ||
| 264 | 265 | struct drm_plane_state *old_state) |
| 265 | 266 | { |
| 266 | 267 | struct malidp_plane *mp; |
| 267 | − const struct malidp_hw_regmap *map; | |
| 268 | 268 | struct malidp_plane_state *ms = to_malidp_plane_state(plane->state); |
| 269 | 269 | u32 src_w, src_h, dest_w, dest_h, val; |
| 270 | 270 | int i; |
| 271 | 271 | |
| 272 | 272 | mp = to_malidp_plane(plane); |
| 273 | − map = &mp->hwdev->map; | |
| 274 | 273 | |
| 275 | 274 | /* convert src values from Q16 fixed point to integer */ |
| 276 | 275 | src_w = plane->state->src_w >> 16; |
| @@ -363,7 +362,7 @@ static const struct drm_plane_helper_funcs malidp_de_plane_helper_funcs = { · 86 unmodified lines | ||
| 363 | 362 | int malidp_de_planes_init(struct drm_device *drm) |
| 364 | 363 | { |
| 365 | 364 | struct malidp_drm *malidp = drm->dev_private; |
| 366 | − const struct malidp_hw_regmap *map = &malidp->dev->map; | |
| 365 | + const struct malidp_hw_regmap *map = &malidp->dev->hw->map; | |
| 367 | 366 | struct malidp_plane *plane = NULL; |
| 368 | 367 | enum drm_plane_type plane_type; |
| 369 | 368 | unsigned long crtcs = 1 << drm->mode_config.num_crtc; |
| @@ -372,9 +372,18 @@ struct adv7511 { · 371 unmodified lines | ||
| 372 | 372 | }; |
| 373 | 373 | |
| 374 | 374 | #ifdef CONFIG_DRM_I2C_ADV7511_CEC |
| 375 | −int adv7511_cec_init(struct device *dev, struct adv7511 *adv7511, | |
| 376 | − unsigned int offset); | |
| 375 | +int adv7511_cec_init(struct device *dev, struct adv7511 *adv7511); | |
| 377 | 376 | void adv7511_cec_irq_process(struct adv7511 *adv7511, unsigned int irq1); |
| 377 | +#else | |
| 378 | +static inline int adv7511_cec_init(struct device *dev, struct adv7511 *adv7511) | |
| 379 | +{ | |
| 380 | + unsigned int offset = adv7511->type == ADV7533 ? | |
| 381 | + ADV7533_REG_CEC_OFFSET : 0; | |
| 382 | + | |
| 383 | + regmap_write(adv7511->regmap, ADV7511_REG_CEC_CTRL + offset, | |
| 384 | + ADV7511_CEC_CTRL_POWER_DOWN); | |
| 385 | + return 0; | |
| 386 | +} | |
| 378 | 387 | #endif |
| 379 | 388 | |
| 380 | 389 | #ifdef CONFIG_DRM_I2C_ADV7533 |
| @@ -300,18 +300,21 @@ static int adv7511_cec_parse_dt(struct device *dev, struct adv7511 *adv7511) · 299 unmodified lines | ||
| 300 | 300 | return 0; |
| 301 | 301 | } |
| 302 | 302 | |
| 303 | −int adv7511_cec_init(struct device *dev, struct adv7511 *adv7511, | |
| 304 | − unsigned int offset) | |
| 303 | +int adv7511_cec_init(struct device *dev, struct adv7511 *adv7511) | |
| 305 | 304 | { |
| 305 | + unsigned int offset = adv7511->type == ADV7533 ? | |
| 306 | + ADV7533_REG_CEC_OFFSET : 0; | |
| 306 | 307 | int ret = adv7511_cec_parse_dt(dev, adv7511); |
| 307 | 308 | |
| 308 | 309 | if (ret) |
| 309 | − return ret; | |
| 310 | + goto err_cec_parse_dt; | |
| 310 | 311 | |
| 311 | 312 | adv7511->cec_adap = cec_allocate_adapter(&adv7511_cec_adap_ops, |
| 312 | 313 | adv7511, dev_name(dev), CEC_CAP_DEFAULTS, ADV7511_MAX_ADDRS); |
| 313 | − if (IS_ERR(adv7511->cec_adap)) | |
| 314 | − return PTR_ERR(adv7511->cec_adap); | |
| 314 | + if (IS_ERR(adv7511->cec_adap)) { | |
| 315 | + ret = PTR_ERR(adv7511->cec_adap); | |
| 316 | + goto err_cec_alloc; | |
| 317 | + } | |
| 315 | 318 | |
| 316 | 319 | regmap_write(adv7511->regmap, ADV7511_REG_CEC_CTRL + offset, 0); |
| 317 | 320 | /* cec soft reset */ |
| @@ -329,9 +332,18 @@ int adv7511_cec_init(struct device *dev, struct adv7511 *adv7511, · 11 unmodified lines | ||
| 329 | 332 | ((adv7511->cec_clk_freq / 750000) - 1) << 2); |
| 330 | 333 | |
| 331 | 334 | ret = cec_register_adapter(adv7511->cec_adap, dev); |
| 332 | − if (ret) { | |
| 333 | − cec_delete_adapter(adv7511->cec_adap); | |
| 334 | − adv7511->cec_adap = NULL; | |
| 335 | − } | |
| 336 | − return ret; | |
| 335 | + if (ret) | |
| 336 | + goto err_cec_register; | |
| 337 | + return 0; | |
| 338 | + | |
| 339 | +err_cec_register: | |
| 340 | + cec_delete_adapter(adv7511->cec_adap); | |
| 341 | + adv7511->cec_adap = NULL; | |
| 342 | +err_cec_alloc: | |
| 343 | + dev_info(dev, "Initializing CEC failed with error %d, disabling CEC\n", | |
| 344 | + ret); | |
| 345 | +err_cec_parse_dt: | |
| 346 | + regmap_write(adv7511->regmap, ADV7511_REG_CEC_CTRL + offset, | |
| 347 | + ADV7511_CEC_CTRL_POWER_DOWN); | |
| 348 | + return ret == -EPROBE_DEFER ? ret : 0; | |
| 337 | 349 | } |
| @@ -1084,7 +1084,6 @@ static int adv7511_probe(struct i2c_client *i2c, const struct i2c_device_id *id) · 1083 unmodified lines | ||
| 1084 | 1084 | struct device *dev = &i2c->dev; |
| 1085 | 1085 | unsigned int main_i2c_addr = i2c->addr << 1; |
| 1086 | 1086 | unsigned int edid_i2c_addr = main_i2c_addr + 4; |
| 1087 | − unsigned int offset; | |
| 1088 | 1087 | unsigned int val; |
| 1089 | 1088 | int ret; |
| 1090 | 1089 | |
| @@ -1192,24 +1191,16 @@ static int adv7511_probe(struct i2c_client *i2c, const struct i2c_device_id *id) · 101 unmodified lines | ||
| 1192 | 1191 | if (adv7511->type == ADV7511) |
| 1193 | 1192 | adv7511_set_link_config(adv7511, &link_config); |
| 1194 | 1193 | |
| 1194 | + ret = adv7511_cec_init(dev, adv7511); | |
| 1195 | + if (ret) | |
| 1196 | + goto err_unregister_cec; | |
| 1197 | + | |
| 1195 | 1198 | adv7511->bridge.funcs = &adv7511_bridge_funcs; |
| 1196 | 1199 | adv7511->bridge.of_node = dev->of_node; |
| 1197 | 1200 | |
| 1198 | 1201 | drm_bridge_add(&adv7511->bridge); |
| 1199 | 1202 | |
| 1200 | 1203 | adv7511_audio_init(dev, adv7511); |
| 1201 | − | |
| 1202 | − offset = adv7511->type == ADV7533 ? ADV7533_REG_CEC_OFFSET : 0; | |
| 1203 | − | |
| 1204 | −#ifdef CONFIG_DRM_I2C_ADV7511_CEC | |
| 1205 | − ret = adv7511_cec_init(dev, adv7511, offset); | |
| 1206 | − if (ret) | |
| 1207 | − goto err_unregister_cec; | |
| 1208 | −#else | |
| 1209 | − regmap_write(adv7511->regmap, ADV7511_REG_CEC_CTRL + offset, | |
| 1210 | − ADV7511_CEC_CTRL_POWER_DOWN); | |
| 1211 | −#endif | |
| 1212 | − | |
| 1213 | 1204 | return 0; |
| 1214 | 1205 | |
| 1215 | 1206 | err_unregister_cec: |
| @@ -13,13 +13,37 @@ · 12 unmodified lines | ||
| 13 | 13 | |
| 14 | 14 | #include <linux/of_graph.h> |
| 15 | 15 | |
| 16 | +struct lvds_encoder { | |
| 17 | + struct drm_bridge bridge; | |
| 18 | + struct drm_bridge *panel_bridge; | |
| 19 | +}; | |
| 20 | + | |
| 21 | +static int lvds_encoder_attach(struct drm_bridge *bridge) | |
| 22 | +{ | |
| 23 | + struct lvds_encoder *lvds_encoder = container_of(bridge, | |
| 24 | + struct lvds_encoder, | |
| 25 | + bridge); | |
| 26 | + | |
| 27 | + return drm_bridge_attach(bridge->encoder, lvds_encoder->panel_bridge, | |
| 28 | + bridge); | |
| 29 | +} | |
| 30 | + | |
| 31 | +static struct drm_bridge_funcs funcs = { | |
| 32 | + .attach = lvds_encoder_attach, | |
| 33 | +}; | |
| 34 | + | |
| 16 | 35 | static int lvds_encoder_probe(struct platform_device *pdev) |
| 17 | 36 | { |
| 18 | 37 | struct device_node *port; |
| 19 | 38 | struct device_node *endpoint; |
| 20 | 39 | struct device_node *panel_node; |
| 21 | 40 | struct drm_panel *panel; |
| 22 | − struct drm_bridge *bridge; | |
| 41 | + struct lvds_encoder *lvds_encoder; | |
| 42 | + | |
| 43 | + lvds_encoder = devm_kzalloc(&pdev->dev, sizeof(*lvds_encoder), | |
| 44 | + GFP_KERNEL); | |
| 45 | + if (!lvds_encoder) | |
| 46 | + return -ENOMEM; | |
| 23 | 47 | |
| 24 | 48 | /* Locate the panel DT node. */ |
| 25 | 49 | port = of_graph_get_port_by_id(pdev->dev.of_node, 1); |
| @@ -49,20 +73,30 @@ static int lvds_encoder_probe(struct platform_device *pdev) · 23 unmodified lines | ||
| 49 | 73 | return -EPROBE_DEFER; |
| 50 | 74 | } |
| 51 | 75 | |
| 52 | − bridge = drm_panel_bridge_add(panel, DRM_MODE_CONNECTOR_LVDS); | |
| 53 | − if (IS_ERR(bridge)) | |
| 54 | − return PTR_ERR(bridge); | |
| 76 | + lvds_encoder->panel_bridge = | |
| 77 | + devm_drm_panel_bridge_add(&pdev->dev, | |
| 78 | + panel, DRM_MODE_CONNECTOR_LVDS); | |
| 79 | + if (IS_ERR(lvds_encoder->panel_bridge)) | |
| 80 | + return PTR_ERR(lvds_encoder->panel_bridge); | |
| 81 | + | |
| 82 | + /* The panel_bridge bridge is attached to the panel's of_node, | |
| 83 | + * but we need a bridge attached to our of_node for our user | |
| 84 | + * to look up. | |
| 85 | + */ | |
| 86 | + lvds_encoder->bridge.of_node = pdev->dev.of_node; | |
| 87 | + lvds_encoder->bridge.funcs = &funcs; | |
| 88 | + drm_bridge_add(&lvds_encoder->bridge); | |
| 55 | 89 | |
| 56 | − platform_set_drvdata(pdev, bridge); | |
| 90 | + platform_set_drvdata(pdev, lvds_encoder); | |
| 57 | 91 | |
| 58 | 92 | return 0; |
| 59 | 93 | } |
| 60 | 94 | |
| 61 | 95 | static int lvds_encoder_remove(struct platform_device *pdev) |
| 62 | 96 | { |
| 63 | − struct drm_bridge *bridge = platform_get_drvdata(pdev); | |
| 97 | + struct lvds_encoder *lvds_encoder = platform_get_drvdata(pdev); | |
| 64 | 98 | |
| 65 | − drm_bridge_remove(bridge); | |
| 99 | + drm_bridge_remove(&lvds_encoder->bridge); | |
| 66 | 100 | |
| 67 | 101 | return 0; |
| 68 | 102 | } |
| @@ -138,6 +138,7 @@ struct dw_hdmi { · 137 unmodified lines | ||
| 138 | 138 | struct device *dev; |
| 139 | 139 | struct clk *isfr_clk; |
| 140 | 140 | struct clk *iahb_clk; |
| 141 | + struct clk *cec_clk; | |
| 141 | 142 | struct dw_hdmi_i2c *i2c; |
| 142 | 143 | |
| 143 | 144 | struct hdmi_data_info hdmi_data; |
| @@ -2382,6 +2383,26 @@ __dw_hdmi_probe(struct platform_device *pdev, · 2238 unmodified lines | ||
| 2382 | 2383 | goto err_isfr; |
| 2383 | 2384 | } |
| 2384 | 2385 | |
| 2386 | + hdmi->cec_clk = devm_clk_get(hdmi->dev, "cec"); | |
| 2387 | + if (PTR_ERR(hdmi->cec_clk) == -ENOENT) { | |
| 2388 | + hdmi->cec_clk = NULL; | |
| 2389 | + } else if (IS_ERR(hdmi->cec_clk)) { | |
| 2390 | + ret = PTR_ERR(hdmi->cec_clk); | |
| 2391 | + if (ret != -EPROBE_DEFER) | |
| 2392 | + dev_err(hdmi->dev, "Cannot get HDMI cec clock: %d\n", | |
| 2393 | + ret); | |
| 2394 | + | |
| 2395 | + hdmi->cec_clk = NULL; | |
| 2396 | + goto err_iahb; | |
| 2397 | + } else { | |
| 2398 | + ret = clk_prepare_enable(hdmi->cec_clk); | |
| 2399 | + if (ret) { | |
| 2400 | + dev_err(hdmi->dev, "Cannot enable HDMI cec clock: %d\n", | |
| 2401 | + ret); | |
| 2402 | + goto err_iahb; | |
| 2403 | + } | |
| 2404 | + } | |
| 2405 | + | |
| 2385 | 2406 | /* Product and revision IDs */ |
| 2386 | 2407 | hdmi->version = (hdmi_readb(hdmi, HDMI_DESIGN_ID) << 8) |
| 2387 | 2408 | | (hdmi_readb(hdmi, HDMI_REVISION_ID) << 0); |
| @@ -2518,6 +2539,8 @@ err_iahb: · 130 unmodified lines | ||
| 2518 | 2539 | cec_notifier_put(hdmi->cec_notifier); |
| 2519 | 2540 | |
| 2520 | 2541 | clk_disable_unprepare(hdmi->iahb_clk); |
| 2542 | + if (hdmi->cec_clk) | |
| 2543 | + clk_disable_unprepare(hdmi->cec_clk); | |
| 2521 | 2544 | err_isfr: |
| 2522 | 2545 | clk_disable_unprepare(hdmi->isfr_clk); |
| 2523 | 2546 | err_res: |
| @@ -2541,6 +2564,8 @@ static void __dw_hdmi_remove(struct dw_hdmi *hdmi) · 17 unmodified lines | ||
| 2541 | 2564 | |
| 2542 | 2565 | clk_disable_unprepare(hdmi->iahb_clk); |
| 2543 | 2566 | clk_disable_unprepare(hdmi->isfr_clk); |
| 2567 | + if (hdmi->cec_clk) | |
| 2568 | + clk_disable_unprepare(hdmi->cec_clk); | |
| 2544 | 2569 | |
| 2545 | 2570 | if (hdmi->i2c) |
| 2546 | 2571 | i2c_del_adapter(&hdmi->i2c->adap); |
| @@ -97,7 +97,7 @@ · 96 unmodified lines | ||
| 97 | 97 | #define DP0_ACTIVEVAL 0x0650 |
| 98 | 98 | #define DP0_SYNCVAL 0x0654 |
| 99 | 99 | #define DP0_MISC 0x0658 |
| 100 | −#define TU_SIZE_RECOMMENDED (0x3f << 16) /* LSCLK cycles per TU */ | |
| 100 | +#define TU_SIZE_RECOMMENDED (63) /* LSCLK cycles per TU */ | |
| 101 | 101 | #define BPC_6 (0 << 5) |
| 102 | 102 | #define BPC_8 (1 << 5) |
| 103 | 103 | |
| @@ -318,7 +318,7 @@ static ssize_t tc_aux_transfer(struct drm_dp_aux *aux, · 214 unmodified lines | ||
| 318 | 318 | tmp = (tmp << 8) | buf[i]; |
| 319 | 319 | i++; |
| 320 | 320 | if (((i % 4) == 0) || (i == size)) { |
| 321 | − tc_write(DP0_AUXWDATA(i >> 2), tmp); | |
| 321 | + tc_write(DP0_AUXWDATA((i - 1) >> 2), tmp); | |
| 322 | 322 | tmp = 0; |
| 323 | 323 | } |
| 324 | 324 | } |
| @@ -603,8 +603,15 @@ static int tc_get_display_props(struct tc_data *tc) · 278 unmodified lines | ||
| 603 | 603 | ret = drm_dp_link_probe(&tc->aux, &tc->link.base); |
| 604 | 604 | if (ret < 0) |
| 605 | 605 | goto err_dpcd_read; |
| 606 | − if ((tc->link.base.rate != 162000) && (tc->link.base.rate != 270000)) | |
| 607 | − goto err_dpcd_inval; | |
| 606 | + if (tc->link.base.rate != 162000 && tc->link.base.rate != 270000) { | |
| 607 | + dev_dbg(tc->dev, "Falling to 2.7 Gbps rate\n"); | |
| 608 | + tc->link.base.rate = 270000; | |
| 609 | + } | |
| 610 | + | |
| 611 | + if (tc->link.base.num_lanes > 2) { | |
| 612 | + dev_dbg(tc->dev, "Falling to 2 lanes\n"); | |
| 613 | + tc->link.base.num_lanes = 2; | |
| 614 | + } | |
| 608 | 615 | |
| 609 | 616 | ret = drm_dp_dpcd_readb(&tc->aux, DP_MAX_DOWNSPREAD, tmp); |
| 610 | 617 | if (ret < 0) |
| @@ -637,9 +644,6 @@ static int tc_get_display_props(struct tc_data *tc) · 26 unmodified lines | ||
| 637 | 644 | err_dpcd_read: |
| 638 | 645 | dev_err(tc->dev, "failed to read DPCD: %d\n", ret); |
| 639 | 646 | return ret; |
| 640 | −err_dpcd_inval: | |
| 641 | − dev_err(tc->dev, "invalid DPCD\n"); | |
| 642 | − return -EINVAL; | |
| 643 | 647 | } |
| 644 | 648 | |
| 645 | 649 | static int tc_set_video_mode(struct tc_data *tc, struct drm_display_mode *mode) |
| @@ -655,6 +659,14 @@ static int tc_set_video_mode(struct tc_data *tc, struct drm_display_mode *mode) · 9 unmodified lines | ||
| 655 | 659 | int lower_margin = mode->vsync_start - mode->vdisplay; |
| 656 | 660 | int vsync_len = mode->vsync_end - mode->vsync_start; |
| 657 | 661 | |
| 662 | + /* | |
| 663 | + * Recommended maximum number of symbols transferred in a transfer unit: | |
| 664 | + * DIV_ROUND_UP((input active video bandwidth in bytes) * tu_size, | |
| 665 | + * (output active video bandwidth in bytes)) | |
| 666 | + * Must be less than tu_size. | |
| 667 | + */ | |
| 668 | + max_tu_symbol = TU_SIZE_RECOMMENDED - 1; | |
| 669 | + | |
| 658 | 670 | dev_dbg(tc->dev, "set mode %dx%d\n", |
| 659 | 671 | mode->hdisplay, mode->vdisplay); |
| 660 | 672 | dev_dbg(tc->dev, "H margin %d,%d sync %d\n", |
| @@ -664,13 +676,18 @@ static int tc_set_video_mode(struct tc_data *tc, struct drm_display_mode *mode) · 3 unmodified lines | ||
| 664 | 676 | dev_dbg(tc->dev, "total: %dx%d\n", mode->htotal, mode->vtotal); |
| 665 | 677 | |
| 666 | 678 | |
| 667 | − /* LCD Ctl Frame Size */ | |
| 668 | − tc_write(VPCTRL0, (0x40 << 20) /* VSDELAY */ | | |
| 679 | + /* | |
| 680 | + * LCD Ctl Frame Size | |
| 681 | + * datasheet is not clear of vsdelay in case of DPI | |
| 682 | + * assume we do not need any delay when DPI is a source of | |
| 683 | + * sync signals | |
| 684 | + */ | |
| 685 | + tc_write(VPCTRL0, (0 << 20) /* VSDELAY */ | | |
| 669 | 686 | OPXLFMT_RGB888 | FRMSYNC_DISABLED | MSF_DISABLED); |
| 670 | − tc_write(HTIM01, (left_margin << 16) | /* H back porch */ | |
| 671 | − (hsync_len << 0)); /* Hsync */ | |
| 672 | − tc_write(HTIM02, (right_margin << 16) | /* H front porch */ | |
| 673 | − (mode->hdisplay << 0)); /* width */ | |
| 687 | + tc_write(HTIM01, (ALIGN(left_margin, 2) << 16) | /* H back porch */ | |
| 688 | + (ALIGN(hsync_len, 2) << 0)); /* Hsync */ | |
| 689 | + tc_write(HTIM02, (ALIGN(right_margin, 2) << 16) | /* H front porch */ | |
| 690 | + (ALIGN(mode->hdisplay, 2) << 0)); /* width */ | |
| 674 | 691 | tc_write(VTIM01, (upper_margin << 16) | /* V back porch */ |
| 675 | 692 | (vsync_len << 0)); /* Vsync */ |
| 676 | 693 | tc_write(VTIM02, (lower_margin << 16) | /* V front porch */ |
| @@ -689,7 +706,7 @@ static int tc_set_video_mode(struct tc_data *tc, struct drm_display_mode *mode) · 12 unmodified lines | ||
| 689 | 706 | /* DP Main Stream Attributes */ |
| 690 | 707 | vid_sync_dly = hsync_len + left_margin + mode->hdisplay; |
| 691 | 708 | tc_write(DP0_VIDSYNCDELAY, |
| 692 | − (0x003e << 16) | /* thresh_dly */ | |
| 709 | + (max_tu_symbol << 16) | /* thresh_dly */ | |
| 693 | 710 | (vid_sync_dly << 0)); |
| 694 | 711 | |
| 695 | 712 | tc_write(DP0_TOTALVAL, (mode->vtotal << 16) | (mode->htotal)); |
| @@ -705,14 +722,8 @@ static int tc_set_video_mode(struct tc_data *tc, struct drm_display_mode *mode) · 9 unmodified lines | ||
| 705 | 722 | tc_write(DPIPXLFMT, VS_POL_ACTIVE_LOW | HS_POL_ACTIVE_LOW | |
| 706 | 723 | DE_POL_ACTIVE_HIGH | SUB_CFG_TYPE_CONFIG1 | DPI_BPP_RGB888); |
| 707 | 724 | |
| 708 | − /* | |
| 709 | − * Recommended maximum number of symbols transferred in a transfer unit: | |
| 710 | − * DIV_ROUND_UP((input active video bandwidth in bytes) * tu_size, | |
| 711 | − * (output active video bandwidth in bytes)) | |
| 712 | − * Must be less than tu_size. | |
| 713 | − */ | |
| 714 | − max_tu_symbol = TU_SIZE_RECOMMENDED - 1; | |
| 715 | − tc_write(DP0_MISC, (max_tu_symbol << 23) | TU_SIZE_RECOMMENDED | BPC_8); | |
| 725 | + tc_write(DP0_MISC, (max_tu_symbol << 23) | (TU_SIZE_RECOMMENDED << 16) | | |
| 726 | + BPC_8); | |
| 716 | 727 | |
| 717 | 728 | return 0; |
| 718 | 729 | err: |
| @@ -808,8 +819,6 @@ static int tc_main_link_setup(struct tc_data *tc) · 89 unmodified lines | ||
| 808 | 819 | unsigned int rate; |
| 809 | 820 | u32 dp_phy_ctrl; |
| 810 | 821 | int timeout; |
| 811 | − bool aligned; | |
| 812 | − bool ready; | |
| 813 | 822 | u32 value; |
| 814 | 823 | int ret; |
| 815 | 824 | u8 tmp[8]; |
| @@ -954,16 +963,15 @@ static int tc_main_link_setup(struct tc_data *tc) · 138 unmodified lines | ||
| 954 | 963 | ret = drm_dp_dpcd_read_link_status(aux, tmp + 2); |
| 955 | 964 | if (ret < 0) |
| 956 | 965 | goto err_dpcd_read; |
| 957 | − ready = (tmp[2] == ((DP_CHANNEL_EQ_BITS << 4) | /* Lane1 */ | |
| 958 | − DP_CHANNEL_EQ_BITS)); /* Lane0 */ | |
| 959 | − aligned = tmp[4] & DP_INTERLANE_ALIGN_DONE; | |
| 960 | − } while ((--timeout) && !(ready && aligned)); | |
| 966 | + } while ((--timeout) && | |
| 967 | + !(drm_dp_channel_eq_ok(tmp + 2, tc->link.base.num_lanes))); | |
| 961 | 968 | |
| 962 | 969 | if (timeout == 0) { |
| 963 | 970 | /* Read DPCD 0x200-0x201 */ |
| 964 | 971 | ret = drm_dp_dpcd_read(aux, DP_SINK_COUNT, tmp, 2); |
| 965 | 972 | if (ret < 0) |
| 966 | 973 | goto err_dpcd_read; |
| 974 | + dev_err(dev, "channel(s) EQ not ok\n"); | |
| 967 | 975 | dev_info(dev, "0x0200 SINK_COUNT: 0x%02x\n", tmp[0]); |
| 968 | 976 | dev_info(dev, "0x0201 DEVICE_SERVICE_IRQ_VECTOR: 0x%02x\n", |
| 969 | 977 | tmp[1]); |
| @@ -974,10 +982,6 @@ static int tc_main_link_setup(struct tc_data *tc) · 4 unmodified lines | ||
| 974 | 982 | dev_info(dev, "0x0206 ADJUST_REQUEST_LANE0_1: 0x%02x\n", |
| 975 | 983 | tmp[6]); |
| 976 | 984 | |
| 977 | − if (!ready) | |
| 978 | − dev_err(dev, "Lane0/1 not ready\n"); | |
| 979 | − if (!aligned) | |
| 980 | − dev_err(dev, "Lane0/1 not aligned\n"); | |
| 981 | 985 | return -EAGAIN; |
| 982 | 986 | } |
| 983 | 987 | |
| @@ -1099,7 +1103,10 @@ static bool tc_bridge_mode_fixup(struct drm_bridge *bridge, · 115 unmodified lines | ||
| 1099 | 1103 | static int tc_connector_mode_valid(struct drm_connector *connector, |
| 1100 | 1104 | struct drm_display_mode *mode) |
| 1101 | 1105 | { |
| 1102 | − /* Accept any mode */ | |
| 1106 | + /* DPI interface clock limitation: upto 154 MHz */ | |
| 1107 | + if (mode->clock > 154000) | |
| 1108 | + return MODE_CLOCK_HIGH; | |
| 1109 | + | |
| 1103 | 1110 | return MODE_OK; |
| 1104 | 1111 | } |
| 1105 | 1112 | |
| @@ -1225,7 +1225,7 @@ drm_atomic_helper_wait_for_vblanks(struct drm_device *dev, · 1224 unmodified lines | ||
| 1225 | 1225 | return; |
| 1226 | 1226 | |
| 1227 | 1227 | for_each_oldnew_crtc_in_state(old_state, crtc, old_crtc_state, new_crtc_state, i) { |
| 1228 | − if (!new_crtc_state->active || !new_crtc_state->planes_changed) | |
| 1228 | + if (!new_crtc_state->active) | |
| 1229 | 1229 | continue; |
| 1230 | 1230 | |
| 1231 | 1231 | ret = drm_crtc_vblank_get(crtc); |
| @@ -1809,6 +1809,10 @@ static int drm_fb_helper_single_fb_probe(struct drm_fb_helper *fb_helper, · 1808 unmodified lines | ||
| 1809 | 1809 | |
| 1810 | 1810 | if (crtc_count == 0 || sizes.fb_width == -1 || sizes.fb_height == -1) { |
| 1811 | 1811 | DRM_INFO("Cannot find any crtc or sizes\n"); |
| 1812 | + | |
| 1813 | + /* First time: disable all crtc's.. */ | |
| 1814 | + if (!fb_helper->deferred_setup && !READ_ONCE(fb_helper->dev->master)) | |
| 1815 | + restore_fbdev_mode(fb_helper); | |
| 1812 | 1816 | return -EAGAIN; |
| 1813 | 1817 | } |
| 1814 | 1818 | |
| @@ -282,6 +282,7 @@ static void clean_virtual_dp_monitor(struct intel_vgpu *vgpu, int port_num) · 281 unmodified lines | ||
| 282 | 282 | static int setup_virtual_dp_monitor(struct intel_vgpu *vgpu, int port_num, |
| 283 | 283 | int type, unsigned int resolution) |
| 284 | 284 | { |
| 285 | + struct drm_i915_private *dev_priv = vgpu->gvt->dev_priv; | |
| 285 | 286 | struct intel_vgpu_port *port = intel_vgpu_port(vgpu, port_num); |
| 286 | 287 | |
| 287 | 288 | if (WARN_ON(resolution >= GVT_EDID_NUM)) |
| @@ -307,6 +308,7 @@ static int setup_virtual_dp_monitor(struct intel_vgpu *vgpu, int port_num, · 19 unmodified lines | ||
| 307 | 308 | port->type = type; |
| 308 | 309 | |
| 309 | 310 | emulate_monitor_status_change(vgpu); |
| 311 | + vgpu_vreg(vgpu, PIPECONF(PIPE_A)) |= PIPECONF_ENABLE; | |
| 310 | 312 | return 0; |
| 311 | 313 | } |
| 312 | 314 | |
| @@ -496,6 +496,12 @@ static int prepare_execlist_workload(struct intel_vgpu_workload *workload) · 495 unmodified lines | ||
| 496 | 496 | goto err_unpin_mm; |
| 497 | 497 | } |
| 498 | 498 | |
| 499 | + ret = intel_gvt_generate_request(workload); | |
| 500 | + if (ret) { | |
| 501 | + gvt_vgpu_err("fail to generate request\n"); | |
| 502 | + goto err_unpin_mm; | |
| 503 | + } | |
| 504 | + | |
| 499 | 505 | ret = prepare_shadow_batch_buffer(workload); |
| 500 | 506 | if (ret) { |
| 501 | 507 | gvt_vgpu_err("fail to prepare_shadow_batch_buffer\n"); |
| @@ -311,9 +311,9 @@ static inline int gtt_set_entry64(void *pt, · 310 unmodified lines | ||
| 311 | 311 | |
| 312 | 312 | #define GTT_HAW 46 |
| 313 | 313 | |
| 314 | −#define ADDR_1G_MASK (((1UL << (GTT_HAW - 30 + 1)) - 1) << 30) | |
| 315 | −#define ADDR_2M_MASK (((1UL << (GTT_HAW - 21 + 1)) - 1) << 21) | |
| 316 | −#define ADDR_4K_MASK (((1UL << (GTT_HAW - 12 + 1)) - 1) << 12) | |
| 314 | +#define ADDR_1G_MASK (((1UL << (GTT_HAW - 30)) - 1) << 30) | |
| 315 | +#define ADDR_2M_MASK (((1UL << (GTT_HAW - 21)) - 1) << 21) | |
| 316 | +#define ADDR_4K_MASK (((1UL << (GTT_HAW - 12)) - 1) << 12) | |
| 317 | 317 | |
| 318 | 318 | static unsigned long gen8_gtt_get_pfn(struct intel_gvt_gtt_entry *e) |
| 319 | 319 | { |
| @@ -1381,40 +1381,6 @@ static int skl_power_well_ctl_write(struct intel_vgpu *vgpu, · 1380 unmodified lines | ||
| 1381 | 1381 | return intel_vgpu_default_mmio_write(vgpu, offset, &v, bytes); |
| 1382 | 1382 | } |
| 1383 | 1383 | |
| 1384 | −static int skl_misc_ctl_write(struct intel_vgpu *vgpu, unsigned int offset, | |
| 1385 | − void *p_data, unsigned int bytes) | |
| 1386 | −{ | |
| 1387 | − struct drm_i915_private *dev_priv = vgpu->gvt->dev_priv; | |
| 1388 | − u32 v = *(u32 *)p_data; | |
| 1389 | − | |
| 1390 | − if (!IS_SKYLAKE(dev_priv) && !IS_KABYLAKE(dev_priv)) | |
| 1391 | − return intel_vgpu_default_mmio_write(vgpu, | |
| 1392 | − offset, p_data, bytes); | |
| 1393 | − | |
| 1394 | − switch (offset) { | |
| 1395 | − case 0x4ddc: | |
| 1396 | − /* bypass WaCompressedResourceSamplerPbeMediaNewHashMode */ | |
| 1397 | − vgpu_vreg(vgpu, offset) = v & ~(1 << 31); | |
| 1398 | − break; | |
| 1399 | − case 0x42080: | |
| 1400 | − /* bypass WaCompressedResourceDisplayNewHashMode */ | |
| 1401 | − vgpu_vreg(vgpu, offset) = v & ~(1 << 15); | |
| 1402 | − break; | |
| 1403 | − case 0xe194: | |
| 1404 | − /* bypass WaCompressedResourceSamplerPbeMediaNewHashMode */ | |
| 1405 | − vgpu_vreg(vgpu, offset) = v & ~(1 << 8); | |
| 1406 | − break; | |
| 1407 | − case 0x7014: | |
| 1408 | − /* bypass WaCompressedResourceSamplerPbeMediaNewHashMode */ | |
| 1409 | − vgpu_vreg(vgpu, offset) = v & ~(1 << 13); | |
| 1410 | − break; | |
| 1411 | − default: | |
| 1412 | − return -EINVAL; | |
| 1413 | − } | |
| 1414 | − | |
| 1415 | − return 0; | |
| 1416 | −} | |
| 1417 | − | |
| 1418 | 1384 | static int skl_lcpll_write(struct intel_vgpu *vgpu, unsigned int offset, |
| 1419 | 1385 | void *p_data, unsigned int bytes) |
| 1420 | 1386 | { |
| @@ -1671,8 +1637,8 @@ static int init_generic_mmio_info(struct intel_gvt *gvt) · 250 unmodified lines | ||
| 1671 | 1637 | MMIO_DFH(GAM_ECOCHK, D_ALL, F_CMD_ACCESS, NULL, NULL); |
| 1672 | 1638 | MMIO_DFH(GEN7_COMMON_SLICE_CHICKEN1, D_ALL, F_MODE_MASK | F_CMD_ACCESS, |
| 1673 | 1639 | NULL, NULL); |
| 1674 | − MMIO_DFH(COMMON_SLICE_CHICKEN2, D_ALL, F_MODE_MASK | F_CMD_ACCESS, NULL, | |
| 1675 | − skl_misc_ctl_write); | |
| 1640 | + MMIO_DFH(COMMON_SLICE_CHICKEN2, D_ALL, F_MODE_MASK | F_CMD_ACCESS, | |
| 1641 | + NULL, NULL); | |
| 1676 | 1642 | MMIO_DFH(0x9030, D_ALL, F_CMD_ACCESS, NULL, NULL); |
| 1677 | 1643 | MMIO_DFH(0x20a0, D_ALL, F_CMD_ACCESS, NULL, NULL); |
| 1678 | 1644 | MMIO_DFH(0x2420, D_ALL, F_CMD_ACCESS, NULL, NULL); |
| @@ -2564,8 +2530,7 @@ static int init_broadwell_mmio_info(struct intel_gvt *gvt) · 885 unmodified lines | ||
| 2564 | 2530 | MMIO_D(0x6e570, D_BDW_PLUS); |
| 2565 | 2531 | MMIO_D(0x65f10, D_BDW_PLUS); |
| 2566 | 2532 | |
| 2567 | − MMIO_DFH(0xe194, D_BDW_PLUS, F_MODE_MASK | F_CMD_ACCESS, NULL, | |
| 2568 | − skl_misc_ctl_write); | |
| 2533 | + MMIO_DFH(0xe194, D_BDW_PLUS, F_MODE_MASK | F_CMD_ACCESS, NULL, NULL); | |
| 2569 | 2534 | MMIO_DFH(0xe188, D_BDW_PLUS, F_MODE_MASK | F_CMD_ACCESS, NULL, NULL); |
| 2570 | 2535 | MMIO_DFH(HALF_SLICE_CHICKEN2, D_BDW_PLUS, F_MODE_MASK | F_CMD_ACCESS, NULL, NULL); |
| 2571 | 2536 | MMIO_DFH(0x2580, D_BDW_PLUS, F_MODE_MASK | F_CMD_ACCESS, NULL, NULL); |
| @@ -2615,8 +2580,8 @@ static int init_skl_mmio_info(struct intel_gvt *gvt) · 43 unmodified lines | ||
| 2615 | 2580 | MMIO_D(GEN9_MEDIA_PG_IDLE_HYSTERESIS, D_SKL_PLUS); |
| 2616 | 2581 | MMIO_D(GEN9_RENDER_PG_IDLE_HYSTERESIS, D_SKL_PLUS); |
| 2617 | 2582 | MMIO_DFH(GEN9_GAMT_ECO_REG_RW_IA, D_SKL_PLUS, F_CMD_ACCESS, NULL, NULL); |
| 2618 | − MMIO_DH(0x4ddc, D_SKL_PLUS, NULL, skl_misc_ctl_write); | |
| 2619 | − MMIO_DH(0x42080, D_SKL_PLUS, NULL, skl_misc_ctl_write); | |
| 2583 | + MMIO_DH(0x4ddc, D_SKL_PLUS, NULL, NULL); | |
| 2584 | + MMIO_DH(0x42080, D_SKL_PLUS, NULL, NULL); | |
| 2620 | 2585 | MMIO_D(0x45504, D_SKL_PLUS); |
| 2621 | 2586 | MMIO_D(0x45520, D_SKL_PLUS); |
| 2622 | 2587 | MMIO_D(0x46000, D_SKL_PLUS); |
| @@ -140,9 +140,10 @@ static int shadow_context_status_change(struct notifier_block *nb, · 139 unmodified lines | ||
| 140 | 140 | struct intel_gvt_workload_scheduler *scheduler = &gvt->scheduler; |
| 141 | 141 | enum intel_engine_id ring_id = req->engine->id; |
| 142 | 142 | struct intel_vgpu_workload *workload; |
| 143 | + unsigned long flags; | |
| 143 | 144 | |
| 144 | 145 | if (!is_gvt_request(req)) { |
| 145 | − spin_lock_bh(&scheduler->mmio_context_lock); | |
| 146 | + spin_lock_irqsave(&scheduler->mmio_context_lock, flags); | |
| 146 | 147 | if (action == INTEL_CONTEXT_SCHEDULE_IN && |
| 147 | 148 | scheduler->engine_owner[ring_id]) { |
| 148 | 149 | /* Switch ring from vGPU to host. */ |
| @@ -150,7 +151,7 @@ static int shadow_context_status_change(struct notifier_block *nb, · 1 unmodified line | ||
| 150 | 151 | NULL, ring_id); |
| 151 | 152 | scheduler->engine_owner[ring_id] = NULL; |
| 152 | 153 | } |
| 153 | − spin_unlock_bh(&scheduler->mmio_context_lock); | |
| 154 | + spin_unlock_irqrestore(&scheduler->mmio_context_lock, flags); | |
| 154 | 155 | |
| 155 | 156 | return NOTIFY_OK; |
| 156 | 157 | } |
| @@ -161,7 +162,7 @@ static int shadow_context_status_change(struct notifier_block *nb, · 4 unmodified lines | ||
| 161 | 162 | |
| 162 | 163 | switch (action) { |
| 163 | 164 | case INTEL_CONTEXT_SCHEDULE_IN: |
| 164 | − spin_lock_bh(&scheduler->mmio_context_lock); | |
| 165 | + spin_lock_irqsave(&scheduler->mmio_context_lock, flags); | |
| 165 | 166 | if (workload->vgpu != scheduler->engine_owner[ring_id]) { |
| 166 | 167 | /* Switch ring from host to vGPU or vGPU to vGPU. */ |
| 167 | 168 | intel_gvt_switch_mmio(scheduler->engine_owner[ring_id], |
| @@ -170,7 +171,7 @@ static int shadow_context_status_change(struct notifier_block *nb, · 2 unmodified lines | ||
| 170 | 171 | } else |
| 171 | 172 | gvt_dbg_sched("skip ring %d mmio switch for vgpu%d\n", |
| 172 | 173 | ring_id, workload->vgpu->id); |
| 173 | − spin_unlock_bh(&scheduler->mmio_context_lock); | |
| 174 | + spin_unlock_irqrestore(&scheduler->mmio_context_lock, flags); | |
| 174 | 175 | atomic_set(&workload->shadow_ctx_active, 1); |
| 175 | 176 | break; |
| 176 | 177 | case INTEL_CONTEXT_SCHEDULE_OUT: |
| @@ -253,7 +254,6 @@ int intel_gvt_scan_and_shadow_workload(struct intel_vgpu_workload *workload) · 76 unmodified lines | ||
| 253 | 254 | struct i915_gem_context *shadow_ctx = workload->vgpu->shadow_ctx; |
| 254 | 255 | struct drm_i915_private *dev_priv = workload->vgpu->gvt->dev_priv; |
| 255 | 256 | struct intel_engine_cs *engine = dev_priv->engine[ring_id]; |
| 256 | − struct drm_i915_gem_request *rq; | |
| 257 | 257 | struct intel_vgpu *vgpu = workload->vgpu; |
| 258 | 258 | struct intel_ring *ring; |
| 259 | 259 | int ret; |
| @@ -299,6 +299,26 @@ int intel_gvt_scan_and_shadow_workload(struct intel_vgpu_workload *workload) · 39 unmodified lines | ||
| 299 | 299 | ret = populate_shadow_context(workload); |
| 300 | 300 | if (ret) |
| 301 | 301 | goto err_unpin; |
| 302 | + workload->shadowed = true; | |
| 303 | + return 0; | |
| 304 | + | |
| 305 | +err_unpin: | |
| 306 | + engine->context_unpin(engine, shadow_ctx); | |
| 307 | +err_shadow: | |
| 308 | + release_shadow_wa_ctx(&workload->wa_ctx); | |
| 309 | +err_scan: | |
| 310 | + return ret; | |
| 311 | +} | |
| 312 | + | |
| 313 | +int intel_gvt_generate_request(struct intel_vgpu_workload *workload) | |
| 314 | +{ | |
| 315 | + int ring_id = workload->ring_id; | |
| 316 | + struct drm_i915_private *dev_priv = workload->vgpu->gvt->dev_priv; | |
| 317 | + struct intel_engine_cs *engine = dev_priv->engine[ring_id]; | |
| 318 | + struct drm_i915_gem_request *rq; | |
| 319 | + struct intel_vgpu *vgpu = workload->vgpu; | |
| 320 | + struct i915_gem_context *shadow_ctx = vgpu->shadow_ctx; | |
| 321 | + int ret; | |
| 302 | 322 | |
| 303 | 323 | rq = i915_gem_request_alloc(dev_priv->engine[ring_id], shadow_ctx); |
| 304 | 324 | if (IS_ERR(rq)) { |
| @@ -313,14 +333,11 @@ int intel_gvt_scan_and_shadow_workload(struct intel_vgpu_workload *workload) · 8 unmodified lines | ||
| 313 | 333 | ret = copy_workload_to_ring_buffer(workload); |
| 314 | 334 | if (ret) |
| 315 | 335 | goto err_unpin; |
| 316 | − workload->shadowed = true; | |
| 317 | 336 | return 0; |
| 318 | 337 | |
| 319 | 338 | err_unpin: |
| 320 | 339 | engine->context_unpin(engine, shadow_ctx); |
| 321 | −err_shadow: | |
| 322 | 340 | release_shadow_wa_ctx(&workload->wa_ctx); |
| 323 | −err_scan: | |
| 324 | 341 | return ret; |
| 325 | 342 | } |
| 326 | 343 | |
| @@ -142,4 +142,7 @@ int intel_vgpu_init_gvt_context(struct intel_vgpu *vgpu); · 141 unmodified lines | ||
| 142 | 142 | void intel_vgpu_clean_gvt_context(struct intel_vgpu *vgpu); |
| 143 | 143 | |
| 144 | 144 | void release_shadow_wa_ctx(struct intel_shadow_wa_ctx *wa_ctx); |
| 145 | + | |
| 146 | +int intel_gvt_generate_request(struct intel_vgpu_workload *workload); | |
| 147 | + | |
| 145 | 148 | #endif |
| @@ -52,7 +52,8 @@ int i915_gemfs_init(struct drm_i915_private *i915) · 51 unmodified lines | ||
| 52 | 52 | |
| 53 | 53 | if (has_transparent_hugepage()) { |
| 54 | 54 | struct super_block *sb = gemfs->mnt_sb; |
| 55 | − char options[] = "huge=within_size"; | |
| 55 | + /* FIXME: Disabled until we get W/A for read BW issue. */ | |
| 56 | + char options[] = "huge=never"; | |
| 56 | 57 | int flags = 0; |
| 57 | 58 | int err; |
| 58 | 59 | |
| @@ -1736,7 +1736,7 @@ extern struct drm_display_mode *intel_find_panel_downclock( · 1735 unmodified lines | ||
| 1736 | 1736 | int intel_backlight_device_register(struct intel_connector *connector); |
| 1737 | 1737 | void intel_backlight_device_unregister(struct intel_connector *connector); |
| 1738 | 1738 | #else /* CONFIG_BACKLIGHT_CLASS_DEVICE */ |
| 1739 | −static int intel_backlight_device_register(struct intel_connector *connector) | |
| 1739 | +static inline int intel_backlight_device_register(struct intel_connector *connector) | |
| 1740 | 1740 | { |
| 1741 | 1741 | return 0; |
| 1742 | 1742 | } |
| @@ -697,10 +697,8 @@ static void intel_fbdev_initial_config(void *data, async_cookie_t cookie) · 696 unmodified lines | ||
| 697 | 697 | |
| 698 | 698 | /* Due to peculiar init order wrt to hpd handling this is separate. */ |
| 699 | 699 | if (drm_fb_helper_initial_config(&ifbdev->helper, |
| 700 | − ifbdev->preferred_bpp)) { | |
| 700 | + ifbdev->preferred_bpp)) | |
| 701 | 701 | intel_fbdev_unregister(to_i915(ifbdev->helper.dev)); |
| 702 | − intel_fbdev_fini(to_i915(ifbdev->helper.dev)); | |
| 703 | − } | |
| 704 | 702 | } |
| 705 | 703 | |
| 706 | 704 | void intel_fbdev_initial_config_async(struct drm_device *dev) |
| @@ -800,7 +798,11 @@ void intel_fbdev_output_poll_changed(struct drm_device *dev) · 93 unmodified lines | ||
| 800 | 798 | { |
| 801 | 799 | struct intel_fbdev *ifbdev = to_i915(dev)->fbdev; |
| 802 | 800 | |
| 803 | − if (ifbdev) | |
| 801 | + if (!ifbdev) | |
| 802 | + return; | |
| 803 | + | |
| 804 | + intel_fbdev_sync(ifbdev); | |
| 805 | + if (ifbdev->vma) | |
| 804 | 806 | drm_fb_helper_hotplug_event(&ifbdev->helper); |
| 805 | 807 | } |
| 806 | 808 | |
| @@ -438,7 +438,9 @@ static bool · 437 unmodified lines | ||
| 438 | 438 | gmbus_is_index_read(struct i2c_msg *msgs, int i, int num) |
| 439 | 439 | { |
| 440 | 440 | return (i + 1 < num && |
| 441 | − !(msgs[i].flags & I2C_M_RD) && msgs[i].len <= 2 && | |
| 441 | + msgs[i].addr == msgs[i + 1].addr && | |
| 442 | + !(msgs[i].flags & I2C_M_RD) && | |
| 443 | + (msgs[i].len == 1 || msgs[i].len == 2) && | |
| 442 | 444 | (msgs[i + 1].flags & I2C_M_RD)); |
| 443 | 445 | } |
| 444 | 446 | |
| @@ -133,9 +133,16 @@ static void imx_drm_atomic_commit_tail(struct drm_atomic_state *state) · 132 unmodified lines | ||
| 133 | 133 | plane_disabling = true; |
| 134 | 134 | } |
| 135 | 135 | |
| 136 | − if (plane_disabling) { | |
| 137 | − drm_atomic_helper_wait_for_vblanks(dev, state); | |
| 136 | + /* | |
| 137 | + * The flip done wait is only strictly required by imx-drm if a deferred | |
| 138 | + * plane disable is in-flight. As the core requires blocking commits | |
| 139 | + * to wait for the flip it is done here unconditionally. This keeps the | |
| 140 | + * workitem around a bit longer than required for the majority of | |
| 141 | + * non-blocking commits, but we accept that for the sake of simplicity. | |
| 142 | + */ | |
| 143 | + drm_atomic_helper_wait_for_flip_done(dev, state); | |
| 138 | 144 | |
| 145 | + if (plane_disabling) { | |
| 139 | 146 | for_each_old_plane_in_state(state, plane, old_plane_state, i) |
| 140 | 147 | ipu_plane_disable_deferred(plane); |
| 141 | 148 | |
| @@ -35,6 +35,7 @@ config DRM_OMAP_CONNECTOR_ANALOG_TV · 34 unmodified lines | ||
| 35 | 35 | |
| 36 | 36 | config DRM_OMAP_PANEL_DPI |
| 37 | 37 | tristate "Generic DPI panel" |
| 38 | + depends on BACKLIGHT_CLASS_DEVICE | |
| 38 | 39 | help |
| 39 | 40 | Driver for generic DPI panels. |
| 40 | 41 | |
| @@ -566,8 +566,8 @@ static int dpi_verify_pll(struct dss_pll *pll) · 565 unmodified lines | ||
| 566 | 566 | } |
| 567 | 567 | |
| 568 | 568 | static const struct soc_device_attribute dpi_soc_devices[] = { |
| 569 | − { .family = "OMAP3[456]*" }, | |
| 570 | − { .family = "[AD]M37*" }, | |
| 569 | + { .machine = "OMAP3[456]*" }, | |
| 570 | + { .machine = "[AD]M37*" }, | |
| 571 | 571 | { /* sentinel */ } |
| 572 | 572 | }; |
| 573 | 573 | |
| @@ -352,7 +352,7 @@ int hdmi4_cec_init(struct platform_device *pdev, struct hdmi_core_data *core, · 351 unmodified lines | ||
| 352 | 352 | { |
| 353 | 353 | const u32 caps = CEC_CAP_TRANSMIT | CEC_CAP_LOG_ADDRS | |
| 354 | 354 | CEC_CAP_PASSTHROUGH | CEC_CAP_RC; |
| 355 | − unsigned int ret; | |
| 355 | + int ret; | |
| 356 | 356 | |
| 357 | 357 | core->adap = cec_allocate_adapter(&hdmi_cec_adap_ops, core, |
| 358 | 358 | "omap4", caps, CEC_MAX_LOG_ADDRS); |
| @@ -886,25 +886,36 @@ struct hdmi4_features { · 885 unmodified lines | ||
| 886 | 886 | bool audio_use_mclk; |
| 887 | 887 | }; |
| 888 | 888 | |
| 889 | −static const struct hdmi4_features hdmi4_es1_features = { | |
| 889 | +static const struct hdmi4_features hdmi4430_es1_features = { | |
| 890 | 890 | .cts_swmode = false, |
| 891 | 891 | .audio_use_mclk = false, |
| 892 | 892 | }; |
| 893 | 893 | |
| 894 | −static const struct hdmi4_features hdmi4_es2_features = { | |
| 894 | +static const struct hdmi4_features hdmi4430_es2_features = { | |
| 895 | 895 | .cts_swmode = true, |
| 896 | 896 | .audio_use_mclk = false, |
| 897 | 897 | }; |
| 898 | 898 | |
| 899 | −static const struct hdmi4_features hdmi4_es3_features = { | |
| 899 | +static const struct hdmi4_features hdmi4_features = { | |
| 900 | 900 | .cts_swmode = true, |
| 901 | 901 | .audio_use_mclk = true, |
| 902 | 902 | }; |
| 903 | 903 | |
| 904 | 904 | static const struct soc_device_attribute hdmi4_soc_devices[] = { |
| 905 | − { .family = "OMAP4", .revision = "ES1.?", .data = &hdmi4_es1_features }, | |
| 906 | − { .family = "OMAP4", .revision = "ES2.?", .data = &hdmi4_es2_features }, | |
| 907 | − { .family = "OMAP4", .data = &hdmi4_es3_features }, | |
| 905 | + { | |
| 906 | + .machine = "OMAP4430", | |
| 907 | + .revision = "ES1.?", | |
| 908 | + .data = &hdmi4430_es1_features, | |
| 909 | + }, | |
| 910 | + { | |
| 911 | + .machine = "OMAP4430", | |
| 912 | + .revision = "ES2.?", | |
| 913 | + .data = &hdmi4430_es2_features, | |
| 914 | + }, | |
| 915 | + { | |
| 916 | + .family = "OMAP4", | |
| 917 | + .data = &hdmi4_features, | |
| 918 | + }, | |
| 908 | 919 | { /* sentinel */ } |
| 909 | 920 | }; |
| 910 | 921 | |
| @@ -638,7 +638,8 @@ static int omap_dmm_probe(struct platform_device *dev) · 637 unmodified lines | ||
| 638 | 638 | match = of_match_node(dmm_of_match, dev->dev.of_node); |
| 639 | 639 | if (!match) { |
| 640 | 640 | dev_err(&dev->dev, "failed to find matching device node\n"); |
| 641 | − return -ENODEV; | |
| 641 | + ret = -ENODEV; | |
| 642 | + goto fail; | |
| 642 | 643 | } |
| 643 | 644 | |
| 644 | 645 | omap_dmm->plat_data = match->data; |
| @@ -5451,28 +5451,6 @@ void cik_pcie_gart_tlb_flush(struct radeon_device *rdev) · 5450 unmodified lines | ||
| 5451 | 5451 | WREG32(VM_INVALIDATE_REQUEST, 0x1); |
| 5452 | 5452 | } |
| 5453 | 5453 | |
| 5454 | −static void cik_pcie_init_compute_vmid(struct radeon_device *rdev) | |
| 5455 | −{ | |
| 5456 | − int i; | |
| 5457 | − uint32_t sh_mem_bases, sh_mem_config; | |
| 5458 | − | |
| 5459 | − sh_mem_bases = 0x6000 | 0x6000 << 16; | |
| 5460 | − sh_mem_config = ALIGNMENT_MODE(SH_MEM_ALIGNMENT_MODE_UNALIGNED); | |
| 5461 | − sh_mem_config |= DEFAULT_MTYPE(MTYPE_NONCACHED); | |
| 5462 | − | |
| 5463 | − mutex_lock(&rdev->srbm_mutex); | |
| 5464 | − for (i = 8; i < 16; i++) { | |
| 5465 | − cik_srbm_select(rdev, 0, 0, 0, i); | |
| 5466 | − /* CP and shaders */ | |
| 5467 | − WREG32(SH_MEM_CONFIG, sh_mem_config); | |
| 5468 | − WREG32(SH_MEM_APE1_BASE, 1); | |
| 5469 | − WREG32(SH_MEM_APE1_LIMIT, 0); | |
| 5470 | − WREG32(SH_MEM_BASES, sh_mem_bases); | |
| 5471 | − } | |
| 5472 | − cik_srbm_select(rdev, 0, 0, 0, 0); | |
| 5473 | − mutex_unlock(&rdev->srbm_mutex); | |
| 5474 | −} | |
| 5475 | − | |
| 5476 | 5454 | /** |
| 5477 | 5455 | * cik_pcie_gart_enable - gart enable |
| 5478 | 5456 | * |
| @@ -5586,8 +5564,6 @@ static int cik_pcie_gart_enable(struct radeon_device *rdev) · 107 unmodified lines | ||
| 5586 | 5564 | cik_srbm_select(rdev, 0, 0, 0, 0); |
| 5587 | 5565 | mutex_unlock(&rdev->srbm_mutex); |
| 5588 | 5566 | |
| 5589 | − cik_pcie_init_compute_vmid(rdev); | |
| 5590 | − | |
| 5591 | 5567 | cik_pcie_gart_tlb_flush(rdev); |
| 5592 | 5568 | DRM_INFO("PCIE GART of %uM enabled (table at 0x%016llX).\n", |
| 5593 | 5569 | (unsigned)(rdev->mc.gtt_size >> 20), |
| @@ -1285,8 +1285,6 @@ static int dw_mipi_dsi_bind(struct device *dev, struct device *master, · 1284 unmodified lines | ||
| 1285 | 1285 | goto err_pllref; |
| 1286 | 1286 | } |
| 1287 | 1287 | |
| 1288 | − pm_runtime_enable(dev); | |
| 1289 | − | |
| 1290 | 1288 | dsi->dsi_host.ops = &dw_mipi_dsi_host_ops; |
| 1291 | 1289 | dsi->dsi_host.dev = dev; |
| 1292 | 1290 | ret = mipi_dsi_host_register(&dsi->dsi_host); |
| @@ -1301,6 +1299,7 @@ static int dw_mipi_dsi_bind(struct device *dev, struct device *master, · 8 unmodified lines | ||
| 1301 | 1299 | } |
| 1302 | 1300 | |
| 1303 | 1301 | dev_set_drvdata(dev, dsi); |
| 1302 | + pm_runtime_enable(dev); | |
| 1304 | 1303 | return 0; |
| 1305 | 1304 | |
| 1306 | 1305 | err_mipi_dsi_host: |
| @@ -1062,7 +1062,6 @@ void ttm_pool_unpopulate(struct ttm_tt *ttm) · 1061 unmodified lines | ||
| 1062 | 1062 | } |
| 1063 | 1063 | EXPORT_SYMBOL(ttm_pool_unpopulate); |
| 1064 | 1064 | |
| 1065 | −#if defined(CONFIG_SWIOTLB) || defined(CONFIG_INTEL_IOMMU) | |
| 1066 | 1065 | int ttm_populate_and_map_pages(struct device *dev, struct ttm_dma_tt *tt) |
| 1067 | 1066 | { |
| 1068 | 1067 | unsigned i, j; |
| @@ -1133,7 +1132,6 @@ void ttm_unmap_and_unpopulate_pages(struct device *dev, struct ttm_dma_tt *tt) · 64 unmodified lines | ||
| 1133 | 1132 | ttm_pool_unpopulate(&tt->ttm); |
| 1134 | 1133 | } |
| 1135 | 1134 | EXPORT_SYMBOL(ttm_unmap_and_unpopulate_pages); |
| 1136 | −#endif | |
| 1137 | 1135 | |
| 1138 | 1136 | int ttm_page_alloc_debugfs(struct seq_file *m, void *data) |
| 1139 | 1137 | { |
| @@ -58,12 +58,21 @@ int ttm_pool_populate(struct ttm_tt *ttm); · 57 unmodified lines | ||
| 58 | 58 | */ |
| 59 | 59 | void ttm_pool_unpopulate(struct ttm_tt *ttm); |
| 60 | 60 | |
| 61 | +/** | |
| 62 | + * Populates and DMA maps pages to fullfil a ttm_dma_populate() request | |
| 63 | + */ | |
| 64 | +int ttm_populate_and_map_pages(struct device *dev, struct ttm_dma_tt *tt); | |
| 65 | + | |
| 66 | +/** | |
| 67 | + * Unpopulates and DMA unmaps pages as part of a | |
| 68 | + * ttm_dma_unpopulate() request */ | |
| 69 | +void ttm_unmap_and_unpopulate_pages(struct device *dev, struct ttm_dma_tt *tt); | |
| 70 | + | |
| 61 | 71 | /** |
| 62 | 72 | * Output the state of pools to debugfs file |
| 63 | 73 | */ |
| 64 | 74 | int ttm_page_alloc_debugfs(struct seq_file *m, void *data); |
| 65 | 75 | |
| 66 | − | |
| 67 | 76 | #if defined(CONFIG_SWIOTLB) || defined(CONFIG_INTEL_IOMMU) |
| 68 | 77 | /** |
| 69 | 78 | * Initialize pool allocator. |
| @@ -83,17 +92,6 @@ int ttm_dma_page_alloc_debugfs(struct seq_file *m, void *data); · 13 unmodified lines | ||
| 83 | 92 | int ttm_dma_populate(struct ttm_dma_tt *ttm_dma, struct device *dev); |
| 84 | 93 | void ttm_dma_unpopulate(struct ttm_dma_tt *ttm_dma, struct device *dev); |
| 85 | 94 | |
| 86 | − | |
| 87 | −/** | |
| 88 | − * Populates and DMA maps pages to fullfil a ttm_dma_populate() request | |
| 89 | − */ | |
| 90 | −int ttm_populate_and_map_pages(struct device *dev, struct ttm_dma_tt *tt); | |
| 91 | − | |
| 92 | −/** | |
| 93 | − * Unpopulates and DMA unmaps pages as part of a | |
| 94 | − * ttm_dma_unpopulate() request */ | |
| 95 | −void ttm_unmap_and_unpopulate_pages(struct device *dev, struct ttm_dma_tt *tt); | |
| 96 | − | |
| 97 | 95 | #else |
| 98 | 96 | static inline int ttm_dma_page_alloc_init(struct ttm_mem_global *glob, |
| 99 | 97 | unsigned max_pages) |
| @@ -116,16 +114,6 @@ static inline void ttm_dma_unpopulate(struct ttm_dma_tt *ttm_dma, · 16 unmodified lines | ||
| 116 | 114 | struct device *dev) |
| 117 | 115 | { |
| 118 | 116 | } |
| 119 | − | |
| 120 | −static inline int ttm_populate_and_map_pages(struct device *dev, struct ttm_dma_tt *tt) | |
| 121 | −{ | |
| 122 | − return -ENOMEM; | |
| 123 | −} | |
| 124 | − | |
| 125 | −static inline void ttm_unmap_and_unpopulate_pages(struct device *dev, struct ttm_dma_tt *tt) | |
| 126 | −{ | |
| 127 | −} | |
| 128 | − | |
| 129 | 117 | #endif |
| 130 | 118 | |
| 131 | 119 | #endif |
| @@ -233,29 +233,29 @@ struct kfd_ioctl_wait_events_args { · 232 unmodified lines | ||
| 233 | 233 | }; |
| 234 | 234 | |
| 235 | 235 | struct kfd_ioctl_set_scratch_backing_va_args { |
| 236 | − uint64_t va_addr; /* to KFD */ | |
| 237 | − uint32_t gpu_id; /* to KFD */ | |
| 238 | − uint32_t pad; | |
| 236 | + __u64 va_addr; /* to KFD */ | |
| 237 | + __u32 gpu_id; /* to KFD */ | |
| 238 | + __u32 pad; | |
| 239 | 239 | }; |
| 240 | 240 | |
| 241 | 241 | struct kfd_ioctl_get_tile_config_args { |
| 242 | 242 | /* to KFD: pointer to tile array */ |
| 243 | − uint64_t tile_config_ptr; | |
| 243 | + __u64 tile_config_ptr; | |
| 244 | 244 | /* to KFD: pointer to macro tile array */ |
| 245 | − uint64_t macro_tile_config_ptr; | |
| 245 | + __u64 macro_tile_config_ptr; | |
| 246 | 246 | /* to KFD: array size allocated by user mode |
| 247 | 247 | * from KFD: array size filled by kernel |
| 248 | 248 | */ |
| 249 | − uint32_t num_tile_configs; | |
| 249 | + __u32 num_tile_configs; | |
| 250 | 250 | /* to KFD: array size allocated by user mode |
| 251 | 251 | * from KFD: array size filled by kernel |
| 252 | 252 | */ |
| 253 | − uint32_t num_macro_tile_configs; | |
| 253 | + __u32 num_macro_tile_configs; | |
| 254 | 254 | |
| 255 | − uint32_t gpu_id; /* to KFD */ | |
| 256 | − uint32_t gb_addr_config; /* from KFD */ | |
| 257 | − uint32_t num_banks; /* from KFD */ | |
| 258 | − uint32_t num_ranks; /* from KFD */ | |
| 255 | + __u32 gpu_id; /* to KFD */ | |
| 256 | + __u32 gb_addr_config; /* from KFD */ | |
| 257 | + __u32 num_banks; /* from KFD */ | |
| 258 | + __u32 num_ranks; /* from KFD */ | |
| 259 | 259 | /* struct size can be extended later if needed |
| 260 | 260 | * without breaking ABI compatibility |
| 261 | 261 | */ |