Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

drm/msm/dpu: split dpu_plane_atomic_check()

Split dpu_plane_atomic_check() function into two pieces:

dpu_plane_atomic_check_nosspp() performing generic checks on the pstate,
without touching the associated SSPP blocks,

and

dpu_plane_atomic_check_sspp(), which takes into account used SSPPs.

Signed-off-by: Dmitry Baryshkov <dmitry.baryshkov@linaro.org>
Reviewed-by: Abhinav Kumar <quic_abhinavk@quicinc.com>
Patchwork: https://patchwork.freedesktop.org/patch/621484/
Link: https://lore.kernel.org/r/20241025-dpu-virtual-wide-v6-5-0310fd519765@linaro.org

+112 -66
+112 -66
drivers/gpu/drm/msm/disp/dpu1/dpu_plane.c
··· 780 780 #define MAX_UPSCALE_RATIO 20 781 781 #define MAX_DOWNSCALE_RATIO 4 782 782 783 - static int dpu_plane_atomic_check(struct drm_plane *plane, 784 - struct drm_atomic_state *state) 783 + static int dpu_plane_atomic_check_nosspp(struct drm_plane *plane, 784 + struct drm_plane_state *new_plane_state, 785 + const struct drm_crtc_state *crtc_state) 785 786 { 786 - struct drm_plane_state *new_plane_state = drm_atomic_get_new_plane_state(state, 787 - plane); 788 787 int i, ret = 0, min_scale, max_scale; 789 788 struct dpu_plane *pdpu = to_dpu_plane(plane); 790 789 struct dpu_kms *kms = _dpu_plane_get_kms(&pdpu->base); 791 790 u64 max_mdp_clk_rate = kms->perf.max_core_clk_rate; 792 791 struct dpu_plane_state *pstate = to_dpu_plane_state(new_plane_state); 793 - struct dpu_sw_pipe *pipe = &pstate->pipe; 794 - struct dpu_sw_pipe *r_pipe = &pstate->r_pipe; 795 - const struct drm_crtc_state *crtc_state = NULL; 796 - const struct msm_format *fmt; 797 792 struct dpu_sw_pipe_cfg *pipe_cfg = &pstate->pipe_cfg; 798 793 struct dpu_sw_pipe_cfg *r_pipe_cfg = &pstate->r_pipe_cfg; 799 794 struct drm_rect fb_rect = { 0 }; 800 795 uint32_t max_linewidth; 801 - unsigned int rotation; 802 - uint32_t supported_rotations; 803 - const struct dpu_sspp_cfg *pipe_hw_caps; 804 - const struct dpu_sspp_sub_blks *sblk; 805 796 806 - if (new_plane_state->crtc) 807 - crtc_state = drm_atomic_get_new_crtc_state(state, 808 - new_plane_state->crtc); 809 - 810 - pipe->sspp = dpu_rm_get_sspp(&kms->rm, pdpu->pipe); 811 - r_pipe->sspp = NULL; 812 - 813 - if (!pipe->sspp) 814 - return -EINVAL; 815 - 816 - pipe_hw_caps = pipe->sspp->cap; 817 - sblk = pipe->sspp->cap->sblk; 818 - 819 - if (sblk->scaler_blk.len) { 820 - min_scale = FRAC_16_16(1, MAX_UPSCALE_RATIO); 821 - max_scale = MAX_DOWNSCALE_RATIO << 16; 822 - } else { 823 - min_scale = DRM_PLANE_NO_SCALING; 824 - max_scale = DRM_PLANE_NO_SCALING; 825 - } 797 + min_scale = FRAC_16_16(1, MAX_UPSCALE_RATIO); 798 + max_scale = MAX_DOWNSCALE_RATIO << 16; 826 799 827 800 ret = drm_atomic_helper_check_plane_state(new_plane_state, crtc_state, 828 801 min_scale, ··· 807 834 } 808 835 if (!new_plane_state->visible) 809 836 return 0; 810 - 811 - pipe->multirect_index = DPU_SSPP_RECT_SOLO; 812 - pipe->multirect_mode = DPU_SSPP_MULTIRECT_NONE; 813 - r_pipe->multirect_index = DPU_SSPP_RECT_SOLO; 814 - r_pipe->multirect_mode = DPU_SSPP_MULTIRECT_NONE; 815 837 816 838 pstate->stage = DPU_STAGE_0 + pstate->base.normalized_zpos; 817 839 if (pstate->stage >= pdpu->catalog->caps->max_mixer_blendstages) { ··· 841 873 if (pstate->layout.plane_pitch[i] > DPU_SSPP_MAX_PITCH_SIZE) 842 874 return -E2BIG; 843 875 844 - fmt = msm_framebuffer_format(new_plane_state->fb); 845 - 846 876 max_linewidth = pdpu->catalog->caps->max_linewidth; 847 877 848 878 drm_rect_rotate(&pipe_cfg->src_rect, ··· 849 883 850 884 if ((drm_rect_width(&pipe_cfg->src_rect) > max_linewidth) || 851 885 _dpu_plane_calc_clk(&crtc_state->adjusted_mode, pipe_cfg) > max_mdp_clk_rate) { 886 + if (drm_rect_width(&pipe_cfg->src_rect) > 2 * max_linewidth) { 887 + DPU_DEBUG_PLANE(pdpu, "invalid src " DRM_RECT_FMT " line:%u\n", 888 + DRM_RECT_ARG(&pipe_cfg->src_rect), max_linewidth); 889 + return -E2BIG; 890 + } 891 + 892 + *r_pipe_cfg = *pipe_cfg; 893 + pipe_cfg->src_rect.x2 = (pipe_cfg->src_rect.x1 + pipe_cfg->src_rect.x2) >> 1; 894 + pipe_cfg->dst_rect.x2 = (pipe_cfg->dst_rect.x1 + pipe_cfg->dst_rect.x2) >> 1; 895 + r_pipe_cfg->src_rect.x1 = pipe_cfg->src_rect.x2; 896 + r_pipe_cfg->dst_rect.x1 = pipe_cfg->dst_rect.x2; 897 + } else { 898 + memset(r_pipe_cfg, 0, sizeof(*r_pipe_cfg)); 899 + } 900 + 901 + drm_rect_rotate_inv(&pipe_cfg->src_rect, 902 + new_plane_state->fb->width, new_plane_state->fb->height, 903 + new_plane_state->rotation); 904 + if (r_pipe_cfg->src_rect.x1 != 0) 905 + drm_rect_rotate_inv(&r_pipe_cfg->src_rect, 906 + new_plane_state->fb->width, new_plane_state->fb->height, 907 + new_plane_state->rotation); 908 + 909 + pstate->needs_qos_remap = drm_atomic_crtc_needs_modeset(crtc_state); 910 + 911 + return 0; 912 + } 913 + 914 + static int dpu_plane_atomic_check_sspp(struct drm_plane *plane, 915 + struct drm_atomic_state *state, 916 + const struct drm_crtc_state *crtc_state) 917 + { 918 + struct drm_plane_state *new_plane_state = 919 + drm_atomic_get_new_plane_state(state, plane); 920 + struct dpu_plane *pdpu = to_dpu_plane(plane); 921 + struct dpu_plane_state *pstate = to_dpu_plane_state(new_plane_state); 922 + struct dpu_sw_pipe *pipe = &pstate->pipe; 923 + struct dpu_sw_pipe *r_pipe = &pstate->r_pipe; 924 + const struct msm_format *fmt; 925 + struct dpu_sw_pipe_cfg *pipe_cfg = &pstate->pipe_cfg; 926 + struct dpu_sw_pipe_cfg *r_pipe_cfg = &pstate->r_pipe_cfg; 927 + uint32_t max_linewidth; 928 + unsigned int rotation; 929 + uint32_t supported_rotations; 930 + const struct dpu_sspp_cfg *pipe_hw_caps; 931 + const struct dpu_sspp_sub_blks *sblk; 932 + int ret = 0; 933 + 934 + pipe_hw_caps = pipe->sspp->cap; 935 + sblk = pipe->sspp->cap->sblk; 936 + 937 + /* 938 + * We already have verified scaling against platform limitations. 939 + * Now check if the SSPP supports scaling at all. 940 + */ 941 + if (!sblk->scaler_blk.len && 942 + ((drm_rect_width(&new_plane_state->src) >> 16 != 943 + drm_rect_width(&new_plane_state->dst)) || 944 + (drm_rect_height(&new_plane_state->src) >> 16 != 945 + drm_rect_height(&new_plane_state->dst)))) 946 + return -ERANGE; 947 + 948 + fmt = msm_framebuffer_format(new_plane_state->fb); 949 + 950 + max_linewidth = pdpu->catalog->caps->max_linewidth; 951 + 952 + ret = dpu_plane_atomic_check_pipe(pdpu, pipe, pipe_cfg, fmt, 953 + &crtc_state->adjusted_mode); 954 + if (ret) 955 + return ret; 956 + 957 + if (drm_rect_width(&r_pipe_cfg->src_rect) != 0) { 852 958 /* 853 959 * In parallel multirect case only the half of the usual width 854 960 * is supported for tiled formats. If we are here, we know that ··· 930 892 if (MSM_FORMAT_IS_UBWC(fmt) && 931 893 drm_rect_width(&pipe_cfg->src_rect) > max_linewidth) { 932 894 DPU_DEBUG_PLANE(pdpu, "invalid src " DRM_RECT_FMT " line:%u, tiled format\n", 933 - DRM_RECT_ARG(&pipe_cfg->src_rect), max_linewidth); 934 - return -E2BIG; 935 - } 936 - 937 - if (drm_rect_width(&pipe_cfg->src_rect) > 2 * max_linewidth) { 938 - DPU_DEBUG_PLANE(pdpu, "invalid src " DRM_RECT_FMT " line:%u\n", 939 895 DRM_RECT_ARG(&pipe_cfg->src_rect), max_linewidth); 940 896 return -E2BIG; 941 897 } ··· 955 923 r_pipe->multirect_index = DPU_SSPP_RECT_1; 956 924 r_pipe->multirect_mode = DPU_SSPP_MULTIRECT_PARALLEL; 957 925 958 - *r_pipe_cfg = *pipe_cfg; 959 - pipe_cfg->src_rect.x2 = (pipe_cfg->src_rect.x1 + pipe_cfg->src_rect.x2) >> 1; 960 - pipe_cfg->dst_rect.x2 = (pipe_cfg->dst_rect.x1 + pipe_cfg->dst_rect.x2) >> 1; 961 - r_pipe_cfg->src_rect.x1 = pipe_cfg->src_rect.x2; 962 - r_pipe_cfg->dst_rect.x1 = pipe_cfg->dst_rect.x2; 963 - } 964 - 965 - drm_rect_rotate_inv(&pipe_cfg->src_rect, 966 - new_plane_state->fb->width, new_plane_state->fb->height, 967 - new_plane_state->rotation); 968 - if (r_pipe->sspp) 969 - drm_rect_rotate_inv(&r_pipe_cfg->src_rect, 970 - new_plane_state->fb->width, new_plane_state->fb->height, 971 - new_plane_state->rotation); 972 - 973 - ret = dpu_plane_atomic_check_pipe(pdpu, pipe, pipe_cfg, fmt, &crtc_state->adjusted_mode); 974 - if (ret) 975 - return ret; 976 - 977 - if (r_pipe->sspp) { 978 926 ret = dpu_plane_atomic_check_pipe(pdpu, r_pipe, r_pipe_cfg, fmt, 979 927 &crtc_state->adjusted_mode); 980 928 if (ret) ··· 977 965 } 978 966 979 967 pstate->rotation = rotation; 980 - pstate->needs_qos_remap = drm_atomic_crtc_needs_modeset(crtc_state); 981 968 982 969 return 0; 970 + } 971 + 972 + static int dpu_plane_atomic_check(struct drm_plane *plane, 973 + struct drm_atomic_state *state) 974 + { 975 + struct drm_plane_state *new_plane_state = drm_atomic_get_new_plane_state(state, 976 + plane); 977 + int ret = 0; 978 + struct dpu_plane *pdpu = to_dpu_plane(plane); 979 + struct dpu_plane_state *pstate = to_dpu_plane_state(new_plane_state); 980 + struct dpu_kms *dpu_kms = _dpu_plane_get_kms(plane); 981 + struct dpu_sw_pipe *pipe = &pstate->pipe; 982 + struct dpu_sw_pipe *r_pipe = &pstate->r_pipe; 983 + const struct drm_crtc_state *crtc_state = NULL; 984 + 985 + if (new_plane_state->crtc) 986 + crtc_state = drm_atomic_get_new_crtc_state(state, 987 + new_plane_state->crtc); 988 + 989 + pipe->sspp = dpu_rm_get_sspp(&dpu_kms->rm, pdpu->pipe); 990 + r_pipe->sspp = NULL; 991 + 992 + ret = dpu_plane_atomic_check_nosspp(plane, new_plane_state, crtc_state); 993 + if (ret) 994 + return ret; 995 + 996 + if (!new_plane_state->visible) 997 + return 0; 998 + 999 + pipe->multirect_index = DPU_SSPP_RECT_SOLO; 1000 + pipe->multirect_mode = DPU_SSPP_MULTIRECT_NONE; 1001 + r_pipe->multirect_index = DPU_SSPP_RECT_SOLO; 1002 + r_pipe->multirect_mode = DPU_SSPP_MULTIRECT_NONE; 1003 + 1004 + return dpu_plane_atomic_check_sspp(plane, state, crtc_state); 983 1005 } 984 1006 985 1007 static void dpu_plane_flush_csc(struct dpu_plane *pdpu, struct dpu_sw_pipe *pipe)