OLD | NEW |
---|---|
1 /* | 1 /* |
2 * Copyright 2015 Google Inc. | 2 * Copyright 2015 Google Inc. |
3 * | 3 * |
4 * Use of this source code is governed by a BSD-style license that can be | 4 * Use of this source code is governed by a BSD-style license that can be |
5 * found in the LICENSE file. | 5 * found in the LICENSE file. |
6 */ | 6 */ |
7 | 7 |
8 #include "GrVkMemory.h" | 8 #include "GrVkMemory.h" |
9 | 9 |
10 #include "GrVkGpu.h" | 10 #include "GrVkGpu.h" |
(...skipping 422 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
433 #endif | 433 #endif |
434 } | 434 } |
435 | 435 |
436 GrVkHeap::~GrVkHeap() { | 436 GrVkHeap::~GrVkHeap() { |
437 } | 437 } |
438 | 438 |
439 bool GrVkHeap::subAlloc(VkDeviceSize size, VkDeviceSize alignment, | 439 bool GrVkHeap::subAlloc(VkDeviceSize size, VkDeviceSize alignment, |
440 uint32_t memoryTypeIndex, GrVkAlloc* alloc) { | 440 uint32_t memoryTypeIndex, GrVkAlloc* alloc) { |
441 VkDeviceSize alignedSize = align_size(size, alignment); | 441 VkDeviceSize alignedSize = align_size(size, alignment); |
442 | 442 |
443 // if requested is larger than our subheap allocation, just alloc directly | |
444 if (alignedSize > fSubHeapSize) { | |
445 VkMemoryAllocateInfo allocInfo = { | |
446 VK_STRUCTURE_TYPE_MEMORY_ALLOCATE_INFO, // sType | |
447 NULL, // pNext | |
448 size, // allocationSize | |
449 memoryTypeIndex, // memoryTypeIndex | |
450 }; | |
451 | |
452 VkResult err = GR_VK_CALL(fGpu->vkInterface(), AllocateMemory(fGpu->devi ce(), | |
453 &allocInfo , | |
454 nullptr, | |
455 &alloc->fM emory)); | |
456 if (VK_SUCCESS != err) { | |
457 return false; | |
458 } | |
459 alloc->fOffset = 0; | |
460 alloc->fSize = 0; // hint that this is not a subheap allocation | |
461 | |
462 return true; | |
463 } | |
464 | |
443 // first try to find a subheap that fits our allocation request | 465 // first try to find a subheap that fits our allocation request |
444 int bestFitIndex = -1; | 466 int bestFitIndex = -1; |
445 VkDeviceSize bestFitSize = 0x7FFFFFFF; | 467 VkDeviceSize bestFitSize = 0x7FFFFFFF; |
446 for (auto i = 0; i < fSubHeaps.count(); ++i) { | 468 for (auto i = 0; i < fSubHeaps.count(); ++i) { |
447 if (fSubHeaps[i]->memoryTypeIndex() == memoryTypeIndex) { | 469 if (fSubHeaps[i]->memoryTypeIndex() == memoryTypeIndex) { |
448 VkDeviceSize heapSize = fSubHeaps[i]->largestBlockSize(); | 470 VkDeviceSize heapSize = fSubHeaps[i]->largestBlockSize(); |
449 if (heapSize >= alignedSize && heapSize < bestFitSize) { | 471 if (heapSize >= alignedSize && heapSize < bestFitSize) { |
450 bestFitIndex = i; | 472 bestFitIndex = i; |
451 bestFitSize = heapSize; | 473 bestFitSize = heapSize; |
452 } | 474 } |
453 } | 475 } |
454 } | 476 } |
455 | 477 |
456 if (bestFitIndex >= 0) { | 478 if (bestFitIndex >= 0) { |
457 SkASSERT(fSubHeaps[bestFitIndex]->alignment() == alignment); | 479 SkASSERT(fSubHeaps[bestFitIndex]->alignment() == alignment); |
458 if (fSubHeaps[bestFitIndex]->alloc(size, alloc)) { | 480 if (fSubHeaps[bestFitIndex]->alloc(size, alloc)) { |
459 fUsedSize += alloc->fSize; | 481 fUsedSize += alloc->fSize; |
460 return true; | 482 return true; |
461 } | 483 } |
462 return false; | 484 return false; |
463 } | 485 } |
464 | 486 |
465 // need to allocate a new subheap | 487 // need to allocate a new subheap |
466 SkAutoTDelete<GrVkSubHeap>& subHeap = fSubHeaps.push_back(); | 488 SkAutoTDelete<GrVkSubHeap>& subHeap = fSubHeaps.push_back(); |
467 subHeap.reset(new GrVkSubHeap(fGpu, memoryTypeIndex, fSubHeapSize, alignment )); | 489 subHeap.reset(new GrVkSubHeap(fGpu, memoryTypeIndex, fSubHeapSize, alignment )); |
490 // try to recover from failed allocation by only allocating what we need | |
491 if (subHeap->size() == 0) { | |
492 VkDeviceSize alignedSize = align_size(size, alignment); | |
493 subHeap.reset(new GrVkSubHeap(fGpu, memoryTypeIndex, alignedSize, alignm ent)); | |
494 if (subHeap->size() == 0) { | |
495 return false; | |
496 } | |
497 } | |
468 fAllocSize += fSubHeapSize; | 498 fAllocSize += fSubHeapSize; |
469 if (subHeap->alloc(size, alloc)) { | 499 if (subHeap->alloc(size, alloc)) { |
470 fUsedSize += alloc->fSize; | 500 fUsedSize += alloc->fSize; |
471 return true; | 501 return true; |
472 } | 502 } |
473 | 503 |
474 return false; | 504 return false; |
475 } | 505 } |
476 | 506 |
477 bool GrVkHeap::singleAlloc(VkDeviceSize size, VkDeviceSize alignment, | 507 bool GrVkHeap::singleAlloc(VkDeviceSize size, VkDeviceSize alignment, |
(...skipping 28 matching lines...) Expand all Loading... | |
506 fAllocSize += alignedSize; | 536 fAllocSize += alignedSize; |
507 if (subHeap->alloc(size, alloc)) { | 537 if (subHeap->alloc(size, alloc)) { |
508 fUsedSize += alloc->fSize; | 538 fUsedSize += alloc->fSize; |
509 return true; | 539 return true; |
510 } | 540 } |
511 | 541 |
512 return false; | 542 return false; |
513 } | 543 } |
514 | 544 |
515 bool GrVkHeap::free(const GrVkAlloc& alloc) { | 545 bool GrVkHeap::free(const GrVkAlloc& alloc) { |
546 // a size of 0 means we're using the system heap | |
547 if (0 == alloc.fSize) { | |
egdaniel
2016/06/16 18:55:23
How does this affect the SingleAlloc guys? Once we
jvanverth1
2016/06/16 20:26:53
Anything that is in a GrVkSubHeap, whether it's su
| |
548 const GrVkInterface* iface = fGpu->vkInterface(); | |
549 GR_VK_CALL(iface, FreeMemory(fGpu->device(), alloc.fMemory, nullptr)); | |
550 return true; | |
551 } | |
552 | |
516 for (auto i = 0; i < fSubHeaps.count(); ++i) { | 553 for (auto i = 0; i < fSubHeaps.count(); ++i) { |
517 if (fSubHeaps[i]->memory() == alloc.fMemory) { | 554 if (fSubHeaps[i]->memory() == alloc.fMemory) { |
518 fSubHeaps[i]->free(alloc); | 555 fSubHeaps[i]->free(alloc); |
519 fUsedSize -= alloc.fSize; | 556 fUsedSize -= alloc.fSize; |
520 return true; | 557 return true; |
521 } | 558 } |
522 } | 559 } |
523 | 560 |
524 return false; | 561 return false; |
525 } | 562 } |
526 | 563 |
527 | 564 |
OLD | NEW |