Commit 788f07eb authored by Dave Airlie's avatar Dave Airlie

Merge tag 'drm-intel-fixes-2019-04-11' of...

Merge tag 'drm-intel-fixes-2019-04-11' of git://anongit.freedesktop.org/drm/drm-intel into drm-fixes

- Revert back to max link rate and lane count on eDP.
- DSI related fixes for all platforms including Ice Lake.
- GVT Fixes including one vGPU display plane size regression fix,
one for preventing use-after-free in ppgtt shadow free function,
and another warning fix for iomem access annotation.
Signed-off-by: default avatarDave Airlie <airlied@redhat.com>

From: Rodrigo Vivi <rodrigo.vivi@intel.com>
Link: https://patchwork.freedesktop.org/patch/msgid/20190411235832.GA6476@intel.com
parents ffb5d6fe 3f5f5d53
...@@ -209,7 +209,7 @@ static int vgpu_get_plane_info(struct drm_device *dev, ...@@ -209,7 +209,7 @@ static int vgpu_get_plane_info(struct drm_device *dev,
struct drm_i915_private *dev_priv = to_i915(dev); struct drm_i915_private *dev_priv = to_i915(dev);
struct intel_vgpu_primary_plane_format p; struct intel_vgpu_primary_plane_format p;
struct intel_vgpu_cursor_plane_format c; struct intel_vgpu_cursor_plane_format c;
int ret; int ret, tile_height = 1;
if (plane_id == DRM_PLANE_TYPE_PRIMARY) { if (plane_id == DRM_PLANE_TYPE_PRIMARY) {
ret = intel_vgpu_decode_primary_plane(vgpu, &p); ret = intel_vgpu_decode_primary_plane(vgpu, &p);
...@@ -228,12 +228,15 @@ static int vgpu_get_plane_info(struct drm_device *dev, ...@@ -228,12 +228,15 @@ static int vgpu_get_plane_info(struct drm_device *dev,
break; break;
case PLANE_CTL_TILED_X: case PLANE_CTL_TILED_X:
info->drm_format_mod = I915_FORMAT_MOD_X_TILED; info->drm_format_mod = I915_FORMAT_MOD_X_TILED;
tile_height = 8;
break; break;
case PLANE_CTL_TILED_Y: case PLANE_CTL_TILED_Y:
info->drm_format_mod = I915_FORMAT_MOD_Y_TILED; info->drm_format_mod = I915_FORMAT_MOD_Y_TILED;
tile_height = 32;
break; break;
case PLANE_CTL_TILED_YF: case PLANE_CTL_TILED_YF:
info->drm_format_mod = I915_FORMAT_MOD_Yf_TILED; info->drm_format_mod = I915_FORMAT_MOD_Yf_TILED;
tile_height = 32;
break; break;
default: default:
gvt_vgpu_err("invalid tiling mode: %x\n", p.tiled); gvt_vgpu_err("invalid tiling mode: %x\n", p.tiled);
...@@ -264,8 +267,8 @@ static int vgpu_get_plane_info(struct drm_device *dev, ...@@ -264,8 +267,8 @@ static int vgpu_get_plane_info(struct drm_device *dev,
return -EINVAL; return -EINVAL;
} }
info->size = (info->stride * info->height + PAGE_SIZE - 1) info->size = (info->stride * roundup(info->height, tile_height)
>> PAGE_SHIFT; + PAGE_SIZE - 1) >> PAGE_SHIFT;
if (info->size == 0) { if (info->size == 0) {
gvt_vgpu_err("fb size is zero\n"); gvt_vgpu_err("fb size is zero\n");
return -EINVAL; return -EINVAL;
......
...@@ -750,14 +750,20 @@ static void ppgtt_free_spt(struct intel_vgpu_ppgtt_spt *spt) ...@@ -750,14 +750,20 @@ static void ppgtt_free_spt(struct intel_vgpu_ppgtt_spt *spt)
static void ppgtt_free_all_spt(struct intel_vgpu *vgpu) static void ppgtt_free_all_spt(struct intel_vgpu *vgpu)
{ {
struct intel_vgpu_ppgtt_spt *spt; struct intel_vgpu_ppgtt_spt *spt, *spn;
struct radix_tree_iter iter; struct radix_tree_iter iter;
void **slot; LIST_HEAD(all_spt);
void __rcu **slot;
rcu_read_lock();
radix_tree_for_each_slot(slot, &vgpu->gtt.spt_tree, &iter, 0) { radix_tree_for_each_slot(slot, &vgpu->gtt.spt_tree, &iter, 0) {
spt = radix_tree_deref_slot(slot); spt = radix_tree_deref_slot(slot);
ppgtt_free_spt(spt); list_move(&spt->post_shadow_list, &all_spt);
} }
rcu_read_unlock();
list_for_each_entry_safe(spt, spn, &all_spt, post_shadow_list)
ppgtt_free_spt(spt);
} }
static int ppgtt_handle_guest_write_page_table_bytes( static int ppgtt_handle_guest_write_page_table_bytes(
......
...@@ -905,7 +905,7 @@ static inline bool intel_vgpu_in_aperture(struct intel_vgpu *vgpu, u64 off) ...@@ -905,7 +905,7 @@ static inline bool intel_vgpu_in_aperture(struct intel_vgpu *vgpu, u64 off)
static int intel_vgpu_aperture_rw(struct intel_vgpu *vgpu, u64 off, static int intel_vgpu_aperture_rw(struct intel_vgpu *vgpu, u64 off,
void *buf, unsigned long count, bool is_write) void *buf, unsigned long count, bool is_write)
{ {
void *aperture_va; void __iomem *aperture_va;
if (!intel_vgpu_in_aperture(vgpu, off) || if (!intel_vgpu_in_aperture(vgpu, off) ||
!intel_vgpu_in_aperture(vgpu, off + count)) { !intel_vgpu_in_aperture(vgpu, off + count)) {
...@@ -920,9 +920,9 @@ static int intel_vgpu_aperture_rw(struct intel_vgpu *vgpu, u64 off, ...@@ -920,9 +920,9 @@ static int intel_vgpu_aperture_rw(struct intel_vgpu *vgpu, u64 off,
return -EIO; return -EIO;
if (is_write) if (is_write)
memcpy(aperture_va + offset_in_page(off), buf, count); memcpy_toio(aperture_va + offset_in_page(off), buf, count);
else else
memcpy(buf, aperture_va + offset_in_page(off), count); memcpy_fromio(buf, aperture_va + offset_in_page(off), count);
io_mapping_unmap(aperture_va); io_mapping_unmap(aperture_va);
......
...@@ -323,6 +323,21 @@ static void gen11_dsi_program_esc_clk_div(struct intel_encoder *encoder) ...@@ -323,6 +323,21 @@ static void gen11_dsi_program_esc_clk_div(struct intel_encoder *encoder)
} }
} }
static void get_dsi_io_power_domains(struct drm_i915_private *dev_priv,
struct intel_dsi *intel_dsi)
{
enum port port;
for_each_dsi_port(port, intel_dsi->ports) {
WARN_ON(intel_dsi->io_wakeref[port]);
intel_dsi->io_wakeref[port] =
intel_display_power_get(dev_priv,
port == PORT_A ?
POWER_DOMAIN_PORT_DDI_A_IO :
POWER_DOMAIN_PORT_DDI_B_IO);
}
}
static void gen11_dsi_enable_io_power(struct intel_encoder *encoder) static void gen11_dsi_enable_io_power(struct intel_encoder *encoder)
{ {
struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); struct drm_i915_private *dev_priv = to_i915(encoder->base.dev);
...@@ -336,13 +351,7 @@ static void gen11_dsi_enable_io_power(struct intel_encoder *encoder) ...@@ -336,13 +351,7 @@ static void gen11_dsi_enable_io_power(struct intel_encoder *encoder)
I915_WRITE(ICL_DSI_IO_MODECTL(port), tmp); I915_WRITE(ICL_DSI_IO_MODECTL(port), tmp);
} }
for_each_dsi_port(port, intel_dsi->ports) { get_dsi_io_power_domains(dev_priv, intel_dsi);
intel_dsi->io_wakeref[port] =
intel_display_power_get(dev_priv,
port == PORT_A ?
POWER_DOMAIN_PORT_DDI_A_IO :
POWER_DOMAIN_PORT_DDI_B_IO);
}
} }
static void gen11_dsi_power_up_lanes(struct intel_encoder *encoder) static void gen11_dsi_power_up_lanes(struct intel_encoder *encoder)
...@@ -589,6 +598,12 @@ static void gen11_dsi_map_pll(struct intel_encoder *encoder, ...@@ -589,6 +598,12 @@ static void gen11_dsi_map_pll(struct intel_encoder *encoder,
val |= DPCLKA_CFGCR0_DDI_CLK_SEL(pll->info->id, port); val |= DPCLKA_CFGCR0_DDI_CLK_SEL(pll->info->id, port);
} }
I915_WRITE(DPCLKA_CFGCR0_ICL, val); I915_WRITE(DPCLKA_CFGCR0_ICL, val);
for_each_dsi_port(port, intel_dsi->ports) {
val &= ~DPCLKA_CFGCR0_DDI_CLK_OFF(port);
}
I915_WRITE(DPCLKA_CFGCR0_ICL, val);
POSTING_READ(DPCLKA_CFGCR0_ICL); POSTING_READ(DPCLKA_CFGCR0_ICL);
mutex_unlock(&dev_priv->dpll_lock); mutex_unlock(&dev_priv->dpll_lock);
...@@ -1117,7 +1132,7 @@ static void gen11_dsi_disable_port(struct intel_encoder *encoder) ...@@ -1117,7 +1132,7 @@ static void gen11_dsi_disable_port(struct intel_encoder *encoder)
DRM_ERROR("DDI port:%c buffer not idle\n", DRM_ERROR("DDI port:%c buffer not idle\n",
port_name(port)); port_name(port));
} }
gen11_dsi_ungate_clocks(encoder); gen11_dsi_gate_clocks(encoder);
} }
static void gen11_dsi_disable_io_power(struct intel_encoder *encoder) static void gen11_dsi_disable_io_power(struct intel_encoder *encoder)
...@@ -1218,20 +1233,11 @@ static int gen11_dsi_compute_config(struct intel_encoder *encoder, ...@@ -1218,20 +1233,11 @@ static int gen11_dsi_compute_config(struct intel_encoder *encoder,
return 0; return 0;
} }
static u64 gen11_dsi_get_power_domains(struct intel_encoder *encoder, static void gen11_dsi_get_power_domains(struct intel_encoder *encoder,
struct intel_crtc_state *crtc_state) struct intel_crtc_state *crtc_state)
{ {
struct intel_dsi *intel_dsi = enc_to_intel_dsi(&encoder->base); get_dsi_io_power_domains(to_i915(encoder->base.dev),
u64 domains = 0; enc_to_intel_dsi(&encoder->base));
enum port port;
for_each_dsi_port(port, intel_dsi->ports)
if (port == PORT_A)
domains |= BIT_ULL(POWER_DOMAIN_PORT_DDI_A_IO);
else
domains |= BIT_ULL(POWER_DOMAIN_PORT_DDI_B_IO);
return domains;
} }
static bool gen11_dsi_get_hw_state(struct intel_encoder *encoder, static bool gen11_dsi_get_hw_state(struct intel_encoder *encoder,
......
...@@ -2075,12 +2075,11 @@ intel_ddi_main_link_aux_domain(struct intel_digital_port *dig_port) ...@@ -2075,12 +2075,11 @@ intel_ddi_main_link_aux_domain(struct intel_digital_port *dig_port)
intel_aux_power_domain(dig_port); intel_aux_power_domain(dig_port);
} }
static u64 intel_ddi_get_power_domains(struct intel_encoder *encoder, static void intel_ddi_get_power_domains(struct intel_encoder *encoder,
struct intel_crtc_state *crtc_state) struct intel_crtc_state *crtc_state)
{ {
struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); struct drm_i915_private *dev_priv = to_i915(encoder->base.dev);
struct intel_digital_port *dig_port; struct intel_digital_port *dig_port;
u64 domains;
/* /*
* TODO: Add support for MST encoders. Atm, the following should never * TODO: Add support for MST encoders. Atm, the following should never
...@@ -2088,10 +2087,10 @@ static u64 intel_ddi_get_power_domains(struct intel_encoder *encoder, ...@@ -2088,10 +2087,10 @@ static u64 intel_ddi_get_power_domains(struct intel_encoder *encoder,
* hook. * hook.
*/ */
if (WARN_ON(intel_crtc_has_type(crtc_state, INTEL_OUTPUT_DP_MST))) if (WARN_ON(intel_crtc_has_type(crtc_state, INTEL_OUTPUT_DP_MST)))
return 0; return;
dig_port = enc_to_dig_port(&encoder->base); dig_port = enc_to_dig_port(&encoder->base);
domains = BIT_ULL(dig_port->ddi_io_power_domain); intel_display_power_get(dev_priv, dig_port->ddi_io_power_domain);
/* /*
* AUX power is only needed for (e)DP mode, and for HDMI mode on TC * AUX power is only needed for (e)DP mode, and for HDMI mode on TC
...@@ -2099,15 +2098,15 @@ static u64 intel_ddi_get_power_domains(struct intel_encoder *encoder, ...@@ -2099,15 +2098,15 @@ static u64 intel_ddi_get_power_domains(struct intel_encoder *encoder,
*/ */
if (intel_crtc_has_dp_encoder(crtc_state) || if (intel_crtc_has_dp_encoder(crtc_state) ||
intel_port_is_tc(dev_priv, encoder->port)) intel_port_is_tc(dev_priv, encoder->port))
domains |= BIT_ULL(intel_ddi_main_link_aux_domain(dig_port)); intel_display_power_get(dev_priv,
intel_ddi_main_link_aux_domain(dig_port));
/* /*
* VDSC power is needed when DSC is enabled * VDSC power is needed when DSC is enabled
*/ */
if (crtc_state->dsc_params.compression_enable) if (crtc_state->dsc_params.compression_enable)
domains |= BIT_ULL(intel_dsc_power_domain(crtc_state)); intel_display_power_get(dev_priv,
intel_dsc_power_domain(crtc_state));
return domains;
} }
void intel_ddi_enable_pipe_clock(const struct intel_crtc_state *crtc_state) void intel_ddi_enable_pipe_clock(const struct intel_crtc_state *crtc_state)
...@@ -2825,10 +2824,10 @@ void icl_sanitize_encoder_pll_mapping(struct intel_encoder *encoder) ...@@ -2825,10 +2824,10 @@ void icl_sanitize_encoder_pll_mapping(struct intel_encoder *encoder)
return; return;
} }
/* /*
* DSI ports should have their DDI clock ungated when disabled * For DSI we keep the ddi clocks gated
* and gated when enabled. * except during enable/disable sequence.
*/ */
ddi_clk_needed = !encoder->base.crtc; ddi_clk_needed = false;
} }
val = I915_READ(DPCLKA_CFGCR0_ICL); val = I915_READ(DPCLKA_CFGCR0_ICL);
......
...@@ -15986,8 +15986,6 @@ get_encoder_power_domains(struct drm_i915_private *dev_priv) ...@@ -15986,8 +15986,6 @@ get_encoder_power_domains(struct drm_i915_private *dev_priv)
struct intel_encoder *encoder; struct intel_encoder *encoder;
for_each_intel_encoder(&dev_priv->drm, encoder) { for_each_intel_encoder(&dev_priv->drm, encoder) {
u64 get_domains;
enum intel_display_power_domain domain;
struct intel_crtc_state *crtc_state; struct intel_crtc_state *crtc_state;
if (!encoder->get_power_domains) if (!encoder->get_power_domains)
...@@ -16001,9 +15999,7 @@ get_encoder_power_domains(struct drm_i915_private *dev_priv) ...@@ -16001,9 +15999,7 @@ get_encoder_power_domains(struct drm_i915_private *dev_priv)
continue; continue;
crtc_state = to_intel_crtc_state(encoder->base.crtc->state); crtc_state = to_intel_crtc_state(encoder->base.crtc->state);
get_domains = encoder->get_power_domains(encoder, crtc_state); encoder->get_power_domains(encoder, crtc_state);
for_each_power_domain(domain, get_domains)
intel_display_power_get(dev_priv, domain);
} }
} }
......
...@@ -1859,42 +1859,6 @@ intel_dp_compute_link_config_wide(struct intel_dp *intel_dp, ...@@ -1859,42 +1859,6 @@ intel_dp_compute_link_config_wide(struct intel_dp *intel_dp,
return -EINVAL; return -EINVAL;
} }
/* Optimize link config in order: max bpp, min lanes, min clock */
static int
intel_dp_compute_link_config_fast(struct intel_dp *intel_dp,
struct intel_crtc_state *pipe_config,
const struct link_config_limits *limits)
{
struct drm_display_mode *adjusted_mode = &pipe_config->base.adjusted_mode;
int bpp, clock, lane_count;
int mode_rate, link_clock, link_avail;
for (bpp = limits->max_bpp; bpp >= limits->min_bpp; bpp -= 2 * 3) {
mode_rate = intel_dp_link_required(adjusted_mode->crtc_clock,
bpp);
for (lane_count = limits->min_lane_count;
lane_count <= limits->max_lane_count;
lane_count <<= 1) {
for (clock = limits->min_clock; clock <= limits->max_clock; clock++) {
link_clock = intel_dp->common_rates[clock];
link_avail = intel_dp_max_data_rate(link_clock,
lane_count);
if (mode_rate <= link_avail) {
pipe_config->lane_count = lane_count;
pipe_config->pipe_bpp = bpp;
pipe_config->port_clock = link_clock;
return 0;
}
}
}
}
return -EINVAL;
}
static int intel_dp_dsc_compute_bpp(struct intel_dp *intel_dp, u8 dsc_max_bpc) static int intel_dp_dsc_compute_bpp(struct intel_dp *intel_dp, u8 dsc_max_bpc)
{ {
int i, num_bpc; int i, num_bpc;
...@@ -2031,15 +1995,13 @@ intel_dp_compute_link_config(struct intel_encoder *encoder, ...@@ -2031,15 +1995,13 @@ intel_dp_compute_link_config(struct intel_encoder *encoder,
limits.min_bpp = 6 * 3; limits.min_bpp = 6 * 3;
limits.max_bpp = intel_dp_compute_bpp(intel_dp, pipe_config); limits.max_bpp = intel_dp_compute_bpp(intel_dp, pipe_config);
if (intel_dp_is_edp(intel_dp) && intel_dp->edp_dpcd[0] < DP_EDP_14) { if (intel_dp_is_edp(intel_dp)) {
/* /*
* Use the maximum clock and number of lanes the eDP panel * Use the maximum clock and number of lanes the eDP panel
* advertizes being capable of. The eDP 1.3 and earlier panels * advertizes being capable of. The panels are generally
* are generally designed to support only a single clock and * designed to support only a single clock and lane
* lane configuration, and typically these values correspond to * configuration, and typically these values correspond to the
* the native resolution of the panel. With eDP 1.4 rate select * native resolution of the panel.
* and DSC, this is decreasingly the case, and we need to be
* able to select less than maximum link config.
*/ */
limits.min_lane_count = limits.max_lane_count; limits.min_lane_count = limits.max_lane_count;
limits.min_clock = limits.max_clock; limits.min_clock = limits.max_clock;
...@@ -2053,22 +2015,11 @@ intel_dp_compute_link_config(struct intel_encoder *encoder, ...@@ -2053,22 +2015,11 @@ intel_dp_compute_link_config(struct intel_encoder *encoder,
intel_dp->common_rates[limits.max_clock], intel_dp->common_rates[limits.max_clock],
limits.max_bpp, adjusted_mode->crtc_clock); limits.max_bpp, adjusted_mode->crtc_clock);
if (intel_dp_is_edp(intel_dp)) /*
/* * Optimize for slow and wide. This is the place to add alternative
* Optimize for fast and narrow. eDP 1.3 section 3.3 and eDP 1.4 * optimization policy.
* section A.1: "It is recommended that the minimum number of */
* lanes be used, using the minimum link rate allowed for that ret = intel_dp_compute_link_config_wide(intel_dp, pipe_config, &limits);
* lane configuration."
*
* Note that we use the max clock and lane count for eDP 1.3 and
* earlier, and fast vs. wide is irrelevant.
*/
ret = intel_dp_compute_link_config_fast(intel_dp, pipe_config,
&limits);
else
/* Optimize for slow and wide. */
ret = intel_dp_compute_link_config_wide(intel_dp, pipe_config,
&limits);
/* enable compression if the mode doesn't fit available BW */ /* enable compression if the mode doesn't fit available BW */
DRM_DEBUG_KMS("Force DSC en = %d\n", intel_dp->force_dsc_en); DRM_DEBUG_KMS("Force DSC en = %d\n", intel_dp->force_dsc_en);
......
...@@ -270,10 +270,12 @@ struct intel_encoder { ...@@ -270,10 +270,12 @@ struct intel_encoder {
* be set correctly before calling this function. */ * be set correctly before calling this function. */
void (*get_config)(struct intel_encoder *, void (*get_config)(struct intel_encoder *,
struct intel_crtc_state *pipe_config); struct intel_crtc_state *pipe_config);
/* Returns a mask of power domains that need to be referenced as part /*
* of the hardware state readout code. */ * Acquires the power domains needed for an active encoder during
u64 (*get_power_domains)(struct intel_encoder *encoder, * hardware state readout.
struct intel_crtc_state *crtc_state); */
void (*get_power_domains)(struct intel_encoder *encoder,
struct intel_crtc_state *crtc_state);
/* /*
* Called during system suspend after all pending requests for the * Called during system suspend after all pending requests for the
* encoder are flushed (for example for DP AUX transactions) and * encoder are flushed (for example for DP AUX transactions) and
......
...@@ -256,6 +256,28 @@ static void band_gap_reset(struct drm_i915_private *dev_priv) ...@@ -256,6 +256,28 @@ static void band_gap_reset(struct drm_i915_private *dev_priv)
mutex_unlock(&dev_priv->sb_lock); mutex_unlock(&dev_priv->sb_lock);
} }
static int bdw_get_pipemisc_bpp(struct intel_crtc *crtc)
{
struct drm_i915_private *dev_priv = to_i915(crtc->base.dev);
u32 tmp;
tmp = I915_READ(PIPEMISC(crtc->pipe));
switch (tmp & PIPEMISC_DITHER_BPC_MASK) {
case PIPEMISC_DITHER_6_BPC:
return 18;
case PIPEMISC_DITHER_8_BPC:
return 24;
case PIPEMISC_DITHER_10_BPC:
return 30;
case PIPEMISC_DITHER_12_BPC:
return 36;
default:
MISSING_CASE(tmp);
return 0;
}
}
static int intel_dsi_compute_config(struct intel_encoder *encoder, static int intel_dsi_compute_config(struct intel_encoder *encoder,
struct intel_crtc_state *pipe_config, struct intel_crtc_state *pipe_config,
struct drm_connector_state *conn_state) struct drm_connector_state *conn_state)
...@@ -1071,6 +1093,8 @@ static void bxt_dsi_get_pipe_config(struct intel_encoder *encoder, ...@@ -1071,6 +1093,8 @@ static void bxt_dsi_get_pipe_config(struct intel_encoder *encoder,
bpp = mipi_dsi_pixel_format_to_bpp( bpp = mipi_dsi_pixel_format_to_bpp(
pixel_format_from_register_bits(fmt)); pixel_format_from_register_bits(fmt));
pipe_config->pipe_bpp = bdw_get_pipemisc_bpp(crtc);
/* Enable Frame time stamo based scanline reporting */ /* Enable Frame time stamo based scanline reporting */
adjusted_mode->private_flags |= adjusted_mode->private_flags |=
I915_MODE_FLAG_GET_SCANLINE_FROM_TIMESTAMP; I915_MODE_FLAG_GET_SCANLINE_FROM_TIMESTAMP;
......
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