aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--drivers/gpu/drm/vc4/vc4_crtc.c17
-rw-r--r--drivers/gpu/drm/vc4/vc4_hdmi.c16
-rw-r--r--drivers/gpu/drm/vc4/vc4_regs.h2
3 files changed, 24 insertions, 11 deletions
diff --git a/drivers/gpu/drm/vc4/vc4_crtc.c b/drivers/gpu/drm/vc4/vc4_crtc.c
index 83cafea03eff..7f08d681a74b 100644
--- a/drivers/gpu/drm/vc4/vc4_crtc.c
+++ b/drivers/gpu/drm/vc4/vc4_crtc.c
@@ -378,6 +378,7 @@ static void vc4_crtc_mode_set_nofb(struct drm_crtc *crtc)
378 struct drm_crtc_state *state = crtc->state; 378 struct drm_crtc_state *state = crtc->state;
379 struct drm_display_mode *mode = &state->adjusted_mode; 379 struct drm_display_mode *mode = &state->adjusted_mode;
380 bool interlace = mode->flags & DRM_MODE_FLAG_INTERLACE; 380 bool interlace = mode->flags & DRM_MODE_FLAG_INTERLACE;
381 u32 pixel_rep = (mode->flags & DRM_MODE_FLAG_DBLCLK) ? 2 : 1;
381 u32 format = PV_CONTROL_FORMAT_24; 382 u32 format = PV_CONTROL_FORMAT_24;
382 bool debug_dump_regs = false; 383 bool debug_dump_regs = false;
383 int clock_select = vc4_get_clock_select(crtc); 384 int clock_select = vc4_get_clock_select(crtc);
@@ -393,14 +394,17 @@ static void vc4_crtc_mode_set_nofb(struct drm_crtc *crtc)
393 CRTC_WRITE(PV_CONTROL, 0); 394 CRTC_WRITE(PV_CONTROL, 0);
394 395
395 CRTC_WRITE(PV_HORZA, 396 CRTC_WRITE(PV_HORZA,
396 VC4_SET_FIELD(mode->htotal - mode->hsync_end, 397 VC4_SET_FIELD((mode->htotal -
398 mode->hsync_end) * pixel_rep,
397 PV_HORZA_HBP) | 399 PV_HORZA_HBP) |
398 VC4_SET_FIELD(mode->hsync_end - mode->hsync_start, 400 VC4_SET_FIELD((mode->hsync_end -
401 mode->hsync_start) * pixel_rep,
399 PV_HORZA_HSYNC)); 402 PV_HORZA_HSYNC));
400 CRTC_WRITE(PV_HORZB, 403 CRTC_WRITE(PV_HORZB,
401 VC4_SET_FIELD(mode->hsync_start - mode->hdisplay, 404 VC4_SET_FIELD((mode->hsync_start -
405 mode->hdisplay) * pixel_rep,
402 PV_HORZB_HFP) | 406 PV_HORZB_HFP) |
403 VC4_SET_FIELD(mode->hdisplay, PV_HORZB_HACTIVE)); 407 VC4_SET_FIELD(mode->hdisplay * pixel_rep, PV_HORZB_HACTIVE));
404 408
405 CRTC_WRITE(PV_VERTA, 409 CRTC_WRITE(PV_VERTA,
406 VC4_SET_FIELD(mode->crtc_vtotal - mode->crtc_vsync_end, 410 VC4_SET_FIELD(mode->crtc_vtotal - mode->crtc_vsync_end,
@@ -434,20 +438,21 @@ static void vc4_crtc_mode_set_nofb(struct drm_crtc *crtc)
434 CRTC_WRITE(PV_V_CONTROL, 438 CRTC_WRITE(PV_V_CONTROL,
435 PV_VCONTROL_CONTINUOUS | 439 PV_VCONTROL_CONTINUOUS |
436 PV_VCONTROL_INTERLACE | 440 PV_VCONTROL_INTERLACE |
437 VC4_SET_FIELD(mode->htotal / 2, 441 VC4_SET_FIELD(mode->htotal * pixel_rep / 2,
438 PV_VCONTROL_ODD_DELAY)); 442 PV_VCONTROL_ODD_DELAY));
439 CRTC_WRITE(PV_VSYNCD_EVEN, 0); 443 CRTC_WRITE(PV_VSYNCD_EVEN, 0);
440 } else { 444 } else {
441 CRTC_WRITE(PV_V_CONTROL, PV_VCONTROL_CONTINUOUS); 445 CRTC_WRITE(PV_V_CONTROL, PV_VCONTROL_CONTINUOUS);
442 } 446 }
443 447
444 CRTC_WRITE(PV_HACT_ACT, mode->hdisplay); 448 CRTC_WRITE(PV_HACT_ACT, mode->hdisplay * pixel_rep);
445 449
446 450
447 CRTC_WRITE(PV_CONTROL, 451 CRTC_WRITE(PV_CONTROL,
448 VC4_SET_FIELD(format, PV_CONTROL_FORMAT) | 452 VC4_SET_FIELD(format, PV_CONTROL_FORMAT) |
449 VC4_SET_FIELD(vc4_get_fifo_full_level(format), 453 VC4_SET_FIELD(vc4_get_fifo_full_level(format),
450 PV_CONTROL_FIFO_LEVEL) | 454 PV_CONTROL_FIFO_LEVEL) |
455 VC4_SET_FIELD(pixel_rep - 1, PV_CONTROL_PIXEL_REP) |
451 PV_CONTROL_CLR_AT_START | 456 PV_CONTROL_CLR_AT_START |
452 PV_CONTROL_TRIGGER_UNDERFLOW | 457 PV_CONTROL_TRIGGER_UNDERFLOW |
453 PV_CONTROL_WAIT_HSTART | 458 PV_CONTROL_WAIT_HSTART |
diff --git a/drivers/gpu/drm/vc4/vc4_hdmi.c b/drivers/gpu/drm/vc4/vc4_hdmi.c
index d6b54b905bee..c4cb2e26de32 100644
--- a/drivers/gpu/drm/vc4/vc4_hdmi.c
+++ b/drivers/gpu/drm/vc4/vc4_hdmi.c
@@ -402,6 +402,7 @@ static void vc4_hdmi_encoder_mode_set(struct drm_encoder *encoder,
402 bool hsync_pos = mode->flags & DRM_MODE_FLAG_PHSYNC; 402 bool hsync_pos = mode->flags & DRM_MODE_FLAG_PHSYNC;
403 bool vsync_pos = mode->flags & DRM_MODE_FLAG_PVSYNC; 403 bool vsync_pos = mode->flags & DRM_MODE_FLAG_PVSYNC;
404 bool interlaced = mode->flags & DRM_MODE_FLAG_INTERLACE; 404 bool interlaced = mode->flags & DRM_MODE_FLAG_INTERLACE;
405 u32 pixel_rep = (mode->flags & DRM_MODE_FLAG_DBLCLK) ? 2 : 1;
405 u32 verta = (VC4_SET_FIELD(mode->crtc_vsync_end - mode->crtc_vsync_start, 406 u32 verta = (VC4_SET_FIELD(mode->crtc_vsync_end - mode->crtc_vsync_start,
406 VC4_HDMI_VERTA_VSP) | 407 VC4_HDMI_VERTA_VSP) |
407 VC4_SET_FIELD(mode->crtc_vsync_start - mode->crtc_vdisplay, 408 VC4_SET_FIELD(mode->crtc_vsync_start - mode->crtc_vdisplay,
@@ -424,7 +425,8 @@ static void vc4_hdmi_encoder_mode_set(struct drm_encoder *encoder,
424 425
425 HD_WRITE(VC4_HD_VID_CTL, 0); 426 HD_WRITE(VC4_HD_VID_CTL, 0);
426 427
427 clk_set_rate(vc4->hdmi->pixel_clock, mode->clock * 1000); 428 clk_set_rate(vc4->hdmi->pixel_clock, mode->clock * 1000 *
429 ((mode->flags & DRM_MODE_FLAG_DBLCLK) ? 2 : 1));
428 430
429 HDMI_WRITE(VC4_HDMI_SCHEDULER_CONTROL, 431 HDMI_WRITE(VC4_HDMI_SCHEDULER_CONTROL,
430 HDMI_READ(VC4_HDMI_SCHEDULER_CONTROL) | 432 HDMI_READ(VC4_HDMI_SCHEDULER_CONTROL) |
@@ -434,14 +436,18 @@ static void vc4_hdmi_encoder_mode_set(struct drm_encoder *encoder,
434 HDMI_WRITE(VC4_HDMI_HORZA, 436 HDMI_WRITE(VC4_HDMI_HORZA,
435 (vsync_pos ? VC4_HDMI_HORZA_VPOS : 0) | 437 (vsync_pos ? VC4_HDMI_HORZA_VPOS : 0) |
436 (hsync_pos ? VC4_HDMI_HORZA_HPOS : 0) | 438 (hsync_pos ? VC4_HDMI_HORZA_HPOS : 0) |
437 VC4_SET_FIELD(mode->hdisplay, VC4_HDMI_HORZA_HAP)); 439 VC4_SET_FIELD(mode->hdisplay * pixel_rep,
440 VC4_HDMI_HORZA_HAP));
438 441
439 HDMI_WRITE(VC4_HDMI_HORZB, 442 HDMI_WRITE(VC4_HDMI_HORZB,
440 VC4_SET_FIELD(mode->htotal - mode->hsync_end, 443 VC4_SET_FIELD((mode->htotal -
444 mode->hsync_end) * pixel_rep,
441 VC4_HDMI_HORZB_HBP) | 445 VC4_HDMI_HORZB_HBP) |
442 VC4_SET_FIELD(mode->hsync_end - mode->hsync_start, 446 VC4_SET_FIELD((mode->hsync_end -
447 mode->hsync_start) * pixel_rep,
443 VC4_HDMI_HORZB_HSP) | 448 VC4_HDMI_HORZB_HSP) |
444 VC4_SET_FIELD(mode->hsync_start - mode->hdisplay, 449 VC4_SET_FIELD((mode->hsync_start -
450 mode->hdisplay) * pixel_rep,
445 VC4_HDMI_HORZB_HFP)); 451 VC4_HDMI_HORZB_HFP));
446 452
447 HDMI_WRITE(VC4_HDMI_VERTA0, verta); 453 HDMI_WRITE(VC4_HDMI_VERTA0, verta);
diff --git a/drivers/gpu/drm/vc4/vc4_regs.h b/drivers/gpu/drm/vc4/vc4_regs.h
index 0b868aafa8db..1aa44c2db556 100644
--- a/drivers/gpu/drm/vc4/vc4_regs.h
+++ b/drivers/gpu/drm/vc4/vc4_regs.h
@@ -175,6 +175,8 @@
175# define PV_CONTROL_CLR_AT_START BIT(14) 175# define PV_CONTROL_CLR_AT_START BIT(14)
176# define PV_CONTROL_TRIGGER_UNDERFLOW BIT(13) 176# define PV_CONTROL_TRIGGER_UNDERFLOW BIT(13)
177# define PV_CONTROL_WAIT_HSTART BIT(12) 177# define PV_CONTROL_WAIT_HSTART BIT(12)
178# define PV_CONTROL_PIXEL_REP_MASK VC4_MASK(5, 4)
179# define PV_CONTROL_PIXEL_REP_SHIFT 4
178# define PV_CONTROL_CLK_SELECT_DSI_VEC 0 180# define PV_CONTROL_CLK_SELECT_DSI_VEC 0
179# define PV_CONTROL_CLK_SELECT_DPI_SMI_HDMI 1 181# define PV_CONTROL_CLK_SELECT_DPI_SMI_HDMI 1
180# define PV_CONTROL_CLK_SELECT_MASK VC4_MASK(3, 2) 182# define PV_CONTROL_CLK_SELECT_MASK VC4_MASK(3, 2)