xref: /linux/drivers/gpu/drm/renesas/rz-du/rzg2l_mipi_dsi.c (revision e2944dc6587f39c3eefb15ee607e700314230a0b)
1 // SPDX-License-Identifier: GPL-2.0
2 /*
3  * RZ/G2L MIPI DSI Encoder Driver
4  *
5  * Copyright (C) 2022 Renesas Electronics Corporation
6  */
7 
8 #include <linux/bitfield.h>
9 #include <linux/clk.h>
10 #include <linux/delay.h>
11 #include <linux/dma-mapping.h>
12 #include <linux/io.h>
13 #include <linux/iopoll.h>
14 #include <linux/math.h>
15 #include <linux/module.h>
16 #include <linux/of.h>
17 #include <linux/of_graph.h>
18 #include <linux/platform_device.h>
19 #include <linux/pm_runtime.h>
20 #include <linux/reset.h>
21 #include <linux/slab.h>
22 #include <linux/units.h>
23 
24 #include <drm/drm_atomic.h>
25 #include <drm/drm_atomic_helper.h>
26 #include <drm/drm_bridge.h>
27 #include <drm/drm_mipi_dsi.h>
28 #include <drm/drm_of.h>
29 #include <drm/drm_panel.h>
30 #include <drm/drm_probe_helper.h>
31 #include <video/mipi_display.h>
32 
33 #include "rzg2l_mipi_dsi_regs.h"
34 
35 #define RZG2L_DCS_BUF_SIZE	128 /* Maximum DCS buffer size in external memory. */
36 
37 #define RZ_MIPI_DSI_FEATURE_16BPP	BIT(0)
38 
39 struct rzg2l_mipi_dsi;
40 
41 struct rzg2l_mipi_dsi_hw_info {
42 	int (*dphy_init)(struct rzg2l_mipi_dsi *dsi, u64 hsfreq_millihz);
43 	void (*dphy_startup_late_init)(struct rzg2l_mipi_dsi *dsi);
44 	void (*dphy_exit)(struct rzg2l_mipi_dsi *dsi);
45 	int (*dphy_conf_clks)(struct rzg2l_mipi_dsi *dsi, unsigned long mode_freq,
46 			      u64 *hsfreq_millihz);
47 	unsigned int (*dphy_mode_clk_check)(struct rzg2l_mipi_dsi *dsi,
48 					    unsigned long mode_freq);
49 	u32 phy_reg_offset;
50 	u32 link_reg_offset;
51 	unsigned long min_dclk;
52 	unsigned long max_dclk;
53 	u8 features;
54 };
55 
56 struct rzg2l_mipi_dsi {
57 	struct device *dev;
58 	void __iomem *mmio;
59 
60 	const struct rzg2l_mipi_dsi_hw_info *info;
61 
62 	struct reset_control *rstc;
63 	struct reset_control *arstc;
64 	struct reset_control *prstc;
65 
66 	struct mipi_dsi_host host;
67 	struct drm_bridge bridge;
68 	struct drm_bridge *next_bridge;
69 
70 	struct clk *vclk;
71 
72 	enum mipi_dsi_pixel_format format;
73 	unsigned int num_data_lanes;
74 	unsigned int lanes;
75 	unsigned long mode_flags;
76 
77 	/* DCS buffer pointers when using external memory. */
78 	dma_addr_t dcs_buf_phys;
79 	u8 *dcs_buf_virt;
80 };
81 
82 static inline struct rzg2l_mipi_dsi *
bridge_to_rzg2l_mipi_dsi(struct drm_bridge * bridge)83 bridge_to_rzg2l_mipi_dsi(struct drm_bridge *bridge)
84 {
85 	return container_of(bridge, struct rzg2l_mipi_dsi, bridge);
86 }
87 
88 static inline struct rzg2l_mipi_dsi *
host_to_rzg2l_mipi_dsi(struct mipi_dsi_host * host)89 host_to_rzg2l_mipi_dsi(struct mipi_dsi_host *host)
90 {
91 	return container_of(host, struct rzg2l_mipi_dsi, host);
92 }
93 
94 struct rzg2l_mipi_dsi_timings {
95 	unsigned long hsfreq_max;
96 	u32 t_init;
97 	u32 tclk_prepare;
98 	u32 ths_prepare;
99 	u32 tclk_zero;
100 	u32 tclk_pre;
101 	u32 tclk_post;
102 	u32 tclk_trail;
103 	u32 ths_zero;
104 	u32 ths_trail;
105 	u32 ths_exit;
106 	u32 tlpx;
107 };
108 
109 static const struct rzg2l_mipi_dsi_timings rzg2l_mipi_dsi_global_timings[] = {
110 	{
111 		.hsfreq_max = 80000000,
112 		.t_init = 79801,
113 		.tclk_prepare = 8,
114 		.ths_prepare = 13,
115 		.tclk_zero = 33,
116 		.tclk_pre = 24,
117 		.tclk_post = 94,
118 		.tclk_trail = 10,
119 		.ths_zero = 23,
120 		.ths_trail = 17,
121 		.ths_exit = 13,
122 		.tlpx = 6,
123 	},
124 	{
125 		.hsfreq_max = 125000000,
126 		.t_init = 79801,
127 		.tclk_prepare = 8,
128 		.ths_prepare = 12,
129 		.tclk_zero = 33,
130 		.tclk_pre = 15,
131 		.tclk_post = 94,
132 		.tclk_trail = 10,
133 		.ths_zero = 23,
134 		.ths_trail = 17,
135 		.ths_exit = 13,
136 		.tlpx = 6,
137 	},
138 	{
139 		.hsfreq_max = 250000000,
140 		.t_init = 79801,
141 		.tclk_prepare = 8,
142 		.ths_prepare = 12,
143 		.tclk_zero = 33,
144 		.tclk_pre = 13,
145 		.tclk_post = 94,
146 		.tclk_trail = 10,
147 		.ths_zero = 23,
148 		.ths_trail = 16,
149 		.ths_exit = 13,
150 		.tlpx = 6,
151 	},
152 	{
153 		.hsfreq_max = 360000000,
154 		.t_init = 79801,
155 		.tclk_prepare = 8,
156 		.ths_prepare = 10,
157 		.tclk_zero = 33,
158 		.tclk_pre = 4,
159 		.tclk_post = 35,
160 		.tclk_trail = 7,
161 		.ths_zero = 16,
162 		.ths_trail = 9,
163 		.ths_exit = 13,
164 		.tlpx = 6,
165 	},
166 	{
167 		.hsfreq_max = 720000000,
168 		.t_init = 79801,
169 		.tclk_prepare = 8,
170 		.ths_prepare = 9,
171 		.tclk_zero = 33,
172 		.tclk_pre = 4,
173 		.tclk_post = 35,
174 		.tclk_trail = 7,
175 		.ths_zero = 16,
176 		.ths_trail = 9,
177 		.ths_exit = 13,
178 		.tlpx = 6,
179 	},
180 	{
181 		.hsfreq_max = 1500000000,
182 		.t_init = 79801,
183 		.tclk_prepare = 8,
184 		.ths_prepare = 9,
185 		.tclk_zero = 33,
186 		.tclk_pre = 4,
187 		.tclk_post = 35,
188 		.tclk_trail = 7,
189 		.ths_zero = 16,
190 		.ths_trail = 9,
191 		.ths_exit = 13,
192 		.tlpx = 6,
193 	},
194 };
195 
rzg2l_mipi_dsi_phy_write(struct rzg2l_mipi_dsi * dsi,u32 reg,u32 data)196 static void rzg2l_mipi_dsi_phy_write(struct rzg2l_mipi_dsi *dsi, u32 reg, u32 data)
197 {
198 	iowrite32(data, dsi->mmio + dsi->info->phy_reg_offset + reg);
199 }
200 
rzg2l_mipi_dsi_link_write(struct rzg2l_mipi_dsi * dsi,u32 reg,u32 data)201 static void rzg2l_mipi_dsi_link_write(struct rzg2l_mipi_dsi *dsi, u32 reg, u32 data)
202 {
203 	iowrite32(data, dsi->mmio + dsi->info->link_reg_offset + reg);
204 }
205 
rzg2l_mipi_dsi_phy_read(struct rzg2l_mipi_dsi * dsi,u32 reg)206 static u32 rzg2l_mipi_dsi_phy_read(struct rzg2l_mipi_dsi *dsi, u32 reg)
207 {
208 	return ioread32(dsi->mmio + dsi->info->phy_reg_offset + reg);
209 }
210 
rzg2l_mipi_dsi_link_read(struct rzg2l_mipi_dsi * dsi,u32 reg)211 static u32 rzg2l_mipi_dsi_link_read(struct rzg2l_mipi_dsi *dsi, u32 reg)
212 {
213 	return ioread32(dsi->mmio + dsi->info->link_reg_offset + reg);
214 }
215 
216 /* -----------------------------------------------------------------------------
217  * Hardware Setup
218  */
219 
rzg2l_mipi_dsi_dphy_init(struct rzg2l_mipi_dsi * dsi,u64 hsfreq_millihz)220 static int rzg2l_mipi_dsi_dphy_init(struct rzg2l_mipi_dsi *dsi,
221 				    u64 hsfreq_millihz)
222 {
223 	unsigned long hsfreq = DIV_ROUND_CLOSEST_ULL(hsfreq_millihz, MILLI);
224 	const struct rzg2l_mipi_dsi_timings *dphy_timings;
225 	unsigned int i;
226 	u32 dphyctrl0;
227 	u32 dphytim0;
228 	u32 dphytim1;
229 	u32 dphytim2;
230 	u32 dphytim3;
231 	int ret;
232 
233 	/* All DSI global operation timings are set with recommended setting */
234 	for (i = 0; i < ARRAY_SIZE(rzg2l_mipi_dsi_global_timings); ++i) {
235 		dphy_timings = &rzg2l_mipi_dsi_global_timings[i];
236 		if (hsfreq <= dphy_timings->hsfreq_max)
237 			break;
238 	}
239 
240 	/* Initializing DPHY before accessing LINK */
241 	dphyctrl0 = DSIDPHYCTRL0_CAL_EN_HSRX_OFS | DSIDPHYCTRL0_CMN_MASTER_EN |
242 		    DSIDPHYCTRL0_RE_VDD_DETVCCQLV18 | DSIDPHYCTRL0_EN_BGR;
243 
244 	rzg2l_mipi_dsi_phy_write(dsi, DSIDPHYCTRL0, dphyctrl0);
245 	usleep_range(20, 30);
246 
247 	dphyctrl0 |= DSIDPHYCTRL0_EN_LDO1200;
248 	rzg2l_mipi_dsi_phy_write(dsi, DSIDPHYCTRL0, dphyctrl0);
249 	usleep_range(10, 20);
250 
251 	dphytim0 = DSIDPHYTIM0_TCLK_MISS(0) |
252 		   DSIDPHYTIM0_T_INIT(dphy_timings->t_init);
253 	dphytim1 = DSIDPHYTIM1_THS_PREPARE(dphy_timings->ths_prepare) |
254 		   DSIDPHYTIM1_TCLK_PREPARE(dphy_timings->tclk_prepare) |
255 		   DSIDPHYTIM1_THS_SETTLE(0) |
256 		   DSIDPHYTIM1_TCLK_SETTLE(0);
257 	dphytim2 = DSIDPHYTIM2_TCLK_TRAIL(dphy_timings->tclk_trail) |
258 		   DSIDPHYTIM2_TCLK_POST(dphy_timings->tclk_post) |
259 		   DSIDPHYTIM2_TCLK_PRE(dphy_timings->tclk_pre) |
260 		   DSIDPHYTIM2_TCLK_ZERO(dphy_timings->tclk_zero);
261 	dphytim3 = DSIDPHYTIM3_TLPX(dphy_timings->tlpx) |
262 		   DSIDPHYTIM3_THS_EXIT(dphy_timings->ths_exit) |
263 		   DSIDPHYTIM3_THS_TRAIL(dphy_timings->ths_trail) |
264 		   DSIDPHYTIM3_THS_ZERO(dphy_timings->ths_zero);
265 
266 	rzg2l_mipi_dsi_phy_write(dsi, DSIDPHYTIM0, dphytim0);
267 	rzg2l_mipi_dsi_phy_write(dsi, DSIDPHYTIM1, dphytim1);
268 	rzg2l_mipi_dsi_phy_write(dsi, DSIDPHYTIM2, dphytim2);
269 	rzg2l_mipi_dsi_phy_write(dsi, DSIDPHYTIM3, dphytim3);
270 
271 	ret = reset_control_deassert(dsi->rstc);
272 	if (ret < 0)
273 		return ret;
274 
275 	udelay(1);
276 
277 	return 0;
278 }
279 
rzg2l_mipi_dsi_dphy_exit(struct rzg2l_mipi_dsi * dsi)280 static void rzg2l_mipi_dsi_dphy_exit(struct rzg2l_mipi_dsi *dsi)
281 {
282 	u32 dphyctrl0;
283 
284 	dphyctrl0 = rzg2l_mipi_dsi_phy_read(dsi, DSIDPHYCTRL0);
285 
286 	dphyctrl0 &= ~(DSIDPHYCTRL0_EN_LDO1200 | DSIDPHYCTRL0_EN_BGR);
287 	rzg2l_mipi_dsi_phy_write(dsi, DSIDPHYCTRL0, dphyctrl0);
288 
289 	reset_control_assert(dsi->rstc);
290 }
291 
rzg2l_dphy_conf_clks(struct rzg2l_mipi_dsi * dsi,unsigned long mode_freq,u64 * hsfreq_millihz)292 static int rzg2l_dphy_conf_clks(struct rzg2l_mipi_dsi *dsi, unsigned long mode_freq,
293 				u64 *hsfreq_millihz)
294 {
295 	unsigned long vclk_rate;
296 	unsigned int bpp;
297 
298 	clk_set_rate(dsi->vclk, mode_freq * KILO);
299 	vclk_rate = clk_get_rate(dsi->vclk);
300 	if (vclk_rate != mode_freq * KILO)
301 		dev_dbg(dsi->dev, "Requested vclk rate %lu, actual %lu mismatch\n",
302 			mode_freq * KILO, vclk_rate);
303 	/*
304 	 * Relationship between hsclk and vclk must follow
305 	 * vclk * bpp = hsclk * 8 * lanes
306 	 * where vclk: video clock (Hz)
307 	 *       bpp: video pixel bit depth
308 	 *       hsclk: DSI HS Byte clock frequency (Hz)
309 	 *       lanes: number of data lanes
310 	 *
311 	 * hsclk(bit) = hsclk(byte) * 8 = hsfreq
312 	 */
313 	bpp = mipi_dsi_pixel_format_to_bpp(dsi->format);
314 	*hsfreq_millihz = DIV_ROUND_CLOSEST_ULL(mul_u32_u32(vclk_rate, bpp * MILLI),
315 						dsi->lanes);
316 
317 	return 0;
318 }
319 
rzg2l_mipi_dsi_startup(struct rzg2l_mipi_dsi * dsi,const struct drm_display_mode * mode)320 static int rzg2l_mipi_dsi_startup(struct rzg2l_mipi_dsi *dsi,
321 				  const struct drm_display_mode *mode)
322 {
323 	unsigned long hsfreq;
324 	u64 hsfreq_millihz;
325 	u32 txsetr;
326 	u32 clstptsetr;
327 	u32 lptrnstsetr;
328 	u32 clkkpt;
329 	u32 clkbfht;
330 	u32 clkstpt;
331 	u32 golpbkt;
332 	u32 dsisetr;
333 	int ret;
334 
335 	ret = pm_runtime_resume_and_get(dsi->dev);
336 	if (ret < 0)
337 		return ret;
338 
339 	ret = dsi->info->dphy_conf_clks(dsi, mode->clock, &hsfreq_millihz);
340 	if (ret < 0)
341 		goto err_phy;
342 
343 	ret = dsi->info->dphy_init(dsi, hsfreq_millihz);
344 	if (ret < 0)
345 		goto err_phy;
346 
347 	/* Enable Data lanes and Clock lanes */
348 	txsetr = TXSETR_DLEN | TXSETR_NUMLANEUSE(dsi->lanes - 1) | TXSETR_CLEN;
349 	rzg2l_mipi_dsi_link_write(dsi, TXSETR, txsetr);
350 
351 	if (dsi->info->dphy_startup_late_init)
352 		dsi->info->dphy_startup_late_init(dsi);
353 
354 	hsfreq = DIV_ROUND_CLOSEST_ULL(hsfreq_millihz, MILLI);
355 	/*
356 	 * Global timings characteristic depends on high speed Clock Frequency
357 	 * Currently MIPI DSI-IF just supports maximum FHD@60 with:
358 	 * - videoclock = 148.5 (MHz)
359 	 * - bpp: maximum 24bpp
360 	 * - data lanes: maximum 4 lanes
361 	 * Therefore maximum hsclk will be 891 Mbps.
362 	 */
363 	if (hsfreq > 445500000) {
364 		clkkpt = 12;
365 		clkbfht = 15;
366 		clkstpt = 48;
367 		golpbkt = 75;
368 	} else if (hsfreq > 250000000) {
369 		clkkpt = 7;
370 		clkbfht = 8;
371 		clkstpt = 27;
372 		golpbkt = 40;
373 	} else {
374 		clkkpt = 8;
375 		clkbfht = 6;
376 		clkstpt = 24;
377 		golpbkt = 29;
378 	}
379 
380 	clstptsetr = CLSTPTSETR_CLKKPT(clkkpt) | CLSTPTSETR_CLKBFHT(clkbfht) |
381 		     CLSTPTSETR_CLKSTPT(clkstpt);
382 	rzg2l_mipi_dsi_link_write(dsi, CLSTPTSETR, clstptsetr);
383 
384 	lptrnstsetr = LPTRNSTSETR_GOLPBKT(golpbkt);
385 	rzg2l_mipi_dsi_link_write(dsi, LPTRNSTSETR, lptrnstsetr);
386 
387 	/*
388 	 * Increase MRPSZ as the default value of 1 will result in long read
389 	 * commands payload not being saved to memory.
390 	 */
391 	dsisetr = rzg2l_mipi_dsi_link_read(dsi, DSISETR);
392 	dsisetr &= ~DSISETR_MRPSZ;
393 	dsisetr |= FIELD_PREP(DSISETR_MRPSZ, RZG2L_DCS_BUF_SIZE);
394 	rzg2l_mipi_dsi_link_write(dsi, DSISETR, dsisetr);
395 
396 	return 0;
397 
398 err_phy:
399 	dsi->info->dphy_exit(dsi);
400 	pm_runtime_put(dsi->dev);
401 
402 	return ret;
403 }
404 
rzg2l_mipi_dsi_stop(struct rzg2l_mipi_dsi * dsi)405 static void rzg2l_mipi_dsi_stop(struct rzg2l_mipi_dsi *dsi)
406 {
407 	dsi->info->dphy_exit(dsi);
408 	pm_runtime_put(dsi->dev);
409 }
410 
rzg2l_mipi_dsi_set_display_timing(struct rzg2l_mipi_dsi * dsi,const struct drm_display_mode * mode)411 static void rzg2l_mipi_dsi_set_display_timing(struct rzg2l_mipi_dsi *dsi,
412 					      const struct drm_display_mode *mode)
413 {
414 	u32 vich1ppsetr;
415 	u32 vich1vssetr;
416 	u32 vich1vpsetr;
417 	u32 vich1hssetr;
418 	u32 vich1hpsetr;
419 	int dsi_format;
420 	u32 delay[2];
421 	u8 index;
422 
423 	/* Configuration for Pixel Packet */
424 	dsi_format = mipi_dsi_pixel_format_to_bpp(dsi->format);
425 	switch (dsi_format) {
426 	case 24:
427 		vich1ppsetr = VICH1PPSETR_DT_RGB24;
428 		break;
429 	case 18:
430 		vich1ppsetr = VICH1PPSETR_DT_RGB18;
431 		break;
432 	}
433 
434 	if ((dsi->mode_flags & MIPI_DSI_MODE_VIDEO_SYNC_PULSE) &&
435 	    !(dsi->mode_flags & MIPI_DSI_MODE_VIDEO_BURST))
436 		vich1ppsetr |= VICH1PPSETR_TXESYNC_PULSE;
437 
438 	rzg2l_mipi_dsi_link_write(dsi, VICH1PPSETR, vich1ppsetr);
439 
440 	/* Configuration for Video Parameters */
441 	vich1vssetr = VICH1VSSETR_VACTIVE(mode->vdisplay) |
442 		      VICH1VSSETR_VSA(mode->vsync_end - mode->vsync_start);
443 	vich1vssetr |= (mode->flags & DRM_MODE_FLAG_PVSYNC) ?
444 			VICH1VSSETR_VSPOL_HIGH : VICH1VSSETR_VSPOL_LOW;
445 
446 	vich1vpsetr = VICH1VPSETR_VFP(mode->vsync_start - mode->vdisplay) |
447 		      VICH1VPSETR_VBP(mode->vtotal - mode->vsync_end);
448 
449 	vich1hssetr = VICH1HSSETR_HACTIVE(mode->hdisplay) |
450 		      VICH1HSSETR_HSA(mode->hsync_end - mode->hsync_start);
451 	vich1hssetr |= (mode->flags & DRM_MODE_FLAG_PHSYNC) ?
452 			VICH1HSSETR_HSPOL_HIGH : VICH1HSSETR_HSPOL_LOW;
453 
454 	vich1hpsetr = VICH1HPSETR_HFP(mode->hsync_start - mode->hdisplay) |
455 		      VICH1HPSETR_HBP(mode->htotal - mode->hsync_end);
456 
457 	rzg2l_mipi_dsi_link_write(dsi, VICH1VSSETR, vich1vssetr);
458 	rzg2l_mipi_dsi_link_write(dsi, VICH1VPSETR, vich1vpsetr);
459 	rzg2l_mipi_dsi_link_write(dsi, VICH1HSSETR, vich1hssetr);
460 	rzg2l_mipi_dsi_link_write(dsi, VICH1HPSETR, vich1hpsetr);
461 
462 	/*
463 	 * Configuration for Delay Value
464 	 * Delay value based on 2 ranges of video clock.
465 	 * 74.25MHz is videoclock of HD@60p or FHD@30p
466 	 */
467 	if (mode->clock > 74250) {
468 		delay[0] = 231;
469 		delay[1] = 216;
470 	} else {
471 		delay[0] = 220;
472 		delay[1] = 212;
473 	}
474 
475 	if (dsi->mode_flags & MIPI_DSI_CLOCK_NON_CONTINUOUS)
476 		index = 0;
477 	else
478 		index = 1;
479 
480 	rzg2l_mipi_dsi_link_write(dsi, VICH1SET1R,
481 				  VICH1SET1R_DLY(delay[index]));
482 }
483 
rzg2l_mipi_dsi_start_hs_clock(struct rzg2l_mipi_dsi * dsi)484 static int rzg2l_mipi_dsi_start_hs_clock(struct rzg2l_mipi_dsi *dsi)
485 {
486 	bool is_clk_cont;
487 	u32 hsclksetr;
488 	u32 status;
489 	int ret;
490 
491 	is_clk_cont = !(dsi->mode_flags & MIPI_DSI_CLOCK_NON_CONTINUOUS);
492 
493 	/* Start HS clock */
494 	hsclksetr = HSCLKSETR_HSCLKRUN_HS | (is_clk_cont ?
495 					     HSCLKSETR_HSCLKMODE_CONT :
496 					     HSCLKSETR_HSCLKMODE_NON_CONT);
497 	rzg2l_mipi_dsi_link_write(dsi, HSCLKSETR, hsclksetr);
498 
499 	if (is_clk_cont) {
500 		ret = read_poll_timeout(rzg2l_mipi_dsi_link_read, status,
501 					status & PLSR_CLLP2HS,
502 					2000, 20000, false, dsi, PLSR);
503 		if (ret < 0) {
504 			dev_err(dsi->dev, "failed to start HS clock\n");
505 			return ret;
506 		}
507 	}
508 
509 	dev_dbg(dsi->dev, "Start High Speed Clock with %s clock mode",
510 		is_clk_cont ? "continuous" : "non-continuous");
511 
512 	return 0;
513 }
514 
rzg2l_mipi_dsi_stop_hs_clock(struct rzg2l_mipi_dsi * dsi)515 static int rzg2l_mipi_dsi_stop_hs_clock(struct rzg2l_mipi_dsi *dsi)
516 {
517 	bool is_clk_cont;
518 	u32 status;
519 	int ret;
520 
521 	is_clk_cont = !(dsi->mode_flags & MIPI_DSI_CLOCK_NON_CONTINUOUS);
522 
523 	/* Stop HS clock */
524 	rzg2l_mipi_dsi_link_write(dsi, HSCLKSETR,
525 				  is_clk_cont ? HSCLKSETR_HSCLKMODE_CONT :
526 				  HSCLKSETR_HSCLKMODE_NON_CONT);
527 
528 	if (is_clk_cont) {
529 		ret = read_poll_timeout(rzg2l_mipi_dsi_link_read, status,
530 					status & PLSR_CLHS2LP,
531 					2000, 20000, false, dsi, PLSR);
532 		if (ret < 0) {
533 			dev_err(dsi->dev, "failed to stop HS clock\n");
534 			return ret;
535 		}
536 	}
537 
538 	return 0;
539 }
540 
rzg2l_mipi_dsi_start_video(struct rzg2l_mipi_dsi * dsi)541 static int rzg2l_mipi_dsi_start_video(struct rzg2l_mipi_dsi *dsi)
542 {
543 	u32 vich1set0r;
544 	u32 status;
545 	int ret;
546 
547 	/* Configuration for Blanking sequence and start video input */
548 	vich1set0r = VICH1SET0R_HFPNOLP | VICH1SET0R_HBPNOLP |
549 		     VICH1SET0R_HSANOLP | VICH1SET0R_VSTART;
550 	rzg2l_mipi_dsi_link_write(dsi, VICH1SET0R, vich1set0r);
551 
552 	ret = read_poll_timeout(rzg2l_mipi_dsi_link_read, status,
553 				status & VICH1SR_VIRDY,
554 				2000, 20000, false, dsi, VICH1SR);
555 	if (ret < 0)
556 		dev_err(dsi->dev, "Failed to start video signal input\n");
557 
558 	return ret;
559 }
560 
rzg2l_mipi_dsi_stop_video(struct rzg2l_mipi_dsi * dsi)561 static int rzg2l_mipi_dsi_stop_video(struct rzg2l_mipi_dsi *dsi)
562 {
563 	u32 status;
564 	int ret;
565 
566 	rzg2l_mipi_dsi_link_write(dsi, VICH1SET0R, VICH1SET0R_VSTPAFT);
567 	ret = read_poll_timeout(rzg2l_mipi_dsi_link_read, status,
568 				(status & VICH1SR_STOP) && (!(status & VICH1SR_RUNNING)),
569 				2000, 20000, false, dsi, VICH1SR);
570 	if (ret < 0)
571 		goto err;
572 
573 	ret = read_poll_timeout(rzg2l_mipi_dsi_link_read, status,
574 				!(status & LINKSR_HSBUSY),
575 				2000, 20000, false, dsi, LINKSR);
576 	if (ret < 0)
577 		goto err;
578 
579 	return 0;
580 
581 err:
582 	dev_err(dsi->dev, "Failed to stop video signal input\n");
583 	return ret;
584 }
585 
586 /* -----------------------------------------------------------------------------
587  * Bridge
588  */
589 
rzg2l_mipi_dsi_attach(struct drm_bridge * bridge,struct drm_encoder * encoder,enum drm_bridge_attach_flags flags)590 static int rzg2l_mipi_dsi_attach(struct drm_bridge *bridge,
591 				 struct drm_encoder *encoder,
592 				 enum drm_bridge_attach_flags flags)
593 {
594 	struct rzg2l_mipi_dsi *dsi = bridge_to_rzg2l_mipi_dsi(bridge);
595 
596 	return drm_bridge_attach(encoder, dsi->next_bridge, bridge,
597 				 flags);
598 }
599 
rzg2l_mipi_dsi_atomic_pre_enable(struct drm_bridge * bridge,struct drm_atomic_state * state)600 static void rzg2l_mipi_dsi_atomic_pre_enable(struct drm_bridge *bridge,
601 					     struct drm_atomic_state *state)
602 {
603 	struct rzg2l_mipi_dsi *dsi = bridge_to_rzg2l_mipi_dsi(bridge);
604 	const struct drm_display_mode *mode;
605 	struct drm_connector *connector;
606 	struct drm_crtc *crtc;
607 	int ret;
608 
609 	connector = drm_atomic_get_new_connector_for_encoder(state, bridge->encoder);
610 	crtc = drm_atomic_get_new_connector_state(state, connector)->crtc;
611 	mode = &drm_atomic_get_new_crtc_state(state, crtc)->adjusted_mode;
612 
613 	ret = rzg2l_mipi_dsi_startup(dsi, mode);
614 	if (ret < 0)
615 		return;
616 
617 	rzg2l_mipi_dsi_set_display_timing(dsi, mode);
618 }
619 
rzg2l_mipi_dsi_atomic_enable(struct drm_bridge * bridge,struct drm_atomic_state * state)620 static void rzg2l_mipi_dsi_atomic_enable(struct drm_bridge *bridge,
621 					 struct drm_atomic_state *state)
622 {
623 	struct rzg2l_mipi_dsi *dsi = bridge_to_rzg2l_mipi_dsi(bridge);
624 	int ret;
625 
626 	ret = rzg2l_mipi_dsi_start_hs_clock(dsi);
627 	if (ret < 0)
628 		goto err_stop;
629 
630 	ret = rzg2l_mipi_dsi_start_video(dsi);
631 	if (ret < 0)
632 		goto err_stop_clock;
633 
634 	return;
635 
636 err_stop_clock:
637 	rzg2l_mipi_dsi_stop_hs_clock(dsi);
638 err_stop:
639 	rzg2l_mipi_dsi_stop(dsi);
640 }
641 
rzg2l_mipi_dsi_atomic_disable(struct drm_bridge * bridge,struct drm_atomic_state * state)642 static void rzg2l_mipi_dsi_atomic_disable(struct drm_bridge *bridge,
643 					  struct drm_atomic_state *state)
644 {
645 	struct rzg2l_mipi_dsi *dsi = bridge_to_rzg2l_mipi_dsi(bridge);
646 
647 	rzg2l_mipi_dsi_stop_video(dsi);
648 	rzg2l_mipi_dsi_stop_hs_clock(dsi);
649 	rzg2l_mipi_dsi_stop(dsi);
650 }
651 
652 static enum drm_mode_status
rzg2l_mipi_dsi_bridge_mode_valid(struct drm_bridge * bridge,const struct drm_display_info * info,const struct drm_display_mode * mode)653 rzg2l_mipi_dsi_bridge_mode_valid(struct drm_bridge *bridge,
654 				 const struct drm_display_info *info,
655 				 const struct drm_display_mode *mode)
656 {
657 	struct rzg2l_mipi_dsi *dsi = bridge_to_rzg2l_mipi_dsi(bridge);
658 
659 	if (mode->clock > dsi->info->max_dclk)
660 		return MODE_CLOCK_HIGH;
661 
662 	if (mode->clock < dsi->info->min_dclk)
663 		return MODE_CLOCK_LOW;
664 
665 	if (dsi->info->dphy_mode_clk_check) {
666 		enum drm_mode_status status;
667 
668 		status = dsi->info->dphy_mode_clk_check(dsi, mode->clock);
669 		if (status != MODE_OK)
670 			return status;
671 	}
672 
673 	return MODE_OK;
674 }
675 
676 static const struct drm_bridge_funcs rzg2l_mipi_dsi_bridge_ops = {
677 	.attach = rzg2l_mipi_dsi_attach,
678 	.atomic_duplicate_state = drm_atomic_helper_bridge_duplicate_state,
679 	.atomic_destroy_state = drm_atomic_helper_bridge_destroy_state,
680 	.atomic_reset = drm_atomic_helper_bridge_reset,
681 	.atomic_pre_enable = rzg2l_mipi_dsi_atomic_pre_enable,
682 	.atomic_enable = rzg2l_mipi_dsi_atomic_enable,
683 	.atomic_disable = rzg2l_mipi_dsi_atomic_disable,
684 	.mode_valid = rzg2l_mipi_dsi_bridge_mode_valid,
685 };
686 
687 /* -----------------------------------------------------------------------------
688  * Host setting
689  */
690 
rzg2l_mipi_dsi_host_attach(struct mipi_dsi_host * host,struct mipi_dsi_device * device)691 static int rzg2l_mipi_dsi_host_attach(struct mipi_dsi_host *host,
692 				      struct mipi_dsi_device *device)
693 {
694 	struct rzg2l_mipi_dsi *dsi = host_to_rzg2l_mipi_dsi(host);
695 	int ret;
696 
697 	if (device->lanes > dsi->num_data_lanes) {
698 		dev_err(dsi->dev,
699 			"Number of lines of device (%u) exceeds host (%u)\n",
700 			device->lanes, dsi->num_data_lanes);
701 		return -EINVAL;
702 	}
703 
704 	switch (mipi_dsi_pixel_format_to_bpp(device->format)) {
705 	case 24:
706 		break;
707 	case 18:
708 		break;
709 	case 16:
710 		if (!(dsi->info->features & RZ_MIPI_DSI_FEATURE_16BPP)) {
711 			dev_err(dsi->dev, "Unsupported format 0x%04x\n",
712 				device->format);
713 			return -EINVAL;
714 		}
715 		break;
716 	default:
717 		dev_err(dsi->dev, "Unsupported format 0x%04x\n", device->format);
718 		return -EINVAL;
719 	}
720 
721 	dsi->lanes = device->lanes;
722 	dsi->format = device->format;
723 	dsi->mode_flags = device->mode_flags;
724 
725 	dsi->next_bridge = devm_drm_of_get_bridge(dsi->dev, dsi->dev->of_node,
726 						  1, 0);
727 	if (IS_ERR(dsi->next_bridge)) {
728 		ret = PTR_ERR(dsi->next_bridge);
729 		dev_err(dsi->dev, "failed to get next bridge: %d\n", ret);
730 		return ret;
731 	}
732 
733 	drm_bridge_add(&dsi->bridge);
734 
735 	return 0;
736 }
737 
rzg2l_mipi_dsi_host_detach(struct mipi_dsi_host * host,struct mipi_dsi_device * device)738 static int rzg2l_mipi_dsi_host_detach(struct mipi_dsi_host *host,
739 				      struct mipi_dsi_device *device)
740 {
741 	struct rzg2l_mipi_dsi *dsi = host_to_rzg2l_mipi_dsi(host);
742 
743 	drm_bridge_remove(&dsi->bridge);
744 
745 	return 0;
746 }
747 
rzg2l_mipi_dsi_read_response(struct rzg2l_mipi_dsi * dsi,const struct mipi_dsi_msg * msg)748 static ssize_t rzg2l_mipi_dsi_read_response(struct rzg2l_mipi_dsi *dsi,
749 					    const struct mipi_dsi_msg *msg)
750 {
751 	u8 *msg_rx = msg->rx_buf;
752 	u8 datatype;
753 	u32 result;
754 	u16 size;
755 
756 	result = rzg2l_mipi_dsi_link_read(dsi, RXRSS0R);
757 	if (result & RXRSS0R_RXPKTDFAIL) {
758 		dev_err(dsi->dev, "packet rx data did not save correctly\n");
759 		return -EPROTO;
760 	}
761 
762 	if (result & RXRSS0R_RXFAIL) {
763 		dev_err(dsi->dev, "packet rx failure\n");
764 		return -EPROTO;
765 	}
766 
767 	if (!(result & RXRSS0R_RXSUC))
768 		return -EPROTO;
769 
770 	datatype = FIELD_GET(RXRSS0R_DT, result);
771 
772 	switch (datatype) {
773 	case 0:
774 		dev_dbg(dsi->dev, "ACK\n");
775 		return 0;
776 	case MIPI_DSI_RX_END_OF_TRANSMISSION:
777 		dev_dbg(dsi->dev, "EoTp\n");
778 		return 0;
779 	case MIPI_DSI_RX_ACKNOWLEDGE_AND_ERROR_REPORT:
780 		dev_dbg(dsi->dev, "Acknowledge and error report: $%02x%02x\n",
781 			(u8)FIELD_GET(RXRSS0R_DATA1, result),
782 			(u8)FIELD_GET(RXRSS0R_DATA0, result));
783 		return 0;
784 	case MIPI_DSI_RX_DCS_SHORT_READ_RESPONSE_1BYTE:
785 	case MIPI_DSI_RX_GENERIC_SHORT_READ_RESPONSE_1BYTE:
786 		msg_rx[0] = FIELD_GET(RXRSS0R_DATA0, result);
787 		return 1;
788 	case MIPI_DSI_RX_DCS_SHORT_READ_RESPONSE_2BYTE:
789 	case MIPI_DSI_RX_GENERIC_SHORT_READ_RESPONSE_2BYTE:
790 		msg_rx[0] = FIELD_GET(RXRSS0R_DATA0, result);
791 		msg_rx[1] = FIELD_GET(RXRSS0R_DATA1, result);
792 		return 2;
793 	case MIPI_DSI_RX_GENERIC_LONG_READ_RESPONSE:
794 	case MIPI_DSI_RX_DCS_LONG_READ_RESPONSE:
795 		size = FIELD_GET(RXRSS0R_WC, result);
796 
797 		if (size > msg->rx_len) {
798 			dev_err(dsi->dev, "rx buffer too small");
799 			return -ENOSPC;
800 		}
801 
802 		memcpy(msg_rx, dsi->dcs_buf_virt, size);
803 		return size;
804 	default:
805 		dev_err(dsi->dev, "unhandled response type: %02x\n", datatype);
806 		return -EPROTO;
807 	}
808 }
809 
rzg2l_mipi_dsi_host_transfer(struct mipi_dsi_host * host,const struct mipi_dsi_msg * msg)810 static ssize_t rzg2l_mipi_dsi_host_transfer(struct mipi_dsi_host *host,
811 					    const struct mipi_dsi_msg *msg)
812 {
813 	struct rzg2l_mipi_dsi *dsi = host_to_rzg2l_mipi_dsi(host);
814 	struct mipi_dsi_packet packet;
815 	bool need_bta;
816 	u32 value;
817 	int ret;
818 
819 	ret = mipi_dsi_create_packet(&packet, msg);
820 	if (ret < 0)
821 		return ret;
822 
823 	/* Terminate operation after this descriptor is finished */
824 	value = SQCH0DSC0AR_NXACT_TERM;
825 
826 	if (msg->flags & MIPI_DSI_MSG_REQ_ACK) {
827 		need_bta = true; /* Message with explicitly requested ACK */
828 		value |= FIELD_PREP(SQCH0DSC0AR_BTA, SQCH0DSC0AR_BTA_NON_READ);
829 	} else if (msg->rx_buf && msg->rx_len > 0) {
830 		need_bta = true; /* Read request */
831 		value |= FIELD_PREP(SQCH0DSC0AR_BTA, SQCH0DSC0AR_BTA_READ);
832 	} else {
833 		need_bta = false;
834 		value |= FIELD_PREP(SQCH0DSC0AR_BTA, SQCH0DSC0AR_BTA_NONE);
835 	}
836 
837 	/* Set transmission speed */
838 	if (msg->flags & MIPI_DSI_MSG_USE_LPM)
839 		value |= SQCH0DSC0AR_SPD_LOW;
840 	else
841 		value |= SQCH0DSC0AR_SPD_HIGH;
842 
843 	/* Write TX packet header */
844 	value |= FIELD_PREP(SQCH0DSC0AR_DT, packet.header[0]) |
845 		FIELD_PREP(SQCH0DSC0AR_DATA0, packet.header[1]) |
846 		FIELD_PREP(SQCH0DSC0AR_DATA1, packet.header[2]);
847 
848 	if (mipi_dsi_packet_format_is_long(msg->type)) {
849 		value |= SQCH0DSC0AR_FMT_LONG;
850 
851 		if (packet.payload_length > RZG2L_DCS_BUF_SIZE) {
852 			dev_err(dsi->dev, "Packet Tx payload size (%d) too large",
853 				(unsigned int)packet.payload_length);
854 			return -ENOSPC;
855 		}
856 
857 		/* Copy TX packet payload data to memory space */
858 		memcpy(dsi->dcs_buf_virt, packet.payload, packet.payload_length);
859 	} else {
860 		value |= SQCH0DSC0AR_FMT_SHORT;
861 	}
862 
863 	rzg2l_mipi_dsi_link_write(dsi, SQCH0DSC0AR, value);
864 
865 	/*
866 	 * Write: specify payload data source location, only used for
867 	 *        long packet.
868 	 * Read:  specify payload data storage location of response
869 	 *        packet. Note: a read packet is always a short packet.
870 	 *        If the response packet is a short packet or a long packet
871 	 *        with WC = 0 (no payload), DTSEL is meaningless.
872 	 */
873 	rzg2l_mipi_dsi_link_write(dsi, SQCH0DSC0BR, SQCH0DSC0BR_DTSEL_MEM_SPACE);
874 
875 	/*
876 	 * Set SQCHxSR.AACTFIN bit when descriptor actions are finished.
877 	 * Read: set Rx result save slot number to 0 (ACTCODE).
878 	 */
879 	rzg2l_mipi_dsi_link_write(dsi, SQCH0DSC0CR, SQCH0DSC0CR_FINACT);
880 
881 	/* Set rx/tx payload data address, only relevant for long packet. */
882 	rzg2l_mipi_dsi_link_write(dsi, SQCH0DSC0DR, (u32)dsi->dcs_buf_phys);
883 
884 	/* Start sequence 0 operation */
885 	value = rzg2l_mipi_dsi_link_read(dsi, SQCH0SET0R);
886 	value |= SQCH0SET0R_START;
887 	rzg2l_mipi_dsi_link_write(dsi, SQCH0SET0R, value);
888 
889 	/* Wait for operation to finish */
890 	ret = read_poll_timeout(rzg2l_mipi_dsi_link_read,
891 				value, value & SQCH0SR_ADESFIN,
892 				2000, 20000, false, dsi, SQCH0SR);
893 	if (ret == 0) {
894 		/* Success: clear status bit */
895 		rzg2l_mipi_dsi_link_write(dsi, SQCH0SCR, SQCH0SCR_ADESFIN);
896 
897 		if (need_bta)
898 			ret = rzg2l_mipi_dsi_read_response(dsi, msg);
899 		else
900 			ret = packet.payload_length;
901 	}
902 
903 	return ret;
904 }
905 
906 static const struct mipi_dsi_host_ops rzg2l_mipi_dsi_host_ops = {
907 	.attach = rzg2l_mipi_dsi_host_attach,
908 	.detach = rzg2l_mipi_dsi_host_detach,
909 	.transfer = rzg2l_mipi_dsi_host_transfer,
910 };
911 
912 /* -----------------------------------------------------------------------------
913  * Power Management
914  */
915 
rzg2l_mipi_pm_runtime_suspend(struct device * dev)916 static int __maybe_unused rzg2l_mipi_pm_runtime_suspend(struct device *dev)
917 {
918 	struct rzg2l_mipi_dsi *dsi = dev_get_drvdata(dev);
919 
920 	reset_control_assert(dsi->prstc);
921 	reset_control_assert(dsi->arstc);
922 
923 	return 0;
924 }
925 
rzg2l_mipi_pm_runtime_resume(struct device * dev)926 static int __maybe_unused rzg2l_mipi_pm_runtime_resume(struct device *dev)
927 {
928 	struct rzg2l_mipi_dsi *dsi = dev_get_drvdata(dev);
929 	int ret;
930 
931 	ret = reset_control_deassert(dsi->arstc);
932 	if (ret < 0)
933 		return ret;
934 
935 	ret = reset_control_deassert(dsi->prstc);
936 	if (ret < 0)
937 		reset_control_assert(dsi->arstc);
938 
939 	return ret;
940 }
941 
942 static const struct dev_pm_ops rzg2l_mipi_pm_ops = {
943 	SET_RUNTIME_PM_OPS(rzg2l_mipi_pm_runtime_suspend, rzg2l_mipi_pm_runtime_resume, NULL)
944 };
945 
946 /* -----------------------------------------------------------------------------
947  * Probe & Remove
948  */
949 
rzg2l_mipi_dsi_probe(struct platform_device * pdev)950 static int rzg2l_mipi_dsi_probe(struct platform_device *pdev)
951 {
952 	unsigned int num_data_lanes;
953 	struct rzg2l_mipi_dsi *dsi;
954 	u32 txsetr;
955 	int ret;
956 
957 	dsi = devm_drm_bridge_alloc(&pdev->dev, struct rzg2l_mipi_dsi, bridge,
958 				    &rzg2l_mipi_dsi_bridge_ops);
959 	if (IS_ERR(dsi))
960 		return PTR_ERR(dsi);
961 
962 	platform_set_drvdata(pdev, dsi);
963 	dsi->dev = &pdev->dev;
964 
965 	dsi->info = of_device_get_match_data(&pdev->dev);
966 
967 	ret = drm_of_get_data_lanes_count_ep(dsi->dev->of_node, 1, 0, 1, 4);
968 	if (ret < 0)
969 		return dev_err_probe(dsi->dev, ret,
970 				     "missing or invalid data-lanes property\n");
971 
972 	num_data_lanes = ret;
973 
974 	dsi->mmio = devm_platform_ioremap_resource(pdev, 0);
975 	if (IS_ERR(dsi->mmio))
976 		return PTR_ERR(dsi->mmio);
977 
978 	dsi->vclk = devm_clk_get(dsi->dev, "vclk");
979 	if (IS_ERR(dsi->vclk))
980 		return PTR_ERR(dsi->vclk);
981 
982 	dsi->rstc = devm_reset_control_get_optional_exclusive(dsi->dev, "rst");
983 	if (IS_ERR(dsi->rstc))
984 		return dev_err_probe(dsi->dev, PTR_ERR(dsi->rstc),
985 				     "failed to get rst\n");
986 
987 	dsi->arstc = devm_reset_control_get_exclusive(dsi->dev, "arst");
988 	if (IS_ERR(dsi->arstc))
989 		return dev_err_probe(&pdev->dev, PTR_ERR(dsi->arstc),
990 				     "failed to get arst\n");
991 
992 	dsi->prstc = devm_reset_control_get_exclusive(dsi->dev, "prst");
993 	if (IS_ERR(dsi->prstc))
994 		return dev_err_probe(dsi->dev, PTR_ERR(dsi->prstc),
995 				     "failed to get prst\n");
996 
997 	platform_set_drvdata(pdev, dsi);
998 
999 	pm_runtime_enable(dsi->dev);
1000 
1001 	ret = pm_runtime_resume_and_get(dsi->dev);
1002 	if (ret < 0)
1003 		goto err_pm_disable;
1004 
1005 	/*
1006 	 * TXSETR register can be read only after DPHY init. But during probe
1007 	 * mode->clock and format are not available. So initialize DPHY with
1008 	 * timing parameters for 80Mbps.
1009 	 */
1010 	ret = dsi->info->dphy_init(dsi, 80000000ULL * MILLI);
1011 	if (ret < 0)
1012 		goto err_phy;
1013 
1014 	txsetr = rzg2l_mipi_dsi_link_read(dsi, TXSETR);
1015 	dsi->num_data_lanes = min(((txsetr >> 16) & 3) + 1, num_data_lanes);
1016 	dsi->info->dphy_exit(dsi);
1017 	pm_runtime_put(dsi->dev);
1018 
1019 	/* Initialize the DRM bridge. */
1020 	dsi->bridge.of_node = dsi->dev->of_node;
1021 
1022 	/* Init host device */
1023 	dsi->host.dev = dsi->dev;
1024 	dsi->host.ops = &rzg2l_mipi_dsi_host_ops;
1025 	ret = mipi_dsi_host_register(&dsi->host);
1026 	if (ret < 0)
1027 		goto err_pm_disable;
1028 
1029 	dsi->dcs_buf_virt = dma_alloc_coherent(dsi->host.dev, RZG2L_DCS_BUF_SIZE,
1030 					       &dsi->dcs_buf_phys, GFP_KERNEL);
1031 	if (!dsi->dcs_buf_virt)
1032 		return -ENOMEM;
1033 
1034 	return 0;
1035 
1036 err_phy:
1037 	dsi->info->dphy_exit(dsi);
1038 	pm_runtime_put(dsi->dev);
1039 err_pm_disable:
1040 	pm_runtime_disable(dsi->dev);
1041 	return ret;
1042 }
1043 
rzg2l_mipi_dsi_remove(struct platform_device * pdev)1044 static void rzg2l_mipi_dsi_remove(struct platform_device *pdev)
1045 {
1046 	struct rzg2l_mipi_dsi *dsi = platform_get_drvdata(pdev);
1047 
1048 	dma_free_coherent(dsi->host.dev, RZG2L_DCS_BUF_SIZE, dsi->dcs_buf_virt,
1049 			  dsi->dcs_buf_phys);
1050 	mipi_dsi_host_unregister(&dsi->host);
1051 	pm_runtime_disable(&pdev->dev);
1052 }
1053 
1054 static const struct rzg2l_mipi_dsi_hw_info rzg2l_mipi_dsi_info = {
1055 	.dphy_init = rzg2l_mipi_dsi_dphy_init,
1056 	.dphy_exit = rzg2l_mipi_dsi_dphy_exit,
1057 	.dphy_conf_clks = rzg2l_dphy_conf_clks,
1058 	.link_reg_offset = 0x10000,
1059 	.min_dclk = 5803,
1060 	.max_dclk = 148500,
1061 };
1062 
1063 static const struct of_device_id rzg2l_mipi_dsi_of_table[] = {
1064 	{ .compatible = "renesas,rzg2l-mipi-dsi", .data = &rzg2l_mipi_dsi_info, },
1065 	{ /* sentinel */ }
1066 };
1067 
1068 MODULE_DEVICE_TABLE(of, rzg2l_mipi_dsi_of_table);
1069 
1070 static struct platform_driver rzg2l_mipi_dsi_platform_driver = {
1071 	.probe	= rzg2l_mipi_dsi_probe,
1072 	.remove = rzg2l_mipi_dsi_remove,
1073 	.driver	= {
1074 		.name = "rzg2l-mipi-dsi",
1075 		.pm = &rzg2l_mipi_pm_ops,
1076 		.of_match_table = rzg2l_mipi_dsi_of_table,
1077 	},
1078 };
1079 
1080 module_platform_driver(rzg2l_mipi_dsi_platform_driver);
1081 
1082 MODULE_AUTHOR("Biju Das <biju.das.jz@bp.renesas.com>");
1083 MODULE_DESCRIPTION("Renesas RZ/G2L MIPI DSI Encoder Driver");
1084 MODULE_LICENSE("GPL");
1085