1 /* $NetBSD: nouveau_bo.c,v 1.19 2021/12/19 10:51:56 riastradh Exp $ */
2
3 /*
4 * Copyright 2007 Dave Airlied
5 * All Rights Reserved.
6 *
7 * Permission is hereby granted, free of charge, to any person obtaining a
8 * copy of this software and associated documentation files (the "Software"),
9 * to deal in the Software without restriction, including without limitation
10 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
11 * and/or sell copies of the Software, and to permit persons to whom the
12 * Software is furnished to do so, subject to the following conditions:
13 *
14 * The above copyright notice and this permission notice (including the next
15 * paragraph) shall be included in all copies or substantial portions of the
16 * Software.
17 *
18 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
20 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
21 * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
22 * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
23 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
24 * OTHER DEALINGS IN THE SOFTWARE.
25 */
26 /*
27 * Authors: Dave Airlied <airlied@linux.ie>
28 * Ben Skeggs <darktama@iinet.net.au>
29 * Jeremy Kolb <jkolb@brandeis.edu>
30 */
31
32 #include <sys/cdefs.h>
33 __KERNEL_RCSID(0, "$NetBSD: nouveau_bo.c,v 1.19 2021/12/19 10:51:56 riastradh Exp $");
34
35 #include <linux/dma-mapping.h>
36 #include <linux/swiotlb.h>
37
38 #include "nouveau_drv.h"
39 #include "nouveau_dma.h"
40 #include "nouveau_fence.h"
41
42 #include "nouveau_bo.h"
43 #include "nouveau_ttm.h"
44 #include "nouveau_gem.h"
45 #include "nouveau_mem.h"
46 #include "nouveau_vmm.h"
47
48 #include <nvif/class.h>
49 #include <nvif/if500b.h>
50 #include <nvif/if900b.h>
51
52 /*
53 * NV10-NV40 tiling helpers
54 */
55
56 static void
nv10_bo_update_tile_region(struct drm_device * dev,struct nouveau_drm_tile * reg,u32 addr,u32 size,u32 pitch,u32 flags)57 nv10_bo_update_tile_region(struct drm_device *dev, struct nouveau_drm_tile *reg,
58 u32 addr, u32 size, u32 pitch, u32 flags)
59 {
60 struct nouveau_drm *drm = nouveau_drm(dev);
61 int i = reg - drm->tile.reg;
62 struct nvkm_fb *fb = nvxx_fb(&drm->client.device);
63 struct nvkm_fb_tile *tile = &fb->tile.region[i];
64
65 nouveau_fence_unref(®->fence);
66
67 if (tile->pitch)
68 nvkm_fb_tile_fini(fb, i, tile);
69
70 if (pitch)
71 nvkm_fb_tile_init(fb, i, addr, size, pitch, flags, tile);
72
73 nvkm_fb_tile_prog(fb, i, tile);
74 }
75
76 static struct nouveau_drm_tile *
nv10_bo_get_tile_region(struct drm_device * dev,int i)77 nv10_bo_get_tile_region(struct drm_device *dev, int i)
78 {
79 struct nouveau_drm *drm = nouveau_drm(dev);
80 struct nouveau_drm_tile *tile = &drm->tile.reg[i];
81
82 spin_lock(&drm->tile.lock);
83
84 if (!tile->used &&
85 (!tile->fence || nouveau_fence_done(tile->fence)))
86 tile->used = true;
87 else
88 tile = NULL;
89
90 spin_unlock(&drm->tile.lock);
91 return tile;
92 }
93
94 static void
nv10_bo_put_tile_region(struct drm_device * dev,struct nouveau_drm_tile * tile,struct dma_fence * fence)95 nv10_bo_put_tile_region(struct drm_device *dev, struct nouveau_drm_tile *tile,
96 struct dma_fence *fence)
97 {
98 struct nouveau_drm *drm = nouveau_drm(dev);
99
100 if (tile) {
101 spin_lock(&drm->tile.lock);
102 tile->fence = (struct nouveau_fence *)dma_fence_get(fence);
103 tile->used = false;
104 spin_unlock(&drm->tile.lock);
105 }
106 }
107
108 static struct nouveau_drm_tile *
nv10_bo_set_tiling(struct drm_device * dev,u32 addr,u32 size,u32 pitch,u32 zeta)109 nv10_bo_set_tiling(struct drm_device *dev, u32 addr,
110 u32 size, u32 pitch, u32 zeta)
111 {
112 struct nouveau_drm *drm = nouveau_drm(dev);
113 struct nvkm_fb *fb = nvxx_fb(&drm->client.device);
114 struct nouveau_drm_tile *tile, *found = NULL;
115 int i;
116
117 for (i = 0; i < fb->tile.regions; i++) {
118 tile = nv10_bo_get_tile_region(dev, i);
119
120 if (pitch && !found) {
121 found = tile;
122 continue;
123
124 } else if (tile && fb->tile.region[i].pitch) {
125 /* Kill an unused tile region. */
126 nv10_bo_update_tile_region(dev, tile, 0, 0, 0, 0);
127 }
128
129 nv10_bo_put_tile_region(dev, tile, NULL);
130 }
131
132 if (found)
133 nv10_bo_update_tile_region(dev, found, addr, size, pitch, zeta);
134 return found;
135 }
136
137 static void
nouveau_bo_del_ttm(struct ttm_buffer_object * bo)138 nouveau_bo_del_ttm(struct ttm_buffer_object *bo)
139 {
140 struct nouveau_drm *drm = nouveau_bdev(bo->bdev);
141 struct drm_device *dev = drm->dev;
142 struct nouveau_bo *nvbo = nouveau_bo(bo);
143
144 WARN_ON(nvbo->pin_refcnt > 0);
145 nv10_bo_put_tile_region(dev, nvbo->tile, NULL);
146
147 /*
148 * If nouveau_bo_new() allocated this buffer, the GEM object was never
149 * initialized, so don't attempt to release it.
150 */
151 if (bo->base.dev)
152 drm_gem_object_release(&bo->base);
153
154 kfree(nvbo);
155 }
156
157 static inline u64
roundup_64(u64 x,u32 y)158 roundup_64(u64 x, u32 y)
159 {
160 x += y - 1;
161 do_div(x, y);
162 return x * y;
163 }
164
165 static void
nouveau_bo_fixup_align(struct nouveau_bo * nvbo,u32 flags,int * align,u64 * size)166 nouveau_bo_fixup_align(struct nouveau_bo *nvbo, u32 flags,
167 int *align, u64 *size)
168 {
169 struct nouveau_drm *drm = nouveau_bdev(nvbo->bo.bdev);
170 struct nvif_device *device = &drm->client.device;
171
172 if (device->info.family < NV_DEVICE_INFO_V0_TESLA) {
173 if (nvbo->mode) {
174 if (device->info.chipset >= 0x40) {
175 *align = 65536;
176 *size = roundup_64(*size, 64 * nvbo->mode);
177
178 } else if (device->info.chipset >= 0x30) {
179 *align = 32768;
180 *size = roundup_64(*size, 64 * nvbo->mode);
181
182 } else if (device->info.chipset >= 0x20) {
183 *align = 16384;
184 *size = roundup_64(*size, 64 * nvbo->mode);
185
186 } else if (device->info.chipset >= 0x10) {
187 *align = 16384;
188 *size = roundup_64(*size, 32 * nvbo->mode);
189 }
190 }
191 } else {
192 *size = roundup_64(*size, (1 << nvbo->page));
193 *align = max((1 << nvbo->page), *align);
194 }
195
196 *size = roundup_64(*size, PAGE_SIZE);
197 }
198
199 struct nouveau_bo *
nouveau_bo_alloc(struct nouveau_cli * cli,u64 * size,int * align,u32 flags,u32 tile_mode,u32 tile_flags)200 nouveau_bo_alloc(struct nouveau_cli *cli, u64 *size, int *align, u32 flags,
201 u32 tile_mode, u32 tile_flags)
202 {
203 struct nouveau_drm *drm = cli->drm;
204 struct nouveau_bo *nvbo;
205 struct nvif_mmu *mmu = &cli->mmu;
206 struct nvif_vmm *vmm = cli->svm.cli ? &cli->svm.vmm : &cli->vmm.vmm;
207 int i, pi = -1;
208
209 if (!*size) {
210 NV_WARN(drm, "skipped size %016"PRIx64"\n", *size);
211 return ERR_PTR(-EINVAL);
212 }
213
214 nvbo = kzalloc(sizeof(struct nouveau_bo), GFP_KERNEL);
215 if (!nvbo)
216 return ERR_PTR(-ENOMEM);
217 INIT_LIST_HEAD(&nvbo->head);
218 INIT_LIST_HEAD(&nvbo->entry);
219 INIT_LIST_HEAD(&nvbo->vma_list);
220 nvbo->bo.bdev = &drm->ttm.bdev;
221
222 /* This is confusing, and doesn't actually mean we want an uncached
223 * mapping, but is what NOUVEAU_GEM_DOMAIN_COHERENT gets translated
224 * into in nouveau_gem_new().
225 */
226 if (flags & TTM_PL_FLAG_UNCACHED) {
227 /* Determine if we can get a cache-coherent map, forcing
228 * uncached mapping if we can't.
229 */
230 if (!nouveau_drm_use_coherent_gpu_mapping(drm))
231 nvbo->force_coherent = true;
232 }
233
234 if (cli->device.info.family >= NV_DEVICE_INFO_V0_FERMI) {
235 nvbo->kind = (tile_flags & 0x0000ff00) >> 8;
236 if (!nvif_mmu_kind_valid(mmu, nvbo->kind)) {
237 kfree(nvbo);
238 return ERR_PTR(-EINVAL);
239 }
240
241 nvbo->comp = mmu->kind[nvbo->kind] != nvbo->kind;
242 } else
243 if (cli->device.info.family >= NV_DEVICE_INFO_V0_TESLA) {
244 nvbo->kind = (tile_flags & 0x00007f00) >> 8;
245 nvbo->comp = (tile_flags & 0x00030000) >> 16;
246 if (!nvif_mmu_kind_valid(mmu, nvbo->kind)) {
247 kfree(nvbo);
248 return ERR_PTR(-EINVAL);
249 }
250 } else {
251 nvbo->zeta = (tile_flags & 0x00000007);
252 }
253 nvbo->mode = tile_mode;
254 nvbo->contig = !(tile_flags & NOUVEAU_GEM_TILE_NONCONTIG);
255
256 /* Determine the desirable target GPU page size for the buffer. */
257 for (i = 0; i < vmm->page_nr; i++) {
258 /* Because we cannot currently allow VMM maps to fail
259 * during buffer migration, we need to determine page
260 * size for the buffer up-front, and pre-allocate its
261 * page tables.
262 *
263 * Skip page sizes that can't support needed domains.
264 */
265 if (cli->device.info.family > NV_DEVICE_INFO_V0_CURIE &&
266 (flags & TTM_PL_FLAG_VRAM) && !vmm->page[i].vram)
267 continue;
268 if ((flags & TTM_PL_FLAG_TT) &&
269 (!vmm->page[i].host || vmm->page[i].shift > PAGE_SHIFT))
270 continue;
271
272 /* Select this page size if it's the first that supports
273 * the potential memory domains, or when it's compatible
274 * with the requested compression settings.
275 */
276 if (pi < 0 || !nvbo->comp || vmm->page[i].comp)
277 pi = i;
278
279 /* Stop once the buffer is larger than the current page size. */
280 if (*size >= 1ULL << vmm->page[i].shift)
281 break;
282 }
283
284 if (WARN_ON(pi < 0))
285 return ERR_PTR(-EINVAL);
286
287 /* Disable compression if suitable settings couldn't be found. */
288 if (nvbo->comp && !vmm->page[pi].comp) {
289 if (mmu->object.oclass >= NVIF_CLASS_MMU_GF100)
290 nvbo->kind = mmu->kind[nvbo->kind];
291 nvbo->comp = 0;
292 }
293 nvbo->page = vmm->page[pi].shift;
294
295 nouveau_bo_fixup_align(nvbo, flags, align, size);
296
297 return nvbo;
298 }
299
300 int
nouveau_bo_init(struct nouveau_bo * nvbo,u64 size,int align,u32 flags,struct sg_table * sg,struct dma_resv * robj)301 nouveau_bo_init(struct nouveau_bo *nvbo, u64 size, int align, u32 flags,
302 struct sg_table *sg, struct dma_resv *robj)
303 {
304 int type = sg ? ttm_bo_type_sg : ttm_bo_type_device;
305 size_t acc_size;
306 int ret;
307
308 acc_size = ttm_bo_dma_acc_size(nvbo->bo.bdev, size, sizeof(*nvbo));
309
310 nvbo->bo.mem.num_pages = size >> PAGE_SHIFT;
311 nouveau_bo_placement_set(nvbo, flags, 0);
312
313 ret = ttm_bo_init(nvbo->bo.bdev, &nvbo->bo, size, type,
314 &nvbo->placement, align >> PAGE_SHIFT, false,
315 acc_size, sg, robj, nouveau_bo_del_ttm);
316 if (ret) {
317 /* ttm will call nouveau_bo_del_ttm if it fails.. */
318 return ret;
319 }
320
321 return 0;
322 }
323
324 int
nouveau_bo_new(struct nouveau_cli * cli,u64 size,int align,uint32_t flags,uint32_t tile_mode,uint32_t tile_flags,struct sg_table * sg,struct dma_resv * robj,struct nouveau_bo ** pnvbo)325 nouveau_bo_new(struct nouveau_cli *cli, u64 size, int align,
326 uint32_t flags, uint32_t tile_mode, uint32_t tile_flags,
327 struct sg_table *sg, struct dma_resv *robj,
328 struct nouveau_bo **pnvbo)
329 {
330 struct nouveau_bo *nvbo;
331 int ret;
332
333 nvbo = nouveau_bo_alloc(cli, &size, &align, flags, tile_mode,
334 tile_flags);
335 if (IS_ERR(nvbo))
336 return PTR_ERR(nvbo);
337
338 ret = nouveau_bo_init(nvbo, size, align, flags, sg, robj);
339 if (ret)
340 return ret;
341
342 *pnvbo = nvbo;
343 return 0;
344 }
345
346 static void
set_placement_list(struct ttm_place * pl,unsigned * n,uint32_t type,uint32_t flags)347 set_placement_list(struct ttm_place *pl, unsigned *n, uint32_t type, uint32_t flags)
348 {
349 *n = 0;
350
351 if (type & TTM_PL_FLAG_VRAM)
352 pl[(*n)++].flags = TTM_PL_FLAG_VRAM | flags;
353 if (type & TTM_PL_FLAG_TT)
354 pl[(*n)++].flags = TTM_PL_FLAG_TT | flags;
355 if (type & TTM_PL_FLAG_SYSTEM)
356 pl[(*n)++].flags = TTM_PL_FLAG_SYSTEM | flags;
357 }
358
359 static void
set_placement_range(struct nouveau_bo * nvbo,uint32_t type)360 set_placement_range(struct nouveau_bo *nvbo, uint32_t type)
361 {
362 struct nouveau_drm *drm = nouveau_bdev(nvbo->bo.bdev);
363 u32 vram_pages = drm->client.device.info.ram_size >> PAGE_SHIFT;
364 unsigned i, fpfn, lpfn;
365
366 if (drm->client.device.info.family == NV_DEVICE_INFO_V0_CELSIUS &&
367 nvbo->mode && (type & TTM_PL_FLAG_VRAM) &&
368 nvbo->bo.mem.num_pages < vram_pages / 4) {
369 /*
370 * Make sure that the color and depth buffers are handled
371 * by independent memory controller units. Up to a 9x
372 * speed up when alpha-blending and depth-test are enabled
373 * at the same time.
374 */
375 if (nvbo->zeta) {
376 fpfn = vram_pages / 2;
377 lpfn = ~0;
378 } else {
379 fpfn = 0;
380 lpfn = vram_pages / 2;
381 }
382 for (i = 0; i < nvbo->placement.num_placement; ++i) {
383 nvbo->placements[i].fpfn = fpfn;
384 nvbo->placements[i].lpfn = lpfn;
385 }
386 for (i = 0; i < nvbo->placement.num_busy_placement; ++i) {
387 nvbo->busy_placements[i].fpfn = fpfn;
388 nvbo->busy_placements[i].lpfn = lpfn;
389 }
390 }
391 }
392
393 void
nouveau_bo_placement_set(struct nouveau_bo * nvbo,uint32_t type,uint32_t busy)394 nouveau_bo_placement_set(struct nouveau_bo *nvbo, uint32_t type, uint32_t busy)
395 {
396 struct ttm_placement *pl = &nvbo->placement;
397 uint32_t flags = (nvbo->force_coherent ? TTM_PL_FLAG_UNCACHED :
398 TTM_PL_MASK_CACHING) |
399 (nvbo->pin_refcnt ? TTM_PL_FLAG_NO_EVICT : 0);
400
401 pl->placement = nvbo->placements;
402 set_placement_list(nvbo->placements, &pl->num_placement,
403 type, flags);
404
405 pl->busy_placement = nvbo->busy_placements;
406 set_placement_list(nvbo->busy_placements, &pl->num_busy_placement,
407 type | busy, flags);
408
409 set_placement_range(nvbo, type);
410 }
411
412 int
nouveau_bo_pin(struct nouveau_bo * nvbo,uint32_t memtype,bool contig)413 nouveau_bo_pin(struct nouveau_bo *nvbo, uint32_t memtype, bool contig)
414 {
415 struct nouveau_drm *drm = nouveau_bdev(nvbo->bo.bdev);
416 struct ttm_buffer_object *bo = &nvbo->bo;
417 bool force = false, evict = false;
418 int ret;
419
420 ret = ttm_bo_reserve(bo, false, false, NULL);
421 if (ret)
422 return ret;
423
424 if (drm->client.device.info.family >= NV_DEVICE_INFO_V0_TESLA &&
425 memtype == TTM_PL_FLAG_VRAM && contig) {
426 if (!nvbo->contig) {
427 nvbo->contig = true;
428 force = true;
429 evict = true;
430 }
431 }
432
433 if (nvbo->pin_refcnt) {
434 if (!(memtype & (1 << bo->mem.mem_type)) || evict) {
435 NV_ERROR(drm, "bo %p pinned elsewhere: "
436 "0x%08x vs 0x%08x\n", bo,
437 1 << bo->mem.mem_type, memtype);
438 ret = -EBUSY;
439 }
440 nvbo->pin_refcnt++;
441 goto out;
442 }
443
444 if (evict) {
445 nouveau_bo_placement_set(nvbo, TTM_PL_FLAG_TT, 0);
446 ret = nouveau_bo_validate(nvbo, false, false);
447 if (ret)
448 goto out;
449 }
450
451 nvbo->pin_refcnt++;
452 nouveau_bo_placement_set(nvbo, memtype, 0);
453
454 /* drop pin_refcnt temporarily, so we don't trip the assertion
455 * in nouveau_bo_move() that makes sure we're not trying to
456 * move a pinned buffer
457 */
458 nvbo->pin_refcnt--;
459 ret = nouveau_bo_validate(nvbo, false, false);
460 if (ret)
461 goto out;
462 nvbo->pin_refcnt++;
463
464 switch (bo->mem.mem_type) {
465 case TTM_PL_VRAM:
466 drm->gem.vram_available -= bo->mem.size;
467 break;
468 case TTM_PL_TT:
469 drm->gem.gart_available -= bo->mem.size;
470 break;
471 default:
472 break;
473 }
474
475 out:
476 if (force && ret)
477 nvbo->contig = false;
478 ttm_bo_unreserve(bo);
479 return ret;
480 }
481
482 int
nouveau_bo_unpin(struct nouveau_bo * nvbo)483 nouveau_bo_unpin(struct nouveau_bo *nvbo)
484 {
485 struct nouveau_drm *drm = nouveau_bdev(nvbo->bo.bdev);
486 struct ttm_buffer_object *bo = &nvbo->bo;
487 int ret, ref;
488
489 ret = ttm_bo_reserve(bo, false, false, NULL);
490 if (ret)
491 return ret;
492
493 ref = --nvbo->pin_refcnt;
494 WARN_ON_ONCE(ref < 0);
495 if (ref)
496 goto out;
497
498 nouveau_bo_placement_set(nvbo, bo->mem.placement, 0);
499
500 ret = nouveau_bo_validate(nvbo, false, false);
501 if (ret == 0) {
502 switch (bo->mem.mem_type) {
503 case TTM_PL_VRAM:
504 drm->gem.vram_available += bo->mem.size;
505 break;
506 case TTM_PL_TT:
507 drm->gem.gart_available += bo->mem.size;
508 break;
509 default:
510 break;
511 }
512 }
513
514 out:
515 ttm_bo_unreserve(bo);
516 return ret;
517 }
518
519 int
nouveau_bo_map(struct nouveau_bo * nvbo)520 nouveau_bo_map(struct nouveau_bo *nvbo)
521 {
522 int ret;
523
524 ret = ttm_bo_reserve(&nvbo->bo, false, false, NULL);
525 if (ret)
526 return ret;
527
528 ret = ttm_bo_kmap(&nvbo->bo, 0, nvbo->bo.mem.num_pages, &nvbo->kmap);
529
530 ttm_bo_unreserve(&nvbo->bo);
531 return ret;
532 }
533
534 void
nouveau_bo_unmap(struct nouveau_bo * nvbo)535 nouveau_bo_unmap(struct nouveau_bo *nvbo)
536 {
537 if (!nvbo)
538 return;
539
540 ttm_bo_kunmap(&nvbo->kmap);
541 }
542
543 void
nouveau_bo_sync_for_device(struct nouveau_bo * nvbo)544 nouveau_bo_sync_for_device(struct nouveau_bo *nvbo)
545 {
546 struct nouveau_drm *drm = nouveau_bdev(nvbo->bo.bdev);
547 struct ttm_dma_tt *ttm_dma = (struct ttm_dma_tt *)nvbo->bo.ttm;
548 #ifndef __NetBSD__
549 int i;
550 #endif
551
552 if (!ttm_dma)
553 return;
554
555 /* Don't waste time looping if the object is coherent */
556 if (nvbo->force_coherent)
557 return;
558
559 #ifdef __NetBSD__
560 bus_dma_tag_t dmat = drm->dev->dmat;
561 bus_dmamap_sync(dmat, ttm_dma->dma_address, 0,
562 PAGE_SIZE*ttm_dma->ttm.num_pages,
563 BUS_DMASYNC_PREREAD|BUS_DMASYNC_PREWRITE);
564 #else
565 for (i = 0; i < ttm_dma->ttm.num_pages; i++)
566 dma_sync_single_for_device(drm->dev->dev,
567 ttm_dma->dma_address[i],
568 PAGE_SIZE, DMA_TO_DEVICE);
569 #endif
570 }
571
572 void
nouveau_bo_sync_for_cpu(struct nouveau_bo * nvbo)573 nouveau_bo_sync_for_cpu(struct nouveau_bo *nvbo)
574 {
575 struct nouveau_drm *drm = nouveau_bdev(nvbo->bo.bdev);
576 struct ttm_dma_tt *ttm_dma = (struct ttm_dma_tt *)nvbo->bo.ttm;
577 #ifndef __NetBSD__
578 int i;
579 #endif
580
581 if (!ttm_dma)
582 return;
583
584 /* Don't waste time looping if the object is coherent */
585 if (nvbo->force_coherent)
586 return;
587
588 #ifdef __NetBSD__
589 bus_dma_tag_t dmat = drm->dev->dmat;
590 bus_dmamap_sync(dmat, ttm_dma->dma_address, 0,
591 PAGE_SIZE*ttm_dma->ttm.num_pages,
592 BUS_DMASYNC_POSTREAD|BUS_DMASYNC_POSTWRITE);
593 #else
594 for (i = 0; i < ttm_dma->ttm.num_pages; i++)
595 dma_sync_single_for_cpu(drm->dev->dev, ttm_dma->dma_address[i],
596 PAGE_SIZE, DMA_FROM_DEVICE);
597 #endif
598 }
599
600 int
nouveau_bo_validate(struct nouveau_bo * nvbo,bool interruptible,bool no_wait_gpu)601 nouveau_bo_validate(struct nouveau_bo *nvbo, bool interruptible,
602 bool no_wait_gpu)
603 {
604 struct ttm_operation_ctx ctx = { interruptible, no_wait_gpu };
605 int ret;
606
607 ret = ttm_bo_validate(&nvbo->bo, &nvbo->placement, &ctx);
608 if (ret)
609 return ret;
610
611 nouveau_bo_sync_for_device(nvbo);
612
613 return 0;
614 }
615
616 #ifdef __NetBSD__
617 /*
618 * XXX Can't use bus_space here because this is all mapped through the
619 * radeon_bo abstraction. Can't assume we're x86 because this is
620 * Nouveau, not Intel.
621 */
622
623 # define __iomem volatile
624 # define __force
625 # define ioread16_native fake_ioread16_native
626 # define ioread32_native fake_ioread32_native
627 # define iowrite16_native fake_iowrite16_native
628 # define iowrite32_native fake_iowrite32_native
629
630 #ifdef notdef
631 static inline uint16_t
ioread16_native(const void __iomem * ptr)632 ioread16_native(const void __iomem *ptr)
633 {
634 uint16_t v;
635
636 v = *(const uint16_t __iomem *)ptr;
637 membar_consumer();
638
639 return v;
640 }
641 #endif
642
643 static inline uint32_t
ioread32_native(const void __iomem * ptr)644 ioread32_native(const void __iomem *ptr)
645 {
646 uint32_t v;
647
648 v = *(const uint32_t __iomem *)ptr;
649 membar_consumer();
650
651 return v;
652 }
653
654 static inline void
iowrite16_native(uint16_t v,void __iomem * ptr)655 iowrite16_native(uint16_t v, void __iomem *ptr)
656 {
657
658 membar_producer();
659 *(uint16_t __iomem *)ptr = v;
660 }
661
662 static inline void
iowrite32_native(uint32_t v,void __iomem * ptr)663 iowrite32_native(uint32_t v, void __iomem *ptr)
664 {
665
666 membar_producer();
667 *(uint32_t __iomem *)ptr = v;
668 }
669 #endif
670
671 void
nouveau_bo_wr16(struct nouveau_bo * nvbo,unsigned index,u16 val)672 nouveau_bo_wr16(struct nouveau_bo *nvbo, unsigned index, u16 val)
673 {
674 bool is_iomem;
675 u16 *mem = ttm_kmap_obj_virtual(&nvbo->kmap, &is_iomem);
676
677 mem += index;
678
679 if (is_iomem)
680 iowrite16_native(val, (void __force __iomem *)mem);
681 else
682 *mem = val;
683 }
684
685 u32
nouveau_bo_rd32(struct nouveau_bo * nvbo,unsigned index)686 nouveau_bo_rd32(struct nouveau_bo *nvbo, unsigned index)
687 {
688 bool is_iomem;
689 u32 *mem = ttm_kmap_obj_virtual(&nvbo->kmap, &is_iomem);
690
691 mem += index;
692
693 if (is_iomem)
694 return ioread32_native((void __force __iomem *)mem);
695 else
696 return *mem;
697 }
698
699 void
nouveau_bo_wr32(struct nouveau_bo * nvbo,unsigned index,u32 val)700 nouveau_bo_wr32(struct nouveau_bo *nvbo, unsigned index, u32 val)
701 {
702 bool is_iomem;
703 u32 *mem = ttm_kmap_obj_virtual(&nvbo->kmap, &is_iomem);
704
705 mem += index;
706
707 if (is_iomem)
708 iowrite32_native(val, (void __force __iomem *)mem);
709 else
710 *mem = val;
711 }
712
713 #ifdef __NetBSD__
714 # undef __iomem
715 # undef __force
716 # undef ioread16_native
717 # undef ioread32_native
718 # undef iowrite16_native
719 # undef iowrite32_native
720 #endif
721
722 static struct ttm_tt *
nouveau_ttm_tt_create(struct ttm_buffer_object * bo,uint32_t page_flags)723 nouveau_ttm_tt_create(struct ttm_buffer_object *bo, uint32_t page_flags)
724 {
725 #if IS_ENABLED(CONFIG_AGP)
726 struct nouveau_drm *drm = nouveau_bdev(bo->bdev);
727
728 if (drm->agp.bridge) {
729 return ttm_agp_tt_create(bo, drm->agp.bridge, page_flags);
730 }
731 #endif
732
733 return nouveau_sgdma_create_ttm(bo, page_flags);
734 }
735
736 static int
nouveau_bo_invalidate_caches(struct ttm_bo_device * bdev,uint32_t flags)737 nouveau_bo_invalidate_caches(struct ttm_bo_device *bdev, uint32_t flags)
738 {
739 /* We'll do this from user space. */
740 return 0;
741 }
742
743 static int
nouveau_bo_init_mem_type(struct ttm_bo_device * bdev,uint32_t type,struct ttm_mem_type_manager * man)744 nouveau_bo_init_mem_type(struct ttm_bo_device *bdev, uint32_t type,
745 struct ttm_mem_type_manager *man)
746 {
747 struct nouveau_drm *drm = nouveau_bdev(bdev);
748 struct nvif_mmu *mmu = &drm->client.mmu;
749
750 switch (type) {
751 case TTM_PL_SYSTEM:
752 man->flags = TTM_MEMTYPE_FLAG_MAPPABLE;
753 man->available_caching = TTM_PL_MASK_CACHING;
754 man->default_caching = TTM_PL_FLAG_CACHED;
755 break;
756 case TTM_PL_VRAM:
757 man->flags = TTM_MEMTYPE_FLAG_FIXED |
758 TTM_MEMTYPE_FLAG_MAPPABLE;
759 man->available_caching = TTM_PL_FLAG_UNCACHED |
760 TTM_PL_FLAG_WC;
761 man->default_caching = TTM_PL_FLAG_WC;
762
763 if (drm->client.device.info.family >= NV_DEVICE_INFO_V0_TESLA) {
764 /* Some BARs do not support being ioremapped WC */
765 const u8 type = mmu->type[drm->ttm.type_vram].type;
766 if (type & NVIF_MEM_UNCACHED) {
767 man->available_caching = TTM_PL_FLAG_UNCACHED;
768 man->default_caching = TTM_PL_FLAG_UNCACHED;
769 }
770
771 man->func = &nouveau_vram_manager;
772 man->io_reserve_fastpath = false;
773 man->use_io_reserve_lru = true;
774 } else {
775 man->func = &ttm_bo_manager_func;
776 }
777 break;
778 case TTM_PL_TT:
779 if (drm->client.device.info.family >= NV_DEVICE_INFO_V0_TESLA)
780 man->func = &nouveau_gart_manager;
781 else
782 if (!drm->agp.bridge)
783 man->func = &nv04_gart_manager;
784 else
785 man->func = &ttm_bo_manager_func;
786
787 if (drm->agp.bridge) {
788 man->flags = TTM_MEMTYPE_FLAG_MAPPABLE;
789 man->available_caching = TTM_PL_FLAG_UNCACHED |
790 TTM_PL_FLAG_WC;
791 man->default_caching = TTM_PL_FLAG_WC;
792 } else {
793 man->flags = TTM_MEMTYPE_FLAG_MAPPABLE |
794 TTM_MEMTYPE_FLAG_CMA;
795 man->available_caching = TTM_PL_MASK_CACHING;
796 man->default_caching = TTM_PL_FLAG_CACHED;
797 }
798
799 break;
800 default:
801 return -EINVAL;
802 }
803 return 0;
804 }
805
806 static void
nouveau_bo_evict_flags(struct ttm_buffer_object * bo,struct ttm_placement * pl)807 nouveau_bo_evict_flags(struct ttm_buffer_object *bo, struct ttm_placement *pl)
808 {
809 struct nouveau_bo *nvbo = nouveau_bo(bo);
810
811 switch (bo->mem.mem_type) {
812 case TTM_PL_VRAM:
813 nouveau_bo_placement_set(nvbo, TTM_PL_FLAG_TT,
814 TTM_PL_FLAG_SYSTEM);
815 break;
816 default:
817 nouveau_bo_placement_set(nvbo, TTM_PL_FLAG_SYSTEM, 0);
818 break;
819 }
820
821 *pl = nvbo->placement;
822 }
823
824
825 static int
nve0_bo_move_init(struct nouveau_channel * chan,u32 handle)826 nve0_bo_move_init(struct nouveau_channel *chan, u32 handle)
827 {
828 int ret = RING_SPACE(chan, 2);
829 if (ret == 0) {
830 BEGIN_NVC0(chan, NvSubCopy, 0x0000, 1);
831 OUT_RING (chan, handle & 0x0000ffff);
832 FIRE_RING (chan);
833 }
834 return ret;
835 }
836
837 static int
nve0_bo_move_copy(struct nouveau_channel * chan,struct ttm_buffer_object * bo,struct ttm_mem_reg * old_reg,struct ttm_mem_reg * new_reg)838 nve0_bo_move_copy(struct nouveau_channel *chan, struct ttm_buffer_object *bo,
839 struct ttm_mem_reg *old_reg, struct ttm_mem_reg *new_reg)
840 {
841 struct nouveau_mem *mem = nouveau_mem(old_reg);
842 int ret = RING_SPACE(chan, 10);
843 if (ret == 0) {
844 BEGIN_NVC0(chan, NvSubCopy, 0x0400, 8);
845 OUT_RING (chan, upper_32_bits(mem->vma[0].addr));
846 OUT_RING (chan, lower_32_bits(mem->vma[0].addr));
847 OUT_RING (chan, upper_32_bits(mem->vma[1].addr));
848 OUT_RING (chan, lower_32_bits(mem->vma[1].addr));
849 OUT_RING (chan, PAGE_SIZE);
850 OUT_RING (chan, PAGE_SIZE);
851 OUT_RING (chan, PAGE_SIZE);
852 OUT_RING (chan, new_reg->num_pages);
853 BEGIN_IMC0(chan, NvSubCopy, 0x0300, 0x0386);
854 }
855 return ret;
856 }
857
858 static int
nvc0_bo_move_init(struct nouveau_channel * chan,u32 handle)859 nvc0_bo_move_init(struct nouveau_channel *chan, u32 handle)
860 {
861 int ret = RING_SPACE(chan, 2);
862 if (ret == 0) {
863 BEGIN_NVC0(chan, NvSubCopy, 0x0000, 1);
864 OUT_RING (chan, handle);
865 }
866 return ret;
867 }
868
869 static int
nvc0_bo_move_copy(struct nouveau_channel * chan,struct ttm_buffer_object * bo,struct ttm_mem_reg * old_reg,struct ttm_mem_reg * new_reg)870 nvc0_bo_move_copy(struct nouveau_channel *chan, struct ttm_buffer_object *bo,
871 struct ttm_mem_reg *old_reg, struct ttm_mem_reg *new_reg)
872 {
873 struct nouveau_mem *mem = nouveau_mem(old_reg);
874 u64 src_offset = mem->vma[0].addr;
875 u64 dst_offset = mem->vma[1].addr;
876 u32 page_count = new_reg->num_pages;
877 int ret;
878
879 page_count = new_reg->num_pages;
880 while (page_count) {
881 int line_count = (page_count > 8191) ? 8191 : page_count;
882
883 ret = RING_SPACE(chan, 11);
884 if (ret)
885 return ret;
886
887 BEGIN_NVC0(chan, NvSubCopy, 0x030c, 8);
888 OUT_RING (chan, upper_32_bits(src_offset));
889 OUT_RING (chan, lower_32_bits(src_offset));
890 OUT_RING (chan, upper_32_bits(dst_offset));
891 OUT_RING (chan, lower_32_bits(dst_offset));
892 OUT_RING (chan, PAGE_SIZE);
893 OUT_RING (chan, PAGE_SIZE);
894 OUT_RING (chan, PAGE_SIZE);
895 OUT_RING (chan, line_count);
896 BEGIN_NVC0(chan, NvSubCopy, 0x0300, 1);
897 OUT_RING (chan, 0x00000110);
898
899 page_count -= line_count;
900 src_offset += (PAGE_SIZE * line_count);
901 dst_offset += (PAGE_SIZE * line_count);
902 }
903
904 return 0;
905 }
906
907 static int
nvc0_bo_move_m2mf(struct nouveau_channel * chan,struct ttm_buffer_object * bo,struct ttm_mem_reg * old_reg,struct ttm_mem_reg * new_reg)908 nvc0_bo_move_m2mf(struct nouveau_channel *chan, struct ttm_buffer_object *bo,
909 struct ttm_mem_reg *old_reg, struct ttm_mem_reg *new_reg)
910 {
911 struct nouveau_mem *mem = nouveau_mem(old_reg);
912 u64 src_offset = mem->vma[0].addr;
913 u64 dst_offset = mem->vma[1].addr;
914 u32 page_count = new_reg->num_pages;
915 int ret;
916
917 page_count = new_reg->num_pages;
918 while (page_count) {
919 int line_count = (page_count > 2047) ? 2047 : page_count;
920
921 ret = RING_SPACE(chan, 12);
922 if (ret)
923 return ret;
924
925 BEGIN_NVC0(chan, NvSubCopy, 0x0238, 2);
926 OUT_RING (chan, upper_32_bits(dst_offset));
927 OUT_RING (chan, lower_32_bits(dst_offset));
928 BEGIN_NVC0(chan, NvSubCopy, 0x030c, 6);
929 OUT_RING (chan, upper_32_bits(src_offset));
930 OUT_RING (chan, lower_32_bits(src_offset));
931 OUT_RING (chan, PAGE_SIZE); /* src_pitch */
932 OUT_RING (chan, PAGE_SIZE); /* dst_pitch */
933 OUT_RING (chan, PAGE_SIZE); /* line_length */
934 OUT_RING (chan, line_count);
935 BEGIN_NVC0(chan, NvSubCopy, 0x0300, 1);
936 OUT_RING (chan, 0x00100110);
937
938 page_count -= line_count;
939 src_offset += (PAGE_SIZE * line_count);
940 dst_offset += (PAGE_SIZE * line_count);
941 }
942
943 return 0;
944 }
945
946 static int
nva3_bo_move_copy(struct nouveau_channel * chan,struct ttm_buffer_object * bo,struct ttm_mem_reg * old_reg,struct ttm_mem_reg * new_reg)947 nva3_bo_move_copy(struct nouveau_channel *chan, struct ttm_buffer_object *bo,
948 struct ttm_mem_reg *old_reg, struct ttm_mem_reg *new_reg)
949 {
950 struct nouveau_mem *mem = nouveau_mem(old_reg);
951 u64 src_offset = mem->vma[0].addr;
952 u64 dst_offset = mem->vma[1].addr;
953 u32 page_count = new_reg->num_pages;
954 int ret;
955
956 page_count = new_reg->num_pages;
957 while (page_count) {
958 int line_count = (page_count > 8191) ? 8191 : page_count;
959
960 ret = RING_SPACE(chan, 11);
961 if (ret)
962 return ret;
963
964 BEGIN_NV04(chan, NvSubCopy, 0x030c, 8);
965 OUT_RING (chan, upper_32_bits(src_offset));
966 OUT_RING (chan, lower_32_bits(src_offset));
967 OUT_RING (chan, upper_32_bits(dst_offset));
968 OUT_RING (chan, lower_32_bits(dst_offset));
969 OUT_RING (chan, PAGE_SIZE);
970 OUT_RING (chan, PAGE_SIZE);
971 OUT_RING (chan, PAGE_SIZE);
972 OUT_RING (chan, line_count);
973 BEGIN_NV04(chan, NvSubCopy, 0x0300, 1);
974 OUT_RING (chan, 0x00000110);
975
976 page_count -= line_count;
977 src_offset += (PAGE_SIZE * line_count);
978 dst_offset += (PAGE_SIZE * line_count);
979 }
980
981 return 0;
982 }
983
984 static int
nv98_bo_move_exec(struct nouveau_channel * chan,struct ttm_buffer_object * bo,struct ttm_mem_reg * old_reg,struct ttm_mem_reg * new_reg)985 nv98_bo_move_exec(struct nouveau_channel *chan, struct ttm_buffer_object *bo,
986 struct ttm_mem_reg *old_reg, struct ttm_mem_reg *new_reg)
987 {
988 struct nouveau_mem *mem = nouveau_mem(old_reg);
989 int ret = RING_SPACE(chan, 7);
990 if (ret == 0) {
991 BEGIN_NV04(chan, NvSubCopy, 0x0320, 6);
992 OUT_RING (chan, upper_32_bits(mem->vma[0].addr));
993 OUT_RING (chan, lower_32_bits(mem->vma[0].addr));
994 OUT_RING (chan, upper_32_bits(mem->vma[1].addr));
995 OUT_RING (chan, lower_32_bits(mem->vma[1].addr));
996 OUT_RING (chan, 0x00000000 /* COPY */);
997 OUT_RING (chan, new_reg->num_pages << PAGE_SHIFT);
998 }
999 return ret;
1000 }
1001
1002 static int
nv84_bo_move_exec(struct nouveau_channel * chan,struct ttm_buffer_object * bo,struct ttm_mem_reg * old_reg,struct ttm_mem_reg * new_reg)1003 nv84_bo_move_exec(struct nouveau_channel *chan, struct ttm_buffer_object *bo,
1004 struct ttm_mem_reg *old_reg, struct ttm_mem_reg *new_reg)
1005 {
1006 struct nouveau_mem *mem = nouveau_mem(old_reg);
1007 int ret = RING_SPACE(chan, 7);
1008 if (ret == 0) {
1009 BEGIN_NV04(chan, NvSubCopy, 0x0304, 6);
1010 OUT_RING (chan, new_reg->num_pages << PAGE_SHIFT);
1011 OUT_RING (chan, upper_32_bits(mem->vma[0].addr));
1012 OUT_RING (chan, lower_32_bits(mem->vma[0].addr));
1013 OUT_RING (chan, upper_32_bits(mem->vma[1].addr));
1014 OUT_RING (chan, lower_32_bits(mem->vma[1].addr));
1015 OUT_RING (chan, 0x00000000 /* MODE_COPY, QUERY_NONE */);
1016 }
1017 return ret;
1018 }
1019
1020 static int
nv50_bo_move_init(struct nouveau_channel * chan,u32 handle)1021 nv50_bo_move_init(struct nouveau_channel *chan, u32 handle)
1022 {
1023 int ret = RING_SPACE(chan, 6);
1024 if (ret == 0) {
1025 BEGIN_NV04(chan, NvSubCopy, 0x0000, 1);
1026 OUT_RING (chan, handle);
1027 BEGIN_NV04(chan, NvSubCopy, 0x0180, 3);
1028 OUT_RING (chan, chan->drm->ntfy.handle);
1029 OUT_RING (chan, chan->vram.handle);
1030 OUT_RING (chan, chan->vram.handle);
1031 }
1032
1033 return ret;
1034 }
1035
1036 static int
nv50_bo_move_m2mf(struct nouveau_channel * chan,struct ttm_buffer_object * bo,struct ttm_mem_reg * old_reg,struct ttm_mem_reg * new_reg)1037 nv50_bo_move_m2mf(struct nouveau_channel *chan, struct ttm_buffer_object *bo,
1038 struct ttm_mem_reg *old_reg, struct ttm_mem_reg *new_reg)
1039 {
1040 struct nouveau_mem *mem = nouveau_mem(old_reg);
1041 u64 length = (new_reg->num_pages << PAGE_SHIFT);
1042 u64 src_offset = mem->vma[0].addr;
1043 u64 dst_offset = mem->vma[1].addr;
1044 int src_tiled = !!mem->kind;
1045 int dst_tiled = !!nouveau_mem(new_reg)->kind;
1046 int ret;
1047
1048 while (length) {
1049 u32 amount, stride, height;
1050
1051 ret = RING_SPACE(chan, 18 + 6 * (src_tiled + dst_tiled));
1052 if (ret)
1053 return ret;
1054
1055 amount = min(length, (u64)(4 * 1024 * 1024));
1056 stride = 16 * 4;
1057 height = amount / stride;
1058
1059 if (src_tiled) {
1060 BEGIN_NV04(chan, NvSubCopy, 0x0200, 7);
1061 OUT_RING (chan, 0);
1062 OUT_RING (chan, 0);
1063 OUT_RING (chan, stride);
1064 OUT_RING (chan, height);
1065 OUT_RING (chan, 1);
1066 OUT_RING (chan, 0);
1067 OUT_RING (chan, 0);
1068 } else {
1069 BEGIN_NV04(chan, NvSubCopy, 0x0200, 1);
1070 OUT_RING (chan, 1);
1071 }
1072 if (dst_tiled) {
1073 BEGIN_NV04(chan, NvSubCopy, 0x021c, 7);
1074 OUT_RING (chan, 0);
1075 OUT_RING (chan, 0);
1076 OUT_RING (chan, stride);
1077 OUT_RING (chan, height);
1078 OUT_RING (chan, 1);
1079 OUT_RING (chan, 0);
1080 OUT_RING (chan, 0);
1081 } else {
1082 BEGIN_NV04(chan, NvSubCopy, 0x021c, 1);
1083 OUT_RING (chan, 1);
1084 }
1085
1086 BEGIN_NV04(chan, NvSubCopy, 0x0238, 2);
1087 OUT_RING (chan, upper_32_bits(src_offset));
1088 OUT_RING (chan, upper_32_bits(dst_offset));
1089 BEGIN_NV04(chan, NvSubCopy, 0x030c, 8);
1090 OUT_RING (chan, lower_32_bits(src_offset));
1091 OUT_RING (chan, lower_32_bits(dst_offset));
1092 OUT_RING (chan, stride);
1093 OUT_RING (chan, stride);
1094 OUT_RING (chan, stride);
1095 OUT_RING (chan, height);
1096 OUT_RING (chan, 0x00000101);
1097 OUT_RING (chan, 0x00000000);
1098 BEGIN_NV04(chan, NvSubCopy, NV_MEMORY_TO_MEMORY_FORMAT_NOP, 1);
1099 OUT_RING (chan, 0);
1100
1101 length -= amount;
1102 src_offset += amount;
1103 dst_offset += amount;
1104 }
1105
1106 return 0;
1107 }
1108
1109 static int
nv04_bo_move_init(struct nouveau_channel * chan,u32 handle)1110 nv04_bo_move_init(struct nouveau_channel *chan, u32 handle)
1111 {
1112 int ret = RING_SPACE(chan, 4);
1113 if (ret == 0) {
1114 BEGIN_NV04(chan, NvSubCopy, 0x0000, 1);
1115 OUT_RING (chan, handle);
1116 BEGIN_NV04(chan, NvSubCopy, 0x0180, 1);
1117 OUT_RING (chan, chan->drm->ntfy.handle);
1118 }
1119
1120 return ret;
1121 }
1122
1123 static inline uint32_t
nouveau_bo_mem_ctxdma(struct ttm_buffer_object * bo,struct nouveau_channel * chan,struct ttm_mem_reg * reg)1124 nouveau_bo_mem_ctxdma(struct ttm_buffer_object *bo,
1125 struct nouveau_channel *chan, struct ttm_mem_reg *reg)
1126 {
1127 if (reg->mem_type == TTM_PL_TT)
1128 return NvDmaTT;
1129 return chan->vram.handle;
1130 }
1131
1132 static int
nv04_bo_move_m2mf(struct nouveau_channel * chan,struct ttm_buffer_object * bo,struct ttm_mem_reg * old_reg,struct ttm_mem_reg * new_reg)1133 nv04_bo_move_m2mf(struct nouveau_channel *chan, struct ttm_buffer_object *bo,
1134 struct ttm_mem_reg *old_reg, struct ttm_mem_reg *new_reg)
1135 {
1136 u32 src_offset = old_reg->start << PAGE_SHIFT;
1137 u32 dst_offset = new_reg->start << PAGE_SHIFT;
1138 u32 page_count = new_reg->num_pages;
1139 int ret;
1140
1141 ret = RING_SPACE(chan, 3);
1142 if (ret)
1143 return ret;
1144
1145 BEGIN_NV04(chan, NvSubCopy, NV_MEMORY_TO_MEMORY_FORMAT_DMA_SOURCE, 2);
1146 OUT_RING (chan, nouveau_bo_mem_ctxdma(bo, chan, old_reg));
1147 OUT_RING (chan, nouveau_bo_mem_ctxdma(bo, chan, new_reg));
1148
1149 page_count = new_reg->num_pages;
1150 while (page_count) {
1151 int line_count = (page_count > 2047) ? 2047 : page_count;
1152
1153 ret = RING_SPACE(chan, 11);
1154 if (ret)
1155 return ret;
1156
1157 BEGIN_NV04(chan, NvSubCopy,
1158 NV_MEMORY_TO_MEMORY_FORMAT_OFFSET_IN, 8);
1159 OUT_RING (chan, src_offset);
1160 OUT_RING (chan, dst_offset);
1161 OUT_RING (chan, PAGE_SIZE); /* src_pitch */
1162 OUT_RING (chan, PAGE_SIZE); /* dst_pitch */
1163 OUT_RING (chan, PAGE_SIZE); /* line_length */
1164 OUT_RING (chan, line_count);
1165 OUT_RING (chan, 0x00000101);
1166 OUT_RING (chan, 0x00000000);
1167 BEGIN_NV04(chan, NvSubCopy, NV_MEMORY_TO_MEMORY_FORMAT_NOP, 1);
1168 OUT_RING (chan, 0);
1169
1170 page_count -= line_count;
1171 src_offset += (PAGE_SIZE * line_count);
1172 dst_offset += (PAGE_SIZE * line_count);
1173 }
1174
1175 return 0;
1176 }
1177
1178 static int
nouveau_bo_move_prep(struct nouveau_drm * drm,struct ttm_buffer_object * bo,struct ttm_mem_reg * reg)1179 nouveau_bo_move_prep(struct nouveau_drm *drm, struct ttm_buffer_object *bo,
1180 struct ttm_mem_reg *reg)
1181 {
1182 struct nouveau_mem *old_mem = nouveau_mem(&bo->mem);
1183 struct nouveau_mem *new_mem = nouveau_mem(reg);
1184 struct nvif_vmm *vmm = &drm->client.vmm.vmm;
1185 int ret;
1186
1187 ret = nvif_vmm_get(vmm, LAZY, false, old_mem->mem.page, 0,
1188 old_mem->mem.size, &old_mem->vma[0]);
1189 if (ret)
1190 return ret;
1191
1192 ret = nvif_vmm_get(vmm, LAZY, false, new_mem->mem.page, 0,
1193 new_mem->mem.size, &old_mem->vma[1]);
1194 if (ret)
1195 goto done;
1196
1197 ret = nouveau_mem_map(old_mem, vmm, &old_mem->vma[0]);
1198 if (ret)
1199 goto done;
1200
1201 ret = nouveau_mem_map(new_mem, vmm, &old_mem->vma[1]);
1202 done:
1203 if (ret) {
1204 nvif_vmm_put(vmm, &old_mem->vma[1]);
1205 nvif_vmm_put(vmm, &old_mem->vma[0]);
1206 }
1207 return 0;
1208 }
1209
1210 static int
nouveau_bo_move_m2mf(struct ttm_buffer_object * bo,int evict,bool intr,bool no_wait_gpu,struct ttm_mem_reg * new_reg)1211 nouveau_bo_move_m2mf(struct ttm_buffer_object *bo, int evict, bool intr,
1212 bool no_wait_gpu, struct ttm_mem_reg *new_reg)
1213 {
1214 struct nouveau_drm *drm = nouveau_bdev(bo->bdev);
1215 struct nouveau_channel *chan = drm->ttm.chan;
1216 struct nouveau_cli *cli = (void *)chan->user.client;
1217 struct nouveau_fence *fence;
1218 int ret;
1219
1220 /* create temporary vmas for the transfer and attach them to the
1221 * old nvkm_mem node, these will get cleaned up after ttm has
1222 * destroyed the ttm_mem_reg
1223 */
1224 if (drm->client.device.info.family >= NV_DEVICE_INFO_V0_TESLA) {
1225 ret = nouveau_bo_move_prep(drm, bo, new_reg);
1226 if (ret)
1227 return ret;
1228 }
1229
1230 mutex_lock_nested(&cli->mutex, SINGLE_DEPTH_NESTING);
1231 ret = nouveau_fence_sync(nouveau_bo(bo), chan, true, intr);
1232 if (ret == 0) {
1233 ret = drm->ttm.move(chan, bo, &bo->mem, new_reg);
1234 if (ret == 0) {
1235 ret = nouveau_fence_new(chan, false, &fence);
1236 if (ret == 0) {
1237 ret = ttm_bo_move_accel_cleanup(bo,
1238 &fence->base,
1239 evict,
1240 new_reg);
1241 nouveau_fence_unref(&fence);
1242 }
1243 }
1244 }
1245 mutex_unlock(&cli->mutex);
1246 return ret;
1247 }
1248
1249 void
nouveau_bo_move_init(struct nouveau_drm * drm)1250 nouveau_bo_move_init(struct nouveau_drm *drm)
1251 {
1252 static const struct _method_table {
1253 const char *name;
1254 int engine;
1255 s32 oclass;
1256 int (*exec)(struct nouveau_channel *,
1257 struct ttm_buffer_object *,
1258 struct ttm_mem_reg *, struct ttm_mem_reg *);
1259 int (*init)(struct nouveau_channel *, u32 handle);
1260 } _methods[] = {
1261 { "COPY", 4, 0xc5b5, nve0_bo_move_copy, nve0_bo_move_init },
1262 { "GRCE", 0, 0xc5b5, nve0_bo_move_copy, nvc0_bo_move_init },
1263 { "COPY", 4, 0xc3b5, nve0_bo_move_copy, nve0_bo_move_init },
1264 { "GRCE", 0, 0xc3b5, nve0_bo_move_copy, nvc0_bo_move_init },
1265 { "COPY", 4, 0xc1b5, nve0_bo_move_copy, nve0_bo_move_init },
1266 { "GRCE", 0, 0xc1b5, nve0_bo_move_copy, nvc0_bo_move_init },
1267 { "COPY", 4, 0xc0b5, nve0_bo_move_copy, nve0_bo_move_init },
1268 { "GRCE", 0, 0xc0b5, nve0_bo_move_copy, nvc0_bo_move_init },
1269 { "COPY", 4, 0xb0b5, nve0_bo_move_copy, nve0_bo_move_init },
1270 { "GRCE", 0, 0xb0b5, nve0_bo_move_copy, nvc0_bo_move_init },
1271 { "COPY", 4, 0xa0b5, nve0_bo_move_copy, nve0_bo_move_init },
1272 { "GRCE", 0, 0xa0b5, nve0_bo_move_copy, nvc0_bo_move_init },
1273 { "COPY1", 5, 0x90b8, nvc0_bo_move_copy, nvc0_bo_move_init },
1274 { "COPY0", 4, 0x90b5, nvc0_bo_move_copy, nvc0_bo_move_init },
1275 { "COPY", 0, 0x85b5, nva3_bo_move_copy, nv50_bo_move_init },
1276 { "CRYPT", 0, 0x74c1, nv84_bo_move_exec, nv50_bo_move_init },
1277 { "M2MF", 0, 0x9039, nvc0_bo_move_m2mf, nvc0_bo_move_init },
1278 { "M2MF", 0, 0x5039, nv50_bo_move_m2mf, nv50_bo_move_init },
1279 { "M2MF", 0, 0x0039, nv04_bo_move_m2mf, nv04_bo_move_init },
1280 {},
1281 { "CRYPT", 0, 0x88b4, nv98_bo_move_exec, nv50_bo_move_init },
1282 };
1283 const struct _method_table *mthd = _methods;
1284 const char *name = "CPU";
1285 int ret;
1286
1287 do {
1288 struct nouveau_channel *chan;
1289
1290 if (mthd->engine)
1291 chan = drm->cechan;
1292 else
1293 chan = drm->channel;
1294 if (chan == NULL)
1295 continue;
1296
1297 ret = nvif_object_init(&chan->user,
1298 mthd->oclass | (mthd->engine << 16),
1299 mthd->oclass, NULL, 0,
1300 &drm->ttm.copy);
1301 if (ret == 0) {
1302 ret = mthd->init(chan, drm->ttm.copy.handle);
1303 if (ret) {
1304 nvif_object_fini(&drm->ttm.copy);
1305 continue;
1306 }
1307
1308 drm->ttm.move = mthd->exec;
1309 drm->ttm.chan = chan;
1310 name = mthd->name;
1311 break;
1312 }
1313 } while ((++mthd)->exec);
1314
1315 NV_INFO(drm, "MM: using %s for buffer copies\n", name);
1316 }
1317
1318 static int
nouveau_bo_move_flipd(struct ttm_buffer_object * bo,bool evict,bool intr,bool no_wait_gpu,struct ttm_mem_reg * new_reg)1319 nouveau_bo_move_flipd(struct ttm_buffer_object *bo, bool evict, bool intr,
1320 bool no_wait_gpu, struct ttm_mem_reg *new_reg)
1321 {
1322 struct ttm_operation_ctx ctx = { intr, no_wait_gpu };
1323 struct ttm_place placement_memtype = {
1324 .fpfn = 0,
1325 .lpfn = 0,
1326 .flags = TTM_PL_FLAG_TT | TTM_PL_MASK_CACHING
1327 };
1328 struct ttm_placement placement;
1329 struct ttm_mem_reg tmp_reg;
1330 int ret;
1331
1332 placement.num_placement = placement.num_busy_placement = 1;
1333 placement.placement = placement.busy_placement = &placement_memtype;
1334
1335 tmp_reg = *new_reg;
1336 tmp_reg.mm_node = NULL;
1337 ret = ttm_bo_mem_space(bo, &placement, &tmp_reg, &ctx);
1338 if (ret)
1339 return ret;
1340
1341 ret = ttm_tt_bind(bo->ttm, &tmp_reg, &ctx);
1342 if (ret)
1343 goto out;
1344
1345 ret = nouveau_bo_move_m2mf(bo, true, intr, no_wait_gpu, &tmp_reg);
1346 if (ret)
1347 goto out;
1348
1349 ret = ttm_bo_move_ttm(bo, &ctx, new_reg);
1350 out:
1351 ttm_bo_mem_put(bo, &tmp_reg);
1352 return ret;
1353 }
1354
1355 static int
nouveau_bo_move_flips(struct ttm_buffer_object * bo,bool evict,bool intr,bool no_wait_gpu,struct ttm_mem_reg * new_reg)1356 nouveau_bo_move_flips(struct ttm_buffer_object *bo, bool evict, bool intr,
1357 bool no_wait_gpu, struct ttm_mem_reg *new_reg)
1358 {
1359 struct ttm_operation_ctx ctx = { intr, no_wait_gpu };
1360 struct ttm_place placement_memtype = {
1361 .fpfn = 0,
1362 .lpfn = 0,
1363 .flags = TTM_PL_FLAG_TT | TTM_PL_MASK_CACHING
1364 };
1365 struct ttm_placement placement;
1366 struct ttm_mem_reg tmp_reg;
1367 int ret;
1368
1369 placement.num_placement = placement.num_busy_placement = 1;
1370 placement.placement = placement.busy_placement = &placement_memtype;
1371
1372 tmp_reg = *new_reg;
1373 tmp_reg.mm_node = NULL;
1374 ret = ttm_bo_mem_space(bo, &placement, &tmp_reg, &ctx);
1375 if (ret)
1376 return ret;
1377
1378 ret = ttm_bo_move_ttm(bo, &ctx, &tmp_reg);
1379 if (ret)
1380 goto out;
1381
1382 ret = nouveau_bo_move_m2mf(bo, true, intr, no_wait_gpu, new_reg);
1383 if (ret)
1384 goto out;
1385
1386 out:
1387 ttm_bo_mem_put(bo, &tmp_reg);
1388 return ret;
1389 }
1390
1391 static void
nouveau_bo_move_ntfy(struct ttm_buffer_object * bo,bool evict,struct ttm_mem_reg * new_reg)1392 nouveau_bo_move_ntfy(struct ttm_buffer_object *bo, bool evict,
1393 struct ttm_mem_reg *new_reg)
1394 {
1395 struct nouveau_mem *mem = new_reg ? nouveau_mem(new_reg) : NULL;
1396 struct nouveau_bo *nvbo = nouveau_bo(bo);
1397 struct nouveau_vma *vma;
1398
1399 /* ttm can now (stupidly) pass the driver bos it didn't create... */
1400 if (bo->destroy != nouveau_bo_del_ttm)
1401 return;
1402
1403 if (mem && new_reg->mem_type != TTM_PL_SYSTEM &&
1404 mem->mem.page == nvbo->page) {
1405 list_for_each_entry(vma, &nvbo->vma_list, head) {
1406 nouveau_vma_map(vma, mem);
1407 }
1408 } else {
1409 list_for_each_entry(vma, &nvbo->vma_list, head) {
1410 WARN_ON(ttm_bo_wait(bo, false, false));
1411 nouveau_vma_unmap(vma);
1412 }
1413 }
1414 }
1415
1416 static int
nouveau_bo_vm_bind(struct ttm_buffer_object * bo,struct ttm_mem_reg * new_reg,struct nouveau_drm_tile ** new_tile)1417 nouveau_bo_vm_bind(struct ttm_buffer_object *bo, struct ttm_mem_reg *new_reg,
1418 struct nouveau_drm_tile **new_tile)
1419 {
1420 struct nouveau_drm *drm = nouveau_bdev(bo->bdev);
1421 struct drm_device *dev = drm->dev;
1422 struct nouveau_bo *nvbo = nouveau_bo(bo);
1423 u64 offset = new_reg->start << PAGE_SHIFT;
1424
1425 *new_tile = NULL;
1426 if (new_reg->mem_type != TTM_PL_VRAM)
1427 return 0;
1428
1429 if (drm->client.device.info.family >= NV_DEVICE_INFO_V0_CELSIUS) {
1430 *new_tile = nv10_bo_set_tiling(dev, offset, new_reg->size,
1431 nvbo->mode, nvbo->zeta);
1432 }
1433
1434 return 0;
1435 }
1436
1437 static void
nouveau_bo_vm_cleanup(struct ttm_buffer_object * bo,struct nouveau_drm_tile * new_tile,struct nouveau_drm_tile ** old_tile)1438 nouveau_bo_vm_cleanup(struct ttm_buffer_object *bo,
1439 struct nouveau_drm_tile *new_tile,
1440 struct nouveau_drm_tile **old_tile)
1441 {
1442 struct nouveau_drm *drm = nouveau_bdev(bo->bdev);
1443 struct drm_device *dev = drm->dev;
1444 struct dma_fence *fence = dma_resv_get_excl(bo->base.resv);
1445
1446 nv10_bo_put_tile_region(dev, *old_tile, fence);
1447 *old_tile = new_tile;
1448 }
1449
1450 static int
nouveau_bo_move(struct ttm_buffer_object * bo,bool evict,struct ttm_operation_ctx * ctx,struct ttm_mem_reg * new_reg)1451 nouveau_bo_move(struct ttm_buffer_object *bo, bool evict,
1452 struct ttm_operation_ctx *ctx,
1453 struct ttm_mem_reg *new_reg)
1454 {
1455 struct nouveau_drm *drm = nouveau_bdev(bo->bdev);
1456 struct nouveau_bo *nvbo = nouveau_bo(bo);
1457 struct ttm_mem_reg *old_reg = &bo->mem;
1458 struct nouveau_drm_tile *new_tile = NULL;
1459 int ret = 0;
1460
1461 ret = ttm_bo_wait(bo, ctx->interruptible, ctx->no_wait_gpu);
1462 if (ret)
1463 return ret;
1464
1465 if (nvbo->pin_refcnt)
1466 NV_WARN(drm, "Moving pinned object %p!\n", nvbo);
1467
1468 if (drm->client.device.info.family < NV_DEVICE_INFO_V0_TESLA) {
1469 ret = nouveau_bo_vm_bind(bo, new_reg, &new_tile);
1470 if (ret)
1471 return ret;
1472 }
1473
1474 /* Fake bo copy. */
1475 if (old_reg->mem_type == TTM_PL_SYSTEM && !bo->ttm) {
1476 BUG_ON(bo->mem.mm_node != NULL);
1477 bo->mem = *new_reg;
1478 new_reg->mm_node = NULL;
1479 goto out;
1480 }
1481
1482 /* Hardware assisted copy. */
1483 if (drm->ttm.move) {
1484 if (new_reg->mem_type == TTM_PL_SYSTEM)
1485 ret = nouveau_bo_move_flipd(bo, evict,
1486 ctx->interruptible,
1487 ctx->no_wait_gpu, new_reg);
1488 else if (old_reg->mem_type == TTM_PL_SYSTEM)
1489 ret = nouveau_bo_move_flips(bo, evict,
1490 ctx->interruptible,
1491 ctx->no_wait_gpu, new_reg);
1492 else
1493 ret = nouveau_bo_move_m2mf(bo, evict,
1494 ctx->interruptible,
1495 ctx->no_wait_gpu, new_reg);
1496 if (!ret)
1497 goto out;
1498 }
1499
1500 /* Fallback to software copy. */
1501 ret = ttm_bo_wait(bo, ctx->interruptible, ctx->no_wait_gpu);
1502 if (ret == 0)
1503 ret = ttm_bo_move_memcpy(bo, ctx, new_reg);
1504
1505 out:
1506 if (drm->client.device.info.family < NV_DEVICE_INFO_V0_TESLA) {
1507 if (ret)
1508 nouveau_bo_vm_cleanup(bo, NULL, &new_tile);
1509 else
1510 nouveau_bo_vm_cleanup(bo, new_tile, &nvbo->tile);
1511 }
1512
1513 return ret;
1514 }
1515
1516 static int
nouveau_bo_verify_access(struct ttm_buffer_object * bo,struct file * filp)1517 nouveau_bo_verify_access(struct ttm_buffer_object *bo, struct file *filp)
1518 {
1519 #ifdef __NetBSD__
1520 struct drm_file *file = filp->f_data;
1521 #else
1522 struct drm_file *file = filp->private_data;
1523 #endif
1524 struct nouveau_bo *nvbo = nouveau_bo(bo);
1525
1526 return drm_vma_node_verify_access(&nvbo->bo.base.vma_node, file);
1527 }
1528
1529 static int
nouveau_ttm_io_mem_reserve(struct ttm_bo_device * bdev,struct ttm_mem_reg * reg)1530 nouveau_ttm_io_mem_reserve(struct ttm_bo_device *bdev, struct ttm_mem_reg *reg)
1531 {
1532 struct ttm_mem_type_manager *man = &bdev->man[reg->mem_type];
1533 struct nouveau_drm *drm = nouveau_bdev(bdev);
1534 struct nvkm_device *device = nvxx_device(&drm->client.device);
1535 struct nouveau_mem *mem = nouveau_mem(reg);
1536
1537 reg->bus.addr = NULL;
1538 reg->bus.offset = 0;
1539 reg->bus.size = reg->num_pages << PAGE_SHIFT;
1540 reg->bus.base = 0;
1541 reg->bus.is_iomem = false;
1542 if (!(man->flags & TTM_MEMTYPE_FLAG_MAPPABLE))
1543 return -EINVAL;
1544 switch (reg->mem_type) {
1545 case TTM_PL_SYSTEM:
1546 /* System memory */
1547 return 0;
1548 case TTM_PL_TT:
1549 #if IS_ENABLED(CONFIG_AGP)
1550 if (drm->agp.bridge) {
1551 reg->bus.offset = reg->start << PAGE_SHIFT;
1552 reg->bus.base = drm->agp.base;
1553 reg->bus.is_iomem = !drm->agp.cma;
1554 }
1555 #endif
1556 if (drm->client.mem->oclass < NVIF_CLASS_MEM_NV50 || !mem->kind)
1557 /* untiled */
1558 break;
1559 /* fall through - tiled memory */
1560 case TTM_PL_VRAM:
1561 reg->bus.offset = reg->start << PAGE_SHIFT;
1562 reg->bus.base = device->func->resource_addr(device, 1);
1563 reg->bus.is_iomem = true;
1564 if (drm->client.mem->oclass >= NVIF_CLASS_MEM_NV50) {
1565 union {
1566 struct nv50_mem_map_v0 nv50;
1567 struct gf100_mem_map_v0 gf100;
1568 } args;
1569 u64 handle, length;
1570 u32 argc = 0;
1571 int ret;
1572
1573 switch (mem->mem.object.oclass) {
1574 case NVIF_CLASS_MEM_NV50:
1575 args.nv50.version = 0;
1576 args.nv50.ro = 0;
1577 args.nv50.kind = mem->kind;
1578 args.nv50.comp = mem->comp;
1579 argc = sizeof(args.nv50);
1580 break;
1581 case NVIF_CLASS_MEM_GF100:
1582 args.gf100.version = 0;
1583 args.gf100.ro = 0;
1584 args.gf100.kind = mem->kind;
1585 argc = sizeof(args.gf100);
1586 break;
1587 default:
1588 WARN_ON(1);
1589 break;
1590 }
1591
1592 ret = nvif_object_map_handle(&mem->mem.object,
1593 &args, argc,
1594 #ifdef __NetBSD__
1595 NULL,
1596 #endif
1597 &handle, &length);
1598 if (ret != 1)
1599 return ret ? ret : -EINVAL;
1600
1601 reg->bus.base = 0;
1602 reg->bus.offset = handle;
1603 }
1604 break;
1605 default:
1606 return -EINVAL;
1607 }
1608 return 0;
1609 }
1610
1611 static void
nouveau_ttm_io_mem_free(struct ttm_bo_device * bdev,struct ttm_mem_reg * reg)1612 nouveau_ttm_io_mem_free(struct ttm_bo_device *bdev, struct ttm_mem_reg *reg)
1613 {
1614 struct nouveau_drm *drm = nouveau_bdev(bdev);
1615 struct nouveau_mem *mem = nouveau_mem(reg);
1616
1617 if (drm->client.mem->oclass >= NVIF_CLASS_MEM_NV50) {
1618 switch (reg->mem_type) {
1619 case TTM_PL_TT:
1620 if (mem->kind)
1621 nvif_object_unmap_handle(&mem->mem.object);
1622 break;
1623 case TTM_PL_VRAM:
1624 nvif_object_unmap_handle(&mem->mem.object);
1625 break;
1626 default:
1627 break;
1628 }
1629 }
1630 }
1631
1632 static int
nouveau_ttm_fault_reserve_notify(struct ttm_buffer_object * bo)1633 nouveau_ttm_fault_reserve_notify(struct ttm_buffer_object *bo)
1634 {
1635 struct nouveau_drm *drm = nouveau_bdev(bo->bdev);
1636 struct nouveau_bo *nvbo = nouveau_bo(bo);
1637 struct nvkm_device *device = nvxx_device(&drm->client.device);
1638 u32 mappable = device->func->resource_size(device, 1) >> PAGE_SHIFT;
1639 int i, ret;
1640
1641 /* as long as the bo isn't in vram, and isn't tiled, we've got
1642 * nothing to do here.
1643 */
1644 if (bo->mem.mem_type != TTM_PL_VRAM) {
1645 if (drm->client.device.info.family < NV_DEVICE_INFO_V0_TESLA ||
1646 !nvbo->kind)
1647 return 0;
1648
1649 if (bo->mem.mem_type == TTM_PL_SYSTEM) {
1650 nouveau_bo_placement_set(nvbo, TTM_PL_TT, 0);
1651
1652 ret = nouveau_bo_validate(nvbo, false, false);
1653 if (ret)
1654 return ret;
1655 }
1656 return 0;
1657 }
1658
1659 /* make sure bo is in mappable vram */
1660 if (drm->client.device.info.family >= NV_DEVICE_INFO_V0_TESLA ||
1661 bo->mem.start + bo->mem.num_pages < mappable)
1662 return 0;
1663
1664 for (i = 0; i < nvbo->placement.num_placement; ++i) {
1665 nvbo->placements[i].fpfn = 0;
1666 nvbo->placements[i].lpfn = mappable;
1667 }
1668
1669 for (i = 0; i < nvbo->placement.num_busy_placement; ++i) {
1670 nvbo->busy_placements[i].fpfn = 0;
1671 nvbo->busy_placements[i].lpfn = mappable;
1672 }
1673
1674 nouveau_bo_placement_set(nvbo, TTM_PL_FLAG_VRAM, 0);
1675 return nouveau_bo_validate(nvbo, false, false);
1676 }
1677
1678 static int
nouveau_ttm_tt_populate(struct ttm_tt * ttm,struct ttm_operation_ctx * ctx)1679 nouveau_ttm_tt_populate(struct ttm_tt *ttm, struct ttm_operation_ctx *ctx)
1680 {
1681 struct ttm_dma_tt *ttm_dma = (void *)ttm;
1682 struct nouveau_drm *drm;
1683 struct device *dev;
1684 unsigned i;
1685 int r;
1686 bool slave = !!(ttm->page_flags & TTM_PAGE_FLAG_SG);
1687
1688 if (ttm->state != tt_unpopulated)
1689 return 0;
1690
1691 if (slave && ttm->sg) {
1692 /* make userspace faulting work */
1693 #ifdef __NetBSD__
1694 r = drm_prime_bus_dmamap_load_sgt(ttm->bdev->dmat,
1695 ttm_dma->dma_address, ttm->sg);
1696 if (r)
1697 return r;
1698 #else
1699 drm_prime_sg_to_page_addr_arrays(ttm->sg, ttm->pages,
1700 ttm_dma->dma_address, ttm->num_pages);
1701 #endif
1702 ttm->state = tt_unbound;
1703 return 0;
1704 }
1705
1706 drm = nouveau_bdev(ttm->bdev);
1707 dev = drm->dev->dev;
1708
1709 #if IS_ENABLED(CONFIG_AGP)
1710 if (drm->agp.bridge) {
1711 return ttm_agp_tt_populate(ttm, ctx);
1712 }
1713 #endif
1714
1715 #ifdef __NetBSD__
1716 __USE(i);
1717 __USE(dev);
1718 return ttm_bus_dma_populate(ttm_dma);
1719 #else
1720 #if IS_ENABLED(CONFIG_SWIOTLB) && IS_ENABLED(CONFIG_X86)
1721 if (swiotlb_nr_tbl()) {
1722 return ttm_dma_populate((void *)ttm, dev, ctx);
1723 }
1724 #endif
1725
1726 r = ttm_pool_populate(ttm, ctx);
1727 if (r) {
1728 return r;
1729 }
1730
1731 for (i = 0; i < ttm->num_pages; i++) {
1732 dma_addr_t addr;
1733
1734 addr = dma_map_page(dev, ttm->pages[i], 0, PAGE_SIZE,
1735 DMA_BIDIRECTIONAL);
1736
1737 if (dma_mapping_error(dev, addr)) {
1738 while (i--) {
1739 dma_unmap_page(dev, ttm_dma->dma_address[i],
1740 PAGE_SIZE, DMA_BIDIRECTIONAL);
1741 ttm_dma->dma_address[i] = 0;
1742 }
1743 ttm_pool_unpopulate(ttm);
1744 return -EFAULT;
1745 }
1746
1747 ttm_dma->dma_address[i] = addr;
1748 }
1749 return 0;
1750 #endif
1751 }
1752
1753 static void
nouveau_ttm_tt_unpopulate(struct ttm_tt * ttm)1754 nouveau_ttm_tt_unpopulate(struct ttm_tt *ttm)
1755 {
1756 struct ttm_dma_tt *ttm_dma = (void *)ttm;
1757 struct nouveau_drm *drm;
1758 struct device *dev;
1759 unsigned i;
1760 bool slave = !!(ttm->page_flags & TTM_PAGE_FLAG_SG);
1761
1762 if (slave)
1763 return;
1764
1765 drm = nouveau_bdev(ttm->bdev);
1766 dev = drm->dev->dev;
1767
1768 #if IS_ENABLED(CONFIG_AGP)
1769 if (drm->agp.bridge) {
1770 ttm_agp_tt_unpopulate(ttm);
1771 return;
1772 }
1773 #endif
1774
1775 #ifdef __NetBSD__
1776 __USE(i);
1777 __USE(dev);
1778 ttm_bus_dma_unpopulate(ttm_dma);
1779 #else
1780 #if IS_ENABLED(CONFIG_SWIOTLB) && IS_ENABLED(CONFIG_X86)
1781 if (swiotlb_nr_tbl()) {
1782 ttm_dma_unpopulate((void *)ttm, dev);
1783 #endif
1784 return;
1785 }
1786
1787 for (i = 0; i < ttm->num_pages; i++) {
1788 if (ttm_dma->dma_address[i]) {
1789 dma_unmap_page(dev, ttm_dma->dma_address[i], PAGE_SIZE,
1790 DMA_BIDIRECTIONAL);
1791 }
1792 }
1793
1794 ttm_pool_unpopulate(ttm);
1795 #endif
1796 }
1797
1798 #ifdef __NetBSD__
1799 static void
nouveau_ttm_tt_swapout(struct ttm_tt * ttm)1800 nouveau_ttm_tt_swapout(struct ttm_tt *ttm)
1801 {
1802 struct ttm_dma_tt *ttm_dma = container_of(ttm, struct ttm_dma_tt, ttm);
1803
1804 ttm_bus_dma_swapout(ttm_dma);
1805 }
1806 #endif
1807
1808 void
nouveau_bo_fence(struct nouveau_bo * nvbo,struct nouveau_fence * fence,bool exclusive)1809 nouveau_bo_fence(struct nouveau_bo *nvbo, struct nouveau_fence *fence, bool exclusive)
1810 {
1811 struct dma_resv *resv = nvbo->bo.base.resv;
1812
1813 if (exclusive)
1814 dma_resv_add_excl_fence(resv, &fence->base);
1815 else if (fence)
1816 dma_resv_add_shared_fence(resv, &fence->base);
1817 }
1818
1819 #ifdef __NetBSD__
1820 static const struct uvm_pagerops nouveau_uvm_ops = {
1821 .pgo_reference = &ttm_bo_uvm_reference,
1822 .pgo_detach = &ttm_bo_uvm_detach,
1823 .pgo_fault = &ttm_bo_uvm_fault,
1824 };
1825 #endif
1826
1827 struct ttm_bo_driver nouveau_bo_driver = {
1828 .ttm_tt_create = &nouveau_ttm_tt_create,
1829 .ttm_tt_populate = &nouveau_ttm_tt_populate,
1830 .ttm_tt_unpopulate = &nouveau_ttm_tt_unpopulate,
1831 #ifdef __NetBSD__
1832 .ttm_tt_swapout = &nouveau_ttm_tt_swapout,
1833 .ttm_uvm_ops = &nouveau_uvm_ops,
1834 #endif
1835 .invalidate_caches = nouveau_bo_invalidate_caches,
1836 .init_mem_type = nouveau_bo_init_mem_type,
1837 .eviction_valuable = ttm_bo_eviction_valuable,
1838 .evict_flags = nouveau_bo_evict_flags,
1839 .move_notify = nouveau_bo_move_ntfy,
1840 .move = nouveau_bo_move,
1841 .verify_access = nouveau_bo_verify_access,
1842 .fault_reserve_notify = &nouveau_ttm_fault_reserve_notify,
1843 .io_mem_reserve = &nouveau_ttm_io_mem_reserve,
1844 .io_mem_free = &nouveau_ttm_io_mem_free,
1845 };
1846