0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019
0020
0021
0022
0023
0024 #include <drm/drm_drv.h>
0025
0026 #include "amdgpu.h"
0027 #include "amdgpu_trace.h"
0028 #include "amdgpu_vm.h"
0029
0030
0031
0032
0033 struct amdgpu_vm_pt_cursor {
0034 uint64_t pfn;
0035 struct amdgpu_vm_bo_base *parent;
0036 struct amdgpu_vm_bo_base *entry;
0037 unsigned int level;
0038 };
0039
0040
0041
0042
0043
0044
0045
0046
0047
0048
0049 static unsigned int amdgpu_vm_pt_level_shift(struct amdgpu_device *adev,
0050 unsigned int level)
0051 {
0052 switch (level) {
0053 case AMDGPU_VM_PDB2:
0054 case AMDGPU_VM_PDB1:
0055 case AMDGPU_VM_PDB0:
0056 return 9 * (AMDGPU_VM_PDB0 - level) +
0057 adev->vm_manager.block_size;
0058 case AMDGPU_VM_PTB:
0059 return 0;
0060 default:
0061 return ~0;
0062 }
0063 }
0064
0065
0066
0067
0068
0069
0070
0071
0072
0073
0074 static unsigned int amdgpu_vm_pt_num_entries(struct amdgpu_device *adev,
0075 unsigned int level)
0076 {
0077 unsigned int shift;
0078
0079 shift = amdgpu_vm_pt_level_shift(adev, adev->vm_manager.root_level);
0080 if (level == adev->vm_manager.root_level)
0081
0082 return round_up(adev->vm_manager.max_pfn, 1ULL << shift)
0083 >> shift;
0084 else if (level != AMDGPU_VM_PTB)
0085
0086 return 512;
0087
0088
0089 return AMDGPU_VM_PTE_COUNT(adev);
0090 }
0091
0092
0093
0094
0095
0096
0097
0098
0099
0100 static unsigned int amdgpu_vm_pt_num_ats_entries(struct amdgpu_device *adev)
0101 {
0102 unsigned int shift;
0103
0104 shift = amdgpu_vm_pt_level_shift(adev, adev->vm_manager.root_level);
0105 return AMDGPU_GMC_HOLE_START >> (shift + AMDGPU_GPU_PAGE_SHIFT);
0106 }
0107
0108
0109
0110
0111
0112
0113
0114
0115
0116
0117 static uint32_t amdgpu_vm_pt_entries_mask(struct amdgpu_device *adev,
0118 unsigned int level)
0119 {
0120 if (level <= adev->vm_manager.root_level)
0121 return 0xffffffff;
0122 else if (level != AMDGPU_VM_PTB)
0123 return 0x1ff;
0124 else
0125 return AMDGPU_VM_PTE_COUNT(adev) - 1;
0126 }
0127
0128
0129
0130
0131
0132
0133
0134
0135
0136
0137 static unsigned int amdgpu_vm_pt_size(struct amdgpu_device *adev,
0138 unsigned int level)
0139 {
0140 return AMDGPU_GPU_PAGE_ALIGN(amdgpu_vm_pt_num_entries(adev, level) * 8);
0141 }
0142
0143
0144
0145
0146
0147
0148
0149
0150
0151 static struct amdgpu_vm_bo_base *
0152 amdgpu_vm_pt_parent(struct amdgpu_vm_bo_base *pt)
0153 {
0154 struct amdgpu_bo *parent = pt->bo->parent;
0155
0156 if (!parent)
0157 return NULL;
0158
0159 return parent->vm_bo;
0160 }
0161
0162
0163
0164
0165
0166
0167
0168
0169
0170
0171
0172 static void amdgpu_vm_pt_start(struct amdgpu_device *adev,
0173 struct amdgpu_vm *vm, uint64_t start,
0174 struct amdgpu_vm_pt_cursor *cursor)
0175 {
0176 cursor->pfn = start;
0177 cursor->parent = NULL;
0178 cursor->entry = &vm->root;
0179 cursor->level = adev->vm_manager.root_level;
0180 }
0181
0182
0183
0184
0185
0186
0187
0188
0189
0190
0191
0192 static bool amdgpu_vm_pt_descendant(struct amdgpu_device *adev,
0193 struct amdgpu_vm_pt_cursor *cursor)
0194 {
0195 unsigned int mask, shift, idx;
0196
0197 if ((cursor->level == AMDGPU_VM_PTB) || !cursor->entry ||
0198 !cursor->entry->bo)
0199 return false;
0200
0201 mask = amdgpu_vm_pt_entries_mask(adev, cursor->level);
0202 shift = amdgpu_vm_pt_level_shift(adev, cursor->level);
0203
0204 ++cursor->level;
0205 idx = (cursor->pfn >> shift) & mask;
0206 cursor->parent = cursor->entry;
0207 cursor->entry = &to_amdgpu_bo_vm(cursor->entry->bo)->entries[idx];
0208 return true;
0209 }
0210
0211
0212
0213
0214
0215
0216
0217
0218
0219
0220
0221 static bool amdgpu_vm_pt_sibling(struct amdgpu_device *adev,
0222 struct amdgpu_vm_pt_cursor *cursor)
0223 {
0224
0225 unsigned int shift, num_entries;
0226 struct amdgpu_bo_vm *parent;
0227
0228
0229 if (!cursor->parent)
0230 return false;
0231
0232
0233 shift = amdgpu_vm_pt_level_shift(adev, cursor->level - 1);
0234 num_entries = amdgpu_vm_pt_num_entries(adev, cursor->level - 1);
0235 parent = to_amdgpu_bo_vm(cursor->parent->bo);
0236
0237 if (cursor->entry == &parent->entries[num_entries - 1])
0238 return false;
0239
0240 cursor->pfn += 1ULL << shift;
0241 cursor->pfn &= ~((1ULL << shift) - 1);
0242 ++cursor->entry;
0243 return true;
0244 }
0245
0246
0247
0248
0249
0250
0251
0252
0253
0254
0255 static bool amdgpu_vm_pt_ancestor(struct amdgpu_vm_pt_cursor *cursor)
0256 {
0257 if (!cursor->parent)
0258 return false;
0259
0260 --cursor->level;
0261 cursor->entry = cursor->parent;
0262 cursor->parent = amdgpu_vm_pt_parent(cursor->parent);
0263 return true;
0264 }
0265
0266
0267
0268
0269
0270
0271
0272
0273
0274 static void amdgpu_vm_pt_next(struct amdgpu_device *adev,
0275 struct amdgpu_vm_pt_cursor *cursor)
0276 {
0277
0278 if (amdgpu_vm_pt_descendant(adev, cursor))
0279 return;
0280
0281
0282 while (!amdgpu_vm_pt_sibling(adev, cursor)) {
0283
0284 if (!amdgpu_vm_pt_ancestor(cursor)) {
0285 cursor->pfn = ~0ll;
0286 return;
0287 }
0288 }
0289 }
0290
0291
0292
0293
0294
0295
0296
0297
0298
0299
0300
0301 static void amdgpu_vm_pt_first_dfs(struct amdgpu_device *adev,
0302 struct amdgpu_vm *vm,
0303 struct amdgpu_vm_pt_cursor *start,
0304 struct amdgpu_vm_pt_cursor *cursor)
0305 {
0306 if (start)
0307 *cursor = *start;
0308 else
0309 amdgpu_vm_pt_start(adev, vm, 0, cursor);
0310
0311 while (amdgpu_vm_pt_descendant(adev, cursor))
0312 ;
0313 }
0314
0315
0316
0317
0318
0319
0320
0321
0322
0323
0324 static bool amdgpu_vm_pt_continue_dfs(struct amdgpu_vm_pt_cursor *start,
0325 struct amdgpu_vm_bo_base *entry)
0326 {
0327 return entry && (!start || entry != start->entry);
0328 }
0329
0330
0331
0332
0333
0334
0335
0336
0337
0338 static void amdgpu_vm_pt_next_dfs(struct amdgpu_device *adev,
0339 struct amdgpu_vm_pt_cursor *cursor)
0340 {
0341 if (!cursor->entry)
0342 return;
0343
0344 if (!cursor->parent)
0345 cursor->entry = NULL;
0346 else if (amdgpu_vm_pt_sibling(adev, cursor))
0347 while (amdgpu_vm_pt_descendant(adev, cursor))
0348 ;
0349 else
0350 amdgpu_vm_pt_ancestor(cursor);
0351 }
0352
0353
0354
0355
0356 #define for_each_amdgpu_vm_pt_dfs_safe(adev, vm, start, cursor, entry) \
0357 for (amdgpu_vm_pt_first_dfs((adev), (vm), (start), &(cursor)), \
0358 (entry) = (cursor).entry, amdgpu_vm_pt_next_dfs((adev), &(cursor));\
0359 amdgpu_vm_pt_continue_dfs((start), (entry)); \
0360 (entry) = (cursor).entry, amdgpu_vm_pt_next_dfs((adev), &(cursor)))
0361
0362
0363
0364
0365
0366
0367
0368
0369
0370
0371
0372
0373
0374
0375 int amdgpu_vm_pt_clear(struct amdgpu_device *adev, struct amdgpu_vm *vm,
0376 struct amdgpu_bo_vm *vmbo, bool immediate)
0377 {
0378 unsigned int level = adev->vm_manager.root_level;
0379 struct ttm_operation_ctx ctx = { true, false };
0380 struct amdgpu_vm_update_params params;
0381 struct amdgpu_bo *ancestor = &vmbo->bo;
0382 unsigned int entries, ats_entries;
0383 struct amdgpu_bo *bo = &vmbo->bo;
0384 uint64_t addr;
0385 int r, idx;
0386
0387
0388 if (ancestor->parent) {
0389 ++level;
0390 while (ancestor->parent->parent) {
0391 ++level;
0392 ancestor = ancestor->parent;
0393 }
0394 }
0395
0396 entries = amdgpu_bo_size(bo) / 8;
0397 if (!vm->pte_support_ats) {
0398 ats_entries = 0;
0399
0400 } else if (!bo->parent) {
0401 ats_entries = amdgpu_vm_pt_num_ats_entries(adev);
0402 ats_entries = min(ats_entries, entries);
0403 entries -= ats_entries;
0404
0405 } else {
0406 struct amdgpu_vm_bo_base *pt;
0407
0408 pt = ancestor->vm_bo;
0409 ats_entries = amdgpu_vm_pt_num_ats_entries(adev);
0410 if ((pt - to_amdgpu_bo_vm(vm->root.bo)->entries) >=
0411 ats_entries) {
0412 ats_entries = 0;
0413 } else {
0414 ats_entries = entries;
0415 entries = 0;
0416 }
0417 }
0418
0419 r = ttm_bo_validate(&bo->tbo, &bo->placement, &ctx);
0420 if (r)
0421 return r;
0422
0423 if (vmbo->shadow) {
0424 struct amdgpu_bo *shadow = vmbo->shadow;
0425
0426 r = ttm_bo_validate(&shadow->tbo, &shadow->placement, &ctx);
0427 if (r)
0428 return r;
0429 }
0430
0431 if (!drm_dev_enter(adev_to_drm(adev), &idx))
0432 return -ENODEV;
0433
0434 r = vm->update_funcs->map_table(vmbo);
0435 if (r)
0436 goto exit;
0437
0438 memset(¶ms, 0, sizeof(params));
0439 params.adev = adev;
0440 params.vm = vm;
0441 params.immediate = immediate;
0442
0443 r = vm->update_funcs->prepare(¶ms, NULL, AMDGPU_SYNC_EXPLICIT);
0444 if (r)
0445 goto exit;
0446
0447 addr = 0;
0448 if (ats_entries) {
0449 uint64_t value = 0, flags;
0450
0451 flags = AMDGPU_PTE_DEFAULT_ATC;
0452 if (level != AMDGPU_VM_PTB) {
0453
0454 flags |= AMDGPU_PDE_PTE;
0455 amdgpu_gmc_get_vm_pde(adev, level, &value, &flags);
0456 }
0457
0458 r = vm->update_funcs->update(¶ms, vmbo, addr, 0,
0459 ats_entries, value, flags);
0460 if (r)
0461 goto exit;
0462
0463 addr += ats_entries * 8;
0464 }
0465
0466 if (entries) {
0467 uint64_t value = 0, flags = 0;
0468
0469 if (adev->asic_type >= CHIP_VEGA10) {
0470 if (level != AMDGPU_VM_PTB) {
0471
0472 flags |= AMDGPU_PDE_PTE;
0473 amdgpu_gmc_get_vm_pde(adev, level,
0474 &value, &flags);
0475 } else {
0476
0477 flags = AMDGPU_PTE_EXECUTABLE;
0478 }
0479 }
0480
0481 r = vm->update_funcs->update(¶ms, vmbo, addr, 0, entries,
0482 value, flags);
0483 if (r)
0484 goto exit;
0485 }
0486
0487 r = vm->update_funcs->commit(¶ms, NULL);
0488 exit:
0489 drm_dev_exit(idx);
0490 return r;
0491 }
0492
0493
0494
0495
0496
0497
0498
0499
0500
0501
0502 int amdgpu_vm_pt_create(struct amdgpu_device *adev, struct amdgpu_vm *vm,
0503 int level, bool immediate, struct amdgpu_bo_vm **vmbo)
0504 {
0505 struct amdgpu_bo_param bp;
0506 struct amdgpu_bo *bo;
0507 struct dma_resv *resv;
0508 unsigned int num_entries;
0509 int r;
0510
0511 memset(&bp, 0, sizeof(bp));
0512
0513 bp.size = amdgpu_vm_pt_size(adev, level);
0514 bp.byte_align = AMDGPU_GPU_PAGE_SIZE;
0515 bp.domain = AMDGPU_GEM_DOMAIN_VRAM;
0516 bp.domain = amdgpu_bo_get_preferred_domain(adev, bp.domain);
0517 bp.flags = AMDGPU_GEM_CREATE_VRAM_CONTIGUOUS |
0518 AMDGPU_GEM_CREATE_CPU_GTT_USWC;
0519
0520 if (level < AMDGPU_VM_PTB)
0521 num_entries = amdgpu_vm_pt_num_entries(adev, level);
0522 else
0523 num_entries = 0;
0524
0525 bp.bo_ptr_size = struct_size((*vmbo), entries, num_entries);
0526
0527 if (vm->use_cpu_for_update)
0528 bp.flags |= AMDGPU_GEM_CREATE_CPU_ACCESS_REQUIRED;
0529
0530 bp.type = ttm_bo_type_kernel;
0531 bp.no_wait_gpu = immediate;
0532 if (vm->root.bo)
0533 bp.resv = vm->root.bo->tbo.base.resv;
0534
0535 r = amdgpu_bo_create_vm(adev, &bp, vmbo);
0536 if (r)
0537 return r;
0538
0539 bo = &(*vmbo)->bo;
0540 if (vm->is_compute_context || (adev->flags & AMD_IS_APU)) {
0541 (*vmbo)->shadow = NULL;
0542 return 0;
0543 }
0544
0545 if (!bp.resv)
0546 WARN_ON(dma_resv_lock(bo->tbo.base.resv,
0547 NULL));
0548 resv = bp.resv;
0549 memset(&bp, 0, sizeof(bp));
0550 bp.size = amdgpu_vm_pt_size(adev, level);
0551 bp.domain = AMDGPU_GEM_DOMAIN_GTT;
0552 bp.flags = AMDGPU_GEM_CREATE_CPU_GTT_USWC;
0553 bp.type = ttm_bo_type_kernel;
0554 bp.resv = bo->tbo.base.resv;
0555 bp.bo_ptr_size = sizeof(struct amdgpu_bo);
0556
0557 r = amdgpu_bo_create(adev, &bp, &(*vmbo)->shadow);
0558
0559 if (!resv)
0560 dma_resv_unlock(bo->tbo.base.resv);
0561
0562 if (r) {
0563 amdgpu_bo_unref(&bo);
0564 return r;
0565 }
0566
0567 (*vmbo)->shadow->parent = amdgpu_bo_ref(bo);
0568 amdgpu_bo_add_to_shadow_list(*vmbo);
0569
0570 return 0;
0571 }
0572
0573
0574
0575
0576
0577
0578
0579
0580
0581
0582
0583
0584
0585
0586
0587 static int amdgpu_vm_pt_alloc(struct amdgpu_device *adev,
0588 struct amdgpu_vm *vm,
0589 struct amdgpu_vm_pt_cursor *cursor,
0590 bool immediate)
0591 {
0592 struct amdgpu_vm_bo_base *entry = cursor->entry;
0593 struct amdgpu_bo *pt_bo;
0594 struct amdgpu_bo_vm *pt;
0595 int r;
0596
0597 if (entry->bo)
0598 return 0;
0599
0600 r = amdgpu_vm_pt_create(adev, vm, cursor->level, immediate, &pt);
0601 if (r)
0602 return r;
0603
0604
0605
0606
0607 pt_bo = &pt->bo;
0608 pt_bo->parent = amdgpu_bo_ref(cursor->parent->bo);
0609 amdgpu_vm_bo_base_init(entry, vm, pt_bo);
0610 r = amdgpu_vm_pt_clear(adev, vm, pt, immediate);
0611 if (r)
0612 goto error_free_pt;
0613
0614 return 0;
0615
0616 error_free_pt:
0617 amdgpu_bo_unref(&pt->shadow);
0618 amdgpu_bo_unref(&pt_bo);
0619 return r;
0620 }
0621
0622
0623
0624
0625
0626
0627 static void amdgpu_vm_pt_free(struct amdgpu_vm_bo_base *entry)
0628 {
0629 struct amdgpu_bo *shadow;
0630
0631 if (!entry->bo)
0632 return;
0633 shadow = amdgpu_bo_shadowed(entry->bo);
0634 if (shadow) {
0635 ttm_bo_set_bulk_move(&shadow->tbo, NULL);
0636 amdgpu_bo_unref(&shadow);
0637 }
0638 ttm_bo_set_bulk_move(&entry->bo->tbo, NULL);
0639 entry->bo->vm_bo = NULL;
0640 list_del(&entry->vm_status);
0641 amdgpu_bo_unref(&entry->bo);
0642 }
0643
0644
0645
0646
0647
0648
0649
0650
0651
0652
0653 static void amdgpu_vm_pt_free_dfs(struct amdgpu_device *adev,
0654 struct amdgpu_vm *vm,
0655 struct amdgpu_vm_pt_cursor *start)
0656 {
0657 struct amdgpu_vm_pt_cursor cursor;
0658 struct amdgpu_vm_bo_base *entry;
0659
0660 for_each_amdgpu_vm_pt_dfs_safe(adev, vm, start, cursor, entry)
0661 amdgpu_vm_pt_free(entry);
0662
0663 if (start)
0664 amdgpu_vm_pt_free(start->entry);
0665 }
0666
0667
0668
0669
0670
0671
0672
0673
0674 void amdgpu_vm_pt_free_root(struct amdgpu_device *adev, struct amdgpu_vm *vm)
0675 {
0676 amdgpu_vm_pt_free_dfs(adev, vm, NULL);
0677 }
0678
0679
0680
0681
0682
0683
0684
0685
0686
0687
0688
0689
0690
0691
0692 bool amdgpu_vm_pt_is_root_clean(struct amdgpu_device *adev,
0693 struct amdgpu_vm *vm)
0694 {
0695 enum amdgpu_vm_level root = adev->vm_manager.root_level;
0696 unsigned int entries = amdgpu_vm_pt_num_entries(adev, root);
0697 unsigned int i = 0;
0698
0699 for (i = 0; i < entries; i++) {
0700 if (to_amdgpu_bo_vm(vm->root.bo)->entries[i].bo)
0701 return false;
0702 }
0703 return true;
0704 }
0705
0706
0707
0708
0709
0710
0711
0712
0713
0714 int amdgpu_vm_pde_update(struct amdgpu_vm_update_params *params,
0715 struct amdgpu_vm_bo_base *entry)
0716 {
0717 struct amdgpu_vm_bo_base *parent = amdgpu_vm_pt_parent(entry);
0718 struct amdgpu_bo *bo = parent->bo, *pbo;
0719 struct amdgpu_vm *vm = params->vm;
0720 uint64_t pde, pt, flags;
0721 unsigned int level;
0722
0723 for (level = 0, pbo = bo->parent; pbo; ++level)
0724 pbo = pbo->parent;
0725
0726 level += params->adev->vm_manager.root_level;
0727 amdgpu_gmc_get_pde_for_bo(entry->bo, level, &pt, &flags);
0728 pde = (entry - to_amdgpu_bo_vm(parent->bo)->entries) * 8;
0729 return vm->update_funcs->update(params, to_amdgpu_bo_vm(bo), pde, pt,
0730 1, 0, flags);
0731 }
0732
0733
0734
0735
0736
0737
0738 static void amdgpu_vm_pte_update_flags(struct amdgpu_vm_update_params *params,
0739 struct amdgpu_bo_vm *pt,
0740 unsigned int level,
0741 uint64_t pe, uint64_t addr,
0742 unsigned int count, uint32_t incr,
0743 uint64_t flags)
0744
0745 {
0746 if (level != AMDGPU_VM_PTB) {
0747 flags |= AMDGPU_PDE_PTE;
0748 amdgpu_gmc_get_vm_pde(params->adev, level, &addr, &flags);
0749
0750 } else if (params->adev->asic_type >= CHIP_VEGA10 &&
0751 !(flags & AMDGPU_PTE_VALID) &&
0752 !(flags & AMDGPU_PTE_PRT)) {
0753
0754
0755 flags |= AMDGPU_PTE_EXECUTABLE;
0756 }
0757
0758 params->vm->update_funcs->update(params, pt, pe, addr, count, incr,
0759 flags);
0760 }
0761
0762
0763
0764
0765
0766
0767
0768
0769
0770
0771
0772
0773
0774 static void amdgpu_vm_pte_fragment(struct amdgpu_vm_update_params *params,
0775 uint64_t start, uint64_t end, uint64_t flags,
0776 unsigned int *frag, uint64_t *frag_end)
0777 {
0778
0779
0780
0781
0782
0783
0784
0785
0786
0787
0788
0789
0790
0791
0792
0793
0794
0795
0796
0797
0798
0799 unsigned int max_frag;
0800
0801 if (params->adev->asic_type < CHIP_VEGA10)
0802 max_frag = params->adev->vm_manager.fragment_size;
0803 else
0804 max_frag = 31;
0805
0806
0807 if (params->pages_addr) {
0808 *frag = 0;
0809 *frag_end = end;
0810 return;
0811 }
0812
0813
0814 *frag = min_t(unsigned int, ffs(start) - 1, fls64(end - start) - 1);
0815 if (*frag >= max_frag) {
0816 *frag = max_frag;
0817 *frag_end = end & ~((1ULL << max_frag) - 1);
0818 } else {
0819 *frag_end = start + (1 << *frag);
0820 }
0821 }
0822
0823
0824
0825
0826
0827
0828
0829
0830
0831
0832
0833
0834
0835
0836
0837 int amdgpu_vm_ptes_update(struct amdgpu_vm_update_params *params,
0838 uint64_t start, uint64_t end,
0839 uint64_t dst, uint64_t flags)
0840 {
0841 struct amdgpu_device *adev = params->adev;
0842 struct amdgpu_vm_pt_cursor cursor;
0843 uint64_t frag_start = start, frag_end;
0844 unsigned int frag;
0845 int r;
0846
0847
0848 amdgpu_vm_pte_fragment(params, frag_start, end, flags, &frag,
0849 &frag_end);
0850
0851
0852 amdgpu_vm_pt_start(adev, params->vm, start, &cursor);
0853 while (cursor.pfn < end) {
0854 unsigned int shift, parent_shift, mask;
0855 uint64_t incr, entry_end, pe_start;
0856 struct amdgpu_bo *pt;
0857
0858 if (!params->unlocked) {
0859
0860
0861
0862 r = amdgpu_vm_pt_alloc(params->adev, params->vm,
0863 &cursor, params->immediate);
0864 if (r)
0865 return r;
0866 }
0867
0868 shift = amdgpu_vm_pt_level_shift(adev, cursor.level);
0869 parent_shift = amdgpu_vm_pt_level_shift(adev, cursor.level - 1);
0870 if (params->unlocked) {
0871
0872 if (amdgpu_vm_pt_descendant(adev, &cursor))
0873 continue;
0874 } else if (adev->asic_type < CHIP_VEGA10 &&
0875 (flags & AMDGPU_PTE_VALID)) {
0876
0877 if (cursor.level != AMDGPU_VM_PTB) {
0878 if (!amdgpu_vm_pt_descendant(adev, &cursor))
0879 return -ENOENT;
0880 continue;
0881 }
0882 } else if (frag < shift) {
0883
0884
0885
0886
0887 if (amdgpu_vm_pt_descendant(adev, &cursor))
0888 continue;
0889 } else if (frag >= parent_shift) {
0890
0891
0892
0893 if (!amdgpu_vm_pt_ancestor(&cursor))
0894 return -EINVAL;
0895 continue;
0896 }
0897
0898 pt = cursor.entry->bo;
0899 if (!pt) {
0900
0901 if (flags & AMDGPU_PTE_VALID)
0902 return -ENOENT;
0903
0904
0905
0906
0907 if (!amdgpu_vm_pt_ancestor(&cursor))
0908 return -EINVAL;
0909
0910 pt = cursor.entry->bo;
0911 shift = parent_shift;
0912 frag_end = max(frag_end, ALIGN(frag_start + 1,
0913 1ULL << shift));
0914 }
0915
0916
0917 incr = (uint64_t)AMDGPU_GPU_PAGE_SIZE << shift;
0918 mask = amdgpu_vm_pt_entries_mask(adev, cursor.level);
0919 pe_start = ((cursor.pfn >> shift) & mask) * 8;
0920 entry_end = ((uint64_t)mask + 1) << shift;
0921 entry_end += cursor.pfn & ~(entry_end - 1);
0922 entry_end = min(entry_end, end);
0923
0924 do {
0925 struct amdgpu_vm *vm = params->vm;
0926 uint64_t upd_end = min(entry_end, frag_end);
0927 unsigned int nptes = (upd_end - frag_start) >> shift;
0928 uint64_t upd_flags = flags | AMDGPU_PTE_FRAG(frag);
0929
0930
0931
0932
0933 nptes = max(nptes, 1u);
0934
0935 trace_amdgpu_vm_update_ptes(params, frag_start, upd_end,
0936 min(nptes, 32u), dst, incr,
0937 upd_flags,
0938 vm->task_info.pid,
0939 vm->immediate.fence_context);
0940 amdgpu_vm_pte_update_flags(params, to_amdgpu_bo_vm(pt),
0941 cursor.level, pe_start, dst,
0942 nptes, incr, upd_flags);
0943
0944 pe_start += nptes * 8;
0945 dst += nptes * incr;
0946
0947 frag_start = upd_end;
0948 if (frag_start >= frag_end) {
0949
0950 amdgpu_vm_pte_fragment(params, frag_start, end,
0951 flags, &frag, &frag_end);
0952 if (frag < shift)
0953 break;
0954 }
0955 } while (frag_start < entry_end);
0956
0957 if (amdgpu_vm_pt_descendant(adev, &cursor)) {
0958
0959
0960
0961
0962
0963
0964 while (cursor.pfn < frag_start) {
0965
0966 if (cursor.entry->bo) {
0967 params->table_freed = true;
0968 amdgpu_vm_pt_free_dfs(adev, params->vm,
0969 &cursor);
0970 }
0971 amdgpu_vm_pt_next(adev, &cursor);
0972 }
0973
0974 } else if (frag >= shift) {
0975
0976 amdgpu_vm_pt_next(adev, &cursor);
0977 }
0978 }
0979
0980 return 0;
0981 }