sim_lib_lang_clojure/
codec.rs1use std::sync::Arc;
2
3use sim_codec::{
4 CodecDefaultDecode, CodecRuntime, Decoder, Input, LocatedDecoder, ReadCx, TreeDecoder,
5 codec_value,
6};
7use sim_kernel::{
8 AbiVersion, CodecId, DefaultFactory, Dependency, Export, Lib, LibManifest, LibTarget, Linker,
9 LocatedExpr, LocatedExprTree, Result, Symbol, Version,
10};
11
12use crate::{clojure_edn_reader_symbol, decode_clojure_edn_tree};
13
14pub struct ClojureEdnCodec;
20
21impl Decoder for ClojureEdnCodec {
22 fn decode(&self, cx: &mut ReadCx<'_>, input: Input) -> Result<sim_kernel::Expr> {
23 decode_clojure_edn_tree(cx, "clojure-edn", input).map(|tree| tree.expr)
24 }
25}
26
27impl LocatedDecoder for ClojureEdnCodec {
28 fn decode_located(
29 &self,
30 cx: &mut ReadCx<'_>,
31 input: Input,
32 source_id: String,
33 ) -> Result<LocatedExpr> {
34 decode_clojure_edn_tree(cx, source_id, input).map(|tree| tree.located())
35 }
36}
37
38impl TreeDecoder for ClojureEdnCodec {
39 fn decode_tree(
40 &self,
41 cx: &mut ReadCx<'_>,
42 input: Input,
43 source_id: String,
44 ) -> Result<LocatedExprTree> {
45 decode_clojure_edn_tree(cx, source_id, input)
46 }
47}
48
49pub struct ClojureEdnCodecLib {
85 symbol: Symbol,
86 codec_id: CodecId,
87}
88
89impl ClojureEdnCodecLib {
90 pub fn new(id: CodecId) -> Self {
92 Self {
93 symbol: clojure_edn_reader_symbol(),
94 codec_id: id,
95 }
96 }
97}
98
99impl Lib for ClojureEdnCodecLib {
100 fn manifest(&self) -> LibManifest {
101 LibManifest {
102 id: self.symbol.clone(),
103 version: Version(env!("CARGO_PKG_VERSION").to_owned()),
104 abi: AbiVersion { major: 0, minor: 1 },
105 target: LibTarget::HostRegistered,
106 requires: Vec::<Dependency>::new(),
107 capabilities: Vec::new(),
108 exports: vec![Export::Codec {
109 symbol: self.symbol.clone(),
110 codec_id: Some(self.codec_id),
111 }],
112 }
113 }
114
115 fn load(&self, _cx: &mut sim_kernel::LoadCx, linker: &mut Linker<'_>) -> Result<()> {
116 let _factory = DefaultFactory;
117 let expr_shape = sim_codec::resolve_expr_shape(linker, &Symbol::qualified("core", "Expr"))?;
118 let options_shape = sim_codec::resolve_options_shape(linker)?;
119
120 linker.codec_value(
121 self.symbol.clone(),
122 codec_value(CodecRuntime {
123 id: self.codec_id,
124 symbol: self.symbol.clone(),
125 decoder: Some(Arc::new(ClojureEdnCodec)),
126 located_decoder: Some(Arc::new(ClojureEdnCodec)),
127 tree_decoder: Some(Arc::new(ClojureEdnCodec)),
128 encoder: None,
129 located_encoder: None,
130 tree_encoder: None,
131 expr_shape,
132 options_shape,
133 default_decode: CodecDefaultDecode::Datum,
134 }),
135 )?;
136 Ok(())
137 }
138}