Expose all planes with superset of formats and with no hw pipe static binding. Accordingly, remove checks from atomic_check reflecting the decoupling. Signed-off-by: Sravanthi Kollukuduru <skolluku@xxxxxxxxxxxxxx> --- drivers/gpu/drm/msm/disp/dpu1/dpu_hw_catalog.c | 26 +--- drivers/gpu/drm/msm/disp/dpu1/dpu_hw_catalog.h | 50 +++----- drivers/gpu/drm/msm/disp/dpu1/dpu_kms.c | 17 +-- drivers/gpu/drm/msm/disp/dpu1/dpu_plane.c | 158 ++++--------------------- drivers/gpu/drm/msm/disp/dpu1/dpu_plane.h | 5 +- 5 files changed, 56 insertions(+), 200 deletions(-) diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_catalog.c b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_catalog.c index c0b8116..c2a7c64 100644 --- a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_catalog.c +++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_catalog.c @@ -44,13 +44,6 @@ #define DEFAULT_DPU_LINE_WIDTH 2048 #define DEFAULT_DPU_OUTPUT_LINE_WIDTH 2560 -#define MAX_HORZ_DECIMATION 4 -#define MAX_VERT_DECIMATION 4 - -#define MAX_UPSCALE_RATIO 20 -#define MAX_DOWNSCALE_RATIO 4 -#define SSPP_UNITY_SCALE 1 - #define STRCAT(X, Y) (X Y) /************************************************************* @@ -58,9 +51,12 @@ *************************************************************/ /* DPU top level caps */ static const struct dpu_caps sdm845_dpu_caps = { + .max_sspp_width = DEFAULT_DPU_OUTPUT_LINE_WIDTH, + .max_sspp_pixel_ram_size = DEFAULT_PIXEL_RAM_SIZE, .max_mixer_width = DEFAULT_DPU_OUTPUT_LINE_WIDTH, .max_mixer_blendstages = 0xb, .qseed_type = DPU_SSPP_SCALER_QSEED3, + .csc_type = DPU_SSPP_CSC_10BIT, .ubwc_version = DPU_HW_UBWC_VER_20, .has_src_split = true, .has_dim_layer = true, @@ -128,19 +124,8 @@ * SSPP sub blocks config *************************************************************/ -/* SSPP common configuration */ -static const struct dpu_sspp_blks_common sdm845_sspp_common = { - .maxlinewidth = DEFAULT_DPU_OUTPUT_LINE_WIDTH, - .pixel_ram_size = DEFAULT_PIXEL_RAM_SIZE, - .maxhdeciexp = MAX_HORZ_DECIMATION, - .maxvdeciexp = MAX_VERT_DECIMATION, -}; - #define _VIG_SBLK(num) \ { \ - .common = &sdm845_sspp_common, \ - .maxdwnscale = MAX_DOWNSCALE_RATIO, \ - .maxupscale = MAX_UPSCALE_RATIO, \ .src_blk = {.name = STRCAT("sspp_src_", num), \ .id = DPU_SSPP_SRC, .base = 0x00, .len = 0x150,}, \ .scaler_blk = {.name = STRCAT("sspp_scaler", num), \ @@ -149,17 +134,12 @@ .csc_blk = {.name = STRCAT("sspp_csc", num), \ .id = DPU_SSPP_CSC_10BIT, \ .base = 0x1a00, .len = 0x100,}, \ - .format_list = plane_formats_yuv, \ } #define _DMA_SBLK(num) \ { \ - .common = &sdm845_sspp_common, \ - .maxdwnscale = SSPP_UNITY_SCALE, \ - .maxupscale = SSPP_UNITY_SCALE, \ .src_blk = {.name = STRCAT("sspp_src_", num), \ .id = DPU_SSPP_SRC, .base = 0x00, .len = 0x150,}, \ - .format_list = plane_formats, \ } static const struct dpu_sspp_sub_blks sdm845_vig_sblk_0 = _VIG_SBLK("0"); diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_catalog.h b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_catalog.h index 1b04448..68644db 100644 --- a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_catalog.h +++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_catalog.h @@ -63,6 +63,10 @@ #define CRTC_DUAL_MIXERS 2 +#define MAX_UPSCALE_RATIO 20 +#define MAX_DOWNSCALE_RATIO 4 +#define SSPP_UNITY_SCALE 1 + #define MAX_XIN_COUNT 16 /** @@ -290,19 +294,26 @@ struct dpu_qos_lut_tbl { /** * struct dpu_caps - define DPU capabilities - * @max_mixer_width max layer mixer line width support. - * @max_mixer_blendstages max layer mixer blend stages or + * @max_sspp_width max: pixelwidth supported by this pipe + * @max_sspp_pixel_ram_size: size of latency hiding and + * de-tiling buffer in bytes + * @max_mixer_width: max layer mixer line width support + * @max_mixer_blendstages: max layer mixer blend stages or * supported z order - * @qseed_type qseed2 or qseed3 support. - * @ubwc_version UBWC feature version (0x0 for not supported) - * @has_src_split source split feature status - * @has_dim_layer dim layer feature status - * @has_idle_pc indicate if idle power collapse feature is supported + * @qseed_type: qseed2 or qseed3 support + * @csc_type: csc or csc_10bit support + * @ubwc_version: UBWC feature version (0x0 for not supported) + * @has_src_split: source split feature status + * @has_dim_layer: dim layer feature status + * @has_idle_pc: indicate if idle power collapse feature is supported */ struct dpu_caps { + u32 max_sspp_width; + u32 max_sspp_pixel_ram_size; u32 max_mixer_width; u32 max_mixer_blendstages; u32 qseed_type; + u32 csc_type; u32 ubwc_version; bool has_src_split; bool has_dim_layer; @@ -310,28 +321,9 @@ struct dpu_caps { }; /** - * struct dpu_sspp_blks_common : SSPP sub-blocks common configuration - * @maxwidth: max pixelwidth supported by this pipe - * @pixel_ram_size: size of latency hiding and de-tiling buffer in bytes - * @maxhdeciexp: max horizontal decimation supported by this pipe - * (max is 2^value) - * @maxvdeciexp: max vertical decimation supported by this pipe - * (max is 2^value) - */ -struct dpu_sspp_blks_common { - u32 maxlinewidth; - u32 pixel_ram_size; - u32 maxhdeciexp; - u32 maxvdeciexp; -}; - -/** * struct dpu_sspp_sub_blks : SSPP sub-blocks - * common: Pointer to common configurations shared by sub blocks * @creq_vblank: creq priority during vertical blanking * @danger_vblank: danger priority during vertical blanking - * @maxdwnscale: max downscale ratio supported(without DECIMATION) - * @maxupscale: maxupscale ratio supported * @max_per_pipe_bw: maximum allowable bandwidth of this pipe in kBps * @src_blk: * @scaler_blk: @@ -340,14 +332,10 @@ struct dpu_sspp_blks_common { * @memcolor: * @pcc_blk: * @igc_blk: - * @format_list: Pointer to list of supported formats */ struct dpu_sspp_sub_blks { - const struct dpu_sspp_blks_common *common; u32 creq_vblank; u32 danger_vblank; - u32 maxdwnscale; - u32 maxupscale; u32 max_per_pipe_bw; struct dpu_src_blk src_blk; struct dpu_scaler_blk scaler_blk; @@ -356,8 +344,6 @@ struct dpu_sspp_sub_blks { struct dpu_pp_blk memcolor_blk; struct dpu_pp_blk pcc_blk; struct dpu_pp_blk igc_blk; - - const struct dpu_format_extended *format_list; }; /** diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_kms.c b/drivers/gpu/drm/msm/disp/dpu1/dpu_kms.c index 8e2e582..bef4e71 100644 --- a/drivers/gpu/drm/msm/disp/dpu1/dpu_kms.c +++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_kms.c @@ -616,13 +616,16 @@ static int _dpu_kms_drm_obj_init(struct dpu_kms *dpu_kms) /* Create the planes */ for (i = 0; i < catalog->sspp_count; i++) { - bool primary = true; + enum drm_plane_type type; - if (catalog->sspp[i].features & BIT(DPU_SSPP_CURSOR) - || primary_planes_idx >= max_crtc_count) - primary = false; + if (catalog->sspp[i].features & BIT(DPU_SSPP_CURSOR)) + type = DRM_PLANE_TYPE_CURSOR; + else if (primary_planes_idx < max_crtc_count) + type = DRM_PLANE_TYPE_PRIMARY; + else + type = DRM_PLANE_TYPE_OVERLAY; - plane = dpu_plane_init(dev, catalog->sspp[i].id, primary, + plane = dpu_plane_init(dev, catalog->sspp[i].id, type, (1UL << max_crtc_count) - 1); if (IS_ERR(plane)) { DPU_ERROR("dpu_plane_init failed\n"); @@ -631,9 +634,9 @@ static int _dpu_kms_drm_obj_init(struct dpu_kms *dpu_kms) } priv->planes[priv->num_planes++] = plane; - if (primary) + if (type == DRM_PLANE_TYPE_PRIMARY) primary_planes[primary_planes_idx++] = plane; - if (catalog->sspp[i].features & BIT(DPU_SSPP_CURSOR)) + if (type == DRM_PLANE_TYPE_CURSOR) cursor_planes[cursor_planes_idx++] = plane; } diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_plane.c b/drivers/gpu/drm/msm/disp/dpu1/dpu_plane.c index 0fd05de..be40a2c 100644 --- a/drivers/gpu/drm/msm/disp/dpu1/dpu_plane.c +++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_plane.c @@ -151,6 +151,7 @@ static bool dpu_plane_sspp_enabled(struct drm_plane_state *state) static inline int _dpu_plane_calc_fill_level(struct drm_plane *plane, const struct dpu_format *fmt, u32 src_width) { + struct dpu_kms *kms; struct dpu_plane *pdpu; struct dpu_plane_state *pstate; u32 fixed_buff_size; @@ -163,7 +164,9 @@ static inline int _dpu_plane_calc_fill_level(struct drm_plane *plane, pdpu = to_dpu_plane(plane); pstate = to_dpu_plane_state(plane->state); - fixed_buff_size = pdpu->pipe_sblk->common->pixel_ram_size; + + kms = _dpu_plane_get_kms(&pdpu->base); + fixed_buff_size = kms->catalog->caps->max_sspp_pixel_ram_size; if (fmt->fetch_planes == DPU_PLANE_PSEUDO_PLANAR) { if (fmt->chroma_sample == DPU_CHROMA_420) { @@ -915,12 +918,14 @@ static int dpu_plane_sspp_atomic_check(struct drm_plane *plane, struct drm_plane_state *state) { int ret = 0; + struct dpu_kms *kms; struct dpu_plane *pdpu; struct dpu_plane_state *pstate; const struct dpu_format *fmt; struct dpu_rect src, dst; uint32_t max_upscale, max_downscale, min_src_size, max_linewidth; bool q16_data = true; + uint32_t caps = 0; if (!plane || !state) { DPU_ERROR("invalid arg(s), plane %d state %d\n", @@ -932,11 +937,8 @@ static int dpu_plane_sspp_atomic_check(struct drm_plane *plane, pdpu = to_dpu_plane(plane); pstate = to_dpu_plane_state(state); - if (!pdpu->pipe_sblk) { - DPU_ERROR_PLANE(pdpu, "invalid catalog\n"); - ret = -EINVAL; - goto exit; - } + kms = _dpu_plane_get_kms(&pdpu->base); + max_linewidth = kms->catalog->caps->max_sspp_width; /* src values are in Q16 fixed point, convert to integer */ POPULATE_RECT(&src, state->src_x, state->src_y, state->src_w, @@ -944,10 +946,6 @@ static int dpu_plane_sspp_atomic_check(struct drm_plane *plane, POPULATE_RECT(&dst, state->crtc_x, state->crtc_y, state->crtc_w, state->crtc_h, !q16_data); - max_upscale = pdpu->pipe_sblk->maxupscale; - max_downscale = pdpu->pipe_sblk->maxdwnscale; - max_linewidth = pdpu->pipe_sblk->common->maxlinewidth; - DPU_DEBUG_PLANE(pdpu, "check %d -> %d\n", dpu_plane_enabled(plane->state), dpu_plane_enabled(state)); @@ -956,18 +954,19 @@ static int dpu_plane_sspp_atomic_check(struct drm_plane *plane, fmt = to_dpu_format(msm_framebuffer_format(state->fb)); - min_src_size = DPU_FORMAT_IS_YUV(fmt) ? 2 : 1; + if (DPU_FORMAT_IS_YUV(fmt)) + caps |= BIT(kms->catalog->caps->qseed_type) | + BIT(kms->catalog->caps->csc_type); - if (DPU_FORMAT_IS_YUV(fmt) && - (!(pdpu->features & DPU_SSPP_SCALER) || - !(pdpu->features & (BIT(DPU_SSPP_CSC) - | BIT(DPU_SSPP_CSC_10BIT))))) { - DPU_ERROR_PLANE(pdpu, - "plane doesn't have scaler/csc for yuv\n"); - ret = -EINVAL; + if ((src.w != dst.w) || (src.h != dst.h)) + caps |= BIT(kms->catalog->caps->qseed_type); + + max_upscale = (caps & DPU_SSPP_SCALER) ? MAX_UPSCALE_RATIO : 1; + max_downscale = (caps & DPU_SSPP_SCALER) ? MAX_DOWNSCALE_RATIO : 1; + min_src_size = DPU_FORMAT_IS_YUV(fmt) ? 2 : 1; /* check src bounds */ - } else if (state->fb->width > MAX_IMG_WIDTH || + if (state->fb->width > MAX_IMG_WIDTH || state->fb->height > MAX_IMG_HEIGHT || src.w < min_src_size || src.h < min_src_size || CHECK_LAYER_BOUNDS(src.x, src.w, state->fb->width) || @@ -989,14 +988,6 @@ static int dpu_plane_sspp_atomic_check(struct drm_plane *plane, dst.x, dst.y, dst.w, dst.h); ret = -EINVAL; - /* decimation validation */ - } else if (!(pdpu->features & DPU_SSPP_SCALER) && - ((src.w != dst.w) || (src.h != dst.h))) { - DPU_ERROR_PLANE(pdpu, - "pipe doesn't support scaling %ux%u->%ux%u\n", - src.w, src.h, dst.w, dst.h); - ret = -EINVAL; - /* check decimated source width */ } else if (src.w > max_linewidth) { DPU_ERROR_PLANE(pdpu, @@ -1292,9 +1283,6 @@ static void dpu_plane_destroy(struct drm_plane *plane) /* this will destroy the states as well */ drm_plane_cleanup(plane); - if (pdpu->pipe_hw) - dpu_hw_sspp_destroy(pdpu->pipe_hw); - kfree(pdpu); } } @@ -1479,8 +1467,6 @@ static int _dpu_plane_init_debugfs(struct drm_plane *plane) struct dpu_plane *pdpu; struct dpu_kms *kms; struct msm_drm_private *priv; - const struct dpu_sspp_sub_blks *sblk = 0; - const struct dpu_sspp_cfg *cfg = 0; if (!plane || !plane->dev) { DPU_ERROR("invalid arguments\n"); @@ -1496,14 +1482,6 @@ static int _dpu_plane_init_debugfs(struct drm_plane *plane) kms = to_dpu_kms(priv->kms); pdpu = to_dpu_plane(plane); - if (pdpu && pdpu->pipe_hw) - cfg = pdpu->pipe_hw->cap; - if (cfg) - sblk = cfg->sblk; - - if (!sblk) - return 0; - /* create overall sub-directory for the pipe */ pdpu->debugfs_root = debugfs_create_dir(pdpu->pipe_name, @@ -1512,60 +1490,6 @@ static int _dpu_plane_init_debugfs(struct drm_plane *plane) if (!pdpu->debugfs_root) return -ENOMEM; - /* don't error check these */ - debugfs_create_x32("features", 0600, - pdpu->debugfs_root, &pdpu->features); - - /* add register dump support */ - dpu_debugfs_setup_regset32(&pdpu->debugfs_src, - sblk->src_blk.base + cfg->base, - sblk->src_blk.len, - kms); - dpu_debugfs_create_regset32("src_blk", 0400, - pdpu->debugfs_root, &pdpu->debugfs_src); - - if (cfg->features & BIT(DPU_SSPP_SCALER_QSEED3) || - cfg->features & BIT(DPU_SSPP_SCALER_QSEED2)) { - dpu_debugfs_setup_regset32(&pdpu->debugfs_scaler, - sblk->scaler_blk.base + cfg->base, - sblk->scaler_blk.len, - kms); - dpu_debugfs_create_regset32("scaler_blk", 0400, - pdpu->debugfs_root, - &pdpu->debugfs_scaler); - debugfs_create_bool("default_scaling", - 0600, - pdpu->debugfs_root, - &pdpu->debugfs_default_scale); - } - - if (cfg->features & BIT(DPU_SSPP_CSC) || - cfg->features & BIT(DPU_SSPP_CSC_10BIT)) { - dpu_debugfs_setup_regset32(&pdpu->debugfs_csc, - sblk->csc_blk.base + cfg->base, - sblk->csc_blk.len, - kms); - dpu_debugfs_create_regset32("csc_blk", 0400, - pdpu->debugfs_root, &pdpu->debugfs_csc); - } - - debugfs_create_u32("xin_id", - 0400, - pdpu->debugfs_root, - (u32 *) &cfg->xin_id); - debugfs_create_u32("clk_ctrl", - 0400, - pdpu->debugfs_root, - (u32 *) &cfg->clk_ctrl); - debugfs_create_x32("creq_vblank", - 0600, - pdpu->debugfs_root, - (u32 *) &sblk->creq_vblank); - debugfs_create_x32("danger_vblank", - 0600, - pdpu->debugfs_root, - (u32 *) &sblk->danger_vblank); - debugfs_create_file("disable_danger", 0600, pdpu->debugfs_root, @@ -1629,14 +1553,13 @@ enum dpu_sspp dpu_plane_pipe(struct drm_plane *plane) /* initialize plane */ struct drm_plane *dpu_plane_init(struct drm_device *dev, - uint32_t pipe, bool primary_plane, + uint32_t pipe, enum drm_plane_type type, unsigned long possible_crtcs) { struct drm_plane *plane = NULL; struct dpu_plane *pdpu; struct msm_drm_private *priv; struct dpu_kms *kms; - enum drm_plane_type type; int zpos_max = DPU_ZPOS_MAX; int ret = -EINVAL; @@ -1670,54 +1593,22 @@ struct drm_plane *dpu_plane_init(struct drm_device *dev, goto exit; } - /* cache local stuff for later */ plane = &pdpu->base; - pdpu->pipe = pipe; - - /* initialize underlying h/w driver */ - pdpu->pipe_hw = dpu_hw_sspp_init(pipe, kms->mmio, kms->catalog); - if (IS_ERR(pdpu->pipe_hw)) { - DPU_ERROR("[%u]SSPP init failed\n", pipe); - ret = PTR_ERR(pdpu->pipe_hw); - goto clean_plane; - } else if (!pdpu->pipe_hw->cap || !pdpu->pipe_hw->cap->sblk) { - DPU_ERROR("[%u]SSPP init returned invalid cfg\n", pipe); - goto clean_sspp; - } - - /* cache features mask for later */ - pdpu->features = pdpu->pipe_hw->cap->features; - pdpu->pipe_sblk = pdpu->pipe_hw->cap->sblk; - if (!pdpu->pipe_sblk) { - DPU_ERROR("[%u]invalid sblk\n", pipe); - goto clean_sspp; - } - - pdpu->nformats = dpu_populate_formats( - pdpu->pipe_sblk->format_list, - pdpu->formats, - 0, + pdpu->nformats = dpu_populate_formats(plane_formats_yuv, + pdpu->formats, 0, ARRAY_SIZE(pdpu->formats)); if (!pdpu->nformats) { DPU_ERROR("[%u]no valid formats for plane\n", pipe); - goto clean_sspp; + goto clean_plane; } - if (pdpu->features & BIT(DPU_SSPP_CURSOR)) - type = DRM_PLANE_TYPE_CURSOR; - else if (primary_plane) - type = DRM_PLANE_TYPE_PRIMARY; - else - type = DRM_PLANE_TYPE_OVERLAY; ret = drm_universal_plane_init(dev, plane, 0xff, &dpu_plane_funcs, pdpu->formats, pdpu->nformats, NULL, type, NULL); if (ret) - goto clean_sspp; - - pdpu->catalog = kms->catalog; + goto clean_plane; if (kms->catalog->mixer_count && kms->catalog->mixer[0].sblk->maxblendstages) { @@ -1742,9 +1633,6 @@ struct drm_plane *dpu_plane_init(struct drm_device *dev, pipe, plane->base.id); return plane; -clean_sspp: - if (pdpu && pdpu->pipe_hw) - dpu_hw_sspp_destroy(pdpu->pipe_hw); clean_plane: kfree(pdpu); exit: diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_plane.h b/drivers/gpu/drm/msm/disp/dpu1/dpu_plane.h index 3795a336..e0688895 100644 --- a/drivers/gpu/drm/msm/disp/dpu1/dpu_plane.h +++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_plane.h @@ -102,12 +102,11 @@ void dpu_plane_get_ctl_flush(struct drm_plane *plane, struct dpu_hw_ctl *ctl, * dpu_plane_init - create new dpu plane for the given pipe * @dev: Pointer to DRM device * @pipe: dpu hardware pipe identifier - * @primary_plane: true if this pipe is primary plane for crtc + * @type: plane type - PRIMARY/CURSOR/OVERLAY * @possible_crtcs: bitmask of crtc that can be attached to the given pipe - * */ struct drm_plane *dpu_plane_init(struct drm_device *dev, - uint32_t pipe, bool primary_plane, + uint32_t pipe, enum drm_plane_type type, unsigned long possible_crtcs); /** -- The Qualcomm Innovation Center, Inc. is a member of the Code Aurora Forum, a Linux Foundation Collaborative Project -- To unsubscribe from this list: send the line "unsubscribe linux-arm-msm" in the body of a message to majordomo@xxxxxxxxxxxxxxx More majordomo info at http://vger.kernel.org/majordomo-info.html