/rust/registry/src/index.crates.io-1949cf8c6b5b557f/flatbuffers-25.12.19/src/vtable_writer.rs
Line | Count | Source |
1 | | /* |
2 | | * Copyright 2018 Google Inc. All rights reserved. |
3 | | * |
4 | | * Licensed under the Apache License, Version 2.0 (the "License"); |
5 | | * you may not use this file except in compliance with the License. |
6 | | * You may obtain a copy of the License at |
7 | | * |
8 | | * http://www.apache.org/licenses/LICENSE-2.0 |
9 | | * |
10 | | * Unless required by applicable law or agreed to in writing, software |
11 | | * distributed under the License is distributed on an "AS IS" BASIS, |
12 | | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
13 | | * See the License for the specific language governing permissions and |
14 | | * limitations under the License. |
15 | | */ |
16 | | |
17 | | use core::ptr::write_bytes; |
18 | | |
19 | | use crate::endian_scalar::emplace_scalar; |
20 | | use crate::primitives::*; |
21 | | |
22 | | /// VTableWriter compartmentalizes actions needed to create a vtable. |
23 | | #[derive(Debug)] |
24 | | pub struct VTableWriter<'a> { |
25 | | buf: &'a mut [u8], |
26 | | } |
27 | | |
28 | | impl<'a> VTableWriter<'a> { |
29 | | #[inline(always)] |
30 | 0 | pub fn init(buf: &'a mut [u8]) -> Self { |
31 | 0 | VTableWriter { buf } |
32 | 0 | } |
33 | | |
34 | | /// Writes the vtable length (in bytes) into the vtable. |
35 | | /// |
36 | | /// Note that callers already need to have computed this to initialize |
37 | | /// a VTableWriter. |
38 | | /// |
39 | | /// In debug mode, asserts that the length of the underlying data is equal |
40 | | /// to the provided value. |
41 | | #[inline(always)] |
42 | 0 | pub fn write_vtable_byte_length(&mut self, n: VOffsetT) { |
43 | 0 | let buf = &mut self.buf[..SIZE_VOFFSET]; |
44 | | // Safety: |
45 | | // Validated range above |
46 | 0 | unsafe { |
47 | 0 | emplace_scalar::<VOffsetT>(buf, n); |
48 | 0 | } |
49 | 0 | debug_assert_eq!(n as usize, self.buf.len()); |
50 | 0 | } |
51 | | |
52 | | /// Writes an object length (in bytes) into the vtable. |
53 | | #[inline(always)] |
54 | 0 | pub fn write_object_inline_size(&mut self, n: VOffsetT) { |
55 | 0 | let buf = &mut self.buf[SIZE_VOFFSET..2 * SIZE_VOFFSET]; |
56 | | // Safety: |
57 | | // Validated range above |
58 | 0 | unsafe { |
59 | 0 | emplace_scalar::<VOffsetT>(buf, n); |
60 | 0 | } |
61 | 0 | } |
62 | | |
63 | | /// Writes an object field offset into the vtable. |
64 | | /// |
65 | | /// Note that this expects field offsets (which are like pointers), not |
66 | | /// field ids (which are like array indices). |
67 | | #[inline(always)] |
68 | 0 | pub fn write_field_offset(&mut self, vtable_offset: VOffsetT, object_data_offset: VOffsetT) { |
69 | 0 | let idx = vtable_offset as usize; |
70 | 0 | let buf = &mut self.buf[idx..idx + SIZE_VOFFSET]; |
71 | | // Safety: |
72 | | // Validated range above |
73 | 0 | unsafe { |
74 | 0 | emplace_scalar::<VOffsetT>(buf, object_data_offset); |
75 | 0 | } |
76 | 0 | } |
77 | | |
78 | | /// Clears all data in this VTableWriter. Used to cleanly undo a |
79 | | /// vtable write. |
80 | | #[inline(always)] |
81 | 0 | pub fn clear(&mut self) { |
82 | | // This is the closest thing to memset in Rust right now. |
83 | 0 | let len = self.buf.len(); |
84 | 0 | let p = self.buf.as_mut_ptr() as *mut u8; |
85 | | |
86 | | // Safety: |
87 | | // p is byte aligned and of length `len` |
88 | 0 | unsafe { |
89 | 0 | write_bytes(p, 0, len); |
90 | 0 | } |
91 | 0 | } |
92 | | } |