ff55c5677c73e34c80a4ec72624697d9179527f2
[oweals/openwrt.git] /
1 From fb76c3ded8c771e8b9287d62b5e13666037f890e Mon Sep 17 00:00:00 2001
2 From: Dave Stevenson <dave.stevenson@raspberrypi.org>
3 Date: Tue, 17 Sep 2019 18:28:17 +0100
4 Subject: [PATCH] drm/vc4: Add support for YUV color encodings and
5  ranges
6
7 The BT601/BT709 color encoding and limited vs full
8 range properties were not being exposed, defaulting
9 always to BT601 limited range.
10
11 Expose the parameters and set the registers appropriately.
12
13 Signed-off-by: Dave Stevenson <dave.stevenson@raspberrypi.org>
14 ---
15  drivers/gpu/drm/vc4/vc4_plane.c | 72 +++++++++++++++++++++++++++++++--
16  drivers/gpu/drm/vc4/vc4_regs.h  |  3 ++
17  2 files changed, 72 insertions(+), 3 deletions(-)
18
19 --- a/drivers/gpu/drm/vc4/vc4_plane.c
20 +++ b/drivers/gpu/drm/vc4/vc4_plane.c
21 @@ -577,6 +577,53 @@ static int vc4_plane_allocate_lbm(struct
22         return 0;
23  }
24  
25 +/* The colorspace conversion matrices are held in 3 entries in the dlist.
26 + * Create an array of them, with entries for each full and limited mode, and
27 + * each supported colorspace.
28 + */
29 +#define VC4_LIMITED_RANGE      0
30 +#define VC4_FULL_RANGE         1
31 +
32 +static const u32 colorspace_coeffs[2][DRM_COLOR_ENCODING_MAX][3] = {
33 +       {
34 +               /* Limited range */
35 +               {
36 +                       /* BT601 */
37 +                       SCALER_CSC0_ITR_R_601_5,
38 +                       SCALER_CSC1_ITR_R_601_5,
39 +                       SCALER_CSC2_ITR_R_601_5,
40 +               }, {
41 +                       /* BT709 */
42 +                       SCALER_CSC0_ITR_R_709_3,
43 +                       SCALER_CSC1_ITR_R_709_3,
44 +                       SCALER_CSC2_ITR_R_709_3,
45 +               }, {
46 +                       /* BT2020. Not supported yet - copy 601 */
47 +                       SCALER_CSC0_ITR_R_601_5,
48 +                       SCALER_CSC1_ITR_R_601_5,
49 +                       SCALER_CSC2_ITR_R_601_5,
50 +               }
51 +       }, {
52 +               /* Full range */
53 +               {
54 +                       /* JFIF */
55 +                       SCALER_CSC0_JPEG_JFIF,
56 +                       SCALER_CSC1_JPEG_JFIF,
57 +                       SCALER_CSC2_JPEG_JFIF,
58 +               }, {
59 +                       /* BT709 */
60 +                       SCALER_CSC0_ITR_R_709_3_FR,
61 +                       SCALER_CSC1_ITR_R_709_3_FR,
62 +                       SCALER_CSC2_ITR_R_709_3_FR,
63 +               }, {
64 +                       /* BT2020. Not supported yet - copy JFIF */
65 +                       SCALER_CSC0_JPEG_JFIF,
66 +                       SCALER_CSC1_JPEG_JFIF,
67 +                       SCALER_CSC2_JPEG_JFIF,
68 +               }
69 +       }
70 +};
71 +
72  /* Writes out a full display list for an active plane to the plane's
73   * private dlist state.
74   */
75 @@ -856,9 +903,20 @@ static int vc4_plane_mode_set(struct drm
76  
77         /* Colorspace conversion words */
78         if (vc4_state->is_yuv) {
79 -               vc4_dlist_write(vc4_state, SCALER_CSC0_ITR_R_601_5);
80 -               vc4_dlist_write(vc4_state, SCALER_CSC1_ITR_R_601_5);
81 -               vc4_dlist_write(vc4_state, SCALER_CSC2_ITR_R_601_5);
82 +               enum drm_color_encoding color_encoding = state->color_encoding;
83 +               enum drm_color_range color_range = state->color_range;
84 +               const u32 *ccm;
85 +
86 +               if (color_encoding >= DRM_COLOR_ENCODING_MAX)
87 +                       color_encoding = DRM_COLOR_YCBCR_BT601;
88 +               if (color_range >= DRM_COLOR_RANGE_MAX)
89 +                       color_range = DRM_COLOR_YCBCR_LIMITED_RANGE;
90 +
91 +               ccm = colorspace_coeffs[color_range][color_encoding];
92 +
93 +               vc4_dlist_write(vc4_state, ccm[0]);
94 +               vc4_dlist_write(vc4_state, ccm[1]);
95 +               vc4_dlist_write(vc4_state, ccm[2]);
96         }
97  
98         vc4_state->lbm_offset = 0;
99 @@ -1265,5 +1323,13 @@ struct drm_plane *vc4_plane_init(struct
100                                            DRM_MODE_REFLECT_X |
101                                            DRM_MODE_REFLECT_Y);
102  
103 +       drm_plane_create_color_properties(plane,
104 +                                         BIT(DRM_COLOR_YCBCR_BT601) |
105 +                                         BIT(DRM_COLOR_YCBCR_BT709),
106 +                                         BIT(DRM_COLOR_YCBCR_LIMITED_RANGE) |
107 +                                         BIT(DRM_COLOR_YCBCR_FULL_RANGE),
108 +                                         DRM_COLOR_YCBCR_BT709,
109 +                                         DRM_COLOR_YCBCR_LIMITED_RANGE);
110 +
111         return plane;
112  }
113 --- a/drivers/gpu/drm/vc4/vc4_regs.h
114 +++ b/drivers/gpu/drm/vc4/vc4_regs.h
115 @@ -950,6 +950,7 @@ enum hvs_pixel_format {
116  #define SCALER_CSC0_ITR_R_601_5                        0x00f00000
117  #define SCALER_CSC0_ITR_R_709_3                        0x00f00000
118  #define SCALER_CSC0_JPEG_JFIF                  0x00000000
119 +#define SCALER_CSC0_ITR_R_709_3_FR             0x00000000
120  
121  /* S2.8 contribution of Cb to Green */
122  #define SCALER_CSC1_COEF_CB_GRN_MASK           VC4_MASK(31, 22)
123 @@ -966,6 +967,7 @@ enum hvs_pixel_format {
124  #define SCALER_CSC1_ITR_R_601_5                        0xe73304a8
125  #define SCALER_CSC1_ITR_R_709_3                        0xf2b784a8
126  #define SCALER_CSC1_JPEG_JFIF                  0xea34a400
127 +#define SCALER_CSC1_ITR_R_709_3_FR             0xe23d0400
128  
129  /* S2.8 contribution of Cb to Red */
130  #define SCALER_CSC2_COEF_CB_RED_MASK           VC4_MASK(29, 20)
131 @@ -979,6 +981,7 @@ enum hvs_pixel_format {
132  #define SCALER_CSC2_ITR_R_601_5                        0x00066204
133  #define SCALER_CSC2_ITR_R_709_3                        0x00072a1c
134  #define SCALER_CSC2_JPEG_JFIF                  0x000599c5
135 +#define SCALER_CSC2_ITR_R_709_3_FR             0x00064ddb
136  
137  #define SCALER_TPZ0_VERT_RECALC                        BIT(31)
138  #define SCALER_TPZ0_SCALE_MASK                 VC4_MASK(28, 8)