From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1751399AbeDDJ6K (ORCPT ); Wed, 4 Apr 2018 05:58:10 -0400 Received: from mail.bootlin.com ([62.4.15.54]:42987 "EHLO mail.bootlin.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1751279AbeDDJ5n (ORCPT ); Wed, 4 Apr 2018 05:57:43 -0400 From: Maxime Ripard To: Thierry Reding , Chen-Yu Tsai , Maxime Ripard , Mark Rutland , Rob Herring , Frank Rowand Cc: dri-devel@lists.freedesktop.org, Gustavo Padovan , Daniel Vetter , Maarten Lankhorst , Sean Paul , devicetree@vger.kernel.org, linux-arm-kernel@lists.infradead.org, linux-kernel@vger.kernel.org, Thomas Petazzoni Subject: [PATCH v4 4/8] drm/sun4i: Tie the DSI controller in the TCON Date: Wed, 4 Apr 2018 11:57:12 +0200 Message-Id: <129f5928113d2ca865bf5269047c2e4ba6fed5e6.1522835818.git-series.maxime.ripard@bootlin.com> X-Mailer: git-send-email 2.14.3 In-Reply-To: References: In-Reply-To: References: Sender: linux-kernel-owner@vger.kernel.org List-ID: X-Mailing-List: linux-kernel@vger.kernel.org The DSI controller needs a particular interface (CPU aka 8080) with some modifications from the TCON in order to run. Make sure the TCON is able to provide it when we are using the DSI output. Reviewed-by: Chen-Yu Tsai Signed-off-by: Maxime Ripard --- drivers/gpu/drm/sun4i/sun4i_tcon.c | 77 +++++++++++++++++++++++++++++++- drivers/gpu/drm/sun4i/sun4i_tcon.h | 42 +++++++++++++++++- 2 files changed, 119 insertions(+) diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.c b/drivers/gpu/drm/sun4i/sun4i_tcon.c index 5f423ed2f01b..08747fc3ee71 100644 --- a/drivers/gpu/drm/sun4i/sun4i_tcon.c +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.c @@ -35,6 +35,7 @@ #include "sun4i_lvds.h" #include "sun4i_rgb.h" #include "sun4i_tcon.h" +#include "sun6i_mipi_dsi.h" #include "sunxi_engine.h" static struct drm_connector *sun4i_tcon_get_connector(const struct drm_encoder *encoder) @@ -169,6 +170,7 @@ void sun4i_tcon_set_status(struct sun4i_tcon *tcon, case DRM_MODE_ENCODER_LVDS: is_lvds = true; /* Fallthrough */ + case DRM_MODE_ENCODER_DSI: case DRM_MODE_ENCODER_NONE: channel = 0; break; @@ -274,6 +276,71 @@ static void sun4i_tcon0_mode_set_common(struct sun4i_tcon *tcon, SUN4I_TCON0_BASIC0_Y(mode->crtc_vdisplay)); } +static void sun4i_tcon0_mode_set_cpu(struct sun4i_tcon *tcon, + struct mipi_dsi_device *device, + const struct drm_display_mode *mode) +{ + u8 bpp = mipi_dsi_pixel_format_to_bpp(device->format); + u8 lanes = device->lanes; + u32 block_space, start_delay; + u32 tcon_div; + + tcon->dclk_min_div = 4; + tcon->dclk_max_div = 127; + + sun4i_tcon0_mode_set_common(tcon, mode); + + regmap_update_bits(tcon->regs, SUN4I_TCON0_CTL_REG, + SUN4I_TCON0_CTL_IF_MASK, + SUN4I_TCON0_CTL_IF_8080); + + regmap_write(tcon->regs, SUN4I_TCON_ECC_FIFO_REG, + SUN4I_TCON_ECC_FIFO_EN); + + regmap_write(tcon->regs, SUN4I_TCON0_CPU_IF_REG, + SUN4I_TCON0_CPU_IF_MODE_DSI | + SUN4I_TCON0_CPU_IF_TRI_FIFO_FLUSH | + SUN4I_TCON0_CPU_IF_TRI_FIFO_EN | + SUN4I_TCON0_CPU_IF_TRI_EN); + + /* + * This looks suspicious, but it works... + * + * The datasheet says that this should be set higher than 20 * + * pixel cycle, but it's not clear what a pixel cycle is. + */ + regmap_read(tcon->regs, SUN4I_TCON0_DCLK_REG, &tcon_div); + tcon_div &= GENMASK(6, 0); + block_space = mode->htotal * bpp / (tcon_div * lanes); + block_space -= mode->hdisplay + 40; + + regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI0_REG, + SUN4I_TCON0_CPU_TRI0_BLOCK_SPACE(block_space) | + SUN4I_TCON0_CPU_TRI0_BLOCK_SIZE(mode->hdisplay)); + + regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI1_REG, + SUN4I_TCON0_CPU_TRI1_BLOCK_NUM(mode->vdisplay)); + + start_delay = (mode->crtc_vtotal - mode->crtc_vdisplay - 10 - 1); + start_delay = start_delay * mode->crtc_htotal * 149; + start_delay = start_delay / (mode->crtc_clock / 1000) / 8; + regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI2_REG, + SUN4I_TCON0_CPU_TRI2_TRANS_START_SET(10) | + SUN4I_TCON0_CPU_TRI2_START_DELAY(start_delay)); + + /* + * The Allwinner BSP has a comment that the period should be + * the display clock * 15, but uses an hardcoded 3000... + */ + regmap_write(tcon->regs, SUN4I_TCON_SAFE_PERIOD_REG, + SUN4I_TCON_SAFE_PERIOD_NUM(3000) | + SUN4I_TCON_SAFE_PERIOD_MODE(3)); + + /* Enable the output on the pins */ + regmap_write(tcon->regs, SUN4I_TCON0_IO_TRI_REG, + 0xe0000000); +} + static void sun4i_tcon0_mode_set_lvds(struct sun4i_tcon *tcon, const struct drm_encoder *encoder, const struct drm_display_mode *mode) @@ -539,7 +606,17 @@ void sun4i_tcon_mode_set(struct sun4i_tcon *tcon, const struct drm_encoder *encoder, const struct drm_display_mode *mode) { + struct sun6i_dsi *dsi; + switch (encoder->encoder_type) { + case DRM_MODE_ENCODER_DSI: + /* + * This is not really elegant, but it's the "cleaner" + * way I could think of... + */ + dsi = encoder_to_sun6i_dsi(encoder); + sun4i_tcon0_mode_set_cpu(tcon, dsi->device, mode); + break; case DRM_MODE_ENCODER_LVDS: sun4i_tcon0_mode_set_lvds(tcon, encoder, mode); break; diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.h b/drivers/gpu/drm/sun4i/sun4i_tcon.h index 2e0fb9640ed9..f6a071cd5a6f 100644 --- a/drivers/gpu/drm/sun4i/sun4i_tcon.h +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.h @@ -35,10 +35,25 @@ #define SUN4I_TCON_GINT0_TCON0_TRI_COUNTER_INT BIT(10) #define SUN4I_TCON_GINT1_REG 0x8 + #define SUN4I_TCON_FRM_CTL_REG 0x10 +#define SUN4I_TCON_FRM_CTL_EN BIT(31) + +#define SUN4I_TCON_FRM_SEED_PR_REG 0x14 +#define SUN4I_TCON_FRM_SEED_PG_REG 0x18 +#define SUN4I_TCON_FRM_SEED_PB_REG 0x1c +#define SUN4I_TCON_FRM_SEED_LR_REG 0x20 +#define SUN4I_TCON_FRM_SEED_LG_REG 0x24 +#define SUN4I_TCON_FRM_SEED_LB_REG 0x28 +#define SUN4I_TCON_FRM_TBL0_REG 0x2c +#define SUN4I_TCON_FRM_TBL1_REG 0x30 +#define SUN4I_TCON_FRM_TBL2_REG 0x34 +#define SUN4I_TCON_FRM_TBL3_REG 0x38 #define SUN4I_TCON0_CTL_REG 0x40 #define SUN4I_TCON0_CTL_TCON_ENABLE BIT(31) +#define SUN4I_TCON0_CTL_IF_MASK GENMASK(25, 24) +#define SUN4I_TCON0_CTL_IF_8080 (1 << 24) #define SUN4I_TCON0_CTL_CLK_DELAY_MASK GENMASK(8, 4) #define SUN4I_TCON0_CTL_CLK_DELAY(delay) ((delay << 4) & SUN4I_TCON0_CTL_CLK_DELAY_MASK) #define SUN4I_TCON0_CTL_SRC_SEL_MASK GENMASK(2, 0) @@ -65,7 +80,14 @@ #define SUN4I_TCON0_BASIC3_V_SYNC(height) (((height) - 1) & 0x7ff) #define SUN4I_TCON0_HV_IF_REG 0x58 + #define SUN4I_TCON0_CPU_IF_REG 0x60 +#define SUN4I_TCON0_CPU_IF_MODE_MASK GENMASK(31, 28) +#define SUN4I_TCON0_CPU_IF_MODE_DSI (1 << 28) +#define SUN4I_TCON0_CPU_IF_TRI_FIFO_FLUSH BIT(16) +#define SUN4I_TCON0_CPU_IF_TRI_FIFO_EN BIT(2) +#define SUN4I_TCON0_CPU_IF_TRI_EN BIT(0) + #define SUN4I_TCON0_CPU_WR_REG 0x64 #define SUN4I_TCON0_CPU_RD0_REG 0x68 #define SUN4I_TCON0_CPU_RDA_REG 0x6c @@ -132,6 +154,10 @@ #define SUN4I_TCON1_IO_POL_REG 0xf0 #define SUN4I_TCON1_IO_TRI_REG 0xf4 + +#define SUN4I_TCON_ECC_FIFO_REG 0xf8 +#define SUN4I_TCON_ECC_FIFO_EN BIT(3) + #define SUN4I_TCON_CEU_CTL_REG 0x100 #define SUN4I_TCON_CEU_MUL_RR_REG 0x110 #define SUN4I_TCON_CEU_MUL_RG_REG 0x114 @@ -148,6 +174,22 @@ #define SUN4I_TCON_CEU_RANGE_R_REG 0x140 #define SUN4I_TCON_CEU_RANGE_G_REG 0x144 #define SUN4I_TCON_CEU_RANGE_B_REG 0x148 + +#define SUN4I_TCON0_CPU_TRI0_REG 0x160 +#define SUN4I_TCON0_CPU_TRI0_BLOCK_SPACE(space) ((((space) - 1) & 0xfff) << 16) +#define SUN4I_TCON0_CPU_TRI0_BLOCK_SIZE(size) (((size) - 1) & 0xfff) + +#define SUN4I_TCON0_CPU_TRI1_REG 0x164 +#define SUN4I_TCON0_CPU_TRI1_BLOCK_NUM(num) (((num) - 1) & 0xffff) + +#define SUN4I_TCON0_CPU_TRI2_REG 0x168 +#define SUN4I_TCON0_CPU_TRI2_START_DELAY(delay) (((delay) & 0xffff) << 16) +#define SUN4I_TCON0_CPU_TRI2_TRANS_START_SET(set) ((set) & 0xfff) + +#define SUN4I_TCON_SAFE_PERIOD_REG 0x1f0 +#define SUN4I_TCON_SAFE_PERIOD_NUM(num) (((num) & 0xfff) << 16) +#define SUN4I_TCON_SAFE_PERIOD_MODE(mode) ((mode) & 0x3) + #define SUN4I_TCON_MUX_CTRL_REG 0x200 #define SUN4I_TCON0_LVDS_ANA0_REG 0x220 -- git-series 0.9.1 From mboxrd@z Thu Jan 1 00:00:00 1970 From: Maxime Ripard Subject: [PATCH v4 4/8] drm/sun4i: Tie the DSI controller in the TCON Date: Wed, 4 Apr 2018 11:57:12 +0200 Message-ID: <129f5928113d2ca865bf5269047c2e4ba6fed5e6.1522835818.git-series.maxime.ripard@bootlin.com> References: Mime-Version: 1.0 Content-Type: text/plain; charset="utf-8" Content-Transfer-Encoding: base64 Return-path: In-Reply-To: In-Reply-To: References: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dri-devel-bounces@lists.freedesktop.org Sender: "dri-devel" To: Thierry Reding , Chen-Yu Tsai , Maxime Ripard , Mark Rutland , Rob Herring , Frank Rowand Cc: devicetree@vger.kernel.org, linux-kernel@vger.kernel.org, dri-devel@lists.freedesktop.org, Thomas Petazzoni , Daniel Vetter , linux-arm-kernel@lists.infradead.org List-Id: devicetree@vger.kernel.org VGhlIERTSSBjb250cm9sbGVyIG5lZWRzIGEgcGFydGljdWxhciBpbnRlcmZhY2UgKENQVSBha2Eg ODA4MCkgd2l0aCBzb21lCm1vZGlmaWNhdGlvbnMgZnJvbSB0aGUgVENPTiBpbiBvcmRlciB0byBy dW4uCgpNYWtlIHN1cmUgdGhlIFRDT04gaXMgYWJsZSB0byBwcm92aWRlIGl0IHdoZW4gd2UgYXJl IHVzaW5nIHRoZSBEU0kgb3V0cHV0LgoKUmV2aWV3ZWQtYnk6IENoZW4tWXUgVHNhaSA8d2Vuc0Bj c2llLm9yZz4KU2lnbmVkLW9mZi1ieTogTWF4aW1lIFJpcGFyZCA8bWF4aW1lLnJpcGFyZEBib290 bGluLmNvbT4KLS0tCiBkcml2ZXJzL2dwdS9kcm0vc3VuNGkvc3VuNGlfdGNvbi5jIHwgNzcgKysr KysrKysrKysrKysrKysrKysrKysrKysrKysrKy0KIGRyaXZlcnMvZ3B1L2RybS9zdW40aS9zdW40 aV90Y29uLmggfCA0MiArKysrKysrKysrKysrKysrKy0KIDIgZmlsZXMgY2hhbmdlZCwgMTE5IGlu c2VydGlvbnMoKykKCmRpZmYgLS1naXQgYS9kcml2ZXJzL2dwdS9kcm0vc3VuNGkvc3VuNGlfdGNv bi5jIGIvZHJpdmVycy9ncHUvZHJtL3N1bjRpL3N1bjRpX3Rjb24uYwppbmRleCA1ZjQyM2VkMmYw MWIuLjA4NzQ3ZmMzZWU3MSAxMDA2NDQKLS0tIGEvZHJpdmVycy9ncHUvZHJtL3N1bjRpL3N1bjRp X3Rjb24uYworKysgYi9kcml2ZXJzL2dwdS9kcm0vc3VuNGkvc3VuNGlfdGNvbi5jCkBAIC0zNSw2 ICszNSw3IEBACiAjaW5jbHVkZSAic3VuNGlfbHZkcy5oIgogI2luY2x1ZGUgInN1bjRpX3JnYi5o IgogI2luY2x1ZGUgInN1bjRpX3Rjb24uaCIKKyNpbmNsdWRlICJzdW42aV9taXBpX2RzaS5oIgog I2luY2x1ZGUgInN1bnhpX2VuZ2luZS5oIgogCiBzdGF0aWMgc3RydWN0IGRybV9jb25uZWN0b3Ig KnN1bjRpX3Rjb25fZ2V0X2Nvbm5lY3Rvcihjb25zdCBzdHJ1Y3QgZHJtX2VuY29kZXIgKmVuY29k ZXIpCkBAIC0xNjksNiArMTcwLDcgQEAgdm9pZCBzdW40aV90Y29uX3NldF9zdGF0dXMoc3RydWN0 IHN1bjRpX3Rjb24gKnRjb24sCiAJY2FzZSBEUk1fTU9ERV9FTkNPREVSX0xWRFM6CiAJCWlzX2x2 ZHMgPSB0cnVlOwogCQkvKiBGYWxsdGhyb3VnaCAqLworCWNhc2UgRFJNX01PREVfRU5DT0RFUl9E U0k6CiAJY2FzZSBEUk1fTU9ERV9FTkNPREVSX05PTkU6CiAJCWNoYW5uZWwgPSAwOwogCQlicmVh azsKQEAgLTI3NCw2ICsyNzYsNzEgQEAgc3RhdGljIHZvaWQgc3VuNGlfdGNvbjBfbW9kZV9zZXRf Y29tbW9uKHN0cnVjdCBzdW40aV90Y29uICp0Y29uLAogCQkgICAgIFNVTjRJX1RDT04wX0JBU0lD MF9ZKG1vZGUtPmNydGNfdmRpc3BsYXkpKTsKIH0KIAorc3RhdGljIHZvaWQgc3VuNGlfdGNvbjBf bW9kZV9zZXRfY3B1KHN0cnVjdCBzdW40aV90Y29uICp0Y29uLAorCQkJCSAgICAgc3RydWN0IG1p cGlfZHNpX2RldmljZSAqZGV2aWNlLAorCQkJCSAgICAgY29uc3Qgc3RydWN0IGRybV9kaXNwbGF5 X21vZGUgKm1vZGUpCit7CisJdTggYnBwID0gbWlwaV9kc2lfcGl4ZWxfZm9ybWF0X3RvX2JwcChk ZXZpY2UtPmZvcm1hdCk7CisJdTggbGFuZXMgPSBkZXZpY2UtPmxhbmVzOworCXUzMiBibG9ja19z cGFjZSwgc3RhcnRfZGVsYXk7CisJdTMyIHRjb25fZGl2OworCisJdGNvbi0+ZGNsa19taW5fZGl2 ID0gNDsKKwl0Y29uLT5kY2xrX21heF9kaXYgPSAxMjc7CisKKwlzdW40aV90Y29uMF9tb2RlX3Nl dF9jb21tb24odGNvbiwgbW9kZSk7CisKKwlyZWdtYXBfdXBkYXRlX2JpdHModGNvbi0+cmVncywg U1VONElfVENPTjBfQ1RMX1JFRywKKwkJCSAgIFNVTjRJX1RDT04wX0NUTF9JRl9NQVNLLAorCQkJ ICAgU1VONElfVENPTjBfQ1RMX0lGXzgwODApOworCisJcmVnbWFwX3dyaXRlKHRjb24tPnJlZ3Ms IFNVTjRJX1RDT05fRUNDX0ZJRk9fUkVHLAorCQkgICAgIFNVTjRJX1RDT05fRUNDX0ZJRk9fRU4p OworCisJcmVnbWFwX3dyaXRlKHRjb24tPnJlZ3MsIFNVTjRJX1RDT04wX0NQVV9JRl9SRUcsCisJ CSAgICAgU1VONElfVENPTjBfQ1BVX0lGX01PREVfRFNJIHwKKwkJICAgICBTVU40SV9UQ09OMF9D UFVfSUZfVFJJX0ZJRk9fRkxVU0ggfAorCQkgICAgIFNVTjRJX1RDT04wX0NQVV9JRl9UUklfRklG T19FTiB8CisJCSAgICAgU1VONElfVENPTjBfQ1BVX0lGX1RSSV9FTik7CisKKwkvKgorCSAqIFRo aXMgbG9va3Mgc3VzcGljaW91cywgYnV0IGl0IHdvcmtzLi4uCisJICoKKwkgKiBUaGUgZGF0YXNo ZWV0IHNheXMgdGhhdCB0aGlzIHNob3VsZCBiZSBzZXQgaGlnaGVyIHRoYW4gMjAgKgorCSAqIHBp eGVsIGN5Y2xlLCBidXQgaXQncyBub3QgY2xlYXIgd2hhdCBhIHBpeGVsIGN5Y2xlIGlzLgorCSAq LworCXJlZ21hcF9yZWFkKHRjb24tPnJlZ3MsIFNVTjRJX1RDT04wX0RDTEtfUkVHLCAmdGNvbl9k aXYpOworCXRjb25fZGl2ICY9IEdFTk1BU0soNiwgMCk7CisJYmxvY2tfc3BhY2UgPSBtb2RlLT5o dG90YWwgKiBicHAgLyAodGNvbl9kaXYgKiBsYW5lcyk7CisJYmxvY2tfc3BhY2UgLT0gbW9kZS0+ aGRpc3BsYXkgKyA0MDsKKworCXJlZ21hcF93cml0ZSh0Y29uLT5yZWdzLCBTVU40SV9UQ09OMF9D UFVfVFJJMF9SRUcsCisJCSAgICAgU1VONElfVENPTjBfQ1BVX1RSSTBfQkxPQ0tfU1BBQ0UoYmxv Y2tfc3BhY2UpIHwKKwkJICAgICBTVU40SV9UQ09OMF9DUFVfVFJJMF9CTE9DS19TSVpFKG1vZGUt PmhkaXNwbGF5KSk7CisKKwlyZWdtYXBfd3JpdGUodGNvbi0+cmVncywgU1VONElfVENPTjBfQ1BV X1RSSTFfUkVHLAorCQkgICAgIFNVTjRJX1RDT04wX0NQVV9UUkkxX0JMT0NLX05VTShtb2RlLT52 ZGlzcGxheSkpOworCisJc3RhcnRfZGVsYXkgPSAobW9kZS0+Y3J0Y192dG90YWwgLSBtb2RlLT5j cnRjX3ZkaXNwbGF5IC0gMTAgLSAxKTsKKwlzdGFydF9kZWxheSA9IHN0YXJ0X2RlbGF5ICogbW9k ZS0+Y3J0Y19odG90YWwgKiAxNDk7CisJc3RhcnRfZGVsYXkgPSBzdGFydF9kZWxheSAvIChtb2Rl LT5jcnRjX2Nsb2NrIC8gMTAwMCkgLyA4OworCXJlZ21hcF93cml0ZSh0Y29uLT5yZWdzLCBTVU40 SV9UQ09OMF9DUFVfVFJJMl9SRUcsCisJCSAgICAgU1VONElfVENPTjBfQ1BVX1RSSTJfVFJBTlNf U1RBUlRfU0VUKDEwKSB8CisJCSAgICAgU1VONElfVENPTjBfQ1BVX1RSSTJfU1RBUlRfREVMQVko c3RhcnRfZGVsYXkpKTsKKworCS8qCisJICogVGhlIEFsbHdpbm5lciBCU1AgaGFzIGEgY29tbWVu dCB0aGF0IHRoZSBwZXJpb2Qgc2hvdWxkIGJlCisJICogdGhlIGRpc3BsYXkgY2xvY2sgKiAxNSwg YnV0IHVzZXMgYW4gaGFyZGNvZGVkIDMwMDAuLi4KKwkgKi8KKwlyZWdtYXBfd3JpdGUodGNvbi0+ cmVncywgU1VONElfVENPTl9TQUZFX1BFUklPRF9SRUcsCisJCSAgICAgU1VONElfVENPTl9TQUZF X1BFUklPRF9OVU0oMzAwMCkgfAorCQkgICAgIFNVTjRJX1RDT05fU0FGRV9QRVJJT0RfTU9ERSgz KSk7CisKKwkvKiBFbmFibGUgdGhlIG91dHB1dCBvbiB0aGUgcGlucyAqLworCXJlZ21hcF93cml0 ZSh0Y29uLT5yZWdzLCBTVU40SV9UQ09OMF9JT19UUklfUkVHLAorCQkgICAgIDB4ZTAwMDAwMDAp OworfQorCiBzdGF0aWMgdm9pZCBzdW40aV90Y29uMF9tb2RlX3NldF9sdmRzKHN0cnVjdCBzdW40 aV90Y29uICp0Y29uLAogCQkJCSAgICAgIGNvbnN0IHN0cnVjdCBkcm1fZW5jb2RlciAqZW5jb2Rl ciwKIAkJCQkgICAgICBjb25zdCBzdHJ1Y3QgZHJtX2Rpc3BsYXlfbW9kZSAqbW9kZSkKQEAgLTUz OSw3ICs2MDYsMTcgQEAgdm9pZCBzdW40aV90Y29uX21vZGVfc2V0KHN0cnVjdCBzdW40aV90Y29u ICp0Y29uLAogCQkJIGNvbnN0IHN0cnVjdCBkcm1fZW5jb2RlciAqZW5jb2RlciwKIAkJCSBjb25z dCBzdHJ1Y3QgZHJtX2Rpc3BsYXlfbW9kZSAqbW9kZSkKIHsKKwlzdHJ1Y3Qgc3VuNmlfZHNpICpk c2k7CisKIAlzd2l0Y2ggKGVuY29kZXItPmVuY29kZXJfdHlwZSkgeworCWNhc2UgRFJNX01PREVf RU5DT0RFUl9EU0k6CisJCS8qCisJCSAqIFRoaXMgaXMgbm90IHJlYWxseSBlbGVnYW50LCBidXQg aXQncyB0aGUgImNsZWFuZXIiCisJCSAqIHdheSBJIGNvdWxkIHRoaW5rIG9mLi4uCisJCSAqLwor CQlkc2kgPSBlbmNvZGVyX3RvX3N1bjZpX2RzaShlbmNvZGVyKTsKKwkJc3VuNGlfdGNvbjBfbW9k ZV9zZXRfY3B1KHRjb24sIGRzaS0+ZGV2aWNlLCBtb2RlKTsKKwkJYnJlYWs7CiAJY2FzZSBEUk1f TU9ERV9FTkNPREVSX0xWRFM6CiAJCXN1bjRpX3Rjb24wX21vZGVfc2V0X2x2ZHModGNvbiwgZW5j b2RlciwgbW9kZSk7CiAJCWJyZWFrOwpkaWZmIC0tZ2l0IGEvZHJpdmVycy9ncHUvZHJtL3N1bjRp L3N1bjRpX3Rjb24uaCBiL2RyaXZlcnMvZ3B1L2RybS9zdW40aS9zdW40aV90Y29uLmgKaW5kZXgg MmUwZmI5NjQwZWQ5Li5mNmEwNzFjZDVhNmYgMTAwNjQ0Ci0tLSBhL2RyaXZlcnMvZ3B1L2RybS9z dW40aS9zdW40aV90Y29uLmgKKysrIGIvZHJpdmVycy9ncHUvZHJtL3N1bjRpL3N1bjRpX3Rjb24u aApAQCAtMzUsMTAgKzM1LDI1IEBACiAjZGVmaW5lIFNVTjRJX1RDT05fR0lOVDBfVENPTjBfVFJJ X0NPVU5URVJfSU5UCQlCSVQoMTApCiAKICNkZWZpbmUgU1VONElfVENPTl9HSU5UMV9SRUcJCQkw eDgKKwogI2RlZmluZSBTVU40SV9UQ09OX0ZSTV9DVExfUkVHCQkJMHgxMAorI2RlZmluZSBTVU40 SV9UQ09OX0ZSTV9DVExfRU4JCQkJQklUKDMxKQorCisjZGVmaW5lIFNVTjRJX1RDT05fRlJNX1NF RURfUFJfUkVHCQkweDE0CisjZGVmaW5lIFNVTjRJX1RDT05fRlJNX1NFRURfUEdfUkVHCQkweDE4 CisjZGVmaW5lIFNVTjRJX1RDT05fRlJNX1NFRURfUEJfUkVHCQkweDFjCisjZGVmaW5lIFNVTjRJ X1RDT05fRlJNX1NFRURfTFJfUkVHCQkweDIwCisjZGVmaW5lIFNVTjRJX1RDT05fRlJNX1NFRURf TEdfUkVHCQkweDI0CisjZGVmaW5lIFNVTjRJX1RDT05fRlJNX1NFRURfTEJfUkVHCQkweDI4Cisj ZGVmaW5lIFNVTjRJX1RDT05fRlJNX1RCTDBfUkVHCQkJMHgyYworI2RlZmluZSBTVU40SV9UQ09O X0ZSTV9UQkwxX1JFRwkJCTB4MzAKKyNkZWZpbmUgU1VONElfVENPTl9GUk1fVEJMMl9SRUcJCQkw eDM0CisjZGVmaW5lIFNVTjRJX1RDT05fRlJNX1RCTDNfUkVHCQkJMHgzOAogCiAjZGVmaW5lIFNV TjRJX1RDT04wX0NUTF9SRUcJCQkweDQwCiAjZGVmaW5lIFNVTjRJX1RDT04wX0NUTF9UQ09OX0VO QUJMRQkJCUJJVCgzMSkKKyNkZWZpbmUgU1VONElfVENPTjBfQ1RMX0lGX01BU0sJCQkJR0VOTUFT SygyNSwgMjQpCisjZGVmaW5lIFNVTjRJX1RDT04wX0NUTF9JRl84MDgwCQkJCSgxIDw8IDI0KQog I2RlZmluZSBTVU40SV9UQ09OMF9DVExfQ0xLX0RFTEFZX01BU0sJCQlHRU5NQVNLKDgsIDQpCiAj ZGVmaW5lIFNVTjRJX1RDT04wX0NUTF9DTEtfREVMQVkoZGVsYXkpCQkoKGRlbGF5IDw8IDQpICYg U1VONElfVENPTjBfQ1RMX0NMS19ERUxBWV9NQVNLKQogI2RlZmluZSBTVU40SV9UQ09OMF9DVExf U1JDX1NFTF9NQVNLCQkJR0VOTUFTSygyLCAwKQpAQCAtNjUsNyArODAsMTQgQEAKICNkZWZpbmUg U1VONElfVENPTjBfQkFTSUMzX1ZfU1lOQyhoZWlnaHQpCQkoKChoZWlnaHQpIC0gMSkgJiAweDdm ZikKIAogI2RlZmluZSBTVU40SV9UQ09OMF9IVl9JRl9SRUcJCQkweDU4CisKICNkZWZpbmUgU1VO NElfVENPTjBfQ1BVX0lGX1JFRwkJCTB4NjAKKyNkZWZpbmUgU1VONElfVENPTjBfQ1BVX0lGX01P REVfTUFTSwkJCUdFTk1BU0soMzEsIDI4KQorI2RlZmluZSBTVU40SV9UQ09OMF9DUFVfSUZfTU9E RV9EU0kJCQkoMSA8PCAyOCkKKyNkZWZpbmUgU1VONElfVENPTjBfQ1BVX0lGX1RSSV9GSUZPX0ZM VVNICQlCSVQoMTYpCisjZGVmaW5lIFNVTjRJX1RDT04wX0NQVV9JRl9UUklfRklGT19FTgkJCUJJ VCgyKQorI2RlZmluZSBTVU40SV9UQ09OMF9DUFVfSUZfVFJJX0VOCQkJQklUKDApCisKICNkZWZp bmUgU1VONElfVENPTjBfQ1BVX1dSX1JFRwkJCTB4NjQKICNkZWZpbmUgU1VONElfVENPTjBfQ1BV X1JEMF9SRUcJCQkweDY4CiAjZGVmaW5lIFNVTjRJX1RDT04wX0NQVV9SREFfUkVHCQkJMHg2YwpA QCAtMTMyLDYgKzE1NCwxMCBAQAogCiAjZGVmaW5lIFNVTjRJX1RDT04xX0lPX1BPTF9SRUcJCQkw eGYwCiAjZGVmaW5lIFNVTjRJX1RDT04xX0lPX1RSSV9SRUcJCQkweGY0CisKKyNkZWZpbmUgU1VO NElfVENPTl9FQ0NfRklGT19SRUcJCQkweGY4CisjZGVmaW5lIFNVTjRJX1RDT05fRUNDX0ZJRk9f RU4JCQkJQklUKDMpCisKICNkZWZpbmUgU1VONElfVENPTl9DRVVfQ1RMX1JFRwkJCTB4MTAwCiAj ZGVmaW5lIFNVTjRJX1RDT05fQ0VVX01VTF9SUl9SRUcJCTB4MTEwCiAjZGVmaW5lIFNVTjRJX1RD T05fQ0VVX01VTF9SR19SRUcJCTB4MTE0CkBAIC0xNDgsNiArMTc0LDIyIEBACiAjZGVmaW5lIFNV TjRJX1RDT05fQ0VVX1JBTkdFX1JfUkVHCQkweDE0MAogI2RlZmluZSBTVU40SV9UQ09OX0NFVV9S QU5HRV9HX1JFRwkJMHgxNDQKICNkZWZpbmUgU1VONElfVENPTl9DRVVfUkFOR0VfQl9SRUcJCTB4 MTQ4CisKKyNkZWZpbmUgU1VONElfVENPTjBfQ1BVX1RSSTBfUkVHCQkweDE2MAorI2RlZmluZSBT VU40SV9UQ09OMF9DUFVfVFJJMF9CTE9DS19TUEFDRShzcGFjZSkJCSgoKChzcGFjZSkgLSAxKSAm IDB4ZmZmKSA8PCAxNikKKyNkZWZpbmUgU1VONElfVENPTjBfQ1BVX1RSSTBfQkxPQ0tfU0laRShz aXplKQkJKCgoc2l6ZSkgLSAxKSAmIDB4ZmZmKQorCisjZGVmaW5lIFNVTjRJX1RDT04wX0NQVV9U UkkxX1JFRwkJMHgxNjQKKyNkZWZpbmUgU1VONElfVENPTjBfQ1BVX1RSSTFfQkxPQ0tfTlVNKG51 bSkJCSgoKG51bSkgLSAxKSAmIDB4ZmZmZikKKworI2RlZmluZSBTVU40SV9UQ09OMF9DUFVfVFJJ Ml9SRUcJCTB4MTY4CisjZGVmaW5lIFNVTjRJX1RDT04wX0NQVV9UUkkyX1NUQVJUX0RFTEFZKGRl bGF5KQkJKCgoZGVsYXkpICYgMHhmZmZmKSA8PCAxNikKKyNkZWZpbmUgU1VONElfVENPTjBfQ1BV X1RSSTJfVFJBTlNfU1RBUlRfU0VUKHNldCkJKChzZXQpICYgMHhmZmYpCisKKyNkZWZpbmUgU1VO NElfVENPTl9TQUZFX1BFUklPRF9SRUcJCTB4MWYwCisjZGVmaW5lIFNVTjRJX1RDT05fU0FGRV9Q RVJJT0RfTlVNKG51bSkJCQkoKChudW0pICYgMHhmZmYpIDw8IDE2KQorI2RlZmluZSBTVU40SV9U Q09OX1NBRkVfUEVSSU9EX01PREUobW9kZSkJCSgobW9kZSkgJiAweDMpCisKICNkZWZpbmUgU1VO NElfVENPTl9NVVhfQ1RSTF9SRUcJCQkweDIwMAogCiAjZGVmaW5lIFNVTjRJX1RDT04wX0xWRFNf QU5BMF9SRUcJCTB4MjIwCi0tIApnaXQtc2VyaWVzIDAuOS4xCl9fX19fX19fX19fX19fX19fX19f X19fX19fX19fX19fX19fX19fX19fX19fX19fCmRyaS1kZXZlbCBtYWlsaW5nIGxpc3QKZHJpLWRl dmVsQGxpc3RzLmZyZWVkZXNrdG9wLm9yZwpodHRwczovL2xpc3RzLmZyZWVkZXNrdG9wLm9yZy9t YWlsbWFuL2xpc3RpbmZvL2RyaS1kZXZlbAo= From mboxrd@z Thu Jan 1 00:00:00 1970 From: maxime.ripard@bootlin.com (Maxime Ripard) Date: Wed, 4 Apr 2018 11:57:12 +0200 Subject: [PATCH v4 4/8] drm/sun4i: Tie the DSI controller in the TCON In-Reply-To: References: Message-ID: <129f5928113d2ca865bf5269047c2e4ba6fed5e6.1522835818.git-series.maxime.ripard@bootlin.com> To: linux-arm-kernel@lists.infradead.org List-Id: linux-arm-kernel.lists.infradead.org The DSI controller needs a particular interface (CPU aka 8080) with some modifications from the TCON in order to run. Make sure the TCON is able to provide it when we are using the DSI output. Reviewed-by: Chen-Yu Tsai Signed-off-by: Maxime Ripard --- drivers/gpu/drm/sun4i/sun4i_tcon.c | 77 +++++++++++++++++++++++++++++++- drivers/gpu/drm/sun4i/sun4i_tcon.h | 42 +++++++++++++++++- 2 files changed, 119 insertions(+) diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.c b/drivers/gpu/drm/sun4i/sun4i_tcon.c index 5f423ed2f01b..08747fc3ee71 100644 --- a/drivers/gpu/drm/sun4i/sun4i_tcon.c +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.c @@ -35,6 +35,7 @@ #include "sun4i_lvds.h" #include "sun4i_rgb.h" #include "sun4i_tcon.h" +#include "sun6i_mipi_dsi.h" #include "sunxi_engine.h" static struct drm_connector *sun4i_tcon_get_connector(const struct drm_encoder *encoder) @@ -169,6 +170,7 @@ void sun4i_tcon_set_status(struct sun4i_tcon *tcon, case DRM_MODE_ENCODER_LVDS: is_lvds = true; /* Fallthrough */ + case DRM_MODE_ENCODER_DSI: case DRM_MODE_ENCODER_NONE: channel = 0; break; @@ -274,6 +276,71 @@ static void sun4i_tcon0_mode_set_common(struct sun4i_tcon *tcon, SUN4I_TCON0_BASIC0_Y(mode->crtc_vdisplay)); } +static void sun4i_tcon0_mode_set_cpu(struct sun4i_tcon *tcon, + struct mipi_dsi_device *device, + const struct drm_display_mode *mode) +{ + u8 bpp = mipi_dsi_pixel_format_to_bpp(device->format); + u8 lanes = device->lanes; + u32 block_space, start_delay; + u32 tcon_div; + + tcon->dclk_min_div = 4; + tcon->dclk_max_div = 127; + + sun4i_tcon0_mode_set_common(tcon, mode); + + regmap_update_bits(tcon->regs, SUN4I_TCON0_CTL_REG, + SUN4I_TCON0_CTL_IF_MASK, + SUN4I_TCON0_CTL_IF_8080); + + regmap_write(tcon->regs, SUN4I_TCON_ECC_FIFO_REG, + SUN4I_TCON_ECC_FIFO_EN); + + regmap_write(tcon->regs, SUN4I_TCON0_CPU_IF_REG, + SUN4I_TCON0_CPU_IF_MODE_DSI | + SUN4I_TCON0_CPU_IF_TRI_FIFO_FLUSH | + SUN4I_TCON0_CPU_IF_TRI_FIFO_EN | + SUN4I_TCON0_CPU_IF_TRI_EN); + + /* + * This looks suspicious, but it works... + * + * The datasheet says that this should be set higher than 20 * + * pixel cycle, but it's not clear what a pixel cycle is. + */ + regmap_read(tcon->regs, SUN4I_TCON0_DCLK_REG, &tcon_div); + tcon_div &= GENMASK(6, 0); + block_space = mode->htotal * bpp / (tcon_div * lanes); + block_space -= mode->hdisplay + 40; + + regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI0_REG, + SUN4I_TCON0_CPU_TRI0_BLOCK_SPACE(block_space) | + SUN4I_TCON0_CPU_TRI0_BLOCK_SIZE(mode->hdisplay)); + + regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI1_REG, + SUN4I_TCON0_CPU_TRI1_BLOCK_NUM(mode->vdisplay)); + + start_delay = (mode->crtc_vtotal - mode->crtc_vdisplay - 10 - 1); + start_delay = start_delay * mode->crtc_htotal * 149; + start_delay = start_delay / (mode->crtc_clock / 1000) / 8; + regmap_write(tcon->regs, SUN4I_TCON0_CPU_TRI2_REG, + SUN4I_TCON0_CPU_TRI2_TRANS_START_SET(10) | + SUN4I_TCON0_CPU_TRI2_START_DELAY(start_delay)); + + /* + * The Allwinner BSP has a comment that the period should be + * the display clock * 15, but uses an hardcoded 3000... + */ + regmap_write(tcon->regs, SUN4I_TCON_SAFE_PERIOD_REG, + SUN4I_TCON_SAFE_PERIOD_NUM(3000) | + SUN4I_TCON_SAFE_PERIOD_MODE(3)); + + /* Enable the output on the pins */ + regmap_write(tcon->regs, SUN4I_TCON0_IO_TRI_REG, + 0xe0000000); +} + static void sun4i_tcon0_mode_set_lvds(struct sun4i_tcon *tcon, const struct drm_encoder *encoder, const struct drm_display_mode *mode) @@ -539,7 +606,17 @@ void sun4i_tcon_mode_set(struct sun4i_tcon *tcon, const struct drm_encoder *encoder, const struct drm_display_mode *mode) { + struct sun6i_dsi *dsi; + switch (encoder->encoder_type) { + case DRM_MODE_ENCODER_DSI: + /* + * This is not really elegant, but it's the "cleaner" + * way I could think of... + */ + dsi = encoder_to_sun6i_dsi(encoder); + sun4i_tcon0_mode_set_cpu(tcon, dsi->device, mode); + break; case DRM_MODE_ENCODER_LVDS: sun4i_tcon0_mode_set_lvds(tcon, encoder, mode); break; diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.h b/drivers/gpu/drm/sun4i/sun4i_tcon.h index 2e0fb9640ed9..f6a071cd5a6f 100644 --- a/drivers/gpu/drm/sun4i/sun4i_tcon.h +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.h @@ -35,10 +35,25 @@ #define SUN4I_TCON_GINT0_TCON0_TRI_COUNTER_INT BIT(10) #define SUN4I_TCON_GINT1_REG 0x8 + #define SUN4I_TCON_FRM_CTL_REG 0x10 +#define SUN4I_TCON_FRM_CTL_EN BIT(31) + +#define SUN4I_TCON_FRM_SEED_PR_REG 0x14 +#define SUN4I_TCON_FRM_SEED_PG_REG 0x18 +#define SUN4I_TCON_FRM_SEED_PB_REG 0x1c +#define SUN4I_TCON_FRM_SEED_LR_REG 0x20 +#define SUN4I_TCON_FRM_SEED_LG_REG 0x24 +#define SUN4I_TCON_FRM_SEED_LB_REG 0x28 +#define SUN4I_TCON_FRM_TBL0_REG 0x2c +#define SUN4I_TCON_FRM_TBL1_REG 0x30 +#define SUN4I_TCON_FRM_TBL2_REG 0x34 +#define SUN4I_TCON_FRM_TBL3_REG 0x38 #define SUN4I_TCON0_CTL_REG 0x40 #define SUN4I_TCON0_CTL_TCON_ENABLE BIT(31) +#define SUN4I_TCON0_CTL_IF_MASK GENMASK(25, 24) +#define SUN4I_TCON0_CTL_IF_8080 (1 << 24) #define SUN4I_TCON0_CTL_CLK_DELAY_MASK GENMASK(8, 4) #define SUN4I_TCON0_CTL_CLK_DELAY(delay) ((delay << 4) & SUN4I_TCON0_CTL_CLK_DELAY_MASK) #define SUN4I_TCON0_CTL_SRC_SEL_MASK GENMASK(2, 0) @@ -65,7 +80,14 @@ #define SUN4I_TCON0_BASIC3_V_SYNC(height) (((height) - 1) & 0x7ff) #define SUN4I_TCON0_HV_IF_REG 0x58 + #define SUN4I_TCON0_CPU_IF_REG 0x60 +#define SUN4I_TCON0_CPU_IF_MODE_MASK GENMASK(31, 28) +#define SUN4I_TCON0_CPU_IF_MODE_DSI (1 << 28) +#define SUN4I_TCON0_CPU_IF_TRI_FIFO_FLUSH BIT(16) +#define SUN4I_TCON0_CPU_IF_TRI_FIFO_EN BIT(2) +#define SUN4I_TCON0_CPU_IF_TRI_EN BIT(0) + #define SUN4I_TCON0_CPU_WR_REG 0x64 #define SUN4I_TCON0_CPU_RD0_REG 0x68 #define SUN4I_TCON0_CPU_RDA_REG 0x6c @@ -132,6 +154,10 @@ #define SUN4I_TCON1_IO_POL_REG 0xf0 #define SUN4I_TCON1_IO_TRI_REG 0xf4 + +#define SUN4I_TCON_ECC_FIFO_REG 0xf8 +#define SUN4I_TCON_ECC_FIFO_EN BIT(3) + #define SUN4I_TCON_CEU_CTL_REG 0x100 #define SUN4I_TCON_CEU_MUL_RR_REG 0x110 #define SUN4I_TCON_CEU_MUL_RG_REG 0x114 @@ -148,6 +174,22 @@ #define SUN4I_TCON_CEU_RANGE_R_REG 0x140 #define SUN4I_TCON_CEU_RANGE_G_REG 0x144 #define SUN4I_TCON_CEU_RANGE_B_REG 0x148 + +#define SUN4I_TCON0_CPU_TRI0_REG 0x160 +#define SUN4I_TCON0_CPU_TRI0_BLOCK_SPACE(space) ((((space) - 1) & 0xfff) << 16) +#define SUN4I_TCON0_CPU_TRI0_BLOCK_SIZE(size) (((size) - 1) & 0xfff) + +#define SUN4I_TCON0_CPU_TRI1_REG 0x164 +#define SUN4I_TCON0_CPU_TRI1_BLOCK_NUM(num) (((num) - 1) & 0xffff) + +#define SUN4I_TCON0_CPU_TRI2_REG 0x168 +#define SUN4I_TCON0_CPU_TRI2_START_DELAY(delay) (((delay) & 0xffff) << 16) +#define SUN4I_TCON0_CPU_TRI2_TRANS_START_SET(set) ((set) & 0xfff) + +#define SUN4I_TCON_SAFE_PERIOD_REG 0x1f0 +#define SUN4I_TCON_SAFE_PERIOD_NUM(num) (((num) & 0xfff) << 16) +#define SUN4I_TCON_SAFE_PERIOD_MODE(mode) ((mode) & 0x3) + #define SUN4I_TCON_MUX_CTRL_REG 0x200 #define SUN4I_TCON0_LVDS_ANA0_REG 0x220 -- git-series 0.9.1