diff options
author | Stanislaw Halik <sthalik@misaki.pl> | 2024-01-12 05:20:08 +0100 |
---|---|---|
committer | Stanislaw Halik <sthalik@misaki.pl> | 2024-01-12 05:20:48 +0100 |
commit | 749753cefb36b72911d806b0c125eba43df3a1db (patch) | |
tree | 60972a7450eb5dcd55f9496fe644d2806f747f6b /serialize | |
parent | a504671200d27508636bfaea023f3a8dc3d19805 (diff) |
a
Diffstat (limited to 'serialize')
-rw-r--r-- | serialize/world-impl.hpp | 10 | ||||
-rw-r--r-- | serialize/world-reader.cpp | 22 | ||||
-rw-r--r-- | serialize/world-writer.cpp | 16 |
3 files changed, 31 insertions, 17 deletions
diff --git a/serialize/world-impl.hpp b/serialize/world-impl.hpp index d4b2feaa..5efd9bbc 100644 --- a/serialize/world-impl.hpp +++ b/serialize/world-impl.hpp @@ -50,7 +50,7 @@ template<typename T> constexpr inline T int_max = std::numeric_limits<T>::max(); #define file_magic ".floormat.save" -constexpr inline proto_t proto_version = 18; +constexpr inline proto_t proto_version = 19; constexpr inline size_t atlas_name_max = 128; constexpr inline auto null_atlas = (atlasid)-1LL; @@ -70,10 +70,10 @@ constexpr inline auto highbits = (T(1) << N)-1 << sizeof(T)*8-N-off; template<size_t N, typename T = uint8_t> constexpr T lowbits = T((T{1} << N)-T{1}); -constexpr inline atlasid meta_short_scenery_bit_ = highbits<atlasid, 1, 0>; -constexpr inline atlasid meta_rotation_bits_ = highbits<atlasid, rotation_BITS, 1>; -constexpr inline atlasid scenery_id_flag_mask_ = meta_short_scenery_bit_ | meta_rotation_bits_; -constexpr inline atlasid scenery_id_max_ = int_max<atlasid> & ~scenery_id_flag_mask_; +constexpr inline uint8_t meta_short_scenery_bit = highbits<uint8_t, 1, 0>; +constexpr inline uint8_t meta_rotation_bits = highbits<uint8_t, rotation_BITS, 1>; +constexpr inline uint8_t scenery_id_flag_mask = meta_short_scenery_bit | meta_rotation_bits; +constexpr inline uint8_t scenery_id_max = int_max<uint8_t> & ~scenery_id_flag_mask; } // namespace diff --git a/serialize/world-reader.cpp b/serialize/world-reader.cpp index 324a0d19..6bfcaa47 100644 --- a/serialize/world-reader.cpp +++ b/serialize/world-reader.cpp @@ -20,6 +20,11 @@ namespace { using namespace floormat; using namespace floormat::Serialize; +constexpr inline atlasid meta_short_scenery_bit_ = highbits<atlasid, 1, 0>; +constexpr inline atlasid meta_rotation_bits_ = highbits<atlasid, rotation_BITS, 1>; +constexpr inline atlasid scenery_id_flag_mask_ = meta_short_scenery_bit_ | meta_rotation_bits_; +constexpr inline atlasid scenery_id_max_ = int_max<atlasid> & ~scenery_id_flag_mask_; + struct reader_state final { explicit reader_state(world& world) noexcept; void deserialize_world(ArrayView<const char> buf); @@ -330,9 +335,20 @@ void reader_state::read_chunks(reader_t& s) } case object_type::scenery: { atlasid id; id << s; - const bool exact = id & meta_short_scenery_bit_; - const auto r = rotation(id >> sizeof(id)*8-1-rotation_BITS & rotation_MASK); - id &= ~scenery_id_flag_mask_; + bool exact; + rotation r; + if (PROTO >= 19) [[likely]] + { + uint8_t bits; bits << s; + exact = bits & meta_short_scenery_bit; + r = rotation(bits >> sizeof(bits)*8-1-rotation_BITS & rotation_MASK); + } + else + { + exact = id & meta_short_scenery_bit_; + r = rotation(id >> sizeof(id)*8-1-rotation_BITS & rotation_MASK); + id &= ~scenery_id_flag_mask_; + } auto sc = lookup_scenery(id); sc.offset = offset; (void)sc.atlas->group(r); diff --git a/serialize/world-writer.cpp b/serialize/world-writer.cpp index 3d16505c..23381ab8 100644 --- a/serialize/world-writer.cpp +++ b/serialize/world-writer.cpp @@ -244,8 +244,8 @@ constexpr auto atlasbuf_size1 = sizeof(uint8_t) + atlasbuf_size0*int_max<uint8_t void writer_state::serialize_scenery_names() { - fm_assert(scenery_map_size < scenery_id_max_); const size_t sz = scenery_map_size; + fm_assert(sz == (atlasid)sz); std::vector<interned_scenery> vec; vec.reserve(scenery_map_size); for (const auto& x : scenery_map) for (const auto& s : x.second) @@ -269,7 +269,6 @@ void writer_state::serialize_scenery_names() auto s = binary_writer{scenery_buf.begin()}; s << uint16_t{scenery_magic}; - fm_assert(sz < scenery_id_max_); s << (atlasid)sz; StringView last; @@ -358,7 +357,7 @@ void writer_state::serialize_scenery(const chunk& c, writer_t& s) const auto sc_exact = C.bbox_offset.isZero() && C.bbox_size == def_char_bbox_size; - id |= meta_short_scenery_bit_ * sc_exact; + id |= meta_short_scenery_bit * sc_exact; id |= static_cast<decltype(id)>(C.r) << sizeof(id)*8-1-rotation_BITS; s << id; write_object_flags(s, C); @@ -384,12 +383,11 @@ void writer_state::serialize_scenery(const chunk& c, writer_t& s) sc.interactive == ss->interactive && sc.delta == 0 && sc.frame == ss->frame; fm_assert(img_s != null_atlas); - atlasid id = img_s; - static_assert(rotation_BITS == 3); - fm_assert(id == (id & lowbits<16-3-1, atlasid>)); - id |= meta_short_scenery_bit_ * sc_exact; - id |= static_cast<decltype(id)>(sc.r) << sizeof(id)*8-1-rotation_BITS; - s << id; + s << img_s; + uint8_t bits = 0; + bits |= meta_short_scenery_bit * sc_exact; + bits |= std::to_underlying(sc.r) << sizeof(bits)*8-1-rotation_BITS; + s << bits; if (!sc_exact) { write_object_flags(s, sc); |