Commit 64222515 authored by Linus Torvalds's avatar Linus Torvalds
Browse files

Merge tag 'drm-fixes-2021-10-22' of git://anongit.freedesktop.org/drm/drm

Pull drm fixes from Dave Airlie:
 "Nothing too crazy at the end of the cycle, the kmb modesetting fixes
  are probably a bit large but it's not a major driver, and its fixing
  monitor doesn't turn on type problems.

  Otherwise it's just a few minor patches, one ast regression revert, an
  msm power stability fix.

  ast:
   - fix regression with connector detect

  msm:
   - fix power stability issue

  msxfb:
   - fix crash on unload

  panel:
   - sync fix

  kmb:
   - modesetting fixes"

* tag 'drm-fixes-2021-10-22' of git://anongit.freedesktop.org/drm/drm:
  Revert "drm/ast: Add detect function support"
  drm/kmb: Enable ADV bridge after modeset
  drm/kmb: Corrected typo in handle_lcd_irq
  drm/kmb: Disable change of plane parameters
  drm/kmb: Remove clearing DPHY regs
  drm/kmb: Limit supported mode to 1080p
  drm/kmb: Work around for higher system clock
  drm/panel: ilitek-ili9881c: Fix sync for Feixin K101-IM2BYL02 panel
  drm: mxsfb: Fix NULL pointer dereference crash on unload
  drm/msm/devfreq: Restrict idle clamping to a618 for now
parents 658aafc8 595cb5e0
Loading
Loading
Loading
Loading
+1 −17
Original line number Diff line number Diff line
@@ -1300,18 +1300,6 @@ static enum drm_mode_status ast_mode_valid(struct drm_connector *connector,
	return flags;
}

static enum drm_connector_status ast_connector_detect(struct drm_connector
						   *connector, bool force)
{
	int r;

	r = ast_get_modes(connector);
	if (r <= 0)
		return connector_status_disconnected;

	return connector_status_connected;
}

static void ast_connector_destroy(struct drm_connector *connector)
{
	struct ast_connector *ast_connector = to_ast_connector(connector);
@@ -1327,7 +1315,6 @@ static const struct drm_connector_helper_funcs ast_connector_helper_funcs = {

static const struct drm_connector_funcs ast_connector_funcs = {
	.reset = drm_atomic_helper_connector_reset,
	.detect = ast_connector_detect,
	.fill_modes = drm_helper_probe_single_connector_modes,
	.destroy = ast_connector_destroy,
	.atomic_duplicate_state = drm_atomic_helper_connector_duplicate_state,
@@ -1355,8 +1342,7 @@ static int ast_connector_init(struct drm_device *dev)
	connector->interlace_allowed = 0;
	connector->doublescan_allowed = 0;

	connector->polled = DRM_CONNECTOR_POLL_CONNECT |
						DRM_CONNECTOR_POLL_DISCONNECT;
	connector->polled = DRM_CONNECTOR_POLL_CONNECT;

	drm_connector_attach_encoder(connector, encoder);

@@ -1425,8 +1411,6 @@ int ast_mode_config_init(struct ast_private *ast)

	drm_mode_config_reset(dev);

	drm_kms_helper_poll_init(dev);

	return 0;
}

+38 −3
Original line number Diff line number Diff line
@@ -66,7 +66,8 @@ static const struct drm_crtc_funcs kmb_crtc_funcs = {
	.disable_vblank = kmb_crtc_disable_vblank,
};

static void kmb_crtc_set_mode(struct drm_crtc *crtc)
static void kmb_crtc_set_mode(struct drm_crtc *crtc,
			      struct drm_atomic_state *old_state)
{
	struct drm_device *dev = crtc->dev;
	struct drm_display_mode *m = &crtc->state->adjusted_mode;
@@ -75,7 +76,7 @@ static void kmb_crtc_set_mode(struct drm_crtc *crtc)
	unsigned int val = 0;

	/* Initialize mipi */
	kmb_dsi_mode_set(kmb->kmb_dsi, m, kmb->sys_clk_mhz);
	kmb_dsi_mode_set(kmb->kmb_dsi, m, kmb->sys_clk_mhz, old_state);
	drm_info(dev,
		 "vfp= %d vbp= %d vsync_len=%d hfp=%d hbp=%d hsync_len=%d\n",
		 m->crtc_vsync_start - m->crtc_vdisplay,
@@ -138,7 +139,7 @@ static void kmb_crtc_atomic_enable(struct drm_crtc *crtc,
	struct kmb_drm_private *kmb = crtc_to_kmb_priv(crtc);

	clk_prepare_enable(kmb->kmb_clk.clk_lcd);
	kmb_crtc_set_mode(crtc);
	kmb_crtc_set_mode(crtc, state);
	drm_crtc_vblank_on(crtc);
}

@@ -185,11 +186,45 @@ static void kmb_crtc_atomic_flush(struct drm_crtc *crtc,
	spin_unlock_irq(&crtc->dev->event_lock);
}

static enum drm_mode_status
		kmb_crtc_mode_valid(struct drm_crtc *crtc,
				    const struct drm_display_mode *mode)
{
	int refresh;
	struct drm_device *dev = crtc->dev;
	int vfp = mode->vsync_start - mode->vdisplay;

	if (mode->vdisplay < KMB_CRTC_MAX_HEIGHT) {
		drm_dbg(dev, "height = %d less than %d",
			mode->vdisplay, KMB_CRTC_MAX_HEIGHT);
		return MODE_BAD_VVALUE;
	}
	if (mode->hdisplay < KMB_CRTC_MAX_WIDTH) {
		drm_dbg(dev, "width = %d less than %d",
			mode->hdisplay, KMB_CRTC_MAX_WIDTH);
		return MODE_BAD_HVALUE;
	}
	refresh = drm_mode_vrefresh(mode);
	if (refresh < KMB_MIN_VREFRESH || refresh > KMB_MAX_VREFRESH) {
		drm_dbg(dev, "refresh = %d less than %d or greater than %d",
			refresh, KMB_MIN_VREFRESH, KMB_MAX_VREFRESH);
		return MODE_BAD;
	}

	if (vfp < KMB_CRTC_MIN_VFP) {
		drm_dbg(dev, "vfp = %d less than %d", vfp, KMB_CRTC_MIN_VFP);
		return MODE_BAD;
	}

	return MODE_OK;
}

static const struct drm_crtc_helper_funcs kmb_crtc_helper_funcs = {
	.atomic_begin = kmb_crtc_atomic_begin,
	.atomic_enable = kmb_crtc_atomic_enable,
	.atomic_disable = kmb_crtc_atomic_disable,
	.atomic_flush = kmb_crtc_atomic_flush,
	.mode_valid = kmb_crtc_mode_valid,
};

int kmb_setup_crtc(struct drm_device *drm)
+1 −1
Original line number Diff line number Diff line
@@ -380,7 +380,7 @@ static irqreturn_t handle_lcd_irq(struct drm_device *dev)
		if (val & LAYER3_DMA_FIFO_UNDERFLOW)
			drm_dbg(&kmb->drm,
				"LAYER3:GL1 DMA UNDERFLOW val = 0x%lx", val);
		if (val & LAYER3_DMA_FIFO_UNDERFLOW)
		if (val & LAYER3_DMA_FIFO_OVERFLOW)
			drm_dbg(&kmb->drm,
				"LAYER3:GL1 DMA OVERFLOW val = 0x%lx", val);
	}
+9 −1
Original line number Diff line number Diff line
@@ -20,11 +20,18 @@
#define DRIVER_MAJOR			1
#define DRIVER_MINOR			1

/* Platform definitions */
#define KMB_CRTC_MIN_VFP		4
#define KMB_CRTC_MAX_WIDTH		1920 /* max width in pixels */
#define KMB_CRTC_MAX_HEIGHT		1080 /* max height in pixels */
#define KMB_CRTC_MIN_WIDTH		1920
#define KMB_CRTC_MIN_HEIGHT		1080
#define KMB_FB_MAX_WIDTH		1920
#define KMB_FB_MAX_HEIGHT		1080
#define KMB_FB_MIN_WIDTH		1
#define KMB_FB_MIN_HEIGHT		1

#define KMB_MIN_VREFRESH		59    /*vertical refresh in Hz */
#define KMB_MAX_VREFRESH		60    /*vertical refresh in Hz */
#define KMB_LCD_DEFAULT_CLK		200000000
#define KMB_SYS_CLK_MHZ			500

@@ -50,6 +57,7 @@ struct kmb_drm_private {
	spinlock_t			irq_lock;
	int				irq_lcd;
	int				sys_clk_mhz;
	struct disp_cfg			init_disp_cfg[KMB_MAX_PLANES];
	struct layer_status		plane_status[KMB_MAX_PLANES];
	int				kmb_under_flow;
	int				kmb_flush_done;
+15 −10
Original line number Diff line number Diff line
@@ -482,6 +482,10 @@ static u32 mipi_tx_fg_section_cfg(struct kmb_dsi *kmb_dsi,
	return 0;
}

#define CLK_DIFF_LOW 50
#define CLK_DIFF_HI 60
#define SYSCLK_500  500

static void mipi_tx_fg_cfg_regs(struct kmb_dsi *kmb_dsi, u8 frame_gen,
				struct mipi_tx_frame_timing_cfg *fg_cfg)
{
@@ -492,7 +496,12 @@ static void mipi_tx_fg_cfg_regs(struct kmb_dsi *kmb_dsi, u8 frame_gen,
	/* 500 Mhz system clock minus 50 to account for the difference in
	 * MIPI clock speed in RTL tests
	 */
	sysclk = kmb_dsi->sys_clk_mhz - 50;
	if (kmb_dsi->sys_clk_mhz == SYSCLK_500) {
		sysclk = kmb_dsi->sys_clk_mhz - CLK_DIFF_LOW;
	} else {
		/* 700 Mhz clk*/
		sysclk = kmb_dsi->sys_clk_mhz - CLK_DIFF_HI;
	}

	/* PPL-Pixel Packing Layer, LLP-Low Level Protocol
	 * Frame genartor timing parameters are clocked on the system clock,
@@ -1322,7 +1331,8 @@ static u32 mipi_tx_init_dphy(struct kmb_dsi *kmb_dsi,
	return 0;
}

static void connect_lcd_to_mipi(struct kmb_dsi *kmb_dsi)
static void connect_lcd_to_mipi(struct kmb_dsi *kmb_dsi,
				struct drm_atomic_state *old_state)
{
	struct regmap *msscam;

@@ -1331,7 +1341,7 @@ static void connect_lcd_to_mipi(struct kmb_dsi *kmb_dsi)
		dev_dbg(kmb_dsi->dev, "failed to get msscam syscon");
		return;
	}

	drm_atomic_bridge_chain_enable(adv_bridge, old_state);
	/* DISABLE MIPI->CIF CONNECTION */
	regmap_write(msscam, MSS_MIPI_CIF_CFG, 0);

@@ -1342,7 +1352,7 @@ static void connect_lcd_to_mipi(struct kmb_dsi *kmb_dsi)
}

int kmb_dsi_mode_set(struct kmb_dsi *kmb_dsi, struct drm_display_mode *mode,
		     int sys_clk_mhz)
		     int sys_clk_mhz, struct drm_atomic_state *old_state)
{
	u64 data_rate;

@@ -1384,18 +1394,13 @@ int kmb_dsi_mode_set(struct kmb_dsi *kmb_dsi, struct drm_display_mode *mode,
		mipi_tx_init_cfg.lane_rate_mbps = data_rate;
	}

	kmb_write_mipi(kmb_dsi, DPHY_ENABLE, 0);
	kmb_write_mipi(kmb_dsi, DPHY_INIT_CTRL0, 0);
	kmb_write_mipi(kmb_dsi, DPHY_INIT_CTRL1, 0);
	kmb_write_mipi(kmb_dsi, DPHY_INIT_CTRL2, 0);

	/* Initialize mipi controller */
	mipi_tx_init_cntrl(kmb_dsi, &mipi_tx_init_cfg);

	/* Dphy initialization */
	mipi_tx_init_dphy(kmb_dsi, &mipi_tx_init_cfg);

	connect_lcd_to_mipi(kmb_dsi);
	connect_lcd_to_mipi(kmb_dsi, old_state);
	dev_info(kmb_dsi->dev, "mipi hw initialized");

	return 0;
Loading