1 | // SPDX-License-Identifier: GPL-2.0 |
2 | /* |
3 | * TI SN65DSI83,84,85 driver |
4 | * |
5 | * Currently supported: |
6 | * - SN65DSI83 |
7 | * = 1x Single-link DSI ~ 1x Single-link LVDS |
8 | * - Supported |
9 | * - Single-link LVDS mode tested |
10 | * - SN65DSI84 |
11 | * = 1x Single-link DSI ~ 2x Single-link or 1x Dual-link LVDS |
12 | * - Supported |
13 | * - Dual-link LVDS mode tested |
14 | * - 2x Single-link LVDS mode unsupported |
15 | * (should be easy to add by someone who has the HW) |
16 | * - SN65DSI85 |
17 | * = 2x Single-link or 1x Dual-link DSI ~ 2x Single-link or 1x Dual-link LVDS |
18 | * - Unsupported |
19 | * (should be easy to add by someone who has the HW) |
20 | * |
21 | * Copyright (C) 2021 Marek Vasut <marex@denx.de> |
22 | * |
23 | * Based on previous work of: |
24 | * Valentin Raevsky <valentin@compulab.co.il> |
25 | * Philippe Schenker <philippe.schenker@toradex.com> |
26 | */ |
27 | |
28 | #include <linux/bits.h> |
29 | #include <linux/clk.h> |
30 | #include <linux/gpio/consumer.h> |
31 | #include <linux/i2c.h> |
32 | #include <linux/media-bus-format.h> |
33 | #include <linux/module.h> |
34 | #include <linux/of.h> |
35 | #include <linux/of_graph.h> |
36 | #include <linux/regmap.h> |
37 | #include <linux/regulator/consumer.h> |
38 | |
39 | #include <drm/drm_atomic_helper.h> |
40 | #include <drm/drm_bridge.h> |
41 | #include <drm/drm_mipi_dsi.h> |
42 | #include <drm/drm_of.h> |
43 | #include <drm/drm_panel.h> |
44 | #include <drm/drm_print.h> |
45 | #include <drm/drm_probe_helper.h> |
46 | |
47 | /* ID registers */ |
48 | #define REG_ID(n) (0x00 + (n)) |
49 | /* Reset and clock registers */ |
50 | #define REG_RC_RESET 0x09 |
51 | #define REG_RC_RESET_SOFT_RESET BIT(0) |
52 | #define REG_RC_LVDS_PLL 0x0a |
53 | #define REG_RC_LVDS_PLL_PLL_EN_STAT BIT(7) |
54 | #define REG_RC_LVDS_PLL_LVDS_CLK_RANGE(n) (((n) & 0x7) << 1) |
55 | #define REG_RC_LVDS_PLL_HS_CLK_SRC_DPHY BIT(0) |
56 | #define REG_RC_DSI_CLK 0x0b |
57 | #define REG_RC_DSI_CLK_DSI_CLK_DIVIDER(n) (((n) & 0x1f) << 3) |
58 | #define REG_RC_DSI_CLK_REFCLK_MULTIPLIER(n) ((n) & 0x3) |
59 | #define REG_RC_PLL_EN 0x0d |
60 | #define REG_RC_PLL_EN_PLL_EN BIT(0) |
61 | /* DSI registers */ |
62 | #define REG_DSI_LANE 0x10 |
63 | #define REG_DSI_LANE_LEFT_RIGHT_PIXELS BIT(7) /* DSI85-only */ |
64 | #define REG_DSI_LANE_DSI_CHANNEL_MODE_DUAL 0 /* DSI85-only */ |
65 | #define REG_DSI_LANE_DSI_CHANNEL_MODE_2SINGLE BIT(6) /* DSI85-only */ |
66 | #define REG_DSI_LANE_DSI_CHANNEL_MODE_SINGLE BIT(5) |
67 | #define REG_DSI_LANE_CHA_DSI_LANES(n) (((n) & 0x3) << 3) |
68 | #define REG_DSI_LANE_CHB_DSI_LANES(n) (((n) & 0x3) << 1) |
69 | #define REG_DSI_LANE_SOT_ERR_TOL_DIS BIT(0) |
70 | #define REG_DSI_EQ 0x11 |
71 | #define REG_DSI_EQ_CHA_DSI_DATA_EQ(n) (((n) & 0x3) << 6) |
72 | #define REG_DSI_EQ_CHA_DSI_CLK_EQ(n) (((n) & 0x3) << 2) |
73 | #define REG_DSI_CLK 0x12 |
74 | #define REG_DSI_CLK_CHA_DSI_CLK_RANGE(n) ((n) & 0xff) |
75 | /* LVDS registers */ |
76 | #define REG_LVDS_FMT 0x18 |
77 | #define REG_LVDS_FMT_DE_NEG_POLARITY BIT(7) |
78 | #define REG_LVDS_FMT_HS_NEG_POLARITY BIT(6) |
79 | #define REG_LVDS_FMT_VS_NEG_POLARITY BIT(5) |
80 | #define REG_LVDS_FMT_LVDS_LINK_CFG BIT(4) /* 0:AB 1:A-only */ |
81 | #define REG_LVDS_FMT_CHA_24BPP_MODE BIT(3) |
82 | #define REG_LVDS_FMT_CHB_24BPP_MODE BIT(2) |
83 | #define REG_LVDS_FMT_CHA_24BPP_FORMAT1 BIT(1) |
84 | #define REG_LVDS_FMT_CHB_24BPP_FORMAT1 BIT(0) |
85 | #define REG_LVDS_VCOM 0x19 |
86 | #define REG_LVDS_VCOM_CHA_LVDS_VOCM BIT(6) |
87 | #define REG_LVDS_VCOM_CHB_LVDS_VOCM BIT(4) |
88 | #define REG_LVDS_VCOM_CHA_LVDS_VOD_SWING(n) (((n) & 0x3) << 2) |
89 | #define REG_LVDS_VCOM_CHB_LVDS_VOD_SWING(n) ((n) & 0x3) |
90 | #define REG_LVDS_LANE 0x1a |
91 | #define REG_LVDS_LANE_EVEN_ODD_SWAP BIT(6) |
92 | #define REG_LVDS_LANE_CHA_REVERSE_LVDS BIT(5) |
93 | #define REG_LVDS_LANE_CHB_REVERSE_LVDS BIT(4) |
94 | #define REG_LVDS_LANE_CHA_LVDS_TERM BIT(1) |
95 | #define REG_LVDS_LANE_CHB_LVDS_TERM BIT(0) |
96 | #define REG_LVDS_CM 0x1b |
97 | #define REG_LVDS_CM_CHA_LVDS_CM_ADJUST(n) (((n) & 0x3) << 4) |
98 | #define REG_LVDS_CM_CHB_LVDS_CM_ADJUST(n) ((n) & 0x3) |
99 | /* Video registers */ |
100 | #define REG_VID_CHA_ACTIVE_LINE_LENGTH_LOW 0x20 |
101 | #define REG_VID_CHA_ACTIVE_LINE_LENGTH_HIGH 0x21 |
102 | #define REG_VID_CHA_VERTICAL_DISPLAY_SIZE_LOW 0x24 |
103 | #define REG_VID_CHA_VERTICAL_DISPLAY_SIZE_HIGH 0x25 |
104 | #define REG_VID_CHA_SYNC_DELAY_LOW 0x28 |
105 | #define REG_VID_CHA_SYNC_DELAY_HIGH 0x29 |
106 | #define REG_VID_CHA_HSYNC_PULSE_WIDTH_LOW 0x2c |
107 | #define REG_VID_CHA_HSYNC_PULSE_WIDTH_HIGH 0x2d |
108 | #define REG_VID_CHA_VSYNC_PULSE_WIDTH_LOW 0x30 |
109 | #define REG_VID_CHA_VSYNC_PULSE_WIDTH_HIGH 0x31 |
110 | #define REG_VID_CHA_HORIZONTAL_BACK_PORCH 0x34 |
111 | #define REG_VID_CHA_VERTICAL_BACK_PORCH 0x36 |
112 | #define REG_VID_CHA_HORIZONTAL_FRONT_PORCH 0x38 |
113 | #define REG_VID_CHA_VERTICAL_FRONT_PORCH 0x3a |
114 | #define REG_VID_CHA_TEST_PATTERN 0x3c |
115 | /* IRQ registers */ |
116 | #define REG_IRQ_GLOBAL 0xe0 |
117 | #define REG_IRQ_GLOBAL_IRQ_EN BIT(0) |
118 | #define REG_IRQ_EN 0xe1 |
119 | #define REG_IRQ_EN_CHA_SYNCH_ERR_EN BIT(7) |
120 | #define REG_IRQ_EN_CHA_CRC_ERR_EN BIT(6) |
121 | #define REG_IRQ_EN_CHA_UNC_ECC_ERR_EN BIT(5) |
122 | #define REG_IRQ_EN_CHA_COR_ECC_ERR_EN BIT(4) |
123 | #define REG_IRQ_EN_CHA_LLP_ERR_EN BIT(3) |
124 | #define REG_IRQ_EN_CHA_SOT_BIT_ERR_EN BIT(2) |
125 | #define REG_IRQ_EN_CHA_PLL_UNLOCK_EN BIT(0) |
126 | #define REG_IRQ_STAT 0xe5 |
127 | #define REG_IRQ_STAT_CHA_SYNCH_ERR BIT(7) |
128 | #define REG_IRQ_STAT_CHA_CRC_ERR BIT(6) |
129 | #define REG_IRQ_STAT_CHA_UNC_ECC_ERR BIT(5) |
130 | #define REG_IRQ_STAT_CHA_COR_ECC_ERR BIT(4) |
131 | #define REG_IRQ_STAT_CHA_LLP_ERR BIT(3) |
132 | #define REG_IRQ_STAT_CHA_SOT_BIT_ERR BIT(2) |
133 | #define REG_IRQ_STAT_CHA_PLL_UNLOCK BIT(0) |
134 | |
135 | enum sn65dsi83_model { |
136 | MODEL_SN65DSI83, |
137 | MODEL_SN65DSI84, |
138 | }; |
139 | |
140 | struct sn65dsi83 { |
141 | struct drm_bridge bridge; |
142 | struct device *dev; |
143 | struct regmap *regmap; |
144 | struct mipi_dsi_device *dsi; |
145 | struct drm_bridge *panel_bridge; |
146 | struct gpio_desc *enable_gpio; |
147 | struct regulator *vcc; |
148 | bool lvds_dual_link; |
149 | bool lvds_dual_link_even_odd_swap; |
150 | }; |
151 | |
152 | static const struct regmap_range sn65dsi83_readable_ranges[] = { |
153 | regmap_reg_range(REG_ID(0), REG_ID(8)), |
154 | regmap_reg_range(REG_RC_LVDS_PLL, REG_RC_DSI_CLK), |
155 | regmap_reg_range(REG_RC_PLL_EN, REG_RC_PLL_EN), |
156 | regmap_reg_range(REG_DSI_LANE, REG_DSI_CLK), |
157 | regmap_reg_range(REG_LVDS_FMT, REG_LVDS_CM), |
158 | regmap_reg_range(REG_VID_CHA_ACTIVE_LINE_LENGTH_LOW, |
159 | REG_VID_CHA_ACTIVE_LINE_LENGTH_HIGH), |
160 | regmap_reg_range(REG_VID_CHA_VERTICAL_DISPLAY_SIZE_LOW, |
161 | REG_VID_CHA_VERTICAL_DISPLAY_SIZE_HIGH), |
162 | regmap_reg_range(REG_VID_CHA_SYNC_DELAY_LOW, |
163 | REG_VID_CHA_SYNC_DELAY_HIGH), |
164 | regmap_reg_range(REG_VID_CHA_HSYNC_PULSE_WIDTH_LOW, |
165 | REG_VID_CHA_HSYNC_PULSE_WIDTH_HIGH), |
166 | regmap_reg_range(REG_VID_CHA_VSYNC_PULSE_WIDTH_LOW, |
167 | REG_VID_CHA_VSYNC_PULSE_WIDTH_HIGH), |
168 | regmap_reg_range(REG_VID_CHA_HORIZONTAL_BACK_PORCH, |
169 | REG_VID_CHA_HORIZONTAL_BACK_PORCH), |
170 | regmap_reg_range(REG_VID_CHA_VERTICAL_BACK_PORCH, |
171 | REG_VID_CHA_VERTICAL_BACK_PORCH), |
172 | regmap_reg_range(REG_VID_CHA_HORIZONTAL_FRONT_PORCH, |
173 | REG_VID_CHA_HORIZONTAL_FRONT_PORCH), |
174 | regmap_reg_range(REG_VID_CHA_VERTICAL_FRONT_PORCH, |
175 | REG_VID_CHA_VERTICAL_FRONT_PORCH), |
176 | regmap_reg_range(REG_VID_CHA_TEST_PATTERN, REG_VID_CHA_TEST_PATTERN), |
177 | regmap_reg_range(REG_IRQ_GLOBAL, REG_IRQ_EN), |
178 | regmap_reg_range(REG_IRQ_STAT, REG_IRQ_STAT), |
179 | }; |
180 | |
181 | static const struct regmap_access_table sn65dsi83_readable_table = { |
182 | .yes_ranges = sn65dsi83_readable_ranges, |
183 | .n_yes_ranges = ARRAY_SIZE(sn65dsi83_readable_ranges), |
184 | }; |
185 | |
186 | static const struct regmap_range sn65dsi83_writeable_ranges[] = { |
187 | regmap_reg_range(REG_RC_RESET, REG_RC_DSI_CLK), |
188 | regmap_reg_range(REG_RC_PLL_EN, REG_RC_PLL_EN), |
189 | regmap_reg_range(REG_DSI_LANE, REG_DSI_CLK), |
190 | regmap_reg_range(REG_LVDS_FMT, REG_LVDS_CM), |
191 | regmap_reg_range(REG_VID_CHA_ACTIVE_LINE_LENGTH_LOW, |
192 | REG_VID_CHA_ACTIVE_LINE_LENGTH_HIGH), |
193 | regmap_reg_range(REG_VID_CHA_VERTICAL_DISPLAY_SIZE_LOW, |
194 | REG_VID_CHA_VERTICAL_DISPLAY_SIZE_HIGH), |
195 | regmap_reg_range(REG_VID_CHA_SYNC_DELAY_LOW, |
196 | REG_VID_CHA_SYNC_DELAY_HIGH), |
197 | regmap_reg_range(REG_VID_CHA_HSYNC_PULSE_WIDTH_LOW, |
198 | REG_VID_CHA_HSYNC_PULSE_WIDTH_HIGH), |
199 | regmap_reg_range(REG_VID_CHA_VSYNC_PULSE_WIDTH_LOW, |
200 | REG_VID_CHA_VSYNC_PULSE_WIDTH_HIGH), |
201 | regmap_reg_range(REG_VID_CHA_HORIZONTAL_BACK_PORCH, |
202 | REG_VID_CHA_HORIZONTAL_BACK_PORCH), |
203 | regmap_reg_range(REG_VID_CHA_VERTICAL_BACK_PORCH, |
204 | REG_VID_CHA_VERTICAL_BACK_PORCH), |
205 | regmap_reg_range(REG_VID_CHA_HORIZONTAL_FRONT_PORCH, |
206 | REG_VID_CHA_HORIZONTAL_FRONT_PORCH), |
207 | regmap_reg_range(REG_VID_CHA_VERTICAL_FRONT_PORCH, |
208 | REG_VID_CHA_VERTICAL_FRONT_PORCH), |
209 | regmap_reg_range(REG_VID_CHA_TEST_PATTERN, REG_VID_CHA_TEST_PATTERN), |
210 | regmap_reg_range(REG_IRQ_GLOBAL, REG_IRQ_EN), |
211 | regmap_reg_range(REG_IRQ_STAT, REG_IRQ_STAT), |
212 | }; |
213 | |
214 | static const struct regmap_access_table sn65dsi83_writeable_table = { |
215 | .yes_ranges = sn65dsi83_writeable_ranges, |
216 | .n_yes_ranges = ARRAY_SIZE(sn65dsi83_writeable_ranges), |
217 | }; |
218 | |
219 | static const struct regmap_range sn65dsi83_volatile_ranges[] = { |
220 | regmap_reg_range(REG_RC_RESET, REG_RC_RESET), |
221 | regmap_reg_range(REG_RC_LVDS_PLL, REG_RC_LVDS_PLL), |
222 | regmap_reg_range(REG_IRQ_STAT, REG_IRQ_STAT), |
223 | }; |
224 | |
225 | static const struct regmap_access_table sn65dsi83_volatile_table = { |
226 | .yes_ranges = sn65dsi83_volatile_ranges, |
227 | .n_yes_ranges = ARRAY_SIZE(sn65dsi83_volatile_ranges), |
228 | }; |
229 | |
230 | static const struct regmap_config sn65dsi83_regmap_config = { |
231 | .reg_bits = 8, |
232 | .val_bits = 8, |
233 | .rd_table = &sn65dsi83_readable_table, |
234 | .wr_table = &sn65dsi83_writeable_table, |
235 | .volatile_table = &sn65dsi83_volatile_table, |
236 | .cache_type = REGCACHE_MAPLE, |
237 | .max_register = REG_IRQ_STAT, |
238 | }; |
239 | |
240 | static struct sn65dsi83 *bridge_to_sn65dsi83(struct drm_bridge *bridge) |
241 | { |
242 | return container_of(bridge, struct sn65dsi83, bridge); |
243 | } |
244 | |
245 | static int sn65dsi83_attach(struct drm_bridge *bridge, |
246 | enum drm_bridge_attach_flags flags) |
247 | { |
248 | struct sn65dsi83 *ctx = bridge_to_sn65dsi83(bridge); |
249 | |
250 | return drm_bridge_attach(encoder: bridge->encoder, bridge: ctx->panel_bridge, |
251 | previous: &ctx->bridge, flags); |
252 | } |
253 | |
254 | static void sn65dsi83_detach(struct drm_bridge *bridge) |
255 | { |
256 | struct sn65dsi83 *ctx = bridge_to_sn65dsi83(bridge); |
257 | |
258 | if (!ctx->dsi) |
259 | return; |
260 | |
261 | ctx->dsi = NULL; |
262 | } |
263 | |
264 | static u8 sn65dsi83_get_lvds_range(struct sn65dsi83 *ctx, |
265 | const struct drm_display_mode *mode) |
266 | { |
267 | /* |
268 | * The encoding of the LVDS_CLK_RANGE is as follows: |
269 | * 000 - 25 MHz <= LVDS_CLK < 37.5 MHz |
270 | * 001 - 37.5 MHz <= LVDS_CLK < 62.5 MHz |
271 | * 010 - 62.5 MHz <= LVDS_CLK < 87.5 MHz |
272 | * 011 - 87.5 MHz <= LVDS_CLK < 112.5 MHz |
273 | * 100 - 112.5 MHz <= LVDS_CLK < 137.5 MHz |
274 | * 101 - 137.5 MHz <= LVDS_CLK <= 154 MHz |
275 | * which is a range of 12.5MHz..162.5MHz in 50MHz steps, except that |
276 | * the ends of the ranges are clamped to the supported range. Since |
277 | * sn65dsi83_mode_valid() already filters the valid modes and limits |
278 | * the clock to 25..154 MHz, the range calculation can be simplified |
279 | * as follows: |
280 | */ |
281 | int mode_clock = mode->clock; |
282 | |
283 | if (ctx->lvds_dual_link) |
284 | mode_clock /= 2; |
285 | |
286 | return (mode_clock - 12500) / 25000; |
287 | } |
288 | |
289 | static u8 sn65dsi83_get_dsi_range(struct sn65dsi83 *ctx, |
290 | const struct drm_display_mode *mode) |
291 | { |
292 | /* |
293 | * The encoding of the CHA_DSI_CLK_RANGE is as follows: |
294 | * 0x00 through 0x07 - Reserved |
295 | * 0x08 - 40 <= DSI_CLK < 45 MHz |
296 | * 0x09 - 45 <= DSI_CLK < 50 MHz |
297 | * ... |
298 | * 0x63 - 495 <= DSI_CLK < 500 MHz |
299 | * 0x64 - 500 MHz |
300 | * 0x65 through 0xFF - Reserved |
301 | * which is DSI clock in 5 MHz steps, clamped to 40..500 MHz. |
302 | * The DSI clock are calculated as: |
303 | * DSI_CLK = mode clock * bpp / dsi_data_lanes / 2 |
304 | * the 2 is there because the bus is DDR. |
305 | */ |
306 | return DIV_ROUND_UP(clamp((unsigned int)mode->clock * |
307 | mipi_dsi_pixel_format_to_bpp(ctx->dsi->format) / |
308 | ctx->dsi->lanes / 2, 40000U, 500000U), 5000U); |
309 | } |
310 | |
311 | static u8 sn65dsi83_get_dsi_div(struct sn65dsi83 *ctx) |
312 | { |
313 | /* The divider is (DSI_CLK / LVDS_CLK) - 1, which really is: */ |
314 | unsigned int dsi_div = mipi_dsi_pixel_format_to_bpp(fmt: ctx->dsi->format); |
315 | |
316 | dsi_div /= ctx->dsi->lanes; |
317 | |
318 | if (!ctx->lvds_dual_link) |
319 | dsi_div /= 2; |
320 | |
321 | return dsi_div - 1; |
322 | } |
323 | |
324 | static void sn65dsi83_atomic_pre_enable(struct drm_bridge *bridge, |
325 | struct drm_bridge_state *old_bridge_state) |
326 | { |
327 | struct sn65dsi83 *ctx = bridge_to_sn65dsi83(bridge); |
328 | struct drm_atomic_state *state = old_bridge_state->base.state; |
329 | const struct drm_bridge_state *bridge_state; |
330 | const struct drm_crtc_state *crtc_state; |
331 | const struct drm_display_mode *mode; |
332 | struct drm_connector *connector; |
333 | struct drm_crtc *crtc; |
334 | bool lvds_format_24bpp; |
335 | bool lvds_format_jeida; |
336 | unsigned int pval; |
337 | __le16 le16val; |
338 | u16 val; |
339 | int ret; |
340 | |
341 | ret = regulator_enable(regulator: ctx->vcc); |
342 | if (ret) { |
343 | dev_err(ctx->dev, "Failed to enable vcc: %d\n" , ret); |
344 | return; |
345 | } |
346 | |
347 | /* Deassert reset */ |
348 | gpiod_set_value_cansleep(desc: ctx->enable_gpio, value: 1); |
349 | usleep_range(min: 10000, max: 11000); |
350 | |
351 | /* Get the LVDS format from the bridge state. */ |
352 | bridge_state = drm_atomic_get_new_bridge_state(state, bridge); |
353 | |
354 | switch (bridge_state->output_bus_cfg.format) { |
355 | case MEDIA_BUS_FMT_RGB666_1X7X3_SPWG: |
356 | lvds_format_24bpp = false; |
357 | lvds_format_jeida = true; |
358 | break; |
359 | case MEDIA_BUS_FMT_RGB888_1X7X4_JEIDA: |
360 | lvds_format_24bpp = true; |
361 | lvds_format_jeida = true; |
362 | break; |
363 | case MEDIA_BUS_FMT_RGB888_1X7X4_SPWG: |
364 | lvds_format_24bpp = true; |
365 | lvds_format_jeida = false; |
366 | break; |
367 | default: |
368 | /* |
369 | * Some bridges still don't set the correct |
370 | * LVDS bus pixel format, use SPWG24 default |
371 | * format until those are fixed. |
372 | */ |
373 | lvds_format_24bpp = true; |
374 | lvds_format_jeida = false; |
375 | dev_warn(ctx->dev, |
376 | "Unsupported LVDS bus format 0x%04x, please check output bridge driver. Falling back to SPWG24.\n" , |
377 | bridge_state->output_bus_cfg.format); |
378 | break; |
379 | } |
380 | |
381 | /* |
382 | * Retrieve the CRTC adjusted mode. This requires a little dance to go |
383 | * from the bridge to the encoder, to the connector and to the CRTC. |
384 | */ |
385 | connector = drm_atomic_get_new_connector_for_encoder(state, |
386 | encoder: bridge->encoder); |
387 | crtc = drm_atomic_get_new_connector_state(state, connector)->crtc; |
388 | crtc_state = drm_atomic_get_new_crtc_state(state, crtc); |
389 | mode = &crtc_state->adjusted_mode; |
390 | |
391 | /* Clear reset, disable PLL */ |
392 | regmap_write(map: ctx->regmap, REG_RC_RESET, val: 0x00); |
393 | regmap_write(map: ctx->regmap, REG_RC_PLL_EN, val: 0x00); |
394 | |
395 | /* Reference clock derived from DSI link clock. */ |
396 | regmap_write(map: ctx->regmap, REG_RC_LVDS_PLL, |
397 | REG_RC_LVDS_PLL_LVDS_CLK_RANGE(sn65dsi83_get_lvds_range(ctx, mode)) | |
398 | REG_RC_LVDS_PLL_HS_CLK_SRC_DPHY); |
399 | regmap_write(map: ctx->regmap, REG_DSI_CLK, |
400 | REG_DSI_CLK_CHA_DSI_CLK_RANGE(sn65dsi83_get_dsi_range(ctx, mode))); |
401 | regmap_write(map: ctx->regmap, REG_RC_DSI_CLK, |
402 | REG_RC_DSI_CLK_DSI_CLK_DIVIDER(sn65dsi83_get_dsi_div(ctx))); |
403 | |
404 | /* Set number of DSI lanes and LVDS link config. */ |
405 | regmap_write(map: ctx->regmap, REG_DSI_LANE, |
406 | REG_DSI_LANE_DSI_CHANNEL_MODE_SINGLE | |
407 | REG_DSI_LANE_CHA_DSI_LANES(~(ctx->dsi->lanes - 1)) | |
408 | /* CHB is DSI85-only, set to default on DSI83/DSI84 */ |
409 | REG_DSI_LANE_CHB_DSI_LANES(3)); |
410 | /* No equalization. */ |
411 | regmap_write(map: ctx->regmap, REG_DSI_EQ, val: 0x00); |
412 | |
413 | /* Set up sync signal polarity. */ |
414 | val = (mode->flags & DRM_MODE_FLAG_NHSYNC ? |
415 | REG_LVDS_FMT_HS_NEG_POLARITY : 0) | |
416 | (mode->flags & DRM_MODE_FLAG_NVSYNC ? |
417 | REG_LVDS_FMT_VS_NEG_POLARITY : 0); |
418 | |
419 | /* Set up bits-per-pixel, 18bpp or 24bpp. */ |
420 | if (lvds_format_24bpp) { |
421 | val |= REG_LVDS_FMT_CHA_24BPP_MODE; |
422 | if (ctx->lvds_dual_link) |
423 | val |= REG_LVDS_FMT_CHB_24BPP_MODE; |
424 | } |
425 | |
426 | /* Set up LVDS format, JEIDA/Format 1 or SPWG/Format 2 */ |
427 | if (lvds_format_jeida) { |
428 | val |= REG_LVDS_FMT_CHA_24BPP_FORMAT1; |
429 | if (ctx->lvds_dual_link) |
430 | val |= REG_LVDS_FMT_CHB_24BPP_FORMAT1; |
431 | } |
432 | |
433 | /* Set up LVDS output config (DSI84,DSI85) */ |
434 | if (!ctx->lvds_dual_link) |
435 | val |= REG_LVDS_FMT_LVDS_LINK_CFG; |
436 | |
437 | regmap_write(map: ctx->regmap, REG_LVDS_FMT, val); |
438 | regmap_write(map: ctx->regmap, REG_LVDS_VCOM, val: 0x05); |
439 | regmap_write(map: ctx->regmap, REG_LVDS_LANE, |
440 | val: (ctx->lvds_dual_link_even_odd_swap ? |
441 | REG_LVDS_LANE_EVEN_ODD_SWAP : 0) | |
442 | REG_LVDS_LANE_CHA_LVDS_TERM | |
443 | REG_LVDS_LANE_CHB_LVDS_TERM); |
444 | regmap_write(map: ctx->regmap, REG_LVDS_CM, val: 0x00); |
445 | |
446 | le16val = cpu_to_le16(mode->hdisplay); |
447 | regmap_bulk_write(map: ctx->regmap, REG_VID_CHA_ACTIVE_LINE_LENGTH_LOW, |
448 | val: &le16val, val_count: 2); |
449 | le16val = cpu_to_le16(mode->vdisplay); |
450 | regmap_bulk_write(map: ctx->regmap, REG_VID_CHA_VERTICAL_DISPLAY_SIZE_LOW, |
451 | val: &le16val, val_count: 2); |
452 | /* 32 + 1 pixel clock to ensure proper operation */ |
453 | le16val = cpu_to_le16(32 + 1); |
454 | regmap_bulk_write(map: ctx->regmap, REG_VID_CHA_SYNC_DELAY_LOW, val: &le16val, val_count: 2); |
455 | le16val = cpu_to_le16(mode->hsync_end - mode->hsync_start); |
456 | regmap_bulk_write(map: ctx->regmap, REG_VID_CHA_HSYNC_PULSE_WIDTH_LOW, |
457 | val: &le16val, val_count: 2); |
458 | le16val = cpu_to_le16(mode->vsync_end - mode->vsync_start); |
459 | regmap_bulk_write(map: ctx->regmap, REG_VID_CHA_VSYNC_PULSE_WIDTH_LOW, |
460 | val: &le16val, val_count: 2); |
461 | regmap_write(map: ctx->regmap, REG_VID_CHA_HORIZONTAL_BACK_PORCH, |
462 | val: mode->htotal - mode->hsync_end); |
463 | regmap_write(map: ctx->regmap, REG_VID_CHA_VERTICAL_BACK_PORCH, |
464 | val: mode->vtotal - mode->vsync_end); |
465 | regmap_write(map: ctx->regmap, REG_VID_CHA_HORIZONTAL_FRONT_PORCH, |
466 | val: mode->hsync_start - mode->hdisplay); |
467 | regmap_write(map: ctx->regmap, REG_VID_CHA_VERTICAL_FRONT_PORCH, |
468 | val: mode->vsync_start - mode->vdisplay); |
469 | regmap_write(map: ctx->regmap, REG_VID_CHA_TEST_PATTERN, val: 0x00); |
470 | |
471 | /* Enable PLL */ |
472 | regmap_write(map: ctx->regmap, REG_RC_PLL_EN, REG_RC_PLL_EN_PLL_EN); |
473 | usleep_range(min: 3000, max: 4000); |
474 | ret = regmap_read_poll_timeout(ctx->regmap, REG_RC_LVDS_PLL, pval, |
475 | pval & REG_RC_LVDS_PLL_PLL_EN_STAT, |
476 | 1000, 100000); |
477 | if (ret) { |
478 | dev_err(ctx->dev, "failed to lock PLL, ret=%i\n" , ret); |
479 | /* On failure, disable PLL again and exit. */ |
480 | regmap_write(map: ctx->regmap, REG_RC_PLL_EN, val: 0x00); |
481 | regulator_disable(regulator: ctx->vcc); |
482 | return; |
483 | } |
484 | |
485 | /* Trigger reset after CSR register update. */ |
486 | regmap_write(map: ctx->regmap, REG_RC_RESET, REG_RC_RESET_SOFT_RESET); |
487 | |
488 | /* Wait for 10ms after soft reset as specified in datasheet */ |
489 | usleep_range(min: 10000, max: 12000); |
490 | } |
491 | |
492 | static void sn65dsi83_atomic_enable(struct drm_bridge *bridge, |
493 | struct drm_bridge_state *old_bridge_state) |
494 | { |
495 | struct sn65dsi83 *ctx = bridge_to_sn65dsi83(bridge); |
496 | unsigned int pval; |
497 | |
498 | /* Clear all errors that got asserted during initialization. */ |
499 | regmap_read(map: ctx->regmap, REG_IRQ_STAT, val: &pval); |
500 | regmap_write(map: ctx->regmap, REG_IRQ_STAT, val: pval); |
501 | |
502 | /* Wait for 1ms and check for errors in status register */ |
503 | usleep_range(min: 1000, max: 1100); |
504 | regmap_read(map: ctx->regmap, REG_IRQ_STAT, val: &pval); |
505 | if (pval) |
506 | dev_err(ctx->dev, "Unexpected link status 0x%02x\n" , pval); |
507 | } |
508 | |
509 | static void sn65dsi83_atomic_disable(struct drm_bridge *bridge, |
510 | struct drm_bridge_state *old_bridge_state) |
511 | { |
512 | struct sn65dsi83 *ctx = bridge_to_sn65dsi83(bridge); |
513 | int ret; |
514 | |
515 | /* Put the chip in reset, pull EN line low, and assure 10ms reset low timing. */ |
516 | gpiod_set_value_cansleep(desc: ctx->enable_gpio, value: 0); |
517 | usleep_range(min: 10000, max: 11000); |
518 | |
519 | ret = regulator_disable(regulator: ctx->vcc); |
520 | if (ret) |
521 | dev_err(ctx->dev, "Failed to disable vcc: %d\n" , ret); |
522 | |
523 | regcache_mark_dirty(map: ctx->regmap); |
524 | } |
525 | |
526 | static enum drm_mode_status |
527 | sn65dsi83_mode_valid(struct drm_bridge *bridge, |
528 | const struct drm_display_info *info, |
529 | const struct drm_display_mode *mode) |
530 | { |
531 | /* LVDS output clock range 25..154 MHz */ |
532 | if (mode->clock < 25000) |
533 | return MODE_CLOCK_LOW; |
534 | if (mode->clock > 154000) |
535 | return MODE_CLOCK_HIGH; |
536 | |
537 | return MODE_OK; |
538 | } |
539 | |
540 | #define MAX_INPUT_SEL_FORMATS 1 |
541 | |
542 | static u32 * |
543 | sn65dsi83_atomic_get_input_bus_fmts(struct drm_bridge *bridge, |
544 | struct drm_bridge_state *bridge_state, |
545 | struct drm_crtc_state *crtc_state, |
546 | struct drm_connector_state *conn_state, |
547 | u32 output_fmt, |
548 | unsigned int *num_input_fmts) |
549 | { |
550 | u32 *input_fmts; |
551 | |
552 | *num_input_fmts = 0; |
553 | |
554 | input_fmts = kcalloc(MAX_INPUT_SEL_FORMATS, size: sizeof(*input_fmts), |
555 | GFP_KERNEL); |
556 | if (!input_fmts) |
557 | return NULL; |
558 | |
559 | /* This is the DSI-end bus format */ |
560 | input_fmts[0] = MEDIA_BUS_FMT_RGB888_1X24; |
561 | *num_input_fmts = 1; |
562 | |
563 | return input_fmts; |
564 | } |
565 | |
566 | static const struct drm_bridge_funcs sn65dsi83_funcs = { |
567 | .attach = sn65dsi83_attach, |
568 | .detach = sn65dsi83_detach, |
569 | .atomic_enable = sn65dsi83_atomic_enable, |
570 | .atomic_pre_enable = sn65dsi83_atomic_pre_enable, |
571 | .atomic_disable = sn65dsi83_atomic_disable, |
572 | .mode_valid = sn65dsi83_mode_valid, |
573 | |
574 | .atomic_duplicate_state = drm_atomic_helper_bridge_duplicate_state, |
575 | .atomic_destroy_state = drm_atomic_helper_bridge_destroy_state, |
576 | .atomic_reset = drm_atomic_helper_bridge_reset, |
577 | .atomic_get_input_bus_fmts = sn65dsi83_atomic_get_input_bus_fmts, |
578 | }; |
579 | |
580 | static int sn65dsi83_parse_dt(struct sn65dsi83 *ctx, enum sn65dsi83_model model) |
581 | { |
582 | struct drm_bridge *panel_bridge; |
583 | struct device *dev = ctx->dev; |
584 | |
585 | ctx->lvds_dual_link = false; |
586 | ctx->lvds_dual_link_even_odd_swap = false; |
587 | if (model != MODEL_SN65DSI83) { |
588 | struct device_node *port2, *port3; |
589 | int dual_link; |
590 | |
591 | port2 = of_graph_get_port_by_id(node: dev->of_node, id: 2); |
592 | port3 = of_graph_get_port_by_id(node: dev->of_node, id: 3); |
593 | dual_link = drm_of_lvds_get_dual_link_pixel_order(port1: port2, port2: port3); |
594 | of_node_put(node: port2); |
595 | of_node_put(node: port3); |
596 | |
597 | if (dual_link == DRM_LVDS_DUAL_LINK_ODD_EVEN_PIXELS) { |
598 | ctx->lvds_dual_link = true; |
599 | /* Odd pixels to LVDS Channel A, even pixels to B */ |
600 | ctx->lvds_dual_link_even_odd_swap = false; |
601 | } else if (dual_link == DRM_LVDS_DUAL_LINK_EVEN_ODD_PIXELS) { |
602 | ctx->lvds_dual_link = true; |
603 | /* Even pixels to LVDS Channel A, odd pixels to B */ |
604 | ctx->lvds_dual_link_even_odd_swap = true; |
605 | } |
606 | } |
607 | |
608 | panel_bridge = devm_drm_of_get_bridge(dev, node: dev->of_node, port: 2, endpoint: 0); |
609 | if (IS_ERR(ptr: panel_bridge)) |
610 | return PTR_ERR(ptr: panel_bridge); |
611 | |
612 | ctx->panel_bridge = panel_bridge; |
613 | |
614 | ctx->vcc = devm_regulator_get(dev, id: "vcc" ); |
615 | if (IS_ERR(ptr: ctx->vcc)) |
616 | return dev_err_probe(dev, err: PTR_ERR(ptr: ctx->vcc), |
617 | fmt: "Failed to get supply 'vcc'\n" ); |
618 | |
619 | return 0; |
620 | } |
621 | |
622 | static int sn65dsi83_host_attach(struct sn65dsi83 *ctx) |
623 | { |
624 | struct device *dev = ctx->dev; |
625 | struct device_node *host_node; |
626 | struct device_node *endpoint; |
627 | struct mipi_dsi_device *dsi; |
628 | struct mipi_dsi_host *host; |
629 | const struct mipi_dsi_device_info info = { |
630 | .type = "sn65dsi83" , |
631 | .channel = 0, |
632 | .node = NULL, |
633 | }; |
634 | int dsi_lanes, ret; |
635 | |
636 | endpoint = of_graph_get_endpoint_by_regs(parent: dev->of_node, port_reg: 0, reg: -1); |
637 | dsi_lanes = drm_of_get_data_lanes_count(endpoint, min: 1, max: 4); |
638 | host_node = of_graph_get_remote_port_parent(node: endpoint); |
639 | host = of_find_mipi_dsi_host_by_node(node: host_node); |
640 | of_node_put(node: host_node); |
641 | of_node_put(node: endpoint); |
642 | |
643 | if (!host) |
644 | return -EPROBE_DEFER; |
645 | |
646 | if (dsi_lanes < 0) |
647 | return dsi_lanes; |
648 | |
649 | dsi = devm_mipi_dsi_device_register_full(dev, host, info: &info); |
650 | if (IS_ERR(ptr: dsi)) |
651 | return dev_err_probe(dev, err: PTR_ERR(ptr: dsi), |
652 | fmt: "failed to create dsi device\n" ); |
653 | |
654 | ctx->dsi = dsi; |
655 | |
656 | dsi->lanes = dsi_lanes; |
657 | dsi->format = MIPI_DSI_FMT_RGB888; |
658 | dsi->mode_flags = MIPI_DSI_MODE_VIDEO | MIPI_DSI_MODE_VIDEO_BURST | |
659 | MIPI_DSI_MODE_VIDEO_NO_HFP | MIPI_DSI_MODE_VIDEO_NO_HBP | |
660 | MIPI_DSI_MODE_VIDEO_NO_HSA | MIPI_DSI_MODE_NO_EOT_PACKET; |
661 | |
662 | ret = devm_mipi_dsi_attach(dev, dsi); |
663 | if (ret < 0) { |
664 | dev_err(dev, "failed to attach dsi to host: %d\n" , ret); |
665 | return ret; |
666 | } |
667 | |
668 | return 0; |
669 | } |
670 | |
671 | static int sn65dsi83_probe(struct i2c_client *client) |
672 | { |
673 | const struct i2c_device_id *id = i2c_client_get_device_id(client); |
674 | struct device *dev = &client->dev; |
675 | enum sn65dsi83_model model; |
676 | struct sn65dsi83 *ctx; |
677 | int ret; |
678 | |
679 | ctx = devm_kzalloc(dev, size: sizeof(*ctx), GFP_KERNEL); |
680 | if (!ctx) |
681 | return -ENOMEM; |
682 | |
683 | ctx->dev = dev; |
684 | |
685 | if (dev->of_node) { |
686 | model = (enum sn65dsi83_model)(uintptr_t) |
687 | of_device_get_match_data(dev); |
688 | } else { |
689 | model = id->driver_data; |
690 | } |
691 | |
692 | /* Put the chip in reset, pull EN line low, and assure 10ms reset low timing. */ |
693 | ctx->enable_gpio = devm_gpiod_get_optional(dev: ctx->dev, con_id: "enable" , |
694 | flags: GPIOD_OUT_LOW); |
695 | if (IS_ERR(ptr: ctx->enable_gpio)) |
696 | return dev_err_probe(dev, err: PTR_ERR(ptr: ctx->enable_gpio), fmt: "failed to get enable GPIO\n" ); |
697 | |
698 | usleep_range(min: 10000, max: 11000); |
699 | |
700 | ret = sn65dsi83_parse_dt(ctx, model); |
701 | if (ret) |
702 | return ret; |
703 | |
704 | ctx->regmap = devm_regmap_init_i2c(client, &sn65dsi83_regmap_config); |
705 | if (IS_ERR(ptr: ctx->regmap)) |
706 | return dev_err_probe(dev, err: PTR_ERR(ptr: ctx->regmap), fmt: "failed to get regmap\n" ); |
707 | |
708 | dev_set_drvdata(dev, data: ctx); |
709 | i2c_set_clientdata(client, data: ctx); |
710 | |
711 | ctx->bridge.funcs = &sn65dsi83_funcs; |
712 | ctx->bridge.of_node = dev->of_node; |
713 | ctx->bridge.pre_enable_prev_first = true; |
714 | drm_bridge_add(bridge: &ctx->bridge); |
715 | |
716 | ret = sn65dsi83_host_attach(ctx); |
717 | if (ret) { |
718 | dev_err_probe(dev, err: ret, fmt: "failed to attach DSI host\n" ); |
719 | goto err_remove_bridge; |
720 | } |
721 | |
722 | return 0; |
723 | |
724 | err_remove_bridge: |
725 | drm_bridge_remove(bridge: &ctx->bridge); |
726 | return ret; |
727 | } |
728 | |
729 | static void sn65dsi83_remove(struct i2c_client *client) |
730 | { |
731 | struct sn65dsi83 *ctx = i2c_get_clientdata(client); |
732 | |
733 | drm_bridge_remove(bridge: &ctx->bridge); |
734 | } |
735 | |
736 | static struct i2c_device_id sn65dsi83_id[] = { |
737 | { "ti,sn65dsi83" , MODEL_SN65DSI83 }, |
738 | { "ti,sn65dsi84" , MODEL_SN65DSI84 }, |
739 | {}, |
740 | }; |
741 | MODULE_DEVICE_TABLE(i2c, sn65dsi83_id); |
742 | |
743 | static const struct of_device_id sn65dsi83_match_table[] = { |
744 | { .compatible = "ti,sn65dsi83" , .data = (void *)MODEL_SN65DSI83 }, |
745 | { .compatible = "ti,sn65dsi84" , .data = (void *)MODEL_SN65DSI84 }, |
746 | {}, |
747 | }; |
748 | MODULE_DEVICE_TABLE(of, sn65dsi83_match_table); |
749 | |
750 | static struct i2c_driver sn65dsi83_driver = { |
751 | .probe = sn65dsi83_probe, |
752 | .remove = sn65dsi83_remove, |
753 | .id_table = sn65dsi83_id, |
754 | .driver = { |
755 | .name = "sn65dsi83" , |
756 | .of_match_table = sn65dsi83_match_table, |
757 | }, |
758 | }; |
759 | module_i2c_driver(sn65dsi83_driver); |
760 | |
761 | MODULE_AUTHOR("Marek Vasut <marex@denx.de>" ); |
762 | MODULE_DESCRIPTION("TI SN65DSI83 DSI to LVDS bridge driver" ); |
763 | MODULE_LICENSE("GPL v2" ); |
764 | |