diff options
Diffstat (limited to 'users/tazjin/german-string/src/lib.rs')
-rw-r--r-- | users/tazjin/german-string/src/lib.rs | 31 |
1 files changed, 29 insertions, 2 deletions
diff --git a/users/tazjin/german-string/src/lib.rs b/users/tazjin/german-string/src/lib.rs index 05e43ed103ad..5cc8aebaab96 100644 --- a/users/tazjin/german-string/src/lib.rs +++ b/users/tazjin/german-string/src/lib.rs @@ -122,11 +122,11 @@ impl GermanString { s.data[..bytes.len()].copy_from_slice(&bytes); GermanString(GSRepr { small: s }) } else { - let mut md = std::mem::ManuallyDrop::new(bytes); + let md = std::mem::ManuallyDrop::new(bytes); let mut large = GSLarge { len: md.len() as u32, prefix: [0u8; 4], - data: StorageClassPtr::transient(md.as_mut_ptr()), + data: StorageClassPtr::transient(md.as_ptr()), }; large.prefix.copy_from_slice(&md[..4]); @@ -160,6 +160,33 @@ impl GermanString { } } + /// Creates a persistent German String by leaking the provided data. + pub fn persistent_leak(bytes: Vec<u8>) -> GermanString { + if bytes.len() > u32::MAX as usize { + panic!("GermanString maximum length is {} bytes", u32::MAX); + } + + if bytes.len() <= 12 { + let mut s = GSSmall { + len: bytes.len() as u32, + data: [0u8; 12], + }; + + s.data[..bytes.len()].copy_from_slice(&bytes); + GermanString(GSRepr { small: s }) + } else { + let md = std::mem::ManuallyDrop::new(bytes); + let mut large = GSLarge { + len: md.len() as u32, + prefix: [0u8; 4], + data: StorageClassPtr::persistent(md.as_ptr()), + }; + + large.prefix.copy_from_slice(&md[..4]); + GermanString(GSRepr { large }) + } + } + /// Creates a persistent German String from a static data buffer. pub fn persistent_from_str(s: &'static str) -> GermanString { GermanString::persistent(s.as_bytes()) |