2 * Copyright (C) Fuzhou Rockchip Electronics Co.Ltd
3 * Author: Chris Zhong <zyw@rock-chips.com>
5 * This software is licensed under the terms of the GNU General Public
6 * License version 2, as published by the Free Software Foundation, and
7 * may be copied, distributed, and modified under those terms.
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
15 #include <linux/clk.h>
16 #include <linux/component.h>
17 #include <linux/extcon.h>
18 #include <linux/firmware.h>
19 #include <linux/regmap.h>
20 #include <linux/reset.h>
21 #include <linux/mfd/syscon.h>
22 #include <linux/phy/phy.h>
23 #include <sound/hdmi-codec.h>
24 #include <video/of_videomode.h>
25 #include <video/videomode.h>
28 #include <linux/platform_device.h>
29 #include "rockchip_dp_core.h"
30 #include "cdn-dp-reg.h"
32 static struct cdn_dp_data rk3399_cdn_dp = {
36 static const struct of_device_id cdn_dp_dt_ids[] = {
37 { .compatible = "rockchip,rk3399-cdn-dp-fb",
38 .data = (void *)&rk3399_cdn_dp },
42 MODULE_DEVICE_TABLE(of, cdn_dp_dt_ids);
44 static int cdn_dp_grf_write(struct cdn_dp_device *dp,
45 unsigned int reg, unsigned int val)
49 ret = clk_prepare_enable(dp->grf_clk);
51 dev_err(dp->dev, "Failed to prepare_enable grf clock\n");
55 ret = regmap_write(dp->grf, reg, val);
57 dev_err(dp->dev, "Could not write to GRF: %d\n", ret);
61 clk_disable_unprepare(dp->grf_clk);
66 static int cdn_dp_set_fw_rate(struct cdn_dp_device *dp)
70 if (!dp->fw_clk_enabled) {
71 rate = clk_get_rate(dp->core_clk);
73 dev_err(dp->dev, "get clk rate failed: %d\n", rate);
76 cdn_dp_set_fw_clk(dp, rate);
77 cdn_dp_clock_reset(dp);
78 dp->fw_clk_enabled = true;
84 static int cdn_dp_clk_enable(struct cdn_dp_device *dp)
88 ret = clk_prepare_enable(dp->pclk);
90 dev_err(dp->dev, "cannot enable dp pclk %d\n", ret);
94 ret = clk_prepare_enable(dp->core_clk);
96 dev_err(dp->dev, "cannot enable core_clk %d\n", ret);
100 ret = pm_runtime_get_sync(dp->dev);
102 dev_err(dp->dev, "cannot get pm runtime %d\n", ret);
106 ret = cdn_dp_set_fw_rate(dp);
108 dev_err(dp->dev, "cannot get set fw rate %d\n", ret);
115 clk_disable_unprepare(dp->core_clk);
117 clk_disable_unprepare(dp->pclk);
119 pm_runtime_put_sync(dp->dev);
123 static void cdn_dp_clk_disable(struct cdn_dp_device *dp)
125 pm_runtime_put_sync(dp->dev);
126 clk_disable_unprepare(dp->pclk);
127 clk_disable_unprepare(dp->core_clk);
130 int cdn_dp_get_edid(void *dp, u8 *buf, int block)
133 struct cdn_dp_device *dp_dev = dp;
135 char start_read_edid = -1;
137 u32 left_size = EDID_BLOCK_SIZE;
139 mutex_lock(&dp_dev->lock);
140 ret = cdn_dp_dpcd_read(dp, 0x0030, guid, 8);
141 if (ret == 0 && guid[0] == 'n' && guid[1] == 'a' &&
142 guid[2] == 'n' && guid[3] == 'o' && guid[4] == 'c') {
145 cdn_dp_dpcd_write(dp, 0x0038, 0x55);
146 while (left_size > 0) {
147 u32 length = (left_size > 8) ? 8 : left_size;
149 ret = cdn_dp_dpcd_read(dp, 0x0038, &start_read_edid, 1);
151 dev_err(dp_dev->dev, "read edid sync number error!\n");
153 } else if (start_read_edid == 0xaa) {
155 ret = cdn_dp_dpcd_read(dp, 0x0030,
160 "read edid bytes [%d~%d] error!\n",
162 readed_size + length);
166 readed_size += length;
168 cdn_dp_dpcd_write(dp, 0x0038, 0x55);
170 if (try_times++ >= 100) {
171 dev_err(dp_dev->dev, "read edid from NanoC failed!\n");
178 ret = cdn_dp_get_edid_block(dp_dev, buf,
179 block, EDID_BLOCK_SIZE);
181 mutex_unlock(&dp_dev->lock);
186 int cdn_dp_connector_detect(void *dp)
188 struct cdn_dp_device *dp_dev = dp;
191 mutex_lock(&dp_dev->lock);
192 if (dp_dev->hpd_status == connector_status_connected)
194 mutex_unlock(&dp_dev->lock);
199 int cdn_dp_encoder_disable(void *dp)
201 struct cdn_dp_device *dp_dev = dp;
204 mutex_lock(&dp_dev->lock);
205 memset(&dp_dev->mode, 0, sizeof(dp_dev->mode));
206 if (dp_dev->hpd_status == connector_status_disconnected) {
207 dp_dev->dpms_mode = DRM_MODE_DPMS_OFF;
208 mutex_unlock(&dp_dev->lock);
212 if (dp_dev->dpms_mode == DRM_MODE_DPMS_ON) {
213 dp_dev->dpms_mode = DRM_MODE_DPMS_OFF;
215 dev_warn(dp_dev->dev, "wrong dpms status,dp encoder has already been disabled\n");
218 mutex_unlock(&dp_dev->lock);
223 static void cdn_dp_commit(struct cdn_dp_device *dp)
226 int ret = cdn_dp_training_start(dp);
229 dev_err(dp->dev, "link training failed: %d\n", ret);
233 ret = cdn_dp_get_training_status(dp);
235 dev_err(dp->dev, "get link training status failed: %d\n", ret);
239 dev_info(dp->dev, "rate:%d, lanes:%d\n",
240 dp->link.rate, dp->link.num_lanes);
243 * Use dpcd@0x0030~0x003f(which is GUID registers) to sync with NanoC
244 * to make sure training is ok. Nanoc will write "nanoc" in GUID registers
245 * when booting, and then we will use these registers to decide whether
246 * need to sync with device which plugged in.
247 * The sync register is 0x0035, firstly we write 0xaa to sync register,
248 * nanoc will read this register and then start the part2 code of DP.
250 ret = cdn_dp_dpcd_read(dp, 0x0030, guid, 8);
251 if (ret == 0 && guid[0] == 'n' && guid[1] == 'a' && guid[2] == 'n' &&
252 guid[3] == 'o' && guid[4] == 'c') {
253 u8 sync_number = 0xaa;
255 cdn_dp_dpcd_write(dp, 0x0035, sync_number);
258 if (cdn_dp_set_video_status(dp, CONTROL_VIDEO_IDLE))
261 if (cdn_dp_config_video(dp)) {
262 dev_err(dp->dev, "unable to config video\n");
266 if (cdn_dp_set_video_status(dp, CONTROL_VIDEO_VALID))
269 dp->dpms_mode = DRM_MODE_DPMS_ON;
272 int cdn_dp_encoder_mode_set(void *dp, struct dp_disp_info *disp_info)
275 struct cdn_dp_device *dp_dev = dp;
276 struct video_info *video = &dp_dev->video_info;
277 struct drm_display_mode disp_mode;
278 struct fb_videomode *mode = disp_info->mode;
280 mutex_lock(&dp_dev->lock);
281 disp_mode.clock = mode->pixclock / 1000;
282 disp_mode.hdisplay = mode->xres;
283 disp_mode.hsync_start = disp_mode.hdisplay + mode->right_margin;
284 disp_mode.hsync_end = disp_mode.hsync_start + mode->hsync_len;
285 disp_mode.htotal = disp_mode.hsync_end + mode->left_margin;
286 disp_mode.vdisplay = mode->yres;
287 disp_mode.vsync_start = disp_mode.vdisplay + mode->lower_margin;
288 disp_mode.vsync_end = disp_mode.vsync_start + mode->vsync_len;
289 disp_mode.vtotal = disp_mode.vsync_end + mode->upper_margin;
291 switch (disp_info->color_depth) {
295 video->color_depth = 10;
298 video->color_depth = 6;
301 video->color_depth = 8;
305 video->color_fmt = PXL_RGB;
307 video->v_sync_polarity = disp_info->vsync_polarity;
308 video->h_sync_polarity = disp_info->hsync_polarity;
310 if (disp_info->vop_sel)
311 val = DP_SEL_VOP_LIT | (DP_SEL_VOP_LIT << 16);
313 val = DP_SEL_VOP_LIT << 16;
315 ret = cdn_dp_grf_write(dp, GRF_SOC_CON9, val);
317 dev_err(dp_dev->dev, "Could not write to GRF: %d\n", ret);
318 mutex_unlock(&dp_dev->lock);
321 memcpy(&dp_dev->mode, &disp_mode, sizeof(disp_mode));
323 mutex_unlock(&dp_dev->lock);
328 int cdn_dp_encoder_enable(void *dp)
330 struct cdn_dp_device *dp_dev = dp;
333 mutex_lock(&dp_dev->lock);
335 if (dp_dev->dpms_mode == DRM_MODE_DPMS_OFF) {
337 * the mode info of dp device will be cleared when dp encoder is disabled
338 * so if clock value of mode is 0, means rockchip_dp_config_video is not
339 * return success, so we don't do cdn_dp_commit.
341 if (dp_dev->mode.clock == 0) {
342 dev_err(dp_dev->dev, "Error !Please make sure function cdn_dp_encoder_mode_set return success!\n");
343 mutex_unlock(&dp_dev->lock);
346 cdn_dp_commit(dp_dev);
348 dev_warn(dp_dev->dev, "wrong dpms status,dp encoder has already been enabled\n");
351 mutex_unlock(&dp_dev->lock);
356 static int cdn_dp_firmware_init(struct cdn_dp_device *dp)
359 const u32 *iram_data, *dram_data;
360 const struct firmware *fw = dp->fw;
361 const struct cdn_firmware_header *hdr;
363 hdr = (struct cdn_firmware_header *)fw->data;
364 if (fw->size != le32_to_cpu(hdr->size_bytes)) {
365 dev_err(dp->dev, "firmware is invalid\n");
369 iram_data = (const u32 *)(fw->data + hdr->header_size);
370 dram_data = (const u32 *)(fw->data + hdr->header_size + hdr->iram_size);
372 ret = cdn_dp_load_firmware(dp, iram_data, hdr->iram_size,
373 dram_data, hdr->dram_size);
377 ret = cdn_dp_set_firmware_active(dp, true);
379 dev_err(dp->dev, "active ucpu failed: %d\n", ret);
384 return cdn_dp_event_config(dp);
387 static int cdn_dp_init(struct cdn_dp_device *dp)
389 struct device *dev = dp->dev;
390 struct device_node *np = dev->of_node;
391 struct platform_device *pdev = to_platform_device(dev);
392 struct resource *res;
394 dp->grf = syscon_regmap_lookup_by_phandle(np, "rockchip,grf");
395 if (IS_ERR(dp->grf)) {
396 dev_err(dev, "cdn-dp needs rockchip,grf property\n");
397 return PTR_ERR(dp->grf);
400 res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
401 dp->regs = devm_ioremap_resource(dev, res);
402 if (IS_ERR(dp->regs)) {
403 dev_err(dev, "ioremap reg failed\n");
404 return PTR_ERR(dp->regs);
407 dp->core_clk = devm_clk_get(dev, "core-clk");
408 if (IS_ERR(dp->core_clk)) {
409 dev_err(dev, "cannot get core_clk_dp\n");
410 return PTR_ERR(dp->core_clk);
413 dp->pclk = devm_clk_get(dev, "pclk");
414 if (IS_ERR(dp->pclk)) {
415 dev_err(dev, "cannot get pclk\n");
416 return PTR_ERR(dp->pclk);
419 dp->spdif_clk = devm_clk_get(dev, "spdif");
420 if (IS_ERR(dp->spdif_clk)) {
421 dev_err(dev, "cannot get spdif_clk\n");
422 return PTR_ERR(dp->spdif_clk);
425 dp->grf_clk = devm_clk_get(dev, "grf");
426 if (IS_ERR(dp->grf_clk)) {
427 dev_err(dev, "cannot get grf clk\n");
428 return PTR_ERR(dp->grf_clk);
431 dp->spdif_rst = devm_reset_control_get(dev, "spdif");
432 if (IS_ERR(dp->spdif_rst)) {
433 dev_err(dev, "no spdif reset control found\n");
434 return PTR_ERR(dp->spdif_rst);
437 dp->dptx_rst = devm_reset_control_get(dev, "dptx");
438 if (IS_ERR(dp->dptx_rst)) {
439 dev_err(dev, "no uphy reset control found\n");
440 return PTR_ERR(dp->dptx_rst);
443 dp->apb_rst = devm_reset_control_get(dev, "apb");
444 if (IS_ERR(dp->apb_rst)) {
445 dev_err(dev, "no apb reset control found\n");
446 return PTR_ERR(dp->apb_rst);
449 dp->dpms_mode = DRM_MODE_DPMS_OFF;
450 dp->fw_clk_enabled = false;
452 pm_runtime_enable(dev);
454 reset_control_assert(dp->dptx_rst);
456 reset_control_deassert(dp->dptx_rst);
457 reset_control_assert(dp->apb_rst);
459 reset_control_deassert(dp->apb_rst);
461 mutex_init(&dp->lock);
462 wake_lock_init(&dp->wake_lock, WAKE_LOCK_SUSPEND, "cdn_dp_fb");
466 struct cdn_dp_device *g_dp;
467 static int cdn_dp_audio_hw_params(struct device *dev, void *data,
468 struct hdmi_codec_daifmt *daifmt,
469 struct hdmi_codec_params *params)
471 struct dp_dev *dp_dev = dev_get_drvdata(dev);
472 struct cdn_dp_device *dp = dp_dev->dp;
474 struct audio_info audio = {
476 .sample_rate = 44100,
480 if (!cdn_dp_connector_detect(dp))
485 audio.format = AFMT_I2S;
488 audio.format = AFMT_SPDIF;
491 dev_err(dev, "%s: Invalid format %d\n", __func__, daifmt->fmt);
495 ret = cdn_dp_audio_config(dp, &audio);
497 dp->audio_info = audio;
502 static void cdn_dp_audio_shutdown(struct device *dev, void *data)
504 struct dp_dev *dp_dev = dev_get_drvdata(dev);
505 struct cdn_dp_device *dp = dp_dev->dp;
508 if (cdn_dp_connector_detect(dp)) {
509 ret = cdn_dp_audio_stop(dp, &dp->audio_info);
511 dp->audio_info.format = AFMT_UNUSED;
515 static int cdn_dp_audio_digital_mute(struct device *dev, void *data,
518 struct dp_dev *dp_dev = dev_get_drvdata(dev);
519 struct cdn_dp_device *dp = dp_dev->dp;
521 if (!cdn_dp_connector_detect(dp))
523 return cdn_dp_audio_mute(dp, enable);
526 static const struct hdmi_codec_ops audio_codec_ops = {
527 .hw_params = cdn_dp_audio_hw_params,
528 .audio_shutdown = cdn_dp_audio_shutdown,
529 .digital_mute = cdn_dp_audio_digital_mute,
532 static int cdn_dp_audio_codec_init(struct cdn_dp_device *dp,
535 struct hdmi_codec_pdata codec_data = {
538 .ops = &audio_codec_ops,
539 .max_i2s_channels = 8,
542 dp->audio_pdev = platform_device_register_data(
543 dev, HDMI_CODEC_DRV_NAME, PLATFORM_DEVID_AUTO,
544 &codec_data, sizeof(codec_data));
546 return PTR_ERR_OR_ZERO(dp->audio_pdev);
549 static int cdn_dp_get_cap_lanes(struct cdn_dp_device *dp,
550 struct extcon_dev *edev)
552 union extcon_property_value property;
559 dptx = extcon_get_state(edev, EXTCON_DISP_DP);
561 extcon_get_property(edev, EXTCON_DISP_DP,
562 EXTCON_PROP_USB_SS, &property);
572 static int cdn_dp_get_dpcd(struct cdn_dp_device *dp, struct cdn_dp_port *port)
579 * Native read with retry for link status and receiver capability reads
580 * for cases where the sink may still not be ready.
582 * Sinks are *supposed* to come up within 1ms from an off state, but
583 * some DOCKs need about 5 seconds to power up, so read the dpcd every
584 * 100ms, if can not get a good dpcd in 10 seconds, give up.
586 for (i = 0; i < 100; i++) {
587 ret = cdn_dp_dpcd_read(dp, DP_SINK_COUNT,
590 dev_dbg(dp->dev, "get dpcd success!\n");
592 sink_count = DP_GET_SINK_COUNT(sink_count);
595 dev_err(dp->dev, "sink cout is 0, no sink device!\n");
602 ret = cdn_dp_dpcd_read(dp, 0x000, dp->dpcd,
603 DP_RECEIVER_CAP_SIZE);
608 } else if (!extcon_get_state(port->extcon, EXTCON_DISP_DP)) {
615 dev_err(dp->dev, "get dpcd failed!\n");
620 static void cdn_dp_enter_standy(struct cdn_dp_device *dp,
621 struct cdn_dp_port *port)
625 ret = phy_power_off(port->phy);
627 dev_err(dp->dev, "phy power off failed: %d", ret);
631 port->phy_status = false;
633 for (i = 0; i < dp->ports; i++)
634 if (dp->port[i]->phy_status)
637 memset(dp->dpcd, 0, DP_RECEIVER_CAP_SIZE);
639 cdn_dp_set_firmware_active(dp, false);
640 cdn_dp_clk_disable(dp);
641 dp->hpd_status = connector_status_disconnected;
643 hpd_change(dp->dev, 0);
646 static int cdn_dp_start_work(struct cdn_dp_device *dp,
647 struct cdn_dp_port *port,
650 union extcon_property_value property;
653 if (!dp->fw_loaded) {
654 ret = request_firmware(&dp->fw, CDN_DP_FIRMWARE, dp->dev);
656 if (ret == -ENOENT && dp->fw_wait <= MAX_FW_WAIT_SECS) {
657 unsigned long time = msecs_to_jiffies(dp->fw_wait * HZ);
660 * Keep trying to load the firmware for up to 1 minute,
661 * if can not find the file.
663 schedule_delayed_work(&port->event_wq, time);
666 dev_err(dp->dev, "failed to request firmware: %d\n",
674 ret = cdn_dp_clk_enable(dp);
676 dev_err(dp->dev, "failed to enable clock for dp: %d\n", ret);
680 cdn_dp_set_firmware_active(dp, true);
682 ret = phy_power_on(port->phy);
684 dev_err(dp->dev, "phy power on failed: %d\n", ret);
688 port->phy_status = true;
690 if (!dp->fw_loaded) {
691 ret = cdn_dp_firmware_init(dp);
693 dev_err(dp->dev, "firmware init failed: %d", ret);
698 ret = cdn_dp_grf_write(dp, GRF_SOC_CON26,
699 DPTX_HPD_SEL_MASK | DPTX_HPD_SEL);
703 ret = cdn_dp_get_hpd_status(dp);
706 dev_err(dp->dev, "hpd does not exist\n");
710 ret = extcon_get_property(port->extcon, EXTCON_DISP_DP,
711 EXTCON_PROP_USB_TYPEC_POLARITY, &property);
713 dev_err(dp->dev, "get property failed\n");
717 ret = cdn_dp_set_host_cap(dp, cap_lanes, property.intval);
719 dev_err(dp->dev, "set host capabilities failed: %d\n", ret);
723 ret = cdn_dp_get_dpcd(dp, port);
730 cdn_dp_grf_write(dp, GRF_SOC_CON26,
731 DPTX_HPD_SEL_MASK | DPTX_HPD_DEL);
734 cdn_dp_set_firmware_active(dp, false);
737 if (phy_power_off(port->phy))
738 dev_err(dp->dev, "phy power off failed: %d", ret);
740 port->phy_status = false;
744 cdn_dp_set_firmware_active(dp, false);
745 cdn_dp_clk_disable(dp);
749 static int cdn_dp_pd_event(struct notifier_block *nb,
750 unsigned long event, void *priv)
752 struct cdn_dp_port *port;
754 port = container_of(nb, struct cdn_dp_port, event_nb);
755 schedule_delayed_work(&port->event_wq, 0);
759 static void cdn_dp_pd_event_wq(struct work_struct *work)
761 struct cdn_dp_port *port = container_of(work, struct cdn_dp_port,
763 struct cdn_dp_device *dp = port->dp;
764 u8 new_cap_lanes, sink_count, i;
767 mutex_lock(&dp->lock);
768 wake_lock_timeout(&dp->wake_lock, msecs_to_jiffies(1000));
770 new_cap_lanes = cdn_dp_get_cap_lanes(dp, port->extcon);
772 if (new_cap_lanes == port->cap_lanes) {
773 if (!new_cap_lanes) {
774 dev_err(dp->dev, "dp lanes is 0, and same with last time\n");
779 * If HPD interrupt is triggered, and cable states is still
780 * attached, that means something on the Type-C Dock/Dongle
781 * changed, check the sink count by DPCD. If sink count became
782 * 0, this port phy can be powered off; if the sink count does
783 * not change, it means the sink device status has update,
784 * re-training to make it work again.
786 ret = cdn_dp_dpcd_read(dp, DP_SINK_COUNT, &sink_count, 1);
787 if (ret || sink_count) {
788 if (dp->dpms_mode == DRM_MODE_DPMS_ON) {
790 "hpd interrupt is triggered when dp is already connected successfully\n");
791 ret = cdn_dp_training_start(dp);
793 cdn_dp_get_training_status(dp);
800 if (dp->hpd_status == connector_status_connected && new_cap_lanes) {
801 dev_err(dp->dev, "error, dp connector has already been connected\n");
805 if (!new_cap_lanes) {
806 dev_info(dp->dev, "dp lanes is 0, enter standby\n");
807 cdn_dp_enter_standy(dp, port);
811 /* if other phy is running, do not do anything, just return */
812 for (i = 0; i < dp->ports; i++) {
813 if (dp->port[i]->phy_status) {
814 dev_warn(dp->dev, "busy, phy[%d] is running",
820 ret = cdn_dp_start_work(dp, port, new_cap_lanes);
822 dev_err(dp->dev, "dp failed to connect ,error = %d\n", ret);
825 port->cap_lanes = new_cap_lanes;
826 dp->hpd_status = connector_status_connected;
827 wake_unlock(&dp->wake_lock);
828 mutex_unlock(&dp->lock);
829 hpd_change(dp->dev, new_cap_lanes);
833 wake_unlock(&dp->wake_lock);
834 mutex_unlock(&dp->lock);
837 static int cdn_dp_bind(struct cdn_dp_device *dp)
839 struct cdn_dp_port *port;
842 ret = cdn_dp_init(dp);
846 dp->hpd_status = connector_status_disconnected;
848 cdn_dp_audio_codec_init(dp, dp->dev);
850 for (i = 0; i < dp->ports; i++) {
853 port->event_nb.notifier_call = cdn_dp_pd_event;
854 INIT_DELAYED_WORK(&port->event_wq, cdn_dp_pd_event_wq);
855 ret = extcon_register_notifier(port->extcon, EXTCON_DISP_DP,
858 dev_err(dp->dev, "regitster EXTCON_DISP_DP notifier err\n");
862 if (extcon_get_state(port->extcon, EXTCON_DISP_DP))
863 schedule_delayed_work(&port->event_wq,
864 msecs_to_jiffies(2000));
870 int cdn_dp_suspend(void *dp_dev)
872 struct cdn_dp_device *dp = dp_dev;
873 struct cdn_dp_port *port;
876 for (i = 0; i < dp->ports; i++) {
878 if (port->phy_status) {
879 cdn_dp_dpcd_write(dp, DP_SET_POWER, DP_SET_POWER_D3);
880 cdn_dp_enter_standy(dp, port);
885 * if dp has been suspended, need to download firmware
886 * and set fw clk again.
888 dp->fw_clk_enabled = false;
889 dp->fw_loaded = false;
894 int cdn_dp_resume(void *dp_dev)
896 struct cdn_dp_device *dp = dp_dev;
897 struct cdn_dp_port *port;
901 reset_control_assert(dp->dptx_rst);
903 reset_control_deassert(dp->dptx_rst);
904 reset_control_assert(dp->apb_rst);
906 reset_control_deassert(dp->apb_rst);
908 for (i = 0; i < dp->ports; i++) {
910 schedule_delayed_work(&port->event_wq, 0);
911 flush_delayed_work(&port->event_wq);
918 static int cdn_dp_probe(struct platform_device *pdev)
920 struct device *dev = &pdev->dev;
921 const struct of_device_id *match;
922 struct cdn_dp_data *dp_data;
923 struct cdn_dp_port *port;
924 struct cdn_dp_device *dp;
925 struct extcon_dev *extcon;
929 dp = devm_kzalloc(dev, sizeof(*dp), GFP_KERNEL);
935 match = of_match_node(cdn_dp_dt_ids, pdev->dev.of_node);
936 dp_data = (struct cdn_dp_data *)match->data;
938 for (i = 0; i < dp_data->max_phy; i++) {
939 extcon = extcon_get_edev_by_phandle(dev, i);
940 phy = devm_of_phy_get_by_index(dev, dev->of_node, i);
942 if (PTR_ERR(extcon) == -EPROBE_DEFER ||
943 PTR_ERR(phy) == -EPROBE_DEFER){
944 /* don't exit if there already has one port */
947 return -EPROBE_DEFER;
951 if (IS_ERR(extcon) || IS_ERR(phy))
954 port = devm_kzalloc(dev, sizeof(*port), GFP_KERNEL);
958 port->extcon = extcon;
962 dp->port[dp->ports++] = port;
966 dev_err(dev, "missing extcon or phy\n");
971 ret = cdn_dp_fb_register(pdev, dp);
976 static struct platform_driver cdn_dp_driver = {
977 .probe = cdn_dp_probe,
980 .owner = THIS_MODULE,
981 .of_match_table = of_match_ptr(cdn_dp_dt_ids),
985 module_platform_driver(cdn_dp_driver);
987 MODULE_AUTHOR("Chris Zhong <zyw@rock-chips.com>");
988 MODULE_DESCRIPTION("cdn DP Driver");
989 MODULE_LICENSE("GPL v2");