]> asedeno.scripts.mit.edu Git - linux.git/blob - drivers/gpu/drm/drm_gem_vram_helper.c
drm: Replace drm_gem_vram_push_to_system() with kunmap + unpin
[linux.git] / drivers / gpu / drm / drm_gem_vram_helper.c
1 // SPDX-License-Identifier: GPL-2.0-or-later
2
3 #include <drm/drm_gem_vram_helper.h>
4 #include <drm/drm_device.h>
5 #include <drm/drm_mode.h>
6 #include <drm/drm_prime.h>
7 #include <drm/drm_vram_mm_helper.h>
8 #include <drm/ttm/ttm_page_alloc.h>
9
10 /**
11  * DOC: overview
12  *
13  * This library provides a GEM buffer object that is backed by video RAM
14  * (VRAM). It can be used for framebuffer devices with dedicated memory.
15  */
16
17 /*
18  * Buffer-objects helpers
19  */
20
21 static void drm_gem_vram_cleanup(struct drm_gem_vram_object *gbo)
22 {
23         /* We got here via ttm_bo_put(), which means that the
24          * TTM buffer object in 'bo' has already been cleaned
25          * up; only release the GEM object.
26          */
27         drm_gem_object_release(&gbo->gem);
28 }
29
30 static void drm_gem_vram_destroy(struct drm_gem_vram_object *gbo)
31 {
32         drm_gem_vram_cleanup(gbo);
33         kfree(gbo);
34 }
35
36 static void ttm_buffer_object_destroy(struct ttm_buffer_object *bo)
37 {
38         struct drm_gem_vram_object *gbo = drm_gem_vram_of_bo(bo);
39
40         drm_gem_vram_destroy(gbo);
41 }
42
43 static void drm_gem_vram_placement(struct drm_gem_vram_object *gbo,
44                                    unsigned long pl_flag)
45 {
46         unsigned int i;
47         unsigned int c = 0;
48
49         gbo->placement.placement = gbo->placements;
50         gbo->placement.busy_placement = gbo->placements;
51
52         if (pl_flag & TTM_PL_FLAG_VRAM)
53                 gbo->placements[c++].flags = TTM_PL_FLAG_WC |
54                                              TTM_PL_FLAG_UNCACHED |
55                                              TTM_PL_FLAG_VRAM;
56
57         if (pl_flag & TTM_PL_FLAG_SYSTEM)
58                 gbo->placements[c++].flags = TTM_PL_MASK_CACHING |
59                                              TTM_PL_FLAG_SYSTEM;
60
61         if (!c)
62                 gbo->placements[c++].flags = TTM_PL_MASK_CACHING |
63                                              TTM_PL_FLAG_SYSTEM;
64
65         gbo->placement.num_placement = c;
66         gbo->placement.num_busy_placement = c;
67
68         for (i = 0; i < c; ++i) {
69                 gbo->placements[i].fpfn = 0;
70                 gbo->placements[i].lpfn = 0;
71         }
72 }
73
74 static int drm_gem_vram_init(struct drm_device *dev,
75                              struct ttm_bo_device *bdev,
76                              struct drm_gem_vram_object *gbo,
77                              size_t size, unsigned long pg_align,
78                              bool interruptible)
79 {
80         int ret;
81         size_t acc_size;
82
83         ret = drm_gem_object_init(dev, &gbo->gem, size);
84         if (ret)
85                 return ret;
86
87         acc_size = ttm_bo_dma_acc_size(bdev, size, sizeof(*gbo));
88
89         gbo->bo.bdev = bdev;
90         drm_gem_vram_placement(gbo, TTM_PL_FLAG_VRAM | TTM_PL_FLAG_SYSTEM);
91
92         ret = ttm_bo_init(bdev, &gbo->bo, size, ttm_bo_type_device,
93                           &gbo->placement, pg_align, interruptible, acc_size,
94                           NULL, NULL, ttm_buffer_object_destroy);
95         if (ret)
96                 goto err_drm_gem_object_release;
97
98         return 0;
99
100 err_drm_gem_object_release:
101         drm_gem_object_release(&gbo->gem);
102         return ret;
103 }
104
105 /**
106  * drm_gem_vram_create() - Creates a VRAM-backed GEM object
107  * @dev:                the DRM device
108  * @bdev:               the TTM BO device backing the object
109  * @size:               the buffer size in bytes
110  * @pg_align:           the buffer's alignment in multiples of the page size
111  * @interruptible:      sleep interruptible if waiting for memory
112  *
113  * Returns:
114  * A new instance of &struct drm_gem_vram_object on success, or
115  * an ERR_PTR()-encoded error code otherwise.
116  */
117 struct drm_gem_vram_object *drm_gem_vram_create(struct drm_device *dev,
118                                                 struct ttm_bo_device *bdev,
119                                                 size_t size,
120                                                 unsigned long pg_align,
121                                                 bool interruptible)
122 {
123         struct drm_gem_vram_object *gbo;
124         int ret;
125
126         gbo = kzalloc(sizeof(*gbo), GFP_KERNEL);
127         if (!gbo)
128                 return ERR_PTR(-ENOMEM);
129
130         ret = drm_gem_vram_init(dev, bdev, gbo, size, pg_align, interruptible);
131         if (ret < 0)
132                 goto err_kfree;
133
134         return gbo;
135
136 err_kfree:
137         kfree(gbo);
138         return ERR_PTR(ret);
139 }
140 EXPORT_SYMBOL(drm_gem_vram_create);
141
142 /**
143  * drm_gem_vram_put() - Releases a reference to a VRAM-backed GEM object
144  * @gbo:        the GEM VRAM object
145  *
146  * See ttm_bo_put() for more information.
147  */
148 void drm_gem_vram_put(struct drm_gem_vram_object *gbo)
149 {
150         ttm_bo_put(&gbo->bo);
151 }
152 EXPORT_SYMBOL(drm_gem_vram_put);
153
154 /**
155  * drm_gem_vram_reserve() - Reserves a VRAM-backed GEM object
156  * @gbo:        the GEM VRAM object
157  * @no_wait:    don't wait for buffer object to become available
158  *
159  * See ttm_bo_reserve() for more information.
160  *
161  * Returns:
162  * 0 on success, or
163  * a negative error code otherwise
164  */
165 int drm_gem_vram_reserve(struct drm_gem_vram_object *gbo, bool no_wait)
166 {
167         return ttm_bo_reserve(&gbo->bo, true, no_wait, NULL);
168 }
169 EXPORT_SYMBOL(drm_gem_vram_reserve);
170
171 /**
172  * drm_gem_vram_unreserve() - \
173         Release a reservation acquired by drm_gem_vram_reserve()
174  * @gbo:        the GEM VRAM object
175  *
176  * See ttm_bo_unreserve() for more information.
177  */
178 void drm_gem_vram_unreserve(struct drm_gem_vram_object *gbo)
179 {
180         ttm_bo_unreserve(&gbo->bo);
181 }
182 EXPORT_SYMBOL(drm_gem_vram_unreserve);
183
184 /**
185  * drm_gem_vram_mmap_offset() - Returns a GEM VRAM object's mmap offset
186  * @gbo:        the GEM VRAM object
187  *
188  * See drm_vma_node_offset_addr() for more information.
189  *
190  * Returns:
191  * The buffer object's offset for userspace mappings on success, or
192  * 0 if no offset is allocated.
193  */
194 u64 drm_gem_vram_mmap_offset(struct drm_gem_vram_object *gbo)
195 {
196         return drm_vma_node_offset_addr(&gbo->bo.vma_node);
197 }
198 EXPORT_SYMBOL(drm_gem_vram_mmap_offset);
199
200 /**
201  * drm_gem_vram_offset() - \
202         Returns a GEM VRAM object's offset in video memory
203  * @gbo:        the GEM VRAM object
204  *
205  * This function returns the buffer object's offset in the device's video
206  * memory. The buffer object has to be pinned to %TTM_PL_VRAM.
207  *
208  * Returns:
209  * The buffer object's offset in video memory on success, or
210  * a negative errno code otherwise.
211  */
212 s64 drm_gem_vram_offset(struct drm_gem_vram_object *gbo)
213 {
214         if (WARN_ON_ONCE(!gbo->pin_count))
215                 return (s64)-ENODEV;
216         return gbo->bo.offset;
217 }
218 EXPORT_SYMBOL(drm_gem_vram_offset);
219
220 /**
221  * drm_gem_vram_pin() - Pins a GEM VRAM object in a region.
222  * @gbo:        the GEM VRAM object
223  * @pl_flag:    a bitmask of possible memory regions
224  *
225  * Pinning a buffer object ensures that it is not evicted from
226  * a memory region. A pinned buffer object has to be unpinned before
227  * it can be pinned to another region.
228  *
229  * Returns:
230  * 0 on success, or
231  * a negative error code otherwise.
232  */
233 int drm_gem_vram_pin(struct drm_gem_vram_object *gbo, unsigned long pl_flag)
234 {
235         int i, ret;
236         struct ttm_operation_ctx ctx = { false, false };
237
238         ret = ttm_bo_reserve(&gbo->bo, true, false, NULL);
239         if (ret < 0)
240                 return ret;
241
242         if (gbo->pin_count)
243                 goto out;
244
245         drm_gem_vram_placement(gbo, pl_flag);
246         for (i = 0; i < gbo->placement.num_placement; ++i)
247                 gbo->placements[i].flags |= TTM_PL_FLAG_NO_EVICT;
248
249         ret = ttm_bo_validate(&gbo->bo, &gbo->placement, &ctx);
250         if (ret < 0)
251                 goto err_ttm_bo_unreserve;
252
253 out:
254         ++gbo->pin_count;
255         ttm_bo_unreserve(&gbo->bo);
256
257         return 0;
258
259 err_ttm_bo_unreserve:
260         ttm_bo_unreserve(&gbo->bo);
261         return ret;
262 }
263 EXPORT_SYMBOL(drm_gem_vram_pin);
264
265 /**
266  * drm_gem_vram_pin_reserved() - Pins a GEM VRAM object in a region.
267  * @gbo:        the GEM VRAM object
268  * @pl_flag:    a bitmask of possible memory regions
269  *
270  * Pinning a buffer object ensures that it is not evicted from
271  * a memory region. A pinned buffer object has to be unpinned before
272  * it can be pinned to another region.
273  *
274  * This function pins a GEM VRAM object that has already been
275  * reserved. Use drm_gem_vram_pin() if possible.
276  *
277  * Returns:
278  * 0 on success, or
279  * a negative error code otherwise.
280  */
281 int drm_gem_vram_pin_reserved(struct drm_gem_vram_object *gbo,
282                               unsigned long pl_flag)
283 {
284         int i, ret;
285         struct ttm_operation_ctx ctx = { false, false };
286
287         if (gbo->pin_count) {
288                 ++gbo->pin_count;
289                 return 0;
290         }
291
292         drm_gem_vram_placement(gbo, pl_flag);
293         for (i = 0; i < gbo->placement.num_placement; ++i)
294                 gbo->placements[i].flags |= TTM_PL_FLAG_NO_EVICT;
295
296         ret = ttm_bo_validate(&gbo->bo, &gbo->placement, &ctx);
297         if (ret < 0)
298                 return ret;
299
300         gbo->pin_count = 1;
301
302         return 0;
303 }
304 EXPORT_SYMBOL(drm_gem_vram_pin_reserved);
305
306 /**
307  * drm_gem_vram_unpin() - Unpins a GEM VRAM object
308  * @gbo:        the GEM VRAM object
309  *
310  * Returns:
311  * 0 on success, or
312  * a negative error code otherwise.
313  */
314 int drm_gem_vram_unpin(struct drm_gem_vram_object *gbo)
315 {
316         int i, ret;
317         struct ttm_operation_ctx ctx = { false, false };
318
319         ret = ttm_bo_reserve(&gbo->bo, true, false, NULL);
320         if (ret < 0)
321                 return ret;
322
323         if (WARN_ON_ONCE(!gbo->pin_count))
324                 goto out;
325
326         --gbo->pin_count;
327         if (gbo->pin_count)
328                 goto out;
329
330         for (i = 0; i < gbo->placement.num_placement ; ++i)
331                 gbo->placements[i].flags &= ~TTM_PL_FLAG_NO_EVICT;
332
333         ret = ttm_bo_validate(&gbo->bo, &gbo->placement, &ctx);
334         if (ret < 0)
335                 goto err_ttm_bo_unreserve;
336
337 out:
338         ttm_bo_unreserve(&gbo->bo);
339
340         return 0;
341
342 err_ttm_bo_unreserve:
343         ttm_bo_unreserve(&gbo->bo);
344         return ret;
345 }
346 EXPORT_SYMBOL(drm_gem_vram_unpin);
347
348 /**
349  * drm_gem_vram_unpin_reserved() - Unpins a GEM VRAM object
350  * @gbo:        the GEM VRAM object
351  *
352  * This function unpins a GEM VRAM object that has already been
353  * reserved. Use drm_gem_vram_unpin() if possible.
354  *
355  * Returns:
356  * 0 on success, or
357  * a negative error code otherwise.
358  */
359 int drm_gem_vram_unpin_reserved(struct drm_gem_vram_object *gbo)
360 {
361         int i, ret;
362         struct ttm_operation_ctx ctx = { false, false };
363
364         if (WARN_ON_ONCE(!gbo->pin_count))
365                 return 0;
366
367         --gbo->pin_count;
368         if (gbo->pin_count)
369                 return 0;
370
371         for (i = 0; i < gbo->placement.num_placement ; ++i)
372                 gbo->placements[i].flags &= ~TTM_PL_FLAG_NO_EVICT;
373
374         ret = ttm_bo_validate(&gbo->bo, &gbo->placement, &ctx);
375         if (ret < 0)
376                 return ret;
377
378         return 0;
379 }
380 EXPORT_SYMBOL(drm_gem_vram_unpin_reserved);
381
382 /**
383  * drm_gem_vram_kmap_at() - Maps a GEM VRAM object into kernel address space
384  * @gbo:        the GEM VRAM object
385  * @map:        establish a mapping if necessary
386  * @is_iomem:   returns true if the mapped memory is I/O memory, or false \
387         otherwise; can be NULL
388  * @kmap:       the mapping's kmap object
389  *
390  * This function maps the buffer object into the kernel's address space
391  * or returns the current mapping. If the parameter map is false, the
392  * function only queries the current mapping, but does not establish a
393  * new one.
394  *
395  * Returns:
396  * The buffers virtual address if mapped, or
397  * NULL if not mapped, or
398  * an ERR_PTR()-encoded error code otherwise.
399  */
400 void *drm_gem_vram_kmap_at(struct drm_gem_vram_object *gbo, bool map,
401                            bool *is_iomem, struct ttm_bo_kmap_obj *kmap)
402 {
403         int ret;
404
405         if (kmap->virtual || !map)
406                 goto out;
407
408         ret = ttm_bo_kmap(&gbo->bo, 0, gbo->bo.num_pages, kmap);
409         if (ret)
410                 return ERR_PTR(ret);
411
412 out:
413         if (!is_iomem)
414                 return kmap->virtual;
415         if (!kmap->virtual) {
416                 *is_iomem = false;
417                 return NULL;
418         }
419         return ttm_kmap_obj_virtual(kmap, is_iomem);
420 }
421 EXPORT_SYMBOL(drm_gem_vram_kmap_at);
422
423 /**
424  * drm_gem_vram_kmap() - Maps a GEM VRAM object into kernel address space
425  * @gbo:        the GEM VRAM object
426  * @map:        establish a mapping if necessary
427  * @is_iomem:   returns true if the mapped memory is I/O memory, or false \
428         otherwise; can be NULL
429  *
430  * This function maps the buffer object into the kernel's address space
431  * or returns the current mapping. If the parameter map is false, the
432  * function only queries the current mapping, but does not establish a
433  * new one.
434  *
435  * Returns:
436  * The buffers virtual address if mapped, or
437  * NULL if not mapped, or
438  * an ERR_PTR()-encoded error code otherwise.
439  */
440 void *drm_gem_vram_kmap(struct drm_gem_vram_object *gbo, bool map,
441                         bool *is_iomem)
442 {
443         return drm_gem_vram_kmap_at(gbo, map, is_iomem, &gbo->kmap);
444 }
445 EXPORT_SYMBOL(drm_gem_vram_kmap);
446
447 /**
448  * drm_gem_vram_kunmap_at() - Unmaps a GEM VRAM object
449  * @gbo:        the GEM VRAM object
450  * @kmap:       the mapping's kmap object
451  */
452 void drm_gem_vram_kunmap_at(struct drm_gem_vram_object *gbo,
453                             struct ttm_bo_kmap_obj *kmap)
454 {
455         if (!kmap->virtual)
456                 return;
457
458         ttm_bo_kunmap(kmap);
459         kmap->virtual = NULL;
460 }
461 EXPORT_SYMBOL(drm_gem_vram_kunmap_at);
462
463 /**
464  * drm_gem_vram_kunmap() - Unmaps a GEM VRAM object
465  * @gbo:        the GEM VRAM object
466  */
467 void drm_gem_vram_kunmap(struct drm_gem_vram_object *gbo)
468 {
469         drm_gem_vram_kunmap_at(gbo, &gbo->kmap);
470 }
471 EXPORT_SYMBOL(drm_gem_vram_kunmap);
472
473 /**
474  * drm_gem_vram_fill_create_dumb() - \
475         Helper for implementing &struct drm_driver.dumb_create
476  * @file:               the DRM file
477  * @dev:                the DRM device
478  * @bdev:               the TTM BO device managing the buffer object
479  * @pg_align:           the buffer's alignment in multiples of the page size
480  * @interruptible:      sleep interruptible if waiting for memory
481  * @args:               the arguments as provided to \
482                                 &struct drm_driver.dumb_create
483  *
484  * This helper function fills &struct drm_mode_create_dumb, which is used
485  * by &struct drm_driver.dumb_create. Implementations of this interface
486  * should forwards their arguments to this helper, plus the driver-specific
487  * parameters.
488  *
489  * Returns:
490  * 0 on success, or
491  * a negative error code otherwise.
492  */
493 int drm_gem_vram_fill_create_dumb(struct drm_file *file,
494                                   struct drm_device *dev,
495                                   struct ttm_bo_device *bdev,
496                                   unsigned long pg_align,
497                                   bool interruptible,
498                                   struct drm_mode_create_dumb *args)
499 {
500         size_t pitch, size;
501         struct drm_gem_vram_object *gbo;
502         int ret;
503         u32 handle;
504
505         pitch = args->width * ((args->bpp + 7) / 8);
506         size = pitch * args->height;
507
508         size = roundup(size, PAGE_SIZE);
509         if (!size)
510                 return -EINVAL;
511
512         gbo = drm_gem_vram_create(dev, bdev, size, pg_align, interruptible);
513         if (IS_ERR(gbo))
514                 return PTR_ERR(gbo);
515
516         ret = drm_gem_handle_create(file, &gbo->gem, &handle);
517         if (ret)
518                 goto err_drm_gem_object_put_unlocked;
519
520         drm_gem_object_put_unlocked(&gbo->gem);
521
522         args->pitch = pitch;
523         args->size = size;
524         args->handle = handle;
525
526         return 0;
527
528 err_drm_gem_object_put_unlocked:
529         drm_gem_object_put_unlocked(&gbo->gem);
530         return ret;
531 }
532 EXPORT_SYMBOL(drm_gem_vram_fill_create_dumb);
533
534 /*
535  * Helpers for struct ttm_bo_driver
536  */
537
538 static bool drm_is_gem_vram(struct ttm_buffer_object *bo)
539 {
540         return (bo->destroy == ttm_buffer_object_destroy);
541 }
542
543 /**
544  * drm_gem_vram_bo_driver_evict_flags() - \
545         Implements &struct ttm_bo_driver.evict_flags
546  * @bo: TTM buffer object. Refers to &struct drm_gem_vram_object.bo
547  * @pl: TTM placement information.
548  */
549 void drm_gem_vram_bo_driver_evict_flags(struct ttm_buffer_object *bo,
550                                         struct ttm_placement *pl)
551 {
552         struct drm_gem_vram_object *gbo;
553
554         /* TTM may pass BOs that are not GEM VRAM BOs. */
555         if (!drm_is_gem_vram(bo))
556                 return;
557
558         gbo = drm_gem_vram_of_bo(bo);
559         drm_gem_vram_placement(gbo, TTM_PL_FLAG_SYSTEM);
560         *pl = gbo->placement;
561 }
562 EXPORT_SYMBOL(drm_gem_vram_bo_driver_evict_flags);
563
564 /**
565  * drm_gem_vram_bo_driver_verify_access() - \
566         Implements &struct ttm_bo_driver.verify_access
567  * @bo:         TTM buffer object. Refers to &struct drm_gem_vram_object.bo
568  * @filp:       File pointer.
569  *
570  * Returns:
571  * 0 on success, or
572  * a negative errno code otherwise.
573  */
574 int drm_gem_vram_bo_driver_verify_access(struct ttm_buffer_object *bo,
575                                          struct file *filp)
576 {
577         struct drm_gem_vram_object *gbo = drm_gem_vram_of_bo(bo);
578
579         return drm_vma_node_verify_access(&gbo->gem.vma_node,
580                                           filp->private_data);
581 }
582 EXPORT_SYMBOL(drm_gem_vram_bo_driver_verify_access);
583
584 /**
585  * drm_gem_vram_mm_funcs - Functions for &struct drm_vram_mm
586  *
587  * Most users of @struct drm_gem_vram_object will also use
588  * @struct drm_vram_mm. This instance of &struct drm_vram_mm_funcs
589  * can be used to connect both.
590  */
591 const struct drm_vram_mm_funcs drm_gem_vram_mm_funcs = {
592         .evict_flags = drm_gem_vram_bo_driver_evict_flags,
593         .verify_access = drm_gem_vram_bo_driver_verify_access
594 };
595 EXPORT_SYMBOL(drm_gem_vram_mm_funcs);
596
597 /*
598  * Helpers for struct drm_driver
599  */
600
601 /**
602  * drm_gem_vram_driver_gem_free_object_unlocked() - \
603         Implements &struct drm_driver.gem_free_object_unlocked
604  * @gem:        GEM object. Refers to &struct drm_gem_vram_object.gem
605  */
606 void drm_gem_vram_driver_gem_free_object_unlocked(struct drm_gem_object *gem)
607 {
608         struct drm_gem_vram_object *gbo = drm_gem_vram_of_gem(gem);
609
610         drm_gem_vram_put(gbo);
611 }
612 EXPORT_SYMBOL(drm_gem_vram_driver_gem_free_object_unlocked);
613
614 /**
615  * drm_gem_vram_driver_create_dumb() - \
616         Implements &struct drm_driver.dumb_create
617  * @file:               the DRM file
618  * @dev:                the DRM device
619  * @args:               the arguments as provided to \
620                                 &struct drm_driver.dumb_create
621  *
622  * This function requires the driver to use @drm_device.vram_mm for its
623  * instance of VRAM MM.
624  *
625  * Returns:
626  * 0 on success, or
627  * a negative error code otherwise.
628  */
629 int drm_gem_vram_driver_dumb_create(struct drm_file *file,
630                                     struct drm_device *dev,
631                                     struct drm_mode_create_dumb *args)
632 {
633         if (WARN_ONCE(!dev->vram_mm, "VRAM MM not initialized"))
634                 return -EINVAL;
635
636         return drm_gem_vram_fill_create_dumb(file, dev, &dev->vram_mm->bdev, 0,
637                                              false, args);
638 }
639 EXPORT_SYMBOL(drm_gem_vram_driver_dumb_create);
640
641 /**
642  * drm_gem_vram_driver_dumb_mmap_offset() - \
643         Implements &struct drm_driver.dumb_mmap_offset
644  * @file:       DRM file pointer.
645  * @dev:        DRM device.
646  * @handle:     GEM handle
647  * @offset:     Returns the mapping's memory offset on success
648  *
649  * Returns:
650  * 0 on success, or
651  * a negative errno code otherwise.
652  */
653 int drm_gem_vram_driver_dumb_mmap_offset(struct drm_file *file,
654                                          struct drm_device *dev,
655                                          uint32_t handle, uint64_t *offset)
656 {
657         struct drm_gem_object *gem;
658         struct drm_gem_vram_object *gbo;
659
660         gem = drm_gem_object_lookup(file, handle);
661         if (!gem)
662                 return -ENOENT;
663
664         gbo = drm_gem_vram_of_gem(gem);
665         *offset = drm_gem_vram_mmap_offset(gbo);
666
667         drm_gem_object_put_unlocked(gem);
668
669         return 0;
670 }
671 EXPORT_SYMBOL(drm_gem_vram_driver_dumb_mmap_offset);
672
673 /*
674  * PRIME helpers for struct drm_driver
675  */
676
677 /**
678  * drm_gem_vram_driver_gem_prime_pin() - \
679         Implements &struct drm_driver.gem_prime_pin
680  * @gem:        The GEM object to pin
681  *
682  * Returns:
683  * 0 on success, or
684  * a negative errno code otherwise.
685  */
686 int drm_gem_vram_driver_gem_prime_pin(struct drm_gem_object *gem)
687 {
688         struct drm_gem_vram_object *gbo = drm_gem_vram_of_gem(gem);
689
690         return drm_gem_vram_pin(gbo, DRM_GEM_VRAM_PL_FLAG_VRAM);
691 }
692 EXPORT_SYMBOL(drm_gem_vram_driver_gem_prime_pin);
693
694 /**
695  * drm_gem_vram_driver_gem_prime_unpin() - \
696         Implements &struct drm_driver.gem_prime_unpin
697  * @gem:        The GEM object to unpin
698  */
699 void drm_gem_vram_driver_gem_prime_unpin(struct drm_gem_object *gem)
700 {
701         struct drm_gem_vram_object *gbo = drm_gem_vram_of_gem(gem);
702
703         drm_gem_vram_unpin(gbo);
704 }
705 EXPORT_SYMBOL(drm_gem_vram_driver_gem_prime_unpin);
706
707 /**
708  * drm_gem_vram_driver_gem_prime_vmap() - \
709         Implements &struct drm_driver.gem_prime_vmap
710  * @gem:        The GEM object to map
711  *
712  * Returns:
713  * The buffers virtual address on success, or
714  * NULL otherwise.
715  */
716 void *drm_gem_vram_driver_gem_prime_vmap(struct drm_gem_object *gem)
717 {
718         struct drm_gem_vram_object *gbo = drm_gem_vram_of_gem(gem);
719         int ret;
720         void *base;
721
722         ret = drm_gem_vram_pin(gbo, DRM_GEM_VRAM_PL_FLAG_VRAM);
723         if (ret)
724                 return NULL;
725         base = drm_gem_vram_kmap(gbo, true, NULL);
726         if (IS_ERR(base)) {
727                 drm_gem_vram_unpin(gbo);
728                 return NULL;
729         }
730         return base;
731 }
732 EXPORT_SYMBOL(drm_gem_vram_driver_gem_prime_vmap);
733
734 /**
735  * drm_gem_vram_driver_gem_prime_vunmap() - \
736         Implements &struct drm_driver.gem_prime_vunmap
737  * @gem:        The GEM object to unmap
738  * @vaddr:      The mapping's base address
739  */
740 void drm_gem_vram_driver_gem_prime_vunmap(struct drm_gem_object *gem,
741                                           void *vaddr)
742 {
743         struct drm_gem_vram_object *gbo = drm_gem_vram_of_gem(gem);
744
745         drm_gem_vram_kunmap(gbo);
746         drm_gem_vram_unpin(gbo);
747 }
748 EXPORT_SYMBOL(drm_gem_vram_driver_gem_prime_vunmap);
749
750 /**
751  * drm_gem_vram_driver_gem_prime_mmap() - \
752         Implements &struct drm_driver.gem_prime_mmap
753  * @gem:        The GEM object to map
754  * @vma:        The VMA describing the mapping
755  *
756  * Returns:
757  * 0 on success, or
758  * a negative errno code otherwise.
759  */
760 int drm_gem_vram_driver_gem_prime_mmap(struct drm_gem_object *gem,
761                                        struct vm_area_struct *vma)
762 {
763         struct drm_gem_vram_object *gbo = drm_gem_vram_of_gem(gem);
764
765         gbo->gem.vma_node.vm_node.start = gbo->bo.vma_node.vm_node.start;
766         return drm_gem_prime_mmap(gem, vma);
767 }
768 EXPORT_SYMBOL(drm_gem_vram_driver_gem_prime_mmap);