Created
July 11, 2022 07:27
-
-
Save superhawk610/748a221404cddabb3b19065170a172a7 to your computer and use it in GitHub Desktop.
dtolnay/unsafe-libyaml Example Usage
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
use std::mem::MaybeUninit; | |
use unsafe_libyaml::*; | |
fn main() { | |
unsafe { | |
let input = "foo: bar\nbaz: garply\n"; | |
let mut parser: MaybeUninit<yaml_parser_t> = MaybeUninit::uninit(); | |
let mut ev: MaybeUninit<yaml_event_t> = MaybeUninit::uninit(); | |
check_err("[init]", yaml_parser_initialize(parser.as_mut_ptr())); | |
let mut parser = parser.assume_init(); | |
yaml_parser_set_input_string(&mut parser, input.as_bytes().as_ptr(), input.len() as u64); | |
// let mut doc: MaybeUninit<yaml_document_t> = MaybeUninit::uninit(); | |
// check_err("[load]", yaml_parser_load(&mut parser, doc.as_mut_ptr())); | |
// let _doc = doc.assume_init(); | |
let mut done = false; | |
while !done { | |
if yaml_parser_parse(&mut parser, ev.as_mut_ptr()) == 0 { | |
let ev = ev.assume_init(); | |
panic!("parsing failed: {:#?}", ev.to_event()); | |
} | |
let mut ev = ev.assume_init(); | |
// process the event | |
dbg!(ev.to_event()); | |
done = matches!(ev.type_, yaml_event_type_t::YAML_STREAM_END_EVENT); | |
yaml_event_delete(&mut ev); | |
} | |
yaml_parser_delete(&mut parser); | |
} | |
} | |
struct Event<'a>(&'a yaml_event_t); | |
trait ToEvent { | |
fn to_event(&self) -> Event<'_>; | |
} | |
impl ToEvent for yaml_event_t { | |
fn to_event(&self) -> Event<'_> { | |
Event(self) | |
} | |
} | |
impl<'a> std::fmt::Debug for Event<'a> { | |
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { | |
use yaml_event_type_t::*; | |
match self.0.type_ { | |
YAML_NO_EVENT => write!(f, "YAML_NO_EVENT"), | |
YAML_STREAM_START_EVENT => write!(f, "YAML_STREAM_START_EVENT"), | |
YAML_STREAM_END_EVENT => write!(f, "YAML_STREAM_END_EVENT"), | |
YAML_DOCUMENT_START_EVENT => write!(f, "YAML_DOCUMENT_START_EVENT"), | |
YAML_DOCUMENT_END_EVENT => write!(f, "YAML_DOCUMENT_END_EVENT"), | |
YAML_ALIAS_EVENT => write!(f, "YAML_ALIAS_EVENT"), | |
YAML_SCALAR_EVENT => f | |
.debug_struct("Event") | |
.field("type_", &"YAML_SCALAR_EVENT") | |
.field("value", &unsafe { | |
std::str::from_utf8_unchecked(std::slice::from_raw_parts( | |
self.0.data.scalar.value, | |
self.0.data.scalar.length as _, | |
)) | |
}) | |
.finish(), | |
YAML_SEQUENCE_START_EVENT => write!(f, "YAML_SEQUENCE_START_EVENT"), | |
YAML_SEQUENCE_END_EVENT => write!(f, "YAML_SEQUENCE_END_EVENT"), | |
YAML_MAPPING_START_EVENT => write!(f, "YAML_MAPPING_START_EVENT"), | |
YAML_MAPPING_END_EVENT => write!(f, "YAML_MAPPING_END_EVENT"), | |
_ => write!(f, "UNKNOWN {}", self.0.type_ as u32), | |
} | |
} | |
} | |
fn check_err(reason: &str, maybe_err: i32) { | |
if maybe_err == 0 { | |
panic!("{}", reason); | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
This roughly follows the example given by LibYAML.