bvh/builder.cpp
| Line | Branch | Exec | Source |
|---|---|---|---|
| 1 | // SPDX-License-Identifier: BSD-3-Clause | ||
| 2 | #include "chrono_batch_render/bvh/builder.h" | ||
| 3 | |||
| 4 | #include <memory> | ||
| 5 | #include <utility> | ||
| 6 | #include <vector> | ||
| 7 | |||
| 8 | #include "chrono_batch_render/bvh/common.h" | ||
| 9 | #include "chrono_batch_render/device/device.h" | ||
| 10 | #include "chrono_batch_render/device/queue.h" | ||
| 11 | #include "chrono_batch_render/util/error.h" | ||
| 12 | #include "chrono_batch_render/util/log.h" | ||
| 13 | |||
| 14 | namespace chrono::batch_render::bvh { | ||
| 15 | |||
| 16 | using device::Device; | ||
| 17 | using device::Traversal; | ||
| 18 | |||
| 19 | 313 | Tlas::Tlas(Traversal format, std::span<const uint32_t> capacities) | |
| 20 | 313 | : m_format(format), m_capacities(capacities.begin(), capacities.end()) { | |
| 21 | 313 | if (capacities.empty()) { | |
| 22 | 2 | throw Error("CreateTlas of no worlds; a TLAS has at least one"); | |
| 23 | } | ||
| 24 | 624 | Log(LogLevel::Debug, "created a {} TLAS of {} worlds holding up to {} instances", | |
| 25 | 312 | FormatName(format), capacities.size(), Total(capacities)); | |
| 26 | 314 | } | |
| 27 | |||
| 28 | 920 | uint64_t Tlas::Handle(uint32_t world) const { | |
| 29 | 920 | if (world >= Count()) { | |
| 30 | 1 | throw Error("World {} of a TLAS of {} worlds", world, Count()); | |
| 31 | } | ||
| 32 | 919 | return m_handles[world]; | |
| 33 | } | ||
| 34 | |||
| 35 | 312 | void Tlas::SetHandles(Device& device, std::vector<uint64_t> handles) { | |
| 36 | 312 | m_handles = std::move(handles); | |
| 37 | 624 | m_table = device.CreateBuffer( | |
| 38 | 312 | {.bytes = m_handles.size() * sizeof(uint64_t), .label = "tlas handles"}); | |
| 39 | 624 | device.GetQueue().Write(*m_table, m_handles.data()); | |
| 40 | 624 | } | |
| 41 | |||
| 42 | 158 | void Builder::SubmitRefit(device::CommandEncoder&& encoder, Tlas& tlas, | |
| 43 | device::BufferRange instances, std::optional<device::BufferRange> counts, | ||
| 44 | std::span<const uint32_t> worlds) { | ||
| 45 | 158 | Refit(encoder, tlas, instances, counts, worlds); | |
| 46 | 158 | m_device.GetQueue().Submit(encoder.Finish()); | |
| 47 | 158 | } | |
| 48 | |||
| 49 | 415 | std::unique_ptr<Builder> Builder::Create(Device& device, Traversal format) { | |
| 50 | 415 | if (format == Traversal::Auto) { | |
| 51 | 398 | format = device.GetTraversal(); | |
| 52 | } | ||
| 53 | 415 | if (format == Traversal::Hardware && device.GetTraversal() != Traversal::Hardware) { | |
| 54 | 1 | throw UnsupportedError("Builder of hardware acceleration structures on {}, which " | |
| 55 | "traverses rays in software", | ||
| 56 | 1 | device.Adapter().alias); | |
| 57 | } | ||
| 58 | 414 | Log(LogLevel::Debug, "created a {} BVH builder for {}", FormatName(format), | |
| 59 | 414 | device.Adapter().alias); | |
| 60 | 414 | if (format == Traversal::Hardware) { | |
| 61 | ✗ | return CreateHardwareBuilder(device); | |
| 62 | } | ||
| 63 | 414 | return CreateSoftwareBuilder(device); | |
| 64 | } | ||
| 65 | |||
| 66 | } | ||
| 67 |