Commit 16b79b33 authored by Jani Nikula's avatar Jani Nikula

drm/i915/display: add support for subplatforms

Add support for subplatforms. This is similar to what the xe driver is
doing. The subplatform is an enum and it's exclusive, i.e. only one
subplatform can match, and it completely identifies the platform and
subplatform. This is different from i915 core, and is notable in the
handling of ULT/ULX and RPL/RPL-U.
Reviewed-by: default avatarRodrigo Vivi <rodrigo.vivi@intel.com>
Link: https://patchwork.freedesktop.org/patch/msgid/8c04e32648395c0b745bc31a1edd4ef6f574bb70.1716399081.git.jani.nikula@intel.comSigned-off-by: default avatarJani Nikula <jani.nikula@intel.com>
parent b2725962
...@@ -20,9 +20,16 @@ ...@@ -20,9 +20,16 @@
__diag_push(); __diag_push();
__diag_ignore_all("-Woverride-init", "Allow field initialization overrides for display info"); __diag_ignore_all("-Woverride-init", "Allow field initialization overrides for display info");
struct subplatform_desc {
enum intel_display_subplatform subplatform;
const char *name;
const u16 *pciidlist;
};
struct platform_desc { struct platform_desc {
enum intel_display_platform platform; enum intel_display_platform platform;
const char *name; const char *name;
const struct subplatform_desc *subplatforms;
const struct intel_display_device_info *info; /* NULL for GMD ID */ const struct intel_display_device_info *info; /* NULL for GMD ID */
}; };
...@@ -30,6 +37,8 @@ struct platform_desc { ...@@ -30,6 +37,8 @@ struct platform_desc {
.platform = (INTEL_DISPLAY_##_platform), \ .platform = (INTEL_DISPLAY_##_platform), \
.name = #_platform .name = #_platform
#define ID(id) (id)
static const struct intel_display_device_info no_display = {}; static const struct intel_display_device_info no_display = {};
#define PIPE_A_OFFSET 0x70000 #define PIPE_A_OFFSET 0x70000
...@@ -460,8 +469,26 @@ static const struct platform_desc vlv_desc = { ...@@ -460,8 +469,26 @@ static const struct platform_desc vlv_desc = {
}, },
}; };
static const u16 hsw_ult_ids[] = {
INTEL_HSW_ULT_GT1_IDS(ID),
INTEL_HSW_ULT_GT2_IDS(ID),
INTEL_HSW_ULT_GT3_IDS(ID),
0
};
static const u16 hsw_ulx_ids[] = {
INTEL_HSW_ULX_GT1_IDS(ID),
INTEL_HSW_ULX_GT2_IDS(ID),
0
};
static const struct platform_desc hsw_desc = { static const struct platform_desc hsw_desc = {
PLATFORM(HASWELL), PLATFORM(HASWELL),
.subplatforms = (const struct subplatform_desc[]) {
{ INTEL_DISPLAY_HASWELL_ULT, "ULT", hsw_ult_ids },
{ INTEL_DISPLAY_HASWELL_ULX, "ULX", hsw_ulx_ids },
{},
},
.info = &(const struct intel_display_device_info) { .info = &(const struct intel_display_device_info) {
.has_ddi = 1, .has_ddi = 1,
.has_dp_mst = 1, .has_dp_mst = 1,
...@@ -483,8 +510,29 @@ static const struct platform_desc hsw_desc = { ...@@ -483,8 +510,29 @@ static const struct platform_desc hsw_desc = {
}, },
}; };
static const u16 bdw_ult_ids[] = {
INTEL_BDW_ULT_GT1_IDS(ID),
INTEL_BDW_ULT_GT2_IDS(ID),
INTEL_BDW_ULT_GT3_IDS(ID),
INTEL_BDW_ULT_RSVD_IDS(ID),
0
};
static const u16 bdw_ulx_ids[] = {
INTEL_BDW_ULX_GT1_IDS(ID),
INTEL_BDW_ULX_GT2_IDS(ID),
INTEL_BDW_ULX_GT3_IDS(ID),
INTEL_BDW_ULX_RSVD_IDS(ID),
0
};
static const struct platform_desc bdw_desc = { static const struct platform_desc bdw_desc = {
PLATFORM(BROADWELL), PLATFORM(BROADWELL),
.subplatforms = (const struct subplatform_desc[]) {
{ INTEL_DISPLAY_BROADWELL_ULT, "ULT", bdw_ult_ids },
{ INTEL_DISPLAY_BROADWELL_ULX, "ULX", bdw_ulx_ids },
{},
},
.info = &(const struct intel_display_device_info) { .info = &(const struct intel_display_device_info) {
.has_ddi = 1, .has_ddi = 1,
.has_dp_mst = 1, .has_dp_mst = 1,
...@@ -549,23 +597,89 @@ static const struct intel_display_device_info skl_display = { ...@@ -549,23 +597,89 @@ static const struct intel_display_device_info skl_display = {
.__runtime_defaults.fbc_mask = BIT(INTEL_FBC_A), .__runtime_defaults.fbc_mask = BIT(INTEL_FBC_A),
}; };
static const u16 skl_ult_ids[] = {
INTEL_SKL_ULT_GT1_IDS(ID),
INTEL_SKL_ULT_GT2_IDS(ID),
INTEL_SKL_ULT_GT3_IDS(ID),
0
};
static const u16 skl_ulx_ids[] = {
INTEL_SKL_ULX_GT1_IDS(ID),
INTEL_SKL_ULX_GT2_IDS(ID),
0
};
static const struct platform_desc skl_desc = { static const struct platform_desc skl_desc = {
PLATFORM(SKYLAKE), PLATFORM(SKYLAKE),
.subplatforms = (const struct subplatform_desc[]) {
{ INTEL_DISPLAY_SKYLAKE_ULT, "ULT", skl_ult_ids },
{ INTEL_DISPLAY_SKYLAKE_ULX, "ULX", skl_ulx_ids },
{},
},
.info = &skl_display, .info = &skl_display,
}; };
static const u16 kbl_ult_ids[] = {
INTEL_KBL_ULT_GT1_IDS(ID),
INTEL_KBL_ULT_GT2_IDS(ID),
INTEL_KBL_ULT_GT3_IDS(ID),
0
};
static const u16 kbl_ulx_ids[] = {
INTEL_KBL_ULX_GT1_IDS(ID),
INTEL_KBL_ULX_GT2_IDS(ID),
INTEL_AML_KBL_GT2_IDS(ID),
0
};
static const struct platform_desc kbl_desc = { static const struct platform_desc kbl_desc = {
PLATFORM(KABYLAKE), PLATFORM(KABYLAKE),
.subplatforms = (const struct subplatform_desc[]) {
{ INTEL_DISPLAY_KABYLAKE_ULT, "ULT", kbl_ult_ids },
{ INTEL_DISPLAY_KABYLAKE_ULX, "ULX", kbl_ulx_ids },
{},
},
.info = &skl_display, .info = &skl_display,
}; };
static const u16 cfl_ult_ids[] = {
INTEL_CFL_U_GT2_IDS(ID),
INTEL_CFL_U_GT3_IDS(ID),
INTEL_WHL_U_GT1_IDS(ID),
INTEL_WHL_U_GT2_IDS(ID),
INTEL_WHL_U_GT3_IDS(ID),
0
};
static const u16 cfl_ulx_ids[] = {
INTEL_AML_CFL_GT2_IDS(ID),
0
};
static const struct platform_desc cfl_desc = { static const struct platform_desc cfl_desc = {
PLATFORM(COFFEELAKE), PLATFORM(COFFEELAKE),
.subplatforms = (const struct subplatform_desc[]) {
{ INTEL_DISPLAY_COFFEELAKE_ULT, "ULT", cfl_ult_ids },
{ INTEL_DISPLAY_COFFEELAKE_ULX, "ULX", cfl_ulx_ids },
{},
},
.info = &skl_display, .info = &skl_display,
}; };
static const u16 cml_ult_ids[] = {
INTEL_CML_U_GT1_IDS(ID),
INTEL_CML_U_GT2_IDS(ID),
0
};
static const struct platform_desc cml_desc = { static const struct platform_desc cml_desc = {
PLATFORM(COMETLAKE), PLATFORM(COMETLAKE),
.subplatforms = (const struct subplatform_desc[]) {
{ INTEL_DISPLAY_COMETLAKE_ULT, "ULT", cml_ult_ids },
{},
},
.info = &skl_display, .info = &skl_display,
}; };
...@@ -654,8 +768,17 @@ static const struct platform_desc glk_desc = { ...@@ -654,8 +768,17 @@ static const struct platform_desc glk_desc = {
BIT(TRANSCODER_DSI_0) | BIT(TRANSCODER_DSI_1), \ BIT(TRANSCODER_DSI_0) | BIT(TRANSCODER_DSI_1), \
.__runtime_defaults.fbc_mask = BIT(INTEL_FBC_A) .__runtime_defaults.fbc_mask = BIT(INTEL_FBC_A)
static const u16 icl_port_f_ids[] = {
INTEL_ICL_PORT_F_IDS(ID),
0
};
static const struct platform_desc icl_desc = { static const struct platform_desc icl_desc = {
PLATFORM(ICELAKE), PLATFORM(ICELAKE),
.subplatforms = (const struct subplatform_desc[]) {
{ INTEL_DISPLAY_ICELAKE_PORT_F, "Port F", icl_port_f_ids },
{},
},
.info = &(const struct intel_display_device_info) { .info = &(const struct intel_display_device_info) {
ICL_DISPLAY, ICL_DISPLAY,
...@@ -722,8 +845,17 @@ static const struct platform_desc ehl_desc = { ...@@ -722,8 +845,17 @@ static const struct platform_desc ehl_desc = {
BIT(TRANSCODER_DSI_0) | BIT(TRANSCODER_DSI_1), \ BIT(TRANSCODER_DSI_0) | BIT(TRANSCODER_DSI_1), \
.__runtime_defaults.fbc_mask = BIT(INTEL_FBC_A) .__runtime_defaults.fbc_mask = BIT(INTEL_FBC_A)
static const u16 tgl_uy_ids[] = {
INTEL_TGL_GT2_IDS(ID),
0
};
static const struct platform_desc tgl_desc = { static const struct platform_desc tgl_desc = {
PLATFORM(TIGERLAKE), PLATFORM(TIGERLAKE),
.subplatforms = (const struct subplatform_desc[]) {
{ INTEL_DISPLAY_TIGERLAKE_UY, "UY", tgl_uy_ids },
{},
},
.info = &(const struct intel_display_device_info) { .info = &(const struct intel_display_device_info) {
XE_D_DISPLAY, XE_D_DISPLAY,
...@@ -762,8 +894,17 @@ static const struct platform_desc rkl_desc = { ...@@ -762,8 +894,17 @@ static const struct platform_desc rkl_desc = {
}, },
}; };
static const u16 adls_rpls_ids[] = {
INTEL_RPLS_IDS(ID),
0
};
static const struct platform_desc adl_s_desc = { static const struct platform_desc adl_s_desc = {
PLATFORM(ALDERLAKE_S), PLATFORM(ALDERLAKE_S),
.subplatforms = (const struct subplatform_desc[]) {
{ INTEL_DISPLAY_ALDERLAKE_S_RAPTORLAKE_S, "RPL-S", adls_rpls_ids },
{},
},
.info = &(const struct intel_display_device_info) { .info = &(const struct intel_display_device_info) {
XE_D_DISPLAY, XE_D_DISPLAY,
.has_hti = 1, .has_hti = 1,
...@@ -830,8 +971,29 @@ static const struct intel_display_device_info xe_lpd_display = { ...@@ -830,8 +971,29 @@ static const struct intel_display_device_info xe_lpd_display = {
BIT(PORT_TC1) | BIT(PORT_TC2) | BIT(PORT_TC3) | BIT(PORT_TC4), BIT(PORT_TC1) | BIT(PORT_TC2) | BIT(PORT_TC3) | BIT(PORT_TC4),
}; };
static const u16 adlp_adln_ids[] = {
INTEL_ADLN_IDS(ID),
0
};
static const u16 adlp_rplu_ids[] = {
INTEL_RPLU_IDS(ID),
0
};
static const u16 adlp_rplp_ids[] = {
INTEL_RPLP_IDS(ID),
0
};
static const struct platform_desc adl_p_desc = { static const struct platform_desc adl_p_desc = {
PLATFORM(ALDERLAKE_P), PLATFORM(ALDERLAKE_P),
.subplatforms = (const struct subplatform_desc[]) {
{ INTEL_DISPLAY_ALDERLAKE_P_ALDERLAKE_N, "ADL-N", adlp_adln_ids },
{ INTEL_DISPLAY_ALDERLAKE_P_RAPTORLAKE_U, "RPL-U", adlp_rplu_ids },
{ INTEL_DISPLAY_ALDERLAKE_P_RAPTORLAKE_P, "RPL-P", adlp_rplp_ids },
{},
},
.info = &xe_lpd_display, .info = &xe_lpd_display,
}; };
...@@ -846,8 +1008,29 @@ static const struct intel_display_device_info xe_hpd_display = { ...@@ -846,8 +1008,29 @@ static const struct intel_display_device_info xe_hpd_display = {
BIT(PORT_TC1), BIT(PORT_TC1),
}; };
static const u16 dg2_g10_ids[] = {
INTEL_DG2_G10_IDS(ID),
0
};
static const u16 dg2_g11_ids[] = {
INTEL_DG2_G11_IDS(ID),
0
};
static const u16 dg2_g12_ids[] = {
INTEL_DG2_G12_IDS(ID),
0
};
static const struct platform_desc dg2_desc = { static const struct platform_desc dg2_desc = {
PLATFORM(DG2), PLATFORM(DG2),
.subplatforms = (const struct subplatform_desc[]) {
{ INTEL_DISPLAY_DG2_G10, "G10", dg2_g10_ids },
{ INTEL_DISPLAY_DG2_G11, "G11", dg2_g11_ids },
{ INTEL_DISPLAY_DG2_G12, "G12", dg2_g12_ids },
{},
},
.info = &xe_hpd_display, .info = &xe_hpd_display,
}; };
...@@ -1059,12 +1242,27 @@ static const struct platform_desc *find_platform_desc(struct pci_dev *pdev) ...@@ -1059,12 +1242,27 @@ static const struct platform_desc *find_platform_desc(struct pci_dev *pdev)
return NULL; return NULL;
} }
static const struct subplatform_desc *
find_subplatform_desc(struct pci_dev *pdev, const struct platform_desc *desc)
{
const struct subplatform_desc *sp;
const u16 *id;
for (sp = desc->subplatforms; sp && sp->subplatform; sp++)
for (id = sp->pciidlist; *id; id++)
if (*id == pdev->device)
return sp;
return NULL;
}
void intel_display_device_probe(struct drm_i915_private *i915) void intel_display_device_probe(struct drm_i915_private *i915)
{ {
struct pci_dev *pdev = to_pci_dev(i915->drm.dev); struct pci_dev *pdev = to_pci_dev(i915->drm.dev);
const struct intel_display_device_info *info; const struct intel_display_device_info *info;
struct intel_display_ip_ver ip_ver = {}; struct intel_display_ip_ver ip_ver = {};
const struct platform_desc *desc; const struct platform_desc *desc;
const struct subplatform_desc *subdesc;
/* Add drm device backpointer as early as possible. */ /* Add drm device backpointer as early as possible. */
i915->display.drm = &i915->drm; i915->display.drm = &i915->drm;
...@@ -1098,6 +1296,12 @@ void intel_display_device_probe(struct drm_i915_private *i915) ...@@ -1098,6 +1296,12 @@ void intel_display_device_probe(struct drm_i915_private *i915)
drm_WARN_ON(&i915->drm, !desc->platform || !desc->name); drm_WARN_ON(&i915->drm, !desc->platform || !desc->name);
DISPLAY_RUNTIME_INFO(i915)->platform = desc->platform; DISPLAY_RUNTIME_INFO(i915)->platform = desc->platform;
subdesc = find_subplatform_desc(pdev, desc);
if (subdesc) {
drm_WARN_ON(&i915->drm, !subdesc->subplatform || !subdesc->name);
DISPLAY_RUNTIME_INFO(i915)->subplatform = subdesc->subplatform;
}
if (ip_ver.ver || ip_ver.rel || ip_ver.step) if (ip_ver.ver || ip_ver.rel || ip_ver.step)
DISPLAY_RUNTIME_INFO(i915)->ip = ip_ver; DISPLAY_RUNTIME_INFO(i915)->ip = ip_ver;
......
...@@ -70,6 +70,31 @@ enum intel_display_platform { ...@@ -70,6 +70,31 @@ enum intel_display_platform {
INTEL_DISPLAY_LUNARLAKE, INTEL_DISPLAY_LUNARLAKE,
}; };
enum intel_display_subplatform {
INTEL_DISPLAY_SUBPLATFORM_UNINITIALIZED = 0,
INTEL_DISPLAY_HASWELL_ULT,
INTEL_DISPLAY_HASWELL_ULX,
INTEL_DISPLAY_BROADWELL_ULT,
INTEL_DISPLAY_BROADWELL_ULX,
INTEL_DISPLAY_SKYLAKE_ULT,
INTEL_DISPLAY_SKYLAKE_ULX,
INTEL_DISPLAY_KABYLAKE_ULT,
INTEL_DISPLAY_KABYLAKE_ULX,
INTEL_DISPLAY_COFFEELAKE_ULT,
INTEL_DISPLAY_COFFEELAKE_ULX,
INTEL_DISPLAY_COMETLAKE_ULT,
INTEL_DISPLAY_COMETLAKE_ULX,
INTEL_DISPLAY_ICELAKE_PORT_F,
INTEL_DISPLAY_TIGERLAKE_UY,
INTEL_DISPLAY_ALDERLAKE_S_RAPTORLAKE_S,
INTEL_DISPLAY_ALDERLAKE_P_ALDERLAKE_N,
INTEL_DISPLAY_ALDERLAKE_P_RAPTORLAKE_P,
INTEL_DISPLAY_ALDERLAKE_P_RAPTORLAKE_U,
INTEL_DISPLAY_DG2_G10,
INTEL_DISPLAY_DG2_G11,
INTEL_DISPLAY_DG2_G12,
};
#define DEV_INFO_DISPLAY_FOR_EACH_FLAG(func) \ #define DEV_INFO_DISPLAY_FOR_EACH_FLAG(func) \
/* Keep in alphabetical order */ \ /* Keep in alphabetical order */ \
func(cursor_needs_physical); \ func(cursor_needs_physical); \
...@@ -168,6 +193,7 @@ enum intel_display_platform { ...@@ -168,6 +193,7 @@ enum intel_display_platform {
struct intel_display_runtime_info { struct intel_display_runtime_info {
enum intel_display_platform platform; enum intel_display_platform platform;
enum intel_display_subplatform subplatform;
struct intel_display_ip_ver { struct intel_display_ip_ver {
u16 ver; u16 ver;
......
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