[ox] Fix various preloader problems

This commit is contained in:
Gary Talent 2024-02-01 21:06:35 -06:00
parent 0626c2a815
commit e81d28a681
4 changed files with 36 additions and 17 deletions

View File

@ -760,7 +760,7 @@ constexpr std::size_t alignOf(const ModelValue &t) noexcept {
size = PlatSpec::alignOf(t.get<int64_t>());
break;
case ModelValue::Type::String:
size = PlatSpec::alignOf(t.get<ox::String>());
size = alignOf<PlatSpec>(t.get<ox::String>());
break;
case ModelValue::Type::Object:
size = alignOf<PlatSpec>(t.get<ox::ModelObject>());

View File

@ -9,6 +9,7 @@
#pragma once
#include <ox/std/serialize.hpp>
#include <ox/std/string.hpp>
#include <ox/std/typetraits.hpp>
#include "alignmentcatcher.hpp"

View File

@ -14,10 +14,12 @@
#include <ox/std/error.hpp>
#include <ox/std/memops.hpp>
#include <ox/std/memory.hpp>
#include <ox/std/string.hpp>
#include <ox/std/types.hpp>
#include <ox/std/typetraits.hpp>
#include <ox/std/units.hpp>
#include <ox/model/modelhandleradaptor.hpp>
#include <ox/model/modelvalue.hpp>
#include "platspecs.hpp"
@ -105,9 +107,9 @@ class Preloader: public ModelHandlerBase<Preloader<PlatSpec>, OpType::Reflect> {
template<typename T>
constexpr ox::Error field(CRStringView, const T **val, std::size_t cnt) noexcept;
constexpr ox::Result<std::size_t> startAlloc(std::size_t sz) noexcept;
constexpr ox::Result<std::size_t> startAlloc(size_t sz, size_t align) noexcept;
constexpr ox::Result<std::size_t> startAlloc(std::size_t sz, std::size_t restore) noexcept;
constexpr ox::Result<std::size_t> startAlloc(size_t sz, size_t align, std::size_t restore) noexcept;
constexpr ox::Error endAlloc() noexcept;
@ -169,14 +171,16 @@ constexpr ox::Error Preloader<PlatSpec>::field(CRStringView name, const T *val)
}
oxReturnError(pad(val));
if constexpr(ox::is_integral_v<T>) {
//oxDebugf("Preloader::field(name, val): {}", name);
return ox::serialize(&m_writer, PlatSpec::correctEndianness(*val));
} else if constexpr(ox::is_pointer_v<T>) {
const PtrType a = startAlloc(sizeOf<PlatSpec>(*val), m_writer.tellp()) + PlatSpec::RomStart;
const PtrType a = startAlloc(sizeOf<PlatSpec>(val), alignOf<PlatSpec>(*val), m_writer.tellp()) + PlatSpec::RomStart;
oxReturnError(field(name, *val));
oxReturnError(endAlloc());
return ox::serialize(&m_writer, PlatSpec::correctEndianness(a));
} else if constexpr(ox::isVector_v<T> || ox::is_same_v<T, ox::ModelValueVector>) {
} else if constexpr(ox::isVector_v<T>) {
return fieldVector(name, val);
} else if constexpr(ox::is_same_v<T, ox::ModelValueVector>) {
val->types();
return fieldVector(name, val);
} else {
m_unionIdx.emplace_back(-1);
@ -222,6 +226,7 @@ constexpr ox::Error Preloader<PlatSpec>::field(CRStringView name, const ox::Arra
if (!unionCheckAndIt()) {
return {};
}
oxReturnError(pad(&(*val)[0]));
// serialize the Array elements
if constexpr(sz) {
m_unionIdx.emplace_back(-1);
@ -239,27 +244,36 @@ constexpr ox::Error Preloader<PlatSpec>::field(CRStringView, const T **val, std:
if (!unionCheckAndIt()) {
return {};
}
if (cnt) {
oxReturnError(pad(*val));
// serialize the array
m_unionIdx.emplace_back(-1);
for (std::size_t i = 0; i < cnt; ++i) {
oxReturnError(this->interface()->field(nullptr, &val[i]));
}
m_unionIdx.pop_back();
}
return {};
}
template<typename PlatSpec>
constexpr ox::Result<std::size_t> Preloader<PlatSpec>::startAlloc(std::size_t sz) noexcept {
oxRequire(a, ox::allocate(&m_writer, sz));
constexpr ox::Result<std::size_t> Preloader<PlatSpec>::startAlloc(size_t sz, size_t align) noexcept {
m_allocStack.emplace_back(static_cast<typename PlatSpec::PtrType>(m_writer.tellp()));
oxReturnError(m_writer.seekp(0, ox::ios_base::end));
const auto padding = m_writer.tellp() % align;
oxRequireM(a, ox::allocate(&m_writer, sz + padding));
a += padding;
oxReturnError(m_writer.seekp(a));
return a;
}
template<typename PlatSpec>
constexpr ox::Result<std::size_t> Preloader<PlatSpec>::startAlloc(std::size_t sz, std::size_t restore) noexcept {
oxRequire(a, ox::allocate(&m_writer, sz));
constexpr ox::Result<std::size_t> Preloader<PlatSpec>::startAlloc(std::size_t sz, size_t align, std::size_t restore) noexcept {
m_allocStack.emplace_back(restore, ox::ios_base::beg);
oxReturnError(m_writer.seekp(0, ox::ios_base::end));
const auto padding = m_writer.tellp() % align;
oxRequireM(a, ox::allocate(&m_writer, sz + padding));
a += padding;
oxReturnError(m_writer.seekp(a));
return a;
}
@ -331,7 +345,11 @@ constexpr ox::Error Preloader<PlatSpec>::fieldVector(
// serialize the Vector elements
if (val->size()) {
const auto sz = sizeOf<PlatSpec>(&(*val)[0]) * val->size();
oxRequire(p, ox::allocate(&m_writer, sz));
const auto align = alignOf<PlatSpec>((*val)[0]);
oxReturnError(m_writer.seekp(0, ox::ios_base::end));
const auto padding = m_writer.tellp() % align;
oxRequireM(p, ox::allocate(&m_writer, sz + padding));
p += padding;
oxReturnError(m_writer.seekp(p));
m_unionIdx.emplace_back(-1);
for (std::size_t i = 0; i < val->size(); ++i) {

View File

@ -20,7 +20,7 @@ namespace ox {
template<OxString_c Str>
[[nodiscard]]
constexpr ox::StringView substr(Str const&str, std::size_t pos) noexcept {
constexpr Str substr(Str const&str, std::size_t pos) noexcept {
if (str.len() >= pos) {
return Str(str.data() + pos, str.len() - pos);
}