From dc50eab76b709d68175a358d6e23a5a3890764d3 Mon Sep 17 00:00:00 2001 From: Daniel Baumann Date: Sat, 18 May 2024 19:39:57 +0200 Subject: Merging upstream version 6.7.7. Signed-off-by: Daniel Baumann --- drivers/gpu/drm/rockchip/cdn-dp-core.c | 2 +- drivers/gpu/drm/rockchip/dw-mipi-dsi-rockchip.c | 23 ++++- drivers/gpu/drm/rockchip/rockchip_drm_vop.c | 52 ++++++---- drivers/gpu/drm/rockchip/rockchip_drm_vop.h | 1 + drivers/gpu/drm/rockchip/rockchip_drm_vop2.c | 83 +++++++++++----- drivers/gpu/drm/rockchip/rockchip_drm_vop2.h | 3 - drivers/gpu/drm/rockchip/rockchip_lvds.c | 2 +- drivers/gpu/drm/rockchip/rockchip_vop2_reg.c | 57 ++++++----- drivers/gpu/drm/rockchip/rockchip_vop_reg.c | 121 ++++++++++++++++++++++-- 9 files changed, 257 insertions(+), 87 deletions(-) (limited to 'drivers/gpu/drm/rockchip') diff --git a/drivers/gpu/drm/rockchip/cdn-dp-core.c b/drivers/gpu/drm/rockchip/cdn-dp-core.c index 3793863c21..21254e4e10 100644 --- a/drivers/gpu/drm/rockchip/cdn-dp-core.c +++ b/drivers/gpu/drm/rockchip/cdn-dp-core.c @@ -1261,7 +1261,7 @@ struct platform_driver cdn_dp_driver = { .driver = { .name = "cdn-dp", .owner = THIS_MODULE, - .of_match_table = of_match_ptr(cdn_dp_dt_ids), + .of_match_table = cdn_dp_dt_ids, .pm = &cdn_dp_pm_ops, }, }; diff --git a/drivers/gpu/drm/rockchip/dw-mipi-dsi-rockchip.c b/drivers/gpu/drm/rockchip/dw-mipi-dsi-rockchip.c index 0100162a73..6396f9324d 100644 --- a/drivers/gpu/drm/rockchip/dw-mipi-dsi-rockchip.c +++ b/drivers/gpu/drm/rockchip/dw-mipi-dsi-rockchip.c @@ -198,6 +198,11 @@ #define RK3568_DSI1_TURNDISABLE BIT(2) #define RK3568_DSI1_FORCERXMODE BIT(0) +#define RV1126_GRF_DSIPHY_CON 0x10220 +#define RV1126_DSI_FORCETXSTOPMODE (0xf << 4) +#define RV1126_DSI_TURNDISABLE BIT(2) +#define RV1126_DSI_FORCERXMODE BIT(0) + #define HIWORD_UPDATE(val, mask) (val | (mask) << 16) enum { @@ -1353,8 +1358,7 @@ static int dw_mipi_dsi_rockchip_probe(struct platform_device *pdev) if (!dsi) return -ENOMEM; - res = platform_get_resource(pdev, IORESOURCE_MEM, 0); - dsi->base = devm_ioremap_resource(dev, res); + dsi->base = devm_platform_get_and_ioremap_resource(pdev, 0, &res); if (IS_ERR(dsi->base)) { DRM_DEV_ERROR(dev, "Unable to get dsi registers\n"); return PTR_ERR(dsi->base); @@ -1651,6 +1655,18 @@ static const struct rockchip_dw_dsi_chip_data rk3568_chip_data[] = { { /* sentinel */ } }; +static const struct rockchip_dw_dsi_chip_data rv1126_chip_data[] = { + { + .reg = 0xffb30000, + .lanecfg1_grf_reg = RV1126_GRF_DSIPHY_CON, + .lanecfg1 = HIWORD_UPDATE(0, RV1126_DSI_TURNDISABLE | + RV1126_DSI_FORCERXMODE | + RV1126_DSI_FORCETXSTOPMODE), + .max_data_lanes = 4, + }, + { /* sentinel */ } +}; + static const struct of_device_id dw_mipi_dsi_rockchip_dt_ids[] = { { .compatible = "rockchip,px30-mipi-dsi", @@ -1664,6 +1680,9 @@ static const struct of_device_id dw_mipi_dsi_rockchip_dt_ids[] = { }, { .compatible = "rockchip,rk3568-mipi-dsi", .data = &rk3568_chip_data, + }, { + .compatible = "rockchip,rv1126-mipi-dsi", + .data = &rv1126_chip_data, }, { /* sentinel */ } }; diff --git a/drivers/gpu/drm/rockchip/rockchip_drm_vop.c b/drivers/gpu/drm/rockchip/rockchip_drm_vop.c index 4b338cb89d..a13473b2d5 100644 --- a/drivers/gpu/drm/rockchip/rockchip_drm_vop.c +++ b/drivers/gpu/drm/rockchip/rockchip_drm_vop.c @@ -280,6 +280,18 @@ static bool has_uv_swapped(uint32_t format) } } +static bool is_fmt_10(uint32_t format) +{ + switch (format) { + case DRM_FORMAT_NV15: + case DRM_FORMAT_NV20: + case DRM_FORMAT_NV30: + return true; + default: + return false; + } +} + static enum vop_data_format vop_convert_format(uint32_t format) { switch (format) { @@ -295,12 +307,15 @@ static enum vop_data_format vop_convert_format(uint32_t format) case DRM_FORMAT_BGR565: return VOP_FMT_RGB565; case DRM_FORMAT_NV12: + case DRM_FORMAT_NV15: case DRM_FORMAT_NV21: return VOP_FMT_YUV420SP; case DRM_FORMAT_NV16: + case DRM_FORMAT_NV20: case DRM_FORMAT_NV61: return VOP_FMT_YUV422SP; case DRM_FORMAT_NV24: + case DRM_FORMAT_NV30: case DRM_FORMAT_NV42: return VOP_FMT_YUV444SP; default: @@ -773,11 +788,6 @@ out: } } -static void vop_plane_destroy(struct drm_plane *plane) -{ - drm_plane_cleanup(plane); -} - static inline bool rockchip_afbc(u64 modifier) { return modifier == ROCKCHIP_AFBC_MOD; @@ -952,7 +962,12 @@ static void vop_plane_atomic_update(struct drm_plane *plane, dsp_sty = dest->y1 + crtc->mode.vtotal - crtc->mode.vsync_start; dsp_st = dsp_sty << 16 | (dsp_stx & 0xffff); - offset = (src->x1 >> 16) * fb->format->cpp[0]; + if (fb->format->char_per_block[0]) + offset = drm_format_info_min_pitch(fb->format, 0, + src->x1 >> 16); + else + offset = (src->x1 >> 16) * fb->format->cpp[0]; + offset += (src->y1 >> 16) * fb->pitches[0]; dma_addr = rk_obj->dma_addr + offset + fb->offsets[0]; @@ -978,6 +993,7 @@ static void vop_plane_atomic_update(struct drm_plane *plane, } VOP_WIN_SET(vop, win, format, format); + VOP_WIN_SET(vop, win, fmt_10, is_fmt_10(fb->format->format)); VOP_WIN_SET(vop, win, yrgb_vir, DIV_ROUND_UP(fb->pitches[0], 4)); VOP_WIN_SET(vop, win, yrgb_mst, dma_addr); VOP_WIN_YUV2YUV_SET(vop, win_yuv2yuv, y2r_en, is_yuv); @@ -987,15 +1003,16 @@ static void vop_plane_atomic_update(struct drm_plane *plane, (new_state->rotation & DRM_MODE_REFLECT_X) ? 1 : 0); if (is_yuv) { - int hsub = fb->format->hsub; - int vsub = fb->format->vsub; - int bpp = fb->format->cpp[1]; - uv_obj = fb->obj[1]; rk_uv_obj = to_rockchip_obj(uv_obj); - offset = (src->x1 >> 16) * bpp / hsub; - offset += (src->y1 >> 16) * fb->pitches[1] / vsub; + if (fb->format->char_per_block[1]) + offset = drm_format_info_min_pitch(fb->format, 1, + src->x1 >> 16); + else + offset = (src->x1 >> 16) * fb->format->cpp[1]; + offset /= fb->format->hsub; + offset += (src->y1 >> 16) * fb->pitches[1] / fb->format->vsub; dma_addr = rk_uv_obj->dma_addr + offset + fb->offsets[1]; VOP_WIN_SET(vop, win, uv_vir, DIV_ROUND_UP(fb->pitches[1], 4)); @@ -1139,7 +1156,7 @@ static const struct drm_plane_helper_funcs plane_helper_funcs = { static const struct drm_plane_funcs vop_plane_funcs = { .update_plane = drm_atomic_helper_update_plane, .disable_plane = drm_atomic_helper_disable_plane, - .destroy = vop_plane_destroy, + .destroy = drm_plane_cleanup, .reset = drm_atomic_helper_plane_reset, .atomic_duplicate_state = drm_atomic_helper_plane_duplicate_state, .atomic_destroy_state = drm_atomic_helper_plane_destroy_state, @@ -1610,11 +1627,6 @@ static const struct drm_crtc_helper_funcs vop_crtc_helper_funcs = { .atomic_disable = vop_crtc_atomic_disable, }; -static void vop_crtc_destroy(struct drm_crtc *crtc) -{ - drm_crtc_cleanup(crtc); -} - static struct drm_crtc_state *vop_crtc_duplicate_state(struct drm_crtc *crtc) { struct rockchip_crtc_state *rockchip_state; @@ -1722,7 +1734,7 @@ vop_crtc_verify_crc_source(struct drm_crtc *crtc, const char *source_name, static const struct drm_crtc_funcs vop_crtc_funcs = { .set_config = drm_atomic_helper_set_config, .page_flip = drm_atomic_helper_page_flip, - .destroy = vop_crtc_destroy, + .destroy = drm_crtc_cleanup, .reset = vop_crtc_reset, .atomic_duplicate_state = vop_crtc_duplicate_state, .atomic_destroy_state = vop_crtc_destroy_state, @@ -1973,7 +1985,7 @@ static void vop_destroy_crtc(struct vop *vop) */ list_for_each_entry_safe(plane, tmp, &drm_dev->mode_config.plane_list, head) - vop_plane_destroy(plane); + drm_plane_cleanup(plane); /* * Destroy CRTC after vop_plane_destroy() since vop_disable_plane() diff --git a/drivers/gpu/drm/rockchip/rockchip_drm_vop.h b/drivers/gpu/drm/rockchip/rockchip_drm_vop.h index 5f56e0597d..4b2daefeb8 100644 --- a/drivers/gpu/drm/rockchip/rockchip_drm_vop.h +++ b/drivers/gpu/drm/rockchip/rockchip_drm_vop.h @@ -186,6 +186,7 @@ struct vop_win_phy { struct vop_reg enable; struct vop_reg gate; struct vop_reg format; + struct vop_reg fmt_10; struct vop_reg rb_swap; struct vop_reg uv_swap; struct vop_reg act_info; diff --git a/drivers/gpu/drm/rockchip/rockchip_drm_vop2.c b/drivers/gpu/drm/rockchip/rockchip_drm_vop2.c index c306806aa3..6862fb146a 100644 --- a/drivers/gpu/drm/rockchip/rockchip_drm_vop2.c +++ b/drivers/gpu/drm/rockchip/rockchip_drm_vop2.c @@ -160,7 +160,6 @@ struct vop2_video_port { struct vop2 *vop2; struct clk *dclk; unsigned int id; - const struct vop2_video_port_regs *regs; const struct vop2_video_port_data *data; struct completion dsp_hold_completion; @@ -283,9 +282,28 @@ static void vop2_win_disable(struct vop2_win *win) vop2_win_write(win, VOP2_WIN_CLUSTER_ENABLE, 0); } +static u32 vop2_get_bpp(const struct drm_format_info *format) +{ + switch (format->format) { + case DRM_FORMAT_YUV420_8BIT: + return 12; + case DRM_FORMAT_YUV420_10BIT: + return 15; + case DRM_FORMAT_VUY101010: + return 30; + default: + return drm_format_info_bpp(format, 0); + } +} + static enum vop2_data_format vop2_convert_format(u32 format) { switch (format) { + case DRM_FORMAT_XRGB2101010: + case DRM_FORMAT_ARGB2101010: + case DRM_FORMAT_XBGR2101010: + case DRM_FORMAT_ABGR2101010: + return VOP2_FMT_XRGB101010; case DRM_FORMAT_XRGB8888: case DRM_FORMAT_ARGB8888: case DRM_FORMAT_XBGR8888: @@ -298,10 +316,19 @@ static enum vop2_data_format vop2_convert_format(u32 format) case DRM_FORMAT_BGR565: return VOP2_FMT_RGB565; case DRM_FORMAT_NV12: + case DRM_FORMAT_NV21: + case DRM_FORMAT_YUV420_8BIT: return VOP2_FMT_YUV420SP; + case DRM_FORMAT_NV15: + case DRM_FORMAT_YUV420_10BIT: + return VOP2_FMT_YUV420SP_10; case DRM_FORMAT_NV16: + case DRM_FORMAT_NV61: return VOP2_FMT_YUV422SP; + case DRM_FORMAT_Y210: + return VOP2_FMT_YUV422SP_10; case DRM_FORMAT_NV24: + case DRM_FORMAT_NV42: return VOP2_FMT_YUV444SP; case DRM_FORMAT_YUYV: case DRM_FORMAT_YVYU: @@ -318,6 +345,11 @@ static enum vop2_data_format vop2_convert_format(u32 format) static enum vop2_afbc_format vop2_convert_afbc_format(u32 format) { switch (format) { + case DRM_FORMAT_XRGB2101010: + case DRM_FORMAT_ARGB2101010: + case DRM_FORMAT_XBGR2101010: + case DRM_FORMAT_ABGR2101010: + return VOP2_AFBC_FMT_ARGB2101010; case DRM_FORMAT_XRGB8888: case DRM_FORMAT_ARGB8888: case DRM_FORMAT_XBGR8888: @@ -329,10 +361,17 @@ static enum vop2_afbc_format vop2_convert_afbc_format(u32 format) case DRM_FORMAT_RGB565: case DRM_FORMAT_BGR565: return VOP2_AFBC_FMT_RGB565; - case DRM_FORMAT_NV12: + case DRM_FORMAT_YUV420_8BIT: return VOP2_AFBC_FMT_YUV420; - case DRM_FORMAT_NV16: + case DRM_FORMAT_YUV420_10BIT: + return VOP2_AFBC_FMT_YUV420_10BIT; + case DRM_FORMAT_YVYU: + case DRM_FORMAT_YUYV: + case DRM_FORMAT_VYUY: + case DRM_FORMAT_UYVY: return VOP2_AFBC_FMT_YUV422; + case DRM_FORMAT_Y210: + return VOP2_AFBC_FMT_YUV422_10BIT; default: return VOP2_AFBC_FMT_INVALID; } @@ -343,6 +382,8 @@ static enum vop2_afbc_format vop2_convert_afbc_format(u32 format) static bool vop2_win_rb_swap(u32 format) { switch (format) { + case DRM_FORMAT_XBGR2101010: + case DRM_FORMAT_ABGR2101010: case DRM_FORMAT_XBGR8888: case DRM_FORMAT_ABGR8888: case DRM_FORMAT_BGR888: @@ -353,21 +394,13 @@ static bool vop2_win_rb_swap(u32 format) } } -static bool vop2_afbc_rb_swap(u32 format) -{ - switch (format) { - case DRM_FORMAT_NV24: - return true; - default: - return false; - } -} - static bool vop2_afbc_uv_swap(u32 format) { switch (format) { - case DRM_FORMAT_NV12: - case DRM_FORMAT_NV16: + case DRM_FORMAT_YUYV: + case DRM_FORMAT_Y210: + case DRM_FORMAT_YUV420_8BIT: + case DRM_FORMAT_YUV420_10BIT: return true; default: return false; @@ -380,6 +413,9 @@ static bool vop2_win_uv_swap(u32 format) case DRM_FORMAT_NV12: case DRM_FORMAT_NV16: case DRM_FORMAT_NV24: + case DRM_FORMAT_NV15: + case DRM_FORMAT_YUYV: + case DRM_FORMAT_UYVY: return true; default: return false; @@ -469,8 +505,8 @@ static bool rockchip_vop2_mod_supported(struct drm_plane *plane, u32 format, return true; if (!rockchip_afbc(plane, modifier)) { - drm_err(vop2->drm, "Unsupported format modifier 0x%llx\n", - modifier); + drm_dbg_kms(vop2->drm, "Unsupported format modifier 0x%llx\n", + modifier); return false; } @@ -483,7 +519,7 @@ static u32 vop2_afbc_transform_offset(struct drm_plane_state *pstate, { struct drm_rect *src = &pstate->src; struct drm_framebuffer *fb = pstate->fb; - u32 bpp = fb->format->cpp[0] * 8; + u32 bpp = vop2_get_bpp(fb->format); u32 vir_width = (fb->pitches[0] << 3) / bpp; u32 width = drm_rect_width(src) >> 16; u32 height = drm_rect_height(src) >> 16; @@ -1081,7 +1117,7 @@ static void vop2_plane_atomic_update(struct drm_plane *plane, struct drm_display_mode *adjusted_mode = &crtc->state->adjusted_mode; struct vop2 *vop2 = win->vop2; struct drm_framebuffer *fb = pstate->fb; - u32 bpp = fb->format->cpp[0] * 8; + u32 bpp = vop2_get_bpp(fb->format); u32 actual_w, actual_h, dsp_w, dsp_h; u32 act_info, dsp_info; u32 format; @@ -1219,7 +1255,6 @@ static void vop2_plane_atomic_update(struct drm_plane *plane, drm_err(vop2->drm, "vp%d %s stride[%d] not 64 pixel aligned\n", vp->id, win->data->name, stride); - rb_swap = vop2_afbc_rb_swap(fb->format->format); uv_swap = vop2_afbc_uv_swap(fb->format->format); /* * This is a workaround for crazy IC design, Cluster @@ -1236,7 +1271,6 @@ static void vop2_plane_atomic_update(struct drm_plane *plane, if (vop2_cluster_window(win)) vop2_win_write(win, VOP2_WIN_AFBC_ENABLE, 1); vop2_win_write(win, VOP2_WIN_AFBC_FORMAT, afbc_format); - vop2_win_write(win, VOP2_WIN_AFBC_RB_SWAP, rb_swap); vop2_win_write(win, VOP2_WIN_AFBC_UV_SWAP, uv_swap); vop2_win_write(win, VOP2_WIN_AFBC_AUTO_GATING_EN, 0); vop2_win_write(win, VOP2_WIN_AFBC_BLOCK_SPLIT_EN, 0); @@ -2251,8 +2285,6 @@ static struct vop2_video_port *find_vp_without_primary(struct vop2 *vop2) return NULL; } -#define NR_LAYERS 6 - static int vop2_create_crtcs(struct vop2 *vop2) { const struct vop2_data *vop2_data = vop2->data; @@ -2273,7 +2305,6 @@ static int vop2_create_crtcs(struct vop2 *vop2) vp = &vop2->vps[i]; vp->vop2 = vop2; vp->id = vp_data->id; - vp->regs = vp_data->regs; vp->data = vp_data; snprintf(dclk_name, sizeof(dclk_name), "dclk_vp%d", vp->id); @@ -2372,7 +2403,7 @@ static int vop2_create_crtcs(struct vop2 *vop2) struct vop2_video_port *vp = &vop2->vps[i]; if (vp->crtc.port) - vp->nlayers = NR_LAYERS / nvps; + vp->nlayers = vop2_data->win_size / nvps; } return 0; @@ -2640,7 +2671,7 @@ static const struct regmap_config vop2_regmap_config = { .max_register = 0x3000, .name = "vop2", .volatile_table = &vop2_volatile_table, - .cache_type = REGCACHE_RBTREE, + .cache_type = REGCACHE_MAPLE, }; static int vop2_bind(struct device *dev, struct device *master, void *data) diff --git a/drivers/gpu/drm/rockchip/rockchip_drm_vop2.h b/drivers/gpu/drm/rockchip/rockchip_drm_vop2.h index f1234a1511..56fd31e052 100644 --- a/drivers/gpu/drm/rockchip/rockchip_drm_vop2.h +++ b/drivers/gpu/drm/rockchip/rockchip_drm_vop2.h @@ -134,16 +134,13 @@ struct vop2_video_port_data { u16 cubic_lut_len; struct vop_rect max_output; const u8 pre_scan_max_dly[4]; - const struct vop2_video_port_regs *regs; unsigned int offset; }; struct vop2_data { u8 nr_vps; - const struct vop2_ctrl *ctrl; const struct vop2_win_data *win; const struct vop2_video_port_data *vp; - const struct vop_csc_table *csc_table; struct vop_rect max_input; struct vop_rect max_output; diff --git a/drivers/gpu/drm/rockchip/rockchip_lvds.c b/drivers/gpu/drm/rockchip/rockchip_lvds.c index 5828593877..f0f47e9abf 100644 --- a/drivers/gpu/drm/rockchip/rockchip_lvds.c +++ b/drivers/gpu/drm/rockchip/rockchip_lvds.c @@ -752,6 +752,6 @@ struct platform_driver rockchip_lvds_driver = { .remove_new = rockchip_lvds_remove, .driver = { .name = "rockchip-lvds", - .of_match_table = of_match_ptr(rockchip_lvds_dt_ids), + .of_match_table = rockchip_lvds_dt_ids, }, }; diff --git a/drivers/gpu/drm/rockchip/rockchip_vop2_reg.c b/drivers/gpu/drm/rockchip/rockchip_vop2_reg.c index 62b573f282..22288ad7f3 100644 --- a/drivers/gpu/drm/rockchip/rockchip_vop2_reg.c +++ b/drivers/gpu/drm/rockchip/rockchip_vop2_reg.c @@ -15,7 +15,11 @@ #include "rockchip_drm_vop2.h" -static const uint32_t formats_win_full_10bit[] = { +static const uint32_t formats_cluster[] = { + DRM_FORMAT_XRGB2101010, + DRM_FORMAT_ARGB2101010, + DRM_FORMAT_XBGR2101010, + DRM_FORMAT_ABGR2101010, DRM_FORMAT_XRGB8888, DRM_FORMAT_ARGB8888, DRM_FORMAT_XBGR8888, @@ -24,12 +28,13 @@ static const uint32_t formats_win_full_10bit[] = { DRM_FORMAT_BGR888, DRM_FORMAT_RGB565, DRM_FORMAT_BGR565, - DRM_FORMAT_NV12, - DRM_FORMAT_NV16, - DRM_FORMAT_NV24, + DRM_FORMAT_YUV420_8BIT, /* yuv420_8bit non-Linear mode only */ + DRM_FORMAT_YUV420_10BIT, /* yuv420_10bit non-Linear mode only */ + DRM_FORMAT_YUYV, /* yuv422_8bit non-Linear mode only*/ + DRM_FORMAT_Y210, /* yuv422_10bit non-Linear mode only */ }; -static const uint32_t formats_win_full_10bit_yuyv[] = { +static const uint32_t formats_rk356x_esmart[] = { DRM_FORMAT_XRGB8888, DRM_FORMAT_ARGB8888, DRM_FORMAT_XBGR8888, @@ -38,14 +43,18 @@ static const uint32_t formats_win_full_10bit_yuyv[] = { DRM_FORMAT_BGR888, DRM_FORMAT_RGB565, DRM_FORMAT_BGR565, - DRM_FORMAT_NV12, - DRM_FORMAT_NV16, - DRM_FORMAT_NV24, - DRM_FORMAT_YVYU, - DRM_FORMAT_VYUY, + DRM_FORMAT_NV12, /* yuv420_8bit linear mode, 2 plane */ + DRM_FORMAT_NV21, /* yuv420_8bit linear mode, 2 plane */ + DRM_FORMAT_NV15, /* yuv420_10bit linear mode, 2 plane, no padding */ + DRM_FORMAT_NV16, /* yuv422_8bit linear mode, 2 plane */ + DRM_FORMAT_NV61, /* yuv422_8bit linear mode, 2 plane */ + DRM_FORMAT_NV24, /* yuv444_8bit linear mode, 2 plane */ + DRM_FORMAT_NV42, /* yuv444_8bit linear mode, 2 plane */ + DRM_FORMAT_YVYU, /* yuv422_8bit[YVYU] linear mode */ + DRM_FORMAT_VYUY, /* yuv422_8bit[VYUY] linear mode */ }; -static const uint32_t formats_win_lite[] = { +static const uint32_t formats_smart[] = { DRM_FORMAT_XRGB8888, DRM_FORMAT_ARGB8888, DRM_FORMAT_XBGR8888, @@ -144,8 +153,8 @@ static const struct vop2_win_data rk3568_vop_win_data[] = { .name = "Smart0-win0", .phys_id = ROCKCHIP_VOP2_SMART0, .base = 0x1c00, - .formats = formats_win_lite, - .nformats = ARRAY_SIZE(formats_win_lite), + .formats = formats_smart, + .nformats = ARRAY_SIZE(formats_smart), .format_modifiers = format_modifiers, .layer_sel_id = 3, .supported_rotations = DRM_MODE_REFLECT_Y, @@ -156,8 +165,8 @@ static const struct vop2_win_data rk3568_vop_win_data[] = { }, { .name = "Smart1-win0", .phys_id = ROCKCHIP_VOP2_SMART1, - .formats = formats_win_lite, - .nformats = ARRAY_SIZE(formats_win_lite), + .formats = formats_smart, + .nformats = ARRAY_SIZE(formats_smart), .format_modifiers = format_modifiers, .base = 0x1e00, .layer_sel_id = 7, @@ -169,8 +178,8 @@ static const struct vop2_win_data rk3568_vop_win_data[] = { }, { .name = "Esmart1-win0", .phys_id = ROCKCHIP_VOP2_ESMART1, - .formats = formats_win_full_10bit_yuyv, - .nformats = ARRAY_SIZE(formats_win_full_10bit_yuyv), + .formats = formats_rk356x_esmart, + .nformats = ARRAY_SIZE(formats_rk356x_esmart), .format_modifiers = format_modifiers, .base = 0x1a00, .layer_sel_id = 6, @@ -182,8 +191,8 @@ static const struct vop2_win_data rk3568_vop_win_data[] = { }, { .name = "Esmart0-win0", .phys_id = ROCKCHIP_VOP2_ESMART0, - .formats = formats_win_full_10bit_yuyv, - .nformats = ARRAY_SIZE(formats_win_full_10bit_yuyv), + .formats = formats_rk356x_esmart, + .nformats = ARRAY_SIZE(formats_rk356x_esmart), .format_modifiers = format_modifiers, .base = 0x1800, .layer_sel_id = 2, @@ -196,8 +205,8 @@ static const struct vop2_win_data rk3568_vop_win_data[] = { .name = "Cluster0-win0", .phys_id = ROCKCHIP_VOP2_CLUSTER0, .base = 0x1000, - .formats = formats_win_full_10bit, - .nformats = ARRAY_SIZE(formats_win_full_10bit), + .formats = formats_cluster, + .nformats = ARRAY_SIZE(formats_cluster), .format_modifiers = format_modifiers_afbc, .layer_sel_id = 0, .supported_rotations = DRM_MODE_ROTATE_90 | DRM_MODE_ROTATE_270 | @@ -211,8 +220,8 @@ static const struct vop2_win_data rk3568_vop_win_data[] = { .name = "Cluster1-win0", .phys_id = ROCKCHIP_VOP2_CLUSTER1, .base = 0x1200, - .formats = formats_win_full_10bit, - .nformats = ARRAY_SIZE(formats_win_full_10bit), + .formats = formats_cluster, + .nformats = ARRAY_SIZE(formats_cluster), .format_modifiers = format_modifiers_afbc, .layer_sel_id = 1, .supported_rotations = DRM_MODE_ROTATE_90 | DRM_MODE_ROTATE_270 | @@ -274,6 +283,6 @@ struct platform_driver vop2_platform_driver = { .remove_new = vop2_remove, .driver = { .name = "rockchip-vop2", - .of_match_table = of_match_ptr(vop2_dt_match), + .of_match_table = vop2_dt_match, }, }; diff --git a/drivers/gpu/drm/rockchip/rockchip_vop_reg.c b/drivers/gpu/drm/rockchip/rockchip_vop_reg.c index 7b28050067..c51ca82320 100644 --- a/drivers/gpu/drm/rockchip/rockchip_vop_reg.c +++ b/drivers/gpu/drm/rockchip/rockchip_vop_reg.c @@ -53,6 +53,26 @@ static const uint32_t formats_win_full[] = { DRM_FORMAT_NV42, }; +static const uint32_t formats_win_full_10[] = { + DRM_FORMAT_XRGB8888, + DRM_FORMAT_ARGB8888, + DRM_FORMAT_XBGR8888, + DRM_FORMAT_ABGR8888, + DRM_FORMAT_RGB888, + DRM_FORMAT_BGR888, + DRM_FORMAT_RGB565, + DRM_FORMAT_BGR565, + DRM_FORMAT_NV12, + DRM_FORMAT_NV21, + DRM_FORMAT_NV16, + DRM_FORMAT_NV61, + DRM_FORMAT_NV24, + DRM_FORMAT_NV42, + DRM_FORMAT_NV15, + DRM_FORMAT_NV20, + DRM_FORMAT_NV30, +}; + static const uint64_t format_modifiers_win_full[] = { DRM_FORMAT_MOD_LINEAR, DRM_FORMAT_MOD_INVALID, @@ -627,11 +647,12 @@ static const struct vop_scl_regs rk3288_win_full_scl = { static const struct vop_win_phy rk3288_win01_data = { .scl = &rk3288_win_full_scl, - .data_formats = formats_win_full, - .nformats = ARRAY_SIZE(formats_win_full), + .data_formats = formats_win_full_10, + .nformats = ARRAY_SIZE(formats_win_full_10), .format_modifiers = format_modifiers_win_full, .enable = VOP_REG(RK3288_WIN0_CTRL0, 0x1, 0), .format = VOP_REG(RK3288_WIN0_CTRL0, 0x7, 1), + .fmt_10 = VOP_REG(RK3288_WIN0_CTRL0, 0x1, 4), .rb_swap = VOP_REG(RK3288_WIN0_CTRL0, 0x1, 12), .uv_swap = VOP_REG(RK3288_WIN0_CTRL0, 0x1, 15), .act_info = VOP_REG(RK3288_WIN0_ACT_INFO, 0x1fff1fff, 0), @@ -936,13 +957,38 @@ static const struct vop_win_yuv2yuv_data rk3399_vop_big_win_yuv2yuv_data[] = { }; -static const struct vop_win_phy rk3399_win01_data = { +static const struct vop_win_phy rk3399_win0_data = { .scl = &rk3288_win_full_scl, - .data_formats = formats_win_full, - .nformats = ARRAY_SIZE(formats_win_full), + .data_formats = formats_win_full_10, + .nformats = ARRAY_SIZE(formats_win_full_10), .format_modifiers = format_modifiers_win_full_afbc, .enable = VOP_REG(RK3288_WIN0_CTRL0, 0x1, 0), .format = VOP_REG(RK3288_WIN0_CTRL0, 0x7, 1), + .fmt_10 = VOP_REG(RK3288_WIN0_CTRL0, 0x1, 4), + .rb_swap = VOP_REG(RK3288_WIN0_CTRL0, 0x1, 12), + .uv_swap = VOP_REG(RK3288_WIN0_CTRL0, 0x1, 15), + .x_mir_en = VOP_REG(RK3288_WIN0_CTRL0, 0x1, 21), + .y_mir_en = VOP_REG(RK3288_WIN0_CTRL0, 0x1, 22), + .act_info = VOP_REG(RK3288_WIN0_ACT_INFO, 0x1fff1fff, 0), + .dsp_info = VOP_REG(RK3288_WIN0_DSP_INFO, 0x0fff0fff, 0), + .dsp_st = VOP_REG(RK3288_WIN0_DSP_ST, 0x1fff1fff, 0), + .yrgb_mst = VOP_REG(RK3288_WIN0_YRGB_MST, 0xffffffff, 0), + .uv_mst = VOP_REG(RK3288_WIN0_CBR_MST, 0xffffffff, 0), + .yrgb_vir = VOP_REG(RK3288_WIN0_VIR, 0x3fff, 0), + .uv_vir = VOP_REG(RK3288_WIN0_VIR, 0x3fff, 16), + .src_alpha_ctl = VOP_REG(RK3288_WIN0_SRC_ALPHA_CTRL, 0xff, 0), + .dst_alpha_ctl = VOP_REG(RK3288_WIN0_DST_ALPHA_CTRL, 0xff, 0), + .channel = VOP_REG(RK3288_WIN0_CTRL2, 0xff, 0), +}; + +static const struct vop_win_phy rk3399_win1_data = { + .scl = &rk3288_win_full_scl, + .data_formats = formats_win_full_10, + .nformats = ARRAY_SIZE(formats_win_full_10), + .format_modifiers = format_modifiers_win_full, + .enable = VOP_REG(RK3288_WIN0_CTRL0, 0x1, 0), + .format = VOP_REG(RK3288_WIN0_CTRL0, 0x7, 1), + .fmt_10 = VOP_REG(RK3288_WIN0_CTRL0, 0x1, 4), .rb_swap = VOP_REG(RK3288_WIN0_CTRL0, 0x1, 12), .uv_swap = VOP_REG(RK3288_WIN0_CTRL0, 0x1, 15), .x_mir_en = VOP_REG(RK3288_WIN0_CTRL0, 0x1, 21), @@ -965,9 +1011,9 @@ static const struct vop_win_phy rk3399_win01_data = { * AFBC on the primary plane. */ static const struct vop_win_data rk3399_vop_win_data[] = { - { .base = 0x00, .phy = &rk3399_win01_data, + { .base = 0x00, .phy = &rk3399_win0_data, .type = DRM_PLANE_TYPE_PRIMARY }, - { .base = 0x40, .phy = &rk3368_win01_data, + { .base = 0x40, .phy = &rk3399_win1_data, .type = DRM_PLANE_TYPE_OVERLAY }, { .base = 0x00, .phy = &rk3368_win23_data, .type = DRM_PLANE_TYPE_OVERLAY }, @@ -1099,11 +1145,11 @@ static const struct vop_intr rk3328_vop_intr = { }; static const struct vop_win_data rk3328_vop_win_data[] = { - { .base = 0xd0, .phy = &rk3368_win01_data, + { .base = 0xd0, .phy = &rk3399_win1_data, .type = DRM_PLANE_TYPE_PRIMARY }, - { .base = 0x1d0, .phy = &rk3368_win01_data, + { .base = 0x1d0, .phy = &rk3399_win1_data, .type = DRM_PLANE_TYPE_OVERLAY }, - { .base = 0x2d0, .phy = &rk3368_win01_data, + { .base = 0x2d0, .phy = &rk3399_win1_data, .type = DRM_PLANE_TYPE_CURSOR }, }; @@ -1120,6 +1166,59 @@ static const struct vop_data rk3328_vop = { .max_output = { 4096, 2160 }, }; +static const struct vop_common rv1126_common = { + .standby = VOP_REG_SYNC(PX30_SYS_CTRL2, 0x1, 1), + .out_mode = VOP_REG(PX30_DSP_CTRL2, 0xf, 16), + .dsp_blank = VOP_REG(PX30_DSP_CTRL2, 0x1, 14), + .dither_down_en = VOP_REG(PX30_DSP_CTRL2, 0x1, 8), + .dither_down_sel = VOP_REG(PX30_DSP_CTRL2, 0x1, 7), + .dither_down_mode = VOP_REG(PX30_DSP_CTRL2, 0x1, 6), + .cfg_done = VOP_REG_SYNC(PX30_REG_CFG_DONE, 0x1, 0), + .dither_up = VOP_REG(PX30_DSP_CTRL2, 0x1, 2), + .dsp_lut_en = VOP_REG(PX30_DSP_CTRL2, 0x1, 5), + .gate_en = VOP_REG(PX30_DSP_CTRL2, 0x1, 0), +}; + +static const struct vop_modeset rv1126_modeset = { + .htotal_pw = VOP_REG(PX30_DSP_HTOTAL_HS_END, 0x0fff0fff, 0), + .hact_st_end = VOP_REG(PX30_DSP_HACT_ST_END, 0x0fff0fff, 0), + .vtotal_pw = VOP_REG(PX30_DSP_VTOTAL_VS_END, 0x0fff0fff, 0), + .vact_st_end = VOP_REG(PX30_DSP_VACT_ST_END, 0x0fff0fff, 0), +}; + +static const struct vop_output rv1126_output = { + .rgb_dclk_pol = VOP_REG(PX30_DSP_CTRL0, 0x1, 1), + .rgb_pin_pol = VOP_REG(PX30_DSP_CTRL0, 0x7, 2), + .rgb_en = VOP_REG(PX30_DSP_CTRL0, 0x1, 0), + .mipi_dclk_pol = VOP_REG(PX30_DSP_CTRL0, 0x1, 25), + .mipi_pin_pol = VOP_REG(PX30_DSP_CTRL0, 0x7, 26), + .mipi_en = VOP_REG(PX30_DSP_CTRL0, 0x1, 24), +}; + +static const struct vop_misc rv1126_misc = { + .global_regdone_en = VOP_REG(PX30_SYS_CTRL2, 0x1, 13), +}; + +static const struct vop_win_data rv1126_vop_win_data[] = { + { .base = 0x00, .phy = &px30_win0_data, + .type = DRM_PLANE_TYPE_OVERLAY }, + { .base = 0x00, .phy = &px30_win2_data, + .type = DRM_PLANE_TYPE_PRIMARY }, +}; + +static const struct vop_data rv1126_vop = { + .version = VOP_VERSION(2, 0xb), + .intr = &px30_intr, + .common = &rv1126_common, + .modeset = &rv1126_modeset, + .output = &rv1126_output, + .misc = &rv1126_misc, + .win = rv1126_vop_win_data, + .win_size = ARRAY_SIZE(rv1126_vop_win_data), + .max_output = { 1920, 1080 }, + .lut_size = 1024, +}; + static const struct of_device_id vop_driver_dt_match[] = { { .compatible = "rockchip,rk3036-vop", .data = &rk3036_vop }, @@ -1147,6 +1246,8 @@ static const struct of_device_id vop_driver_dt_match[] = { .data = &rk3228_vop }, { .compatible = "rockchip,rk3328-vop", .data = &rk3328_vop }, + { .compatible = "rockchip,rv1126-vop", + .data = &rv1126_vop }, {}, }; MODULE_DEVICE_TABLE(of, vop_driver_dt_match); -- cgit v1.2.3