1 /* 2 * Copyright 2008 Advanced Micro Devices, Inc. 3 * Copyright 2008 Red Hat Inc. 4 * Copyright 2009 Jerome Glisse. 5 * 6 * Permission is hereby granted, free of charge, to any person obtaining a 7 * copy of this software and associated documentation files (the "Software"), 8 * to deal in the Software without restriction, including without limitation 9 * the rights to use, copy, modify, merge, publish, distribute, sublicense, 10 * and/or sell copies of the Software, and to permit persons to whom the 11 * Software is furnished to do so, subject to the following conditions: 12 * 13 * The above copyright notice and this permission notice shall be included in 14 * all copies or substantial portions of the Software. 15 * 16 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 19 * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR 20 * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, 21 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR 22 * OTHER DEALINGS IN THE SOFTWARE. 23 * 24 * Authors: Dave Airlie 25 * Alex Deucher 26 * Jerome Glisse 27 */ 28 #include <linux/ktime.h> 29 #include <linux/pagemap.h> 30 #include <drm/drmP.h> 31 #include <drm/amdgpu_drm.h> 32 #include "amdgpu.h" 33 34 void amdgpu_gem_object_free(struct drm_gem_object *gobj) 35 { 36 struct amdgpu_bo *robj = gem_to_amdgpu_bo(gobj); 37 38 if (robj) { 39 if (robj->gem_base.import_attach) 40 drm_prime_gem_destroy(&robj->gem_base, robj->tbo.sg); 41 amdgpu_mn_unregister(robj); 42 amdgpu_bo_unref(&robj); 43 } 44 } 45 46 int amdgpu_gem_object_create(struct amdgpu_device *adev, unsigned long size, 47 int alignment, u32 initial_domain, 48 u64 flags, bool kernel, 49 struct reservation_object *resv, 50 struct drm_gem_object **obj) 51 { 52 struct amdgpu_bo *bo; 53 int r; 54 55 *obj = NULL; 56 /* At least align on page size */ 57 if (alignment < PAGE_SIZE) { 58 alignment = PAGE_SIZE; 59 } 60 61 retry: 62 r = amdgpu_bo_create(adev, size, alignment, kernel, initial_domain, 63 flags, NULL, resv, 0, &bo); 64 if (r) { 65 if (r != -ERESTARTSYS) { 66 if (flags & AMDGPU_GEM_CREATE_CPU_ACCESS_REQUIRED) { 67 flags &= ~AMDGPU_GEM_CREATE_CPU_ACCESS_REQUIRED; 68 goto retry; 69 } 70 71 if (initial_domain == AMDGPU_GEM_DOMAIN_VRAM) { 72 initial_domain |= AMDGPU_GEM_DOMAIN_GTT; 73 goto retry; 74 } 75 DRM_ERROR("Failed to allocate GEM object (%ld, %d, %u, %d)\n", 76 size, initial_domain, alignment, r); 77 } 78 return r; 79 } 80 *obj = &bo->gem_base; 81 82 return 0; 83 } 84 85 void amdgpu_gem_force_release(struct amdgpu_device *adev) 86 { 87 struct drm_device *ddev = adev->ddev; 88 struct drm_file *file; 89 90 mutex_lock(&ddev->filelist_mutex); 91 92 list_for_each_entry(file, &ddev->filelist, lhead) { 93 struct drm_gem_object *gobj; 94 int handle; 95 96 WARN_ONCE(1, "Still active user space clients!\n"); 97 spin_lock(&file->table_lock); 98 idr_for_each_entry(&file->object_idr, gobj, handle) { 99 WARN_ONCE(1, "And also active allocations!\n"); 100 drm_gem_object_put_unlocked(gobj); 101 } 102 idr_destroy(&file->object_idr); 103 spin_unlock(&file->table_lock); 104 } 105 106 mutex_unlock(&ddev->filelist_mutex); 107 } 108 109 /* 110 * Call from drm_gem_handle_create which appear in both new and open ioctl 111 * case. 112 */ 113 int amdgpu_gem_object_open(struct drm_gem_object *obj, 114 struct drm_file *file_priv) 115 { 116 struct amdgpu_bo *abo = gem_to_amdgpu_bo(obj); 117 struct amdgpu_device *adev = amdgpu_ttm_adev(abo->tbo.bdev); 118 struct amdgpu_fpriv *fpriv = file_priv->driver_priv; 119 struct amdgpu_vm *vm = &fpriv->vm; 120 struct amdgpu_bo_va *bo_va; 121 struct mm_struct *mm; 122 int r; 123 124 mm = amdgpu_ttm_tt_get_usermm(abo->tbo.ttm); 125 if (mm && mm != current->mm) 126 return -EPERM; 127 128 if (abo->flags & AMDGPU_GEM_CREATE_VM_ALWAYS_VALID && 129 abo->tbo.resv != vm->root.base.bo->tbo.resv) 130 return -EPERM; 131 132 r = amdgpu_bo_reserve(abo, false); 133 if (r) 134 return r; 135 136 bo_va = amdgpu_vm_bo_find(vm, abo); 137 if (!bo_va) { 138 bo_va = amdgpu_vm_bo_add(adev, vm, abo); 139 } else { 140 ++bo_va->ref_count; 141 } 142 amdgpu_bo_unreserve(abo); 143 return 0; 144 } 145 146 void amdgpu_gem_object_close(struct drm_gem_object *obj, 147 struct drm_file *file_priv) 148 { 149 struct amdgpu_bo *bo = gem_to_amdgpu_bo(obj); 150 struct amdgpu_device *adev = amdgpu_ttm_adev(bo->tbo.bdev); 151 struct amdgpu_fpriv *fpriv = file_priv->driver_priv; 152 struct amdgpu_vm *vm = &fpriv->vm; 153 154 struct amdgpu_bo_list_entry vm_pd; 155 struct list_head list, duplicates; 156 struct ttm_validate_buffer tv; 157 struct ww_acquire_ctx ticket; 158 struct amdgpu_bo_va *bo_va; 159 int r; 160 161 INIT_LIST_HEAD(&list); 162 INIT_LIST_HEAD(&duplicates); 163 164 tv.bo = &bo->tbo; 165 tv.shared = true; 166 list_add(&tv.head, &list); 167 168 amdgpu_vm_get_pd_bo(vm, &list, &vm_pd); 169 170 r = ttm_eu_reserve_buffers(&ticket, &list, false, &duplicates); 171 if (r) { 172 dev_err(adev->dev, "leaking bo va because " 173 "we fail to reserve bo (%d)\n", r); 174 return; 175 } 176 bo_va = amdgpu_vm_bo_find(vm, bo); 177 if (bo_va && --bo_va->ref_count == 0) { 178 amdgpu_vm_bo_rmv(adev, bo_va); 179 180 if (amdgpu_vm_ready(vm)) { 181 struct dma_fence *fence = NULL; 182 183 r = amdgpu_vm_clear_freed(adev, vm, &fence); 184 if (unlikely(r)) { 185 dev_err(adev->dev, "failed to clear page " 186 "tables on GEM object close (%d)\n", r); 187 } 188 189 if (fence) { 190 amdgpu_bo_fence(bo, fence, true); 191 dma_fence_put(fence); 192 } 193 } 194 } 195 ttm_eu_backoff_reservation(&ticket, &list); 196 } 197 198 /* 199 * GEM ioctls. 200 */ 201 int amdgpu_gem_create_ioctl(struct drm_device *dev, void *data, 202 struct drm_file *filp) 203 { 204 struct amdgpu_device *adev = dev->dev_private; 205 struct amdgpu_fpriv *fpriv = filp->driver_priv; 206 struct amdgpu_vm *vm = &fpriv->vm; 207 union drm_amdgpu_gem_create *args = data; 208 uint64_t flags = args->in.domain_flags; 209 uint64_t size = args->in.bo_size; 210 struct reservation_object *resv = NULL; 211 struct drm_gem_object *gobj; 212 uint32_t handle; 213 int r; 214 215 /* reject invalid gem flags */ 216 if (flags & ~(AMDGPU_GEM_CREATE_CPU_ACCESS_REQUIRED | 217 AMDGPU_GEM_CREATE_NO_CPU_ACCESS | 218 AMDGPU_GEM_CREATE_CPU_GTT_USWC | 219 AMDGPU_GEM_CREATE_VRAM_CLEARED | 220 AMDGPU_GEM_CREATE_VM_ALWAYS_VALID | 221 AMDGPU_GEM_CREATE_EXPLICIT_SYNC)) 222 223 return -EINVAL; 224 225 /* reject invalid gem domains */ 226 if (args->in.domains & ~(AMDGPU_GEM_DOMAIN_CPU | 227 AMDGPU_GEM_DOMAIN_GTT | 228 AMDGPU_GEM_DOMAIN_VRAM | 229 AMDGPU_GEM_DOMAIN_GDS | 230 AMDGPU_GEM_DOMAIN_GWS | 231 AMDGPU_GEM_DOMAIN_OA)) 232 return -EINVAL; 233 234 /* create a gem object to contain this object in */ 235 if (args->in.domains & (AMDGPU_GEM_DOMAIN_GDS | 236 AMDGPU_GEM_DOMAIN_GWS | AMDGPU_GEM_DOMAIN_OA)) { 237 flags |= AMDGPU_GEM_CREATE_NO_CPU_ACCESS; 238 if (args->in.domains == AMDGPU_GEM_DOMAIN_GDS) 239 size = size << AMDGPU_GDS_SHIFT; 240 else if (args->in.domains == AMDGPU_GEM_DOMAIN_GWS) 241 size = size << AMDGPU_GWS_SHIFT; 242 else if (args->in.domains == AMDGPU_GEM_DOMAIN_OA) 243 size = size << AMDGPU_OA_SHIFT; 244 else 245 return -EINVAL; 246 } 247 size = roundup(size, PAGE_SIZE); 248 249 if (flags & AMDGPU_GEM_CREATE_VM_ALWAYS_VALID) { 250 r = amdgpu_bo_reserve(vm->root.base.bo, false); 251 if (r) 252 return r; 253 254 resv = vm->root.base.bo->tbo.resv; 255 } 256 257 r = amdgpu_gem_object_create(adev, size, args->in.alignment, 258 (u32)(0xffffffff & args->in.domains), 259 flags, false, resv, &gobj); 260 if (flags & AMDGPU_GEM_CREATE_VM_ALWAYS_VALID) { 261 if (!r) { 262 struct amdgpu_bo *abo = gem_to_amdgpu_bo(gobj); 263 264 abo->parent = amdgpu_bo_ref(vm->root.base.bo); 265 } 266 amdgpu_bo_unreserve(vm->root.base.bo); 267 } 268 if (r) 269 return r; 270 271 r = drm_gem_handle_create(filp, gobj, &handle); 272 /* drop reference from allocate - handle holds it now */ 273 drm_gem_object_put_unlocked(gobj); 274 if (r) 275 return r; 276 277 memset(args, 0, sizeof(*args)); 278 args->out.handle = handle; 279 return 0; 280 } 281 282 int amdgpu_gem_userptr_ioctl(struct drm_device *dev, void *data, 283 struct drm_file *filp) 284 { 285 struct amdgpu_device *adev = dev->dev_private; 286 struct drm_amdgpu_gem_userptr *args = data; 287 struct drm_gem_object *gobj; 288 struct amdgpu_bo *bo; 289 uint32_t handle; 290 int r; 291 292 if (offset_in_page(args->addr | args->size)) 293 return -EINVAL; 294 295 /* reject unknown flag values */ 296 if (args->flags & ~(AMDGPU_GEM_USERPTR_READONLY | 297 AMDGPU_GEM_USERPTR_ANONONLY | AMDGPU_GEM_USERPTR_VALIDATE | 298 AMDGPU_GEM_USERPTR_REGISTER)) 299 return -EINVAL; 300 301 if (!(args->flags & AMDGPU_GEM_USERPTR_READONLY) && 302 !(args->flags & AMDGPU_GEM_USERPTR_REGISTER)) { 303 304 /* if we want to write to it we must install a MMU notifier */ 305 return -EACCES; 306 } 307 308 /* create a gem object to contain this object in */ 309 r = amdgpu_gem_object_create(adev, args->size, 0, AMDGPU_GEM_DOMAIN_CPU, 310 0, 0, NULL, &gobj); 311 if (r) 312 return r; 313 314 bo = gem_to_amdgpu_bo(gobj); 315 bo->preferred_domains = AMDGPU_GEM_DOMAIN_GTT; 316 bo->allowed_domains = AMDGPU_GEM_DOMAIN_GTT; 317 r = amdgpu_ttm_tt_set_userptr(bo->tbo.ttm, args->addr, args->flags); 318 if (r) 319 goto release_object; 320 321 if (args->flags & AMDGPU_GEM_USERPTR_REGISTER) { 322 r = amdgpu_mn_register(bo, args->addr); 323 if (r) 324 goto release_object; 325 } 326 327 if (args->flags & AMDGPU_GEM_USERPTR_VALIDATE) { 328 r = amdgpu_ttm_tt_get_user_pages(bo->tbo.ttm, 329 bo->tbo.ttm->pages); 330 if (r) 331 goto release_object; 332 333 r = amdgpu_bo_reserve(bo, true); 334 if (r) 335 goto free_pages; 336 337 amdgpu_ttm_placement_from_domain(bo, AMDGPU_GEM_DOMAIN_GTT); 338 r = ttm_bo_validate(&bo->tbo, &bo->placement, true, false); 339 amdgpu_bo_unreserve(bo); 340 if (r) 341 goto free_pages; 342 } 343 344 r = drm_gem_handle_create(filp, gobj, &handle); 345 /* drop reference from allocate - handle holds it now */ 346 drm_gem_object_put_unlocked(gobj); 347 if (r) 348 return r; 349 350 args->handle = handle; 351 return 0; 352 353 free_pages: 354 release_pages(bo->tbo.ttm->pages, bo->tbo.ttm->num_pages); 355 356 release_object: 357 drm_gem_object_put_unlocked(gobj); 358 359 return r; 360 } 361 362 int amdgpu_mode_dumb_mmap(struct drm_file *filp, 363 struct drm_device *dev, 364 uint32_t handle, uint64_t *offset_p) 365 { 366 struct drm_gem_object *gobj; 367 struct amdgpu_bo *robj; 368 369 gobj = drm_gem_object_lookup(filp, handle); 370 if (gobj == NULL) { 371 return -ENOENT; 372 } 373 robj = gem_to_amdgpu_bo(gobj); 374 if (amdgpu_ttm_tt_get_usermm(robj->tbo.ttm) || 375 (robj->flags & AMDGPU_GEM_CREATE_NO_CPU_ACCESS)) { 376 drm_gem_object_put_unlocked(gobj); 377 return -EPERM; 378 } 379 *offset_p = amdgpu_bo_mmap_offset(robj); 380 drm_gem_object_put_unlocked(gobj); 381 return 0; 382 } 383 384 int amdgpu_gem_mmap_ioctl(struct drm_device *dev, void *data, 385 struct drm_file *filp) 386 { 387 union drm_amdgpu_gem_mmap *args = data; 388 uint32_t handle = args->in.handle; 389 memset(args, 0, sizeof(*args)); 390 return amdgpu_mode_dumb_mmap(filp, dev, handle, &args->out.addr_ptr); 391 } 392 393 /** 394 * amdgpu_gem_timeout - calculate jiffies timeout from absolute value 395 * 396 * @timeout_ns: timeout in ns 397 * 398 * Calculate the timeout in jiffies from an absolute timeout in ns. 399 */ 400 unsigned long amdgpu_gem_timeout(uint64_t timeout_ns) 401 { 402 unsigned long timeout_jiffies; 403 ktime_t timeout; 404 405 /* clamp timeout if it's to large */ 406 if (((int64_t)timeout_ns) < 0) 407 return MAX_SCHEDULE_TIMEOUT; 408 409 timeout = ktime_sub(ns_to_ktime(timeout_ns), ktime_get()); 410 if (ktime_to_ns(timeout) < 0) 411 return 0; 412 413 timeout_jiffies = nsecs_to_jiffies(ktime_to_ns(timeout)); 414 /* clamp timeout to avoid unsigned-> signed overflow */ 415 if (timeout_jiffies > MAX_SCHEDULE_TIMEOUT ) 416 return MAX_SCHEDULE_TIMEOUT - 1; 417 418 return timeout_jiffies; 419 } 420 421 int amdgpu_gem_wait_idle_ioctl(struct drm_device *dev, void *data, 422 struct drm_file *filp) 423 { 424 union drm_amdgpu_gem_wait_idle *args = data; 425 struct drm_gem_object *gobj; 426 struct amdgpu_bo *robj; 427 uint32_t handle = args->in.handle; 428 unsigned long timeout = amdgpu_gem_timeout(args->in.timeout); 429 int r = 0; 430 long ret; 431 432 gobj = drm_gem_object_lookup(filp, handle); 433 if (gobj == NULL) { 434 return -ENOENT; 435 } 436 robj = gem_to_amdgpu_bo(gobj); 437 ret = reservation_object_wait_timeout_rcu(robj->tbo.resv, true, true, 438 timeout); 439 440 /* ret == 0 means not signaled, 441 * ret > 0 means signaled 442 * ret < 0 means interrupted before timeout 443 */ 444 if (ret >= 0) { 445 memset(args, 0, sizeof(*args)); 446 args->out.status = (ret == 0); 447 } else 448 r = ret; 449 450 drm_gem_object_put_unlocked(gobj); 451 return r; 452 } 453 454 int amdgpu_gem_metadata_ioctl(struct drm_device *dev, void *data, 455 struct drm_file *filp) 456 { 457 struct drm_amdgpu_gem_metadata *args = data; 458 struct drm_gem_object *gobj; 459 struct amdgpu_bo *robj; 460 int r = -1; 461 462 DRM_DEBUG("%d \n", args->handle); 463 gobj = drm_gem_object_lookup(filp, args->handle); 464 if (gobj == NULL) 465 return -ENOENT; 466 robj = gem_to_amdgpu_bo(gobj); 467 468 r = amdgpu_bo_reserve(robj, false); 469 if (unlikely(r != 0)) 470 goto out; 471 472 if (args->op == AMDGPU_GEM_METADATA_OP_GET_METADATA) { 473 amdgpu_bo_get_tiling_flags(robj, &args->data.tiling_info); 474 r = amdgpu_bo_get_metadata(robj, args->data.data, 475 sizeof(args->data.data), 476 &args->data.data_size_bytes, 477 &args->data.flags); 478 } else if (args->op == AMDGPU_GEM_METADATA_OP_SET_METADATA) { 479 if (args->data.data_size_bytes > sizeof(args->data.data)) { 480 r = -EINVAL; 481 goto unreserve; 482 } 483 r = amdgpu_bo_set_tiling_flags(robj, args->data.tiling_info); 484 if (!r) 485 r = amdgpu_bo_set_metadata(robj, args->data.data, 486 args->data.data_size_bytes, 487 args->data.flags); 488 } 489 490 unreserve: 491 amdgpu_bo_unreserve(robj); 492 out: 493 drm_gem_object_put_unlocked(gobj); 494 return r; 495 } 496 497 /** 498 * amdgpu_gem_va_update_vm -update the bo_va in its VM 499 * 500 * @adev: amdgpu_device pointer 501 * @vm: vm to update 502 * @bo_va: bo_va to update 503 * @list: validation list 504 * @operation: map, unmap or clear 505 * 506 * Update the bo_va directly after setting its address. Errors are not 507 * vital here, so they are not reported back to userspace. 508 */ 509 static void amdgpu_gem_va_update_vm(struct amdgpu_device *adev, 510 struct amdgpu_vm *vm, 511 struct amdgpu_bo_va *bo_va, 512 struct list_head *list, 513 uint32_t operation) 514 { 515 int r; 516 517 if (!amdgpu_vm_ready(vm)) 518 return; 519 520 r = amdgpu_vm_update_directories(adev, vm); 521 if (r) 522 goto error; 523 524 r = amdgpu_vm_clear_freed(adev, vm, NULL); 525 if (r) 526 goto error; 527 528 if (operation == AMDGPU_VA_OP_MAP || 529 operation == AMDGPU_VA_OP_REPLACE) 530 r = amdgpu_vm_bo_update(adev, bo_va, false); 531 532 error: 533 if (r && r != -ERESTARTSYS) 534 DRM_ERROR("Couldn't update BO_VA (%d)\n", r); 535 } 536 537 int amdgpu_gem_va_ioctl(struct drm_device *dev, void *data, 538 struct drm_file *filp) 539 { 540 const uint32_t valid_flags = AMDGPU_VM_DELAY_UPDATE | 541 AMDGPU_VM_PAGE_READABLE | AMDGPU_VM_PAGE_WRITEABLE | 542 AMDGPU_VM_PAGE_EXECUTABLE | AMDGPU_VM_MTYPE_MASK; 543 const uint32_t prt_flags = AMDGPU_VM_DELAY_UPDATE | 544 AMDGPU_VM_PAGE_PRT; 545 546 struct drm_amdgpu_gem_va *args = data; 547 struct drm_gem_object *gobj; 548 struct amdgpu_device *adev = dev->dev_private; 549 struct amdgpu_fpriv *fpriv = filp->driver_priv; 550 struct amdgpu_bo *abo; 551 struct amdgpu_bo_va *bo_va; 552 struct amdgpu_bo_list_entry vm_pd; 553 struct ttm_validate_buffer tv; 554 struct ww_acquire_ctx ticket; 555 struct list_head list, duplicates; 556 uint64_t va_flags; 557 int r = 0; 558 559 if (args->va_address < AMDGPU_VA_RESERVED_SIZE) { 560 dev_err(&dev->pdev->dev, 561 "va_address 0x%LX is in reserved area 0x%LX\n", 562 args->va_address, AMDGPU_VA_RESERVED_SIZE); 563 return -EINVAL; 564 } 565 566 if ((args->flags & ~valid_flags) && (args->flags & ~prt_flags)) { 567 dev_err(&dev->pdev->dev, "invalid flags combination 0x%08X\n", 568 args->flags); 569 return -EINVAL; 570 } 571 572 switch (args->operation) { 573 case AMDGPU_VA_OP_MAP: 574 case AMDGPU_VA_OP_UNMAP: 575 case AMDGPU_VA_OP_CLEAR: 576 case AMDGPU_VA_OP_REPLACE: 577 break; 578 default: 579 dev_err(&dev->pdev->dev, "unsupported operation %d\n", 580 args->operation); 581 return -EINVAL; 582 } 583 584 INIT_LIST_HEAD(&list); 585 INIT_LIST_HEAD(&duplicates); 586 if ((args->operation != AMDGPU_VA_OP_CLEAR) && 587 !(args->flags & AMDGPU_VM_PAGE_PRT)) { 588 gobj = drm_gem_object_lookup(filp, args->handle); 589 if (gobj == NULL) 590 return -ENOENT; 591 abo = gem_to_amdgpu_bo(gobj); 592 tv.bo = &abo->tbo; 593 tv.shared = false; 594 list_add(&tv.head, &list); 595 } else { 596 gobj = NULL; 597 abo = NULL; 598 } 599 600 amdgpu_vm_get_pd_bo(&fpriv->vm, &list, &vm_pd); 601 602 r = ttm_eu_reserve_buffers(&ticket, &list, true, &duplicates); 603 if (r) 604 goto error_unref; 605 606 if (abo) { 607 bo_va = amdgpu_vm_bo_find(&fpriv->vm, abo); 608 if (!bo_va) { 609 r = -ENOENT; 610 goto error_backoff; 611 } 612 } else if (args->operation != AMDGPU_VA_OP_CLEAR) { 613 bo_va = fpriv->prt_va; 614 } else { 615 bo_va = NULL; 616 } 617 618 switch (args->operation) { 619 case AMDGPU_VA_OP_MAP: 620 r = amdgpu_vm_alloc_pts(adev, bo_va->base.vm, args->va_address, 621 args->map_size); 622 if (r) 623 goto error_backoff; 624 625 va_flags = amdgpu_vm_get_pte_flags(adev, args->flags); 626 r = amdgpu_vm_bo_map(adev, bo_va, args->va_address, 627 args->offset_in_bo, args->map_size, 628 va_flags); 629 break; 630 case AMDGPU_VA_OP_UNMAP: 631 r = amdgpu_vm_bo_unmap(adev, bo_va, args->va_address); 632 break; 633 634 case AMDGPU_VA_OP_CLEAR: 635 r = amdgpu_vm_bo_clear_mappings(adev, &fpriv->vm, 636 args->va_address, 637 args->map_size); 638 break; 639 case AMDGPU_VA_OP_REPLACE: 640 r = amdgpu_vm_alloc_pts(adev, bo_va->base.vm, args->va_address, 641 args->map_size); 642 if (r) 643 goto error_backoff; 644 645 va_flags = amdgpu_vm_get_pte_flags(adev, args->flags); 646 r = amdgpu_vm_bo_replace_map(adev, bo_va, args->va_address, 647 args->offset_in_bo, args->map_size, 648 va_flags); 649 break; 650 default: 651 break; 652 } 653 if (!r && !(args->flags & AMDGPU_VM_DELAY_UPDATE) && !amdgpu_vm_debug) 654 amdgpu_gem_va_update_vm(adev, &fpriv->vm, bo_va, &list, 655 args->operation); 656 657 error_backoff: 658 ttm_eu_backoff_reservation(&ticket, &list); 659 660 error_unref: 661 drm_gem_object_put_unlocked(gobj); 662 return r; 663 } 664 665 int amdgpu_gem_op_ioctl(struct drm_device *dev, void *data, 666 struct drm_file *filp) 667 { 668 struct amdgpu_device *adev = dev->dev_private; 669 struct drm_amdgpu_gem_op *args = data; 670 struct drm_gem_object *gobj; 671 struct amdgpu_bo *robj; 672 int r; 673 674 gobj = drm_gem_object_lookup(filp, args->handle); 675 if (gobj == NULL) { 676 return -ENOENT; 677 } 678 robj = gem_to_amdgpu_bo(gobj); 679 680 r = amdgpu_bo_reserve(robj, false); 681 if (unlikely(r)) 682 goto out; 683 684 switch (args->op) { 685 case AMDGPU_GEM_OP_GET_GEM_CREATE_INFO: { 686 struct drm_amdgpu_gem_create_in info; 687 void __user *out = u64_to_user_ptr(args->value); 688 689 info.bo_size = robj->gem_base.size; 690 info.alignment = robj->tbo.mem.page_alignment << PAGE_SHIFT; 691 info.domains = robj->preferred_domains; 692 info.domain_flags = robj->flags; 693 amdgpu_bo_unreserve(robj); 694 if (copy_to_user(out, &info, sizeof(info))) 695 r = -EFAULT; 696 break; 697 } 698 case AMDGPU_GEM_OP_SET_PLACEMENT: 699 if (robj->prime_shared_count && (args->value & AMDGPU_GEM_DOMAIN_VRAM)) { 700 r = -EINVAL; 701 amdgpu_bo_unreserve(robj); 702 break; 703 } 704 if (amdgpu_ttm_tt_get_usermm(robj->tbo.ttm)) { 705 r = -EPERM; 706 amdgpu_bo_unreserve(robj); 707 break; 708 } 709 robj->preferred_domains = args->value & (AMDGPU_GEM_DOMAIN_VRAM | 710 AMDGPU_GEM_DOMAIN_GTT | 711 AMDGPU_GEM_DOMAIN_CPU); 712 robj->allowed_domains = robj->preferred_domains; 713 if (robj->allowed_domains == AMDGPU_GEM_DOMAIN_VRAM) 714 robj->allowed_domains |= AMDGPU_GEM_DOMAIN_GTT; 715 716 if (robj->flags & AMDGPU_GEM_CREATE_VM_ALWAYS_VALID) 717 amdgpu_vm_bo_invalidate(adev, robj, true); 718 719 amdgpu_bo_unreserve(robj); 720 break; 721 default: 722 amdgpu_bo_unreserve(robj); 723 r = -EINVAL; 724 } 725 726 out: 727 drm_gem_object_put_unlocked(gobj); 728 return r; 729 } 730 731 int amdgpu_mode_dumb_create(struct drm_file *file_priv, 732 struct drm_device *dev, 733 struct drm_mode_create_dumb *args) 734 { 735 struct amdgpu_device *adev = dev->dev_private; 736 struct drm_gem_object *gobj; 737 uint32_t handle; 738 int r; 739 740 args->pitch = amdgpu_align_pitch(adev, args->width, 741 DIV_ROUND_UP(args->bpp, 8), 0); 742 args->size = (u64)args->pitch * args->height; 743 args->size = ALIGN(args->size, PAGE_SIZE); 744 745 r = amdgpu_gem_object_create(adev, args->size, 0, 746 AMDGPU_GEM_DOMAIN_VRAM, 747 AMDGPU_GEM_CREATE_CPU_ACCESS_REQUIRED, 748 false, NULL, &gobj); 749 if (r) 750 return -ENOMEM; 751 752 r = drm_gem_handle_create(file_priv, gobj, &handle); 753 /* drop reference from allocate - handle holds it now */ 754 drm_gem_object_put_unlocked(gobj); 755 if (r) { 756 return r; 757 } 758 args->handle = handle; 759 return 0; 760 } 761 762 #if defined(CONFIG_DEBUG_FS) 763 static int amdgpu_debugfs_gem_bo_info(int id, void *ptr, void *data) 764 { 765 struct drm_gem_object *gobj = ptr; 766 struct amdgpu_bo *bo = gem_to_amdgpu_bo(gobj); 767 struct seq_file *m = data; 768 769 unsigned domain; 770 const char *placement; 771 unsigned pin_count; 772 uint64_t offset; 773 774 domain = amdgpu_mem_type_to_domain(bo->tbo.mem.mem_type); 775 switch (domain) { 776 case AMDGPU_GEM_DOMAIN_VRAM: 777 placement = "VRAM"; 778 break; 779 case AMDGPU_GEM_DOMAIN_GTT: 780 placement = " GTT"; 781 break; 782 case AMDGPU_GEM_DOMAIN_CPU: 783 default: 784 placement = " CPU"; 785 break; 786 } 787 seq_printf(m, "\t0x%08x: %12ld byte %s", 788 id, amdgpu_bo_size(bo), placement); 789 790 offset = READ_ONCE(bo->tbo.mem.start); 791 if (offset != AMDGPU_BO_INVALID_OFFSET) 792 seq_printf(m, " @ 0x%010Lx", offset); 793 794 pin_count = READ_ONCE(bo->pin_count); 795 if (pin_count) 796 seq_printf(m, " pin count %d", pin_count); 797 seq_printf(m, "\n"); 798 799 return 0; 800 } 801 802 static int amdgpu_debugfs_gem_info(struct seq_file *m, void *data) 803 { 804 struct drm_info_node *node = (struct drm_info_node *)m->private; 805 struct drm_device *dev = node->minor->dev; 806 struct drm_file *file; 807 int r; 808 809 r = mutex_lock_interruptible(&dev->filelist_mutex); 810 if (r) 811 return r; 812 813 list_for_each_entry(file, &dev->filelist, lhead) { 814 struct task_struct *task; 815 816 /* 817 * Although we have a valid reference on file->pid, that does 818 * not guarantee that the task_struct who called get_pid() is 819 * still alive (e.g. get_pid(current) => fork() => exit()). 820 * Therefore, we need to protect this ->comm access using RCU. 821 */ 822 rcu_read_lock(); 823 task = pid_task(file->pid, PIDTYPE_PID); 824 seq_printf(m, "pid %8d command %s:\n", pid_nr(file->pid), 825 task ? task->comm : "<unknown>"); 826 rcu_read_unlock(); 827 828 spin_lock(&file->table_lock); 829 idr_for_each(&file->object_idr, amdgpu_debugfs_gem_bo_info, m); 830 spin_unlock(&file->table_lock); 831 } 832 833 mutex_unlock(&dev->filelist_mutex); 834 return 0; 835 } 836 837 static const struct drm_info_list amdgpu_debugfs_gem_list[] = { 838 {"amdgpu_gem_info", &amdgpu_debugfs_gem_info, 0, NULL}, 839 }; 840 #endif 841 842 int amdgpu_gem_debugfs_init(struct amdgpu_device *adev) 843 { 844 #if defined(CONFIG_DEBUG_FS) 845 return amdgpu_debugfs_add_files(adev, amdgpu_debugfs_gem_list, 1); 846 #endif 847 return 0; 848 } 849