Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
torvalds
GitHub Repository: torvalds/linux
Path: blob/master/include/drm/drm_fourcc.h
26278 views
1
/*
2
* Copyright (c) 2016 Laurent Pinchart <[email protected]>
3
*
4
* Permission to use, copy, modify, distribute, and sell this software and its
5
* documentation for any purpose is hereby granted without fee, provided that
6
* the above copyright notice appear in all copies and that both that copyright
7
* notice and this permission notice appear in supporting documentation, and
8
* that the name of the copyright holders not be used in advertising or
9
* publicity pertaining to distribution of the software without specific,
10
* written prior permission. The copyright holders make no representations
11
* about the suitability of this software for any purpose. It is provided "as
12
* is" without express or implied warranty.
13
*
14
* THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
15
* INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
16
* EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY SPECIAL, INDIRECT OR
17
* CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
18
* DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
19
* TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE
20
* OF THIS SOFTWARE.
21
*/
22
#ifndef __DRM_FOURCC_H__
23
#define __DRM_FOURCC_H__
24
25
#include <linux/math.h>
26
#include <linux/types.h>
27
#include <uapi/drm/drm_fourcc.h>
28
29
/**
30
* DRM_FORMAT_MAX_PLANES - maximum number of planes a DRM format can have
31
*/
32
#define DRM_FORMAT_MAX_PLANES 4u
33
34
/*
35
* DRM formats are little endian. Define host endian variants for the
36
* most common formats here, to reduce the #ifdefs needed in drivers.
37
*
38
* Note that the DRM_FORMAT_BIG_ENDIAN flag should only be used in
39
* case the format can't be specified otherwise, so we don't end up
40
* with two values describing the same format.
41
*/
42
#ifdef __BIG_ENDIAN
43
# define DRM_FORMAT_HOST_XRGB1555 (DRM_FORMAT_XRGB1555 | \
44
DRM_FORMAT_BIG_ENDIAN)
45
# define DRM_FORMAT_HOST_RGB565 (DRM_FORMAT_RGB565 | \
46
DRM_FORMAT_BIG_ENDIAN)
47
# define DRM_FORMAT_HOST_XRGB8888 DRM_FORMAT_BGRX8888
48
# define DRM_FORMAT_HOST_ARGB8888 DRM_FORMAT_BGRA8888
49
#else
50
# define DRM_FORMAT_HOST_XRGB1555 DRM_FORMAT_XRGB1555
51
# define DRM_FORMAT_HOST_RGB565 DRM_FORMAT_RGB565
52
# define DRM_FORMAT_HOST_XRGB8888 DRM_FORMAT_XRGB8888
53
# define DRM_FORMAT_HOST_ARGB8888 DRM_FORMAT_ARGB8888
54
#endif
55
56
struct drm_device;
57
58
/**
59
* struct drm_format_info - information about a DRM format
60
*/
61
struct drm_format_info {
62
/** @format: 4CC format identifier (DRM_FORMAT_*) */
63
u32 format;
64
65
/**
66
* @depth:
67
*
68
* Color depth (number of bits per pixel excluding padding bits),
69
* valid for a subset of RGB formats only. This is a legacy field, do
70
* not use in new code and set to 0 for new formats.
71
*/
72
u8 depth;
73
74
/** @num_planes: Number of color planes (1 to 3) */
75
u8 num_planes;
76
77
union {
78
/**
79
* @cpp:
80
*
81
* Number of bytes per pixel (per plane), this is aliased with
82
* @char_per_block. It is deprecated in favour of using the
83
* triplet @char_per_block, @block_w, @block_h for better
84
* describing the pixel format.
85
*/
86
u8 cpp[DRM_FORMAT_MAX_PLANES];
87
88
/**
89
* @char_per_block:
90
*
91
* Number of bytes per block (per plane), where blocks are
92
* defined as a rectangle of pixels which are stored next to
93
* each other in a byte aligned memory region. Together with
94
* @block_w and @block_h this is used to properly describe tiles
95
* in tiled formats or to describe groups of pixels in packed
96
* formats for which the memory needed for a single pixel is not
97
* byte aligned.
98
*
99
* @cpp has been kept for historical reasons because there are
100
* a lot of places in drivers where it's used. In drm core for
101
* generic code paths the preferred way is to use
102
* @char_per_block, drm_format_info_block_width() and
103
* drm_format_info_block_height() which allows handling both
104
* block and non-block formats in the same way.
105
*
106
* For formats that are intended to be used only with non-linear
107
* modifiers both @cpp and @char_per_block must be 0 in the
108
* generic format table. Drivers could supply accurate
109
* information from their drm_mode_config.get_format_info hook
110
* if they want the core to be validating the pitch.
111
*/
112
u8 char_per_block[DRM_FORMAT_MAX_PLANES];
113
};
114
115
/**
116
* @block_w:
117
*
118
* Block width in pixels, this is intended to be accessed through
119
* drm_format_info_block_width()
120
*/
121
u8 block_w[DRM_FORMAT_MAX_PLANES];
122
123
/**
124
* @block_h:
125
*
126
* Block height in pixels, this is intended to be accessed through
127
* drm_format_info_block_height()
128
*/
129
u8 block_h[DRM_FORMAT_MAX_PLANES];
130
131
/** @hsub: Horizontal chroma subsampling factor */
132
u8 hsub;
133
/** @vsub: Vertical chroma subsampling factor */
134
u8 vsub;
135
136
/** @has_alpha: Does the format embeds an alpha component? */
137
bool has_alpha;
138
139
/** @is_yuv: Is it a YUV format? */
140
bool is_yuv;
141
142
/** @is_color_indexed: Is it a color-indexed format? */
143
bool is_color_indexed;
144
};
145
146
/**
147
* drm_format_info_is_yuv_packed - check that the format info matches a YUV
148
* format with data laid in a single plane
149
* @info: format info
150
*
151
* Returns:
152
* A boolean indicating whether the format info matches a packed YUV format.
153
*/
154
static inline bool
155
drm_format_info_is_yuv_packed(const struct drm_format_info *info)
156
{
157
return info->is_yuv && info->num_planes == 1;
158
}
159
160
/**
161
* drm_format_info_is_yuv_semiplanar - check that the format info matches a YUV
162
* format with data laid in two planes (luminance and chrominance)
163
* @info: format info
164
*
165
* Returns:
166
* A boolean indicating whether the format info matches a semiplanar YUV format.
167
*/
168
static inline bool
169
drm_format_info_is_yuv_semiplanar(const struct drm_format_info *info)
170
{
171
return info->is_yuv && info->num_planes == 2;
172
}
173
174
/**
175
* drm_format_info_is_yuv_planar - check that the format info matches a YUV
176
* format with data laid in three planes (one for each YUV component)
177
* @info: format info
178
*
179
* Returns:
180
* A boolean indicating whether the format info matches a planar YUV format.
181
*/
182
static inline bool
183
drm_format_info_is_yuv_planar(const struct drm_format_info *info)
184
{
185
return info->is_yuv && info->num_planes == 3;
186
}
187
188
/**
189
* drm_format_info_is_yuv_sampling_410 - check that the format info matches a
190
* YUV format with 4:1:0 sub-sampling
191
* @info: format info
192
*
193
* Returns:
194
* A boolean indicating whether the format info matches a YUV format with 4:1:0
195
* sub-sampling.
196
*/
197
static inline bool
198
drm_format_info_is_yuv_sampling_410(const struct drm_format_info *info)
199
{
200
return info->is_yuv && info->hsub == 4 && info->vsub == 4;
201
}
202
203
/**
204
* drm_format_info_is_yuv_sampling_411 - check that the format info matches a
205
* YUV format with 4:1:1 sub-sampling
206
* @info: format info
207
*
208
* Returns:
209
* A boolean indicating whether the format info matches a YUV format with 4:1:1
210
* sub-sampling.
211
*/
212
static inline bool
213
drm_format_info_is_yuv_sampling_411(const struct drm_format_info *info)
214
{
215
return info->is_yuv && info->hsub == 4 && info->vsub == 1;
216
}
217
218
/**
219
* drm_format_info_is_yuv_sampling_420 - check that the format info matches a
220
* YUV format with 4:2:0 sub-sampling
221
* @info: format info
222
*
223
* Returns:
224
* A boolean indicating whether the format info matches a YUV format with 4:2:0
225
* sub-sampling.
226
*/
227
static inline bool
228
drm_format_info_is_yuv_sampling_420(const struct drm_format_info *info)
229
{
230
return info->is_yuv && info->hsub == 2 && info->vsub == 2;
231
}
232
233
/**
234
* drm_format_info_is_yuv_sampling_422 - check that the format info matches a
235
* YUV format with 4:2:2 sub-sampling
236
* @info: format info
237
*
238
* Returns:
239
* A boolean indicating whether the format info matches a YUV format with 4:2:2
240
* sub-sampling.
241
*/
242
static inline bool
243
drm_format_info_is_yuv_sampling_422(const struct drm_format_info *info)
244
{
245
return info->is_yuv && info->hsub == 2 && info->vsub == 1;
246
}
247
248
/**
249
* drm_format_info_is_yuv_sampling_444 - check that the format info matches a
250
* YUV format with 4:4:4 sub-sampling
251
* @info: format info
252
*
253
* Returns:
254
* A boolean indicating whether the format info matches a YUV format with 4:4:4
255
* sub-sampling.
256
*/
257
static inline bool
258
drm_format_info_is_yuv_sampling_444(const struct drm_format_info *info)
259
{
260
return info->is_yuv && info->hsub == 1 && info->vsub == 1;
261
}
262
263
/**
264
* drm_format_info_plane_width - width of the plane given the first plane
265
* @info: pixel format info
266
* @width: width of the first plane
267
* @plane: plane index
268
*
269
* Returns:
270
* The width of @plane, given that the width of the first plane is @width.
271
*/
272
static inline
273
int drm_format_info_plane_width(const struct drm_format_info *info, int width,
274
int plane)
275
{
276
if (!info || plane >= info->num_planes)
277
return 0;
278
279
if (plane == 0)
280
return width;
281
282
return DIV_ROUND_UP(width, info->hsub);
283
}
284
285
/**
286
* drm_format_info_plane_height - height of the plane given the first plane
287
* @info: pixel format info
288
* @height: height of the first plane
289
* @plane: plane index
290
*
291
* Returns:
292
* The height of @plane, given that the height of the first plane is @height.
293
*/
294
static inline
295
int drm_format_info_plane_height(const struct drm_format_info *info, int height,
296
int plane)
297
{
298
if (!info || plane >= info->num_planes)
299
return 0;
300
301
if (plane == 0)
302
return height;
303
304
return DIV_ROUND_UP(height, info->vsub);
305
}
306
307
const struct drm_format_info *__drm_format_info(u32 format);
308
const struct drm_format_info *drm_format_info(u32 format);
309
const struct drm_format_info *
310
drm_get_format_info(struct drm_device *dev,
311
u32 pixel_format, u64 modifier);
312
uint32_t drm_mode_legacy_fb_format(uint32_t bpp, uint32_t depth);
313
uint32_t drm_driver_legacy_fb_format(struct drm_device *dev,
314
uint32_t bpp, uint32_t depth);
315
uint32_t drm_driver_color_mode_format(struct drm_device *dev, unsigned int color_mode);
316
unsigned int drm_format_info_block_width(const struct drm_format_info *info,
317
int plane);
318
unsigned int drm_format_info_block_height(const struct drm_format_info *info,
319
int plane);
320
unsigned int drm_format_info_bpp(const struct drm_format_info *info, int plane);
321
uint64_t drm_format_info_min_pitch(const struct drm_format_info *info,
322
int plane, unsigned int buffer_width);
323
324
#endif /* __DRM_FOURCC_H__ */
325
326