forked from ~ljy/RK356X_SDK_RELEASE

hc
2023-12-11 6778948f9de86c3cfaf36725a7c87dcff9ba247f
kernel/drivers/gpu/drm/omapdrm/dss/sdi.c
....@@ -1,33 +1,24 @@
1
+// SPDX-License-Identifier: GPL-2.0-only
12 /*
23 * Copyright (C) 2009 Nokia Corporation
34 * Author: Tomi Valkeinen <tomi.valkeinen@ti.com>
4
- *
5
- * This program is free software; you can redistribute it and/or modify it
6
- * under the terms of the GNU General Public License version 2 as published by
7
- * the Free Software Foundation.
8
- *
9
- * This program is distributed in the hope that it will be useful, but WITHOUT
10
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
12
- * more details.
13
- *
14
- * You should have received a copy of the GNU General Public License along with
15
- * this program. If not, see <http://www.gnu.org/licenses/>.
165 */
176
187 #define DSS_SUBSYS_NAME "SDI"
198
20
-#include <linux/kernel.h>
219 #include <linux/delay.h>
2210 #include <linux/err.h>
23
-#include <linux/regulator/consumer.h>
2411 #include <linux/export.h>
25
-#include <linux/platform_device.h>
26
-#include <linux/string.h>
12
+#include <linux/kernel.h>
2713 #include <linux/of.h>
14
+#include <linux/platform_device.h>
15
+#include <linux/regulator/consumer.h>
16
+#include <linux/string.h>
2817
29
-#include "omapdss.h"
18
+#include <drm/drm_bridge.h>
19
+
3020 #include "dss.h"
21
+#include "omapdss.h"
3122
3223 struct sdi_device {
3324 struct platform_device *pdev;
....@@ -37,13 +28,15 @@
3728 struct regulator *vdds_sdi_reg;
3829
3930 struct dss_lcd_mgr_config mgr_config;
40
- struct videomode vm;
31
+ unsigned long pixelclock;
4132 int datapairs;
4233
4334 struct omap_dss_device output;
35
+ struct drm_bridge bridge;
4436 };
4537
46
-#define dssdev_to_sdi(dssdev) container_of(dssdev, struct sdi_device, output)
38
+#define drm_bridge_to_sdi(bridge) \
39
+ container_of(bridge, struct sdi_device, bridge)
4740
4841 struct sdi_clk_calc_ctx {
4942 struct sdi_device *sdi;
....@@ -129,48 +122,99 @@
129122 dss_mgr_set_lcd_config(&sdi->output, &sdi->mgr_config);
130123 }
131124
132
-static int sdi_display_enable(struct omap_dss_device *dssdev)
133
-{
134
- struct sdi_device *sdi = dssdev_to_sdi(dssdev);
135
- struct videomode *vm = &sdi->vm;
136
- unsigned long fck;
137
- struct dispc_clock_info dispc_cinfo;
138
- unsigned long pck;
139
- int r;
125
+/* -----------------------------------------------------------------------------
126
+ * DRM Bridge Operations
127
+ */
140128
141
- if (!sdi->output.dispc_channel_connected) {
142
- DSSERR("failed to enable display: no output/manager\n");
143
- return -ENODEV;
144
- }
129
+static int sdi_bridge_attach(struct drm_bridge *bridge,
130
+ enum drm_bridge_attach_flags flags)
131
+{
132
+ struct sdi_device *sdi = drm_bridge_to_sdi(bridge);
133
+
134
+ if (!(flags & DRM_BRIDGE_ATTACH_NO_CONNECTOR))
135
+ return -EINVAL;
136
+
137
+ return drm_bridge_attach(bridge->encoder, sdi->output.next_bridge,
138
+ bridge, flags);
139
+}
140
+
141
+static enum drm_mode_status
142
+sdi_bridge_mode_valid(struct drm_bridge *bridge,
143
+ const struct drm_display_info *info,
144
+ const struct drm_display_mode *mode)
145
+{
146
+ struct sdi_device *sdi = drm_bridge_to_sdi(bridge);
147
+ unsigned long pixelclock = mode->clock * 1000;
148
+ struct dispc_clock_info dispc_cinfo;
149
+ unsigned long fck;
150
+ int ret;
151
+
152
+ if (pixelclock == 0)
153
+ return MODE_NOCLOCK;
154
+
155
+ ret = sdi_calc_clock_div(sdi, pixelclock, &fck, &dispc_cinfo);
156
+ if (ret < 0)
157
+ return MODE_CLOCK_RANGE;
158
+
159
+ return MODE_OK;
160
+}
161
+
162
+static bool sdi_bridge_mode_fixup(struct drm_bridge *bridge,
163
+ const struct drm_display_mode *mode,
164
+ struct drm_display_mode *adjusted_mode)
165
+{
166
+ struct sdi_device *sdi = drm_bridge_to_sdi(bridge);
167
+ unsigned long pixelclock = mode->clock * 1000;
168
+ struct dispc_clock_info dispc_cinfo;
169
+ unsigned long fck;
170
+ unsigned long pck;
171
+ int ret;
172
+
173
+ ret = sdi_calc_clock_div(sdi, pixelclock, &fck, &dispc_cinfo);
174
+ if (ret < 0)
175
+ return false;
176
+
177
+ pck = fck / dispc_cinfo.lck_div / dispc_cinfo.pck_div;
178
+
179
+ if (pck != pixelclock)
180
+ dev_dbg(&sdi->pdev->dev,
181
+ "pixel clock adjusted from %lu Hz to %lu Hz\n",
182
+ pixelclock, pck);
183
+
184
+ adjusted_mode->clock = pck / 1000;
185
+
186
+ return true;
187
+}
188
+
189
+static void sdi_bridge_mode_set(struct drm_bridge *bridge,
190
+ const struct drm_display_mode *mode,
191
+ const struct drm_display_mode *adjusted_mode)
192
+{
193
+ struct sdi_device *sdi = drm_bridge_to_sdi(bridge);
194
+
195
+ sdi->pixelclock = adjusted_mode->clock * 1000;
196
+}
197
+
198
+static void sdi_bridge_enable(struct drm_bridge *bridge)
199
+{
200
+ struct sdi_device *sdi = drm_bridge_to_sdi(bridge);
201
+ struct dispc_clock_info dispc_cinfo;
202
+ unsigned long fck;
203
+ int r;
145204
146205 r = regulator_enable(sdi->vdds_sdi_reg);
147206 if (r)
148
- goto err_reg_enable;
207
+ return;
149208
150209 r = dispc_runtime_get(sdi->dss->dispc);
151210 if (r)
152211 goto err_get_dispc;
153212
154
- /* 15.5.9.1.2 */
155
- vm->flags |= DISPLAY_FLAGS_PIXDATA_POSEDGE | DISPLAY_FLAGS_SYNC_POSEDGE;
156
-
157
- r = sdi_calc_clock_div(sdi, vm->pixelclock, &fck, &dispc_cinfo);
213
+ r = sdi_calc_clock_div(sdi, sdi->pixelclock, &fck, &dispc_cinfo);
158214 if (r)
159215 goto err_calc_clock_div;
160216
161217 sdi->mgr_config.clock_info = dispc_cinfo;
162
-
163
- pck = fck / dispc_cinfo.lck_div / dispc_cinfo.pck_div;
164
-
165
- if (pck != vm->pixelclock) {
166
- DSSWARN("Could not find exact pixel clock. Requested %lu Hz, got %lu Hz\n",
167
- vm->pixelclock, pck);
168
-
169
- vm->pixelclock = pck;
170
- }
171
-
172
-
173
- dss_mgr_set_timings(&sdi->output, vm);
174218
175219 r = dss_set_fck_rate(sdi->dss, fck);
176220 if (r)
....@@ -202,7 +246,7 @@
202246 if (r)
203247 goto err_mgr_enable;
204248
205
- return 0;
249
+ return;
206250
207251 err_mgr_enable:
208252 dss_sdi_disable(sdi->dss);
....@@ -212,13 +256,11 @@
212256 dispc_runtime_put(sdi->dss->dispc);
213257 err_get_dispc:
214258 regulator_disable(sdi->vdds_sdi_reg);
215
-err_reg_enable:
216
- return r;
217259 }
218260
219
-static void sdi_display_disable(struct omap_dss_device *dssdev)
261
+static void sdi_bridge_disable(struct drm_bridge *bridge)
220262 {
221
- struct sdi_device *sdi = dssdev_to_sdi(dssdev);
263
+ struct sdi_device *sdi = drm_bridge_to_sdi(bridge);
222264
223265 dss_mgr_disable(&sdi->output);
224266
....@@ -229,128 +271,68 @@
229271 regulator_disable(sdi->vdds_sdi_reg);
230272 }
231273
232
-static void sdi_set_timings(struct omap_dss_device *dssdev,
233
- struct videomode *vm)
234
-{
235
- struct sdi_device *sdi = dssdev_to_sdi(dssdev);
236
-
237
- sdi->vm = *vm;
238
-}
239
-
240
-static void sdi_get_timings(struct omap_dss_device *dssdev,
241
- struct videomode *vm)
242
-{
243
- struct sdi_device *sdi = dssdev_to_sdi(dssdev);
244
-
245
- *vm = sdi->vm;
246
-}
247
-
248
-static int sdi_check_timings(struct omap_dss_device *dssdev,
249
- struct videomode *vm)
250
-{
251
- struct sdi_device *sdi = dssdev_to_sdi(dssdev);
252
- enum omap_channel channel = dssdev->dispc_channel;
253
-
254
- if (!dispc_mgr_timings_ok(sdi->dss->dispc, channel, vm))
255
- return -EINVAL;
256
-
257
- if (vm->pixelclock == 0)
258
- return -EINVAL;
259
-
260
- return 0;
261
-}
262
-
263
-static int sdi_init_regulator(struct sdi_device *sdi)
264
-{
265
- struct regulator *vdds_sdi;
266
-
267
- if (sdi->vdds_sdi_reg)
268
- return 0;
269
-
270
- vdds_sdi = devm_regulator_get(&sdi->pdev->dev, "vdds_sdi");
271
- if (IS_ERR(vdds_sdi)) {
272
- if (PTR_ERR(vdds_sdi) != -EPROBE_DEFER)
273
- DSSERR("can't get VDDS_SDI regulator\n");
274
- return PTR_ERR(vdds_sdi);
275
- }
276
-
277
- sdi->vdds_sdi_reg = vdds_sdi;
278
-
279
- return 0;
280
-}
281
-
282
-static int sdi_connect(struct omap_dss_device *dssdev,
283
- struct omap_dss_device *dst)
284
-{
285
- struct sdi_device *sdi = dssdev_to_sdi(dssdev);
286
- int r;
287
-
288
- r = sdi_init_regulator(sdi);
289
- if (r)
290
- return r;
291
-
292
- r = dss_mgr_connect(&sdi->output, dssdev);
293
- if (r)
294
- return r;
295
-
296
- r = omapdss_output_set_device(dssdev, dst);
297
- if (r) {
298
- DSSERR("failed to connect output to new device: %s\n",
299
- dst->name);
300
- dss_mgr_disconnect(&sdi->output, dssdev);
301
- return r;
302
- }
303
-
304
- return 0;
305
-}
306
-
307
-static void sdi_disconnect(struct omap_dss_device *dssdev,
308
- struct omap_dss_device *dst)
309
-{
310
- struct sdi_device *sdi = dssdev_to_sdi(dssdev);
311
-
312
- WARN_ON(dst != dssdev->dst);
313
-
314
- if (dst != dssdev->dst)
315
- return;
316
-
317
- omapdss_output_unset_device(dssdev);
318
-
319
- dss_mgr_disconnect(&sdi->output, dssdev);
320
-}
321
-
322
-static const struct omapdss_sdi_ops sdi_ops = {
323
- .connect = sdi_connect,
324
- .disconnect = sdi_disconnect,
325
-
326
- .enable = sdi_display_enable,
327
- .disable = sdi_display_disable,
328
-
329
- .check_timings = sdi_check_timings,
330
- .set_timings = sdi_set_timings,
331
- .get_timings = sdi_get_timings,
274
+static const struct drm_bridge_funcs sdi_bridge_funcs = {
275
+ .attach = sdi_bridge_attach,
276
+ .mode_valid = sdi_bridge_mode_valid,
277
+ .mode_fixup = sdi_bridge_mode_fixup,
278
+ .mode_set = sdi_bridge_mode_set,
279
+ .enable = sdi_bridge_enable,
280
+ .disable = sdi_bridge_disable,
332281 };
333282
334
-static void sdi_init_output(struct sdi_device *sdi)
283
+static void sdi_bridge_init(struct sdi_device *sdi)
284
+{
285
+ sdi->bridge.funcs = &sdi_bridge_funcs;
286
+ sdi->bridge.of_node = sdi->pdev->dev.of_node;
287
+ sdi->bridge.type = DRM_MODE_CONNECTOR_LVDS;
288
+
289
+ drm_bridge_add(&sdi->bridge);
290
+}
291
+
292
+static void sdi_bridge_cleanup(struct sdi_device *sdi)
293
+{
294
+ drm_bridge_remove(&sdi->bridge);
295
+}
296
+
297
+/* -----------------------------------------------------------------------------
298
+ * Initialisation and Cleanup
299
+ */
300
+
301
+static int sdi_init_output(struct sdi_device *sdi)
335302 {
336303 struct omap_dss_device *out = &sdi->output;
304
+ int r;
305
+
306
+ sdi_bridge_init(sdi);
337307
338308 out->dev = &sdi->pdev->dev;
339309 out->id = OMAP_DSS_OUTPUT_SDI;
340
- out->output_type = OMAP_DISPLAY_TYPE_SDI;
310
+ out->type = OMAP_DISPLAY_TYPE_SDI;
341311 out->name = "sdi.0";
342312 out->dispc_channel = OMAP_DSS_CHANNEL_LCD;
343313 /* We have SDI only on OMAP3, where it's on port 1 */
344
- out->port_num = 1;
345
- out->ops.sdi = &sdi_ops;
314
+ out->of_port = 1;
346315 out->owner = THIS_MODULE;
316
+ out->bus_flags = DRM_BUS_FLAG_PIXDATA_DRIVE_POSEDGE /* 15.5.9.1.2 */
317
+ | DRM_BUS_FLAG_SYNC_DRIVE_POSEDGE;
347318
348
- omapdss_register_output(out);
319
+ r = omapdss_device_init_output(out, &sdi->bridge);
320
+ if (r < 0) {
321
+ sdi_bridge_cleanup(sdi);
322
+ return r;
323
+ }
324
+
325
+ omapdss_device_register(out);
326
+
327
+ return 0;
349328 }
350329
351330 static void sdi_uninit_output(struct sdi_device *sdi)
352331 {
353
- omapdss_unregister_output(&sdi->output);
332
+ omapdss_device_unregister(&sdi->output);
333
+ omapdss_device_cleanup_output(&sdi->output);
334
+
335
+ sdi_bridge_cleanup(sdi);
354336 }
355337
356338 int sdi_init_port(struct dss_device *dss, struct platform_device *pdev,
....@@ -372,25 +354,32 @@
372354 }
373355
374356 r = of_property_read_u32(ep, "datapairs", &datapairs);
357
+ of_node_put(ep);
375358 if (r) {
376359 DSSERR("failed to parse datapairs\n");
377
- goto err_datapairs;
360
+ goto err_free;
378361 }
379362
380363 sdi->datapairs = datapairs;
381364 sdi->dss = dss;
382365
383
- of_node_put(ep);
384
-
385366 sdi->pdev = pdev;
386367 port->data = sdi;
387368
388
- sdi_init_output(sdi);
369
+ sdi->vdds_sdi_reg = devm_regulator_get(&pdev->dev, "vdds_sdi");
370
+ if (IS_ERR(sdi->vdds_sdi_reg)) {
371
+ r = PTR_ERR(sdi->vdds_sdi_reg);
372
+ if (r != -EPROBE_DEFER)
373
+ DSSERR("can't get VDDS_SDI regulator\n");
374
+ goto err_free;
375
+ }
376
+
377
+ r = sdi_init_output(sdi);
378
+ if (r)
379
+ goto err_free;
389380
390381 return 0;
391382
392
-err_datapairs:
393
- of_node_put(ep);
394383 err_free:
395384 kfree(sdi);
396385