xref: /openbmc/linux/drivers/gpu/drm/drm_plane.c (revision 1d61d359)
1 /*
2  * Copyright (c) 2016 Intel Corporation
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 
23 #include <linux/slab.h>
24 #include <linux/uaccess.h>
25 
26 #include <drm/drm_plane.h>
27 #include <drm/drm_drv.h>
28 #include <drm/drm_print.h>
29 #include <drm/drm_framebuffer.h>
30 #include <drm/drm_file.h>
31 #include <drm/drm_crtc.h>
32 #include <drm/drm_fourcc.h>
33 #include <drm/drm_managed.h>
34 #include <drm/drm_vblank.h>
35 
36 #include "drm_crtc_internal.h"
37 
38 /**
39  * DOC: overview
40  *
41  * A plane represents an image source that can be blended with or overlaid on
42  * top of a CRTC during the scanout process. Planes take their input data from a
43  * &drm_framebuffer object. The plane itself specifies the cropping and scaling
44  * of that image, and where it is placed on the visible area of a display
45  * pipeline, represented by &drm_crtc. A plane can also have additional
46  * properties that specify how the pixels are positioned and blended, like
47  * rotation or Z-position. All these properties are stored in &drm_plane_state.
48  *
49  * To create a plane, a KMS drivers allocates and zeroes an instances of
50  * &struct drm_plane (possibly as part of a larger structure) and registers it
51  * with a call to drm_universal_plane_init().
52  *
53  * Each plane has a type, see enum drm_plane_type. A plane can be compatible
54  * with multiple CRTCs, see &drm_plane.possible_crtcs.
55  *
56  * Each CRTC must have a unique primary plane userspace can attach to enable
57  * the CRTC. In other words, userspace must be able to attach a different
58  * primary plane to each CRTC at the same time. Primary planes can still be
59  * compatible with multiple CRTCs. There must be exactly as many primary planes
60  * as there are CRTCs.
61  *
62  * Legacy uAPI doesn't expose the primary and cursor planes directly. DRM core
63  * relies on the driver to set the primary and optionally the cursor plane used
64  * for legacy IOCTLs. This is done by calling drm_crtc_init_with_planes(). All
65  * drivers must provide one primary plane per CRTC to avoid surprising legacy
66  * userspace too much.
67  */
68 
69 /**
70  * DOC: standard plane properties
71  *
72  * DRM planes have a few standardized properties:
73  *
74  * type:
75  *     Immutable property describing the type of the plane.
76  *
77  *     For user-space which has enabled the &DRM_CLIENT_CAP_ATOMIC capability,
78  *     the plane type is just a hint and is mostly superseded by atomic
79  *     test-only commits. The type hint can still be used to come up more
80  *     easily with a plane configuration accepted by the driver.
81  *
82  *     The value of this property can be one of the following:
83  *
84  *     "Primary":
85  *         To light up a CRTC, attaching a primary plane is the most likely to
86  *         work if it covers the whole CRTC and doesn't have scaling or
87  *         cropping set up.
88  *
89  *         Drivers may support more features for the primary plane, user-space
90  *         can find out with test-only atomic commits.
91  *
92  *         Some primary planes are implicitly used by the kernel in the legacy
93  *         IOCTLs &DRM_IOCTL_MODE_SETCRTC and &DRM_IOCTL_MODE_PAGE_FLIP.
94  *         Therefore user-space must not mix explicit usage of any primary
95  *         plane (e.g. through an atomic commit) with these legacy IOCTLs.
96  *
97  *     "Cursor":
98  *         To enable this plane, using a framebuffer configured without scaling
99  *         or cropping and with the following properties is the most likely to
100  *         work:
101  *
102  *         - If the driver provides the capabilities &DRM_CAP_CURSOR_WIDTH and
103  *           &DRM_CAP_CURSOR_HEIGHT, create the framebuffer with this size.
104  *           Otherwise, create a framebuffer with the size 64x64.
105  *         - If the driver doesn't support modifiers, create a framebuffer with
106  *           a linear layout. Otherwise, use the IN_FORMATS plane property.
107  *
108  *         Drivers may support more features for the cursor plane, user-space
109  *         can find out with test-only atomic commits.
110  *
111  *         Some cursor planes are implicitly used by the kernel in the legacy
112  *         IOCTLs &DRM_IOCTL_MODE_CURSOR and &DRM_IOCTL_MODE_CURSOR2.
113  *         Therefore user-space must not mix explicit usage of any cursor
114  *         plane (e.g. through an atomic commit) with these legacy IOCTLs.
115  *
116  *         Some drivers may support cursors even if no cursor plane is exposed.
117  *         In this case, the legacy cursor IOCTLs can be used to configure the
118  *         cursor.
119  *
120  *     "Overlay":
121  *         Neither primary nor cursor.
122  *
123  *         Overlay planes are the only planes exposed when the
124  *         &DRM_CLIENT_CAP_UNIVERSAL_PLANES capability is disabled.
125  *
126  * IN_FORMATS:
127  *     Blob property which contains the set of buffer format and modifier
128  *     pairs supported by this plane. The blob is a struct
129  *     drm_format_modifier_blob. Without this property the plane doesn't
130  *     support buffers with modifiers. Userspace cannot change this property.
131  *
132  *     Note that userspace can check the &DRM_CAP_ADDFB2_MODIFIERS driver
133  *     capability for general modifier support. If this flag is set then every
134  *     plane will have the IN_FORMATS property, even when it only supports
135  *     DRM_FORMAT_MOD_LINEAR. Before linux kernel release v5.1 there have been
136  *     various bugs in this area with inconsistencies between the capability
137  *     flag and per-plane properties.
138  */
139 
140 static unsigned int drm_num_planes(struct drm_device *dev)
141 {
142 	unsigned int num = 0;
143 	struct drm_plane *tmp;
144 
145 	drm_for_each_plane(tmp, dev) {
146 		num++;
147 	}
148 
149 	return num;
150 }
151 
152 static inline u32 *
153 formats_ptr(struct drm_format_modifier_blob *blob)
154 {
155 	return (u32 *)(((char *)blob) + blob->formats_offset);
156 }
157 
158 static inline struct drm_format_modifier *
159 modifiers_ptr(struct drm_format_modifier_blob *blob)
160 {
161 	return (struct drm_format_modifier *)(((char *)blob) + blob->modifiers_offset);
162 }
163 
164 static int create_in_format_blob(struct drm_device *dev, struct drm_plane *plane)
165 {
166 	const struct drm_mode_config *config = &dev->mode_config;
167 	struct drm_property_blob *blob;
168 	struct drm_format_modifier *mod;
169 	size_t blob_size, formats_size, modifiers_size;
170 	struct drm_format_modifier_blob *blob_data;
171 	unsigned int i, j;
172 
173 	formats_size = sizeof(__u32) * plane->format_count;
174 	if (WARN_ON(!formats_size)) {
175 		/* 0 formats are never expected */
176 		return 0;
177 	}
178 
179 	modifiers_size =
180 		sizeof(struct drm_format_modifier) * plane->modifier_count;
181 
182 	blob_size = sizeof(struct drm_format_modifier_blob);
183 	/* Modifiers offset is a pointer to a struct with a 64 bit field so it
184 	 * should be naturally aligned to 8B.
185 	 */
186 	BUILD_BUG_ON(sizeof(struct drm_format_modifier_blob) % 8);
187 	blob_size += ALIGN(formats_size, 8);
188 	blob_size += modifiers_size;
189 
190 	blob = drm_property_create_blob(dev, blob_size, NULL);
191 	if (IS_ERR(blob))
192 		return -1;
193 
194 	blob_data = blob->data;
195 	blob_data->version = FORMAT_BLOB_CURRENT;
196 	blob_data->count_formats = plane->format_count;
197 	blob_data->formats_offset = sizeof(struct drm_format_modifier_blob);
198 	blob_data->count_modifiers = plane->modifier_count;
199 
200 	blob_data->modifiers_offset =
201 		ALIGN(blob_data->formats_offset + formats_size, 8);
202 
203 	memcpy(formats_ptr(blob_data), plane->format_types, formats_size);
204 
205 	mod = modifiers_ptr(blob_data);
206 	for (i = 0; i < plane->modifier_count; i++) {
207 		for (j = 0; j < plane->format_count; j++) {
208 			if (!plane->funcs->format_mod_supported ||
209 			    plane->funcs->format_mod_supported(plane,
210 							       plane->format_types[j],
211 							       plane->modifiers[i])) {
212 				mod->formats |= 1ULL << j;
213 			}
214 		}
215 
216 		mod->modifier = plane->modifiers[i];
217 		mod->offset = 0;
218 		mod->pad = 0;
219 		mod++;
220 	}
221 
222 	drm_object_attach_property(&plane->base, config->modifiers_property,
223 				   blob->base.id);
224 
225 	return 0;
226 }
227 
228 __printf(9, 0)
229 static int __drm_universal_plane_init(struct drm_device *dev,
230 				      struct drm_plane *plane,
231 				      uint32_t possible_crtcs,
232 				      const struct drm_plane_funcs *funcs,
233 				      const uint32_t *formats,
234 				      unsigned int format_count,
235 				      const uint64_t *format_modifiers,
236 				      enum drm_plane_type type,
237 				      const char *name, va_list ap)
238 {
239 	struct drm_mode_config *config = &dev->mode_config;
240 	unsigned int format_modifier_count = 0;
241 	int ret;
242 
243 	/* plane index is used with 32bit bitmasks */
244 	if (WARN_ON(config->num_total_plane >= 32))
245 		return -EINVAL;
246 
247 	WARN_ON(drm_drv_uses_atomic_modeset(dev) &&
248 		(!funcs->atomic_destroy_state ||
249 		 !funcs->atomic_duplicate_state));
250 
251 	ret = drm_mode_object_add(dev, &plane->base, DRM_MODE_OBJECT_PLANE);
252 	if (ret)
253 		return ret;
254 
255 	drm_modeset_lock_init(&plane->mutex);
256 
257 	plane->base.properties = &plane->properties;
258 	plane->dev = dev;
259 	plane->funcs = funcs;
260 	plane->format_types = kmalloc_array(format_count, sizeof(uint32_t),
261 					    GFP_KERNEL);
262 	if (!plane->format_types) {
263 		DRM_DEBUG_KMS("out of memory when allocating plane\n");
264 		drm_mode_object_unregister(dev, &plane->base);
265 		return -ENOMEM;
266 	}
267 
268 	/*
269 	 * First driver to need more than 64 formats needs to fix this. Each
270 	 * format is encoded as a bit and the current code only supports a u64.
271 	 */
272 	if (WARN_ON(format_count > 64))
273 		return -EINVAL;
274 
275 	if (format_modifiers) {
276 		const uint64_t *temp_modifiers = format_modifiers;
277 
278 		while (*temp_modifiers++ != DRM_FORMAT_MOD_INVALID)
279 			format_modifier_count++;
280 	}
281 
282 	/* autoset the cap and check for consistency across all planes */
283 	if (format_modifier_count) {
284 		drm_WARN_ON(dev, !config->allow_fb_modifiers &&
285 			    !list_empty(&config->plane_list));
286 		config->allow_fb_modifiers = true;
287 	} else {
288 		drm_WARN_ON(dev, config->allow_fb_modifiers);
289 	}
290 
291 	plane->modifier_count = format_modifier_count;
292 	plane->modifiers = kmalloc_array(format_modifier_count,
293 					 sizeof(format_modifiers[0]),
294 					 GFP_KERNEL);
295 
296 	if (format_modifier_count && !plane->modifiers) {
297 		DRM_DEBUG_KMS("out of memory when allocating plane\n");
298 		kfree(plane->format_types);
299 		drm_mode_object_unregister(dev, &plane->base);
300 		return -ENOMEM;
301 	}
302 
303 	if (name) {
304 		plane->name = kvasprintf(GFP_KERNEL, name, ap);
305 	} else {
306 		plane->name = kasprintf(GFP_KERNEL, "plane-%d",
307 					drm_num_planes(dev));
308 	}
309 	if (!plane->name) {
310 		kfree(plane->format_types);
311 		kfree(plane->modifiers);
312 		drm_mode_object_unregister(dev, &plane->base);
313 		return -ENOMEM;
314 	}
315 
316 	memcpy(plane->format_types, formats, format_count * sizeof(uint32_t));
317 	plane->format_count = format_count;
318 	memcpy(plane->modifiers, format_modifiers,
319 	       format_modifier_count * sizeof(format_modifiers[0]));
320 	plane->possible_crtcs = possible_crtcs;
321 	plane->type = type;
322 
323 	list_add_tail(&plane->head, &config->plane_list);
324 	plane->index = config->num_total_plane++;
325 
326 	drm_object_attach_property(&plane->base,
327 				   config->plane_type_property,
328 				   plane->type);
329 
330 	if (drm_core_check_feature(dev, DRIVER_ATOMIC)) {
331 		drm_object_attach_property(&plane->base, config->prop_fb_id, 0);
332 		drm_object_attach_property(&plane->base, config->prop_in_fence_fd, -1);
333 		drm_object_attach_property(&plane->base, config->prop_crtc_id, 0);
334 		drm_object_attach_property(&plane->base, config->prop_crtc_x, 0);
335 		drm_object_attach_property(&plane->base, config->prop_crtc_y, 0);
336 		drm_object_attach_property(&plane->base, config->prop_crtc_w, 0);
337 		drm_object_attach_property(&plane->base, config->prop_crtc_h, 0);
338 		drm_object_attach_property(&plane->base, config->prop_src_x, 0);
339 		drm_object_attach_property(&plane->base, config->prop_src_y, 0);
340 		drm_object_attach_property(&plane->base, config->prop_src_w, 0);
341 		drm_object_attach_property(&plane->base, config->prop_src_h, 0);
342 	}
343 
344 	if (config->allow_fb_modifiers)
345 		create_in_format_blob(dev, plane);
346 
347 	return 0;
348 }
349 
350 /**
351  * drm_universal_plane_init - Initialize a new universal plane object
352  * @dev: DRM device
353  * @plane: plane object to init
354  * @possible_crtcs: bitmask of possible CRTCs
355  * @funcs: callbacks for the new plane
356  * @formats: array of supported formats (DRM_FORMAT\_\*)
357  * @format_count: number of elements in @formats
358  * @format_modifiers: array of struct drm_format modifiers terminated by
359  *                    DRM_FORMAT_MOD_INVALID
360  * @type: type of plane (overlay, primary, cursor)
361  * @name: printf style format string for the plane name, or NULL for default name
362  *
363  * Initializes a plane object of type @type. The &drm_plane_funcs.destroy hook
364  * should call drm_plane_cleanup() and kfree() the plane structure. The plane
365  * structure should not be allocated with devm_kzalloc().
366  *
367  * Note: consider using drmm_universal_plane_alloc() instead of
368  * drm_universal_plane_init() to let the DRM managed resource infrastructure
369  * take care of cleanup and deallocation.
370  *
371  * Drivers supporting modifiers must set @format_modifiers on all their planes,
372  * even those that only support DRM_FORMAT_MOD_LINEAR.
373  *
374  * Returns:
375  * Zero on success, error code on failure.
376  */
377 int drm_universal_plane_init(struct drm_device *dev, struct drm_plane *plane,
378 			     uint32_t possible_crtcs,
379 			     const struct drm_plane_funcs *funcs,
380 			     const uint32_t *formats, unsigned int format_count,
381 			     const uint64_t *format_modifiers,
382 			     enum drm_plane_type type,
383 			     const char *name, ...)
384 {
385 	va_list ap;
386 	int ret;
387 
388 	WARN_ON(!funcs->destroy);
389 
390 	va_start(ap, name);
391 	ret = __drm_universal_plane_init(dev, plane, possible_crtcs, funcs,
392 					 formats, format_count, format_modifiers,
393 					 type, name, ap);
394 	va_end(ap);
395 	return ret;
396 }
397 EXPORT_SYMBOL(drm_universal_plane_init);
398 
399 static void drmm_universal_plane_alloc_release(struct drm_device *dev, void *ptr)
400 {
401 	struct drm_plane *plane = ptr;
402 
403 	if (WARN_ON(!plane->dev))
404 		return;
405 
406 	drm_plane_cleanup(plane);
407 }
408 
409 void *__drmm_universal_plane_alloc(struct drm_device *dev, size_t size,
410 				   size_t offset, uint32_t possible_crtcs,
411 				   const struct drm_plane_funcs *funcs,
412 				   const uint32_t *formats, unsigned int format_count,
413 				   const uint64_t *format_modifiers,
414 				   enum drm_plane_type type,
415 				   const char *name, ...)
416 {
417 	void *container;
418 	struct drm_plane *plane;
419 	va_list ap;
420 	int ret;
421 
422 	if (WARN_ON(!funcs || funcs->destroy))
423 		return ERR_PTR(-EINVAL);
424 
425 	container = drmm_kzalloc(dev, size, GFP_KERNEL);
426 	if (!container)
427 		return ERR_PTR(-ENOMEM);
428 
429 	plane = container + offset;
430 
431 	va_start(ap, name);
432 	ret = __drm_universal_plane_init(dev, plane, possible_crtcs, funcs,
433 					 formats, format_count, format_modifiers,
434 					 type, name, ap);
435 	va_end(ap);
436 	if (ret)
437 		return ERR_PTR(ret);
438 
439 	ret = drmm_add_action_or_reset(dev, drmm_universal_plane_alloc_release,
440 				       plane);
441 	if (ret)
442 		return ERR_PTR(ret);
443 
444 	return container;
445 }
446 EXPORT_SYMBOL(__drmm_universal_plane_alloc);
447 
448 int drm_plane_register_all(struct drm_device *dev)
449 {
450 	unsigned int num_planes = 0;
451 	unsigned int num_zpos = 0;
452 	struct drm_plane *plane;
453 	int ret = 0;
454 
455 	drm_for_each_plane(plane, dev) {
456 		if (plane->funcs->late_register)
457 			ret = plane->funcs->late_register(plane);
458 		if (ret)
459 			return ret;
460 
461 		if (plane->zpos_property)
462 			num_zpos++;
463 		num_planes++;
464 	}
465 
466 	drm_WARN(dev, num_zpos && num_planes != num_zpos,
467 		 "Mixing planes with and without zpos property is invalid\n");
468 
469 	return 0;
470 }
471 
472 void drm_plane_unregister_all(struct drm_device *dev)
473 {
474 	struct drm_plane *plane;
475 
476 	drm_for_each_plane(plane, dev) {
477 		if (plane->funcs->early_unregister)
478 			plane->funcs->early_unregister(plane);
479 	}
480 }
481 
482 /**
483  * drm_plane_init - Initialize a legacy plane
484  * @dev: DRM device
485  * @plane: plane object to init
486  * @possible_crtcs: bitmask of possible CRTCs
487  * @funcs: callbacks for the new plane
488  * @formats: array of supported formats (DRM_FORMAT\_\*)
489  * @format_count: number of elements in @formats
490  * @is_primary: plane type (primary vs overlay)
491  *
492  * Legacy API to initialize a DRM plane.
493  *
494  * New drivers should call drm_universal_plane_init() instead.
495  *
496  * Returns:
497  * Zero on success, error code on failure.
498  */
499 int drm_plane_init(struct drm_device *dev, struct drm_plane *plane,
500 		   uint32_t possible_crtcs,
501 		   const struct drm_plane_funcs *funcs,
502 		   const uint32_t *formats, unsigned int format_count,
503 		   bool is_primary)
504 {
505 	enum drm_plane_type type;
506 
507 	type = is_primary ? DRM_PLANE_TYPE_PRIMARY : DRM_PLANE_TYPE_OVERLAY;
508 	return drm_universal_plane_init(dev, plane, possible_crtcs, funcs,
509 					formats, format_count,
510 					NULL, type, NULL);
511 }
512 EXPORT_SYMBOL(drm_plane_init);
513 
514 /**
515  * drm_plane_cleanup - Clean up the core plane usage
516  * @plane: plane to cleanup
517  *
518  * This function cleans up @plane and removes it from the DRM mode setting
519  * core. Note that the function does *not* free the plane structure itself,
520  * this is the responsibility of the caller.
521  */
522 void drm_plane_cleanup(struct drm_plane *plane)
523 {
524 	struct drm_device *dev = plane->dev;
525 
526 	drm_modeset_lock_fini(&plane->mutex);
527 
528 	kfree(plane->format_types);
529 	kfree(plane->modifiers);
530 	drm_mode_object_unregister(dev, &plane->base);
531 
532 	BUG_ON(list_empty(&plane->head));
533 
534 	/* Note that the plane_list is considered to be static; should we
535 	 * remove the drm_plane at runtime we would have to decrement all
536 	 * the indices on the drm_plane after us in the plane_list.
537 	 */
538 
539 	list_del(&plane->head);
540 	dev->mode_config.num_total_plane--;
541 
542 	WARN_ON(plane->state && !plane->funcs->atomic_destroy_state);
543 	if (plane->state && plane->funcs->atomic_destroy_state)
544 		plane->funcs->atomic_destroy_state(plane, plane->state);
545 
546 	kfree(plane->name);
547 
548 	memset(plane, 0, sizeof(*plane));
549 }
550 EXPORT_SYMBOL(drm_plane_cleanup);
551 
552 /**
553  * drm_plane_from_index - find the registered plane at an index
554  * @dev: DRM device
555  * @idx: index of registered plane to find for
556  *
557  * Given a plane index, return the registered plane from DRM device's
558  * list of planes with matching index. This is the inverse of drm_plane_index().
559  */
560 struct drm_plane *
561 drm_plane_from_index(struct drm_device *dev, int idx)
562 {
563 	struct drm_plane *plane;
564 
565 	drm_for_each_plane(plane, dev)
566 		if (idx == plane->index)
567 			return plane;
568 
569 	return NULL;
570 }
571 EXPORT_SYMBOL(drm_plane_from_index);
572 
573 /**
574  * drm_plane_force_disable - Forcibly disable a plane
575  * @plane: plane to disable
576  *
577  * Forces the plane to be disabled.
578  *
579  * Used when the plane's current framebuffer is destroyed,
580  * and when restoring fbdev mode.
581  *
582  * Note that this function is not suitable for atomic drivers, since it doesn't
583  * wire through the lock acquisition context properly and hence can't handle
584  * retries or driver private locks. You probably want to use
585  * drm_atomic_helper_disable_plane() or
586  * drm_atomic_helper_disable_planes_on_crtc() instead.
587  */
588 void drm_plane_force_disable(struct drm_plane *plane)
589 {
590 	int ret;
591 
592 	if (!plane->fb)
593 		return;
594 
595 	WARN_ON(drm_drv_uses_atomic_modeset(plane->dev));
596 
597 	plane->old_fb = plane->fb;
598 	ret = plane->funcs->disable_plane(plane, NULL);
599 	if (ret) {
600 		DRM_ERROR("failed to disable plane with busy fb\n");
601 		plane->old_fb = NULL;
602 		return;
603 	}
604 	/* disconnect the plane from the fb and crtc: */
605 	drm_framebuffer_put(plane->old_fb);
606 	plane->old_fb = NULL;
607 	plane->fb = NULL;
608 	plane->crtc = NULL;
609 }
610 EXPORT_SYMBOL(drm_plane_force_disable);
611 
612 /**
613  * drm_mode_plane_set_obj_prop - set the value of a property
614  * @plane: drm plane object to set property value for
615  * @property: property to set
616  * @value: value the property should be set to
617  *
618  * This functions sets a given property on a given plane object. This function
619  * calls the driver's ->set_property callback and changes the software state of
620  * the property if the callback succeeds.
621  *
622  * Returns:
623  * Zero on success, error code on failure.
624  */
625 int drm_mode_plane_set_obj_prop(struct drm_plane *plane,
626 				struct drm_property *property,
627 				uint64_t value)
628 {
629 	int ret = -EINVAL;
630 	struct drm_mode_object *obj = &plane->base;
631 
632 	if (plane->funcs->set_property)
633 		ret = plane->funcs->set_property(plane, property, value);
634 	if (!ret)
635 		drm_object_property_set_value(obj, property, value);
636 
637 	return ret;
638 }
639 EXPORT_SYMBOL(drm_mode_plane_set_obj_prop);
640 
641 int drm_mode_getplane_res(struct drm_device *dev, void *data,
642 			  struct drm_file *file_priv)
643 {
644 	struct drm_mode_get_plane_res *plane_resp = data;
645 	struct drm_plane *plane;
646 	uint32_t __user *plane_ptr;
647 	int count = 0;
648 
649 	if (!drm_core_check_feature(dev, DRIVER_MODESET))
650 		return -EOPNOTSUPP;
651 
652 	plane_ptr = u64_to_user_ptr(plane_resp->plane_id_ptr);
653 
654 	/*
655 	 * This ioctl is called twice, once to determine how much space is
656 	 * needed, and the 2nd time to fill it.
657 	 */
658 	drm_for_each_plane(plane, dev) {
659 		/*
660 		 * Unless userspace set the 'universal planes'
661 		 * capability bit, only advertise overlays.
662 		 */
663 		if (plane->type != DRM_PLANE_TYPE_OVERLAY &&
664 		    !file_priv->universal_planes)
665 			continue;
666 
667 		if (drm_lease_held(file_priv, plane->base.id)) {
668 			if (count < plane_resp->count_planes &&
669 			    put_user(plane->base.id, plane_ptr + count))
670 				return -EFAULT;
671 			count++;
672 		}
673 	}
674 	plane_resp->count_planes = count;
675 
676 	return 0;
677 }
678 
679 int drm_mode_getplane(struct drm_device *dev, void *data,
680 		      struct drm_file *file_priv)
681 {
682 	struct drm_mode_get_plane *plane_resp = data;
683 	struct drm_plane *plane;
684 	uint32_t __user *format_ptr;
685 
686 	if (!drm_core_check_feature(dev, DRIVER_MODESET))
687 		return -EOPNOTSUPP;
688 
689 	plane = drm_plane_find(dev, file_priv, plane_resp->plane_id);
690 	if (!plane)
691 		return -ENOENT;
692 
693 	drm_modeset_lock(&plane->mutex, NULL);
694 	if (plane->state && plane->state->crtc && drm_lease_held(file_priv, plane->state->crtc->base.id))
695 		plane_resp->crtc_id = plane->state->crtc->base.id;
696 	else if (!plane->state && plane->crtc && drm_lease_held(file_priv, plane->crtc->base.id))
697 		plane_resp->crtc_id = plane->crtc->base.id;
698 	else
699 		plane_resp->crtc_id = 0;
700 
701 	if (plane->state && plane->state->fb)
702 		plane_resp->fb_id = plane->state->fb->base.id;
703 	else if (!plane->state && plane->fb)
704 		plane_resp->fb_id = plane->fb->base.id;
705 	else
706 		plane_resp->fb_id = 0;
707 	drm_modeset_unlock(&plane->mutex);
708 
709 	plane_resp->plane_id = plane->base.id;
710 	plane_resp->possible_crtcs = drm_lease_filter_crtcs(file_priv,
711 							    plane->possible_crtcs);
712 
713 	plane_resp->gamma_size = 0;
714 
715 	/*
716 	 * This ioctl is called twice, once to determine how much space is
717 	 * needed, and the 2nd time to fill it.
718 	 */
719 	if (plane->format_count &&
720 	    (plane_resp->count_format_types >= plane->format_count)) {
721 		format_ptr = (uint32_t __user *)(unsigned long)plane_resp->format_type_ptr;
722 		if (copy_to_user(format_ptr,
723 				 plane->format_types,
724 				 sizeof(uint32_t) * plane->format_count)) {
725 			return -EFAULT;
726 		}
727 	}
728 	plane_resp->count_format_types = plane->format_count;
729 
730 	return 0;
731 }
732 
733 int drm_plane_check_pixel_format(struct drm_plane *plane,
734 				 u32 format, u64 modifier)
735 {
736 	unsigned int i;
737 
738 	for (i = 0; i < plane->format_count; i++) {
739 		if (format == plane->format_types[i])
740 			break;
741 	}
742 	if (i == plane->format_count)
743 		return -EINVAL;
744 
745 	if (plane->funcs->format_mod_supported) {
746 		if (!plane->funcs->format_mod_supported(plane, format, modifier))
747 			return -EINVAL;
748 	} else {
749 		if (!plane->modifier_count)
750 			return 0;
751 
752 		for (i = 0; i < plane->modifier_count; i++) {
753 			if (modifier == plane->modifiers[i])
754 				break;
755 		}
756 		if (i == plane->modifier_count)
757 			return -EINVAL;
758 	}
759 
760 	return 0;
761 }
762 
763 static int __setplane_check(struct drm_plane *plane,
764 			    struct drm_crtc *crtc,
765 			    struct drm_framebuffer *fb,
766 			    int32_t crtc_x, int32_t crtc_y,
767 			    uint32_t crtc_w, uint32_t crtc_h,
768 			    uint32_t src_x, uint32_t src_y,
769 			    uint32_t src_w, uint32_t src_h)
770 {
771 	int ret;
772 
773 	/* Check whether this plane is usable on this CRTC */
774 	if (!(plane->possible_crtcs & drm_crtc_mask(crtc))) {
775 		DRM_DEBUG_KMS("Invalid crtc for plane\n");
776 		return -EINVAL;
777 	}
778 
779 	/* Check whether this plane supports the fb pixel format. */
780 	ret = drm_plane_check_pixel_format(plane, fb->format->format,
781 					   fb->modifier);
782 	if (ret) {
783 		DRM_DEBUG_KMS("Invalid pixel format %p4cc, modifier 0x%llx\n",
784 			      &fb->format->format, fb->modifier);
785 		return ret;
786 	}
787 
788 	/* Give drivers some help against integer overflows */
789 	if (crtc_w > INT_MAX ||
790 	    crtc_x > INT_MAX - (int32_t) crtc_w ||
791 	    crtc_h > INT_MAX ||
792 	    crtc_y > INT_MAX - (int32_t) crtc_h) {
793 		DRM_DEBUG_KMS("Invalid CRTC coordinates %ux%u+%d+%d\n",
794 			      crtc_w, crtc_h, crtc_x, crtc_y);
795 		return -ERANGE;
796 	}
797 
798 	ret = drm_framebuffer_check_src_coords(src_x, src_y, src_w, src_h, fb);
799 	if (ret)
800 		return ret;
801 
802 	return 0;
803 }
804 
805 /**
806  * drm_any_plane_has_format - Check whether any plane supports this format and modifier combination
807  * @dev: DRM device
808  * @format: pixel format (DRM_FORMAT_*)
809  * @modifier: data layout modifier
810  *
811  * Returns:
812  * Whether at least one plane supports the specified format and modifier combination.
813  */
814 bool drm_any_plane_has_format(struct drm_device *dev,
815 			      u32 format, u64 modifier)
816 {
817 	struct drm_plane *plane;
818 
819 	drm_for_each_plane(plane, dev) {
820 		if (drm_plane_check_pixel_format(plane, format, modifier) == 0)
821 			return true;
822 	}
823 
824 	return false;
825 }
826 EXPORT_SYMBOL(drm_any_plane_has_format);
827 
828 /*
829  * __setplane_internal - setplane handler for internal callers
830  *
831  * This function will take a reference on the new fb for the plane
832  * on success.
833  *
834  * src_{x,y,w,h} are provided in 16.16 fixed point format
835  */
836 static int __setplane_internal(struct drm_plane *plane,
837 			       struct drm_crtc *crtc,
838 			       struct drm_framebuffer *fb,
839 			       int32_t crtc_x, int32_t crtc_y,
840 			       uint32_t crtc_w, uint32_t crtc_h,
841 			       /* src_{x,y,w,h} values are 16.16 fixed point */
842 			       uint32_t src_x, uint32_t src_y,
843 			       uint32_t src_w, uint32_t src_h,
844 			       struct drm_modeset_acquire_ctx *ctx)
845 {
846 	int ret = 0;
847 
848 	WARN_ON(drm_drv_uses_atomic_modeset(plane->dev));
849 
850 	/* No fb means shut it down */
851 	if (!fb) {
852 		plane->old_fb = plane->fb;
853 		ret = plane->funcs->disable_plane(plane, ctx);
854 		if (!ret) {
855 			plane->crtc = NULL;
856 			plane->fb = NULL;
857 		} else {
858 			plane->old_fb = NULL;
859 		}
860 		goto out;
861 	}
862 
863 	ret = __setplane_check(plane, crtc, fb,
864 			       crtc_x, crtc_y, crtc_w, crtc_h,
865 			       src_x, src_y, src_w, src_h);
866 	if (ret)
867 		goto out;
868 
869 	plane->old_fb = plane->fb;
870 	ret = plane->funcs->update_plane(plane, crtc, fb,
871 					 crtc_x, crtc_y, crtc_w, crtc_h,
872 					 src_x, src_y, src_w, src_h, ctx);
873 	if (!ret) {
874 		plane->crtc = crtc;
875 		plane->fb = fb;
876 		drm_framebuffer_get(plane->fb);
877 	} else {
878 		plane->old_fb = NULL;
879 	}
880 
881 out:
882 	if (plane->old_fb)
883 		drm_framebuffer_put(plane->old_fb);
884 	plane->old_fb = NULL;
885 
886 	return ret;
887 }
888 
889 static int __setplane_atomic(struct drm_plane *plane,
890 			     struct drm_crtc *crtc,
891 			     struct drm_framebuffer *fb,
892 			     int32_t crtc_x, int32_t crtc_y,
893 			     uint32_t crtc_w, uint32_t crtc_h,
894 			     uint32_t src_x, uint32_t src_y,
895 			     uint32_t src_w, uint32_t src_h,
896 			     struct drm_modeset_acquire_ctx *ctx)
897 {
898 	int ret;
899 
900 	WARN_ON(!drm_drv_uses_atomic_modeset(plane->dev));
901 
902 	/* No fb means shut it down */
903 	if (!fb)
904 		return plane->funcs->disable_plane(plane, ctx);
905 
906 	/*
907 	 * FIXME: This is redundant with drm_atomic_plane_check(),
908 	 * but the legacy cursor/"async" .update_plane() tricks
909 	 * don't call that so we still need this here. Should remove
910 	 * this when all .update_plane() implementations have been
911 	 * fixed to call drm_atomic_plane_check().
912 	 */
913 	ret = __setplane_check(plane, crtc, fb,
914 			       crtc_x, crtc_y, crtc_w, crtc_h,
915 			       src_x, src_y, src_w, src_h);
916 	if (ret)
917 		return ret;
918 
919 	return plane->funcs->update_plane(plane, crtc, fb,
920 					  crtc_x, crtc_y, crtc_w, crtc_h,
921 					  src_x, src_y, src_w, src_h, ctx);
922 }
923 
924 static int setplane_internal(struct drm_plane *plane,
925 			     struct drm_crtc *crtc,
926 			     struct drm_framebuffer *fb,
927 			     int32_t crtc_x, int32_t crtc_y,
928 			     uint32_t crtc_w, uint32_t crtc_h,
929 			     /* src_{x,y,w,h} values are 16.16 fixed point */
930 			     uint32_t src_x, uint32_t src_y,
931 			     uint32_t src_w, uint32_t src_h)
932 {
933 	struct drm_modeset_acquire_ctx ctx;
934 	int ret;
935 
936 	DRM_MODESET_LOCK_ALL_BEGIN(plane->dev, ctx,
937 				   DRM_MODESET_ACQUIRE_INTERRUPTIBLE, ret);
938 
939 	if (drm_drv_uses_atomic_modeset(plane->dev))
940 		ret = __setplane_atomic(plane, crtc, fb,
941 					crtc_x, crtc_y, crtc_w, crtc_h,
942 					src_x, src_y, src_w, src_h, &ctx);
943 	else
944 		ret = __setplane_internal(plane, crtc, fb,
945 					  crtc_x, crtc_y, crtc_w, crtc_h,
946 					  src_x, src_y, src_w, src_h, &ctx);
947 
948 	DRM_MODESET_LOCK_ALL_END(plane->dev, ctx, ret);
949 
950 	return ret;
951 }
952 
953 int drm_mode_setplane(struct drm_device *dev, void *data,
954 		      struct drm_file *file_priv)
955 {
956 	struct drm_mode_set_plane *plane_req = data;
957 	struct drm_plane *plane;
958 	struct drm_crtc *crtc = NULL;
959 	struct drm_framebuffer *fb = NULL;
960 	int ret;
961 
962 	if (!drm_core_check_feature(dev, DRIVER_MODESET))
963 		return -EOPNOTSUPP;
964 
965 	/*
966 	 * First, find the plane, crtc, and fb objects.  If not available,
967 	 * we don't bother to call the driver.
968 	 */
969 	plane = drm_plane_find(dev, file_priv, plane_req->plane_id);
970 	if (!plane) {
971 		DRM_DEBUG_KMS("Unknown plane ID %d\n",
972 			      plane_req->plane_id);
973 		return -ENOENT;
974 	}
975 
976 	if (plane_req->fb_id) {
977 		fb = drm_framebuffer_lookup(dev, file_priv, plane_req->fb_id);
978 		if (!fb) {
979 			DRM_DEBUG_KMS("Unknown framebuffer ID %d\n",
980 				      plane_req->fb_id);
981 			return -ENOENT;
982 		}
983 
984 		crtc = drm_crtc_find(dev, file_priv, plane_req->crtc_id);
985 		if (!crtc) {
986 			drm_framebuffer_put(fb);
987 			DRM_DEBUG_KMS("Unknown crtc ID %d\n",
988 				      plane_req->crtc_id);
989 			return -ENOENT;
990 		}
991 	}
992 
993 	ret = setplane_internal(plane, crtc, fb,
994 				plane_req->crtc_x, plane_req->crtc_y,
995 				plane_req->crtc_w, plane_req->crtc_h,
996 				plane_req->src_x, plane_req->src_y,
997 				plane_req->src_w, plane_req->src_h);
998 
999 	if (fb)
1000 		drm_framebuffer_put(fb);
1001 
1002 	return ret;
1003 }
1004 
1005 static int drm_mode_cursor_universal(struct drm_crtc *crtc,
1006 				     struct drm_mode_cursor2 *req,
1007 				     struct drm_file *file_priv,
1008 				     struct drm_modeset_acquire_ctx *ctx)
1009 {
1010 	struct drm_device *dev = crtc->dev;
1011 	struct drm_plane *plane = crtc->cursor;
1012 	struct drm_framebuffer *fb = NULL;
1013 	struct drm_mode_fb_cmd2 fbreq = {
1014 		.width = req->width,
1015 		.height = req->height,
1016 		.pixel_format = DRM_FORMAT_ARGB8888,
1017 		.pitches = { req->width * 4 },
1018 		.handles = { req->handle },
1019 	};
1020 	int32_t crtc_x, crtc_y;
1021 	uint32_t crtc_w = 0, crtc_h = 0;
1022 	uint32_t src_w = 0, src_h = 0;
1023 	int ret = 0;
1024 
1025 	BUG_ON(!plane);
1026 	WARN_ON(plane->crtc != crtc && plane->crtc != NULL);
1027 
1028 	/*
1029 	 * Obtain fb we'll be using (either new or existing) and take an extra
1030 	 * reference to it if fb != null.  setplane will take care of dropping
1031 	 * the reference if the plane update fails.
1032 	 */
1033 	if (req->flags & DRM_MODE_CURSOR_BO) {
1034 		if (req->handle) {
1035 			fb = drm_internal_framebuffer_create(dev, &fbreq, file_priv);
1036 			if (IS_ERR(fb)) {
1037 				DRM_DEBUG_KMS("failed to wrap cursor buffer in drm framebuffer\n");
1038 				return PTR_ERR(fb);
1039 			}
1040 
1041 			fb->hot_x = req->hot_x;
1042 			fb->hot_y = req->hot_y;
1043 		} else {
1044 			fb = NULL;
1045 		}
1046 	} else {
1047 		if (plane->state)
1048 			fb = plane->state->fb;
1049 		else
1050 			fb = plane->fb;
1051 
1052 		if (fb)
1053 			drm_framebuffer_get(fb);
1054 	}
1055 
1056 	if (req->flags & DRM_MODE_CURSOR_MOVE) {
1057 		crtc_x = req->x;
1058 		crtc_y = req->y;
1059 	} else {
1060 		crtc_x = crtc->cursor_x;
1061 		crtc_y = crtc->cursor_y;
1062 	}
1063 
1064 	if (fb) {
1065 		crtc_w = fb->width;
1066 		crtc_h = fb->height;
1067 		src_w = fb->width << 16;
1068 		src_h = fb->height << 16;
1069 	}
1070 
1071 	if (drm_drv_uses_atomic_modeset(dev))
1072 		ret = __setplane_atomic(plane, crtc, fb,
1073 					crtc_x, crtc_y, crtc_w, crtc_h,
1074 					0, 0, src_w, src_h, ctx);
1075 	else
1076 		ret = __setplane_internal(plane, crtc, fb,
1077 					  crtc_x, crtc_y, crtc_w, crtc_h,
1078 					  0, 0, src_w, src_h, ctx);
1079 
1080 	if (fb)
1081 		drm_framebuffer_put(fb);
1082 
1083 	/* Update successful; save new cursor position, if necessary */
1084 	if (ret == 0 && req->flags & DRM_MODE_CURSOR_MOVE) {
1085 		crtc->cursor_x = req->x;
1086 		crtc->cursor_y = req->y;
1087 	}
1088 
1089 	return ret;
1090 }
1091 
1092 static int drm_mode_cursor_common(struct drm_device *dev,
1093 				  struct drm_mode_cursor2 *req,
1094 				  struct drm_file *file_priv)
1095 {
1096 	struct drm_crtc *crtc;
1097 	struct drm_modeset_acquire_ctx ctx;
1098 	int ret = 0;
1099 
1100 	if (!drm_core_check_feature(dev, DRIVER_MODESET))
1101 		return -EOPNOTSUPP;
1102 
1103 	if (!req->flags || (~DRM_MODE_CURSOR_FLAGS & req->flags))
1104 		return -EINVAL;
1105 
1106 	crtc = drm_crtc_find(dev, file_priv, req->crtc_id);
1107 	if (!crtc) {
1108 		DRM_DEBUG_KMS("Unknown CRTC ID %d\n", req->crtc_id);
1109 		return -ENOENT;
1110 	}
1111 
1112 	drm_modeset_acquire_init(&ctx, DRM_MODESET_ACQUIRE_INTERRUPTIBLE);
1113 retry:
1114 	ret = drm_modeset_lock(&crtc->mutex, &ctx);
1115 	if (ret)
1116 		goto out;
1117 	/*
1118 	 * If this crtc has a universal cursor plane, call that plane's update
1119 	 * handler rather than using legacy cursor handlers.
1120 	 */
1121 	if (crtc->cursor) {
1122 		ret = drm_modeset_lock(&crtc->cursor->mutex, &ctx);
1123 		if (ret)
1124 			goto out;
1125 
1126 		if (!drm_lease_held(file_priv, crtc->cursor->base.id)) {
1127 			ret = -EACCES;
1128 			goto out;
1129 		}
1130 
1131 		ret = drm_mode_cursor_universal(crtc, req, file_priv, &ctx);
1132 		goto out;
1133 	}
1134 
1135 	if (req->flags & DRM_MODE_CURSOR_BO) {
1136 		if (!crtc->funcs->cursor_set && !crtc->funcs->cursor_set2) {
1137 			ret = -ENXIO;
1138 			goto out;
1139 		}
1140 		/* Turns off the cursor if handle is 0 */
1141 		if (crtc->funcs->cursor_set2)
1142 			ret = crtc->funcs->cursor_set2(crtc, file_priv, req->handle,
1143 						      req->width, req->height, req->hot_x, req->hot_y);
1144 		else
1145 			ret = crtc->funcs->cursor_set(crtc, file_priv, req->handle,
1146 						      req->width, req->height);
1147 	}
1148 
1149 	if (req->flags & DRM_MODE_CURSOR_MOVE) {
1150 		if (crtc->funcs->cursor_move) {
1151 			ret = crtc->funcs->cursor_move(crtc, req->x, req->y);
1152 		} else {
1153 			ret = -EFAULT;
1154 			goto out;
1155 		}
1156 	}
1157 out:
1158 	if (ret == -EDEADLK) {
1159 		ret = drm_modeset_backoff(&ctx);
1160 		if (!ret)
1161 			goto retry;
1162 	}
1163 
1164 	drm_modeset_drop_locks(&ctx);
1165 	drm_modeset_acquire_fini(&ctx);
1166 
1167 	return ret;
1168 
1169 }
1170 
1171 
1172 int drm_mode_cursor_ioctl(struct drm_device *dev,
1173 			  void *data, struct drm_file *file_priv)
1174 {
1175 	struct drm_mode_cursor *req = data;
1176 	struct drm_mode_cursor2 new_req;
1177 
1178 	memcpy(&new_req, req, sizeof(struct drm_mode_cursor));
1179 	new_req.hot_x = new_req.hot_y = 0;
1180 
1181 	return drm_mode_cursor_common(dev, &new_req, file_priv);
1182 }
1183 
1184 /*
1185  * Set the cursor configuration based on user request. This implements the 2nd
1186  * version of the cursor ioctl, which allows userspace to additionally specify
1187  * the hotspot of the pointer.
1188  */
1189 int drm_mode_cursor2_ioctl(struct drm_device *dev,
1190 			   void *data, struct drm_file *file_priv)
1191 {
1192 	struct drm_mode_cursor2 *req = data;
1193 
1194 	return drm_mode_cursor_common(dev, req, file_priv);
1195 }
1196 
1197 int drm_mode_page_flip_ioctl(struct drm_device *dev,
1198 			     void *data, struct drm_file *file_priv)
1199 {
1200 	struct drm_mode_crtc_page_flip_target *page_flip = data;
1201 	struct drm_crtc *crtc;
1202 	struct drm_plane *plane;
1203 	struct drm_framebuffer *fb = NULL, *old_fb;
1204 	struct drm_pending_vblank_event *e = NULL;
1205 	u32 target_vblank = page_flip->sequence;
1206 	struct drm_modeset_acquire_ctx ctx;
1207 	int ret = -EINVAL;
1208 
1209 	if (!drm_core_check_feature(dev, DRIVER_MODESET))
1210 		return -EOPNOTSUPP;
1211 
1212 	if (page_flip->flags & ~DRM_MODE_PAGE_FLIP_FLAGS)
1213 		return -EINVAL;
1214 
1215 	if (page_flip->sequence != 0 && !(page_flip->flags & DRM_MODE_PAGE_FLIP_TARGET))
1216 		return -EINVAL;
1217 
1218 	/* Only one of the DRM_MODE_PAGE_FLIP_TARGET_ABSOLUTE/RELATIVE flags
1219 	 * can be specified
1220 	 */
1221 	if ((page_flip->flags & DRM_MODE_PAGE_FLIP_TARGET) == DRM_MODE_PAGE_FLIP_TARGET)
1222 		return -EINVAL;
1223 
1224 	if ((page_flip->flags & DRM_MODE_PAGE_FLIP_ASYNC) && !dev->mode_config.async_page_flip)
1225 		return -EINVAL;
1226 
1227 	crtc = drm_crtc_find(dev, file_priv, page_flip->crtc_id);
1228 	if (!crtc)
1229 		return -ENOENT;
1230 
1231 	plane = crtc->primary;
1232 
1233 	if (!drm_lease_held(file_priv, plane->base.id))
1234 		return -EACCES;
1235 
1236 	if (crtc->funcs->page_flip_target) {
1237 		u32 current_vblank;
1238 		int r;
1239 
1240 		r = drm_crtc_vblank_get(crtc);
1241 		if (r)
1242 			return r;
1243 
1244 		current_vblank = (u32)drm_crtc_vblank_count(crtc);
1245 
1246 		switch (page_flip->flags & DRM_MODE_PAGE_FLIP_TARGET) {
1247 		case DRM_MODE_PAGE_FLIP_TARGET_ABSOLUTE:
1248 			if ((int)(target_vblank - current_vblank) > 1) {
1249 				DRM_DEBUG("Invalid absolute flip target %u, "
1250 					  "must be <= %u\n", target_vblank,
1251 					  current_vblank + 1);
1252 				drm_crtc_vblank_put(crtc);
1253 				return -EINVAL;
1254 			}
1255 			break;
1256 		case DRM_MODE_PAGE_FLIP_TARGET_RELATIVE:
1257 			if (target_vblank != 0 && target_vblank != 1) {
1258 				DRM_DEBUG("Invalid relative flip target %u, "
1259 					  "must be 0 or 1\n", target_vblank);
1260 				drm_crtc_vblank_put(crtc);
1261 				return -EINVAL;
1262 			}
1263 			target_vblank += current_vblank;
1264 			break;
1265 		default:
1266 			target_vblank = current_vblank +
1267 				!(page_flip->flags & DRM_MODE_PAGE_FLIP_ASYNC);
1268 			break;
1269 		}
1270 	} else if (crtc->funcs->page_flip == NULL ||
1271 		   (page_flip->flags & DRM_MODE_PAGE_FLIP_TARGET)) {
1272 		return -EINVAL;
1273 	}
1274 
1275 	drm_modeset_acquire_init(&ctx, DRM_MODESET_ACQUIRE_INTERRUPTIBLE);
1276 retry:
1277 	ret = drm_modeset_lock(&crtc->mutex, &ctx);
1278 	if (ret)
1279 		goto out;
1280 	ret = drm_modeset_lock(&plane->mutex, &ctx);
1281 	if (ret)
1282 		goto out;
1283 
1284 	if (plane->state)
1285 		old_fb = plane->state->fb;
1286 	else
1287 		old_fb = plane->fb;
1288 
1289 	if (old_fb == NULL) {
1290 		/* The framebuffer is currently unbound, presumably
1291 		 * due to a hotplug event, that userspace has not
1292 		 * yet discovered.
1293 		 */
1294 		ret = -EBUSY;
1295 		goto out;
1296 	}
1297 
1298 	fb = drm_framebuffer_lookup(dev, file_priv, page_flip->fb_id);
1299 	if (!fb) {
1300 		ret = -ENOENT;
1301 		goto out;
1302 	}
1303 
1304 	if (plane->state) {
1305 		const struct drm_plane_state *state = plane->state;
1306 
1307 		ret = drm_framebuffer_check_src_coords(state->src_x,
1308 						       state->src_y,
1309 						       state->src_w,
1310 						       state->src_h,
1311 						       fb);
1312 	} else {
1313 		ret = drm_crtc_check_viewport(crtc, crtc->x, crtc->y,
1314 					      &crtc->mode, fb);
1315 	}
1316 	if (ret)
1317 		goto out;
1318 
1319 	/*
1320 	 * Only check the FOURCC format code, excluding modifiers. This is
1321 	 * enough for all legacy drivers. Atomic drivers have their own
1322 	 * checks in their ->atomic_check implementation, which will
1323 	 * return -EINVAL if any hw or driver constraint is violated due
1324 	 * to modifier changes.
1325 	 */
1326 	if (old_fb->format->format != fb->format->format) {
1327 		DRM_DEBUG_KMS("Page flip is not allowed to change frame buffer format.\n");
1328 		ret = -EINVAL;
1329 		goto out;
1330 	}
1331 
1332 	if (page_flip->flags & DRM_MODE_PAGE_FLIP_EVENT) {
1333 		e = kzalloc(sizeof *e, GFP_KERNEL);
1334 		if (!e) {
1335 			ret = -ENOMEM;
1336 			goto out;
1337 		}
1338 
1339 		e->event.base.type = DRM_EVENT_FLIP_COMPLETE;
1340 		e->event.base.length = sizeof(e->event);
1341 		e->event.vbl.user_data = page_flip->user_data;
1342 		e->event.vbl.crtc_id = crtc->base.id;
1343 
1344 		ret = drm_event_reserve_init(dev, file_priv, &e->base, &e->event.base);
1345 		if (ret) {
1346 			kfree(e);
1347 			e = NULL;
1348 			goto out;
1349 		}
1350 	}
1351 
1352 	plane->old_fb = plane->fb;
1353 	if (crtc->funcs->page_flip_target)
1354 		ret = crtc->funcs->page_flip_target(crtc, fb, e,
1355 						    page_flip->flags,
1356 						    target_vblank,
1357 						    &ctx);
1358 	else
1359 		ret = crtc->funcs->page_flip(crtc, fb, e, page_flip->flags,
1360 					     &ctx);
1361 	if (ret) {
1362 		if (page_flip->flags & DRM_MODE_PAGE_FLIP_EVENT)
1363 			drm_event_cancel_free(dev, &e->base);
1364 		/* Keep the old fb, don't unref it. */
1365 		plane->old_fb = NULL;
1366 	} else {
1367 		if (!plane->state) {
1368 			plane->fb = fb;
1369 			drm_framebuffer_get(fb);
1370 		}
1371 	}
1372 
1373 out:
1374 	if (fb)
1375 		drm_framebuffer_put(fb);
1376 	if (plane->old_fb)
1377 		drm_framebuffer_put(plane->old_fb);
1378 	plane->old_fb = NULL;
1379 
1380 	if (ret == -EDEADLK) {
1381 		ret = drm_modeset_backoff(&ctx);
1382 		if (!ret)
1383 			goto retry;
1384 	}
1385 
1386 	drm_modeset_drop_locks(&ctx);
1387 	drm_modeset_acquire_fini(&ctx);
1388 
1389 	if (ret && crtc->funcs->page_flip_target)
1390 		drm_crtc_vblank_put(crtc);
1391 
1392 	return ret;
1393 }
1394 
1395 /**
1396  * DOC: damage tracking
1397  *
1398  * FB_DAMAGE_CLIPS is an optional plane property which provides a means to
1399  * specify a list of damage rectangles on a plane in framebuffer coordinates of
1400  * the framebuffer attached to the plane. In current context damage is the area
1401  * of plane framebuffer that has changed since last plane update (also called
1402  * page-flip), irrespective of whether currently attached framebuffer is same as
1403  * framebuffer attached during last plane update or not.
1404  *
1405  * FB_DAMAGE_CLIPS is a hint to kernel which could be helpful for some drivers
1406  * to optimize internally especially for virtual devices where each framebuffer
1407  * change needs to be transmitted over network, usb, etc.
1408  *
1409  * Since FB_DAMAGE_CLIPS is a hint so it is an optional property. User-space can
1410  * ignore damage clips property and in that case driver will do a full plane
1411  * update. In case damage clips are provided then it is guaranteed that the area
1412  * inside damage clips will be updated to plane. For efficiency driver can do
1413  * full update or can update more than specified in damage clips. Since driver
1414  * is free to read more, user-space must always render the entire visible
1415  * framebuffer. Otherwise there can be corruptions. Also, if a user-space
1416  * provides damage clips which doesn't encompass the actual damage to
1417  * framebuffer (since last plane update) can result in incorrect rendering.
1418  *
1419  * FB_DAMAGE_CLIPS is a blob property with the layout of blob data is simply an
1420  * array of &drm_mode_rect. Unlike plane &drm_plane_state.src coordinates,
1421  * damage clips are not in 16.16 fixed point. Similar to plane src in
1422  * framebuffer, damage clips cannot be negative. In damage clip, x1/y1 are
1423  * inclusive and x2/y2 are exclusive. While kernel does not error for overlapped
1424  * damage clips, it is strongly discouraged.
1425  *
1426  * Drivers that are interested in damage interface for plane should enable
1427  * FB_DAMAGE_CLIPS property by calling drm_plane_enable_fb_damage_clips().
1428  * Drivers implementing damage can use drm_atomic_helper_damage_iter_init() and
1429  * drm_atomic_helper_damage_iter_next() helper iterator function to get damage
1430  * rectangles clipped to &drm_plane_state.src.
1431  */
1432 
1433 /**
1434  * drm_plane_enable_fb_damage_clips - Enables plane fb damage clips property.
1435  * @plane: Plane on which to enable damage clips property.
1436  *
1437  * This function lets driver to enable the damage clips property on a plane.
1438  */
1439 void drm_plane_enable_fb_damage_clips(struct drm_plane *plane)
1440 {
1441 	struct drm_device *dev = plane->dev;
1442 	struct drm_mode_config *config = &dev->mode_config;
1443 
1444 	drm_object_attach_property(&plane->base, config->prop_fb_damage_clips,
1445 				   0);
1446 }
1447 EXPORT_SYMBOL(drm_plane_enable_fb_damage_clips);
1448 
1449 /**
1450  * drm_plane_get_damage_clips_count - Returns damage clips count.
1451  * @state: Plane state.
1452  *
1453  * Simple helper to get the number of &drm_mode_rect clips set by user-space
1454  * during plane update.
1455  *
1456  * Return: Number of clips in plane fb_damage_clips blob property.
1457  */
1458 unsigned int
1459 drm_plane_get_damage_clips_count(const struct drm_plane_state *state)
1460 {
1461 	return (state && state->fb_damage_clips) ?
1462 		state->fb_damage_clips->length/sizeof(struct drm_mode_rect) : 0;
1463 }
1464 EXPORT_SYMBOL(drm_plane_get_damage_clips_count);
1465 
1466 struct drm_mode_rect *
1467 __drm_plane_get_damage_clips(const struct drm_plane_state *state)
1468 {
1469 	return (struct drm_mode_rect *)((state && state->fb_damage_clips) ?
1470 					state->fb_damage_clips->data : NULL);
1471 }
1472 
1473 /**
1474  * drm_plane_get_damage_clips - Returns damage clips.
1475  * @state: Plane state.
1476  *
1477  * Note that this function returns uapi type &drm_mode_rect. Drivers might want
1478  * to use the helper functions drm_atomic_helper_damage_iter_init() and
1479  * drm_atomic_helper_damage_iter_next() or drm_atomic_helper_damage_merged() if
1480  * the driver can only handle a single damage region at most.
1481  *
1482  * Return: Damage clips in plane fb_damage_clips blob property.
1483  */
1484 struct drm_mode_rect *
1485 drm_plane_get_damage_clips(const struct drm_plane_state *state)
1486 {
1487 	struct drm_device *dev = state->plane->dev;
1488 	struct drm_mode_config *config = &dev->mode_config;
1489 
1490 	/* check that drm_plane_enable_fb_damage_clips() was called */
1491 	if (!drm_mode_obj_find_prop_id(&state->plane->base,
1492 				       config->prop_fb_damage_clips->base.id))
1493 		drm_warn_once(dev, "drm_plane_enable_fb_damage_clips() not called\n");
1494 
1495 	return __drm_plane_get_damage_clips(state);
1496 }
1497 EXPORT_SYMBOL(drm_plane_get_damage_clips);
1498 
1499 struct drm_property *
1500 drm_create_scaling_filter_prop(struct drm_device *dev,
1501 			       unsigned int supported_filters)
1502 {
1503 	struct drm_property *prop;
1504 	static const struct drm_prop_enum_list props[] = {
1505 		{ DRM_SCALING_FILTER_DEFAULT, "Default" },
1506 		{ DRM_SCALING_FILTER_NEAREST_NEIGHBOR, "Nearest Neighbor" },
1507 	};
1508 	unsigned int valid_mode_mask = BIT(DRM_SCALING_FILTER_DEFAULT) |
1509 				       BIT(DRM_SCALING_FILTER_NEAREST_NEIGHBOR);
1510 	int i;
1511 
1512 	if (WARN_ON((supported_filters & ~valid_mode_mask) ||
1513 		    ((supported_filters & BIT(DRM_SCALING_FILTER_DEFAULT)) == 0)))
1514 		return ERR_PTR(-EINVAL);
1515 
1516 	prop = drm_property_create(dev, DRM_MODE_PROP_ENUM,
1517 				   "SCALING_FILTER",
1518 				   hweight32(supported_filters));
1519 	if (!prop)
1520 		return ERR_PTR(-ENOMEM);
1521 
1522 	for (i = 0; i < ARRAY_SIZE(props); i++) {
1523 		int ret;
1524 
1525 		if (!(BIT(props[i].type) & supported_filters))
1526 			continue;
1527 
1528 		ret = drm_property_add_enum(prop, props[i].type,
1529 					    props[i].name);
1530 
1531 		if (ret) {
1532 			drm_property_destroy(dev, prop);
1533 
1534 			return ERR_PTR(ret);
1535 		}
1536 	}
1537 
1538 	return prop;
1539 }
1540 
1541 /**
1542  * drm_plane_create_scaling_filter_property - create a new scaling filter
1543  * property
1544  *
1545  * @plane: drm plane
1546  * @supported_filters: bitmask of supported scaling filters, must include
1547  *		       BIT(DRM_SCALING_FILTER_DEFAULT).
1548  *
1549  * This function lets driver to enable the scaling filter property on a given
1550  * plane.
1551  *
1552  * RETURNS:
1553  * Zero for success or -errno
1554  */
1555 int drm_plane_create_scaling_filter_property(struct drm_plane *plane,
1556 					     unsigned int supported_filters)
1557 {
1558 	struct drm_property *prop =
1559 		drm_create_scaling_filter_prop(plane->dev, supported_filters);
1560 
1561 	if (IS_ERR(prop))
1562 		return PTR_ERR(prop);
1563 
1564 	drm_object_attach_property(&plane->base, prop,
1565 				   DRM_SCALING_FILTER_DEFAULT);
1566 	plane->scaling_filter_property = prop;
1567 
1568 	return 0;
1569 }
1570 EXPORT_SYMBOL(drm_plane_create_scaling_filter_property);
1571