From 9d77db3c730780c8ef5ccd4b66403ff5675cfe4e Mon Sep 17 00:00:00 2001 From: hc <hc@nodka.com> Date: Mon, 13 May 2024 10:30:14 +0000 Subject: [PATCH] modify sin led gpio --- kernel/drivers/gpu/drm/rockchip/rockchip_rgb.c | 98 +++++++++++++++++++++++++++++++++++++------------ 1 files changed, 74 insertions(+), 24 deletions(-) diff --git a/kernel/drivers/gpu/drm/rockchip/rockchip_rgb.c b/kernel/drivers/gpu/drm/rockchip/rockchip_rgb.c index 1ba2a8d..a7f2057 100644 --- a/kernel/drivers/gpu/drm/rockchip/rockchip_rgb.c +++ b/kernel/drivers/gpu/drm/rockchip/rockchip_rgb.c @@ -68,7 +68,8 @@ }; struct rockchip_rgb_data { - u32 max_dclk_rate; + u32 rgb_max_dclk_rate; + u32 mcu_max_dclk_rate; const struct rockchip_rgb_funcs *funcs; }; @@ -129,7 +130,9 @@ struct rockchip_rgb { u8 id; u32 max_dclk_rate; + u32 mcu_pix_total; struct device *dev; + struct device_node *np_mcu_panel; struct drm_panel *panel; struct drm_bridge *bridge; struct drm_connector connector; @@ -137,7 +140,6 @@ struct phy *phy; struct regmap *grf; bool data_sync_bypass; - bool is_mcu_panel; bool phy_enabled; const struct rockchip_rgb_funcs *funcs; struct rockchip_drm_sub_dev sub_dev; @@ -277,6 +279,15 @@ s->output_mode = ROCKCHIP_OUT_MODE_P565; s->output_if = VOP_OUTPUT_IF_RGB; break; + case MEDIA_BUS_FMT_RGB565_2X8_LE: + case MEDIA_BUS_FMT_BGR565_2X8_LE: + s->output_mode = ROCKCHIP_OUT_MODE_S565; + s->output_if = VOP_OUTPUT_IF_RGB; + break; + case MEDIA_BUS_FMT_RGB666_3X6: + s->output_mode = ROCKCHIP_OUT_MODE_S666; + s->output_if = VOP_OUTPUT_IF_RGB; + break; case MEDIA_BUS_FMT_RGB888_3X8: case MEDIA_BUS_FMT_BGR888_3X8: s->output_mode = ROCKCHIP_OUT_MODE_S888; @@ -323,7 +334,7 @@ { struct rockchip_rgb *rgb = encoder_to_rgb(encoder); - if (rgb->is_mcu_panel) { + if (rgb->np_mcu_panel) { struct rockchip_mcu_panel *mcu_panel = to_rockchip_mcu_panel(rgb->panel); mcu_panel->prepared = true; @@ -358,11 +369,22 @@ { struct rockchip_rgb *rgb = encoder_to_rgb(encoder); struct device *dev = rgb->dev; + struct drm_display_info *info = &rgb->connector.display_info; u32 request_clock = mode->clock; u32 max_clock = rgb->max_dclk_rate; + u32 bus_format; + + if (info->num_bus_formats) + bus_format = info->bus_formats[0]; + else + bus_format = MEDIA_BUS_FMT_RGB888_1X24; if (mode->flags & DRM_MODE_FLAG_DBLCLK) request_clock *= 2; + + if (rgb->np_mcu_panel) + request_clock *= rockchip_drm_get_cycles_per_pixel(bus_format) * + (rgb->mcu_pix_total + 1); if (max_clock != 0 && request_clock > max_clock) { DRM_DEV_ERROR(dev, "mode [%dx%d] clock %d is higher than max_clock %d\n", @@ -444,16 +466,18 @@ return 0; } -static int rockchip_mcu_panel_init(struct rockchip_rgb *rgb, struct device_node *np_mcu_panel) +static int rockchip_mcu_panel_init(struct rockchip_rgb *rgb) { struct device *dev = rgb->dev; - struct device_node *port, *endpoint, *np_crtc, *remote; + struct device_node *np_mcu_panel = rgb->np_mcu_panel; + struct device_node *port, *endpoint, *np_crtc, *remote, *np_mcu_timing; struct rockchip_mcu_panel *mcu_panel = to_rockchip_mcu_panel(rgb->panel); struct drm_display_mode *mode; const void *data; int len; int ret; u32 bus_flags; + u32 val; mcu_panel->enable_gpio = devm_fwnode_gpiod_get_index(dev, &np_mcu_panel->fwnode, "enable", 0, GPIOD_ASIS, @@ -544,6 +568,8 @@ if (remote) { np_crtc = of_get_next_parent(remote); mcu_panel->np_crtc = np_crtc; + + of_node_put(np_crtc); break; } } @@ -553,6 +579,31 @@ DRM_DEV_ERROR(dev, "failed to find available crtc for mcu panel\n"); return -EINVAL; } + + np_mcu_timing = of_get_child_by_name(mcu_panel->np_crtc, "mcu-timing"); + if (!np_mcu_timing) { + np_crtc = of_get_parent(mcu_panel->np_crtc); + if (np_crtc) + np_mcu_timing = of_get_child_by_name(np_crtc, "mcu-timing"); + + if (!np_mcu_timing) { + DRM_DEV_ERROR(dev, "failed to find timing config for mcu panel\n"); + of_node_put(np_crtc); + return -EINVAL; + } + + of_node_put(np_crtc); + } + + ret = of_property_read_u32(np_mcu_timing, "mcu-pix-total", &val); + if (ret || val == 0) { + DRM_DEV_ERROR(dev, "failed to parse mcu_pix_total config\n"); + of_node_put(np_mcu_timing); + return -EINVAL; + } + rgb->mcu_pix_total = val; + + of_node_put(np_mcu_timing); } return 0; @@ -741,9 +792,10 @@ .get_modes = rockchip_mcu_panel_get_modes, }; -static struct backlight_device *rockchip_mcu_panel_find_backlight(struct device_node *np_mcu_panel) +static struct backlight_device *rockchip_mcu_panel_find_backlight(struct rockchip_rgb *rgb) { struct backlight_device *bd = NULL; + struct device_node *np_mcu_panel = rgb->np_mcu_panel; struct device_node *np = NULL; np = of_parse_phandle(np_mcu_panel, "backlight", 0); @@ -768,45 +820,35 @@ struct drm_device *drm_dev = data; struct drm_encoder *encoder = &rgb->encoder; struct drm_connector *connector; - struct fwnode_handle *fwnode_mcu_panel; int ret; - fwnode_mcu_panel = device_get_named_child_node(dev, "mcu-panel"); - if (fwnode_mcu_panel) { + if (rgb->np_mcu_panel) { struct rockchip_mcu_panel *mcu_panel; - struct device_node *np_mcu_panel = to_of_node(fwnode_mcu_panel); mcu_panel = devm_kzalloc(dev, sizeof(*mcu_panel), GFP_KERNEL); if (!mcu_panel) { - of_node_put(np_mcu_panel); return -ENOMEM; } mcu_panel->drm_dev = drm_dev; rgb->panel = &mcu_panel->base; - ret = rockchip_mcu_panel_init(rgb, np_mcu_panel); + ret = rockchip_mcu_panel_init(rgb); if (ret < 0) { DRM_DEV_ERROR(dev, "failed to init mcu panel: %d\n", ret); - of_node_put(np_mcu_panel); return ret; } - rgb->panel->backlight = rockchip_mcu_panel_find_backlight(np_mcu_panel); + rgb->panel->backlight = rockchip_mcu_panel_find_backlight(rgb); if (!rgb->panel->backlight) { DRM_DEV_ERROR(dev, "failed to find backlight device"); - of_node_put(np_mcu_panel); return -EINVAL; } - - of_node_put(np_mcu_panel); drm_panel_init(&mcu_panel->base, dev, &rockchip_mcu_panel_funcs, DRM_MODE_CONNECTOR_DPI); drm_panel_add(&mcu_panel->base); - - rgb->is_mcu_panel = true; } else { ret = drm_of_find_panel_or_bridge(dev->of_node, 1, -1, &rgb->panel, &rgb->bridge); @@ -899,6 +941,7 @@ struct device *dev = &pdev->dev; struct rockchip_rgb *rgb; const struct rockchip_rgb_data *rgb_data; + struct fwnode_handle *fwnode_mcu_panel; int ret, id; rgb = devm_kzalloc(&pdev->dev, sizeof(*rgb), GFP_KERNEL); @@ -909,17 +952,23 @@ if (id < 0) id = 0; + rgb->data_sync_bypass = of_property_read_bool(dev->of_node, "rockchip,data-sync-bypass"); + + fwnode_mcu_panel = device_get_named_child_node(dev, "mcu-panel"); + if (fwnode_mcu_panel) + rgb->np_mcu_panel = to_of_node(fwnode_mcu_panel); + rgb_data = of_device_get_match_data(dev); if (rgb_data) { - rgb->max_dclk_rate = rgb_data->max_dclk_rate; rgb->funcs = rgb_data->funcs; + if (rgb->np_mcu_panel) + rgb->max_dclk_rate = rgb_data->mcu_max_dclk_rate; + else + rgb->max_dclk_rate = rgb_data->rgb_max_dclk_rate; } rgb->id = id; rgb->dev = dev; platform_set_drvdata(pdev, rgb); - - rgb->data_sync_bypass = - of_property_read_bool(dev->of_node, "rockchip,data-sync-bypass"); if (dev->parent && dev->parent->of_node) { rgb->grf = syscon_node_to_regmap(dev->parent->of_node); @@ -1061,7 +1110,8 @@ }; static const struct rockchip_rgb_data rv1106_rgb = { - .max_dclk_rate = 74250, + .rgb_max_dclk_rate = 74250, + .mcu_max_dclk_rate = 150000, .funcs = &rv1106_rgb_funcs, }; -- Gitblit v1.6.2