Commit 644df22f authored by Maxime Ripard's avatar Maxime Ripard

drm/vc4: crtc: Deal with different number of pixel per clock

Some of the HDMI pixelvalves in vc5 output two pixels per clock cycle.
Let's put the number of pixel output per clock cycle in the CRTC data and
update the various calculations to reflect that.
Signed-off-by: default avatarMaxime Ripard <maxime@cerno.tech>
Tested-by: default avatarChanwoo Choi <cw00.choi@samsung.com>
Tested-by: default avatarHoegeun Kwon <hoegeun.kwon@samsung.com>
Tested-by: default avatarStefan Wahren <stefan.wahren@i2se.com>
Reviewed-by: default avatarEric Anholt <eric@anholt.net>
Link: https://patchwork.freedesktop.org/patch/msgid/18a3bb079981ba820132b37e736a4bb371234d2e.1599120059.git-series.maxime@cerno.tech
parent 0ddd59c5
...@@ -235,6 +235,7 @@ static void vc4_crtc_config_pv(struct drm_crtc *crtc) ...@@ -235,6 +235,7 @@ static void vc4_crtc_config_pv(struct drm_crtc *crtc)
struct drm_encoder *encoder = vc4_get_crtc_encoder(crtc); struct drm_encoder *encoder = vc4_get_crtc_encoder(crtc);
struct vc4_encoder *vc4_encoder = to_vc4_encoder(encoder); struct vc4_encoder *vc4_encoder = to_vc4_encoder(encoder);
struct vc4_crtc *vc4_crtc = to_vc4_crtc(crtc); struct vc4_crtc *vc4_crtc = to_vc4_crtc(crtc);
const struct vc4_pv_data *pv_data = vc4_crtc_to_vc4_pv_data(vc4_crtc);
struct drm_crtc_state *state = crtc->state; struct drm_crtc_state *state = crtc->state;
struct drm_display_mode *mode = &state->adjusted_mode; struct drm_display_mode *mode = &state->adjusted_mode;
bool interlace = mode->flags & DRM_MODE_FLAG_INTERLACE; bool interlace = mode->flags & DRM_MODE_FLAG_INTERLACE;
...@@ -242,6 +243,7 @@ static void vc4_crtc_config_pv(struct drm_crtc *crtc) ...@@ -242,6 +243,7 @@ static void vc4_crtc_config_pv(struct drm_crtc *crtc)
bool is_dsi = (vc4_encoder->type == VC4_ENCODER_TYPE_DSI0 || bool is_dsi = (vc4_encoder->type == VC4_ENCODER_TYPE_DSI0 ||
vc4_encoder->type == VC4_ENCODER_TYPE_DSI1); vc4_encoder->type == VC4_ENCODER_TYPE_DSI1);
u32 format = is_dsi ? PV_CONTROL_FORMAT_DSIV_24 : PV_CONTROL_FORMAT_24; u32 format = is_dsi ? PV_CONTROL_FORMAT_DSIV_24 : PV_CONTROL_FORMAT_24;
u8 ppc = pv_data->pixels_per_clock;
/* Reset the PV fifo. */ /* Reset the PV fifo. */
CRTC_WRITE(PV_CONTROL, 0); CRTC_WRITE(PV_CONTROL, 0);
...@@ -249,17 +251,16 @@ static void vc4_crtc_config_pv(struct drm_crtc *crtc) ...@@ -249,17 +251,16 @@ static void vc4_crtc_config_pv(struct drm_crtc *crtc)
CRTC_WRITE(PV_CONTROL, 0); CRTC_WRITE(PV_CONTROL, 0);
CRTC_WRITE(PV_HORZA, CRTC_WRITE(PV_HORZA,
VC4_SET_FIELD((mode->htotal - VC4_SET_FIELD((mode->htotal - mode->hsync_end) * pixel_rep / ppc,
mode->hsync_end) * pixel_rep,
PV_HORZA_HBP) | PV_HORZA_HBP) |
VC4_SET_FIELD((mode->hsync_end - VC4_SET_FIELD((mode->hsync_end - mode->hsync_start) * pixel_rep / ppc,
mode->hsync_start) * pixel_rep,
PV_HORZA_HSYNC)); PV_HORZA_HSYNC));
CRTC_WRITE(PV_HORZB, CRTC_WRITE(PV_HORZB,
VC4_SET_FIELD((mode->hsync_start - VC4_SET_FIELD((mode->hsync_start - mode->hdisplay) * pixel_rep / ppc,
mode->hdisplay) * pixel_rep,
PV_HORZB_HFP) | PV_HORZB_HFP) |
VC4_SET_FIELD(mode->hdisplay * pixel_rep, PV_HORZB_HACTIVE)); VC4_SET_FIELD(mode->hdisplay * pixel_rep / ppc,
PV_HORZB_HACTIVE));
CRTC_WRITE(PV_VERTA, CRTC_WRITE(PV_VERTA,
VC4_SET_FIELD(mode->crtc_vtotal - mode->crtc_vsync_end, VC4_SET_FIELD(mode->crtc_vtotal - mode->crtc_vsync_end,
...@@ -761,6 +762,7 @@ static const struct vc4_pv_data bcm2835_pv0_data = { ...@@ -761,6 +762,7 @@ static const struct vc4_pv_data bcm2835_pv0_data = {
.hvs_channel = 0, .hvs_channel = 0,
}, },
.debugfs_name = "crtc0_regs", .debugfs_name = "crtc0_regs",
.pixels_per_clock = 1,
.encoder_types = { .encoder_types = {
[PV_CONTROL_CLK_SELECT_DSI] = VC4_ENCODER_TYPE_DSI0, [PV_CONTROL_CLK_SELECT_DSI] = VC4_ENCODER_TYPE_DSI0,
[PV_CONTROL_CLK_SELECT_DPI_SMI_HDMI] = VC4_ENCODER_TYPE_DPI, [PV_CONTROL_CLK_SELECT_DPI_SMI_HDMI] = VC4_ENCODER_TYPE_DPI,
...@@ -772,6 +774,7 @@ static const struct vc4_pv_data bcm2835_pv1_data = { ...@@ -772,6 +774,7 @@ static const struct vc4_pv_data bcm2835_pv1_data = {
.hvs_channel = 2, .hvs_channel = 2,
}, },
.debugfs_name = "crtc1_regs", .debugfs_name = "crtc1_regs",
.pixels_per_clock = 1,
.encoder_types = { .encoder_types = {
[PV_CONTROL_CLK_SELECT_DSI] = VC4_ENCODER_TYPE_DSI1, [PV_CONTROL_CLK_SELECT_DSI] = VC4_ENCODER_TYPE_DSI1,
[PV_CONTROL_CLK_SELECT_DPI_SMI_HDMI] = VC4_ENCODER_TYPE_SMI, [PV_CONTROL_CLK_SELECT_DPI_SMI_HDMI] = VC4_ENCODER_TYPE_SMI,
...@@ -783,6 +786,7 @@ static const struct vc4_pv_data bcm2835_pv2_data = { ...@@ -783,6 +786,7 @@ static const struct vc4_pv_data bcm2835_pv2_data = {
.hvs_channel = 1, .hvs_channel = 1,
}, },
.debugfs_name = "crtc2_regs", .debugfs_name = "crtc2_regs",
.pixels_per_clock = 1,
.encoder_types = { .encoder_types = {
[PV_CONTROL_CLK_SELECT_DPI_SMI_HDMI] = VC4_ENCODER_TYPE_HDMI, [PV_CONTROL_CLK_SELECT_DPI_SMI_HDMI] = VC4_ENCODER_TYPE_HDMI,
[PV_CONTROL_CLK_SELECT_VEC] = VC4_ENCODER_TYPE_VEC, [PV_CONTROL_CLK_SELECT_VEC] = VC4_ENCODER_TYPE_VEC,
......
...@@ -454,6 +454,9 @@ struct vc4_crtc_data { ...@@ -454,6 +454,9 @@ struct vc4_crtc_data {
struct vc4_pv_data { struct vc4_pv_data {
struct vc4_crtc_data base; struct vc4_crtc_data base;
/* Number of pixels output per clock period */
u8 pixels_per_clock;
enum vc4_encoder_type encoder_types[4]; enum vc4_encoder_type encoder_types[4];
const char *debugfs_name; const char *debugfs_name;
......
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