use crate::cesr::{code_b2_to_b64, int_to_b64, nab_sextets, Parsable, Versionage, VERSION};
use crate::errors::MatterError;
use num_bigint::BigUint;
use num_traits::ToPrimitive;
use once_cell::sync::Lazy;
use std::collections::HashMap;
use std::str;
#[allow(dead_code)]
pub mod gen_dex {
use once_cell::sync::Lazy;
use std::collections::HashMap;
pub const KERI_ACDC_SPAC: &str = "--AAA";
pub const KERI: &str = "--AAA";
pub const ACDC: &str = "--AAA";
pub const SPAC: &str = "--AAA";
pub static MAP: Lazy<HashMap<&'static str, &'static str>> = Lazy::new(|| {
let mut map = HashMap::new();
map.insert("KERI_ACDC_SPAC", KERI_ACDC_SPAC);
map.insert("KERI", KERI);
map.insert("ACDC", ACDC);
map.insert("SPAC", SPAC);
map
});
pub static TUPLE: [&'static str; 4] = [KERI_ACDC_SPAC, KERI, ACDC, SPAC];
}
#[allow(dead_code)]
pub mod ctr_dex_1_0 {
use once_cell::sync::Lazy;
use std::collections::HashMap;
pub const CONTROLLER_IDX_SIGS: &str = "-A"; pub const WITNESS_IDX_SIGS: &str = "-B"; pub const NON_TRANS_RECEIPT_COUPLES: &str = "-C"; pub const TRANS_RECEIPT_QUADRUPLES: &str = "-D"; pub const FIRST_SEEN_REPLAY_COUPLES: &str = "-E"; pub const TRANS_IDX_SIG_GROUPS: &str = "-F"; pub const SEAL_SOURCE_COUPLES: &str = "-G"; pub const TRANS_LAST_IDX_SIG_GROUPS: &str = "-H"; pub const SEAL_SOURCE_TRIPLES: &str = "-I"; pub const SAD_PATH_SIG_GROUPS: &str = "-J"; pub const ROOT_SAD_PATH_SIG_GROUPS: &str = "-K"; pub const PATHED_MATERIAL_GROUP: &str = "-L"; pub const BIG_PATHED_MATERIAL_GROUP: &str = "-0L"; pub const ATTACHMENT_GROUP: &str = "-V"; pub const BIG_ATTACHMENT_GROUP: &str = "-0V"; pub const ESSR_PAYLOAD_GROUP: &str = "-Z"; pub const KERI_ACDC_GENUS_VERSION: &str = "--AAA";
pub static TUPLE: Lazy<Vec<&'static str>> = Lazy::new(|| {
vec![
CONTROLLER_IDX_SIGS,
WITNESS_IDX_SIGS,
NON_TRANS_RECEIPT_COUPLES,
TRANS_RECEIPT_QUADRUPLES,
FIRST_SEEN_REPLAY_COUPLES,
TRANS_IDX_SIG_GROUPS,
SEAL_SOURCE_COUPLES,
TRANS_LAST_IDX_SIG_GROUPS,
SEAL_SOURCE_TRIPLES,
SAD_PATH_SIG_GROUPS,
ROOT_SAD_PATH_SIG_GROUPS,
PATHED_MATERIAL_GROUP,
BIG_PATHED_MATERIAL_GROUP,
ATTACHMENT_GROUP,
BIG_ATTACHMENT_GROUP,
ESSR_PAYLOAD_GROUP,
KERI_ACDC_GENUS_VERSION,
]
});
pub static MAP: Lazy<HashMap<&'static str, &'static str>> = Lazy::new(|| {
let mut map = HashMap::new();
map.insert(CONTROLLER_IDX_SIGS, "Controller Indexed Signatures");
map.insert(WITNESS_IDX_SIGS, "Witness Indexed Signatures");
map.insert(
NON_TRANS_RECEIPT_COUPLES,
"Non-Transferable Receipt Couples",
);
map.insert(TRANS_RECEIPT_QUADRUPLES, "Transferable Receipt Quadruples");
map.insert(FIRST_SEEN_REPLAY_COUPLES, "First Seen Replay Couples");
map.insert(
TRANS_IDX_SIG_GROUPS,
"Transferable Indexed Signature Groups",
);
map.insert(SEAL_SOURCE_COUPLES, "Seal Source Couples");
map.insert(
TRANS_LAST_IDX_SIG_GROUPS,
"Transferable Last Indexed Signature Groups",
);
map.insert(SEAL_SOURCE_TRIPLES, "Seal Source Triples");
map.insert(SAD_PATH_SIG_GROUPS, "SAD Path Signature Groups");
map.insert(ROOT_SAD_PATH_SIG_GROUPS, "Root SAD Path Signature Groups");
map.insert(PATHED_MATERIAL_GROUP, "Pathed Material Group");
map.insert(BIG_PATHED_MATERIAL_GROUP, "Big Pathed Material Group");
map.insert(ATTACHMENT_GROUP, "Attachment Group");
map.insert(BIG_ATTACHMENT_GROUP, "Big Attachment Group");
map.insert(ESSR_PAYLOAD_GROUP, "ESSR Payload Group");
map.insert(KERI_ACDC_GENUS_VERSION, "KERI ACDC Genus Version");
map
});
}
#[allow(dead_code)]
pub mod ctr_dex_2_0 {
use once_cell::sync::Lazy;
use std::collections::HashMap;
pub const GENERIC_GROUP: &str = "-A"; pub const BIG_GENERIC_GROUP: &str = "-0A"; pub const MESSAGE_GROUP: &str = "-B"; pub const BIG_MESSAGE_GROUP: &str = "-0B"; pub const ATTACHMENT_GROUP: &str = "-C"; pub const BIG_ATTACHMENT_GROUP: &str = "-0C"; pub const DATAGRAM_SEGMENT_GROUP: &str = "-D"; pub const BIG_DATAGRAM_SEGMENT_GROUP: &str = "-0D"; pub const ESSR_WRAPPER_GROUP: &str = "-E"; pub const BIG_ESSR_WRAPPER_GROUP: &str = "-0E"; pub const FIXED_MESSAGE_BODY_GROUP: &str = "-F"; pub const BIG_FIXED_MESSAGE_BODY_GROUP: &str = "-0F"; pub const MAP_MESSAGE_BODY_GROUP: &str = "-G"; pub const BIG_MAP_MESSAGE_BODY_GROUP: &str = "-0G"; pub const GENERIC_MAP_GROUP: &str = "-H"; pub const BIG_GENERIC_MAP_GROUP: &str = "-0H"; pub const GENERIC_LIST_GROUP: &str = "-I"; pub const BIG_GENERIC_LIST_GROUP: &str = "-0I"; pub const CONTROLLER_IDX_SIGS: &str = "-J"; pub const BIG_CONTROLLER_IDX_SIGS: &str = "-0J"; pub const WITNESS_IDX_SIGS: &str = "-K"; pub const BIG_WITNESS_IDX_SIGS: &str = "-0K"; pub const NON_TRANS_RECEIPT_COUPLES: &str = "-L"; pub const BIG_NON_TRANS_RECEIPT_COUPLES: &str = "-0L"; pub const TRANS_RECEIPT_QUADRUPLES: &str = "-M"; pub const BIG_TRANS_RECEIPT_QUADRUPLES: &str = "-0M"; pub const FIRST_SEEN_REPLAY_COUPLES: &str = "-N"; pub const BIG_FIRST_SEEN_REPLAY_COUPLES: &str = "-0N"; pub const TRANS_IDX_SIG_GROUPS: &str = "-O"; pub const BIG_TRANS_IDX_SIG_GROUPS: &str = "-0O"; pub const TRANS_LAST_IDX_SIG_GROUPS: &str = "-P"; pub const BIG_TRANS_LAST_IDX_SIG_GROUPS: &str = "-0P"; pub const SEAL_SOURCE_COUPLES: &str = "-Q"; pub const BIG_SEAL_SOURCE_COUPLES: &str = "-0Q"; pub const SEAL_SOURCE_TRIPLES: &str = "-R"; pub const BIG_SEAL_SOURCE_TRIPLES: &str = "-0R"; pub const PATHED_MATERIAL_GROUP: &str = "-S"; pub const BIG_PATHED_MATERIAL_GROUP: &str = "-0S"; pub const SAD_PATH_SIG_GROUPS: &str = "-T"; pub const BIG_SAD_PATH_SIG_GROUPS: &str = "-0T"; pub const ROOT_SAD_PATH_SIG_GROUPS: &str = "-U"; pub const BIG_ROOT_SAD_PATH_SIG_GROUPS: &str = "-0U"; pub const DIGEST_SEAL_SINGLES: &str = "-V"; pub const BIG_DIGEST_SEAL_SINGLES: &str = "-0V"; pub const MERKLE_ROOT_SEAL_SINGLES: &str = "-W"; pub const BIG_MERKLE_ROOT_SEAL_SINGLES: &str = "-0W"; pub const BACKER_REGISTRAR_SEAL_COUPLES: &str = "-X"; pub const BIG_BACKER_REGISTRAR_SEAL_COUPLES: &str = "-0X"; pub const SEAL_SOURCE_LAST_SINGLES: &str = "-Y"; pub const BIG_SEAL_SOURCE_LAST_SINGLES: &str = "-0Y"; pub const ESSR_PAYLOAD_GROUP: &str = "-Z"; pub const BIG_ESSR_PAYLOAD_GROUP: &str = "-0Z"; pub const KERI_ACDC_GENUS_VERSION: &str = "--AAA";
pub static TUPLE: Lazy<Vec<&'static str>> = Lazy::new(|| {
vec![
GENERIC_GROUP,
BIG_GENERIC_GROUP,
MESSAGE_GROUP,
BIG_MESSAGE_GROUP,
ATTACHMENT_GROUP,
BIG_ATTACHMENT_GROUP,
DATAGRAM_SEGMENT_GROUP,
BIG_DATAGRAM_SEGMENT_GROUP,
ESSR_WRAPPER_GROUP,
BIG_ESSR_WRAPPER_GROUP,
FIXED_MESSAGE_BODY_GROUP,
BIG_FIXED_MESSAGE_BODY_GROUP,
MAP_MESSAGE_BODY_GROUP,
BIG_MAP_MESSAGE_BODY_GROUP,
GENERIC_MAP_GROUP,
BIG_GENERIC_MAP_GROUP,
GENERIC_LIST_GROUP,
BIG_GENERIC_LIST_GROUP,
CONTROLLER_IDX_SIGS,
BIG_CONTROLLER_IDX_SIGS,
WITNESS_IDX_SIGS,
BIG_WITNESS_IDX_SIGS,
NON_TRANS_RECEIPT_COUPLES,
BIG_NON_TRANS_RECEIPT_COUPLES,
TRANS_RECEIPT_QUADRUPLES,
BIG_TRANS_RECEIPT_QUADRUPLES,
FIRST_SEEN_REPLAY_COUPLES,
BIG_FIRST_SEEN_REPLAY_COUPLES,
TRANS_IDX_SIG_GROUPS,
BIG_TRANS_IDX_SIG_GROUPS,
TRANS_LAST_IDX_SIG_GROUPS,
BIG_TRANS_LAST_IDX_SIG_GROUPS,
SEAL_SOURCE_COUPLES,
BIG_SEAL_SOURCE_COUPLES,
SEAL_SOURCE_TRIPLES,
BIG_SEAL_SOURCE_TRIPLES,
PATHED_MATERIAL_GROUP,
BIG_PATHED_MATERIAL_GROUP,
SAD_PATH_SIG_GROUPS,
BIG_SAD_PATH_SIG_GROUPS,
ROOT_SAD_PATH_SIG_GROUPS,
BIG_ROOT_SAD_PATH_SIG_GROUPS,
DIGEST_SEAL_SINGLES,
BIG_DIGEST_SEAL_SINGLES,
MERKLE_ROOT_SEAL_SINGLES,
BIG_MERKLE_ROOT_SEAL_SINGLES,
BACKER_REGISTRAR_SEAL_COUPLES,
BIG_BACKER_REGISTRAR_SEAL_COUPLES,
SEAL_SOURCE_LAST_SINGLES,
BIG_SEAL_SOURCE_LAST_SINGLES,
ESSR_PAYLOAD_GROUP,
BIG_ESSR_PAYLOAD_GROUP,
KERI_ACDC_GENUS_VERSION,
]
});
pub static MAP: Lazy<HashMap<&'static str, &'static str>> = Lazy::new(|| {
let mut map = HashMap::new();
map.insert(GENERIC_GROUP, "Generic Group");
map.insert(BIG_GENERIC_GROUP, "Big Generic Group");
map.insert(MESSAGE_GROUP, "Message Body plus Attachments Group");
map.insert(BIG_MESSAGE_GROUP, "Big Message Body plus Attachments Group");
map.insert(ATTACHMENT_GROUP, "Message Attachments Only Group");
map.insert(BIG_ATTACHMENT_GROUP, "Big Attachments Only Group");
map.insert(DATAGRAM_SEGMENT_GROUP, "Datagram Segment Group");
map.insert(BIG_DATAGRAM_SEGMENT_GROUP, "Big Datagram Segment Group");
map.insert(ESSR_WRAPPER_GROUP, "ESSR Wrapper Group");
map.insert(BIG_ESSR_WRAPPER_GROUP, "Big ESSR Wrapper Group");
map.insert(FIXED_MESSAGE_BODY_GROUP, "Fixed Field Message Body Group");
map.insert(
BIG_FIXED_MESSAGE_BODY_GROUP,
"Big Fixed Field Message Body Group",
);
map.insert(MAP_MESSAGE_BODY_GROUP, "Field Map Message Body Group");
map.insert(
BIG_MAP_MESSAGE_BODY_GROUP,
"Big Field Map Message Body Group",
);
map.insert(GENERIC_MAP_GROUP, "Generic Field Map Group");
map.insert(BIG_GENERIC_MAP_GROUP, "Big Generic Field Map Group");
map.insert(GENERIC_LIST_GROUP, "Generic List Group");
map.insert(BIG_GENERIC_LIST_GROUP, "Big Generic List Group");
map.insert(CONTROLLER_IDX_SIGS, "Controller Indexed Signatures");
map.insert(BIG_CONTROLLER_IDX_SIGS, "Big Controller Indexed Signatures");
map.insert(WITNESS_IDX_SIGS, "Witness Indexed Signatures");
map.insert(BIG_WITNESS_IDX_SIGS, "Big Witness Indexed Signatures");
map.insert(
NON_TRANS_RECEIPT_COUPLES,
"Non-Transferable Receipt Couples",
);
map.insert(
BIG_NON_TRANS_RECEIPT_COUPLES,
"Big Non-Transferable Receipt Couples",
);
map.insert(TRANS_RECEIPT_QUADRUPLES, "Transferable Receipt Quadruples");
map.insert(
BIG_TRANS_RECEIPT_QUADRUPLES,
"Big Transferable Receipt Quadruples",
);
map.insert(FIRST_SEEN_REPLAY_COUPLES, "First Seen Replay Couples");
map.insert(
BIG_FIRST_SEEN_REPLAY_COUPLES,
"Big First Seen Replay Couples",
);
map.insert(
TRANS_IDX_SIG_GROUPS,
"Transferable Indexed Signature Groups",
);
map.insert(
BIG_TRANS_IDX_SIG_GROUPS,
"Big Transferable Indexed Signature Groups",
);
map.insert(
TRANS_LAST_IDX_SIG_GROUPS,
"Transferable Last Indexed Signature Groups",
);
map.insert(
BIG_TRANS_LAST_IDX_SIG_GROUPS,
"Big Transferable Last Indexed Signature Groups",
);
map.insert(SEAL_SOURCE_COUPLES, "Seal Source Couples");
map.insert(BIG_SEAL_SOURCE_COUPLES, "Big Seal Source Couples");
map.insert(SEAL_SOURCE_TRIPLES, "Seal Source Triples");
map.insert(BIG_SEAL_SOURCE_TRIPLES, "Big Seal Source Triples");
map.insert(PATHED_MATERIAL_GROUP, "Pathed Material Group");
map.insert(BIG_PATHED_MATERIAL_GROUP, "Big Pathed Material Group");
map.insert(SAD_PATH_SIG_GROUPS, "SAD Path Signature Groups");
map.insert(BIG_SAD_PATH_SIG_GROUPS, "Big SAD Path Signature Groups");
map.insert(ROOT_SAD_PATH_SIG_GROUPS, "Root SAD Path Signature Groups");
map.insert(
BIG_ROOT_SAD_PATH_SIG_GROUPS,
"Big Root SAD Path Signature Groups",
);
map.insert(DIGEST_SEAL_SINGLES, "Digest Seal Singles");
map.insert(BIG_DIGEST_SEAL_SINGLES, "Big Digest Seal Singles");
map.insert(MERKLE_ROOT_SEAL_SINGLES, "Merkle Root Seal Singles");
map.insert(BIG_MERKLE_ROOT_SEAL_SINGLES, "Big Merkle Root Seal Singles");
map.insert(
BACKER_REGISTRAR_SEAL_COUPLES,
"Backer Registrar Seal Couples",
);
map.insert(
BIG_BACKER_REGISTRAR_SEAL_COUPLES,
"Big Backer Registrar Seal Couples",
);
map.insert(SEAL_SOURCE_LAST_SINGLES, "Seal Source Last Singles");
map.insert(BIG_SEAL_SOURCE_LAST_SINGLES, "Big Seal Source Last Singles");
map.insert(ESSR_PAYLOAD_GROUP, "ESSR Payload Group");
map.insert(BIG_ESSR_PAYLOAD_GROUP, "Big ESSR Payload Group");
map.insert(KERI_ACDC_GENUS_VERSION, "KERI ACDC Genus Version");
map
});
}
#[allow(dead_code)]
pub mod seal_dex_2_0 {
use once_cell::sync::Lazy;
use std::collections::HashMap;
pub const SEAL_SOURCE_COUPLES: &str = "-Q"; pub const BIG_SEAL_SOURCE_COUPLES: &str = "-0Q"; pub const SEAL_SOURCE_TRIPLES: &str = "-R"; pub const BIG_SEAL_SOURCE_TRIPLES: &str = "-0R"; pub const DIGEST_SEAL_SINGLES: &str = "-V"; pub const BIG_DIGEST_SEAL_SINGLES: &str = "-0V"; pub const MERKLE_ROOT_SEAL_SINGLES: &str = "-W"; pub const BIG_MERKLE_ROOT_SEAL_SINGLES: &str = "-0W"; pub const BACKER_REGISTRAR_SEAL_COUPLES: &str = "-X"; pub const BIG_BACKER_REGISTRAR_SEAL_COUPLES: &str = "-0X"; pub const SEAL_SOURCE_LAST_SINGLES: &str = "-Y"; pub const BIG_SEAL_SOURCE_LAST_SINGLES: &str = "-0Y";
pub static TUPLE: Lazy<Vec<&'static str>> = Lazy::new(|| {
vec![
SEAL_SOURCE_COUPLES,
BIG_SEAL_SOURCE_COUPLES,
SEAL_SOURCE_TRIPLES,
BIG_SEAL_SOURCE_TRIPLES,
DIGEST_SEAL_SINGLES,
BIG_DIGEST_SEAL_SINGLES,
MERKLE_ROOT_SEAL_SINGLES,
BIG_MERKLE_ROOT_SEAL_SINGLES,
BACKER_REGISTRAR_SEAL_COUPLES,
BIG_BACKER_REGISTRAR_SEAL_COUPLES,
SEAL_SOURCE_LAST_SINGLES,
BIG_SEAL_SOURCE_LAST_SINGLES,
]
});
pub static MAP: Lazy<HashMap<&'static str, &'static str>> = Lazy::new(|| {
let mut map = HashMap::new();
map.insert(SEAL_SOURCE_COUPLES, "Seal Source Couples");
map.insert(BIG_SEAL_SOURCE_COUPLES, "Big Seal Source Couples");
map.insert(SEAL_SOURCE_TRIPLES, "Seal Source Triples");
map.insert(BIG_SEAL_SOURCE_TRIPLES, "Big Seal Source Triples");
map.insert(DIGEST_SEAL_SINGLES, "Digest Seal Singles");
map.insert(BIG_DIGEST_SEAL_SINGLES, "Big Digest Seal Singles");
map.insert(MERKLE_ROOT_SEAL_SINGLES, "Merkle Root Seal Singles");
map.insert(BIG_MERKLE_ROOT_SEAL_SINGLES, "Big Merkle Root Seal Singles");
map.insert(
BACKER_REGISTRAR_SEAL_COUPLES,
"Backer Registrar Seal Couples",
);
map.insert(
BIG_BACKER_REGISTRAR_SEAL_COUPLES,
"Big Backer Registrar Seal Couples",
);
map.insert(SEAL_SOURCE_LAST_SINGLES, "Seal Source Last Singles");
map.insert(BIG_SEAL_SOURCE_LAST_SINGLES, "Big Seal Source Last Singles");
map
});
}
#[derive(Clone, Copy, Debug)]
pub struct Cizage {
pub hs: u32, pub ss: u32, pub fs: u32, }
pub fn get_sizes_1_0() -> HashMap<&'static str, Cizage> {
let mut sizes = HashMap::new();
sizes.insert(
"-A",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-B",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-C",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-D",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-E",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-F",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-G",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-H",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-I",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-J",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-K",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-L",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-0L",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-V",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-0V",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-Z",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"--AAA",
Cizage {
hs: 5,
ss: 3,
fs: 8,
},
);
sizes
}
pub fn get_sizes_2_0() -> HashMap<&'static str, Cizage> {
let mut sizes = HashMap::new();
sizes.insert(
"-A",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-B",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-C",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-D",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-E",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-F",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-G",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-H",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-I",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-J",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-K",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-L",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-M",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-N",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-O",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-P",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-Q",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-R",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-S",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-T",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-U",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-V",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-W",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-X",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-Y",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-Z",
Cizage {
hs: 2,
ss: 2,
fs: 4,
},
);
sizes.insert(
"-0A",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0B",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0C",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0D",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0E",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0F",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0G",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0H",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0I",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0J",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0K",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0L",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0M",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0N",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0O",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0P",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0Q",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0R",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0S",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0T",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0U",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0V",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0W",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0X",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0Y",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"-0Z",
Cizage {
hs: 3,
ss: 5,
fs: 8,
},
);
sizes.insert(
"--AAA",
Cizage {
hs: 5,
ss: 3,
fs: 8,
},
);
sizes
}
pub fn hards() -> HashMap<Vec<u8>, u32> {
let mut map = HashMap::new();
for c in b'A'..=b'Z' {
let key = format!("-{}", c as char).into_bytes();
map.insert(key, 2);
}
for c in b'a'..=b'z' {
let key = format!("-{}", c as char).into_bytes();
map.insert(key, 2);
}
map.insert(b"-0".to_vec(), 3); map.insert(b"--".to_vec(), 5);
map
}
pub static BARDS: Lazy<HashMap<Vec<u8>, u32>> = Lazy::new(|| {
let mut map = HashMap::new();
map.insert(vec![0xfb, 0x40], 3);
map.insert(vec![0xfb, 0xe0], 5);
for second_byte in [
0x00, 0x10, 0x20, 0x30, 0x40, 0x50, 0x60, 0x70, 0x80, 0x90, 0xa0, 0xb0, 0xc0, 0xd0, 0xe0,
0xf0,
] {
map.insert(vec![0xf8, second_byte], 2);
}
for second_byte in [
0x00, 0x10, 0x20, 0x30, 0x40, 0x50, 0x60, 0x70, 0x80, 0x90, 0xa0, 0xb0, 0xc0, 0xd0, 0xe0,
0xf0,
] {
map.insert(vec![0xf9, second_byte], 2);
}
for second_byte in [
0x00, 0x10, 0x20, 0x30, 0x40, 0x50, 0x60, 0x70, 0x80, 0x90, 0xa0, 0xb0, 0xc0, 0xd0, 0xe0,
0xf0,
] {
map.insert(vec![0xfa, second_byte], 2);
}
for second_byte in [0x00, 0x10, 0x20, 0x30] {
map.insert(vec![0xfb, second_byte], 2);
}
map
});
pub fn code_b64_to_b2(s: Vec<u8>) -> Vec<u8> {
let ss = str::from_utf8(&s).unwrap();
let i = b64_to_int(ss);
let padding_bits = 2 * (s.len() % 4);
let padded_i = i << padding_bits;
padded_i.to_bytes_be().to_vec()
}
fn b64_to_int(s: &str) -> BigUint {
let mut result = BigUint::from(0u32);
for c in s.chars() {
result <<= 6;
let val = match c {
'A'..='Z' => (c as u8 - b'A') as u32,
'a'..='z' => (c as u8 - b'a' + 26) as u32,
'0'..='9' => (c as u8 - b'0' + 52) as u32,
'-' => 62,
'_' => 63,
_ => panic!("Invalid Base64 character: {}", c),
};
result += BigUint::from(val);
}
result
}
fn pow_u64(base: u64, exp: u32) -> u64 {
base.checked_pow(exp).unwrap_or_else(|| u64::MAX)
}
#[allow(dead_code)]
pub trait Counter {
fn code(&self) -> &str;
fn name(&self) -> &str;
fn count(&self) -> u64;
fn qb64(&self) -> String;
fn qb64b(&self) -> Vec<u8>;
fn qb2(&self) -> Vec<u8>;
fn hard(&self) -> &str;
fn soft(&self) -> String;
fn both(&self) -> String;
fn full_size(&self) -> u32;
fn version(&self) -> Result<&Versionage, MatterError>;
fn gvrsn(&self) -> Result<&Versionage, MatterError>;
}
#[derive(Debug)]
pub struct BaseCounter {
code: String,
count: u64,
version: Versionage,
}
impl BaseCounter {
pub fn from_code_and_count(
code: Option<&str>,
count: Option<u64>,
count_b64: Option<&str>,
) -> Result<Self, MatterError> {
let gvrsn = VERSION;
let codes = if gvrsn.major == 1 {
&ctr_dex_1_0::MAP
} else {
&ctr_dex_2_0::MAP
};
let sizes = if gvrsn.major == 1 {
&get_sizes_1_0()
} else {
&get_sizes_2_0()
};
let mut code_str = match code {
Some(c) => c.to_string(),
None => return Err(MatterError::InvalidCode("No code provided".to_string())),
};
if !sizes.contains_key(code_str.as_str()) || code_str.len() < 2 {
match codes.get(code_str.as_str()) {
Some(actual_code) => {
code_str = actual_code.to_string();
if !sizes.contains_key(code_str.as_str()) || code_str.len() < 2 {
return Err(MatterError::InvalidCode(format!(
"Unsupported code={}",
code_str
)));
}
}
None => {
return Err(MatterError::InvalidCode(format!(
"Unsupported code={}",
code_str
)));
}
}
}
let size = sizes[code_str.as_str()];
let (hs, ss, fs) = (size.hs, size.ss, size.fs);
let cs = hs + ss;
if hs < 2 || fs != cs || cs % 4 != 0 {
return Err(MatterError::InvalidCodeSize(format!(
"Whole code size not full size or not multiple of 4. cs={} fs={}",
cs, fs
)));
}
let count_value = match count {
Some(c) => c,
None => match count_b64 {
Some(cb64) => b64_to_int(cb64).to_u64().unwrap_or(1),
None => 1,
},
};
let mut code_str = code_str;
let mut ss_value = ss;
if !"-123456789-_".contains(&code_str[1..2]) {
if ss != 2 && ss != 5 {
return Err(MatterError::InvalidVarIndex(format!(
"Invalid ss={} for code={}",
ss, code_str
)));
}
if code_str.chars().nth(1) != Some('0') && count_value > (64u64.pow(2) - 1) {
code_str = format!("-0{}", code_str.chars().nth(1).unwrap());
ss_value = 5;
}
}
if count_value > (64u64.pow(ss_value) - 1) {
return Err(MatterError::InvalidVarIndex(format!(
"Invalid count={} for code={} with ss={}",
count_value, code_str, ss_value
)));
}
Ok(BaseCounter {
code: code_str,
count: count_value,
version: gvrsn,
})
}
pub fn from_qb64(qb64: &str) -> Result<Self, MatterError> {
if qb64.is_empty() {
return Err(MatterError::ShortageError(
"Empty material, Need more characters.".to_string(),
));
}
if qb64.len() < 2 {
return Err(MatterError::ShortageError(format!(
"Need {} more characters.",
2 - qb64.len()
)));
}
let hards = hards();
let sizes = &get_sizes_1_0();
let first = &qb64[..2];
if !hards.contains_key(first.as_bytes()) {
return Err(MatterError::InvalidCode(format!(
"Invalid code selector={}",
first
)));
}
let hs = *hards.get(first.as_bytes()).unwrap() as usize;
if qb64.len() < hs {
return Err(MatterError::ShortageError(format!(
"Need {} more characters.",
hs - qb64.len()
)));
}
let hard = &qb64[..hs];
if !sizes.contains_key(hard) {
return Err(MatterError::UnexpectedCodeError(format!(
"Unsupported code ={}",
hard
)));
}
let size = sizes.get(hard).unwrap();
let (hs, fs) = (size.hs as usize, size.fs as usize);
if qb64.len() < fs {
return Err(MatterError::ShortageError(format!(
"Need {} more characters.",
fs - qb64.len()
)));
}
let count_bytes = &qb64[hs..fs];
let count_str = str::from_utf8(count_bytes.as_bytes())
.map_err(|_| MatterError::EncodingError("Invalid UTF-8 in count chars".to_string()))?;
let count = b64_to_int(count_str)
.to_u64()
.ok_or_else(|| MatterError::ValueError("Count value too large for u64".to_string()))?;
Ok(BaseCounter {
code: hard.to_string(),
count,
version: VERSION,
})
}
fn bexfil(qb2: &[u8]) -> Result<Self, MatterError> {
if qb2.is_empty() {
return Err(MatterError::ShortageError(
"Empty material, Need more bytes.".to_string(),
));
}
let sizes = &get_sizes_1_0();
let first = nab_sextets(qb2, 2)
.map_err(|e| MatterError::EncodingError(format!("Failed to extract sextets: {}", e)))?;
if !BARDS.contains_key(&first) {
return if first.len() > 0 && first[0] == 0xfc {
Err(MatterError::UnexpectedOpCodeError(
"Unexpected op code start while extracting Matter.".to_string(),
))
} else {
Err(MatterError::UnexpectedCodeError(format!(
"Unsupported code start sextet={:?}",
first
)))
};
}
let hs = *BARDS.get(&first).unwrap();
let bhs = ((hs * 3 + 3) / 4) as usize;
if qb2.len() < bhs {
return Err(MatterError::ShortageError(format!(
"Need {} more bytes.",
bhs - qb2.len()
)));
}
let hard = code_b2_to_b64(qb2, hs as usize)
.map_err(|e| MatterError::EncodingError(format!("Failed to convert code: {}", e)))?;
if !sizes.contains_key(hard.as_str()) {
return Err(MatterError::UnexpectedCodeError(format!(
"Unsupported code ={}",
hard
)));
}
let size = *sizes.get(hard.as_str()).unwrap();
let (hs, fs) = (size.hs as usize, size.fs as usize);
let bcs = (fs * 3 + 3) / 4;
if qb2.len() < bcs {
return Err(MatterError::ShortageError(format!(
"Need {} more bytes.",
bcs - qb2.len()
)));
}
let both = code_b2_to_b64(qb2, fs)
.map_err(|e| MatterError::EncodingError(format!("Failed to convert code: {}", e)))?;
let count = b64_to_int(&both[hs..fs])
.to_u64()
.ok_or_else(|| MatterError::ValueError("Count value too large for u64".to_string()))?;
Ok(BaseCounter {
code: hard.to_string(),
count,
version: VERSION,
})
}
fn infil(&self) -> Result<String, MatterError> {
let code = &self.code; let count = self.count;
let sizes = &get_sizes_1_0();
let size = sizes[code.as_str()];
let ss = size.ss;
let max_count = pow_u64(64, ss).checked_sub(1).ok_or_else(|| {
MatterError::ValueError("Arithmetic overflow in max count calculation".to_string())
})?;
if count > max_count {
return Err(MatterError::InvalidVarIndexError(format!(
"Invalid count={} for code={}.",
count, code
)));
}
let count_b64 = int_to_b64(count as u32, ss as usize);
let both = format!("{}{}", code, count_b64);
if both.len() % 4 != 0 {
return Err(MatterError::InvalidCodeSizeError(format!(
"Invalid size = {} of {} not a multiple of 4.",
both.len(),
both
)));
}
Ok(both)
}
fn binfil(&self) -> Result<Vec<u8>, MatterError> {
let code = &self.code; let count = self.count;
let sizes = &get_sizes_1_0();
let size = sizes[code.as_str()];
let (_, ss, fs) = (size.hs, size.ss, size.fs);
let max_count = pow_u64(64, ss).checked_sub(1).ok_or_else(|| {
MatterError::ValueError("Arithmetic overflow in max count calculation".to_string())
})?;
if count > max_count {
return Err(MatterError::InvalidVarIndexError(format!(
"Invalid count={} for code={}.",
count, code
)));
}
let count_b64 = int_to_b64(count as u32, ss as usize);
let both = format!("{}{}", code, count_b64);
if both.len() != fs as usize {
return Err(MatterError::InvalidCodeSizeError(format!(
"Mismatch code size = {} with table = {}.",
fs,
both.len()
)));
}
let result = code_b64_to_b2(both.into_bytes());
Ok(result)
}
}
impl Parsable for BaseCounter {
fn from_qb64b(data: &mut Vec<u8>, strip: Option<bool>) -> Result<Self, MatterError> {
let qb64b = data.as_slice();
let qb64 = str::from_utf8(qb64b).ok();
let idx = BaseCounter::from_qb64(qb64.unwrap_or(""))?;
if strip.unwrap_or(false) {
let fs = idx.full_size();
data.drain(..fs as usize);
}
Ok(idx)
}
fn from_qb2(data: &mut Vec<u8>, strip: Option<bool>) -> Result<Self, MatterError> {
let qb2 = data.as_slice();
let idx = BaseCounter::bexfil(qb2)?;
if strip.unwrap_or(false) {
let fs = idx.full_size();
data.drain(..fs as usize);
}
Ok(idx)
}
}
impl Counter for BaseCounter {
fn code(&self) -> &str {
&self.code
}
fn name(&self) -> &str {
self.code()
}
fn count(&self) -> u64 {
self.count
}
fn qb64(&self) -> String {
let result = self.infil();
result.unwrap()
}
fn qb64b(&self) -> Vec<u8> {
let result = self.qb64();
result.as_bytes().to_vec()
}
fn qb2(&self) -> Vec<u8> {
let result = self.binfil();
result.unwrap()
}
fn hard(&self) -> &str {
self.code()
}
fn soft(&self) -> String {
let sizes = get_sizes_1_0();
let size = sizes[self.code.as_str()];
int_to_b64(self.count() as u32, size.ss as usize)
}
fn both(&self) -> String {
format! {"{}{}", self.code(), self.soft()}
}
fn full_size(&self) -> u32 {
let sizes = &get_sizes_1_0();
let size = sizes[self.code.as_str()];
size.fs
}
fn version(&self) -> Result<&Versionage, MatterError> {
Ok(&(self.version))
}
fn gvrsn(&self) -> Result<&Versionage, MatterError> {
self.version()
}
}
#[cfg(test)]
mod tests {
use super::gen_dex;
use super::*;
use crate::cesr::decode_b64;
#[test]
fn test_genus_codes() {
assert_eq!(gen_dex::KERI_ACDC_SPAC, "--AAA");
assert_eq!(gen_dex::KERI, "--AAA");
assert_eq!(gen_dex::ACDC, "--AAA");
assert_eq!(gen_dex::SPAC, "--AAA");
assert_eq!(gen_dex::MAP.get("KERI_ACDC_SPAC"), Some(&"--AAA"));
assert_eq!(gen_dex::MAP.get("KERI"), Some(&"--AAA"));
assert_eq!(gen_dex::MAP.get("ACDC"), Some(&"--AAA"));
assert_eq!(gen_dex::MAP.get("SPAC"), Some(&"--AAA"));
assert_eq!(gen_dex::TUPLE.len(), 4);
assert!(gen_dex::TUPLE.contains(&"--AAA"));
}
#[test]
fn test_base_counter_v1() -> Result<(), MatterError> {
let count = 1u64;
let code = ctr_dex_1_0::CONTROLLER_IDX_SIGS.to_string();
let qsc = format!("{}{}", code, int_to_b64(count as u32, 2));
assert_eq!(qsc, "-AAB");
let mut qscb = qsc.as_bytes().to_vec();
let mut qscb2 = decode_b64(&qsc)?;
let counter = BaseCounter::from_code_and_count(Some(code.as_str()), Some(count), None)?;
assert_eq!(counter.code, ctr_dex_1_0::CONTROLLER_IDX_SIGS);
assert_eq!(counter.name(), "-A");
assert_eq!(counter.count, count);
assert_eq!(counter.qb64b(), qscb);
assert_eq!(counter.qb64(), qsc);
assert_eq!(counter.qb2(), qscb2);
assert_eq!(counter.version.major, 1);
assert_eq!(counter.version.minor, 0);
assert_eq!(counter.full_size(), 4);
assert_eq!(counter.soft(), "AB");
assert_eq!(counter.both(), qsc);
assert_eq!(counter.both(), counter.code.clone() + &counter.soft());
assert_eq!(counter.both(), counter.qb64());
let counter = BaseCounter::from_code_and_count(
Some(ctr_dex_1_0::CONTROLLER_IDX_SIGS.clone()),
Some(count),
None,
)?;
assert_eq!(counter.code, ctr_dex_1_0::CONTROLLER_IDX_SIGS);
assert_eq!(counter.name(), "-A");
assert_eq!(counter.count, count);
assert_eq!(counter.qb64b(), qscb);
assert_eq!(counter.qb64(), qsc);
assert_eq!(counter.qb2(), qscb2);
assert_eq!(counter.version.major, 1);
assert_eq!(counter.version.minor, 0);
let counter = BaseCounter::from_code_and_count(
Some(ctr_dex_1_0::CONTROLLER_IDX_SIGS.clone()),
Some(count),
None,
)?;
assert_eq!(counter.code, ctr_dex_1_0::CONTROLLER_IDX_SIGS);
assert_eq!(counter.name(), "-A");
assert_eq!(counter.count, count);
assert_eq!(counter.qb64b(), qscb);
assert_eq!(counter.qb64(), qsc);
assert_eq!(counter.qb2(), qscb2);
assert_eq!(counter.version.major, 1);
assert_eq!(counter.version.minor, 0);
let counter = BaseCounter::from_code_and_count(
Some(ctr_dex_1_0::CONTROLLER_IDX_SIGS.clone()),
Some(1), None,
)?;
assert_eq!(counter.code, ctr_dex_1_0::CONTROLLER_IDX_SIGS);
assert_eq!(counter.name(), "-A");
assert_eq!(counter.count, count); assert_eq!(counter.qb64b(), qscb);
assert_eq!(counter.qb64(), qsc);
assert_eq!(counter.qb2(), qscb2);
assert_eq!(counter.version.major, 1);
assert_eq!(counter.version.minor, 0);
let counter = BaseCounter::from_qb64b(&mut qscb, None)?;
assert_eq!(counter.code, ctr_dex_1_0::CONTROLLER_IDX_SIGS);
assert_eq!(counter.name(), "-A");
assert_eq!(counter.count, count);
assert_eq!(counter.qb64b(), qscb);
assert_eq!(counter.qb64(), qsc);
assert_eq!(counter.qb2(), qscb2);
assert_eq!(counter.version.major, 1);
assert_eq!(counter.version.minor, 0);
let counter = BaseCounter::from_qb64(qsc.as_str())?;
assert_eq!(counter.code, ctr_dex_1_0::CONTROLLER_IDX_SIGS);
assert_eq!(counter.name(), "-A");
assert_eq!(counter.count, count);
assert_eq!(counter.qb64b(), qscb);
assert_eq!(counter.qb64(), qsc);
assert_eq!(counter.qb2(), qscb2);
assert_eq!(counter.version.major, 1);
assert_eq!(counter.version.minor, 0);
let counter = BaseCounter::from_qb2(&mut qscb2, None).expect("Failed to decode qb2");
assert_eq!(counter.code, ctr_dex_1_0::CONTROLLER_IDX_SIGS);
assert_eq!(counter.name(), "-A");
assert_eq!(counter.count, count);
assert_eq!(counter.qb64b(), qscb);
assert_eq!(counter.qb64(), qsc);
assert_eq!(counter.qb2(), qscb2);
assert_eq!(counter.version.major, 1);
assert_eq!(counter.version.minor, 0);
let long_qsc64 = format!("{}ABCD", qsc);
let counter = BaseCounter::from_qb64(long_qsc64.as_str())?;
assert_eq!(counter.qb64().len(), counter.full_size() as usize);
let short_qsc64 = qsc[..qsc.len() - 1].to_string();
let result = BaseCounter::from_qb64(short_qsc64.as_str());
assert!(result.is_err());
assert!(matches!(result.unwrap_err(), MatterError::ShortageError(_)));
let mut long_qscb2 = qscb2.clone();
long_qscb2.extend_from_slice(&[1, 2, 3, 4, 5]);
let counter = BaseCounter::from_qb2(&mut long_qscb2, None)?;
assert_eq!(counter.qb2(), qscb2);
assert_eq!(counter.qb64().len(), counter.full_size() as usize);
let mut short_qscb2 = qscb2[..qscb2.len() - 1].to_vec();
let result = BaseCounter::from_qb2(&mut short_qscb2, None);
assert!(result.is_err());
assert!(matches!(result.unwrap_err(), MatterError::ShortageError(_)));
let count = 5u64;
let qsc = format!(
"{}{}",
ctr_dex_1_0::CONTROLLER_IDX_SIGS,
int_to_b64(count as u32, 2)
);
assert_eq!(qsc, "-AAF");
let mut qscb = qsc.as_bytes().to_vec();
let qscb2 = decode_b64(&qsc)?;
let counter = BaseCounter::from_code_and_count(
Some(ctr_dex_1_0::CONTROLLER_IDX_SIGS.clone()),
Some(count),
None,
)?;
assert_eq!(counter.code, ctr_dex_1_0::CONTROLLER_IDX_SIGS);
assert_eq!(counter.name(), "-A");
assert_eq!(counter.count, count);
assert_eq!(counter.qb64b(), qscb);
assert_eq!(counter.qb64(), qsc);
assert_eq!(counter.qb2(), qscb2);
assert_eq!(counter.version.major, 1);
assert_eq!(counter.version.minor, 0);
let counter = BaseCounter::from_qb64b(&mut qscb, None)?;
assert_eq!(counter.code, ctr_dex_1_0::CONTROLLER_IDX_SIGS);
assert_eq!(counter.name(), "-A");
assert_eq!(counter.count, count);
assert_eq!(counter.qb64b(), qscb);
assert_eq!(counter.qb64(), qsc);
assert_eq!(counter.qb2(), qscb2);
assert_eq!(counter.version.major, 1);
assert_eq!(counter.version.minor, 0);
let count = 100024000u64;
let qsc = format!(
"{}{}",
ctr_dex_1_0::BIG_ATTACHMENT_GROUP,
int_to_b64(count as u32, 5)
);
assert_eq!(qsc, "-0VF9j7A");
let qscb = qsc.as_bytes().to_vec();
let qscb2 = decode_b64(&qsc)?;
let counter = BaseCounter::from_code_and_count(
Some(ctr_dex_1_0::BIG_ATTACHMENT_GROUP.clone()),
Some(count),
None,
)?;
assert_eq!(counter.code, ctr_dex_1_0::BIG_ATTACHMENT_GROUP);
assert_eq!(counter.name(), "-0V");
assert_eq!(counter.count, count);
assert_eq!(counter.qb64b(), qscb);
assert_eq!(counter.qb64(), qsc);
assert_eq!(counter.qb2(), qscb2);
assert_eq!(counter.version.major, 1);
assert_eq!(counter.version.minor, 0);
let counter = BaseCounter::from_qb64(qsc.as_str())?;
let qb2 = counter.qb2();
let test = counter.binfil()?;
assert_eq!(test, qb2);
let count = 100024000u64;
let qsc = format!(
"{}{}",
ctr_dex_1_0::BIG_PATHED_MATERIAL_GROUP,
int_to_b64(count as u32, 5)
);
assert_eq!(qsc, "-0LF9j7A");
let qscb = qsc.as_bytes().to_vec();
let qscb2 = decode_b64(&qsc)?;
let counter = BaseCounter::from_code_and_count(
Some(ctr_dex_1_0::BIG_PATHED_MATERIAL_GROUP.clone()),
Some(count),
None,
)?;
assert_eq!(counter.code, ctr_dex_1_0::BIG_PATHED_MATERIAL_GROUP);
assert_eq!(counter.name(), "-0L");
assert_eq!(counter.count, count);
assert_eq!(counter.qb64b(), qscb);
assert_eq!(counter.qb64(), qsc);
assert_eq!(counter.qb2(), qscb2);
assert_eq!(counter.version.major, 1);
assert_eq!(counter.version.minor, 0);
let count = 1u64;
let qsc = format!(
"{}{}",
ctr_dex_1_0::CONTROLLER_IDX_SIGS,
int_to_b64(count as u32, 2)
);
assert_eq!(qsc, "-AAB");
let qscb = qsc.as_bytes().to_vec();
let qscb2 = decode_b64(&qsc)?;
let counter = BaseCounter::from_qb64(qsc.as_str())?;
assert_eq!(counter.code, ctr_dex_1_0::CONTROLLER_IDX_SIGS);
assert_eq!(counter.name(), "-A");
assert_eq!(counter.count, count);
assert_eq!(counter.qb64b(), qscb);
assert_eq!(counter.qb64(), qsc);
assert_eq!(counter.qb2(), qscb2);
assert_eq!(counter.version.major, 1);
assert_eq!(counter.version.minor, 0);
let count = 1024u64;
let qsc = format!(
"{}{}",
ctr_dex_1_0::BIG_ATTACHMENT_GROUP,
int_to_b64(count as u32, 5)
);
assert_eq!(qsc, "-0VAAAQA");
let qscb = qsc.as_bytes().to_vec();
let qscb2 = decode_b64(&qsc)?;
let mut ims = qscb.clone();
let counter = BaseCounter::from_qb64b(&mut ims, None)?;
assert_eq!(counter.code, ctr_dex_1_0::BIG_ATTACHMENT_GROUP);
assert_eq!(counter.name(), "-0V");
assert_eq!(counter.count, count);
assert_eq!(counter.qb64b(), qscb);
assert_eq!(counter.qb64(), qsc);
assert_eq!(counter.qb2(), qscb2);
assert_eq!(counter.version.major, 1);
assert_eq!(counter.version.minor, 0);
assert_eq!(counter.full_size(), 8);
let mut ims = qscb2.clone();
let counter = BaseCounter::from_qb2(&mut ims, None)?;
assert_eq!(counter.code, ctr_dex_1_0::BIG_ATTACHMENT_GROUP);
assert_eq!(counter.name(), "-0V");
assert_eq!(counter.count, count);
assert_eq!(counter.qb64b(), qscb);
assert_eq!(counter.qb64(), qsc);
assert_eq!(counter.qb2(), qscb2);
assert_eq!(counter.version.major, 1);
assert_eq!(counter.version.minor, 0);
assert_eq!(counter.full_size(), 8);
Ok(())
}
}