Commit 62a05f4a authored by Daniel Vetter's avatar Daniel Vetter

Merge tag 'drm-msm-next-2024-07-04' of https://gitlab.freedesktop.org/drm/msm into drm-next

Updates for v6.11

Core:
- SM7150 support

DPU:
- SM7150 support
- Fix DSC support for DSI panels in video mode
- Fixed TE vsync source support for DSI command-mode panels
- Fix for devices without UBWC in the display controller (ie.
  QCM2290)

DSI:
- Remove unused register-writing wrappers
- Fix DSC support for panels in video mode
- Add support for parsing TE vsync source
- Add support for MSM8937 (28nm DSI PHY)

MDP5:
- Add support for MSM8937
- Fix configuration for MSM8953

GPU:
- Split giant device table into per-gen "hw catalog" similar to
  what is done on the display side of the driver
- Fix a702 UBWC mode
- Fix unused variably warnings
- GPU memory traces
- Add param for userspace to know if raytracing is supported
- Memory barrier cleanup and GBIF unhalt fix
- X185 support (aka gpu in X1 laptop chips)
- a505 support
- fixes
Signed-off-by: default avatarDaniel Vetter <daniel.vetter@ffwll.ch>
From: Rob Clark <robdclark@gmail.com>
Link: https://patchwork.freedesktop.org/patch/msgid/CAF6AEGvZQpYEHpSCgXGJ2kaHJDK6QFAFfTsfiWm4b2zZOnjXGw@mail.gmail.com
parents d076e2bd fe34394e
...@@ -32,6 +32,7 @@ properties: ...@@ -32,6 +32,7 @@ properties:
- qcom,sm6125-dsi-ctrl - qcom,sm6125-dsi-ctrl
- qcom,sm6350-dsi-ctrl - qcom,sm6350-dsi-ctrl
- qcom,sm6375-dsi-ctrl - qcom,sm6375-dsi-ctrl
- qcom,sm7150-dsi-ctrl
- qcom,sm8150-dsi-ctrl - qcom,sm8150-dsi-ctrl
- qcom,sm8250-dsi-ctrl - qcom,sm8250-dsi-ctrl
- qcom,sm8350-dsi-ctrl - qcom,sm8350-dsi-ctrl
...@@ -162,6 +163,22 @@ properties: ...@@ -162,6 +163,22 @@ properties:
items: items:
enum: [ 0, 1, 2, 3 ] enum: [ 0, 1, 2, 3 ]
qcom,te-source:
$ref: /schemas/types.yaml#/definitions/string
description:
Specifies the source of vsync signal from the panel used for
tearing elimination.
default: mdp_vsync_p
enum:
- mdp_vsync_p
- mdp_vsync_s
- mdp_vsync_e
- timer0
- timer1
- timer2
- timer3
- timer4
required: required:
- port@0 - port@0
- port@1 - port@1
...@@ -332,6 +349,7 @@ allOf: ...@@ -332,6 +349,7 @@ allOf:
enum: enum:
- qcom,sc7180-dsi-ctrl - qcom,sc7180-dsi-ctrl
- qcom,sc7280-dsi-ctrl - qcom,sc7280-dsi-ctrl
- qcom,sm7150-dsi-ctrl
- qcom,sm8150-dsi-ctrl - qcom,sm8150-dsi-ctrl
- qcom,sm8250-dsi-ctrl - qcom,sm8250-dsi-ctrl
- qcom,sm8350-dsi-ctrl - qcom,sm8350-dsi-ctrl
...@@ -452,6 +470,7 @@ examples: ...@@ -452,6 +470,7 @@ examples:
dsi0_out: endpoint { dsi0_out: endpoint {
remote-endpoint = <&sn65dsi86_in>; remote-endpoint = <&sn65dsi86_in>;
data-lanes = <0 1 2 3>; data-lanes = <0 1 2 3>;
qcom,te-source = "mdp_vsync_e";
}; };
}; };
}; };
......
...@@ -16,6 +16,7 @@ properties: ...@@ -16,6 +16,7 @@ properties:
compatible: compatible:
enum: enum:
- qcom,dsi-phy-28nm-8226 - qcom,dsi-phy-28nm-8226
- qcom,dsi-phy-28nm-8937
- qcom,dsi-phy-28nm-8960 - qcom,dsi-phy-28nm-8960
- qcom,dsi-phy-28nm-hpm - qcom,dsi-phy-28nm-hpm
- qcom,dsi-phy-28nm-hpm-fam-b - qcom,dsi-phy-28nm-hpm-fam-b
......
...@@ -23,6 +23,9 @@ properties: ...@@ -23,6 +23,9 @@ properties:
- items: - items:
- pattern: '^qcom,adreno-gmu-[67][0-9][0-9]\.[0-9]$' - pattern: '^qcom,adreno-gmu-[67][0-9][0-9]\.[0-9]$'
- const: qcom,adreno-gmu - const: qcom,adreno-gmu
- items:
- pattern: '^qcom,adreno-gmu-x[1-9][0-9][0-9]\.[0-9]$'
- const: qcom,adreno-gmu
- const: qcom,adreno-gmu-wrapper - const: qcom,adreno-gmu-wrapper
reg: reg:
...@@ -225,6 +228,7 @@ allOf: ...@@ -225,6 +228,7 @@ allOf:
- qcom,adreno-gmu-730.1 - qcom,adreno-gmu-730.1
- qcom,adreno-gmu-740.1 - qcom,adreno-gmu-740.1
- qcom,adreno-gmu-750.1 - qcom,adreno-gmu-750.1
- qcom,adreno-gmu-x185.1
then: then:
properties: properties:
reg: reg:
......
...@@ -10,6 +10,18 @@ title: Adreno or Snapdragon GPUs ...@@ -10,6 +10,18 @@ title: Adreno or Snapdragon GPUs
maintainers: maintainers:
- Rob Clark <robdclark@gmail.com> - Rob Clark <robdclark@gmail.com>
# dtschema does not select nodes based on pattern+const, so add custom select
# as a work-around:
select:
properties:
compatible:
contains:
enum:
- qcom,adreno
- amd,imageon
required:
- compatible
properties: properties:
compatible: compatible:
oneOf: oneOf:
...@@ -17,7 +29,7 @@ properties: ...@@ -17,7 +29,7 @@ properties:
The driver is parsing the compat string for Adreno to The driver is parsing the compat string for Adreno to
figure out the chip-id. figure out the chip-id.
items: items:
- pattern: '^qcom,adreno-[0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f][0-9a-f]$' - pattern: '^qcom,adreno-[0-9a-f]{8}$'
- const: qcom,adreno - const: qcom,adreno
- description: | - description: |
The driver is parsing the compat string for Adreno to The driver is parsing the compat string for Adreno to
...@@ -32,9 +44,13 @@ properties: ...@@ -32,9 +44,13 @@ properties:
- pattern: '^amd,imageon-200\.[0-1]$' - pattern: '^amd,imageon-200\.[0-1]$'
- const: amd,imageon - const: amd,imageon
clocks: true clocks:
minItems: 2
maxItems: 7
clock-names: true clock-names:
minItems: 2
maxItems: 7
reg: reg:
minItems: 1 minItems: 1
...@@ -42,7 +58,10 @@ properties: ...@@ -42,7 +58,10 @@ properties:
reg-names: reg-names:
minItems: 1 minItems: 1
maxItems: 3 items:
- const: kgsl_3d0_reg_memory
- const: cx_mem
- const: cx_dbgc
interrupts: interrupts:
maxItems: 1 maxItems: 1
......
...@@ -25,6 +25,7 @@ properties: ...@@ -25,6 +25,7 @@ properties:
- qcom,msm8226-mdp5 - qcom,msm8226-mdp5
- qcom,msm8916-mdp5 - qcom,msm8916-mdp5
- qcom,msm8917-mdp5 - qcom,msm8917-mdp5
- qcom,msm8937-mdp5
- qcom,msm8953-mdp5 - qcom,msm8953-mdp5
- qcom,msm8974-mdp5 - qcom,msm8974-mdp5
- qcom,msm8976-mdp5 - qcom,msm8976-mdp5
......
...@@ -126,6 +126,7 @@ patternProperties: ...@@ -126,6 +126,7 @@ patternProperties:
- qcom,dsi-phy-14nm-8953 - qcom,dsi-phy-14nm-8953
- qcom,dsi-phy-20nm - qcom,dsi-phy-20nm
- qcom,dsi-phy-28nm-8226 - qcom,dsi-phy-28nm-8226
- qcom,dsi-phy-28nm-8937
- qcom,dsi-phy-28nm-hpm - qcom,dsi-phy-28nm-hpm
- qcom,dsi-phy-28nm-hpm-fam-b - qcom,dsi-phy-28nm-hpm-fam-b
- qcom,dsi-phy-28nm-lp - qcom,dsi-phy-28nm-lp
......
# SPDX-License-Identifier: GPL-2.0-only OR BSD-2-Clause
%YAML 1.2
---
$id: http://devicetree.org/schemas/display/msm/qcom,sm7150-dpu.yaml#
$schema: http://devicetree.org/meta-schemas/core.yaml#
title: Qualcomm SM7150 Display Processing Unit (DPU)
maintainers:
- Danila Tikhonov <danila@jiaxyga.com>
$ref: /schemas/display/msm/dpu-common.yaml#
properties:
compatible:
const: qcom,sm7150-dpu
reg:
items:
- description: Address offset and size for mdp register set
- description: Address offset and size for vbif register set
reg-names:
items:
- const: mdp
- const: vbif
clocks:
items:
- description: Display hf axi clock
- description: Display ahb clock
- description: Display rotator clock
- description: Display lut clock
- description: Display core clock
- description: Display vsync clock
clock-names:
items:
- const: bus
- const: iface
- const: rot
- const: lut
- const: core
- const: vsync
required:
- compatible
- reg
- reg-names
- clocks
- clock-names
unevaluatedProperties: false
examples:
- |
#include <dt-bindings/interrupt-controller/arm-gic.h>
#include <dt-bindings/power/qcom,rpmhpd.h>
display-controller@ae01000 {
compatible = "qcom,sm7150-dpu";
reg = <0x0ae01000 0x8f000>,
<0x0aeb0000 0x2008>;
reg-names = "mdp", "vbif";
clocks = <&gcc_disp_hf_axi_clk>,
<&dispcc_mdss_ahb_clk>,
<&dispcc_mdss_rot_clk>,
<&dispcc_mdss_mdp_lut_clk>,
<&dispcc_mdss_mdp_clk>,
<&dispcc_mdss_vsync_clk>;
clock-names = "bus",
"iface",
"rot",
"lut",
"core",
"vsync";
assigned-clocks = <&dispcc_mdss_vsync_clk>;
assigned-clock-rates = <19200000>;
operating-points-v2 = <&mdp_opp_table>;
power-domains = <&rpmhpd RPMHPD_CX>;
interrupt-parent = <&mdss>;
interrupts = <0>;
ports {
#address-cells = <1>;
#size-cells = <0>;
port@0 {
reg = <0>;
dpu_intf1_out: endpoint {
remote-endpoint = <&mdss_dsi0_in>;
};
};
port@1 {
reg = <1>;
dpu_intf2_out: endpoint {
remote-endpoint = <&mdss_dsi1_in>;
};
};
port@2 {
reg = <2>;
dpu_intf0_out: endpoint {
remote-endpoint = <&dp_in>;
};
};
};
mdp_opp_table: opp-table {
compatible = "operating-points-v2";
opp-19200000 {
opp-hz = /bits/ 64 <19200000>;
required-opps = <&rpmhpd_opp_min_svs>;
};
opp-200000000 {
opp-hz = /bits/ 64 <200000000>;
required-opps = <&rpmhpd_opp_low_svs>;
};
opp-300000000 {
opp-hz = /bits/ 64 <300000000>;
required-opps = <&rpmhpd_opp_svs>;
};
opp-344000000 {
opp-hz = /bits/ 64 <344000000>;
required-opps = <&rpmhpd_opp_svs_l1>;
};
opp-430000000 {
opp-hz = /bits/ 64 <430000000>;
required-opps = <&rpmhpd_opp_nom>;
};
};
};
...
...@@ -1394,6 +1394,20 @@ int qcom_scm_lmh_dcvsh(u32 payload_fn, u32 payload_reg, u32 payload_val, ...@@ -1394,6 +1394,20 @@ int qcom_scm_lmh_dcvsh(u32 payload_fn, u32 payload_reg, u32 payload_val,
} }
EXPORT_SYMBOL_GPL(qcom_scm_lmh_dcvsh); EXPORT_SYMBOL_GPL(qcom_scm_lmh_dcvsh);
int qcom_scm_gpu_init_regs(u32 gpu_req)
{
struct qcom_scm_desc desc = {
.svc = QCOM_SCM_SVC_GPU,
.cmd = QCOM_SCM_SVC_GPU_INIT_REGS,
.arginfo = QCOM_SCM_ARGS(1),
.args[0] = gpu_req,
.owner = ARM_SMCCC_OWNER_SIP,
};
return qcom_scm_call(__scm->dev, &desc, NULL);
}
EXPORT_SYMBOL_GPL(qcom_scm_gpu_init_regs);
static int qcom_scm_find_dload_address(struct device *dev, u64 *addr) static int qcom_scm_find_dload_address(struct device *dev, u64 *addr)
{ {
struct device_node *tcsr; struct device_node *tcsr;
......
...@@ -138,6 +138,9 @@ int scm_legacy_call(struct device *dev, const struct qcom_scm_desc *desc, ...@@ -138,6 +138,9 @@ int scm_legacy_call(struct device *dev, const struct qcom_scm_desc *desc,
#define QCOM_SCM_WAITQ_RESUME 0x02 #define QCOM_SCM_WAITQ_RESUME 0x02
#define QCOM_SCM_WAITQ_GET_WQ_CTX 0x03 #define QCOM_SCM_WAITQ_GET_WQ_CTX 0x03
#define QCOM_SCM_SVC_GPU 0x28
#define QCOM_SCM_SVC_GPU_INIT_REGS 0x01
/* common error codes */ /* common error codes */
#define QCOM_SCM_V2_EBUSY -12 #define QCOM_SCM_V2_EBUSY -12
#define QCOM_SCM_ENOMEM -5 #define QCOM_SCM_ENOMEM -5
......
...@@ -33,6 +33,7 @@ config DRM_MSM ...@@ -33,6 +33,7 @@ config DRM_MSM
select PM_OPP select PM_OPP
select NVMEM select NVMEM
select PM_GENERIC_DOMAINS select PM_GENERIC_DOMAINS
select TRACE_GPU_MEM
help help
DRM/KMS driver for MSM/snapdragon. DRM/KMS driver for MSM/snapdragon.
......
...@@ -8,13 +8,18 @@ ccflags-$(CONFIG_DRM_MSM_DP) += -I $(src)/dp ...@@ -8,13 +8,18 @@ ccflags-$(CONFIG_DRM_MSM_DP) += -I $(src)/dp
adreno-y := \ adreno-y := \
adreno/adreno_device.o \ adreno/adreno_device.o \
adreno/adreno_gpu.o \ adreno/adreno_gpu.o \
adreno/a2xx_catalog.o \
adreno/a2xx_gpu.o \ adreno/a2xx_gpu.o \
adreno/a2xx_gpummu.o \ adreno/a2xx_gpummu.o \
adreno/a3xx_catalog.o \
adreno/a3xx_gpu.o \ adreno/a3xx_gpu.o \
adreno/a4xx_catalog.o \
adreno/a4xx_gpu.o \ adreno/a4xx_gpu.o \
adreno/a5xx_catalog.o \
adreno/a5xx_gpu.o \ adreno/a5xx_gpu.o \
adreno/a5xx_power.o \ adreno/a5xx_power.o \
adreno/a5xx_preempt.o \ adreno/a5xx_preempt.o \
adreno/a6xx_catalog.o \
adreno/a6xx_gpu.o \ adreno/a6xx_gpu.o \
adreno/a6xx_gmu.o \ adreno/a6xx_gmu.o \
adreno/a6xx_hfi.o \ adreno/a6xx_hfi.o \
......
// SPDX-License-Identifier: GPL-2.0-only
/*
* Copyright (C) 2013-2014 Red Hat
* Author: Rob Clark <robdclark@gmail.com>
*
* Copyright (c) 2014,2017 The Linux Foundation. All rights reserved.
*/
#include "adreno_gpu.h"
static const struct adreno_info a2xx_gpus[] = {
{
.chip_ids = ADRENO_CHIP_IDS(0x02000000),
.family = ADRENO_2XX_GEN1,
.revn = 200,
.fw = {
[ADRENO_FW_PM4] = "yamato_pm4.fw",
[ADRENO_FW_PFP] = "yamato_pfp.fw",
},
.gmem = SZ_256K,
.inactive_period = DRM_MSM_INACTIVE_PERIOD,
.init = a2xx_gpu_init,
}, { /* a200 on i.mx51 has only 128kib gmem */
.chip_ids = ADRENO_CHIP_IDS(0x02000001),
.family = ADRENO_2XX_GEN1,
.revn = 201,
.fw = {
[ADRENO_FW_PM4] = "yamato_pm4.fw",
[ADRENO_FW_PFP] = "yamato_pfp.fw",
},
.gmem = SZ_128K,
.inactive_period = DRM_MSM_INACTIVE_PERIOD,
.init = a2xx_gpu_init,
}, {
.chip_ids = ADRENO_CHIP_IDS(0x02020000),
.family = ADRENO_2XX_GEN2,
.revn = 220,
.fw = {
[ADRENO_FW_PM4] = "leia_pm4_470.fw",
[ADRENO_FW_PFP] = "leia_pfp_470.fw",
},
.gmem = SZ_512K,
.inactive_period = DRM_MSM_INACTIVE_PERIOD,
.init = a2xx_gpu_init,
}
};
DECLARE_ADRENO_GPULIST(a2xx);
MODULE_FIRMWARE("qcom/leia_pfp_470.fw");
MODULE_FIRMWARE("qcom/leia_pm4_470.fw");
MODULE_FIRMWARE("qcom/yamato_pfp.fw");
MODULE_FIRMWARE("qcom/yamato_pm4.fw");
// SPDX-License-Identifier: GPL-2.0-only
/*
* Copyright (C) 2013-2014 Red Hat
* Author: Rob Clark <robdclark@gmail.com>
*
* Copyright (c) 2014,2017 The Linux Foundation. All rights reserved.
*/
#include "adreno_gpu.h"
static const struct adreno_info a3xx_gpus[] = {
{
.chip_ids = ADRENO_CHIP_IDS(0x03000512),
.family = ADRENO_3XX,
.fw = {
[ADRENO_FW_PM4] = "a330_pm4.fw",
[ADRENO_FW_PFP] = "a330_pfp.fw",
},
.gmem = SZ_128K,
.inactive_period = DRM_MSM_INACTIVE_PERIOD,
.init = a3xx_gpu_init,
}, {
.chip_ids = ADRENO_CHIP_IDS(0x03000520),
.family = ADRENO_3XX,
.revn = 305,
.fw = {
[ADRENO_FW_PM4] = "a300_pm4.fw",
[ADRENO_FW_PFP] = "a300_pfp.fw",
},
.gmem = SZ_256K,
.inactive_period = DRM_MSM_INACTIVE_PERIOD,
.init = a3xx_gpu_init,
}, {
.chip_ids = ADRENO_CHIP_IDS(0x03000600),
.family = ADRENO_3XX,
.revn = 307, /* because a305c is revn==306 */
.fw = {
[ADRENO_FW_PM4] = "a300_pm4.fw",
[ADRENO_FW_PFP] = "a300_pfp.fw",
},
.gmem = SZ_128K,
.inactive_period = DRM_MSM_INACTIVE_PERIOD,
.init = a3xx_gpu_init,
}, {
.chip_ids = ADRENO_CHIP_IDS(
0x03020000,
0x03020001,
0x03020002
),
.family = ADRENO_3XX,
.revn = 320,
.fw = {
[ADRENO_FW_PM4] = "a300_pm4.fw",
[ADRENO_FW_PFP] = "a300_pfp.fw",
},
.gmem = SZ_512K,
.inactive_period = DRM_MSM_INACTIVE_PERIOD,
.init = a3xx_gpu_init,
}, {
.chip_ids = ADRENO_CHIP_IDS(
0x03030000,
0x03030001,
0x03030002
),
.family = ADRENO_3XX,
.revn = 330,
.fw = {
[ADRENO_FW_PM4] = "a330_pm4.fw",
[ADRENO_FW_PFP] = "a330_pfp.fw",
},
.gmem = SZ_1M,
.inactive_period = DRM_MSM_INACTIVE_PERIOD,
.init = a3xx_gpu_init,
}
};
DECLARE_ADRENO_GPULIST(a3xx);
MODULE_FIRMWARE("qcom/a300_pm4.fw");
MODULE_FIRMWARE("qcom/a300_pfp.fw");
MODULE_FIRMWARE("qcom/a330_pm4.fw");
MODULE_FIRMWARE("qcom/a330_pfp.fw");
// SPDX-License-Identifier: GPL-2.0-only
/*
* Copyright (C) 2013-2014 Red Hat
* Author: Rob Clark <robdclark@gmail.com>
*
* Copyright (c) 2014,2017 The Linux Foundation. All rights reserved.
*/
#include "adreno_gpu.h"
static const struct adreno_info a4xx_gpus[] = {
{
.chip_ids = ADRENO_CHIP_IDS(0x04000500),
.family = ADRENO_4XX,
.revn = 405,
.fw = {
[ADRENO_FW_PM4] = "a420_pm4.fw",
[ADRENO_FW_PFP] = "a420_pfp.fw",
},
.gmem = SZ_256K,
.inactive_period = DRM_MSM_INACTIVE_PERIOD,
.init = a4xx_gpu_init,
}, {
.chip_ids = ADRENO_CHIP_IDS(0x04020000),
.family = ADRENO_4XX,
.revn = 420,
.fw = {
[ADRENO_FW_PM4] = "a420_pm4.fw",
[ADRENO_FW_PFP] = "a420_pfp.fw",
},
.gmem = (SZ_1M + SZ_512K),
.inactive_period = DRM_MSM_INACTIVE_PERIOD,
.init = a4xx_gpu_init,
}, {
.chip_ids = ADRENO_CHIP_IDS(0x04030002),
.family = ADRENO_4XX,
.revn = 430,
.fw = {
[ADRENO_FW_PM4] = "a420_pm4.fw",
[ADRENO_FW_PFP] = "a420_pfp.fw",
},
.gmem = (SZ_1M + SZ_512K),
.inactive_period = DRM_MSM_INACTIVE_PERIOD,
.init = a4xx_gpu_init,
}
};
DECLARE_ADRENO_GPULIST(a4xx);
MODULE_FIRMWARE("qcom/a420_pm4.fw");
MODULE_FIRMWARE("qcom/a420_pfp.fw");
// SPDX-License-Identifier: GPL-2.0-only
/*
* Copyright (C) 2013-2014 Red Hat
* Author: Rob Clark <robdclark@gmail.com>
*
* Copyright (c) 2014,2017 The Linux Foundation. All rights reserved.
*/
#include "adreno_gpu.h"
static const struct adreno_info a5xx_gpus[] = {
{
.chip_ids = ADRENO_CHIP_IDS(0x05000500),
.family = ADRENO_5XX,
.revn = 505,
.fw = {
[ADRENO_FW_PM4] = "a530_pm4.fw",
[ADRENO_FW_PFP] = "a530_pfp.fw",
},
.gmem = (SZ_128K + SZ_8K),
.inactive_period = DRM_MSM_INACTIVE_PERIOD,
.quirks = ADRENO_QUIRK_TWO_PASS_USE_WFI |
ADRENO_QUIRK_LMLOADKILL_DISABLE,
.init = a5xx_gpu_init,
}, {
.chip_ids = ADRENO_CHIP_IDS(0x05000600),
.family = ADRENO_5XX,
.revn = 506,
.fw = {
[ADRENO_FW_PM4] = "a530_pm4.fw",
[ADRENO_FW_PFP] = "a530_pfp.fw",
},
.gmem = (SZ_128K + SZ_8K),
/*
* Increase inactive period to 250 to avoid bouncing
* the GDSC which appears to make it grumpy
*/
.inactive_period = 250,
.quirks = ADRENO_QUIRK_TWO_PASS_USE_WFI |
ADRENO_QUIRK_LMLOADKILL_DISABLE,
.init = a5xx_gpu_init,
.zapfw = "a506_zap.mdt",
}, {
.chip_ids = ADRENO_CHIP_IDS(0x05000800),
.family = ADRENO_5XX,
.revn = 508,
.fw = {
[ADRENO_FW_PM4] = "a530_pm4.fw",
[ADRENO_FW_PFP] = "a530_pfp.fw",
},
.gmem = (SZ_128K + SZ_8K),
/*
* Increase inactive period to 250 to avoid bouncing
* the GDSC which appears to make it grumpy
*/
.inactive_period = 250,
.quirks = ADRENO_QUIRK_LMLOADKILL_DISABLE,
.init = a5xx_gpu_init,
.zapfw = "a508_zap.mdt",
}, {
.chip_ids = ADRENO_CHIP_IDS(0x05000900),
.family = ADRENO_5XX,
.revn = 509,
.fw = {
[ADRENO_FW_PM4] = "a530_pm4.fw",
[ADRENO_FW_PFP] = "a530_pfp.fw",
},
.gmem = (SZ_256K + SZ_16K),
/*
* Increase inactive period to 250 to avoid bouncing
* the GDSC which appears to make it grumpy
*/
.inactive_period = 250,
.quirks = ADRENO_QUIRK_LMLOADKILL_DISABLE,
.init = a5xx_gpu_init,
/* Adreno 509 uses the same ZAP as 512 */
.zapfw = "a512_zap.mdt",
}, {
.chip_ids = ADRENO_CHIP_IDS(0x05010000),
.family = ADRENO_5XX,
.revn = 510,
.fw = {
[ADRENO_FW_PM4] = "a530_pm4.fw",
[ADRENO_FW_PFP] = "a530_pfp.fw",
},
.gmem = SZ_256K,
/*
* Increase inactive period to 250 to avoid bouncing
* the GDSC which appears to make it grumpy
*/
.inactive_period = 250,
.init = a5xx_gpu_init,
}, {
.chip_ids = ADRENO_CHIP_IDS(0x05010200),
.family = ADRENO_5XX,
.revn = 512,
.fw = {
[ADRENO_FW_PM4] = "a530_pm4.fw",
[ADRENO_FW_PFP] = "a530_pfp.fw",
},
.gmem = (SZ_256K + SZ_16K),
/*
* Increase inactive period to 250 to avoid bouncing
* the GDSC which appears to make it grumpy
*/
.inactive_period = 250,
.quirks = ADRENO_QUIRK_LMLOADKILL_DISABLE,
.init = a5xx_gpu_init,
.zapfw = "a512_zap.mdt",
}, {
.chip_ids = ADRENO_CHIP_IDS(
0x05030002,
0x05030004
),
.family = ADRENO_5XX,
.revn = 530,
.fw = {
[ADRENO_FW_PM4] = "a530_pm4.fw",
[ADRENO_FW_PFP] = "a530_pfp.fw",
[ADRENO_FW_GPMU] = "a530v3_gpmu.fw2",
},
.gmem = SZ_1M,
/*
* Increase inactive period to 250 to avoid bouncing
* the GDSC which appears to make it grumpy
*/
.inactive_period = 250,
.quirks = ADRENO_QUIRK_TWO_PASS_USE_WFI |
ADRENO_QUIRK_FAULT_DETECT_MASK,
.init = a5xx_gpu_init,
.zapfw = "a530_zap.mdt",
}, {
.chip_ids = ADRENO_CHIP_IDS(0x05040001),
.family = ADRENO_5XX,
.revn = 540,
.fw = {
[ADRENO_FW_PM4] = "a530_pm4.fw",
[ADRENO_FW_PFP] = "a530_pfp.fw",
[ADRENO_FW_GPMU] = "a540_gpmu.fw2",
},
.gmem = SZ_1M,
/*
* Increase inactive period to 250 to avoid bouncing
* the GDSC which appears to make it grumpy
*/
.inactive_period = 250,
.quirks = ADRENO_QUIRK_LMLOADKILL_DISABLE,
.init = a5xx_gpu_init,
.zapfw = "a540_zap.mdt",
}
};
DECLARE_ADRENO_GPULIST(a5xx);
MODULE_FIRMWARE("qcom/a530_pm4.fw");
MODULE_FIRMWARE("qcom/a530_pfp.fw");
MODULE_FIRMWARE("qcom/a530v3_gpmu.fw2");
MODULE_FIRMWARE("qcom/a530_zap.mdt");
MODULE_FIRMWARE("qcom/a530_zap.b00");
MODULE_FIRMWARE("qcom/a530_zap.b01");
MODULE_FIRMWARE("qcom/a530_zap.b02");
MODULE_FIRMWARE("qcom/a540_gpmu.fw2");
...@@ -439,7 +439,8 @@ void a5xx_set_hwcg(struct msm_gpu *gpu, bool state) ...@@ -439,7 +439,8 @@ void a5xx_set_hwcg(struct msm_gpu *gpu, bool state)
const struct adreno_five_hwcg_regs *regs; const struct adreno_five_hwcg_regs *regs;
unsigned int i, sz; unsigned int i, sz;
if (adreno_is_a506(adreno_gpu) || adreno_is_a508(adreno_gpu)) { if (adreno_is_a505(adreno_gpu) || adreno_is_a506(adreno_gpu) ||
adreno_is_a508(adreno_gpu)) {
regs = a50x_hwcg; regs = a50x_hwcg;
sz = ARRAY_SIZE(a50x_hwcg); sz = ARRAY_SIZE(a50x_hwcg);
} else if (adreno_is_a509(adreno_gpu) || adreno_is_a512(adreno_gpu)) { } else if (adreno_is_a509(adreno_gpu) || adreno_is_a512(adreno_gpu)) {
...@@ -483,7 +484,8 @@ static int a5xx_me_init(struct msm_gpu *gpu) ...@@ -483,7 +484,8 @@ static int a5xx_me_init(struct msm_gpu *gpu)
OUT_RING(ring, 0x00000000); OUT_RING(ring, 0x00000000);
/* Specify workarounds for various microcode issues */ /* Specify workarounds for various microcode issues */
if (adreno_is_a506(adreno_gpu) || adreno_is_a530(adreno_gpu)) { if (adreno_is_a505(adreno_gpu) || adreno_is_a506(adreno_gpu) ||
adreno_is_a530(adreno_gpu)) {
/* Workaround for token end syncs /* Workaround for token end syncs
* Force a WFI after every direct-render 3D mode draw and every * Force a WFI after every direct-render 3D mode draw and every
* 2D mode 3 draw * 2D mode 3 draw
...@@ -752,10 +754,11 @@ static int a5xx_hw_init(struct msm_gpu *gpu) ...@@ -752,10 +754,11 @@ static int a5xx_hw_init(struct msm_gpu *gpu)
0x00100000 + adreno_gpu->info->gmem - 1); 0x00100000 + adreno_gpu->info->gmem - 1);
gpu_write(gpu, REG_A5XX_UCHE_GMEM_RANGE_MAX_HI, 0x00000000); gpu_write(gpu, REG_A5XX_UCHE_GMEM_RANGE_MAX_HI, 0x00000000);
if (adreno_is_a506(adreno_gpu) || adreno_is_a508(adreno_gpu) || if (adreno_is_a505(adreno_gpu) || adreno_is_a506(adreno_gpu) ||
adreno_is_a510(adreno_gpu)) { adreno_is_a508(adreno_gpu) || adreno_is_a510(adreno_gpu)) {
gpu_write(gpu, REG_A5XX_CP_MEQ_THRESHOLDS, 0x20); gpu_write(gpu, REG_A5XX_CP_MEQ_THRESHOLDS, 0x20);
if (adreno_is_a506(adreno_gpu) || adreno_is_a508(adreno_gpu)) if (adreno_is_a505(adreno_gpu) || adreno_is_a506(adreno_gpu) ||
adreno_is_a508(adreno_gpu))
gpu_write(gpu, REG_A5XX_CP_MERCIU_SIZE, 0x400); gpu_write(gpu, REG_A5XX_CP_MERCIU_SIZE, 0x400);
else else
gpu_write(gpu, REG_A5XX_CP_MERCIU_SIZE, 0x20); gpu_write(gpu, REG_A5XX_CP_MERCIU_SIZE, 0x20);
...@@ -771,7 +774,8 @@ static int a5xx_hw_init(struct msm_gpu *gpu) ...@@ -771,7 +774,8 @@ static int a5xx_hw_init(struct msm_gpu *gpu)
gpu_write(gpu, REG_A5XX_CP_ROQ_THRESHOLDS_1, 0x40201B16); gpu_write(gpu, REG_A5XX_CP_ROQ_THRESHOLDS_1, 0x40201B16);
} }
if (adreno_is_a506(adreno_gpu) || adreno_is_a508(adreno_gpu)) if (adreno_is_a505(adreno_gpu) || adreno_is_a506(adreno_gpu) ||
adreno_is_a508(adreno_gpu))
gpu_write(gpu, REG_A5XX_PC_DBG_ECO_CNTL, gpu_write(gpu, REG_A5XX_PC_DBG_ECO_CNTL,
(0x100 << 11 | 0x100 << 22)); (0x100 << 11 | 0x100 << 22));
else if (adreno_is_a509(adreno_gpu) || adreno_is_a510(adreno_gpu) || else if (adreno_is_a509(adreno_gpu) || adreno_is_a510(adreno_gpu) ||
...@@ -789,8 +793,9 @@ static int a5xx_hw_init(struct msm_gpu *gpu) ...@@ -789,8 +793,9 @@ static int a5xx_hw_init(struct msm_gpu *gpu)
* Disable the RB sampler datapath DP2 clock gating optimization * Disable the RB sampler datapath DP2 clock gating optimization
* for 1-SP GPUs, as it is enabled by default. * for 1-SP GPUs, as it is enabled by default.
*/ */
if (adreno_is_a506(adreno_gpu) || adreno_is_a508(adreno_gpu) || if (adreno_is_a505(adreno_gpu) || adreno_is_a506(adreno_gpu) ||
adreno_is_a509(adreno_gpu) || adreno_is_a512(adreno_gpu)) adreno_is_a508(adreno_gpu) || adreno_is_a509(adreno_gpu) ||
adreno_is_a512(adreno_gpu))
gpu_rmw(gpu, REG_A5XX_RB_DBG_ECO_CNTL, 0, (1 << 9)); gpu_rmw(gpu, REG_A5XX_RB_DBG_ECO_CNTL, 0, (1 << 9));
/* Disable UCHE global filter as SP can invalidate/flush independently */ /* Disable UCHE global filter as SP can invalidate/flush independently */
...@@ -1345,7 +1350,7 @@ static int a5xx_pm_resume(struct msm_gpu *gpu) ...@@ -1345,7 +1350,7 @@ static int a5xx_pm_resume(struct msm_gpu *gpu)
if (ret) if (ret)
return ret; return ret;
/* Adreno 506, 508, 509, 510, 512 needs manual RBBM sus/res control */ /* Adreno 505, 506, 508, 509, 510, 512 needs manual RBBM sus/res control */
if (!(adreno_is_a530(adreno_gpu) || adreno_is_a540(adreno_gpu))) { if (!(adreno_is_a530(adreno_gpu) || adreno_is_a540(adreno_gpu))) {
/* Halt the sp_input_clk at HM level */ /* Halt the sp_input_clk at HM level */
gpu_write(gpu, REG_A5XX_RBBM_CLOCK_CNTL, 0x00000055); gpu_write(gpu, REG_A5XX_RBBM_CLOCK_CNTL, 0x00000055);
...@@ -1388,9 +1393,9 @@ static int a5xx_pm_suspend(struct msm_gpu *gpu) ...@@ -1388,9 +1393,9 @@ static int a5xx_pm_suspend(struct msm_gpu *gpu)
u32 mask = 0xf; u32 mask = 0xf;
int i, ret; int i, ret;
/* A506, A508, A510 have 3 XIN ports in VBIF */ /* A505, A506, A508, A510 have 3 XIN ports in VBIF */
if (adreno_is_a506(adreno_gpu) || adreno_is_a508(adreno_gpu) || if (adreno_is_a505(adreno_gpu) || adreno_is_a506(adreno_gpu) ||
adreno_is_a510(adreno_gpu)) adreno_is_a508(adreno_gpu) || adreno_is_a510(adreno_gpu))
mask = 0x7; mask = 0x7;
/* Clear the VBIF pipe before shutting down */ /* Clear the VBIF pipe before shutting down */
......
This diff is collapsed.
...@@ -466,9 +466,7 @@ static int a6xx_rpmh_start(struct a6xx_gmu *gmu) ...@@ -466,9 +466,7 @@ static int a6xx_rpmh_start(struct a6xx_gmu *gmu)
int ret; int ret;
u32 val; u32 val;
gmu_write(gmu, REG_A6XX_GMU_RSCC_CONTROL_REQ, 1 << 1); gmu_write(gmu, REG_A6XX_GMU_RSCC_CONTROL_REQ, BIT(1));
/* Wait for the register to finish posting */
wmb();
ret = gmu_poll_timeout(gmu, REG_A6XX_GMU_RSCC_CONTROL_ACK, val, ret = gmu_poll_timeout(gmu, REG_A6XX_GMU_RSCC_CONTROL_ACK, val,
val & (1 << 1), 100, 10000); val & (1 << 1), 100, 10000);
...@@ -769,8 +767,9 @@ static int a6xx_gmu_fw_start(struct a6xx_gmu *gmu, unsigned int state) ...@@ -769,8 +767,9 @@ static int a6xx_gmu_fw_start(struct a6xx_gmu *gmu, unsigned int state)
{ {
struct a6xx_gpu *a6xx_gpu = container_of(gmu, struct a6xx_gpu, gmu); struct a6xx_gpu *a6xx_gpu = container_of(gmu, struct a6xx_gpu, gmu);
struct adreno_gpu *adreno_gpu = &a6xx_gpu->base; struct adreno_gpu *adreno_gpu = &a6xx_gpu->base;
const struct a6xx_info *a6xx_info = adreno_gpu->info->a6xx;
u32 fence_range_lower, fence_range_upper; u32 fence_range_lower, fence_range_upper;
u32 chipid, chipid_min = 0; u32 chipid = 0;
int ret; int ret;
/* Vote veto for FAL10 */ /* Vote veto for FAL10 */
...@@ -830,27 +829,8 @@ static int a6xx_gmu_fw_start(struct a6xx_gmu *gmu, unsigned int state) ...@@ -830,27 +829,8 @@ static int a6xx_gmu_fw_start(struct a6xx_gmu *gmu, unsigned int state)
*/ */
gmu_write(gmu, REG_A6XX_GMU_CM3_CFG, 0x4052); gmu_write(gmu, REG_A6XX_GMU_CM3_CFG, 0x4052);
/* NOTE: A730 may also fall in this if-condition with a future GMU fw update. */ if (a6xx_info->gmu_chipid) {
if (adreno_is_a7xx(adreno_gpu) && !adreno_is_a730(adreno_gpu)) { chipid = a6xx_info->gmu_chipid;
/* A7xx GPUs have obfuscated chip IDs. Use constant maj = 7 */
chipid = FIELD_PREP(GENMASK(31, 24), 0x7);
/*
* The min part has a 1-1 mapping for each GPU SKU.
* This chipid that the GMU expects corresponds to the "GENX_Y_Z" naming,
* where X = major, Y = minor, Z = patchlevel, e.g. GEN7_2_1 for prod A740.
*/
if (adreno_is_a740(adreno_gpu))
chipid_min = 2;
else if (adreno_is_a750(adreno_gpu))
chipid_min = 9;
else
return -EINVAL;
chipid |= FIELD_PREP(GENMASK(23, 16), chipid_min);
/* Get the patchid (which may vary) from the device tree */
chipid |= FIELD_PREP(GENMASK(15, 8), adreno_patchid(adreno_gpu));
} else { } else {
/* /*
* Note that the GMU has a slightly different layout for * Note that the GMU has a slightly different layout for
...@@ -1329,7 +1309,13 @@ static int a6xx_gmu_rpmh_arc_votes_init(struct device *dev, u32 *votes, ...@@ -1329,7 +1309,13 @@ static int a6xx_gmu_rpmh_arc_votes_init(struct device *dev, u32 *votes,
if (!pri_count) if (!pri_count)
return -EINVAL; return -EINVAL;
sec = cmd_db_read_aux_data("mx.lvl", &sec_count); /*
* Some targets have a separate gfx mxc rail. So try to read that first and then fall back
* to regular mx rail if it is missing
*/
sec = cmd_db_read_aux_data("gmxc.lvl", &sec_count);
if (IS_ERR(sec) && sec != ERR_PTR(-EPROBE_DEFER))
sec = cmd_db_read_aux_data("mx.lvl", &sec_count);
if (IS_ERR(sec)) if (IS_ERR(sec))
return PTR_ERR(sec); return PTR_ERR(sec);
......
This diff is collapsed.
...@@ -12,6 +12,18 @@ ...@@ -12,6 +12,18 @@
extern bool hang_debug; extern bool hang_debug;
/**
* struct a6xx_info - a6xx specific information from device table
*
* @hwcg: hw clock gating register sequence
* @protect: CP_PROTECT settings
*/
struct a6xx_info {
const struct adreno_reglist *hwcg;
const struct adreno_protect *protect;
u32 gmu_chipid;
};
struct a6xx_gpu { struct a6xx_gpu {
struct adreno_gpu base; struct adreno_gpu base;
......
...@@ -8,19 +8,16 @@ ...@@ -8,19 +8,16 @@
#include "a6xx_gpu_state.h" #include "a6xx_gpu_state.h"
#include "a6xx_gmu.xml.h" #include "a6xx_gmu.xml.h"
/* Ignore diagnostics about register tables that we aren't using yet. We don't static const unsigned int *gen7_0_0_external_core_regs[] __always_unused;
* want to modify these headers too much from their original source. static const unsigned int *gen7_2_0_external_core_regs[] __always_unused;
*/ static const unsigned int *gen7_9_0_external_core_regs[] __always_unused;
#pragma GCC diagnostic push static struct gen7_sptp_cluster_registers gen7_9_0_sptp_clusters[] __always_unused;
#pragma GCC diagnostic ignored "-Wunused-variable" static const u32 gen7_9_0_cx_debugbus_blocks[] __always_unused;
#pragma GCC diagnostic ignored "-Wunused-const-variable"
#include "adreno_gen7_0_0_snapshot.h" #include "adreno_gen7_0_0_snapshot.h"
#include "adreno_gen7_2_0_snapshot.h" #include "adreno_gen7_2_0_snapshot.h"
#include "adreno_gen7_9_0_snapshot.h" #include "adreno_gen7_9_0_snapshot.h"
#pragma GCC diagnostic pop
struct a6xx_gpu_state_obj { struct a6xx_gpu_state_obj {
const void *handle; const void *handle;
u32 *data; u32 *data;
......
This diff is collapsed.
...@@ -46,7 +46,7 @@ static int zap_shader_load_mdt(struct msm_gpu *gpu, const char *fwname, ...@@ -46,7 +46,7 @@ static int zap_shader_load_mdt(struct msm_gpu *gpu, const char *fwname,
} }
np = of_get_child_by_name(dev->of_node, "zap-shader"); np = of_get_child_by_name(dev->of_node, "zap-shader");
if (!np) { if (!of_device_is_available(np)) {
zap_available = false; zap_available = false;
return -ENODEV; return -ENODEV;
} }
...@@ -376,6 +376,9 @@ int adreno_get_param(struct msm_gpu *gpu, struct msm_file_private *ctx, ...@@ -376,6 +376,9 @@ int adreno_get_param(struct msm_gpu *gpu, struct msm_file_private *ctx,
case MSM_PARAM_HIGHEST_BANK_BIT: case MSM_PARAM_HIGHEST_BANK_BIT:
*value = adreno_gpu->ubwc_config.highest_bank_bit; *value = adreno_gpu->ubwc_config.highest_bank_bit;
return 0; return 0;
case MSM_PARAM_RAYTRACING:
*value = adreno_gpu->has_ray_tracing;
return 0;
default: default:
DBG("%s: invalid param: %u", gpu->name, param); DBG("%s: invalid param: %u", gpu->name, param);
return -EINVAL; return -EINVAL;
...@@ -887,6 +890,7 @@ void adreno_show(struct msm_gpu *gpu, struct msm_gpu_state *state, ...@@ -887,6 +890,7 @@ void adreno_show(struct msm_gpu *gpu, struct msm_gpu_state *state,
drm_printf(p, " - iova: 0x%016llx\n", drm_printf(p, " - iova: 0x%016llx\n",
state->bos[i].iova); state->bos[i].iova);
drm_printf(p, " size: %zd\n", state->bos[i].size); drm_printf(p, " size: %zd\n", state->bos[i].size);
drm_printf(p, " flags: 0x%x\n", state->bos[i].flags);
drm_printf(p, " name: %-32s\n", state->bos[i].name); drm_printf(p, " name: %-32s\n", state->bos[i].name);
adreno_show_object(p, &state->bos[i].data, adreno_show_object(p, &state->bos[i].data,
......
...@@ -77,14 +77,13 @@ struct adreno_reglist { ...@@ -77,14 +77,13 @@ struct adreno_reglist {
u32 value; u32 value;
}; };
extern const struct adreno_reglist a612_hwcg[], a615_hwcg[], a630_hwcg[], a640_hwcg[], a650_hwcg[];
extern const struct adreno_reglist a660_hwcg[], a690_hwcg[], a702_hwcg[], a730_hwcg[], a740_hwcg[];
struct adreno_speedbin { struct adreno_speedbin {
uint16_t fuse; uint16_t fuse;
uint16_t speedbin; uint16_t speedbin;
}; };
struct a6xx_info;
struct adreno_info { struct adreno_info {
const char *machine; const char *machine;
/** /**
...@@ -101,7 +100,9 @@ struct adreno_info { ...@@ -101,7 +100,9 @@ struct adreno_info {
struct msm_gpu *(*init)(struct drm_device *dev); struct msm_gpu *(*init)(struct drm_device *dev);
const char *zapfw; const char *zapfw;
u32 inactive_period; u32 inactive_period;
const struct adreno_reglist *hwcg; union {
const struct a6xx_info *a6xx;
};
u64 address_space_size; u64 address_space_size;
/** /**
* @speedbins: Optional table of fuse to speedbin mappings * @speedbins: Optional table of fuse to speedbin mappings
...@@ -114,6 +115,16 @@ struct adreno_info { ...@@ -114,6 +115,16 @@ struct adreno_info {
#define ADRENO_CHIP_IDS(tbl...) (uint32_t[]) { tbl, 0 } #define ADRENO_CHIP_IDS(tbl...) (uint32_t[]) { tbl, 0 }
struct adreno_gpulist {
const struct adreno_info *gpus;
unsigned gpus_count;
};
#define DECLARE_ADRENO_GPULIST(name) \
const struct adreno_gpulist name ## _gpulist = { \
name ## _gpus, ARRAY_SIZE(name ## _gpus) \
}
/* /*
* Helper to build a speedbin table, ie. the table: * Helper to build a speedbin table, ie. the table:
* fuse | speedbin * fuse | speedbin
...@@ -132,6 +143,19 @@ struct adreno_info { ...@@ -132,6 +143,19 @@ struct adreno_info {
*/ */
#define ADRENO_SPEEDBINS(tbl...) (struct adreno_speedbin[]) { tbl {SHRT_MAX, 0} } #define ADRENO_SPEEDBINS(tbl...) (struct adreno_speedbin[]) { tbl {SHRT_MAX, 0} }
struct adreno_protect {
const uint32_t *regs;
uint32_t count;
uint32_t count_max;
};
#define DECLARE_ADRENO_PROTECT(name, __count_max) \
static const struct adreno_protect name = { \
.regs = name ## _regs, \
.count = ARRAY_SIZE(name ## _regs), \
.count_max = __count_max, \
};
struct adreno_gpu { struct adreno_gpu {
struct msm_gpu base; struct msm_gpu base;
const struct adreno_info *info; const struct adreno_info *info;
...@@ -182,6 +206,8 @@ struct adreno_gpu { ...@@ -182,6 +206,8 @@ struct adreno_gpu {
*/ */
const unsigned int *reg_offsets; const unsigned int *reg_offsets;
bool gmu_is_wrapper; bool gmu_is_wrapper;
bool has_ray_tracing;
}; };
#define to_adreno_gpu(x) container_of(x, struct adreno_gpu, base) #define to_adreno_gpu(x) container_of(x, struct adreno_gpu, base)
...@@ -298,6 +324,11 @@ static inline int adreno_is_a430(const struct adreno_gpu *gpu) ...@@ -298,6 +324,11 @@ static inline int adreno_is_a430(const struct adreno_gpu *gpu)
return adreno_is_revn(gpu, 430); return adreno_is_revn(gpu, 430);
} }
static inline int adreno_is_a505(const struct adreno_gpu *gpu)
{
return adreno_is_revn(gpu, 505);
}
static inline int adreno_is_a506(const struct adreno_gpu *gpu) static inline int adreno_is_a506(const struct adreno_gpu *gpu)
{ {
return adreno_is_revn(gpu, 506); return adreno_is_revn(gpu, 506);
...@@ -448,6 +479,11 @@ static inline int adreno_is_a750(struct adreno_gpu *gpu) ...@@ -448,6 +479,11 @@ static inline int adreno_is_a750(struct adreno_gpu *gpu)
return gpu->info->chip_ids[0] == 0x43051401; return gpu->info->chip_ids[0] == 0x43051401;
} }
static inline int adreno_is_x185(struct adreno_gpu *gpu)
{
return gpu->info->chip_ids[0] == 0x43050c01;
}
static inline int adreno_is_a740_family(struct adreno_gpu *gpu) static inline int adreno_is_a740_family(struct adreno_gpu *gpu)
{ {
if (WARN_ON_ONCE(!gpu->info)) if (WARN_ON_ONCE(!gpu->info))
......
/* SPDX-License-Identifier: GPL-2.0-only */
/*
* Copyright (c) 2018-2019, The Linux Foundation. All rights reserved.
* Copyright (c) 2024, Danila Tikhonov <danila@jiaxyga.com>
*/
#ifndef _DPU_5_2_SM7150_H
#define _DPU_5_2_SM7150_H
static const struct dpu_caps sm7150_dpu_caps = {
.max_mixer_width = DEFAULT_DPU_OUTPUT_LINE_WIDTH,
.max_mixer_blendstages = 0xb,
.has_src_split = true,
.has_dim_layer = true,
.has_idle_pc = true,
.has_3d_merge = true,
.max_linewidth = 2880,
.pixel_ram_size = DEFAULT_PIXEL_RAM_SIZE,
.max_hdeci_exp = MAX_HORZ_DECIMATION,
.max_vdeci_exp = MAX_VERT_DECIMATION,
};
static const struct dpu_mdp_cfg sm7150_mdp = {
.name = "top_0",
.base = 0x0, .len = 0x45c,
.features = BIT(DPU_MDP_AUDIO_SELECT),
.clk_ctrls = {
[DPU_CLK_CTRL_VIG0] = { .reg_off = 0x2ac, .bit_off = 0 },
[DPU_CLK_CTRL_VIG1] = { .reg_off = 0x2b4, .bit_off = 0 },
[DPU_CLK_CTRL_DMA0] = { .reg_off = 0x2ac, .bit_off = 8 },
[DPU_CLK_CTRL_DMA1] = { .reg_off = 0x2b4, .bit_off = 8 },
[DPU_CLK_CTRL_DMA2] = { .reg_off = 0x2bc, .bit_off = 8 },
[DPU_CLK_CTRL_WB2] = { .reg_off = 0x2bc, .bit_off = 16 },
},
};
static const struct dpu_ctl_cfg sm7150_ctl[] = {
{
.name = "ctl_0", .id = CTL_0,
.base = 0x1000, .len = 0x1e0,
.features = BIT(DPU_CTL_ACTIVE_CFG) | BIT(DPU_CTL_SPLIT_DISPLAY),
.intr_start = DPU_IRQ_IDX(MDP_SSPP_TOP0_INTR2, 9),
}, {
.name = "ctl_1", .id = CTL_1,
.base = 0x1200, .len = 0x1e0,
.features = BIT(DPU_CTL_ACTIVE_CFG) | BIT(DPU_CTL_SPLIT_DISPLAY),
.intr_start = DPU_IRQ_IDX(MDP_SSPP_TOP0_INTR2, 10),
}, {
.name = "ctl_2", .id = CTL_2,
.base = 0x1400, .len = 0x1e0,
.features = BIT(DPU_CTL_ACTIVE_CFG),
.intr_start = DPU_IRQ_IDX(MDP_SSPP_TOP0_INTR2, 11),
}, {
.name = "ctl_3", .id = CTL_3,
.base = 0x1600, .len = 0x1e0,
.features = BIT(DPU_CTL_ACTIVE_CFG),
.intr_start = DPU_IRQ_IDX(MDP_SSPP_TOP0_INTR2, 12),
}, {
.name = "ctl_4", .id = CTL_4,
.base = 0x1800, .len = 0x1e0,
.features = BIT(DPU_CTL_ACTIVE_CFG),
.intr_start = DPU_IRQ_IDX(MDP_SSPP_TOP0_INTR2, 13),
}, {
.name = "ctl_5", .id = CTL_5,
.base = 0x1a00, .len = 0x1e0,
.features = BIT(DPU_CTL_ACTIVE_CFG),
.intr_start = DPU_IRQ_IDX(MDP_SSPP_TOP0_INTR2, 23),
},
};
static const struct dpu_sspp_cfg sm7150_sspp[] = {
{
.name = "sspp_0", .id = SSPP_VIG0,
.base = 0x4000, .len = 0x1f0,
.features = VIG_SDM845_MASK,
.sblk = &dpu_vig_sblk_qseed3_2_4,
.xin_id = 0,
.type = SSPP_TYPE_VIG,
.clk_ctrl = DPU_CLK_CTRL_VIG0,
}, {
.name = "sspp_1", .id = SSPP_VIG1,
.base = 0x6000, .len = 0x1f0,
.features = VIG_SDM845_MASK,
.sblk = &dpu_vig_sblk_qseed3_2_4,
.xin_id = 4,
.type = SSPP_TYPE_VIG,
.clk_ctrl = DPU_CLK_CTRL_VIG1,
}, {
.name = "sspp_2", .id = SSPP_DMA0,
.base = 0x24000, .len = 0x1f0,
.features = DMA_SDM845_MASK,
.sblk = &dpu_dma_sblk,
.xin_id = 1,
.type = SSPP_TYPE_DMA,
.clk_ctrl = DPU_CLK_CTRL_DMA0,
}, {
.name = "sspp_9", .id = SSPP_DMA1,
.base = 0x26000, .len = 0x1f0,
.features = DMA_SDM845_MASK,
.sblk = &dpu_dma_sblk,
.xin_id = 5,
.type = SSPP_TYPE_DMA,
.clk_ctrl = DPU_CLK_CTRL_DMA1,
}, {
.name = "sspp_10", .id = SSPP_DMA2,
.base = 0x28000, .len = 0x1f0,
.features = DMA_CURSOR_SDM845_MASK,
.sblk = &dpu_dma_sblk,
.xin_id = 9,
.type = SSPP_TYPE_DMA,
.clk_ctrl = DPU_CLK_CTRL_DMA2,
},
};
static const struct dpu_lm_cfg sm7150_lm[] = {
{
.name = "lm_0", .id = LM_0,
.base = 0x44000, .len = 0x320,
.features = MIXER_SDM845_MASK,
.sblk = &sdm845_lm_sblk,
.lm_pair = LM_1,
.pingpong = PINGPONG_0,
.dspp = DSPP_0,
}, {
.name = "lm_1", .id = LM_1,
.base = 0x45000, .len = 0x320,
.features = MIXER_SDM845_MASK,
.sblk = &sdm845_lm_sblk,
.lm_pair = LM_0,
.pingpong = PINGPONG_1,
.dspp = DSPP_1,
}, {
.name = "lm_2", .id = LM_2,
.base = 0x46000, .len = 0x320,
.features = MIXER_SDM845_MASK,
.sblk = &sdm845_lm_sblk,
.lm_pair = LM_3,
.pingpong = PINGPONG_2,
}, {
.name = "lm_3", .id = LM_3,
.base = 0x47000, .len = 0x320,
.features = MIXER_SDM845_MASK,
.sblk = &sdm845_lm_sblk,
.lm_pair = LM_2,
.pingpong = PINGPONG_3,
},
};
static const struct dpu_dspp_cfg sm7150_dspp[] = {
{
.name = "dspp_0", .id = DSPP_0,
.base = 0x54000, .len = 0x1800,
.features = DSPP_SC7180_MASK,
.sblk = &sdm845_dspp_sblk,
}, {
.name = "dspp_1", .id = DSPP_1,
.base = 0x56000, .len = 0x1800,
.features = DSPP_SC7180_MASK,
.sblk = &sdm845_dspp_sblk,
},
};
static const struct dpu_pingpong_cfg sm7150_pp[] = {
{
.name = "pingpong_0", .id = PINGPONG_0,
.base = 0x70000, .len = 0xd4,
.features = PINGPONG_SM8150_MASK,
.sblk = &sdm845_pp_sblk,
.merge_3d = MERGE_3D_0,
.intr_done = DPU_IRQ_IDX(MDP_SSPP_TOP0_INTR, 8),
}, {
.name = "pingpong_1", .id = PINGPONG_1,
.base = 0x70800, .len = 0xd4,
.features = PINGPONG_SM8150_MASK,
.sblk = &sdm845_pp_sblk,
.merge_3d = MERGE_3D_0,
.intr_done = DPU_IRQ_IDX(MDP_SSPP_TOP0_INTR, 9),
}, {
.name = "pingpong_2", .id = PINGPONG_2,
.base = 0x71000, .len = 0xd4,
.features = PINGPONG_SM8150_MASK,
.sblk = &sdm845_pp_sblk,
.merge_3d = MERGE_3D_1,
.intr_done = DPU_IRQ_IDX(MDP_SSPP_TOP0_INTR, 10),
}, {
.name = "pingpong_3", .id = PINGPONG_3,
.base = 0x71800, .len = 0xd4,
.features = PINGPONG_SM8150_MASK,
.sblk = &sdm845_pp_sblk,
.merge_3d = MERGE_3D_1,
.intr_done = DPU_IRQ_IDX(MDP_SSPP_TOP0_INTR, 11),
},
};
static const struct dpu_merge_3d_cfg sm7150_merge_3d[] = {
{
.name = "merge_3d_0", .id = MERGE_3D_0,
.base = 0x83000, .len = 0x8,
}, {
.name = "merge_3d_1", .id = MERGE_3D_1,
.base = 0x83100, .len = 0x8,
},
};
static const struct dpu_dsc_cfg sm7150_dsc[] = {
{
.name = "dsc_0", .id = DSC_0,
.base = 0x80000, .len = 0x140,
.features = BIT(DPU_DSC_OUTPUT_CTRL),
}, {
.name = "dsc_1", .id = DSC_1,
.base = 0x80400, .len = 0x140,
.features = BIT(DPU_DSC_OUTPUT_CTRL),
},
};
static const struct dpu_intf_cfg sm7150_intf[] = {
{
.name = "intf_0", .id = INTF_0,
.base = 0x6a000, .len = 0x280,
.features = INTF_SC7180_MASK,
.type = INTF_DP,
.controller_id = MSM_DP_CONTROLLER_0,
.prog_fetch_lines_worst_case = 24,
.intr_underrun = DPU_IRQ_IDX(MDP_SSPP_TOP0_INTR, 24),
.intr_vsync = DPU_IRQ_IDX(MDP_SSPP_TOP0_INTR, 25),
}, {
.name = "intf_1", .id = INTF_1,
.base = 0x6a800, .len = 0x2bc,
.features = INTF_SC7180_MASK,
.type = INTF_DSI,
.controller_id = MSM_DSI_CONTROLLER_0,
.prog_fetch_lines_worst_case = 24,
.intr_underrun = DPU_IRQ_IDX(MDP_SSPP_TOP0_INTR, 26),
.intr_vsync = DPU_IRQ_IDX(MDP_SSPP_TOP0_INTR, 27),
.intr_tear_rd_ptr = DPU_IRQ_IDX(MDP_INTF1_TEAR_INTR, 2),
}, {
.name = "intf_2", .id = INTF_2,
.base = 0x6b000, .len = 0x2bc,
.features = INTF_SC7180_MASK,
.type = INTF_DSI,
.controller_id = MSM_DSI_CONTROLLER_1,
.prog_fetch_lines_worst_case = 24,
.intr_underrun = DPU_IRQ_IDX(MDP_SSPP_TOP0_INTR, 28),
.intr_vsync = DPU_IRQ_IDX(MDP_SSPP_TOP0_INTR, 29),
.intr_tear_rd_ptr = DPU_IRQ_IDX(MDP_INTF2_TEAR_INTR, 2),
}, {
.name = "intf_3", .id = INTF_3,
.base = 0x6b800, .len = 0x280,
.features = INTF_SC7180_MASK,
.type = INTF_DP,
.controller_id = MSM_DP_CONTROLLER_1,
.prog_fetch_lines_worst_case = 24,
.intr_underrun = DPU_IRQ_IDX(MDP_SSPP_TOP0_INTR, 30),
.intr_vsync = DPU_IRQ_IDX(MDP_SSPP_TOP0_INTR, 31),
},
};
static const struct dpu_wb_cfg sm7150_wb[] = {
{
.name = "wb_2", .id = WB_2,
.base = 0x65000, .len = 0x2c8,
.features = WB_SM8250_MASK,
.format_list = wb2_formats_rgb,
.num_formats = ARRAY_SIZE(wb2_formats_rgb),
.clk_ctrl = DPU_CLK_CTRL_WB2,
.xin_id = 6,
.vbif_idx = VBIF_RT,
.maxlinewidth = 4096,
.intr_wb_done = DPU_IRQ_IDX(MDP_SSPP_TOP0_INTR, 4),
},
};
static const struct dpu_perf_cfg sm7150_perf_data = {
.max_bw_low = 7100000,
.max_bw_high = 7100000,
.min_core_ib = 2400000,
.min_llcc_ib = 800000,
.min_dram_ib = 800000,
.min_prefill_lines = 24,
.danger_lut_tbl = {0xf, 0xffff, 0x0},
.safe_lut_tbl = {0xfff8, 0xf000, 0xffff},
.qos_lut_tbl = {
{
.nentry = ARRAY_SIZE(sm8150_qos_linear),
.entries = sm8150_qos_linear
}, {
.nentry = ARRAY_SIZE(sc7180_qos_macrotile),
.entries = sc7180_qos_macrotile
}, {
.nentry = ARRAY_SIZE(sc7180_qos_nrt),
.entries = sc7180_qos_nrt
},
},
.cdp_cfg = {
{.rd_enable = 1, .wr_enable = 1},
{.rd_enable = 1, .wr_enable = 0}
},
.clk_inefficiency_factor = 105,
.bw_inefficiency_factor = 120,
};
static const struct dpu_mdss_version sm7150_mdss_ver = {
.core_major_ver = 5,
.core_minor_ver = 2,
};
const struct dpu_mdss_cfg dpu_sm7150_cfg = {
.mdss_ver = &sm7150_mdss_ver,
.caps = &sm7150_dpu_caps,
.mdp = &sm7150_mdp,
.ctl_count = ARRAY_SIZE(sm7150_ctl),
.ctl = sm7150_ctl,
.sspp_count = ARRAY_SIZE(sm7150_sspp),
.sspp = sm7150_sspp,
.mixer_count = ARRAY_SIZE(sm7150_lm),
.mixer = sm7150_lm,
.dspp_count = ARRAY_SIZE(sm7150_dspp),
.dspp = sm7150_dspp,
.pingpong_count = ARRAY_SIZE(sm7150_pp),
.pingpong = sm7150_pp,
.merge_3d_count = ARRAY_SIZE(sm7150_merge_3d),
.merge_3d = sm7150_merge_3d,
.dsc_count = ARRAY_SIZE(sm7150_dsc),
.dsc = sm7150_dsc,
.intf_count = ARRAY_SIZE(sm7150_intf),
.intf = sm7150_intf,
.wb_count = ARRAY_SIZE(sm7150_wb),
.wb = sm7150_wb,
.vbif_count = ARRAY_SIZE(sdm845_vbif),
.vbif = sdm845_vbif,
.perf = &sm7150_perf_data,
};
#endif
...@@ -658,18 +658,18 @@ static void dpu_crtc_frame_event_work(struct kthread_work *work) ...@@ -658,18 +658,18 @@ static void dpu_crtc_frame_event_work(struct kthread_work *work)
DPU_ATRACE_END("crtc_frame_event"); DPU_ATRACE_END("crtc_frame_event");
} }
/* /**
* dpu_crtc_frame_event_cb - crtc frame event callback API. CRTC module * dpu_crtc_frame_event_cb - crtc frame event callback API
* registers this API to encoder for all frame event callbacks like * @crtc: Pointer to crtc
* frame_error, frame_done, idle_timeout, etc. Encoder may call different events * @event: Event to process
* from different context - IRQ, user thread, commit_thread, etc. Each event *
* should be carefully reviewed and should be processed in proper task context * Encoder may call this for different events from different context - IRQ,
* to avoid schedulin delay or properly manage the irq context's bottom half * user thread, commit_thread, etc. Each event should be carefully reviewed and
* processing. * should be processed in proper task context to avoid schedulin delay or
* properly manage the irq context's bottom half processing.
*/ */
static void dpu_crtc_frame_event_cb(void *data, u32 event) void dpu_crtc_frame_event_cb(struct drm_crtc *crtc, u32 event)
{ {
struct drm_crtc *crtc = (struct drm_crtc *)data;
struct dpu_crtc *dpu_crtc; struct dpu_crtc *dpu_crtc;
struct msm_drm_private *priv; struct msm_drm_private *priv;
struct dpu_crtc_frame_event *fevent; struct dpu_crtc_frame_event *fevent;
...@@ -1091,9 +1091,6 @@ static void dpu_crtc_disable(struct drm_crtc *crtc, ...@@ -1091,9 +1091,6 @@ static void dpu_crtc_disable(struct drm_crtc *crtc,
dpu_core_perf_crtc_update(crtc, 0); dpu_core_perf_crtc_update(crtc, 0);
drm_for_each_encoder_mask(encoder, crtc->dev, crtc->state->encoder_mask)
dpu_encoder_register_frame_event_callback(encoder, NULL, NULL);
memset(cstate->mixers, 0, sizeof(cstate->mixers)); memset(cstate->mixers, 0, sizeof(cstate->mixers));
cstate->num_mixers = 0; cstate->num_mixers = 0;
...@@ -1132,8 +1129,6 @@ static void dpu_crtc_enable(struct drm_crtc *crtc, ...@@ -1132,8 +1129,6 @@ static void dpu_crtc_enable(struct drm_crtc *crtc,
*/ */
if (dpu_encoder_get_intf_mode(encoder) == INTF_MODE_VIDEO) if (dpu_encoder_get_intf_mode(encoder) == INTF_MODE_VIDEO)
request_bandwidth = true; request_bandwidth = true;
dpu_encoder_register_frame_event_callback(encoder,
dpu_crtc_frame_event_cb, (void *)crtc);
} }
if (request_bandwidth) if (request_bandwidth)
......
...@@ -300,4 +300,6 @@ static inline enum dpu_crtc_client_type dpu_crtc_get_client_type( ...@@ -300,4 +300,6 @@ static inline enum dpu_crtc_client_type dpu_crtc_get_client_type(
return crtc && crtc->state ? RT_CLIENT : NRT_CLIENT; return crtc && crtc->state ? RT_CLIENT : NRT_CLIENT;
} }
void dpu_crtc_frame_event_cb(struct drm_crtc *crtc, u32 event);
#endif /* _DPU_CRTC_H_ */ #endif /* _DPU_CRTC_H_ */
...@@ -151,8 +151,6 @@ enum dpu_enc_rc_states { ...@@ -151,8 +151,6 @@ enum dpu_enc_rc_states {
* @frame_busy_mask: Bitmask tracking which phys_enc we are still * @frame_busy_mask: Bitmask tracking which phys_enc we are still
* busy processing current command. * busy processing current command.
* Bit0 = phys_encs[0] etc. * Bit0 = phys_encs[0] etc.
* @crtc_frame_event_cb: callback handler for frame event
* @crtc_frame_event_cb_data: callback handler private data
* @frame_done_timeout_ms: frame done timeout in ms * @frame_done_timeout_ms: frame done timeout in ms
* @frame_done_timeout_cnt: atomic counter tracking the number of frame * @frame_done_timeout_cnt: atomic counter tracking the number of frame
* done timeouts * done timeouts
...@@ -192,8 +190,6 @@ struct dpu_encoder_virt { ...@@ -192,8 +190,6 @@ struct dpu_encoder_virt {
struct mutex enc_lock; struct mutex enc_lock;
DECLARE_BITMAP(frame_busy_mask, MAX_PHYS_ENCODERS_PER_VIRTUAL); DECLARE_BITMAP(frame_busy_mask, MAX_PHYS_ENCODERS_PER_VIRTUAL);
void (*crtc_frame_event_cb)(void *, u32 event);
void *crtc_frame_event_cb_data;
atomic_t frame_done_timeout_ms; atomic_t frame_done_timeout_ms;
atomic_t frame_done_timeout_cnt; atomic_t frame_done_timeout_cnt;
...@@ -428,7 +424,7 @@ int dpu_encoder_helper_wait_for_irq(struct dpu_encoder_phys *phys_enc, ...@@ -428,7 +424,7 @@ int dpu_encoder_helper_wait_for_irq(struct dpu_encoder_phys *phys_enc,
return -EWOULDBLOCK; return -EWOULDBLOCK;
} }
if (irq_idx < 0) { if (irq_idx == 0) {
DRM_DEBUG_KMS("skip irq wait id=%u, callback=%ps\n", DRM_DEBUG_KMS("skip irq wait id=%u, callback=%ps\n",
DRMID(phys_enc->parent), func); DRMID(phys_enc->parent), func);
return 0; return 0;
...@@ -564,7 +560,7 @@ bool dpu_encoder_use_dsc_merge(struct drm_encoder *drm_enc) ...@@ -564,7 +560,7 @@ bool dpu_encoder_use_dsc_merge(struct drm_encoder *drm_enc)
return (num_dsc > 0) && (num_dsc > intf_count); return (num_dsc > 0) && (num_dsc > intf_count);
} }
static struct drm_dsc_config *dpu_encoder_get_dsc_config(struct drm_encoder *drm_enc) struct drm_dsc_config *dpu_encoder_get_dsc_config(struct drm_encoder *drm_enc)
{ {
struct msm_drm_private *priv = drm_enc->dev->dev_private; struct msm_drm_private *priv = drm_enc->dev->dev_private;
struct dpu_encoder_virt *dpu_enc = to_dpu_encoder_virt(drm_enc); struct dpu_encoder_virt *dpu_enc = to_dpu_encoder_virt(drm_enc);
...@@ -736,18 +732,14 @@ static void _dpu_encoder_update_vsync_source(struct dpu_encoder_virt *dpu_enc, ...@@ -736,18 +732,14 @@ static void _dpu_encoder_update_vsync_source(struct dpu_encoder_virt *dpu_enc,
return; return;
} }
if (hw_mdptop->ops.setup_vsync_source && if (hw_mdptop->ops.setup_vsync_source) {
disp_info->is_cmd_mode) {
for (i = 0; i < dpu_enc->num_phys_encs; i++) for (i = 0; i < dpu_enc->num_phys_encs; i++)
vsync_cfg.ppnumber[i] = dpu_enc->hw_pp[i]->idx; vsync_cfg.ppnumber[i] = dpu_enc->hw_pp[i]->idx;
vsync_cfg.pp_count = dpu_enc->num_phys_encs; vsync_cfg.pp_count = dpu_enc->num_phys_encs;
vsync_cfg.frame_rate = drm_mode_vrefresh(&dpu_enc->base.crtc->state->adjusted_mode); vsync_cfg.frame_rate = drm_mode_vrefresh(&dpu_enc->base.crtc->state->adjusted_mode);
if (disp_info->is_te_using_watchdog_timer) vsync_cfg.vsync_source = disp_info->vsync_source;
vsync_cfg.vsync_source = DPU_VSYNC_SOURCE_WD_TIMER_0;
else
vsync_cfg.vsync_source = DPU_VSYNC0_SOURCE_GPIO;
hw_mdptop->ops.setup_vsync_source(hw_mdptop, &vsync_cfg); hw_mdptop->ops.setup_vsync_source(hw_mdptop, &vsync_cfg);
...@@ -1200,6 +1192,8 @@ static void dpu_encoder_virt_atomic_mode_set(struct drm_encoder *drm_enc, ...@@ -1200,6 +1192,8 @@ static void dpu_encoder_virt_atomic_mode_set(struct drm_encoder *drm_enc,
phys->hw_ctl = to_dpu_hw_ctl(hw_ctl[i]); phys->hw_ctl = to_dpu_hw_ctl(hw_ctl[i]);
phys->cached_mode = crtc_state->adjusted_mode; phys->cached_mode = crtc_state->adjusted_mode;
if (phys->ops.atomic_mode_set)
phys->ops.atomic_mode_set(phys, crtc_state, conn_state);
} }
} }
...@@ -1226,7 +1220,8 @@ static void _dpu_encoder_virt_enable_helper(struct drm_encoder *drm_enc) ...@@ -1226,7 +1220,8 @@ static void _dpu_encoder_virt_enable_helper(struct drm_encoder *drm_enc)
dpu_enc->cur_master->hw_mdptop->ops.intf_audio_select( dpu_enc->cur_master->hw_mdptop->ops.intf_audio_select(
dpu_enc->cur_master->hw_mdptop); dpu_enc->cur_master->hw_mdptop);
_dpu_encoder_update_vsync_source(dpu_enc, &dpu_enc->disp_info); if (dpu_enc->disp_info.is_cmd_mode)
_dpu_encoder_update_vsync_source(dpu_enc, &dpu_enc->disp_info);
if (dpu_enc->disp_info.intf_type == INTF_DSI && if (dpu_enc->disp_info.intf_type == INTF_DSI &&
!WARN_ON(dpu_enc->num_phys_encs == 0)) { !WARN_ON(dpu_enc->num_phys_encs == 0)) {
...@@ -1454,28 +1449,6 @@ void dpu_encoder_toggle_vblank_for_crtc(struct drm_encoder *drm_enc, ...@@ -1454,28 +1449,6 @@ void dpu_encoder_toggle_vblank_for_crtc(struct drm_encoder *drm_enc,
} }
} }
void dpu_encoder_register_frame_event_callback(struct drm_encoder *drm_enc,
void (*frame_event_cb)(void *, u32 event),
void *frame_event_cb_data)
{
struct dpu_encoder_virt *dpu_enc = to_dpu_encoder_virt(drm_enc);
unsigned long lock_flags;
bool enable;
enable = frame_event_cb ? true : false;
if (!drm_enc) {
DPU_ERROR("invalid encoder\n");
return;
}
trace_dpu_enc_frame_event_cb(DRMID(drm_enc), enable);
spin_lock_irqsave(&dpu_enc->enc_spinlock, lock_flags);
dpu_enc->crtc_frame_event_cb = frame_event_cb;
dpu_enc->crtc_frame_event_cb_data = frame_event_cb_data;
spin_unlock_irqrestore(&dpu_enc->enc_spinlock, lock_flags);
}
void dpu_encoder_frame_done_callback( void dpu_encoder_frame_done_callback(
struct drm_encoder *drm_enc, struct drm_encoder *drm_enc,
struct dpu_encoder_phys *ready_phys, u32 event) struct dpu_encoder_phys *ready_phys, u32 event)
...@@ -1515,15 +1488,12 @@ void dpu_encoder_frame_done_callback( ...@@ -1515,15 +1488,12 @@ void dpu_encoder_frame_done_callback(
dpu_encoder_resource_control(drm_enc, dpu_encoder_resource_control(drm_enc,
DPU_ENC_RC_EVENT_FRAME_DONE); DPU_ENC_RC_EVENT_FRAME_DONE);
if (dpu_enc->crtc_frame_event_cb) if (dpu_enc->crtc)
dpu_enc->crtc_frame_event_cb( dpu_crtc_frame_event_cb(dpu_enc->crtc, event);
dpu_enc->crtc_frame_event_cb_data,
event);
} }
} else { } else {
if (dpu_enc->crtc_frame_event_cb) if (dpu_enc->crtc)
dpu_enc->crtc_frame_event_cb( dpu_crtc_frame_event_cb(dpu_enc->crtc, event);
dpu_enc->crtc_frame_event_cb_data, event);
} }
} }
...@@ -1741,8 +1711,7 @@ void dpu_encoder_trigger_kickoff_pending(struct drm_encoder *drm_enc) ...@@ -1741,8 +1711,7 @@ void dpu_encoder_trigger_kickoff_pending(struct drm_encoder *drm_enc)
phys = dpu_enc->phys_encs[i]; phys = dpu_enc->phys_encs[i];
ctl = phys->hw_ctl; ctl = phys->hw_ctl;
if (ctl->ops.clear_pending_flush) ctl->ops.clear_pending_flush(ctl);
ctl->ops.clear_pending_flush(ctl);
/* update only for command mode primary ctl */ /* update only for command mode primary ctl */
if ((phys == dpu_enc->cur_master) && if ((phys == dpu_enc->cur_master) &&
...@@ -2457,7 +2426,7 @@ static void dpu_encoder_frame_done_timeout(struct timer_list *t) ...@@ -2457,7 +2426,7 @@ static void dpu_encoder_frame_done_timeout(struct timer_list *t)
return; return;
} }
if (!dpu_enc->frame_busy_mask[0] || !dpu_enc->crtc_frame_event_cb) { if (!dpu_enc->frame_busy_mask[0] || !dpu_enc->crtc) {
DRM_DEBUG_KMS("id:%u invalid timeout frame_busy_mask=%lu\n", DRM_DEBUG_KMS("id:%u invalid timeout frame_busy_mask=%lu\n",
DRMID(drm_enc), dpu_enc->frame_busy_mask[0]); DRMID(drm_enc), dpu_enc->frame_busy_mask[0]);
return; return;
...@@ -2473,7 +2442,7 @@ static void dpu_encoder_frame_done_timeout(struct timer_list *t) ...@@ -2473,7 +2442,7 @@ static void dpu_encoder_frame_done_timeout(struct timer_list *t)
event = DPU_ENCODER_FRAME_EVENT_ERROR; event = DPU_ENCODER_FRAME_EVENT_ERROR;
trace_dpu_enc_frame_done_timeout(DRMID(drm_enc), event); trace_dpu_enc_frame_done_timeout(DRMID(drm_enc), event);
dpu_enc->crtc_frame_event_cb(dpu_enc->crtc_frame_event_cb_data, event); dpu_crtc_frame_event_cb(dpu_enc->crtc, event);
} }
static const struct drm_encoder_helper_funcs dpu_encoder_helper_funcs = { static const struct drm_encoder_helper_funcs dpu_encoder_helper_funcs = {
......
...@@ -26,15 +26,14 @@ ...@@ -26,15 +26,14 @@
* @h_tile_instance: Controller instance used per tile. Number of elements is * @h_tile_instance: Controller instance used per tile. Number of elements is
* based on num_of_h_tiles * based on num_of_h_tiles
* @is_cmd_mode Boolean to indicate if the CMD mode is requested * @is_cmd_mode Boolean to indicate if the CMD mode is requested
* @is_te_using_watchdog_timer: Boolean to indicate watchdog TE is * @vsync_source: Source of the TE signal for DSI CMD devices
* used instead of panel TE in cmd mode panels
*/ */
struct msm_display_info { struct msm_display_info {
enum dpu_intf_type intf_type; enum dpu_intf_type intf_type;
uint32_t num_of_h_tiles; uint32_t num_of_h_tiles;
uint32_t h_tile_instance[MAX_H_TILES_PER_DISPLAY]; uint32_t h_tile_instance[MAX_H_TILES_PER_DISPLAY];
bool is_cmd_mode; bool is_cmd_mode;
bool is_te_using_watchdog_timer; enum dpu_vsync_source vsync_source;
}; };
/** /**
...@@ -55,16 +54,6 @@ void dpu_encoder_assign_crtc(struct drm_encoder *encoder, ...@@ -55,16 +54,6 @@ void dpu_encoder_assign_crtc(struct drm_encoder *encoder,
void dpu_encoder_toggle_vblank_for_crtc(struct drm_encoder *encoder, void dpu_encoder_toggle_vblank_for_crtc(struct drm_encoder *encoder,
struct drm_crtc *crtc, bool enable); struct drm_crtc *crtc, bool enable);
/**
* dpu_encoder_register_frame_event_callback - provide callback to encoder that
* will be called after the request is complete, or other events.
* @encoder: encoder pointer
* @cb: callback pointer, provide NULL to deregister
* @data: user data provided to callback
*/
void dpu_encoder_register_frame_event_callback(struct drm_encoder *encoder,
void (*cb)(void *, u32), void *data);
/** /**
* dpu_encoder_prepare_for_kickoff - schedule double buffer flip of the ctl * dpu_encoder_prepare_for_kickoff - schedule double buffer flip of the ctl
* path (i.e. ctl flush and start) at next appropriate time. * path (i.e. ctl flush and start) at next appropriate time.
......
...@@ -838,6 +838,7 @@ extern const struct dpu_mdss_cfg dpu_sdm845_cfg; ...@@ -838,6 +838,7 @@ extern const struct dpu_mdss_cfg dpu_sdm845_cfg;
extern const struct dpu_mdss_cfg dpu_sdm670_cfg; extern const struct dpu_mdss_cfg dpu_sdm670_cfg;
extern const struct dpu_mdss_cfg dpu_sm8150_cfg; extern const struct dpu_mdss_cfg dpu_sm8150_cfg;
extern const struct dpu_mdss_cfg dpu_sc8180x_cfg; extern const struct dpu_mdss_cfg dpu_sc8180x_cfg;
extern const struct dpu_mdss_cfg dpu_sm7150_cfg;
extern const struct dpu_mdss_cfg dpu_sm8250_cfg; extern const struct dpu_mdss_cfg dpu_sm8250_cfg;
extern const struct dpu_mdss_cfg dpu_sc7180_cfg; extern const struct dpu_mdss_cfg dpu_sc7180_cfg;
extern const struct dpu_mdss_cfg dpu_sm6115_cfg; extern const struct dpu_mdss_cfg dpu_sm6115_cfg;
......
...@@ -83,7 +83,8 @@ struct dpu_hw_ctl_ops { ...@@ -83,7 +83,8 @@ struct dpu_hw_ctl_ops {
/** /**
* Clear the value of the cached pending_flush_mask * Clear the value of the cached pending_flush_mask
* No effect on hardware * No effect on hardware.
* Required to be implemented.
* @ctx : ctl path ctx pointer * @ctx : ctl path ctx pointer
*/ */
void (*clear_pending_flush)(struct dpu_hw_ctl *ctx); void (*clear_pending_flush)(struct dpu_hw_ctl *ctx);
......
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment