@@ -97,7 +97,7 @@ struct Vk {
9797 Arc<Physical_Device, Alloc> physical_device;
9898 Arc<Device, Alloc> device;
9999 Arc<Device_Memory, Alloc> host_memory;
100- Arc<Device_Memory, Alloc> device_memory ;
100+ Vec< Arc<Device_Memory, Alloc>, Alloc> device_memories ;
101101 Arc<Swapchain, Alloc> swapchain;
102102 Arc<Descriptor_Pool, Alloc> descriptor_pool;
103103 Arc<Command_Pool_Manager<Queue_Family::graphics>, Alloc> graphics_command_pool;
@@ -165,9 +165,16 @@ Vk::Vk(Config config) {
165165 host_memory = Arc<Device_Memory, Alloc>::make (physical_device, device.dup (), Heap::host,
166166 config.host_heap );
167167
168- device_memory = Arc<Device_Memory, Alloc>::make (physical_device, device.dup (), Heap::device,
169- device->heap_size (Heap::device) -
170- config.device_heap_margin );
168+ {
169+ u64 allocated = 0 ;
170+ u64 target = device->heap_size (Heap::device) - config.device_heap_margin ;
171+ while (allocated < target) {
172+ u64 size = Math::min (target - allocated, physical_device->max_allocation ());
173+ device_memories.push (
174+ Arc<Device_Memory, Alloc>::make (physical_device, device.dup (), Heap::device, size));
175+ allocated += size;
176+ }
177+ }
171178
172179 descriptor_pool = Arc<Descriptor_Pool, Alloc>::make (device.dup (), config.descriptors_per_type ,
173180 config.ray_tracing );
@@ -219,8 +226,8 @@ void Vk::imgui() {
219226 Text (" Swapchain images: %u | Max frames: %u" , swapchain->slot_count (), state.frames_in_flight );
220227 Text (" Extent: %ux%u" , swapchain->extent ().width , swapchain->extent ().height );
221228
222- if (TreeNodeEx (" Device Heap " , ImGuiTreeNodeFlags_DefaultOpen)) {
223- device_memory->imgui ();
229+ if (TreeNodeEx (" Device Heaps " , ImGuiTreeNodeFlags_DefaultOpen)) {
230+ for ( auto & device_memory : device_memories) device_memory->imgui ();
224231 TreePop ();
225232 }
226233 if (TreeNodeEx (" Host Heap" , ImGuiTreeNodeFlags_DefaultOpen)) {
@@ -438,11 +445,21 @@ Semaphore Vk::make_semaphore() {
438445}
439446
440447Opt<TLAS::Staged> Vk::make_tlas (Buffer instances, u32 n_instances) {
441- return TLAS::make (device_memory.dup (), move (instances), n_instances);
448+ for (auto & device_memory : device_memories) {
449+ if (auto tlas = TLAS::make (device_memory.dup (), move (instances), n_instances); tlas.ok ()) {
450+ return tlas;
451+ }
452+ }
453+ return {};
442454}
443455
444456Opt<BLAS::Staged> Vk::make_blas (Buffer geometry, Vec<BLAS::Offsets, Alloc> offsets) {
445- return BLAS::make (device_memory.dup (), move (geometry), move (offsets));
457+ for (auto & device_memory : device_memories) {
458+ if (auto blas = BLAS::make (device_memory.dup (), move (geometry), move (offsets)); blas.ok ()) {
459+ return blas;
460+ }
461+ }
462+ return {};
446463}
447464
448465Pipeline Vk::make_pipeline (Pipeline::Info info) {
@@ -557,11 +574,21 @@ Opt<Buffer> make_staging(u64 size) {
557574}
558575
559576Opt<Buffer> make_buffer (u64 size, VkBufferUsageFlags usage) {
560- return impl::singleton->device_memory ->make (size, usage);
577+ for (auto & device_memory : impl::singleton->device_memories ) {
578+ if (auto buf = device_memory->make (size, usage); buf.ok ()) {
579+ return buf;
580+ }
581+ }
582+ return {};
561583}
562584
563585Opt<Image> make_image (VkExtent3D extent, VkFormat format, VkImageUsageFlags usage) {
564- return impl::singleton->device_memory ->make (extent, format, usage);
586+ for (auto & device_memory : impl::singleton->device_memories ) {
587+ if (auto img = device_memory->make (extent, format, usage); img.ok ()) {
588+ return img;
589+ }
590+ }
591+ return {};
565592}
566593
567594Opt<TLAS::Staged> make_tlas (Buffer instances, u32 n_instances) {
0 commit comments