aboutsummaryrefslogtreecommitdiff
path: root/common/object/src/buffer.rs
diff options
context:
space:
mode:
authormetamuffin <metamuffin@disroot.org>2026-01-06 14:56:20 +0100
committermetamuffin <metamuffin@disroot.org>2026-01-06 14:56:20 +0100
commitffbdb9ce397a6408d5a91cbdcbaf4e13b0c3ba0b (patch)
treee84bb53bb2cb3f55617c9e44b5f07cbd964aa404 /common/object/src/buffer.rs
parentc04f49adaa2cb0fa3074d6b122d1e11689c4f5de (diff)
downloadjellything-ffbdb9ce397a6408d5a91cbdcbaf4e13b0c3ba0b.tar
jellything-ffbdb9ce397a6408d5a91cbdcbaf4e13b0c3ba0b.tar.bz2
jellything-ffbdb9ce397a6408d5a91cbdcbaf4e13b0c3ba0b.tar.zst
Multi fields; object buffer constructor; unit tests
Diffstat (limited to 'common/object/src/buffer.rs')
-rw-r--r--common/object/src/buffer.rs50
1 files changed, 50 insertions, 0 deletions
diff --git a/common/object/src/buffer.rs b/common/object/src/buffer.rs
new file mode 100644
index 0000000..56b8caf
--- /dev/null
+++ b/common/object/src/buffer.rs
@@ -0,0 +1,50 @@
+/*
+ This file is part of jellything (https://codeberg.org/metamuffin/jellything)
+ which is licensed under the GNU Affero General Public License (version 3); see /COPYING.
+ Copyright (C) 2026 metamuffin <metamuffin.org>
+*/
+
+use crate::{Object, Tag, ValueStore};
+
+pub struct ObjectBuffer(pub Vec<u32>);
+
+impl ObjectBuffer {
+ pub fn empty() -> Self {
+ Self(vec![0])
+ }
+ pub fn as_object<'a>(&'a self) -> Object<'a> {
+ Object::load(&self.0).unwrap()
+ }
+ pub fn new(fields: &mut [(Tag, &dyn ValueStore)]) -> ObjectBuffer {
+ let mut tags = Vec::new();
+ let mut offsets = Vec::new();
+ let mut values = Vec::new();
+ fields.sort_by_key(|(t, _)| t.0);
+ let mut temp = Vec::new();
+ for (tag, val) in fields {
+ tags.push(tag.0);
+ if val.is_aligned() {
+ offsets.push((values.len() as u32) << 2);
+ val.store_aligned(&mut values);
+ } else {
+ temp.clear();
+ val.store_unaligned(&mut temp);
+ let mut pad = 0;
+ while temp.len() % 4 != 0 {
+ pad += 1;
+ temp.push(0);
+ }
+ offsets.push(((values.len() as u32) << 2) | pad);
+ values.extend(bytemuck::cast_slice(&temp)); // ok bc. temp length is a whole number of dwords
+ }
+ }
+ ObjectBuffer(
+ [tags.len() as u32]
+ .into_iter()
+ .chain(tags)
+ .chain(offsets)
+ .chain(values)
+ .collect(),
+ )
+ }
+}