# Syntax File consists from 2 sections: - how to read the config (`config structure`) - how to serialize config (`serialization config`) `config structure` describes the structure of your config file. All definitions, procedures and arguents layout. `serialization config` describes the structurization of the read data. ## Syntax ```text '() - a list of items separated by the space. i.e '("test" "test2") ; - a single line comment. ;[comment here]; - a multiline commnet. 234u - (u) unsigned integer 2123 - without (u) signed integer. 0xFFAB - a hex representation of integer "" - a string symbol - symbol is a string without quotes with special chars #t #f - a boolean true and false i.e (test #t) () - a procedure i.e (test (another (test))) 3..6 - a non inclusive range from 3 to 5 incl 3u..6u - a non inclusive range unsigned rang1..range2 - a non inclusive range as symbols -3..=6 - an inclusive range from -3 to 6 incl. ``` ## Definitions `` - a variable with specific type and title of the variable. `(arg)` - argument of the procedure, strongly ordered. `(proc)` - a inner procedure which can be defined in procedure in orbitrary order. `(rootprocedure)` - a root of the config file i.e first iteration: ```scheme (abc "123" ; (...) ) (cde "1") ``` `(rootstruct)` - a root structure of the data i.e common structure: ```Rust struct MyMainStruct { //... } ``` `(struct)` - a definition of the structure. `(field)` - a field of the structure. `(enum)` - a definition of the enumerator. `(serializator)` - a separator of different serialized namespaces. `(verion)` - a version of the current script. ## Structure ```txt (version ) (serializator (use ) ... (define <[string;u64;i64]:data> :allowed_in_procs>) ... (define-enum `[string:enum_name]` `[vector:def_enum]` `[vector:allowed_in_procs]`) ... (procedure (arg <"string:path"> ) ... (proc "string:path" :procedues> (allow ) ) ... ) ... (struct (field ( ( ))) ) ) ; empty enum (enum (enumopt (empty) ) ) ; enum with named fields (structs) (enum (enumopt (struct (field ( ( ))) ) ) ) ) ; enum with anonymous fields (enum (enumopt (vec (field ( ( ))) ) ) ) (enumopt (vec (field ( ( ))) ) ) ) ) (rootprocedure (proc ) ) (rootstruct (field ( ( ))) ) ) ) ``` ### (serializator) Allowed inner procedures: - (rootstruct) - (rootprocedure) - (enum) - (struct) - (define) - (define-enum) - (use) - (procedure) ```scheme (serializator "test" (use ...) (use ...) (define ...) (define ...) (define-enum ...) (define-enum ...) (procedure ...) (procedure ...) (struct ...) (enum ...) (rootstruct ...) (rootstruct ...) ) ``` ### (procedure) Defines the procedure in config file and its contents. Structure: ```txt (procedure [string:title] ) where [string:title] - a label of the procedure which later will be used in config file. ``` Example: ```scheme (procedure "tcp" (arg "l_host_ip" string) (arg "l_host_port" uinteger) ) ``` ``` scheme ;; In this example, the above code will parse (tcp "127.0.0.1" 20000) ;; as: ;; "l_host_ip" -> "127.0.0.1" ;; "l_host_port" -> 20000 ``` ```scheme (procedure "tcp" (arg "l_host_ip" string) (arg "l_host_port" uinteger) ) (procedure "server" (arg "l_server_name" string) (proc "l_server_tcp" '("tcp")) ) ``` ```scheme ;; In this example, the above will parse: (server "local" (tcp "127.0.0.1" 2500) ) ;; as: ;; "l_server_name" -> local ;; "l_server_tcp" -> ;; "l_host_ip" -> 127.0.0.1 ;; "l_host_port" -> 2500 ``` ```scheme (procedure "tcp" (arg "l_host_ip" string) (arg "l_host_port" uinteger) ) (procedure "server" (arg "l_server_name" string) (proc "l_server_tcp" '("tcp")) ) (procedure "servers" (arg "l_servers_groupname" string) ;; allow the (server) to be optional and repeat (proc "l_servers_server" '("server") (allow '(optional collection))) ) ``` ```scheme ;; In this example the above will parse: ;; if no (server) is defined then don't throw the error ;; because it is optional (servers "group1") ;; as: ;; "servers" -> group1 ;; "l_servers_server" -> None ;; -- OR -- (servers "group1" (server "local" (tcp "127.0.0.1" 2500) ) ) ;; as: ;; "servers" -> group1 ;; "l_servers_server" -> ;; "server" -> ;; "l_server_name" -> local ;; "l_server_tcp" -> ;; "l_host_ip" -> 127.0.0.1 ;; "l_host_port" -> 2500 ;; -- OR -- ;; All (server) will be collected into the list (servers "group1" (server "local" (tcp "127.0.0.1" 2500) ) (server "ipx0" (tcp "192.168.0.1" 2501) ) (server "ipx0" (tcp "192.168.0.1" 2502) ) ) ;; as: ;; "servers" -> group1 ;; "l_servers_server" -> ;; "server" -> ;; "l_server_name" -> local ;; "l_server_tcp" -> ;; "l_host_ip" -> 127.0.0.1 ;; "l_host_port" -> 2500 ;; ;; "l_server_name" -> ipx0 ;; "l_server_tcp" -> ;; "l_host_ip" -> 192.168.0.1 ;; "l_host_port" -> 2501 ;; ;; "l_server_name" -> ipx0 ;; "l_server_tcp" -> ;; "l_host_ip" -> 192.168.0.1 ;; "l_host_port" -> 2502 ``` ### (procedure_empty) Special modificator which tells scheme that the procedure does not carry any data and it is empty. ```scheme ... (procedure "tcp" (procedure_empty) ) ... ``` ```scheme (tcp) ``` ### (arg) `arg` defines the argument in the `(procedure)`. The arguments are always collected in a strict order as it is defined in the scheme. It can not be optional or a collection. Data types: |Datatype|Subtype| Subsubtype |Annotation|Deserial type| Description| |------------|-------|------------|----------|----------|-----------| | string | none | none | "" | none | A basic string. Exit char \ for \ " | | uint | none | none | 0123456789u| byte, word, dword, qword | An uinteger number u64 | | int | none | none | +-0123456789| byte, word, dword, qword | An integer number i64 | | long-int | none | none | +-0123456789l | 128 bit | An integer number 128bit long| | long-uint | none | none | 0123456789lu | 128 bit | An integer number 128bit long| | boolean | none | none | 't 'f | none | A boolean | | entity | none | none | @ent | none | A `extension` - entity | | variable | none | none | $var | none | A `etension` - variable | | range | int | none | -2..3 | none | A range non inclusive | | range | uint | none | -2..3 | none | A range non inclusive | | range-inc | int | none | -2..=200 | none | A range inclusive | | range-inc | uint | none | 2u..=200u | none | A range inclusive | | symbol | none | none | symbol | none | A defined symbol | | vector | string | none | '("itm1" "itm2") | hashset, array | A list of strings | | vector | uint | none | '(1u 2u) | hashset, array | A list of uint | | vector | int | none | '(-1 2) | hashset, array | A list of int | | vector | long-uint | none | '(1lu 2lu) | hashset, array | A list of uint | | vector | long-int | none | '(-1l 2l) | hashset, array | A list of int | | vector | boolean | none | '('t 't 'f) | hashset, array | A list if boolean | | vector | symbol | none | '(symb1 symb2) | hashset, array | A list of symbols | | vector | entity | none | '(@ent1 @ent2) | hashset, array | A list of entitites | | vector | variable | none | '($var $var) | hashset, array | A list of variables | | vector | range | int | '(0..2 4..6) | array | A list of ranges | | vector | range | uint | '(0u..2u 4u..6u) | array | A list of ranges | | vector | range-inc | int | '(0..2 4..6) | array | A list of ranges | | vector | range-inc | uint | '(0u..2u 4u..6u) | array | A list of ranges | | vector | enumerator | none | '(EnumName::Item EnumName::Item2) | array | A list of enumerators. Enums must be same type!| | vector | auto-type | none | '("test" 4u 3 #t @ent) | array | A list of any primitive value | vector | vector | xxx | xxx | xxx | Not possible!| | enumerator | none | none | EnumName::Item | none | An enumerator for argument | | auto-type | none | none | "abc" or 4u or #t...| none | Any primitive lile int, uint, string, bool | **IMPORTANT!**: `auto-type` for uint or int only 8 bytes (u64, i64) long! Structure: > (arg `[label]` `[datatype]` `[modifiers]`) >> where: >> `[label]` a mandatory label which will be used during serialization step >> `[datatype]` a datatype to expect >> `[modifiers]` an additional modifiers ```scheme (arg "l_test" string) (arg "l_test2" integer) (arg "l_test3" vecotr string) (arg "l_test5" vector range int) ``` ### (arg-enum-bind) A `modifier` which is used in arg with datatype `enumerator`. This modifier allows not to specify namespace of the enumerator, for example, `MyEnum::Item1` which will become just `Item1` symbol. Structure: > (arg-enum-bind `[string:namespace_enum_name]`) >> where: >> `[string:namespace_enum_name]` - a `string` which sets the namespace label of the enum. **Example:** ```scheme (procedure "enumtest" (arg "enum_data" enumerator) (arg "enum_data_2" enumerator (arg-enum-bin "OurEnum")) ) ; for the following input (enumtest MyEnum::item1 item2) ; OurEnum::item2 ``` ### (proc) Defines the procedure which canbe used in the config. The order can be `arbitrary` when placed in config. Subprocs are: - (allowed) modifies the behaviour. Structure: > (proc `[string:label]` `[vector:procedure_names]` > ([`proc-allow`] ...) > ) >> where: >> `[string:label]` a mandatory label which will be used during serialization step >> `[vector:procedure_names]` a `(procedure)` list, can be more than one for enum ### (proc-allow) Structure: > (allow [vector:properties])) >> where: >> `[vector:properties]` a list of properties to grant Properties: - `optional` allows the procedure to be optional i.e to be defined in config only when it is needed - `collection` allows the procedure to be repeated i.e to be defined multiple tiles in config ```scheme (procedure "server" (arg "l_server_name" string) (proc "l_server_proto" '("tcp" "udp") (proc-allow '(collection optional)) ) ) ``` ## (use) Sets a path to `shmi` file. An `shmi` file an 'include' file which contains `procedures`/`structs`/`defines`. The content is attached to the serializator. See examples. Structure: > (use `[string:path_to_shmi_file]`) >> where: >> `[string:path_to_shmi_file]` - a full or partial path to the file without extension. A path depends on how the static scheme parser was initialized. If root path was provided then a relative (partial) path should be set. Else, full path from root dir should be set. ## (define) Defines a symbol which can be used in config. The `definition` use can be limited to specific `(procedure)`. Structure: > (define `[string:alias_title]` `[[string;u64;i64]:data]` `[vector:allowed_in_procs]`) >> where: >> `[string:alias_title]` an alias title which can be used in scheme >> `[[string;u64;i64]:data]` a data which is defined by the alias >> `[vector:allowed_in_procs]` a list of `(procedures)` where usage is allowed. >> If `empty` then allowed anywhere. ```scheme (define "sfx" 0u '("audio-channel")) (define "music" 1u '("audio-channel")) (define "voice" 2u '("audio-channel")) (define "all" "cfg:all" '()) ``` ## (define-enum) Defines a specific symbol (with namespace) which represents an enum item (without payload) which can be used in procedure's arguments. Structure: > (define-enum `[string:enum_name]` `[vector:def_enum]` `[vector:allowed_in_procs]`) >> where: >> `[string:enum_name]` an Enum structure name like pub struct MyEnum so -> "MyEnum" >> `[vector:def_enum]` an enum's items >> `[vector:allowed_in_procs]` a list of `(procedures)` where usage is allowed.>> If `empty` then allowed anywhere. In order to coply with Rust's naming conversions, the items of the enum i.e fields of the enum, the first letter of each is automatically uppercased. For example: ```scheme (define-enum "MyEnum" '("item1" "item2") '("enumtest")) ``` An `'("item1" "item2")` will be converted to the following format: ```Rust #[derive(Clone, Debug, Serialize, Deserialize)] pub enum MyEnum { Item1, Item2 } ``` And the dynamic scheme config file: ```scheme (enumtest MyEnum::item1) ``` Will be converted to: ```json {"enum1":"Item1"} ``` ## (struct) This item is related to serialization part which is not mandatory if it is not required to serialize / deserialize config. Defines a structure layout. This layout is used to serialize collected data. Structure is binded to specific `(procedure)`. Structure: >(struct `[string:struct_title]` `[[symbol(none);string;list:procedure_name]` > ... >) >> where: >> `[string:struct_title]` - a title of the struture which is used to generate Rust code. It should follow Rust's naming rules i.e `ScreenResolution`. >> `[[symbol(none);string;list:procedure_name]` - a title/s of `(procedure)` which are described by current instance of `(struct)` or symbol `none` if used in `enum` declaration. When procedures shares the same data strucuture, a one `(struct)` can be declared to describe struture of the data. ```scheme (procedure "resolution" ... ) (struct "ScreenResolution" "resolution" ... ) ; The above struct will be converted to rust code as: ; pub struct ScreenResolution ; { ; ... ; } ``` --or-- ```scheme (procedure "block" ... ) (procedure "unblock" ... ) (struct "ScreenResolution" '("block" "unblock") ... ) ; The above struct will be used to for both "block" and "unblock". ``` ## (field) Describes a field of the structure. Structure: ```txt (field [string:field_name] ; - MODIFICATORS (f/optional) ; optional modificator (sets field as optional) ; - DATA TYPE (f/struct [vector[string]:path_to_item]) ; -- OR (f/boolean [vector[string]:path_to_item]) ; -- OR (f/uint [vector[string]:path_to_item] (val/width [symbol:int_width]) ) ; -- OR (f/int [vector[string]:path_to_item] (val/width [symbol:int_width]) ) ; -- OR (f/string [vector[string]:path_to_item]) ; -- OR (f/enum [vector[string]:path_to_item]) ; -- OR (f/range [vector[string]:path_to_item]) ; -- OR (f/rangei [vector[string]:path_to_item]) ; -- OR (f/vector ; - SUB DATA TYPE (f/struct [vector[string]:path_to_item]) ; -- OR (f/boolean [vector[string]:path_to_item]) ; -- OR (f/uint [vector[string]:path_to_item] (val/width [symbol:int_width]) ) ; -- OR (f/int [vector[string]:path_to_item] (val/width [symbol:int_width]) ) ; -- OR (f/string [vector[string]:path_to_item]) ; -- OR (f/enum [vector[string]:path_to_item]) ; -- OR (f/argenum [vector[string]:path_to_item] [string:enum_title]) ; - VECTOR SPECIFIC MODIFICATOR (vector/type [symbol[array,hashset]:type]) ) ; -- OR (f/argenum [vector[string]:path_to_item] [string:enum_title]) ) where: [string:field_name] - a title of the field [vector[string]:path_to_item] - a path to the item which is constructed from labels. [symbol[array,hashset]:type] - a type of the collection deserialization. [symbol:int_width] - a width of the integer i.e 8, 16, 32, 64. See table below 'integer bitwidth' [string:enum_title] - a title of the enum defined in the `(define-enum)`. ``` Example: ```scheme (procedure "info" ; ... ) (struct "ScreenInfo" "info" ; ... ) ; ... (procedure "resolution" (arg "arg_res" string) (arg "arg_depth" uint) (proc "p_info" '(info) (allow '(optional))) ) (struct "ScreenResolution" "resolution" (field "sr_res" (f/string '("arg_res"))) (field "sr_depth" (f/uint '("arg_depth"))) (field "sr_info" (f/optional) (f/struct '("p_info"))) ) ; ... ; The above struct will be converted to rust code as: ; pub struct ScreenResolution ; { ; pub sr_res: String, ; pub sr_depth: u64, ; pub sr_info: Option, ; } ``` ### Integer bitwidth For the integer types it is possible to specify the exact width. If width is not specified the default is 8 bytes i.e 64 bits. |Symbol|Width|Bit length eqiv| |------|-----|---------------| |byte | 1u | 8 | |word | 2u | 16 | |dword | 4u | 32 | |qword | 8u | 64 | |oword | 16u | 128 | ## (val/width) Optional. The procedure `(val/width)` specifies the bitwidth of the `field` which is declared as `f/int` `f/uint`. In the body of the procedures `(f/int)` and `(f/uint)` after argument `path`, the procedure can be specified. The argument is a symbol from the table above or value from the second column. ```txt (val/width [symbol|uint:int_bitwidth]) where: [symbol|uint:int_bitwidth] - a symbol or uint value which specifies the bit width. The values are specified in the table above (1st and 2nd column). ``` Example: ```scheme (struct "Levels" "levels" (field "ch_a" (f/optional) (f/uint '("label1" "alpha_lvl") (val/width 4u) ) ) (field "ch_b" (f/int '("label2" "beta_lvl") (val/width word) ) ) ) ``` ```rust Generated Rust code: #[derive(Clone, Debug, Serialize, Deserialize)] pub struct Levels { pub ch_a: Option, pub ch_b: i16, } ``` **Important notice** The `(f/vector)` can generate vector either for `(arg)` declared as `vector` or `(proc)` collection which has struct defined. So, the following construction will work ```scheme (procedure "address" (arg "a_addr" string) ) (procedure "machine" (proc "p_address" '("address") (allow '(collection))) ) (struct "NetMachine" "machine" (field "nm_addrs" (f/vector (f/string '("p_address" "a_addr")))) ) ``` and will be serialized as: ```rust pub struct NetMachine { nm_addrs: Vec } ``` But, usually a `procedure` **address** requires a `struct` descritpion expecially if there are more than one `arg`. ```scheme (procedure "address" (arg "a_addr" string) ) (struct "NetAddr" "address" (field "net_addr" (f/string '("a_addr"))) ) (procedure "machine" (proc "p_address" '("address") (allow '(collection))) ) (struct "NetMachine" "machine" (field "nm_addrs" (f/vector (f/struct '("p_address")))) ) ``` ### (f/optional) Sets the field as optional. This means the data type of the field will be wrapped in `Option<>`. ### (vector/type) A specific, `optional` procedure only for the type `f/vector`. It controlls which type of the collection will used during conversion to the Rust code. There are two types: - hashset (HashSet) - array (Vec<>) Static arrays are not supported. Abstract example: ```scheme (struct "ScreenResolution" "resolution" (field "sr_res" (f/string '("arg_res"))) (field "sr_depth" (f/uint '("arg_depth"))) (field "sr_info" (f/optional) (f/vector (f/struct '("p_info")) (vector/type array) ) ) ) ``` ### Field data types The following data types are available: |f/type|rust|path endpoint| |------|----|-------------| |f/uint| u64|(arg)| |f/int| i64|(arg)| |f/uint-long| u128| (arg)| |f/int-long| i128| (arg)| |f/string| String|(arg)| |f/struct| [struct name]|(proc)| |f/enum| [enum name] |(proc)| |f/boolean| bool |(arg)| |f/range | Range<> |(arg)| |f/rangei | RangeInclusive<> |(arg)| |f/vector | Vec<> or HashSet<> |(arg) or (proc)| |f/argenum | pub enum [enum name] |(arg)| |f/any | ShmTypeAnyField |(arg)| Only specific `f/type` cab be applied to serialize the whole procedure or single argument. `f/vector` can be applied on both however it depends on the context. An `ShmTypeAnyField` is a constrant enum which has the following format: ```rust #[derive(Clone, Debug, Serialize, Deserialize)] pub enum ShmTypeAnyField { Int(i64), UInt(u64), Bool(bool), String(String) } ``` ## (enum) This item is related to serialization part which is not mandatory if it is not required to serialize / deserialize config. Defines an enumerator layout. This layout is used to serialize collected data. Enum is binded to one or many `(procedure)`. Procedures should be specified in `(proc)` section. ```txt (enum [string:enum title] [vector[string]:procedures] (comment "...") ; optional, single (enumopt ...) (enumopt ...) ) where: [string:enum title] - a title of the struture which is used to generate Rust code. It should follow Rust's naming rules i.e `GeomType`. [vector[string]:procedures] - a list of procedures that are serialized as enum. ``` Example: ```scheme (procedure "Test") (procedure "Ray" (arg "length" uint) (arg "width" uint) ) (procedure "Line" (arg "xpoint" int) (arg "ypoint" int) (arg "zpoint" int) ) (procedure "levels" (arg "title" string) (proc "label1" '("alpha") (allow '(optional))) (proc "label2" '("beta")) (proc "label3" '("Ray" "Line" "Test") (allow '(collection))) ) (enum "GeomType" '("Ray" "Line" "Test") (comment "") ;... ) ; The above enum will be constructed as: ; /// ;pub enum GeomType ;{ ; ... ;} ``` ### (enumopt) Defines an enumerator option for the specific enum instance. ```txt ; Empty struct (enumopt [string:procedure_name] [string:enum_alias] (comment [string:comment]) ; optional (empty) ; a const modificator ) where: [string:procedure_name] - a one `(procedure)` title which was declared in the `(enum)` proc. [string:enum_alias] - a rename of the enum option i.e (enumopt "alpha" "Alpha") so in rust enum it will be "enum {Alpha, ...}". (comment [string:comment]) - an option which allowes to generate comment above the item. (empty) - a procedure which indicates that it is empty. ``` ```txt ; An enum item with tuple (enumopt [string:procedure_name>] [string:enum_alias] (comment [string:comment]) ; optional (vec (field [const=anon:field_name] ; - MODIFICATORS (f/optional) ; optional modificator (sets field as optional) ; - DATA TYPE (f/struct [vector[string]:path_to_item]) ; -- OR (f/boolean [vector[string]:path_to_item]) ; -- OR (f/uint [vector[string]:path_to_item]) ; -- OR (f/int [vector[string]:path_to_item]) ; -- OR (f/string [vector[string]:path_to_item]) ; -- OR (f/enum [vector[string]:path_to_item]) ; -- OR (f/any [vector[string]:path_to_item]) ; -- OR (f/range [vector[string]:path_to_item]) ; -- OR (f/rangei [vector[string]:path_to_item]) ; -- OR (f/vector ; - SUB DATA TYPE (f/struct [vector[string]:path_to_item]) ; -- OR (f/boolean [vector[string]:path_to_item]) ; -- OR (f/uint [vector[string]:path_to_item]) ; -- OR (f/int [vector[string]:path_to_item]) ; -- OR (f/string [vector[string]:path_to_item]) ; -- OR (f/any [vector[string]:path_to_item]) ; -- OR (f/enum [vector[string]:path_to_item]) ; -- OR (f/argenum [vector[string]:path_to_item] [string:enum_title]) ; - VECTOR SPECIFIC MODIFICATOR (vector/type [symbol[array,hashset]:type]) ) ; -- OR (f/argenum [vector[string]:path_to_item] [string:enum_title]) ) ) ) where: [string:field_name] - a title of the field [vector[string]:path_to_item] - a path to the item which is constructed from labels. [symbol[array,hashset]:type] - a type of the collection deserialization. [string:enum_title] - a title of the enum defined in the `(define-enum)`. (comment [string:comment]) - an option which allowes to generate comment above the item. ``` ```txt ; An enum item with struct (enumopt [string:procedure_name] [string:enum_alias] (comment [string:comment]) ; optional (struct [const_symbol=none] [const_symbol=none] (field [string:field_name] ; - MODIFICATORS (f/optional) ; optional modificator (sets field as optional) ; - DATA TYPE (f/struct [vector[string]:path_to_item]) ; -- OR (f/boolean [vector[string]:path_to_item]) ; -- OR (f/uint [vector[string]:path_to_item]) ; -- OR (f/int [vector[string]:path_to_item]) ; -- OR (f/string [vector[string]:path_to_item]) ; -- OR (f/any [vector[string]:path_to_item]) ; -- OR (f/enum [vector[string]:path_to_item]) ; -- OR (f/vector ; - SUB DATA TYPE (f/struct [vector[string]:path_to_item]) ; -- OR (f/boolean [vector[string]:path_to_item]) ; -- OR (f/uint [vector[string]:path_to_item]) ; -- OR (f/int [vector[string]:path_to_item]) ; -- OR (f/string [vector[string]:path_to_item]) ; -- OR (f/any [vector[string]:path_to_item]) ; -- OR (f/enum [vector[string]:path_to_item]) ; -- OR (f/argenum [vector[string]:path_to_item] [string:enum_title]) ; - VECTOR SPECIFIC MODIFICATOR (vector/type [symbol[array,hashset]:type]) ) ; -- OR (f/argenum [vector[string]:path_to_item] [string:enum_title]) ) ) ) ) where: [string:field_name] - a title of the field [const_symbol=none] - a 'none' symbol [vector[string]:path_to_item] - a path to the item which is constructed from labels. [symbol[array,hashset]:type] - a type of the collection deserialization. [string:enum_title] - a title of the enum defined in the `(define-enum)`. (comment [string:comment]) - an option which allowes to generate comment above the item. ``` Example: ```scheme (enum "TestUseEnum" '("yellow" "red" "green" "color-rgb" "color-rgba-profile") (comment "An enumerator for the color spaces") (enumopt "yellow" "Yellow" (comment "A bind to yellow color") (empty) ) (enumopt "red" "Red" (empty) ) (enumopt "green" "Green" (empty) ) (enumopt "color-rgb" "ColorRgb" (vec (field anon (f/uint '("arg_r"))) (field anon (f/uint '("arg_g"))) (field anon (f/uint '("arg_b"))) ) ) (enumopt "color-rgba-profile" "ColorRgbaProfile" (struct none none (field "profile_name" (f/string '("arg_profile_name"))) (field "col_r" (f/uint '("p_color" "arg_r"))) (field "col_g" (f/uint '("p_color" "arg_g"))) (field "col_b" (f/uint '("p_color" "arg_b"))) (field "col_a" (f/uint '("arg_a"))) ) ) ) ``` ## (rootprocedure) and (rootstruct) Is a root of the document. The syntax is same as for `(procedure)` and `(struct)`. But in order to deserialize `(rootstruct)` into `rust enum`, a single field should be declared with the `anon` field name. Example: ```scheme (rootstruct "LdLogStructFormat" (field anon (f/enum '("l_root"))) ) ``` For example see: - examples/init_use1.shm - examples/init_use_dyn1.shm - examples/inituse1.rs