diff --git a/.latest_aztec_cli_vars b/.latest_aztec_cli_vars new file mode 100644 index 00000000..cd3c2231 --- /dev/null +++ b/.latest_aztec_cli_vars @@ -0,0 +1,210 @@ +ACVM_BINARY_PATH +ACVM_WORKING_DIRECTORY +GOVERNANCE_CONTRACT_ADDRESS +API_KEY +API_PREFIX +ARCHIVER_MAX_LOGS +ARCHIVER_POLLING_INTERVAL_MS +ARCHIVER_URL +ARCHIVER_VIEM_POLLING_INTERVAL_MS +ARCHIVER_BATCH_SIZE +ASSUME_PROVEN_THROUGH_BLOCK_NUMBER +AZTEC_NODE_URL +AZTEC_PORT +BB_BINARY_PATH +BB_SKIP_CLEANUP +BB_WORKING_DIRECTORY +BOOTSTRAP_NODES +BLOB_SINK_PORT +BLOB_SINK_URL +BOT_DA_GAS_LIMIT +BOT_FEE_PAYMENT_METHOD +BOT_FLUSH_SETUP_TRANSACTIONS +BOT_FOLLOW_CHAIN +BOT_L2_GAS_LIMIT +BOT_MAX_PENDING_TXS +BOT_NO_START +BOT_NO_WAIT_FOR_TRANSFERS +BOT_PRIVATE_KEY +BOT_PRIVATE_TRANSFERS_PER_TX +BOT_PUBLIC_TRANSFERS_PER_TX +BOT_PXE_URL +BOT_RECIPIENT_ENCRYPTION_SECRET +BOT_SKIP_PUBLIC_SIMULATION +BOT_TOKEN_CONTRACT +BOT_TOKEN_SALT +BOT_TX_INTERVAL_SECONDS +BOT_TX_MINED_WAIT_SECONDS +BOT_MAX_CONSECUTIVE_ERRORS +BOT_STOP_WHEN_UNHEALTHY +COINBASE +DATA_DIRECTORY +DATA_STORE_MAP_SIZE_KB +DEBUG +DEPLOY_AZTEC_CONTRACTS_SALT +DEPLOY_AZTEC_CONTRACTS +ENFORCE_FEES +ETHEREUM_HOST +FEE_JUICE_CONTRACT_ADDRESS +FEE_JUICE_PORTAL_CONTRACT_ADDRESS +FEE_RECIPIENT +GOVERNANCE_PROPOSER_CONTRACT_ADDRESS +GOVERNANCE_PROPOSER_PAYLOAD_ADDRESS +INBOX_CONTRACT_ADDRESS +L1_CHAIN_ID +L1_CONSENSUS_HOST_URL +L1_CONSENSUS_HOST_API_KEY +L1_CONSENSUS_HOST_API_KEY_HEADER +L1_PRIVATE_KEY +L2_QUEUE_SIZE +LOG_ELAPSED_TIME +LOG_JSON +LOG_MULTILINE +LOG_LEVEL +MNEMONIC +NETWORK_NAME +NETWORK +NO_PXE +COIN_ISSUER_CONTRACT_ADDRESS +USE_GCLOUD_OBSERVABILITY +OTEL_EXPORTER_OTLP_METRICS_ENDPOINT +OTEL_EXPORTER_OTLP_TRACES_ENDPOINT +OTEL_EXPORTER_OTLP_LOGS_ENDPOINT +OTEL_SERVICE_NAME +OTEL_COLLECT_INTERVAL_MS +OTEL_EXCLUDE_METRICS +OTEL_EXPORT_TIMEOUT_MS +OUTBOX_CONTRACT_ADDRESS +P2P_BLOCK_CHECK_INTERVAL_MS +P2P_BLOCK_REQUEST_BATCH_SIZE +P2P_ENABLED +P2P_GOSSIPSUB_D +P2P_GOSSIPSUB_DHI +P2P_GOSSIPSUB_DLO +P2P_GOSSIPSUB_INTERVAL_MS +P2P_GOSSIPSUB_MCACHE_GOSSIP +P2P_GOSSIPSUB_MCACHE_LENGTH +P2P_GOSSIPSUB_TX_INVALID_MESSAGE_DELIVERIES_DECAY +P2P_GOSSIPSUB_TX_INVALID_MESSAGE_DELIVERIES_WEIGHT +P2P_GOSSIPSUB_TX_TOPIC_WEIGHT +P2P_L2_QUEUE_SIZE +P2P_MAX_PEERS +P2P_MIN_PEERS +P2P_PEER_CHECK_INTERVAL_MS +P2P_PEER_PENALTY_VALUES +P2P_QUERY_FOR_IP +P2P_REQRESP_INDIVIDUAL_REQUEST_TIMEOUT_MS +P2P_REQRESP_OVERALL_REQUEST_TIMEOUT_MS +P2P_SEVERE_PEER_PENALTY_BLOCK_LENGTH +P2P_TCP_LISTEN_ADDR +P2P_TCP_ANNOUNCE_ADDR +P2P_TX_POOL_KEEP_PROVEN_FOR +P2P_ATTESTATION_POOL_KEEP_FOR +P2P_TX_PROTOCOL +P2P_UDP_ANNOUNCE_ADDR +P2P_UDP_LISTEN_ADDR +P2P_ARCHIVED_TX_LIMIT +PEER_ID_PRIVATE_KEY +PROOF_VERIFIER_L1_START_BLOCK +PROOF_VERIFIER_POLL_INTERVAL_MS +PROVER_AGENT_ENABLED +PROVER_AGENT_CONCURRENCY +PROVER_AGENT_COUNT +PROVER_AGENT_PROOF_TYPES +PROVER_AGENT_POLL_INTERVAL_MS +PROVER_BROKER_HOST +PROVER_BROKER_ENABLED +PROVER_BROKER_JOB_TIMEOUT_MS +PROVER_BROKER_POLL_INTERVAL_MS +PROVER_BROKER_JOB_MAX_RETRIES +PROVER_COORDINATION_NODE_URL +PROVER_DISABLED +PROVER_FAILED_PROOF_STORE +PROVER_ID +PROVER_JOB_POLL_INTERVAL_MS +PROVER_JOB_TIMEOUT_MS +PROVER_NODE_POLLING_INTERVAL_MS +PROVER_NODE_MAX_PENDING_JOBS +PROVER_NODE_MAX_PARALLEL_BLOCKS_PER_EPOCH +PROVER_NODE_TX_GATHERING_TIMEOUT_MS +PROVER_NODE_TX_GATHERING_INTERVAL_MS +PROVER_NODE_TX_GATHERING_MAX_PARALLEL_REQUESTS +PROVER_PUBLISH_RETRY_INTERVAL_MS +PROVER_PUBLISHER_PRIVATE_KEY +PROVER_REAL_PROOFS +PROVER_REQUIRED_CONFIRMATIONS +PROVER_TEST_DELAY_MS +PXE_L2_STARTING_BLOCK +PXE_PROVER_ENABLED +QUOTE_PROVIDER_BASIS_POINT_FEE +QUOTE_PROVIDER_BOND_AMOUNT +QUOTE_PROVIDER_URL +PROVER_TARGET_ESCROW_AMOUNT +PROVER_MINIMUM_ESCROW_AMOUNT +REGISTRY_CONTRACT_ADDRESS +ROLLUP_CONTRACT_ADDRESS +SEQ_ALLOWED_SETUP_FN +SEQ_MAX_BLOCK_SIZE_IN_BYTES +SEQ_MAX_TX_PER_BLOCK +SEQ_MIN_TX_PER_BLOCK +SEQ_MAX_DA_BLOCK_GAS +SEQ_MAX_L2_BLOCK_GAS +SEQ_PUBLISH_RETRY_INTERVAL_MS +SEQ_PUBLISHER_PRIVATE_KEY +SEQ_REQUIRED_CONFIRMATIONS +SEQ_TX_POLLING_INTERVAL_MS +SEQ_ENFORCE_TIME_TABLE +SEQ_MAX_L1_TX_INCLUSION_TIME_INTO_SLOT +SLASH_FACTORY_CONTRACT_ADDRESS +STAKING_ASSET_CONTRACT_ADDRESS +REWARD_DISTRIBUTOR_CONTRACT_ADDRESS +TELEMETRY +TEST_ACCOUNTS +TX_GOSSIP_VERSION +TXE_PORT +VALIDATOR_ATTESTATIONS_POLLING_INTERVAL_MS +VALIDATOR_DISABLED +VALIDATOR_PRIVATE_KEY +VALIDATOR_REEXECUTE +VERSION +WS_BLOCK_CHECK_INTERVAL_MS +WS_PROVEN_BLOCKS_ONLY +WS_BLOCK_REQUEST_BATCH_SIZE +VERIFIER_VIEM_POLLING_INTERVAL_MS +L1_READER_VIEM_POLLING_INTERVAL_MS +PROVER_VIEM_POLLING_INTERVAL_MS +SEQ_VIEM_POLLING_INTERVAL_MS +WS_DB_MAP_SIZE_KB +WS_DATA_DIRECTORY +WS_NUM_HISTORIC_BLOCKS +ETHEREUM_SLOT_DURATION +AZTEC_SLOT_DURATION +AZTEC_EPOCH_DURATION +AZTEC_TARGET_COMMITTEE_SIZE +AZTEC_EPOCH_PROOF_CLAIM_WINDOW_IN_L2_SLOTS +AZTEC_MINIMUM_STAKE +AZTEC_SLASHING_QUORUM +AZTEC_SLASHING_ROUND_SIZE +AZTEC_GOVERNANCE_PROPOSER_QUORUM +AZTEC_GOVERNANCE_PROPOSER_ROUND_SIZE +L1_GAS_LIMIT_BUFFER_PERCENTAGE +L1_GAS_LIMIT_BUFFER_FIXED +L1_GAS_PRICE_MIN +L1_GAS_PRICE_MAX +L1_BLOB_FEE_PER_GAS_MAX +L1_PRIORITY_FEE_BUMP_PERCENTAGE +L1_PRIORITY_FEE_RETRY_BUMP_PERCENTAGE +L1_FIXED_PRIORITY_FEE_PER_GAS +L1_TX_MONITOR_MAX_ATTEMPTS +L1_TX_MONITOR_CHECK_INTERVAL_MS +L1_TX_MONITOR_STALL_TIME_MS +L1_TX_MONITOR_TX_TIMEOUT_MS +L1_TX_PROPAGATION_MAX_QUERY_ATTEMPTS +FAUCET_MNEMONIC_ACCOUNT_INDEX +FAUCET_ETH_AMOUNT +FAUCET_INTERVAL_MS +FAUCET_L1_ASSETS +K8S_POD_NAME +K8S_POD_UID +K8S_NAMESPACE_NAME +CUSTOM_FORWARDER_CONTRACT_ADDRESS diff --git a/Cargo.toml b/Cargo.toml index 56f1ba08..c6e521fd 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,6 +1,6 @@ [workspace] members = ["packages/*"] -exclude = ["packages/circom", "test"] +exclude = ["packages/circom", "test", "packages/noir"] # [patch."https://github.com/stalwartlabs/mail-builder"] # mail-builder = { version = "0.2.5", git = "https://github.com/stalwartlabs//mail-builder", tag = "0.2.5" } diff --git a/README.md b/README.md index 58c06b56..0a5f7e8b 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,6 @@ # zk-regex -A library to compile regex verification in circom. Explained on [our blog post](https://prove.email/blog/zkregex). You can use regex to specify how to parse an email in a ZK Email proof when defining a new patterm on [the ZK Email SDK registry](https://sdk.prove.email/). Noir coming soon. +A library to compile regex verification in circom. Explained on [our blog post](https://prove.email/blog/zkregex). You can use regex to specify how to parse an email in a ZK Email proof when defining a new patterm on [the ZK Email SDK registry](https://sdk.prove.email/). Noir support is also available. diff --git a/packages/circom/tests/simple_regex.test.js b/packages/circom/tests/simple_regex.test.js index 8b9d89e1..d5e97ebc 100644 --- a/packages/circom/tests/simple_regex.test.js +++ b/packages/circom/tests/simple_regex.test.js @@ -68,7 +68,7 @@ describe("Simple Regex", () => { for (let idx = 0; idx < 64; ++idx) { if (revealedIdx[substr_idx].includes(idx)) { expect(BigInt(paddedStr[idx])).toEqual( - witness[2 + 64 * substr_idx + idx] + witness[2 + 64 * substr_idx + idx] ); } else { expect(0n).toEqual(witness[2 + 64 * substr_idx + idx]); diff --git a/packages/compiler/Cargo.toml b/packages/compiler/Cargo.toml index 049a959e..b606b414 100644 --- a/packages/compiler/Cargo.toml +++ b/packages/compiler/Cargo.toml @@ -36,3 +36,5 @@ regex = "=1.10.6" getrandom = { version = "0.2", features = ["js"] } wasm-bindgen = "0.2" serde-wasm-bindgen = "0.6.5" +comptime = { git = "https://github.com/jp4g/sparse_array", branch = "feat/comptime-codegen" } +# comptime = { path = "../../../../aztec/sparse_array/comptime" } diff --git a/packages/compiler/src/bin/compiler.rs b/packages/compiler/src/bin/compiler.rs index ba53749b..c3b811cc 100644 --- a/packages/compiler/src/bin/compiler.rs +++ b/packages/compiler/src/bin/compiler.rs @@ -60,28 +60,44 @@ enum Commands { Decomposed { #[arg(short, long)] decomposed_regex_path: String, - #[arg(short, long)] + #[arg(long)] halo2_dir_path: Option, #[arg(short, long)] circom_file_path: Option, #[arg(short, long)] template_name: Option, + #[arg(long)] + noir_file_path: Option, #[arg(short, long)] gen_substrs: Option, + #[arg(short, long)] + sparse_array: Option, + #[arg(short, long)] + force_match: Option, + #[arg(short, long)] + use_common: Option, }, Raw { #[arg(short, long)] raw_regex: String, #[arg(short, long)] substrs_json_path: Option, - #[arg(short, long)] + #[arg(long)] halo2_dir_path: Option, #[arg(short, long)] circom_file_path: Option, #[arg(short, long)] template_name: Option, + #[arg(long)] + noir_file_path: Option, #[arg(short, long)] gen_substrs: Option, + #[arg(short, long)] + sparse_array: Option, + #[arg(short, long)] + force_match: Option, + #[arg(short, long)] + use_common: Option, }, } @@ -99,7 +115,11 @@ fn process_decomposed(cli: Cli) { halo2_dir_path, circom_file_path, template_name, + noir_file_path, gen_substrs, + sparse_array, + force_match, + use_common, } = cli.command { if let Err(e) = gen_from_decomposed( @@ -107,7 +127,11 @@ fn process_decomposed(cli: Cli) { halo2_dir_path.as_deref(), circom_file_path.as_deref(), template_name.as_deref(), + noir_file_path.as_deref(), gen_substrs, + sparse_array, + force_match, + use_common.as_deref(), ) { eprintln!("Error: {}", e); std::process::exit(1); @@ -122,7 +146,11 @@ fn process_raw(cli: Cli) { halo2_dir_path, circom_file_path, template_name, + noir_file_path, gen_substrs, + sparse_array, + force_match, + use_common, } = cli.command { if let Err(e) = gen_from_raw( @@ -131,7 +159,11 @@ fn process_raw(cli: Cli) { halo2_dir_path.as_deref(), circom_file_path.as_deref(), template_name.as_deref(), + noir_file_path.as_deref(), gen_substrs, + sparse_array, + force_match, + use_common.as_deref(), ) { eprintln!("Error: {}", e); std::process::exit(1); diff --git a/packages/compiler/src/lib.rs b/packages/compiler/src/lib.rs index 3a7fa04e..91170751 100644 --- a/packages/compiler/src/lib.rs +++ b/packages/compiler/src/lib.rs @@ -1,6 +1,7 @@ mod circom; mod errors; mod halo2; +mod noir; mod regex; mod structs; mod wasm; @@ -9,6 +10,7 @@ use circom::gen_circom_template; use errors::CompilerError; use halo2::gen_halo2_tables; use itertools::Itertools; +use noir::gen_noir_fn; use regex::{create_regex_and_dfa_from_str_and_defs, get_regex_and_dfa}; use std::{fs::File, path::PathBuf}; use structs::{DecomposedRegexConfig, RegexAndDFA, SubstringDefinitionsJson}; @@ -46,6 +48,9 @@ fn load_substring_definitions_json( /// * `circom_template_name` - An optional name for the Circom template. /// * `num_public_parts` - The number of public parts in the regex. /// * `gen_substrs` - A boolean indicating whether to generate substrings. +/// * `sparse_array` - A boolean indicating whether to use a sparse array for the DFA. (TEST UTILITY) +/// * `force_match` - A boolean indicating whether the circuit should force a match or export a boolean. (TEST UTILITY) +/// * `add_common` - A boolean indicating whether to add common regex definitions in the file or not. (TEST UTILITY) /// /// # Returns /// @@ -55,8 +60,12 @@ fn generate_outputs( halo2_dir_path: Option<&str>, circom_file_path: Option<&str>, circom_template_name: Option<&str>, + noir_file_path: Option<&str>, num_public_parts: usize, gen_substrs: bool, + sparse_array: Option, + force_match: Option, + use_common: Option<&str>, ) -> Result<(), CompilerError> { if let Some(halo2_dir_path) = halo2_dir_path { let halo2_dir_path = PathBuf::from(halo2_dir_path); @@ -86,6 +95,17 @@ fn generate_outputs( )?; } + if let Some(noir_file_path) = noir_file_path { + gen_noir_fn( + regex_and_dfa, + &PathBuf::from(noir_file_path), + gen_substrs, + sparse_array, + force_match, + use_common, + )?; + } + Ok(()) } @@ -107,7 +127,11 @@ pub fn gen_from_decomposed( halo2_dir_path: Option<&str>, circom_file_path: Option<&str>, circom_template_name: Option<&str>, + noir_file_path: Option<&str>, gen_substrs: Option, + sparse_array: Option, + force_match: Option, + use_common: Option<&str>, ) -> Result<(), CompilerError> { let mut decomposed_regex_config: DecomposedRegexConfig = serde_json::from_reader(File::open(decomposed_regex_path)?)?; @@ -126,8 +150,12 @@ pub fn gen_from_decomposed( halo2_dir_path, circom_file_path, circom_template_name, + noir_file_path, num_public_parts, gen_substrs, + sparse_array, + force_match, + use_common, )?; Ok(()) @@ -153,22 +181,30 @@ pub fn gen_from_raw( halo2_dir_path: Option<&str>, circom_file_path: Option<&str>, template_name: Option<&str>, + noir_file_path: Option<&str>, gen_substrs: Option, + sparse_array: Option, + force_match: Option, + use_common: Option<&str>, ) -> Result<(), CompilerError> { let substrs_defs_json = load_substring_definitions_json(substrs_json_path)?; let num_public_parts = substrs_defs_json.transitions.len(); let regex_and_dfa = create_regex_and_dfa_from_str_and_defs(raw_regex, substrs_defs_json)?; - let gen_substrs = gen_substrs.unwrap_or(true); + let gen_substrs = gen_substrs.unwrap_or(false); generate_outputs( ®ex_and_dfa, halo2_dir_path, circom_file_path, template_name, + noir_file_path, num_public_parts, gen_substrs, + sparse_array, + force_match, + use_common, )?; Ok(()) diff --git a/packages/compiler/src/noir/common.rs b/packages/compiler/src/noir/common.rs new file mode 100644 index 00000000..13609ba8 --- /dev/null +++ b/packages/compiler/src/noir/common.rs @@ -0,0 +1,209 @@ +/** + * Defines common regex structures and functions to be used in generated code + * + * @returns the common regex file definition + */ +pub fn get_common_regex_def() -> String { + format!( + r#" + {SEQUENCE_DEF} + {EXTRACT_SUBSTRING_DEF} + {MASK_MATCH_DEF} + {REVERSE_VEC_DEF} + "# + ) +} + +const SEQUENCE_DEF: &str = r#" +// points to a seque +pub struct Sequence { + index: u32, + length: u32, + end: u32 +} + +impl Sequence { + pub fn new(index: u32, length: u32) -> Self { + Self { index, length, end: index + length } + } + + pub fn default() -> Self { + Self { index: 0, length: 0, end: 0 } + } + + pub fn initialized(self) -> bool { + self.length > 0 + } + + pub fn index(self) -> u32 { + self.index + } + + pub fn length(self) -> u32 { + self.length + } + + pub fn end(self) -> u32 { + self.end + } + + pub fn in_range(self, index: u32) -> bool { + // if index + length == 0, index < self.end implicitly returns false if uninitialized + index >= self.index & index < self.end + } +} +"#; + +const EXTRACT_SUBSTRING_DEF: &str = r#" +/** + * Extracts all substrings from a pattern match + * @dev not super optimal - all substrings will be assumed to be of the length of longest substring. + * often this will be the size of the input. Use at discretion. + * + * @param input - the input array to extract from + * @param sequences - the sequences to extract from the input + * @returns the extracted substrings + */ +pub fn extract_all_substrings< + let INPUT_LENGTH: u32, + let NUM_SUBSTRINGS: u32, + let MAX_SUBSTRING_LENGTH: u32 +>( + input: [u8; INPUT_LENGTH], + sequences: BoundedVec, +) -> BoundedVec, NUM_SUBSTRINGS> {{ + let mut substrings: BoundedVec, NUM_SUBSTRINGS> = BoundedVec::new(); + for i in 0..NUM_SUBSTRINGS {{ + let substring = sequences.get_unchecked(i); + let mut extracted_substring = extract_substring(substring, input); + let mut len = substrings.len() + 1; + if i >= sequences.len() {{ + extracted_substring = BoundedVec::new(); + len = substrings.len(); + }} + substrings.len = len; + substrings.storage[i] = extracted_substring; + }} + substrings +}} + +/** + * Optimized algorithm for extracting a subsequence from an input array + * + * @param substring_sequence - the sequence to extract from the input + * @param input - the input array to extract from + * @returns the extracted subsequence + */ +pub fn extract_substring( + substring_sequence: Sequence, + input: [u8; INPUT_LENGTH], +) -> BoundedVec { + let mut substring: BoundedVec = unsafe { __extract_substring(substring_sequence, input) }; + assert(substring_sequence.length == substring.len(), "length mismatch"); + for i in 0..MAX_SUBSTRING_LENGTH { + // hack for index to never exceed array bounds + // must be constrained to be true when matching is required to prevent 0's passing when shouldn't + // @dev while this adds constraints in worse case it can be more efficient if MAX_SUBSTRING_LENGTH < INPUT_LENGTH + let input_range_check = substring_sequence.index + i < INPUT_LENGTH; + let index = (substring_sequence.index + i) as Field * input_range_check as Field; + + // range where input should match substring + let sequence_range_check = i >= substring_sequence.length; + + // constrain array construction if in range + let expected_byte = input[index]; + let byte = substring.get_unchecked(i); + let matched = (expected_byte as Field == byte as Field); + assert(matched | sequence_range_check, "incorrect substring construction"); + } + substring +} + +/** + * Unconstrained helper to build the extracted substring + * @dev must be checked by extract_substring to constrain construction of substring + * + * @param substring_sequence - the sequence to extract from the input + * @param input - the input array to extract from + * @returns the extracted subsequence + */ +unconstrained fn __extract_substring( + substring_sequence: Sequence, + input: [u8; INPUT_LENGTH], +) -> BoundedVec { + let mut substring: BoundedVec = BoundedVec::new(); + for i in 0..substring_sequence.length { + let byte = input[substring_sequence.index + i]; + substring.push(byte); + } + substring +} + "#; + +const MASK_MATCH_DEF: &str = r#" +// pub fn mask_input( +// substring_sequences: BoundedVec, +// input: [u8; INPUT_LENGTH], +// ) -> [u8; INPUT_LENGTH] { +// let masked: [u8; INPUT_LENGTH] = unsafe { __mask_input(substring_sequences, input) }; +// for i in 0..INPUT_LENGTH { +// let any_in_range = substring_sequences +// .storage() +// .any(|sequence: Sequence| sequence.in_range(i)); +// let expected_byte = input[i] as Field * any_in_range as Field; +// assert(masked[i] as Field == expected_byte, "Incorrect masking"); +// } +// masked +// } + +unconstrained fn __mask_input( + substring_sequences: BoundedVec, + input: [u8; INPUT_LENGTH], +) -> [u8; INPUT_LENGTH] { + let mut masked_input: [u8; INPUT_LENGTH] = [0; INPUT_LENGTH]; + for i in 0..substring_sequences.len() { + let sequence = substring_sequences.get_unchecked(i); + for j in sequence.index..sequence.end() { + masked_input[j] = input[j]; + } + } + masked_input +} +"#; + +const REVERSE_VEC_DEF: &str = r#" +/** + * Optimized reversal of a BoundedVector with preservation of 0-padding at end + * + * @param input - the input vector to reverse + * @returns the reversed vector + */ +fn reverse_vec(input: BoundedVec) -> BoundedVec { + let mut reversed = unsafe { __reverse_vec(input) }; + for i in 0..N { + let in_range = (i < reversed.len()) as Field; + // if in range choose opposite index, otherwise choose same index to check 0's + // yeah I know this is ugly show me a more efficient version and I'll use it + let index = (((input.len() as Field) - (i as Field * in_range) - 1) * in_range as Field + (i as Field * (1 - in_range))) as Field; + let expected_byte = input.get_unchecked(index as u32) as Field * in_range as Field; + let byte = reversed.get_unchecked(i) as Field; + assert(byte == expected_byte, "Incorrect reverse"); + } + reversed +} + +/** + * Unconstrained helper to build the reversed vector without using mutable RAM tables + * @dev SHOULD NOT BE CALLED BY ANYTHING EXCEPT `reverse_vec` + * + * @param input - the input vector to reverse + * @output - the reversed vector + **/ +unconstrained fn __reverse_vec(input: BoundedVec) -> BoundedVec { + let mut reversed: BoundedVec = BoundedVec::new(); + for i in 0..input.len() { + reversed.push(input.get(input.len() - i - 1)); + } + reversed +} +"#; diff --git a/packages/compiler/src/noir/conditions.rs b/packages/compiler/src/noir/conditions.rs new file mode 100644 index 00000000..5fa67255 --- /dev/null +++ b/packages/compiler/src/noir/conditions.rs @@ -0,0 +1,293 @@ +use super::utils::indent; +use itertools::Itertools; +use std::collections::BTreeSet; + +#[derive(Debug, Clone)] +pub struct StateMatch { + single: usize, // the single state + match_vec: Vec, // all of the states to & with the single state + s: bool, // whether single is s or s_next +} + +/** + * Get the final states that can cause the regex match to be accepted or rejected + * + */ +pub fn get_final_states_predicate(accept_state_ids: &Vec) -> String { + accept_state_ids + .iter() + .map(|id| format!("(s == {id})")) + .collect_vec() + .join(" | ") +} + +/** + * Get the exact end state that a running match should recognize as the end of a match span + */ +pub fn get_end_states_predicate(accept_state_ids: &Vec) -> String { + match accept_state_ids.len() == 1 { + true => format!( + "(s == {}) & (s_next == {})", + accept_state_ids[0], accept_state_ids[0] + ), + false => format!( + "(s == {}) & (s_next == {})", + accept_state_ids[0], accept_state_ids[1] + ), + } +} + +pub fn get_end_range_predicate(accept_state_ids: &Vec) -> String { + accept_state_ids + .iter() + .map(|id| format!("(s_next == {})", id)) + .join(" | ") +} + +pub fn get_substring_range_predicates(substr_ranges: &Vec>) -> String { + let substr_cases = substr_ranges + .iter() + .enumerate() + .map(|(index, range)| squash_transition_predicate(range, index)) + .join(""); + + let final_range_predicate = { + let mut cases = Vec::new(); + for i in 0..substr_ranges.len() { + cases.push(format!("case_{}", i)); + } + let case_str = cases.join(", "); + indent( + &format!( + r#" +let substring_range_check = [{case_str}] + .all(|case| case == true); + +assert(substring_range_check, "substr array ranges wrong"); + "# + ), + 2, + ) + }; + + format!( + r#" +{substr_cases} + +{final_range_predicate} + "# + ) +} + +pub fn substring_extraction_conditions( + substr_ranges: &Vec>, + accept_state_ids: &Vec, +) -> String { + // 1. SUBSTRING MATCH/ SEQUENCE CONSTURCITON CONDITIONS // + let mut first_condition = true; + let mut sequence_conditions = substr_ranges + .iter() + .map(|range_set| { + // Combine the range conditions into a single line using `|` operator + let range_conditions = range_set + .iter() + .map(|(range_start, range_end)| { + format!("(s == {range_start}) & (s_next == {range_end})") + }) + .collect::>() + .join(" | "); + let start_index = indent( + &format!( + r#" +if (consecutive_substr == 0) {{ +current_substring.index = i; +}};"# + ), + 1, + ); + // For the first condition, use `if`, for others, use `else if` + let start_part = match first_condition { + true => "if", + false => "else if", + }; + first_condition = false; + + // The body of the condition handling substring creation/updating + format!( + r#" +{start_part} ({range_conditions}) {{ + {start_index} + current_substring.length += 1; + consecutive_substr = 1; +}}"# + ) + }) + .collect::>() + .join("\n"); + + // 2. JOIN WITH FINAL CONDITIONS // + let end_states_predicate = get_end_states_predicate(accept_state_ids); + let substring_conditions = format!( + r#" +{sequence_conditions} else if ((consecutive_substr == 1) & (s_next == 0)) {{ + current_substring = Sequence::default(); + full_match = Sequence::default(); + substrings = BoundedVec::new(); + consecutive_substr = 0; +}} else if {end_states_predicate} {{ + full_match.length = i - full_match.index + 1; + complete = true; +}} else if (consecutive_substr == 1) {{ + // The substring is done so "save" it + substrings.push(current_substring); + // reset the substring holder for next use + current_substring = Sequence::default(); + consecutive_substr = 0; +}}"# + ); + + indent(&substring_conditions, 2) +} + +/** + * Determines the combination of (s, s_next) with minimal boolean comparisons to elimitate gates + * + * @param states- the s -> s_next pairs for a substring match + * @param index - the index of the substring match + * @return the optimize state matches + */ +fn squash_transition_predicate(states: &BTreeSet<(usize, usize)>, index: usize) -> String { + use std::collections::{HashMap, HashSet}; + + // Create maps for forward and reverse connections + let mut s_to_next: HashMap> = HashMap::new(); + let mut next_to_s: HashMap> = HashMap::new(); + + for &(s, next) in states { + s_to_next.entry(s).or_default().push(next); + next_to_s.entry(next).or_default().push(s); + } + + // Helper function to get sorted unique values + let get_unique_sorted = |v: &Vec| -> Vec { + let mut unique: Vec = v.iter().copied().collect(); + unique.sort_unstable(); + unique.dedup(); + unique + }; + + let mut result = Vec::new(); + let mut covered = HashSet::new(); + + // First pass: Find nodes that have multiple outgoing edges + for (&num, matches_found) in &s_to_next { + let matches = get_unique_sorted(matches_found); + if matches.len() > 1 { + result.push(StateMatch { + single: num, + match_vec: matches.clone(), + s: true, + }); + for &m in &matches { + covered.insert((num, m)); + } + } + } + + // Second pass: Find remaining edges that need to be covered + let mut uncovered = states + .iter() + .filter(|&&(s, next)| !covered.contains(&(s, next))) + .collect::>(); + + // Group remaining by destination + let mut dest_groups: HashMap> = HashMap::new(); + for &(s, next) in &uncovered { + dest_groups.entry(*next).or_default().push(*s); + } + + // Add any groups with multiple sources + for (dest, sources) in dest_groups { + let mut sources = sources; + sources.sort_unstable(); + result.push(StateMatch { + single: dest, + match_vec: sources, + s: false, + }); + } + + // Sort results by single value + result.sort_by_key(|sm| sm.single); + + // Build the string + let cases = result + .iter() + .map(|state| { + let (single_label, matches_label) = match state.s { + true => ("s", "s_next"), + false => ("s_next", "s"), + }; + let matches_str = state + .match_vec + .iter() + .map(|state| format!("({} == {})", matches_label, state)) + .join(" | "); + format!("({} == {}) & ({})", single_label, state.single, matches_str) + }) + .join(",\n\t"); + + indent( + &format!( + r#" +let range_{index} = substrings.get_unchecked({index}).in_range(i); +let case_{index} = [ + {cases} +].any(|case| case == true) | !range_{index}; +"# + ), + 2, + ) +} + +/** + * Either force a check of a final condition, or simply define it and return the bool + * @dev essentially only used to export regex match conditions + */ +pub fn force_match_condition( + force_match: bool, + condition: String, + return_type: Option, +) -> (String, String, String) { + // determine the return type and statement to return + let (return_type_str, return_statement_str) = match return_type.is_some() { + true => match force_match { + true => ( + format!("-> {}", return_type.unwrap()), + String::from("substrings"), + ), + false => ( + format!("-> ({}, bool)", return_type.unwrap()), + String::from("(substrings, matched)"), + ), + }, + false => match force_match { + true => (String::from(""), String::from("")), + false => (String::from("-> bool"), String::from("matched")), + }, + }; + + let match_statement_str =match force_match { + true => format!( + r#" + assert({condition}, "Match not found"); + "# + ), + false => format!( + r#" + let matched: bool = {condition}; + "# + ), + }; + (return_type_str, return_statement_str, match_statement_str) +} diff --git a/packages/compiler/src/noir/fn_body.rs b/packages/compiler/src/noir/fn_body.rs new file mode 100644 index 00000000..8ff62909 --- /dev/null +++ b/packages/compiler/src/noir/fn_body.rs @@ -0,0 +1,193 @@ +use super::{ + conditions::{ + force_match_condition, get_final_states_predicate, substring_extraction_conditions, + get_end_states_predicate, get_substring_range_predicates + }, + table::access_table, + BYTE_SIZE, +}; +use std::collections::BTreeSet; + +pub fn match_def( + regex_pattern: &str, + accept_state_ids: &Vec, + sparse_array: bool, + force_match: bool, +) -> String { + // table access according to lookup table arch + let table_access_255 = access_table("255", sparse_array); + let table_access_s_idx = access_table("s_idx", sparse_array); + let final_states_predicate = get_final_states_predicate(accept_state_ids); + // conditional returns and asserts based on whether the circuit should force a regex match + let (return_type, return_statement, force_match_condition) = + force_match_condition(force_match, final_states_predicate, None); + format!( + r#" +pub fn regex_match(input: [u8; N]) {return_type} {{ + // regex: {regex_pattern} + let mut s = 0; + s = {table_access_255}; + for i in 0..input.len() {{ + let s_idx = s * {BYTE_SIZE} + input[i] as Field; + std::as_witness(s_idx); + s = {table_access_s_idx}; + }} + {force_match_condition} + {return_statement} +}}"#, + ) + .trim() + .to_owned() +} + +pub fn capture_def( + accept_state_ids: &Vec, + substr_ranges: &Vec>, + sparse_array: bool, + force_match: bool +) -> String { + // table access according to lookup table arch + let table_access_255 = access_table("255", sparse_array); + let table_access_s_next = access_table("s * 256 + temp", sparse_array); + let table_access_s_next_temp = access_table("temp", sparse_array); + + // DFA predicates and conditional substring sequence building + let final_states_predicate = get_final_states_predicate(accept_state_ids); + let end_states_predicate = get_end_states_predicate(accept_state_ids); + let substring_range_predicates = get_substring_range_predicates(substr_ranges); + + let substr_length = substr_ranges.len(); + + + // conditional returns and asserts based on whether the circuit should force a regex match + let (return_type, return_statement, force_match_condition) = + force_match_condition( + force_match, + final_states_predicate, + Some(format!("BoundedVec")) + ); + + format!( + r#" +pub fn regex_match(input: [u8; N]) {return_type} {{ + let substrings = unsafe {{ __regex_match(input) }}; + + // "Previous" state + let mut s: Field = 0; + s = {table_access_255}; + // "Next"/upcoming state + let mut s_next: Field = 0; + let mut start_range = 0; + let mut end_range = 0; + + // check the match + for i in 0..N {{ + // state transition + let temp = input[i] as Field; + s_next = {table_access_s_next}; + let potential_s_next = {table_access_s_next_temp}; + if s_next == 0 {{ + s = 0; + s_next = potential_s_next; + }} + std::as_witness(s_next); + + // range conditions for substring matches + if ((start_range == 0) & (end_range == 0)) {{ + start_range = i as Field; + }} + if (({end_states_predicate}) & (end_range == 0)) {{ + end_range = i as Field + 1; + }} + {substring_range_predicates} + s = s_next; + }} + // check final state + {force_match_condition} + // constrain extracted substrings to be in match range + //let full_match = Sequence::new(start_range as u32, end_range as u32 - start_range as u32); + //let full_match_end = full_match.end(); + // for i in 0..{substr_length} {{ + // let substring = substrings.get_unchecked(i); + // let is_not_valid = i >= substrings.len(); + // let index_check = substring.index >= full_match.index; + // let length_check = substring.end() <= full_match_end; + // let check = (index_check) | is_not_valid; + // assert(check, f"Substring {{i}} range is out of bounds of the full match found"); + // }} + {return_statement} +}} + "# + ) +} + +pub fn unconstrained_capture_def( + regex_pattern: &str, + accept_state_ids: &Vec, + substr_ranges: &Vec>, + sparse_array: bool, +) -> String { + // table access according to lookup table arch + let table_access_255 = access_table("255", sparse_array); + let table_access_s_next = access_table("s * 256 + temp", sparse_array); + let table_access_s_next_temp = access_table("temp", sparse_array); + + // DFA predicates and conditional substring sequence building + let final_states_predicate = get_final_states_predicate(accept_state_ids); + let extraction_conditions = substring_extraction_conditions(substr_ranges, accept_state_ids); + + let substr_length = substr_ranges.len(); + format!( + r#" +pub unconstrained fn __regex_match(input: [u8; N]) -> BoundedVec {{ + // regex: {regex_pattern} + let mut substrings: BoundedVec = BoundedVec::new(); + let mut current_substring = Sequence::default(); + let mut full_match = Sequence::default(); + + // "Previous" state + let mut s: Field = 0; + s = {table_access_255}; + // "Next"/upcoming state + let mut s_next: Field = 0; + + let mut consecutive_substr = 0; + let mut complete = false; + + for i in 0..input.len() {{ + let temp = input[i] as Field; + let mut reset = false; + s_next = {table_access_s_next}; + let potential_s_next = {table_access_s_next_temp}; + if s_next == 0 {{ + reset = true; + s = 0; + s_next = potential_s_next; + }} + // If a substring was in the making, but the state was reset + // we disregard previous progress because apparently it is invalid + if (reset & (consecutive_substr == 1)) {{ + current_substring = Sequence::default(); + consecutive_substr = 0; + }} + // Fill up substrings +{extraction_conditions} + s = s_next; + if complete == true {{ + break; + }} + }} + assert({final_states_predicate}, f"no match: {{s}}"); + // Add pending substring that hasn't been added + if consecutive_substr == 1 {{ + substrings.push(current_substring); + full_match.length = input.len() - full_match.index; + }} + + + + substrings +}} + "# + ) +} diff --git a/packages/compiler/src/noir/mod.rs b/packages/compiler/src/noir/mod.rs new file mode 100644 index 00000000..43620d14 --- /dev/null +++ b/packages/compiler/src/noir/mod.rs @@ -0,0 +1,199 @@ +mod common; +mod conditions; +mod fn_body; +mod table; +mod utils; + +use itertools::Itertools; +use std::{fs::File, io::Write, path::Path, collections::BTreeSet}; + +use crate::structs::RegexAndDFA; +use self::{ + table::make_lookup_table, + utils::escape_non_ascii, + fn_body::{match_def, capture_def, unconstrained_capture_def}, + common::get_common_regex_def +}; + +const ACCEPT_STATE_ID: &str = "accept"; +const BYTE_SIZE: u32 = 256; // u8 size + +type TableRows = Vec<(usize, u8, usize)>; + +/** + * Codegen Noir ZK Regex + * + * @param regex_and_dfa - the regex and dfa to generate the noir function for + * @param path - the path to write the noir function to + * @param gen_substrs - whether to generate substring matches + * @param sparse_array - whether to use a sparse array for the DFA + * @param force_match - whether the circuit should force a match or export a boolean + * @param add_common - optional dependency import to include for regex common definitions + */ +pub fn gen_noir_fn( + regex_and_dfa: &RegexAndDFA, + path: &Path, + gen_substrs: bool, + sparse_array: Option, + force_match: Option, + use_common: Option<&str> +) -> Result<(), std::io::Error> { + println!("{}", regex_and_dfa.dfa); + let use_sparse = sparse_array.unwrap_or(false); + let force_match = force_match.unwrap_or(true); + let noir_fn = to_noir_fn(regex_and_dfa, gen_substrs, use_sparse, force_match, use_common); + let mut file = File::create(path)?; + file.write_all(noir_fn.as_bytes())?; + file.flush()?; + Ok(()) +} + +/// Generates Noir code based on the DFA and whether a substring should be extracted. +/// +/// # Arguments +/// +/// * `regex_and_dfa` - The `RegexAndDFA` struct containing the regex pattern and DFA. +/// * `gen_substrs` - A boolean indicating whether to generate substrings. +/// * `sparse_array` - A boolean indicating whether to use a sparse array for the DFA. +/// * `force_match` - A boolean indicating whether the circuit should force a match or export a boolean. +/// * `use_common` - An optional dependency import to include for regex common definitions. +/// +/// # Returns +/// +/// A `String` that contains the Noir code +fn to_noir_fn( + regex_and_dfa: &RegexAndDFA, + gen_substrs: bool, + sparse_array: bool, + force_match: bool, + use_common: Option<&str>, +) -> String { + // Regex pattern + let mut regex_pattern = + regex_and_dfa + .regex_pattern + .replace('\n', "\\n") + .replace('\r', "\\r"); + println!("Generating Noir code for regex: {}", regex_pattern); + regex_pattern = escape_non_ascii(®ex_pattern); + // Parse the accepted states and rows for the DFA lookup table + let (accept_state_ids, rows) = parse_dfa(regex_and_dfa); + + // Determine the needed size of the lookup table + let mut table_size = BYTE_SIZE as usize * regex_and_dfa.dfa.states.len(); + if !regex_and_dfa.has_end_anchor { + table_size += BYTE_SIZE as usize; + } + + // generate the lookup table + let table_def = make_lookup_table(&rows, table_size, sparse_array); + + // let sparse_array_str = sparse_array.to_noir_string(None); + + // substring_ranges contains the transitions that belong to the substring + let substr_ranges: &Vec> = ®ex_and_dfa.substrings.substring_ranges; + // Note: substring_boundaries is only filled if the substring info is coming from decomposed setting + // and will be empty in the raw setting (using json file for substr transitions). This is why substring_ranges is used here + + // generate function body + let regex_match_def = match gen_substrs { + true => { + let constrained = capture_def(&accept_state_ids, substr_ranges, sparse_array, force_match); + let unconstrained = unconstrained_capture_def(®ex_pattern, &accept_state_ids, substr_ranges, sparse_array); + format!(r#" +{constrained} +{unconstrained} + "#) + } + false => match_def(®ex_pattern, &accept_state_ids, sparse_array, force_match), + }; + + // codegen the file + let mut regex_codegen = format!( + r#" +{table_def} +{regex_match_def} + "# + ); + if use_common.is_none() { + let common_regex_def = get_common_regex_def(); + + regex_codegen = format!( + r#" +{regex_codegen} +{common_regex_def} + "#, + ); + } else { + let common_import = format!("use {}::Sequence;", use_common.unwrap()); + regex_codegen = format!( + r#" +{common_import} +{regex_codegen} + "#, + ); + } + + regex_codegen +} + +/** + * Parse the accepted states and rows for the DFA lookup table + * + * @param regex_and_dfa - the regex and dfa to generate the noir function for + * @returns + * - the accepted states + * - the rows for the DFA lookup table + */ +fn parse_dfa(regex_and_dfa: &RegexAndDFA) -> (Vec, TableRows) { + // Multiple accepting states are not supported + // This is a vector nonetheless, to support an extra accepting state we'll use + // to allow any character occurrences after the original accepting state + let mut accept_state_ids = regex_and_dfa + .dfa + .states + .iter() + .filter(|s| s.state_type == ACCEPT_STATE_ID) + .map(|s| s.state_id) + .collect_vec(); + assert!( + accept_state_ids.len() == 1, + "there should be exactly 1 accept state" + ); + + // curr_state + char_code -> next_state + let mut rows: Vec<(usize, u8, usize)> = vec![]; + + // $ support + // In case that there is no end_anchor, we add an additional accepting state to which any + // character occurence after the accepting state will go. + // This needs to be a new state, otherwise substring extraction won't work correctly + if !regex_and_dfa.has_end_anchor { + let original_accept_id = accept_state_ids.get(0).unwrap().clone(); + // Create a new highest state + let extra_accept_id = regex_and_dfa + .dfa + .states + .iter() + .max_by_key(|state| state.state_id) + .map(|state| state.state_id) + .unwrap() + + 1; + accept_state_ids.push(extra_accept_id); + for char_code in 0..=254 { + rows.push((original_accept_id, char_code, extra_accept_id)); + rows.push((extra_accept_id, char_code, extra_accept_id)); + } + } + + // interstitial states + for state in regex_and_dfa.dfa.states.iter() { + for (&tran_next_state_id, tran) in &state.transitions { + for &char_code in tran { + rows.push((state.state_id, char_code, tran_next_state_id)); + } + } + }; + + (accept_state_ids, rows) +} diff --git a/packages/compiler/src/noir/table.rs b/packages/compiler/src/noir/table.rs new file mode 100644 index 00000000..b44b37c3 --- /dev/null +++ b/packages/compiler/src/noir/table.rs @@ -0,0 +1,80 @@ +use super::{utils::indent, BYTE_SIZE, TableRows}; +use comptime::{FieldElement, SparseArray}; + +/** + * Make lookup table for the DFA + * + * @param rows - the dfa transitions to add as rows to the table + * @param size - the total size of the table + * @param sparse_array - whether to use a sparse array or not + * @returns the codegen for the DFA lookup table in Noir + */ +pub fn make_lookup_table( + rows: &TableRows, + size: usize, + sparse_array: bool, +) -> String { + match sparse_array { + true => make_sparse_table(rows, size), + false => make_simple_table(rows, size), + } +} + +/** + * Make a simple lookup table for the DFA + * @dev simple means just a normal ROM table vs sparse array + * + * @param rows - the dfa transitions to add as rows to the table + * @param size - the total size of the table + * @returns the codegen for the DFA lookup table in Noir + */ +fn make_simple_table(rows: &TableRows, size: usize) -> String { + let mut body = String::new(); + for (curr_state_id, char_code, next_state_id) in rows { + body += + &format!("table[{curr_state_id} * {BYTE_SIZE} + {char_code}] = {next_state_id};\n",); + } + body = indent(&body, 1); + format!( + r#" +global table: [Field; {size}] = comptime {{ make_lookup_table() }}; + +comptime fn make_lookup_table() -> [Field; {size}] {{ + let mut table = [0; {size}]; + {body} + table +}}"# + ) +} + +/** + * Make a lookup table for the DFA using a sparse array + * + * @param rows - the dfa transitions to add as rows to the table + * @param size - the total size of the table + * @returns the codegen for the DFA lookup table in Noir + */ +fn make_sparse_table(rows: &TableRows, size: usize) -> String { + let mut keys: Vec = Vec::new(); + let mut values: Vec = Vec::new(); + for (curr_state_id, char_code, next_state_id) in rows { + keys.push(FieldElement::from( + curr_state_id * BYTE_SIZE as usize + *char_code as usize, + )); + values.push(FieldElement::from(*next_state_id)); + } + + let sparse_array = + SparseArray::create(&keys, &values, FieldElement::from(size)).to_noir_string(None); + format!(r#" +global table: {sparse_array} + "#) +} + +/// Access table by array index or sparse API index +pub fn access_table(s: &str, sparse: bool) -> String { + match sparse { + true => format!("table.get({})", s), + false => format!("table[{}]", s), + } +} diff --git a/packages/compiler/src/noir/utils.rs b/packages/compiler/src/noir/utils.rs new file mode 100644 index 00000000..94c82e98 --- /dev/null +++ b/packages/compiler/src/noir/utils.rs @@ -0,0 +1,29 @@ +/// Indents each line of the given string by a specified number of levels. +/// Each level adds four spaces to the beginning of non-whitespace lines. +pub(crate) fn indent(s: &str, level: usize) -> String { + let indent_str = " ".repeat(level); + s.split("\n") + .map(|s| { + if s.trim().is_empty() { + s.to_owned() + } else { + format!("{}{}", indent_str, s) + } + }) + .collect::>() + .join("\n") +} + +// Noir does not like non-ascii comments so use this to show regex +pub(crate) fn escape_non_ascii(input: &str) -> String { + input + .chars() + .map(|c| { + if c.is_ascii() { + c.to_string() + } else { + format!("\\u{{{:04x}}}", c as u32) + } + }) + .collect() +} \ No newline at end of file diff --git a/packages/compiler/src/noir2.rs b/packages/compiler/src/noir2.rs new file mode 100644 index 00000000..5a97ef25 --- /dev/null +++ b/packages/compiler/src/noir2.rs @@ -0,0 +1,656 @@ +use std::{ + collections::{BTreeSet, HashMap, HashSet}, + fs::File, + io::Write, + iter::FromIterator, + path::Path, +}; + +use comptime::{FieldElement, SparseArray}; +use itertools::Itertools; + +use crate::structs::RegexAndDFA; + +const ACCEPT_STATE_ID: &str = "accept"; +const BYTE_SIZE: u32 = 256; // u8 size + +pub fn gen_noir_fn( + regex_and_dfa: &RegexAndDFA, + path: &Path, + gen_substrs: bool, + sparse_array: Option, +) -> Result<(), std::io::Error> { + println!("{}", regex_and_dfa.dfa); + let use_sparse = sparse_array.unwrap_or(false); + let noir_fn = to_noir_fn(regex_and_dfa, gen_substrs, use_sparse); + let mut file = File::create(path)?; + file.write_all(noir_fn.as_bytes())?; + file.flush()?; + Ok(()) +} + +/// Generates Noir code based on the DFA and whether a substring should be extracted. +/// +/// # Arguments +/// +/// * `regex_and_dfa` - The `RegexAndDFA` struct containing the regex pattern and DFA. +/// * `gen_substrs` - A boolean indicating whether to generate substrings. +/// +/// # Returns +/// +/// A `String` that contains the Noir code +fn to_noir_fn(regex_and_dfa: &RegexAndDFA, gen_substrs: bool, sparse_array: bool) -> String { + // Multiple accepting states are not supported + // This is a vector nonetheless, to support an extra accepting state we'll use + // to allow any character occurrences after the original accepting state + let mut accept_state_ids: Vec = { + let accept_states = regex_and_dfa + .dfa + .states + .iter() + .filter(|s| s.state_type == ACCEPT_STATE_ID) + .map(|s| s.state_id) + .collect_vec(); + assert!( + accept_states.len() == 1, + "there should be exactly 1 accept state" + ); + accept_states + }; + + // curr_state + char_code -> next_state + let mut rows: Vec<(usize, u8, usize)> = vec![]; + + // $ support + // In case that there is no end_anchor, we add an additional accepting state to which any + // character occurence after the accepting state will go. + // This needs to be a new state, otherwise substring extraction won't work correctly + if !regex_and_dfa.has_end_anchor { + let original_accept_id = accept_state_ids.get(0).unwrap().clone(); + // Create a new highest state + let extra_accept_id = regex_and_dfa + .dfa + .states + .iter() + .max_by_key(|state| state.state_id) + .map(|state| state.state_id) + .unwrap() + + 1; + accept_state_ids.push(extra_accept_id); + for char_code in 0..=254 { + rows.push((original_accept_id, char_code, extra_accept_id)); + rows.push((extra_accept_id, char_code, extra_accept_id)); + } + } + + for state in regex_and_dfa.dfa.states.iter() { + for (&tran_next_state_id, tran) in &state.transitions { + for &char_code in tran { + rows.push((state.state_id, char_code, tran_next_state_id)); + } + } + } + + let mut table_size = BYTE_SIZE as usize * regex_and_dfa.dfa.states.len(); + if !regex_and_dfa.has_end_anchor { + table_size += BYTE_SIZE as usize; + } + + // handle conditional use of sparse array + let mut table_str = String::new(); + if !sparse_array { + let mut lut_body = String::new(); + for (curr_state_id, char_code, next_state_id) in rows { + lut_body += &format!( + "table[{curr_state_id} * {BYTE_SIZE} + {char_code}] = {next_state_id};\n", + ); + } + lut_body = indent(&lut_body, 1); + + table_str = format!( + r#" +global table: [Field; {table_size}] = comptime {{ make_lookup_table() }}; + +comptime fn make_lookup_table() -> [Field; {table_size}] {{ + let mut table = [0; {table_size}]; + {lut_body} + table +}} + + "# + ); + } else { + let mut keys: Vec = Vec::new(); + let mut values: Vec = Vec::new(); + for (curr_state_id, char_code, next_state_id) in rows { + keys.push(FieldElement::from( + curr_state_id * BYTE_SIZE as usize + char_code as usize, + )); + values.push(FieldElement::from(next_state_id)); + } + + let sparse_array: SparseArray = + SparseArray::create(&keys, &values, FieldElement::from(table_size)); + + table_str = format!( + r#" +global table: {sparse_str} + + "#, + sparse_str = sparse_array.to_noir_string(None) + ); + } + + // make sparse array in comptime + + // let sparse_array_str = sparse_array.to_noir_string(None); + + // substring_ranges contains the transitions that belong to the substring + let substr_ranges: &Vec> = ®ex_and_dfa.substrings.substring_ranges; + // Note: substring_boundaries is only filled if the substring info is coming from decomposed setting + // and will be empty in the raw setting (using json file for substr transitions). This is why substring_ranges is used here + + let final_states_condition_body = accept_state_ids + .iter() + .map(|id| format!("(s == {id})")) + .collect_vec() + .join(" | "); + let end_states_condition_body = match accept_state_ids.len() == 1 { + true => format!( + "(s == {}) & (s_next == {})", + accept_state_ids[0], accept_state_ids[0] + ), + false => format!( + "(s == {}) & (s_next == {})", + accept_state_ids[0], accept_state_ids[1] + ), + }; + + let end_range_condition = accept_state_ids + .iter() + .map(|id| format!("(s_next == {})", id)) + .join(" | "); + + let range_conditions = substr_ranges + .iter() + .enumerate() + .map(|(index, range)| { + let sorted = organize_states(range); + ranges_to_predicate(sorted, index) + }) + .join(""); + + let final_range_predicate = { + let mut cases = Vec::new(); + for i in 0..substr_ranges.len() { + cases.push(format!("case_{}", i)); + } + let case_str = cases.join(", "); + indent( + &format!( + r#" +let substring_range_check = [{case_str}] + .all(|case| case == true); + +assert(substring_range_check, "substr array ranges wrong"); + "# + ), + 2, + ) + }; + + let fn_body = if gen_substrs { + let mut first_condition = true; + + let mut conditions = substr_ranges + .iter() + .map(|range_set| { + // Combine the range conditions into a single line using `|` operator + let range_conditions = range_set + .iter() + .map(|(range_start, range_end)| { + format!("(s == {range_start}) & (s_next == {range_end})") + }) + .collect::>() + .join(" | "); + + // For the first condition, use `if`, for others, use `else if` + let (start_part, start_index) = if first_condition { + first_condition = false; + let start_index_text = format!( + "if (consecutive_substr == 0) {{ + full_match.index = i; + current_substring.index = i; + }};\n" + ); + ("if", start_index_text) + } else { + ("else if", format!("")) + }; + + // The body of the condition handling substring creation/updating + format!( + "{start_part} ({range_conditions}) {{ + {start_index} + current_substring.length += 1; + consecutive_substr = 1; +}}" + ) + }) + .collect::>() + .join("\n"); + + // Add the final else if for resetting the consecutive_substr + let final_conditions = format!( + "{conditions} else if ((consecutive_substr == 1) & (s_next == 0)) {{ + current_substring = Sequence::default(); + full_match = Sequence::default(); + substrings = BoundedVec::new(); + consecutive_substr = 0; +}} else if {end_states_condition_body} {{ + full_match.length = i - full_match.index + 1; + complete = true; +}} else if (consecutive_substr == 1) {{ + // The substring is done so \"save\" it + substrings.push(current_substring); + // reset the substring holder for next use + current_substring = Sequence::default(); + consecutive_substr = 0; +}}" + ); + + conditions = indent(&final_conditions, 2); // Indent twice to align with the for loop's body + + format!( + r#" +{table_str} +pub fn regex_match(input: [u8; N]) -> BoundedVec, {substr_length}> {{ + let pattern_match = unsafe {{ __regex_match(input) }}; + + // "Previous" state + let mut s: Field = 0; + s = {table_access_255}; + // "Next"/upcoming state + let mut s_next: Field = 0; + let mut start_range = 0; + let mut end_range = 0; + + // check the match + for i in 0..N {{ + // state transition + let temp = input[i] as Field; + s_next = {table_access_s_next}; + let potential_s_next = {table_access_s_next_temp}; + if s_next == 0 {{ + s = 0; + s_next = potential_s_next; + }} + std::as_witness(s_next); + + // range conditions for substring matches + if ((start_range == 0) & (end_range == 0)) {{ + start_range = i as Field; + }} + //let switch = (start_range + end_range != 0) as Field; + //let keep_start_case = start_range - (start_range * switch); + //let set_start_i_case = (1 - switch) * i as Field; + //start_range = keep_start_case + set_start_i_case; + //if (({end_range_condition}) & (end_range == 0)) {{ + // end_range = i as Field + 1; + //}} + if (({end_states_condition_body}) & (end_range == 0)) {{ + end_range = i as Field + 1; + }} + + {range_conditions} + + {final_range_predicate} + + s = s_next; + }} + // check final state + //assert({final_states_condition_body}, f"no match: {{s}}"); + let matched = {final_states_condition_body}; + // constrain extracted substrings to be in match range + let full_match = Sequence::new(start_range as u32, end_range as u32 - start_range as u32); + let full_match_end = full_match.end(); + for i in 0..{substr_length} {{ + let substring = pattern_match.substrings.get_unchecked(i); + let is_not_valid = i >= pattern_match.substrings.len(); + let index_check = substring.index >= full_match.index; + let length_check = substring.end() <= full_match_end; + let check = (index_check) | is_not_valid; + assert(check, f"Substring {{i}} range is out of bounds of the full match found"); + }} + + // extract substrings + let mut substrings: BoundedVec, {substr_length}> = BoundedVec::new(); + for i in 0..{substr_length} {{ + let substring = pattern_match.substrings.get_unchecked(i); + let mut extracted_substring = extract_substring(substring, input); + let mut len = substrings.len() + 1; + if i >= pattern_match.substrings.len() {{ + extracted_substring = BoundedVec::new(); + len = substrings.len(); + }} + substrings.len = len; + substrings.storage[i] = extracted_substring; + }} + + substrings +}} + +pub unconstrained fn __regex_match(input: [u8; N]) -> RegexMatch {{ + // regex: {regex_pattern} + let mut substrings: BoundedVec = BoundedVec::new(); + let mut current_substring = Sequence::default(); + let mut full_match = Sequence::default(); + + // "Previous" state + let mut s: Field = 0; + s = {table_access_255}; + // "Next"/upcoming state + let mut s_next: Field = 0; + + let mut consecutive_substr = 0; + let mut complete = false; + + for i in 0..input.len() {{ + let temp = input[i] as Field; + let mut reset = false; + s_next = {table_access_s_next}; + let potential_s_next = {table_access_s_next_temp}; + if s_next == 0 {{ + reset = true; + s = 0; + s_next = potential_s_next; + }} + // If a substring was in the making, but the state was reset + // we disregard previous progress because apparently it is invalid + if (reset & (consecutive_substr == 1)) {{ + current_substring = Sequence::default(); + consecutive_substr = 0; + }} + // Fill up substrings +{conditions} + s = s_next; + if complete == true {{ + break; + }} + }} + assert({final_states_condition_body}, f"no match: {{s}}"); + // Add pending substring that hasn't been added + if consecutive_substr == 1 {{ + substrings.push(current_substring); + full_match.length = input.len() - full_match.index; + }} + + // make masked array + let mut masked = [0; N]; + for i in 0..substrings.len() {{ + let substring = substrings.get(i); + let start_index = substring.index; + let end_index = start_index + substring.length; + for j in start_index..end_index {{ + masked[j] = input[j]; + }} + }} + + RegexMatch {{ masked, full_match, substrings }} +}} + +{COMMON_NOIR_CODE} +"#, + regex_pattern = escape_non_ascii( + ®ex_and_dfa + .regex_pattern + .replace('\n', "\\n") + .replace('\r', "\\r") + ), + table_access_255 = access_table("255", sparse_array), + table_access_s_next = access_table("s * 256 + temp", sparse_array), + table_access_s_next_temp = access_table("temp", sparse_array), + substr_length = regex_and_dfa.substrings.substring_ranges.len(), + ) + } else { + format!( + r#" +{table_str} +pub fn regex_match(input: [u8; N]) {{ + // regex: {regex_pattern} + let mut s = 0; + s = {table_access_255}; + for i in 0..input.len() {{ + let s_idx = s * {BYTE_SIZE} + input[i] as Field; + std::as_witness(s_idx); + s = {table_access_s_idx}; + }} + assert({final_states_condition_body}, f"no match: {{s}}"); +}}"#, + regex_pattern = escape_non_ascii( + ®ex_and_dfa + .regex_pattern + .replace('\n', "\\n") + .replace('\r', "\\r") + ), + table_access_255 = access_table("255", sparse_array), + table_access_s_idx = access_table("s_idx", sparse_array), + ) + }; + + format!( + r#" + {fn_body} + "# + ) + .trim() + .to_owned() +} + +/// Indents each line of the given string by a specified number of levels. +/// Each level adds four spaces to the beginning of non-whitespace lines. +fn indent(s: &str, level: usize) -> String { + let indent_str = " ".repeat(level); + s.split("\n") + .map(|s| { + if s.trim().is_empty() { + s.to_owned() + } else { + format!("{}{}", indent_str, s) + } + }) + .collect::>() + .join("\n") +} + +/// Access table by array index or sparse API index +fn access_table(s: &str, sparse: bool) -> String { + match sparse { + true => format!("table.get({})", s), + false => format!("table[{}]", s), + } +} + +// Noir does not like non-ascii comments so use this to show regex +fn escape_non_ascii(input: &str) -> String { + input + .chars() + .map(|c| { + if c.is_ascii() { + c.to_string() + } else { + format!("\\u{{{:04x}}}", c as u32) + } + }) + .collect() +} + +#[derive(Debug, Clone)] +struct StateMatch { + single: usize, + match_vec: Vec, + s: bool, +} + +fn organize_states(states: &BTreeSet<(usize, usize)>) -> Vec { + use std::collections::{HashMap, HashSet}; + + // Create maps for forward and reverse connections + let mut s_to_next: HashMap> = HashMap::new(); + let mut next_to_s: HashMap> = HashMap::new(); + + for &(s, next) in states { + s_to_next.entry(s).or_default().push(next); + next_to_s.entry(next).or_default().push(s); + } + + // Helper function to get sorted unique values + let get_unique_sorted = |v: &Vec| -> Vec { + let mut unique: Vec = v.iter().copied().collect(); + unique.sort_unstable(); + unique.dedup(); + unique + }; + + let mut result = Vec::new(); + let mut covered = HashSet::new(); + + // First pass: Find nodes that have multiple outgoing edges + for (&num, matches_found) in &s_to_next { + let matches = get_unique_sorted(matches_found); + if matches.len() > 1 { + result.push(StateMatch { + single: num, + match_vec: matches.clone(), + s: true, + }); + for &m in &matches { + covered.insert((num, m)); + } + } + } + + // Second pass: Find remaining edges that need to be covered + let mut uncovered = states + .iter() + .filter(|&&(s, next)| !covered.contains(&(s, next))) + .collect::>(); + + // Group remaining by destination + let mut dest_groups: HashMap> = HashMap::new(); + for &(s, next) in &uncovered { + dest_groups.entry(*next).or_default().push(*s); + } + + // Add any groups with multiple sources + for (dest, sources) in dest_groups { + let mut sources = sources; + sources.sort_unstable(); + result.push(StateMatch { + single: dest, + match_vec: sources, + s: false, + }); + } + + // Sort results by single value + result.sort_by_key(|sm| sm.single); + + result +} + +fn ranges_to_predicate(states: Vec, index: usize) -> String { + let cases = states + .iter() + .map(|state| { + let (single_label, matches_label) = match state.s { + true => ("s", "s_next"), + false => ("s_next", "s"), + }; + let matches_str = state + .match_vec + .iter() + .map(|state| format!("({} == {})", matches_label, state)) + .join(" | "); + format!("({} == {}) & ({})", single_label, state.single, matches_str) + }) + .join(",\n\t"); + indent( + &format!( + r#" +let range_{index} = pattern_match.substrings.get_unchecked({index}).in_range(i); +let case_{index} = [ + {cases} +].any(|case| case == true) | !range_{index}; +"# + ), + 2, + ) +} +const COMMON_NOIR_CODE: &str = r#" +pub struct Sequence { + index: u32, + length: u32, +} + +impl Sequence { + pub fn new(index: u32, length: u32) -> Self { + Self { index, length } + } + + pub fn default() -> Self { + Self { index: 0, length: 0 } + } + + pub fn end(self) -> u32 { + self.index + self.length + } + + pub fn in_range(self, index: u32) -> bool { + index >= self.index & index < self.end() + } +} + +pub struct RegexMatch { + masked: [u8; INPUT_LENGTH], + full_match: Sequence, + substrings: BoundedVec, +} + +pub fn extract_substring( + substring_sequence: Sequence, + input: [u8; INPUT_LENGTH], +) -> BoundedVec { + let mut substring: BoundedVec = unsafe { __extract_substring(substring_sequence, input) }; + assert(substring_sequence.length == substring.len(), "length mismatch"); + for i in 0..MAX_SUBSTRING_LENGTH { + // hack for index to never exceed array bounds + // must be constrained to be true when matching is required to prevent 0's passing when shouldn't + // @dev while this adds constraints in worse case it can be more efficient if MAX_SUBSTRING_LENGTH < INPUT_LENGTH + let input_range_check = substring_sequence.index + i < INPUT_LENGTH; + let index = (substring_sequence.index + i) as Field * input_range_check as Field; + + // range where input should match substring + let sequence_range_check = i >= substring_sequence.length; + + // constrain array construction if in range + let expected_byte = input[index]; + let byte = substring.get_unchecked(i); + let matched = (expected_byte as Field == byte as Field); + assert(matched | sequence_range_check, "incorrect substring construction"); + } + substring +} + +unconstrained fn __extract_substring( + substring_sequence: Sequence, + input: [u8; INPUT_LENGTH], +) -> BoundedVec { + let mut substring: BoundedVec = BoundedVec::new(); + for i in 0..substring_sequence.length { + let byte = input[substring_sequence.index + i]; + substring.push(byte); + } + substring +} + "#; diff --git a/packages/compiler/src/q.rs b/packages/compiler/src/q.rs new file mode 100644 index 00000000..d81affe5 --- /dev/null +++ b/packages/compiler/src/q.rs @@ -0,0 +1,406 @@ +use std::{ + collections::{BTreeSet, HashMap, HashSet}, + fs::File, + io::Write, + iter::FromIterator, + path::Path, +}; + +use comptime::{FieldElement, SparseArray}; +use itertools::Itertools; + +use crate::structs::RegexAndDFA; + +const ACCEPT_STATE_ID: &str = "accept"; +const BYTE_SIZE: u32 = 256; // u8 size + +pub fn gen_noir_fn( + regex_and_dfa: &RegexAndDFA, + path: &Path, + gen_substrs: bool, + sparse_array: Option, +) -> Result<(), std::io::Error> { + println!("{}", regex_and_dfa.dfa); + let use_sparse = sparse_array.unwrap_or(false); + let noir_fn = to_noir_fn(regex_and_dfa, gen_substrs, use_sparse); + let mut file = File::create(path)?; + file.write_all(noir_fn.as_bytes())?; + file.flush()?; + Ok(()) +} + +/// Generates Noir code based on the DFA and whether a substring should be extracted. +/// +/// # Arguments +/// +/// * `regex_and_dfa` - The `RegexAndDFA` struct containing the regex pattern and DFA. +/// * `gen_substrs` - A boolean indicating whether to generate substrings. +/// +/// # Returns +/// +/// A `String` that contains the Noir code +fn to_noir_fn(regex_and_dfa: &RegexAndDFA, gen_substrs: bool, sparse_array: bool) -> String { + // Multiple accepting states are not supported + // This is a vector nonetheless, to support an extra accepting state we'll use + // to allow any character occurrences after the original accepting state + let mut accept_state_ids: Vec = { + let accept_states = regex_and_dfa + .dfa + .states + .iter() + .filter(|s| s.state_type == ACCEPT_STATE_ID) + .map(|s| s.state_id) + .collect_vec(); + assert!( + accept_states.len() == 1, + "there should be exactly 1 accept state" + ); + accept_states + }; + + // curr_state + char_code -> next_state + let mut rows: Vec<(usize, u8, usize)> = vec![]; + + // $ support + // In case that there is no end_anchor, we add an additional accepting state to which any + // character occurence after the accepting state will go. + // This needs to be a new state, otherwise substring extraction won't work correctly + if !regex_and_dfa.has_end_anchor { + let original_accept_id = accept_state_ids.get(0).unwrap().clone(); + // Create a new highest state + let extra_accept_id = regex_and_dfa + .dfa + .states + .iter() + .max_by_key(|state| state.state_id) + .map(|state| state.state_id) + .unwrap() + + 1; + accept_state_ids.push(extra_accept_id); + for char_code in 0..=254 { + rows.push((original_accept_id, char_code, extra_accept_id)); + rows.push((extra_accept_id, char_code, extra_accept_id)); + } + } + + for state in regex_and_dfa.dfa.states.iter() { + for (&tran_next_state_id, tran) in &state.transitions { + for &char_code in tran { + rows.push((state.state_id, char_code, tran_next_state_id)); + } + } + } + + let mut table_size = BYTE_SIZE as usize * regex_and_dfa.dfa.states.len(); + if !regex_and_dfa.has_end_anchor { + table_size += BYTE_SIZE as usize; + } + + + + // make sparse array in comptime + + // let sparse_array_str = sparse_array.to_noir_string(None); + + // substring_ranges contains the transitions that belong to the substring + let substr_ranges: &Vec> = ®ex_and_dfa.substrings.substring_ranges; + // Note: substring_boundaries is only filled if the substring info is coming from decomposed setting + // and will be empty in the raw setting (using json file for substr transitions). This is why substring_ranges is used here + + let final_states_condition_body = accept_state_ids + .iter() + .map(|id| format!("(s == {id})")) + .collect_vec() + .join(" | "); + let end_states_condition_body = match accept_state_ids.len() == 1 { + true => format!( + "(s == {}) & (s_next == {})", + accept_state_ids[0], accept_state_ids[0] + ), + false => format!( + "(s == {}) & (s_next == {})", + accept_state_ids[0], accept_state_ids[1] + ), + }; + + let end_range_condition = accept_state_ids + .iter() + .map(|id| format!("(s_next == {})", id)) + .join(" | "); + + let range_conditions = substr_ranges + .iter() + .enumerate() + .map(|(index, range)| { + let sorted = organize_states(range); + ranges_to_predicate(sorted, index) + }) + .join(""); + + let final_range_predicate = { + let mut cases = Vec::new(); + for i in 0..substr_ranges.len() { + cases.push(format!("case_{}", i)); + } + let case_str = cases.join(", "); + indent( + &format!( + r#" +let substring_range_check = [{case_str}] + .all(|case| case == true); + +assert(substring_range_check, "substr array ranges wrong"); + "# + ), + 2, + ) + }; + + let fn_body = if gen_substrs { + let mut first_condition = true; + + let mut conditions = substr_ranges + .iter() + .map(|range_set| { + // Combine the range conditions into a single line using `|` operator + let range_conditions = range_set + .iter() + .map(|(range_start, range_end)| { + format!("(s == {range_start}) & (s_next == {range_end})") + }) + .collect::>() + .join(" | "); + + // For the first condition, use `if`, for others, use `else if` + let (start_part, start_index) = if first_condition { + first_condition = false; + let start_index_text = format!( + "if (consecutive_substr == 0) {{ + full_match.index = i; + current_substring.index = i; + }};\n" + ); + ("if", start_index_text) + } else { + ("else if", format!("")) + }; + + // The body of the condition handling substring creation/updating + format!( + "{start_part} ({range_conditions}) {{ + {start_index} + current_substring.length += 1; + consecutive_substr = 1; +}}" + ) + }) + .collect::>() + .join("\n"); + + // Add the final else if for resetting the consecutive_substr + let final_conditions = format!( + "{conditions} else if ((consecutive_substr == 1) & (s_next == 0)) {{ + current_substring = Sequence::default(); + full_match = Sequence::default(); + substrings = BoundedVec::new(); + consecutive_substr = 0; +}} else if {end_states_condition_body} {{ + full_match.length = i - full_match.index + 1; + complete = true; +}} else if (consecutive_substr == 1) {{ + // The substring is done so \"save\" it + substrings.push(current_substring); + // reset the substring holder for next use + current_substring = Sequence::default(); + consecutive_substr = 0; +}}" + ); + + conditions = indent(&final_conditions, 2); // Indent twice to align with the for loop's body + + format!( + r#" +{table_str} +pub fn regex_match(input: [u8; N]) -> BoundedVec, {substr_length}> {{ + let pattern_match = unsafe {{ __regex_match(input) }}; + + // "Previous" state + let mut s: Field = 0; + s = {table_access_255}; + // "Next"/upcoming state + let mut s_next: Field = 0; + let mut start_range = 0; + let mut end_range = 0; + + // check the match + for i in 0..N {{ + // state transition + let temp = input[i] as Field; + s_next = {table_access_s_next}; + let potential_s_next = {table_access_s_next_temp}; + if s_next == 0 {{ + s = 0; + s_next = potential_s_next; + }} + std::as_witness(s_next); + + // range conditions for substring matches + if ((start_range == 0) & (end_range == 0)) {{ + start_range = i as Field; + }} + //let switch = (start_range + end_range != 0) as Field; + //let keep_start_case = start_range - (start_range * switch); + //let set_start_i_case = (1 - switch) * i as Field; + //start_range = keep_start_case + set_start_i_case; + //if (({end_range_condition}) & (end_range == 0)) {{ + // end_range = i as Field + 1; + //}} + if (({end_states_condition_body}) & (end_range == 0)) {{ + end_range = i as Field + 1; + }} + + {range_conditions} + + {final_range_predicate} + + s = s_next; + }} + // check final state + //assert({final_states_condition_body}, f"no match: {{s}}"); + let matched = {final_states_condition_body}; + // constrain extracted substrings to be in match range + let full_match = Sequence::new(start_range as u32, end_range as u32 - start_range as u32); + let full_match_end = full_match.end(); + for i in 0..{substr_length} {{ + let substring = pattern_match.substrings.get_unchecked(i); + let is_not_valid = i >= pattern_match.substrings.len(); + let index_check = substring.index >= full_match.index; + let length_check = substring.end() <= full_match_end; + let check = (index_check) | is_not_valid; + assert(check, f"Substring {{i}} range is out of bounds of the full match found"); + }} + + // extract substrings + let mut substrings: BoundedVec, {substr_length}> = BoundedVec::new(); + for i in 0..{substr_length} {{ + let substring = pattern_match.substrings.get_unchecked(i); + let mut extracted_substring = extract_substring(substring, input); + let mut len = substrings.len() + 1; + if i >= pattern_match.substrings.len() {{ + extracted_substring = BoundedVec::new(); + len = substrings.len(); + }} + substrings.len = len; + substrings.storage[i] = extracted_substring; + }} + + substrings +}} + +pub unconstrained fn __regex_match(input: [u8; N]) -> RegexMatch {{ + // regex: {regex_pattern} + let mut substrings: BoundedVec = BoundedVec::new(); + let mut current_substring = Sequence::default(); + let mut full_match = Sequence::default(); + + // "Previous" state + let mut s: Field = 0; + s = {table_access_255}; + // "Next"/upcoming state + let mut s_next: Field = 0; + + let mut consecutive_substr = 0; + let mut complete = false; + + for i in 0..input.len() {{ + let temp = input[i] as Field; + let mut reset = false; + s_next = {table_access_s_next}; + let potential_s_next = {table_access_s_next_temp}; + if s_next == 0 {{ + reset = true; + s = 0; + s_next = potential_s_next; + }} + // If a substring was in the making, but the state was reset + // we disregard previous progress because apparently it is invalid + if (reset & (consecutive_substr == 1)) {{ + current_substring = Sequence::default(); + consecutive_substr = 0; + }} + // Fill up substrings +{conditions} + s = s_next; + if complete == true {{ + break; + }} + }} + assert({final_states_condition_body}, f"no match: {{s}}"); + // Add pending substring that hasn't been added + if consecutive_substr == 1 {{ + substrings.push(current_substring); + full_match.length = input.len() - full_match.index; + }} + + // make masked array + let mut masked = [0; N]; + for i in 0..substrings.len() {{ + let substring = substrings.get(i); + let start_index = substring.index; + let end_index = start_index + substring.length; + for j in start_index..end_index {{ + masked[j] = input[j]; + }} + }} + + RegexMatch {{ masked, full_match, substrings }} +}} + +{COMMON_NOIR_CODE} +"#, + regex_pattern = escape_non_ascii( + ®ex_and_dfa + .regex_pattern + .replace('\n', "\\n") + .replace('\r', "\\r") + ), + table_access_255 = access_table("255", sparse_array), + table_access_s_next = access_table("s * 256 + temp", sparse_array), + table_access_s_next_temp = access_table("temp", sparse_array), + substr_length = regex_and_dfa.substrings.substring_ranges.len(), + ) + } else { + format!( + r#" +{table_str} +pub fn regex_match(input: [u8; N]) {{ + // regex: {regex_pattern} + let mut s = 0; + s = {table_access_255}; + for i in 0..input.len() {{ + let s_idx = s * {BYTE_SIZE} + input[i] as Field; + std::as_witness(s_idx); + s = {table_access_s_idx}; + }} + assert({final_states_condition_body}, f"no match: {{s}}"); +}}"#, + regex_pattern = escape_non_ascii( + ®ex_and_dfa + .regex_pattern + .replace('\n', "\\n") + .replace('\r', "\\r") + ), + table_access_255 = access_table("255", sparse_array), + table_access_s_idx = access_table("s_idx", sparse_array), + ) + }; + + format!( + r#" + {fn_body} + "# + ) + .trim() + .to_owned() +} + diff --git a/packages/compiler/src/structs.rs b/packages/compiler/src/structs.rs index 2fcdc78f..337b14e3 100644 --- a/packages/compiler/src/structs.rs +++ b/packages/compiler/src/structs.rs @@ -54,3 +54,74 @@ pub struct RegexAndDFA { pub struct SubstringDefinitionsJson { pub transitions: Vec>, } + +impl std::fmt::Display for DFAStateNode { + fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result { + let state_type = match self.state_type.as_str() { + "start" => "START", + "accept" => "ACCEPT", + _ => "NORMAL", + }; + + writeln!(f, "State {} ({})", self.state_id, state_type)?; + + for (dest, chars) in &self.transitions { + let mut ranges = Vec::new(); + let mut current_range: Option<(u8, u8)> = None; + let mut sorted_chars: Vec = chars.iter().copied().collect(); + sorted_chars.sort_unstable(); + + for &b in &sorted_chars { + match current_range { + Some((start, end)) if b == end + 1 => current_range = Some((start, b)), + Some((start, end)) => { + ranges.push((start, end)); + current_range = Some((b, b)); + } + None => current_range = Some((b, b)), + } + } + if let Some(range) = current_range { + ranges.push(range); + } + + let transitions: Vec = ranges + .iter() + .map(|(start, end)| { + let start_char = byte_to_char(*start); + let end_char = byte_to_char(*end); + if start == end { + start_char + } else { + format!("{}-{}", start_char, end_char) + } + }) + .collect(); + + writeln!(f, "└── [{}] → State {}", transitions.join(", "), dest)?; + } + + Ok(()) + } +} + +impl std::fmt::Display for DFAGraph { + fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result { + for state in &self.states { + write!(f, "{}", state)?; + writeln!(f, "{}", "-".repeat(50))?; + } + Ok(()) + } +} + +fn byte_to_char(b: u8) -> String { + match b { + 0x09 => "\\t".into(), + 0x0A => "\\n".into(), + 0x0D => "\\r".into(), + 0x20 => "␣".into(), + 0x21..=0x7E => format!("{}", b as char), + _ => format!("0x{:02X}", b), + } +} diff --git a/packages/noir/Nargo.toml b/packages/noir/Nargo.toml new file mode 100644 index 00000000..4239b8a1 --- /dev/null +++ b/packages/noir/Nargo.toml @@ -0,0 +1,9 @@ +[package] +name = "zkregex" +type = "lib" +authors = [""] +compiler_version = ">=1.0.0" + +[dependencies] +base64 = { tag = "v0.3.1", git = "https://github.com/noir-lang/noir_base64" } +# sparse_array = { git = "https://github.com/jp4g/sparse_array/", tag = "feat/comptime-codegen"} \ No newline at end of file diff --git a/packages/noir/README.md b/packages/noir/README.md new file mode 100644 index 00000000..1a68b6b0 --- /dev/null +++ b/packages/noir/README.md @@ -0,0 +1 @@ +# ZK-Regex.nr \ No newline at end of file diff --git a/packages/noir/regex_gen.sh b/packages/noir/regex_gen.sh new file mode 100755 index 00000000..bd30155f --- /dev/null +++ b/packages/noir/regex_gen.sh @@ -0,0 +1,39 @@ +#!/bin/bash +CURRENT_DIR="$(pwd)" +SCRIPT_DIR="$(dirname "$(realpath "$0")")" +cd $SCRIPT_DIR + +gen_regex() { + # Name of circuit to set + circuit_name=$(echo "${1%.json}" | sed -r 's/(^|_)(.)/\U\2/g') + # Name of file to set + file_name="${1%.json}.nr" + + # Gen regex with matching + # zk-regex decomposed \ + # -d "$1" \ + # --noir-file-path "../src/capture/$file_name" \ + # -t "$circuit_name" \ + # -g true \ + # --sparse-array false \ + # --use-common crate::common \ + # --force-match false + + zk-regex decomposed \ + -d "$1" \ + --noir-file-path "../src/match/$file_name" \ + -t "$circuit_name" \ + -g false \ + --sparse-array false \ + --use-common crate::common \ + --force-match false +} + +cd templates/ + +for file in *.json; do + gen_regex "$file" +done + + +cd $CURRENT_DIR \ No newline at end of file diff --git a/packages/noir/src/basic/basic.nr b/packages/noir/src/basic/basic.nr new file mode 100644 index 00000000..c0ddccae --- /dev/null +++ b/packages/noir/src/basic/basic.nr @@ -0,0 +1,540 @@ + +use crate::common::Sequence; + + +global table: [Field; 1280] = comptime { make_lookup_table() }; + +comptime fn make_lookup_table() -> [Field; 1280] { + let mut table = [0; 1280]; + table[3 * 256 + 0] = 4; + table[4 * 256 + 0] = 4; + table[3 * 256 + 1] = 4; + table[4 * 256 + 1] = 4; + table[3 * 256 + 2] = 4; + table[4 * 256 + 2] = 4; + table[3 * 256 + 3] = 4; + table[4 * 256 + 3] = 4; + table[3 * 256 + 4] = 4; + table[4 * 256 + 4] = 4; + table[3 * 256 + 5] = 4; + table[4 * 256 + 5] = 4; + table[3 * 256 + 6] = 4; + table[4 * 256 + 6] = 4; + table[3 * 256 + 7] = 4; + table[4 * 256 + 7] = 4; + table[3 * 256 + 8] = 4; + table[4 * 256 + 8] = 4; + table[3 * 256 + 9] = 4; + table[4 * 256 + 9] = 4; + table[3 * 256 + 10] = 4; + table[4 * 256 + 10] = 4; + table[3 * 256 + 11] = 4; + table[4 * 256 + 11] = 4; + table[3 * 256 + 12] = 4; + table[4 * 256 + 12] = 4; + table[3 * 256 + 13] = 4; + table[4 * 256 + 13] = 4; + table[3 * 256 + 14] = 4; + table[4 * 256 + 14] = 4; + table[3 * 256 + 15] = 4; + table[4 * 256 + 15] = 4; + table[3 * 256 + 16] = 4; + table[4 * 256 + 16] = 4; + table[3 * 256 + 17] = 4; + table[4 * 256 + 17] = 4; + table[3 * 256 + 18] = 4; + table[4 * 256 + 18] = 4; + table[3 * 256 + 19] = 4; + table[4 * 256 + 19] = 4; + table[3 * 256 + 20] = 4; + table[4 * 256 + 20] = 4; + table[3 * 256 + 21] = 4; + table[4 * 256 + 21] = 4; + table[3 * 256 + 22] = 4; + table[4 * 256 + 22] = 4; + table[3 * 256 + 23] = 4; + table[4 * 256 + 23] = 4; + table[3 * 256 + 24] = 4; + table[4 * 256 + 24] = 4; + table[3 * 256 + 25] = 4; + table[4 * 256 + 25] = 4; + table[3 * 256 + 26] = 4; + table[4 * 256 + 26] = 4; + table[3 * 256 + 27] = 4; + table[4 * 256 + 27] = 4; + table[3 * 256 + 28] = 4; + table[4 * 256 + 28] = 4; + table[3 * 256 + 29] = 4; + table[4 * 256 + 29] = 4; + table[3 * 256 + 30] = 4; + table[4 * 256 + 30] = 4; + table[3 * 256 + 31] = 4; + table[4 * 256 + 31] = 4; + table[3 * 256 + 32] = 4; + table[4 * 256 + 32] = 4; + table[3 * 256 + 33] = 4; + table[4 * 256 + 33] = 4; + table[3 * 256 + 34] = 4; + table[4 * 256 + 34] = 4; + table[3 * 256 + 35] = 4; + table[4 * 256 + 35] = 4; + table[3 * 256 + 36] = 4; + table[4 * 256 + 36] = 4; + table[3 * 256 + 37] = 4; + table[4 * 256 + 37] = 4; + table[3 * 256 + 38] = 4; + table[4 * 256 + 38] = 4; + table[3 * 256 + 39] = 4; + table[4 * 256 + 39] = 4; + table[3 * 256 + 40] = 4; + table[4 * 256 + 40] = 4; + table[3 * 256 + 41] = 4; + table[4 * 256 + 41] = 4; + table[3 * 256 + 42] = 4; + table[4 * 256 + 42] = 4; + table[3 * 256 + 43] = 4; + table[4 * 256 + 43] = 4; + table[3 * 256 + 44] = 4; + table[4 * 256 + 44] = 4; + table[3 * 256 + 45] = 4; + table[4 * 256 + 45] = 4; + table[3 * 256 + 46] = 4; + table[4 * 256 + 46] = 4; + table[3 * 256 + 47] = 4; + table[4 * 256 + 47] = 4; + table[3 * 256 + 48] = 4; + table[4 * 256 + 48] = 4; + table[3 * 256 + 49] = 4; + table[4 * 256 + 49] = 4; + table[3 * 256 + 50] = 4; + table[4 * 256 + 50] = 4; + table[3 * 256 + 51] = 4; + table[4 * 256 + 51] = 4; + table[3 * 256 + 52] = 4; + table[4 * 256 + 52] = 4; + table[3 * 256 + 53] = 4; + table[4 * 256 + 53] = 4; + table[3 * 256 + 54] = 4; + table[4 * 256 + 54] = 4; + table[3 * 256 + 55] = 4; + table[4 * 256 + 55] = 4; + table[3 * 256 + 56] = 4; + table[4 * 256 + 56] = 4; + table[3 * 256 + 57] = 4; + table[4 * 256 + 57] = 4; + table[3 * 256 + 58] = 4; + table[4 * 256 + 58] = 4; + table[3 * 256 + 59] = 4; + table[4 * 256 + 59] = 4; + table[3 * 256 + 60] = 4; + table[4 * 256 + 60] = 4; + table[3 * 256 + 61] = 4; + table[4 * 256 + 61] = 4; + table[3 * 256 + 62] = 4; + table[4 * 256 + 62] = 4; + table[3 * 256 + 63] = 4; + table[4 * 256 + 63] = 4; + table[3 * 256 + 64] = 4; + table[4 * 256 + 64] = 4; + table[3 * 256 + 65] = 4; + table[4 * 256 + 65] = 4; + table[3 * 256 + 66] = 4; + table[4 * 256 + 66] = 4; + table[3 * 256 + 67] = 4; + table[4 * 256 + 67] = 4; + table[3 * 256 + 68] = 4; + table[4 * 256 + 68] = 4; + table[3 * 256 + 69] = 4; + table[4 * 256 + 69] = 4; + table[3 * 256 + 70] = 4; + table[4 * 256 + 70] = 4; + table[3 * 256 + 71] = 4; + table[4 * 256 + 71] = 4; + table[3 * 256 + 72] = 4; + table[4 * 256 + 72] = 4; + table[3 * 256 + 73] = 4; + table[4 * 256 + 73] = 4; + table[3 * 256 + 74] = 4; + table[4 * 256 + 74] = 4; + table[3 * 256 + 75] = 4; + table[4 * 256 + 75] = 4; + table[3 * 256 + 76] = 4; + table[4 * 256 + 76] = 4; + table[3 * 256 + 77] = 4; + table[4 * 256 + 77] = 4; + table[3 * 256 + 78] = 4; + table[4 * 256 + 78] = 4; + table[3 * 256 + 79] = 4; + table[4 * 256 + 79] = 4; + table[3 * 256 + 80] = 4; + table[4 * 256 + 80] = 4; + table[3 * 256 + 81] = 4; + table[4 * 256 + 81] = 4; + table[3 * 256 + 82] = 4; + table[4 * 256 + 82] = 4; + table[3 * 256 + 83] = 4; + table[4 * 256 + 83] = 4; + table[3 * 256 + 84] = 4; + table[4 * 256 + 84] = 4; + table[3 * 256 + 85] = 4; + table[4 * 256 + 85] = 4; + table[3 * 256 + 86] = 4; + table[4 * 256 + 86] = 4; + table[3 * 256 + 87] = 4; + table[4 * 256 + 87] = 4; + table[3 * 256 + 88] = 4; + table[4 * 256 + 88] = 4; + table[3 * 256 + 89] = 4; + table[4 * 256 + 89] = 4; + table[3 * 256 + 90] = 4; + table[4 * 256 + 90] = 4; + table[3 * 256 + 91] = 4; + table[4 * 256 + 91] = 4; + table[3 * 256 + 92] = 4; + table[4 * 256 + 92] = 4; + table[3 * 256 + 93] = 4; + table[4 * 256 + 93] = 4; + table[3 * 256 + 94] = 4; + table[4 * 256 + 94] = 4; + table[3 * 256 + 95] = 4; + table[4 * 256 + 95] = 4; + table[3 * 256 + 96] = 4; + table[4 * 256 + 96] = 4; + table[3 * 256 + 97] = 4; + table[4 * 256 + 97] = 4; + table[3 * 256 + 98] = 4; + table[4 * 256 + 98] = 4; + table[3 * 256 + 99] = 4; + table[4 * 256 + 99] = 4; + table[3 * 256 + 100] = 4; + table[4 * 256 + 100] = 4; + table[3 * 256 + 101] = 4; + table[4 * 256 + 101] = 4; + table[3 * 256 + 102] = 4; + table[4 * 256 + 102] = 4; + table[3 * 256 + 103] = 4; + table[4 * 256 + 103] = 4; + table[3 * 256 + 104] = 4; + table[4 * 256 + 104] = 4; + table[3 * 256 + 105] = 4; + table[4 * 256 + 105] = 4; + table[3 * 256 + 106] = 4; + table[4 * 256 + 106] = 4; + table[3 * 256 + 107] = 4; + table[4 * 256 + 107] = 4; + table[3 * 256 + 108] = 4; + table[4 * 256 + 108] = 4; + table[3 * 256 + 109] = 4; + table[4 * 256 + 109] = 4; + table[3 * 256 + 110] = 4; + table[4 * 256 + 110] = 4; + table[3 * 256 + 111] = 4; + table[4 * 256 + 111] = 4; + table[3 * 256 + 112] = 4; + table[4 * 256 + 112] = 4; + table[3 * 256 + 113] = 4; + table[4 * 256 + 113] = 4; + table[3 * 256 + 114] = 4; + table[4 * 256 + 114] = 4; + table[3 * 256 + 115] = 4; + table[4 * 256 + 115] = 4; + table[3 * 256 + 116] = 4; + table[4 * 256 + 116] = 4; + table[3 * 256 + 117] = 4; + table[4 * 256 + 117] = 4; + table[3 * 256 + 118] = 4; + table[4 * 256 + 118] = 4; + table[3 * 256 + 119] = 4; + table[4 * 256 + 119] = 4; + table[3 * 256 + 120] = 4; + table[4 * 256 + 120] = 4; + table[3 * 256 + 121] = 4; + table[4 * 256 + 121] = 4; + table[3 * 256 + 122] = 4; + table[4 * 256 + 122] = 4; + table[3 * 256 + 123] = 4; + table[4 * 256 + 123] = 4; + table[3 * 256 + 124] = 4; + table[4 * 256 + 124] = 4; + table[3 * 256 + 125] = 4; + table[4 * 256 + 125] = 4; + table[3 * 256 + 126] = 4; + table[4 * 256 + 126] = 4; + table[3 * 256 + 127] = 4; + table[4 * 256 + 127] = 4; + table[3 * 256 + 128] = 4; + table[4 * 256 + 128] = 4; + table[3 * 256 + 129] = 4; + table[4 * 256 + 129] = 4; + table[3 * 256 + 130] = 4; + table[4 * 256 + 130] = 4; + table[3 * 256 + 131] = 4; + table[4 * 256 + 131] = 4; + table[3 * 256 + 132] = 4; + table[4 * 256 + 132] = 4; + table[3 * 256 + 133] = 4; + table[4 * 256 + 133] = 4; + table[3 * 256 + 134] = 4; + table[4 * 256 + 134] = 4; + table[3 * 256 + 135] = 4; + table[4 * 256 + 135] = 4; + table[3 * 256 + 136] = 4; + table[4 * 256 + 136] = 4; + table[3 * 256 + 137] = 4; + table[4 * 256 + 137] = 4; + table[3 * 256 + 138] = 4; + table[4 * 256 + 138] = 4; + table[3 * 256 + 139] = 4; + table[4 * 256 + 139] = 4; + table[3 * 256 + 140] = 4; + table[4 * 256 + 140] = 4; + table[3 * 256 + 141] = 4; + table[4 * 256 + 141] = 4; + table[3 * 256 + 142] = 4; + table[4 * 256 + 142] = 4; + table[3 * 256 + 143] = 4; + table[4 * 256 + 143] = 4; + table[3 * 256 + 144] = 4; + table[4 * 256 + 144] = 4; + table[3 * 256 + 145] = 4; + table[4 * 256 + 145] = 4; + table[3 * 256 + 146] = 4; + table[4 * 256 + 146] = 4; + table[3 * 256 + 147] = 4; + table[4 * 256 + 147] = 4; + table[3 * 256 + 148] = 4; + table[4 * 256 + 148] = 4; + table[3 * 256 + 149] = 4; + table[4 * 256 + 149] = 4; + table[3 * 256 + 150] = 4; + table[4 * 256 + 150] = 4; + table[3 * 256 + 151] = 4; + table[4 * 256 + 151] = 4; + table[3 * 256 + 152] = 4; + table[4 * 256 + 152] = 4; + table[3 * 256 + 153] = 4; + table[4 * 256 + 153] = 4; + table[3 * 256 + 154] = 4; + table[4 * 256 + 154] = 4; + table[3 * 256 + 155] = 4; + table[4 * 256 + 155] = 4; + table[3 * 256 + 156] = 4; + table[4 * 256 + 156] = 4; + table[3 * 256 + 157] = 4; + table[4 * 256 + 157] = 4; + table[3 * 256 + 158] = 4; + table[4 * 256 + 158] = 4; + table[3 * 256 + 159] = 4; + table[4 * 256 + 159] = 4; + table[3 * 256 + 160] = 4; + table[4 * 256 + 160] = 4; + table[3 * 256 + 161] = 4; + table[4 * 256 + 161] = 4; + table[3 * 256 + 162] = 4; + table[4 * 256 + 162] = 4; + table[3 * 256 + 163] = 4; + table[4 * 256 + 163] = 4; + table[3 * 256 + 164] = 4; + table[4 * 256 + 164] = 4; + table[3 * 256 + 165] = 4; + table[4 * 256 + 165] = 4; + table[3 * 256 + 166] = 4; + table[4 * 256 + 166] = 4; + table[3 * 256 + 167] = 4; + table[4 * 256 + 167] = 4; + table[3 * 256 + 168] = 4; + table[4 * 256 + 168] = 4; + table[3 * 256 + 169] = 4; + table[4 * 256 + 169] = 4; + table[3 * 256 + 170] = 4; + table[4 * 256 + 170] = 4; + table[3 * 256 + 171] = 4; + table[4 * 256 + 171] = 4; + table[3 * 256 + 172] = 4; + table[4 * 256 + 172] = 4; + table[3 * 256 + 173] = 4; + table[4 * 256 + 173] = 4; + table[3 * 256 + 174] = 4; + table[4 * 256 + 174] = 4; + table[3 * 256 + 175] = 4; + table[4 * 256 + 175] = 4; + table[3 * 256 + 176] = 4; + table[4 * 256 + 176] = 4; + table[3 * 256 + 177] = 4; + table[4 * 256 + 177] = 4; + table[3 * 256 + 178] = 4; + table[4 * 256 + 178] = 4; + table[3 * 256 + 179] = 4; + table[4 * 256 + 179] = 4; + table[3 * 256 + 180] = 4; + table[4 * 256 + 180] = 4; + table[3 * 256 + 181] = 4; + table[4 * 256 + 181] = 4; + table[3 * 256 + 182] = 4; + table[4 * 256 + 182] = 4; + table[3 * 256 + 183] = 4; + table[4 * 256 + 183] = 4; + table[3 * 256 + 184] = 4; + table[4 * 256 + 184] = 4; + table[3 * 256 + 185] = 4; + table[4 * 256 + 185] = 4; + table[3 * 256 + 186] = 4; + table[4 * 256 + 186] = 4; + table[3 * 256 + 187] = 4; + table[4 * 256 + 187] = 4; + table[3 * 256 + 188] = 4; + table[4 * 256 + 188] = 4; + table[3 * 256 + 189] = 4; + table[4 * 256 + 189] = 4; + table[3 * 256 + 190] = 4; + table[4 * 256 + 190] = 4; + table[3 * 256 + 191] = 4; + table[4 * 256 + 191] = 4; + table[3 * 256 + 192] = 4; + table[4 * 256 + 192] = 4; + table[3 * 256 + 193] = 4; + table[4 * 256 + 193] = 4; + table[3 * 256 + 194] = 4; + table[4 * 256 + 194] = 4; + table[3 * 256 + 195] = 4; + table[4 * 256 + 195] = 4; + table[3 * 256 + 196] = 4; + table[4 * 256 + 196] = 4; + table[3 * 256 + 197] = 4; + table[4 * 256 + 197] = 4; + table[3 * 256 + 198] = 4; + table[4 * 256 + 198] = 4; + table[3 * 256 + 199] = 4; + table[4 * 256 + 199] = 4; + table[3 * 256 + 200] = 4; + table[4 * 256 + 200] = 4; + table[3 * 256 + 201] = 4; + table[4 * 256 + 201] = 4; + table[3 * 256 + 202] = 4; + table[4 * 256 + 202] = 4; + table[3 * 256 + 203] = 4; + table[4 * 256 + 203] = 4; + table[3 * 256 + 204] = 4; + table[4 * 256 + 204] = 4; + table[3 * 256 + 205] = 4; + table[4 * 256 + 205] = 4; + table[3 * 256 + 206] = 4; + table[4 * 256 + 206] = 4; + table[3 * 256 + 207] = 4; + table[4 * 256 + 207] = 4; + table[3 * 256 + 208] = 4; + table[4 * 256 + 208] = 4; + table[3 * 256 + 209] = 4; + table[4 * 256 + 209] = 4; + table[3 * 256 + 210] = 4; + table[4 * 256 + 210] = 4; + table[3 * 256 + 211] = 4; + table[4 * 256 + 211] = 4; + table[3 * 256 + 212] = 4; + table[4 * 256 + 212] = 4; + table[3 * 256 + 213] = 4; + table[4 * 256 + 213] = 4; + table[3 * 256 + 214] = 4; + table[4 * 256 + 214] = 4; + table[3 * 256 + 215] = 4; + table[4 * 256 + 215] = 4; + table[3 * 256 + 216] = 4; + table[4 * 256 + 216] = 4; + table[3 * 256 + 217] = 4; + table[4 * 256 + 217] = 4; + table[3 * 256 + 218] = 4; + table[4 * 256 + 218] = 4; + table[3 * 256 + 219] = 4; + table[4 * 256 + 219] = 4; + table[3 * 256 + 220] = 4; + table[4 * 256 + 220] = 4; + table[3 * 256 + 221] = 4; + table[4 * 256 + 221] = 4; + table[3 * 256 + 222] = 4; + table[4 * 256 + 222] = 4; + table[3 * 256 + 223] = 4; + table[4 * 256 + 223] = 4; + table[3 * 256 + 224] = 4; + table[4 * 256 + 224] = 4; + table[3 * 256 + 225] = 4; + table[4 * 256 + 225] = 4; + table[3 * 256 + 226] = 4; + table[4 * 256 + 226] = 4; + table[3 * 256 + 227] = 4; + table[4 * 256 + 227] = 4; + table[3 * 256 + 228] = 4; + table[4 * 256 + 228] = 4; + table[3 * 256 + 229] = 4; + table[4 * 256 + 229] = 4; + table[3 * 256 + 230] = 4; + table[4 * 256 + 230] = 4; + table[3 * 256 + 231] = 4; + table[4 * 256 + 231] = 4; + table[3 * 256 + 232] = 4; + table[4 * 256 + 232] = 4; + table[3 * 256 + 233] = 4; + table[4 * 256 + 233] = 4; + table[3 * 256 + 234] = 4; + table[4 * 256 + 234] = 4; + table[3 * 256 + 235] = 4; + table[4 * 256 + 235] = 4; + table[3 * 256 + 236] = 4; + table[4 * 256 + 236] = 4; + table[3 * 256 + 237] = 4; + table[4 * 256 + 237] = 4; + table[3 * 256 + 238] = 4; + table[4 * 256 + 238] = 4; + table[3 * 256 + 239] = 4; + table[4 * 256 + 239] = 4; + table[3 * 256 + 240] = 4; + table[4 * 256 + 240] = 4; + table[3 * 256 + 241] = 4; + table[4 * 256 + 241] = 4; + table[3 * 256 + 242] = 4; + table[4 * 256 + 242] = 4; + table[3 * 256 + 243] = 4; + table[4 * 256 + 243] = 4; + table[3 * 256 + 244] = 4; + table[4 * 256 + 244] = 4; + table[3 * 256 + 245] = 4; + table[4 * 256 + 245] = 4; + table[3 * 256 + 246] = 4; + table[4 * 256 + 246] = 4; + table[3 * 256 + 247] = 4; + table[4 * 256 + 247] = 4; + table[3 * 256 + 248] = 4; + table[4 * 256 + 248] = 4; + table[3 * 256 + 249] = 4; + table[4 * 256 + 249] = 4; + table[3 * 256 + 250] = 4; + table[4 * 256 + 250] = 4; + table[3 * 256 + 251] = 4; + table[4 * 256 + 251] = 4; + table[3 * 256 + 252] = 4; + table[4 * 256 + 252] = 4; + table[3 * 256 + 253] = 4; + table[4 * 256 + 253] = 4; + table[3 * 256 + 254] = 4; + table[4 * 256 + 254] = 4; + table[0 * 256 + 97] = 1; + table[1 * 256 + 98] = 2; + table[2 * 256 + 99] = 3; + + table +} +pub fn regex_match(input: [u8; N]) -> bool { + // regex: abc + let mut s = 0; + s = table[255]; + for i in 0..input.len() { + let s_idx = s * 256 + input[i] as Field; + std::as_witness(s_idx); + s = table[s_idx]; + } + + let matched: bool = (s == 3) | (s == 4); + + matched +} + + \ No newline at end of file diff --git a/packages/noir/src/basic/body_hash.nr b/packages/noir/src/basic/body_hash.nr new file mode 100644 index 00000000..06a92469 --- /dev/null +++ b/packages/noir/src/basic/body_hash.nr @@ -0,0 +1,1610 @@ + +use crate::common::Sequence; + + +global table: [Field; 9216] = comptime { make_lookup_table() }; + +comptime fn make_lookup_table() -> [Field; 9216] { + let mut table = [0; 9216]; + table[34 * 256 + 0] = 35; + table[35 * 256 + 0] = 35; + table[34 * 256 + 1] = 35; + table[35 * 256 + 1] = 35; + table[34 * 256 + 2] = 35; + table[35 * 256 + 2] = 35; + table[34 * 256 + 3] = 35; + table[35 * 256 + 3] = 35; + table[34 * 256 + 4] = 35; + table[35 * 256 + 4] = 35; + table[34 * 256 + 5] = 35; + table[35 * 256 + 5] = 35; + table[34 * 256 + 6] = 35; + table[35 * 256 + 6] = 35; + table[34 * 256 + 7] = 35; + table[35 * 256 + 7] = 35; + table[34 * 256 + 8] = 35; + table[35 * 256 + 8] = 35; + table[34 * 256 + 9] = 35; + table[35 * 256 + 9] = 35; + table[34 * 256 + 10] = 35; + table[35 * 256 + 10] = 35; + table[34 * 256 + 11] = 35; + table[35 * 256 + 11] = 35; + table[34 * 256 + 12] = 35; + table[35 * 256 + 12] = 35; + table[34 * 256 + 13] = 35; + table[35 * 256 + 13] = 35; + table[34 * 256 + 14] = 35; + table[35 * 256 + 14] = 35; + table[34 * 256 + 15] = 35; + table[35 * 256 + 15] = 35; + table[34 * 256 + 16] = 35; + table[35 * 256 + 16] = 35; + table[34 * 256 + 17] = 35; + table[35 * 256 + 17] = 35; + table[34 * 256 + 18] = 35; + table[35 * 256 + 18] = 35; + table[34 * 256 + 19] = 35; + table[35 * 256 + 19] = 35; + table[34 * 256 + 20] = 35; + table[35 * 256 + 20] = 35; + table[34 * 256 + 21] = 35; + table[35 * 256 + 21] = 35; + table[34 * 256 + 22] = 35; + table[35 * 256 + 22] = 35; + table[34 * 256 + 23] = 35; + table[35 * 256 + 23] = 35; + table[34 * 256 + 24] = 35; + table[35 * 256 + 24] = 35; + table[34 * 256 + 25] = 35; + table[35 * 256 + 25] = 35; + table[34 * 256 + 26] = 35; + table[35 * 256 + 26] = 35; + table[34 * 256 + 27] = 35; + table[35 * 256 + 27] = 35; + table[34 * 256 + 28] = 35; + table[35 * 256 + 28] = 35; + table[34 * 256 + 29] = 35; + table[35 * 256 + 29] = 35; + table[34 * 256 + 30] = 35; + table[35 * 256 + 30] = 35; + table[34 * 256 + 31] = 35; + table[35 * 256 + 31] = 35; + table[34 * 256 + 32] = 35; + table[35 * 256 + 32] = 35; + table[34 * 256 + 33] = 35; + table[35 * 256 + 33] = 35; + table[34 * 256 + 34] = 35; + table[35 * 256 + 34] = 35; + table[34 * 256 + 35] = 35; + table[35 * 256 + 35] = 35; + table[34 * 256 + 36] = 35; + table[35 * 256 + 36] = 35; + table[34 * 256 + 37] = 35; + table[35 * 256 + 37] = 35; + table[34 * 256 + 38] = 35; + table[35 * 256 + 38] = 35; + table[34 * 256 + 39] = 35; + table[35 * 256 + 39] = 35; + table[34 * 256 + 40] = 35; + table[35 * 256 + 40] = 35; + table[34 * 256 + 41] = 35; + table[35 * 256 + 41] = 35; + table[34 * 256 + 42] = 35; + table[35 * 256 + 42] = 35; + table[34 * 256 + 43] = 35; + table[35 * 256 + 43] = 35; + table[34 * 256 + 44] = 35; + table[35 * 256 + 44] = 35; + table[34 * 256 + 45] = 35; + table[35 * 256 + 45] = 35; + table[34 * 256 + 46] = 35; + table[35 * 256 + 46] = 35; + table[34 * 256 + 47] = 35; + table[35 * 256 + 47] = 35; + table[34 * 256 + 48] = 35; + table[35 * 256 + 48] = 35; + table[34 * 256 + 49] = 35; + table[35 * 256 + 49] = 35; + table[34 * 256 + 50] = 35; + table[35 * 256 + 50] = 35; + table[34 * 256 + 51] = 35; + table[35 * 256 + 51] = 35; + table[34 * 256 + 52] = 35; + table[35 * 256 + 52] = 35; + table[34 * 256 + 53] = 35; + table[35 * 256 + 53] = 35; + table[34 * 256 + 54] = 35; + table[35 * 256 + 54] = 35; + table[34 * 256 + 55] = 35; + table[35 * 256 + 55] = 35; + table[34 * 256 + 56] = 35; + table[35 * 256 + 56] = 35; + table[34 * 256 + 57] = 35; + table[35 * 256 + 57] = 35; + table[34 * 256 + 58] = 35; + table[35 * 256 + 58] = 35; + table[34 * 256 + 59] = 35; + table[35 * 256 + 59] = 35; + table[34 * 256 + 60] = 35; + table[35 * 256 + 60] = 35; + table[34 * 256 + 61] = 35; + table[35 * 256 + 61] = 35; + table[34 * 256 + 62] = 35; + table[35 * 256 + 62] = 35; + table[34 * 256 + 63] = 35; + table[35 * 256 + 63] = 35; + table[34 * 256 + 64] = 35; + table[35 * 256 + 64] = 35; + table[34 * 256 + 65] = 35; + table[35 * 256 + 65] = 35; + table[34 * 256 + 66] = 35; + table[35 * 256 + 66] = 35; + table[34 * 256 + 67] = 35; + table[35 * 256 + 67] = 35; + table[34 * 256 + 68] = 35; + table[35 * 256 + 68] = 35; + table[34 * 256 + 69] = 35; + table[35 * 256 + 69] = 35; + table[34 * 256 + 70] = 35; + table[35 * 256 + 70] = 35; + table[34 * 256 + 71] = 35; + table[35 * 256 + 71] = 35; + table[34 * 256 + 72] = 35; + table[35 * 256 + 72] = 35; + table[34 * 256 + 73] = 35; + table[35 * 256 + 73] = 35; + table[34 * 256 + 74] = 35; + table[35 * 256 + 74] = 35; + table[34 * 256 + 75] = 35; + table[35 * 256 + 75] = 35; + table[34 * 256 + 76] = 35; + table[35 * 256 + 76] = 35; + table[34 * 256 + 77] = 35; + table[35 * 256 + 77] = 35; + table[34 * 256 + 78] = 35; + table[35 * 256 + 78] = 35; + table[34 * 256 + 79] = 35; + table[35 * 256 + 79] = 35; + table[34 * 256 + 80] = 35; + table[35 * 256 + 80] = 35; + table[34 * 256 + 81] = 35; + table[35 * 256 + 81] = 35; + table[34 * 256 + 82] = 35; + table[35 * 256 + 82] = 35; + table[34 * 256 + 83] = 35; + table[35 * 256 + 83] = 35; + table[34 * 256 + 84] = 35; + table[35 * 256 + 84] = 35; + table[34 * 256 + 85] = 35; + table[35 * 256 + 85] = 35; + table[34 * 256 + 86] = 35; + table[35 * 256 + 86] = 35; + table[34 * 256 + 87] = 35; + table[35 * 256 + 87] = 35; + table[34 * 256 + 88] = 35; + table[35 * 256 + 88] = 35; + table[34 * 256 + 89] = 35; + table[35 * 256 + 89] = 35; + table[34 * 256 + 90] = 35; + table[35 * 256 + 90] = 35; + table[34 * 256 + 91] = 35; + table[35 * 256 + 91] = 35; + table[34 * 256 + 92] = 35; + table[35 * 256 + 92] = 35; + table[34 * 256 + 93] = 35; + table[35 * 256 + 93] = 35; + table[34 * 256 + 94] = 35; + table[35 * 256 + 94] = 35; + table[34 * 256 + 95] = 35; + table[35 * 256 + 95] = 35; + table[34 * 256 + 96] = 35; + table[35 * 256 + 96] = 35; + table[34 * 256 + 97] = 35; + table[35 * 256 + 97] = 35; + table[34 * 256 + 98] = 35; + table[35 * 256 + 98] = 35; + table[34 * 256 + 99] = 35; + table[35 * 256 + 99] = 35; + table[34 * 256 + 100] = 35; + table[35 * 256 + 100] = 35; + table[34 * 256 + 101] = 35; + table[35 * 256 + 101] = 35; + table[34 * 256 + 102] = 35; + table[35 * 256 + 102] = 35; + table[34 * 256 + 103] = 35; + table[35 * 256 + 103] = 35; + table[34 * 256 + 104] = 35; + table[35 * 256 + 104] = 35; + table[34 * 256 + 105] = 35; + table[35 * 256 + 105] = 35; + table[34 * 256 + 106] = 35; + table[35 * 256 + 106] = 35; + table[34 * 256 + 107] = 35; + table[35 * 256 + 107] = 35; + table[34 * 256 + 108] = 35; + table[35 * 256 + 108] = 35; + table[34 * 256 + 109] = 35; + table[35 * 256 + 109] = 35; + table[34 * 256 + 110] = 35; + table[35 * 256 + 110] = 35; + table[34 * 256 + 111] = 35; + table[35 * 256 + 111] = 35; + table[34 * 256 + 112] = 35; + table[35 * 256 + 112] = 35; + table[34 * 256 + 113] = 35; + table[35 * 256 + 113] = 35; + table[34 * 256 + 114] = 35; + table[35 * 256 + 114] = 35; + table[34 * 256 + 115] = 35; + table[35 * 256 + 115] = 35; + table[34 * 256 + 116] = 35; + table[35 * 256 + 116] = 35; + table[34 * 256 + 117] = 35; + table[35 * 256 + 117] = 35; + table[34 * 256 + 118] = 35; + table[35 * 256 + 118] = 35; + table[34 * 256 + 119] = 35; + table[35 * 256 + 119] = 35; + table[34 * 256 + 120] = 35; + table[35 * 256 + 120] = 35; + table[34 * 256 + 121] = 35; + table[35 * 256 + 121] = 35; + table[34 * 256 + 122] = 35; + table[35 * 256 + 122] = 35; + table[34 * 256 + 123] = 35; + table[35 * 256 + 123] = 35; + table[34 * 256 + 124] = 35; + table[35 * 256 + 124] = 35; + table[34 * 256 + 125] = 35; + table[35 * 256 + 125] = 35; + table[34 * 256 + 126] = 35; + table[35 * 256 + 126] = 35; + table[34 * 256 + 127] = 35; + table[35 * 256 + 127] = 35; + table[34 * 256 + 128] = 35; + table[35 * 256 + 128] = 35; + table[34 * 256 + 129] = 35; + table[35 * 256 + 129] = 35; + table[34 * 256 + 130] = 35; + table[35 * 256 + 130] = 35; + table[34 * 256 + 131] = 35; + table[35 * 256 + 131] = 35; + table[34 * 256 + 132] = 35; + table[35 * 256 + 132] = 35; + table[34 * 256 + 133] = 35; + table[35 * 256 + 133] = 35; + table[34 * 256 + 134] = 35; + table[35 * 256 + 134] = 35; + table[34 * 256 + 135] = 35; + table[35 * 256 + 135] = 35; + table[34 * 256 + 136] = 35; + table[35 * 256 + 136] = 35; + table[34 * 256 + 137] = 35; + table[35 * 256 + 137] = 35; + table[34 * 256 + 138] = 35; + table[35 * 256 + 138] = 35; + table[34 * 256 + 139] = 35; + table[35 * 256 + 139] = 35; + table[34 * 256 + 140] = 35; + table[35 * 256 + 140] = 35; + table[34 * 256 + 141] = 35; + table[35 * 256 + 141] = 35; + table[34 * 256 + 142] = 35; + table[35 * 256 + 142] = 35; + table[34 * 256 + 143] = 35; + table[35 * 256 + 143] = 35; + table[34 * 256 + 144] = 35; + table[35 * 256 + 144] = 35; + table[34 * 256 + 145] = 35; + table[35 * 256 + 145] = 35; + table[34 * 256 + 146] = 35; + table[35 * 256 + 146] = 35; + table[34 * 256 + 147] = 35; + table[35 * 256 + 147] = 35; + table[34 * 256 + 148] = 35; + table[35 * 256 + 148] = 35; + table[34 * 256 + 149] = 35; + table[35 * 256 + 149] = 35; + table[34 * 256 + 150] = 35; + table[35 * 256 + 150] = 35; + table[34 * 256 + 151] = 35; + table[35 * 256 + 151] = 35; + table[34 * 256 + 152] = 35; + table[35 * 256 + 152] = 35; + table[34 * 256 + 153] = 35; + table[35 * 256 + 153] = 35; + table[34 * 256 + 154] = 35; + table[35 * 256 + 154] = 35; + table[34 * 256 + 155] = 35; + table[35 * 256 + 155] = 35; + table[34 * 256 + 156] = 35; + table[35 * 256 + 156] = 35; + table[34 * 256 + 157] = 35; + table[35 * 256 + 157] = 35; + table[34 * 256 + 158] = 35; + table[35 * 256 + 158] = 35; + table[34 * 256 + 159] = 35; + table[35 * 256 + 159] = 35; + table[34 * 256 + 160] = 35; + table[35 * 256 + 160] = 35; + table[34 * 256 + 161] = 35; + table[35 * 256 + 161] = 35; + table[34 * 256 + 162] = 35; + table[35 * 256 + 162] = 35; + table[34 * 256 + 163] = 35; + table[35 * 256 + 163] = 35; + table[34 * 256 + 164] = 35; + table[35 * 256 + 164] = 35; + table[34 * 256 + 165] = 35; + table[35 * 256 + 165] = 35; + table[34 * 256 + 166] = 35; + table[35 * 256 + 166] = 35; + table[34 * 256 + 167] = 35; + table[35 * 256 + 167] = 35; + table[34 * 256 + 168] = 35; + table[35 * 256 + 168] = 35; + table[34 * 256 + 169] = 35; + table[35 * 256 + 169] = 35; + table[34 * 256 + 170] = 35; + table[35 * 256 + 170] = 35; + table[34 * 256 + 171] = 35; + table[35 * 256 + 171] = 35; + table[34 * 256 + 172] = 35; + table[35 * 256 + 172] = 35; + table[34 * 256 + 173] = 35; + table[35 * 256 + 173] = 35; + table[34 * 256 + 174] = 35; + table[35 * 256 + 174] = 35; + table[34 * 256 + 175] = 35; + table[35 * 256 + 175] = 35; + table[34 * 256 + 176] = 35; + table[35 * 256 + 176] = 35; + table[34 * 256 + 177] = 35; + table[35 * 256 + 177] = 35; + table[34 * 256 + 178] = 35; + table[35 * 256 + 178] = 35; + table[34 * 256 + 179] = 35; + table[35 * 256 + 179] = 35; + table[34 * 256 + 180] = 35; + table[35 * 256 + 180] = 35; + table[34 * 256 + 181] = 35; + table[35 * 256 + 181] = 35; + table[34 * 256 + 182] = 35; + table[35 * 256 + 182] = 35; + table[34 * 256 + 183] = 35; + table[35 * 256 + 183] = 35; + table[34 * 256 + 184] = 35; + table[35 * 256 + 184] = 35; + table[34 * 256 + 185] = 35; + table[35 * 256 + 185] = 35; + table[34 * 256 + 186] = 35; + table[35 * 256 + 186] = 35; + table[34 * 256 + 187] = 35; + table[35 * 256 + 187] = 35; + table[34 * 256 + 188] = 35; + table[35 * 256 + 188] = 35; + table[34 * 256 + 189] = 35; + table[35 * 256 + 189] = 35; + table[34 * 256 + 190] = 35; + table[35 * 256 + 190] = 35; + table[34 * 256 + 191] = 35; + table[35 * 256 + 191] = 35; + table[34 * 256 + 192] = 35; + table[35 * 256 + 192] = 35; + table[34 * 256 + 193] = 35; + table[35 * 256 + 193] = 35; + table[34 * 256 + 194] = 35; + table[35 * 256 + 194] = 35; + table[34 * 256 + 195] = 35; + table[35 * 256 + 195] = 35; + table[34 * 256 + 196] = 35; + table[35 * 256 + 196] = 35; + table[34 * 256 + 197] = 35; + table[35 * 256 + 197] = 35; + table[34 * 256 + 198] = 35; + table[35 * 256 + 198] = 35; + table[34 * 256 + 199] = 35; + table[35 * 256 + 199] = 35; + table[34 * 256 + 200] = 35; + table[35 * 256 + 200] = 35; + table[34 * 256 + 201] = 35; + table[35 * 256 + 201] = 35; + table[34 * 256 + 202] = 35; + table[35 * 256 + 202] = 35; + table[34 * 256 + 203] = 35; + table[35 * 256 + 203] = 35; + table[34 * 256 + 204] = 35; + table[35 * 256 + 204] = 35; + table[34 * 256 + 205] = 35; + table[35 * 256 + 205] = 35; + table[34 * 256 + 206] = 35; + table[35 * 256 + 206] = 35; + table[34 * 256 + 207] = 35; + table[35 * 256 + 207] = 35; + table[34 * 256 + 208] = 35; + table[35 * 256 + 208] = 35; + table[34 * 256 + 209] = 35; + table[35 * 256 + 209] = 35; + table[34 * 256 + 210] = 35; + table[35 * 256 + 210] = 35; + table[34 * 256 + 211] = 35; + table[35 * 256 + 211] = 35; + table[34 * 256 + 212] = 35; + table[35 * 256 + 212] = 35; + table[34 * 256 + 213] = 35; + table[35 * 256 + 213] = 35; + table[34 * 256 + 214] = 35; + table[35 * 256 + 214] = 35; + table[34 * 256 + 215] = 35; + table[35 * 256 + 215] = 35; + table[34 * 256 + 216] = 35; + table[35 * 256 + 216] = 35; + table[34 * 256 + 217] = 35; + table[35 * 256 + 217] = 35; + table[34 * 256 + 218] = 35; + table[35 * 256 + 218] = 35; + table[34 * 256 + 219] = 35; + table[35 * 256 + 219] = 35; + table[34 * 256 + 220] = 35; + table[35 * 256 + 220] = 35; + table[34 * 256 + 221] = 35; + table[35 * 256 + 221] = 35; + table[34 * 256 + 222] = 35; + table[35 * 256 + 222] = 35; + table[34 * 256 + 223] = 35; + table[35 * 256 + 223] = 35; + table[34 * 256 + 224] = 35; + table[35 * 256 + 224] = 35; + table[34 * 256 + 225] = 35; + table[35 * 256 + 225] = 35; + table[34 * 256 + 226] = 35; + table[35 * 256 + 226] = 35; + table[34 * 256 + 227] = 35; + table[35 * 256 + 227] = 35; + table[34 * 256 + 228] = 35; + table[35 * 256 + 228] = 35; + table[34 * 256 + 229] = 35; + table[35 * 256 + 229] = 35; + table[34 * 256 + 230] = 35; + table[35 * 256 + 230] = 35; + table[34 * 256 + 231] = 35; + table[35 * 256 + 231] = 35; + table[34 * 256 + 232] = 35; + table[35 * 256 + 232] = 35; + table[34 * 256 + 233] = 35; + table[35 * 256 + 233] = 35; + table[34 * 256 + 234] = 35; + table[35 * 256 + 234] = 35; + table[34 * 256 + 235] = 35; + table[35 * 256 + 235] = 35; + table[34 * 256 + 236] = 35; + table[35 * 256 + 236] = 35; + table[34 * 256 + 237] = 35; + table[35 * 256 + 237] = 35; + table[34 * 256 + 238] = 35; + table[35 * 256 + 238] = 35; + table[34 * 256 + 239] = 35; + table[35 * 256 + 239] = 35; + table[34 * 256 + 240] = 35; + table[35 * 256 + 240] = 35; + table[34 * 256 + 241] = 35; + table[35 * 256 + 241] = 35; + table[34 * 256 + 242] = 35; + table[35 * 256 + 242] = 35; + table[34 * 256 + 243] = 35; + table[35 * 256 + 243] = 35; + table[34 * 256 + 244] = 35; + table[35 * 256 + 244] = 35; + table[34 * 256 + 245] = 35; + table[35 * 256 + 245] = 35; + table[34 * 256 + 246] = 35; + table[35 * 256 + 246] = 35; + table[34 * 256 + 247] = 35; + table[35 * 256 + 247] = 35; + table[34 * 256 + 248] = 35; + table[35 * 256 + 248] = 35; + table[34 * 256 + 249] = 35; + table[35 * 256 + 249] = 35; + table[34 * 256 + 250] = 35; + table[35 * 256 + 250] = 35; + table[34 * 256 + 251] = 35; + table[35 * 256 + 251] = 35; + table[34 * 256 + 252] = 35; + table[35 * 256 + 252] = 35; + table[34 * 256 + 253] = 35; + table[35 * 256 + 253] = 35; + table[34 * 256 + 254] = 35; + table[35 * 256 + 254] = 35; + table[0 * 256 + 13] = 1; + table[0 * 256 + 255] = 2; + table[1 * 256 + 10] = 2; + table[2 * 256 + 100] = 3; + table[3 * 256 + 107] = 4; + table[4 * 256 + 105] = 5; + table[5 * 256 + 109] = 6; + table[6 * 256 + 45] = 7; + table[7 * 256 + 115] = 8; + table[8 * 256 + 105] = 9; + table[9 * 256 + 103] = 10; + table[10 * 256 + 110] = 11; + table[11 * 256 + 97] = 12; + table[12 * 256 + 116] = 13; + table[13 * 256 + 117] = 14; + table[14 * 256 + 114] = 15; + table[15 * 256 + 101] = 16; + table[16 * 256 + 58] = 17; + table[17 * 256 + 97] = 18; + table[17 * 256 + 98] = 18; + table[17 * 256 + 99] = 18; + table[17 * 256 + 100] = 18; + table[17 * 256 + 101] = 18; + table[17 * 256 + 102] = 18; + table[17 * 256 + 103] = 18; + table[17 * 256 + 104] = 18; + table[17 * 256 + 105] = 18; + table[17 * 256 + 106] = 18; + table[17 * 256 + 107] = 18; + table[17 * 256 + 108] = 18; + table[17 * 256 + 109] = 18; + table[17 * 256 + 110] = 18; + table[17 * 256 + 111] = 18; + table[17 * 256 + 112] = 18; + table[17 * 256 + 113] = 18; + table[17 * 256 + 114] = 18; + table[17 * 256 + 115] = 18; + table[17 * 256 + 116] = 18; + table[17 * 256 + 117] = 18; + table[17 * 256 + 118] = 18; + table[17 * 256 + 119] = 18; + table[17 * 256 + 120] = 18; + table[17 * 256 + 121] = 18; + table[17 * 256 + 122] = 18; + table[18 * 256 + 97] = 18; + table[18 * 256 + 98] = 18; + table[18 * 256 + 99] = 18; + table[18 * 256 + 100] = 18; + table[18 * 256 + 101] = 18; + table[18 * 256 + 102] = 18; + table[18 * 256 + 103] = 18; + table[18 * 256 + 104] = 18; + table[18 * 256 + 105] = 18; + table[18 * 256 + 106] = 18; + table[18 * 256 + 107] = 18; + table[18 * 256 + 108] = 18; + table[18 * 256 + 109] = 18; + table[18 * 256 + 110] = 18; + table[18 * 256 + 111] = 18; + table[18 * 256 + 112] = 18; + table[18 * 256 + 113] = 18; + table[18 * 256 + 114] = 18; + table[18 * 256 + 115] = 18; + table[18 * 256 + 116] = 18; + table[18 * 256 + 117] = 18; + table[18 * 256 + 118] = 18; + table[18 * 256 + 119] = 18; + table[18 * 256 + 120] = 18; + table[18 * 256 + 121] = 18; + table[18 * 256 + 122] = 18; + table[18 * 256 + 61] = 19; + table[19 * 256 + 0] = 20; + table[19 * 256 + 1] = 20; + table[19 * 256 + 2] = 20; + table[19 * 256 + 3] = 20; + table[19 * 256 + 4] = 20; + table[19 * 256 + 5] = 20; + table[19 * 256 + 6] = 20; + table[19 * 256 + 7] = 20; + table[19 * 256 + 8] = 20; + table[19 * 256 + 9] = 20; + table[19 * 256 + 10] = 20; + table[19 * 256 + 11] = 20; + table[19 * 256 + 12] = 20; + table[19 * 256 + 13] = 20; + table[19 * 256 + 14] = 20; + table[19 * 256 + 15] = 20; + table[19 * 256 + 16] = 20; + table[19 * 256 + 17] = 20; + table[19 * 256 + 18] = 20; + table[19 * 256 + 19] = 20; + table[19 * 256 + 20] = 20; + table[19 * 256 + 21] = 20; + table[19 * 256 + 22] = 20; + table[19 * 256 + 23] = 20; + table[19 * 256 + 24] = 20; + table[19 * 256 + 25] = 20; + table[19 * 256 + 26] = 20; + table[19 * 256 + 27] = 20; + table[19 * 256 + 28] = 20; + table[19 * 256 + 29] = 20; + table[19 * 256 + 30] = 20; + table[19 * 256 + 31] = 20; + table[19 * 256 + 32] = 20; + table[19 * 256 + 33] = 20; + table[19 * 256 + 34] = 20; + table[19 * 256 + 35] = 20; + table[19 * 256 + 36] = 20; + table[19 * 256 + 37] = 20; + table[19 * 256 + 38] = 20; + table[19 * 256 + 39] = 20; + table[19 * 256 + 40] = 20; + table[19 * 256 + 41] = 20; + table[19 * 256 + 42] = 20; + table[19 * 256 + 43] = 20; + table[19 * 256 + 44] = 20; + table[19 * 256 + 45] = 20; + table[19 * 256 + 46] = 20; + table[19 * 256 + 47] = 20; + table[19 * 256 + 48] = 20; + table[19 * 256 + 49] = 20; + table[19 * 256 + 50] = 20; + table[19 * 256 + 51] = 20; + table[19 * 256 + 52] = 20; + table[19 * 256 + 53] = 20; + table[19 * 256 + 54] = 20; + table[19 * 256 + 55] = 20; + table[19 * 256 + 56] = 20; + table[19 * 256 + 57] = 20; + table[19 * 256 + 58] = 20; + table[19 * 256 + 60] = 20; + table[19 * 256 + 61] = 20; + table[19 * 256 + 62] = 20; + table[19 * 256 + 63] = 20; + table[19 * 256 + 64] = 20; + table[19 * 256 + 65] = 20; + table[19 * 256 + 66] = 20; + table[19 * 256 + 67] = 20; + table[19 * 256 + 68] = 20; + table[19 * 256 + 69] = 20; + table[19 * 256 + 70] = 20; + table[19 * 256 + 71] = 20; + table[19 * 256 + 72] = 20; + table[19 * 256 + 73] = 20; + table[19 * 256 + 74] = 20; + table[19 * 256 + 75] = 20; + table[19 * 256 + 76] = 20; + table[19 * 256 + 77] = 20; + table[19 * 256 + 78] = 20; + table[19 * 256 + 79] = 20; + table[19 * 256 + 80] = 20; + table[19 * 256 + 81] = 20; + table[19 * 256 + 82] = 20; + table[19 * 256 + 83] = 20; + table[19 * 256 + 84] = 20; + table[19 * 256 + 85] = 20; + table[19 * 256 + 86] = 20; + table[19 * 256 + 87] = 20; + table[19 * 256 + 88] = 20; + table[19 * 256 + 89] = 20; + table[19 * 256 + 90] = 20; + table[19 * 256 + 91] = 20; + table[19 * 256 + 92] = 20; + table[19 * 256 + 93] = 20; + table[19 * 256 + 94] = 20; + table[19 * 256 + 95] = 20; + table[19 * 256 + 96] = 20; + table[19 * 256 + 97] = 20; + table[19 * 256 + 98] = 20; + table[19 * 256 + 99] = 20; + table[19 * 256 + 100] = 20; + table[19 * 256 + 101] = 20; + table[19 * 256 + 102] = 20; + table[19 * 256 + 103] = 20; + table[19 * 256 + 104] = 20; + table[19 * 256 + 105] = 20; + table[19 * 256 + 106] = 20; + table[19 * 256 + 107] = 20; + table[19 * 256 + 108] = 20; + table[19 * 256 + 109] = 20; + table[19 * 256 + 110] = 20; + table[19 * 256 + 111] = 20; + table[19 * 256 + 112] = 20; + table[19 * 256 + 113] = 20; + table[19 * 256 + 114] = 20; + table[19 * 256 + 115] = 20; + table[19 * 256 + 116] = 20; + table[19 * 256 + 117] = 20; + table[19 * 256 + 118] = 20; + table[19 * 256 + 119] = 20; + table[19 * 256 + 120] = 20; + table[19 * 256 + 121] = 20; + table[19 * 256 + 122] = 20; + table[19 * 256 + 123] = 20; + table[19 * 256 + 124] = 20; + table[19 * 256 + 125] = 20; + table[19 * 256 + 126] = 20; + table[19 * 256 + 127] = 20; + table[19 * 256 + 194] = 21; + table[19 * 256 + 195] = 21; + table[19 * 256 + 196] = 21; + table[19 * 256 + 197] = 21; + table[19 * 256 + 198] = 21; + table[19 * 256 + 199] = 21; + table[19 * 256 + 200] = 21; + table[19 * 256 + 201] = 21; + table[19 * 256 + 202] = 21; + table[19 * 256 + 203] = 21; + table[19 * 256 + 204] = 21; + table[19 * 256 + 205] = 21; + table[19 * 256 + 206] = 21; + table[19 * 256 + 207] = 21; + table[19 * 256 + 208] = 21; + table[19 * 256 + 209] = 21; + table[19 * 256 + 210] = 21; + table[19 * 256 + 211] = 21; + table[19 * 256 + 212] = 21; + table[19 * 256 + 213] = 21; + table[19 * 256 + 214] = 21; + table[19 * 256 + 215] = 21; + table[19 * 256 + 216] = 21; + table[19 * 256 + 217] = 21; + table[19 * 256 + 218] = 21; + table[19 * 256 + 219] = 21; + table[19 * 256 + 220] = 21; + table[19 * 256 + 221] = 21; + table[19 * 256 + 222] = 21; + table[19 * 256 + 223] = 21; + table[19 * 256 + 224] = 22; + table[19 * 256 + 225] = 23; + table[19 * 256 + 226] = 23; + table[19 * 256 + 227] = 23; + table[19 * 256 + 228] = 23; + table[19 * 256 + 229] = 23; + table[19 * 256 + 230] = 23; + table[19 * 256 + 231] = 23; + table[19 * 256 + 232] = 23; + table[19 * 256 + 233] = 23; + table[19 * 256 + 234] = 23; + table[19 * 256 + 235] = 23; + table[19 * 256 + 236] = 23; + table[19 * 256 + 238] = 23; + table[19 * 256 + 239] = 23; + table[19 * 256 + 237] = 24; + table[19 * 256 + 240] = 25; + table[19 * 256 + 241] = 26; + table[19 * 256 + 242] = 26; + table[19 * 256 + 243] = 26; + table[19 * 256 + 244] = 27; + table[20 * 256 + 0] = 20; + table[20 * 256 + 1] = 20; + table[20 * 256 + 2] = 20; + table[20 * 256 + 3] = 20; + table[20 * 256 + 4] = 20; + table[20 * 256 + 5] = 20; + table[20 * 256 + 6] = 20; + table[20 * 256 + 7] = 20; + table[20 * 256 + 8] = 20; + table[20 * 256 + 9] = 20; + table[20 * 256 + 10] = 20; + table[20 * 256 + 11] = 20; + table[20 * 256 + 12] = 20; + table[20 * 256 + 13] = 20; + table[20 * 256 + 14] = 20; + table[20 * 256 + 15] = 20; + table[20 * 256 + 16] = 20; + table[20 * 256 + 17] = 20; + table[20 * 256 + 18] = 20; + table[20 * 256 + 19] = 20; + table[20 * 256 + 20] = 20; + table[20 * 256 + 21] = 20; + table[20 * 256 + 22] = 20; + table[20 * 256 + 23] = 20; + table[20 * 256 + 24] = 20; + table[20 * 256 + 25] = 20; + table[20 * 256 + 26] = 20; + table[20 * 256 + 27] = 20; + table[20 * 256 + 28] = 20; + table[20 * 256 + 29] = 20; + table[20 * 256 + 30] = 20; + table[20 * 256 + 31] = 20; + table[20 * 256 + 32] = 20; + table[20 * 256 + 33] = 20; + table[20 * 256 + 34] = 20; + table[20 * 256 + 35] = 20; + table[20 * 256 + 36] = 20; + table[20 * 256 + 37] = 20; + table[20 * 256 + 38] = 20; + table[20 * 256 + 39] = 20; + table[20 * 256 + 40] = 20; + table[20 * 256 + 41] = 20; + table[20 * 256 + 42] = 20; + table[20 * 256 + 43] = 20; + table[20 * 256 + 44] = 20; + table[20 * 256 + 45] = 20; + table[20 * 256 + 46] = 20; + table[20 * 256 + 47] = 20; + table[20 * 256 + 48] = 20; + table[20 * 256 + 49] = 20; + table[20 * 256 + 50] = 20; + table[20 * 256 + 51] = 20; + table[20 * 256 + 52] = 20; + table[20 * 256 + 53] = 20; + table[20 * 256 + 54] = 20; + table[20 * 256 + 55] = 20; + table[20 * 256 + 56] = 20; + table[20 * 256 + 57] = 20; + table[20 * 256 + 58] = 20; + table[20 * 256 + 60] = 20; + table[20 * 256 + 61] = 20; + table[20 * 256 + 62] = 20; + table[20 * 256 + 63] = 20; + table[20 * 256 + 64] = 20; + table[20 * 256 + 65] = 20; + table[20 * 256 + 66] = 20; + table[20 * 256 + 67] = 20; + table[20 * 256 + 68] = 20; + table[20 * 256 + 69] = 20; + table[20 * 256 + 70] = 20; + table[20 * 256 + 71] = 20; + table[20 * 256 + 72] = 20; + table[20 * 256 + 73] = 20; + table[20 * 256 + 74] = 20; + table[20 * 256 + 75] = 20; + table[20 * 256 + 76] = 20; + table[20 * 256 + 77] = 20; + table[20 * 256 + 78] = 20; + table[20 * 256 + 79] = 20; + table[20 * 256 + 80] = 20; + table[20 * 256 + 81] = 20; + table[20 * 256 + 82] = 20; + table[20 * 256 + 83] = 20; + table[20 * 256 + 84] = 20; + table[20 * 256 + 85] = 20; + table[20 * 256 + 86] = 20; + table[20 * 256 + 87] = 20; + table[20 * 256 + 88] = 20; + table[20 * 256 + 89] = 20; + table[20 * 256 + 90] = 20; + table[20 * 256 + 91] = 20; + table[20 * 256 + 92] = 20; + table[20 * 256 + 93] = 20; + table[20 * 256 + 94] = 20; + table[20 * 256 + 95] = 20; + table[20 * 256 + 96] = 20; + table[20 * 256 + 97] = 20; + table[20 * 256 + 98] = 20; + table[20 * 256 + 99] = 20; + table[20 * 256 + 100] = 20; + table[20 * 256 + 101] = 20; + table[20 * 256 + 102] = 20; + table[20 * 256 + 103] = 20; + table[20 * 256 + 104] = 20; + table[20 * 256 + 105] = 20; + table[20 * 256 + 106] = 20; + table[20 * 256 + 107] = 20; + table[20 * 256 + 108] = 20; + table[20 * 256 + 109] = 20; + table[20 * 256 + 110] = 20; + table[20 * 256 + 111] = 20; + table[20 * 256 + 112] = 20; + table[20 * 256 + 113] = 20; + table[20 * 256 + 114] = 20; + table[20 * 256 + 115] = 20; + table[20 * 256 + 116] = 20; + table[20 * 256 + 117] = 20; + table[20 * 256 + 118] = 20; + table[20 * 256 + 119] = 20; + table[20 * 256 + 120] = 20; + table[20 * 256 + 121] = 20; + table[20 * 256 + 122] = 20; + table[20 * 256 + 123] = 20; + table[20 * 256 + 124] = 20; + table[20 * 256 + 125] = 20; + table[20 * 256 + 126] = 20; + table[20 * 256 + 127] = 20; + table[20 * 256 + 194] = 21; + table[20 * 256 + 195] = 21; + table[20 * 256 + 196] = 21; + table[20 * 256 + 197] = 21; + table[20 * 256 + 198] = 21; + table[20 * 256 + 199] = 21; + table[20 * 256 + 200] = 21; + table[20 * 256 + 201] = 21; + table[20 * 256 + 202] = 21; + table[20 * 256 + 203] = 21; + table[20 * 256 + 204] = 21; + table[20 * 256 + 205] = 21; + table[20 * 256 + 206] = 21; + table[20 * 256 + 207] = 21; + table[20 * 256 + 208] = 21; + table[20 * 256 + 209] = 21; + table[20 * 256 + 210] = 21; + table[20 * 256 + 211] = 21; + table[20 * 256 + 212] = 21; + table[20 * 256 + 213] = 21; + table[20 * 256 + 214] = 21; + table[20 * 256 + 215] = 21; + table[20 * 256 + 216] = 21; + table[20 * 256 + 217] = 21; + table[20 * 256 + 218] = 21; + table[20 * 256 + 219] = 21; + table[20 * 256 + 220] = 21; + table[20 * 256 + 221] = 21; + table[20 * 256 + 222] = 21; + table[20 * 256 + 223] = 21; + table[20 * 256 + 224] = 22; + table[20 * 256 + 225] = 23; + table[20 * 256 + 226] = 23; + table[20 * 256 + 227] = 23; + table[20 * 256 + 228] = 23; + table[20 * 256 + 229] = 23; + table[20 * 256 + 230] = 23; + table[20 * 256 + 231] = 23; + table[20 * 256 + 232] = 23; + table[20 * 256 + 233] = 23; + table[20 * 256 + 234] = 23; + table[20 * 256 + 235] = 23; + table[20 * 256 + 236] = 23; + table[20 * 256 + 238] = 23; + table[20 * 256 + 239] = 23; + table[20 * 256 + 237] = 24; + table[20 * 256 + 240] = 25; + table[20 * 256 + 241] = 26; + table[20 * 256 + 242] = 26; + table[20 * 256 + 243] = 26; + table[20 * 256 + 244] = 27; + table[20 * 256 + 59] = 28; + table[21 * 256 + 128] = 20; + table[21 * 256 + 129] = 20; + table[21 * 256 + 130] = 20; + table[21 * 256 + 131] = 20; + table[21 * 256 + 132] = 20; + table[21 * 256 + 133] = 20; + table[21 * 256 + 134] = 20; + table[21 * 256 + 135] = 20; + table[21 * 256 + 136] = 20; + table[21 * 256 + 137] = 20; + table[21 * 256 + 138] = 20; + table[21 * 256 + 139] = 20; + table[21 * 256 + 140] = 20; + table[21 * 256 + 141] = 20; + table[21 * 256 + 142] = 20; + table[21 * 256 + 143] = 20; + table[21 * 256 + 144] = 20; + table[21 * 256 + 145] = 20; + table[21 * 256 + 146] = 20; + table[21 * 256 + 147] = 20; + table[21 * 256 + 148] = 20; + table[21 * 256 + 149] = 20; + table[21 * 256 + 150] = 20; + table[21 * 256 + 151] = 20; + table[21 * 256 + 152] = 20; + table[21 * 256 + 153] = 20; + table[21 * 256 + 154] = 20; + table[21 * 256 + 155] = 20; + table[21 * 256 + 156] = 20; + table[21 * 256 + 157] = 20; + table[21 * 256 + 158] = 20; + table[21 * 256 + 159] = 20; + table[21 * 256 + 160] = 20; + table[21 * 256 + 161] = 20; + table[21 * 256 + 162] = 20; + table[21 * 256 + 163] = 20; + table[21 * 256 + 164] = 20; + table[21 * 256 + 165] = 20; + table[21 * 256 + 166] = 20; + table[21 * 256 + 167] = 20; + table[21 * 256 + 168] = 20; + table[21 * 256 + 169] = 20; + table[21 * 256 + 170] = 20; + table[21 * 256 + 171] = 20; + table[21 * 256 + 172] = 20; + table[21 * 256 + 173] = 20; + table[21 * 256 + 174] = 20; + table[21 * 256 + 175] = 20; + table[21 * 256 + 176] = 20; + table[21 * 256 + 177] = 20; + table[21 * 256 + 178] = 20; + table[21 * 256 + 179] = 20; + table[21 * 256 + 180] = 20; + table[21 * 256 + 181] = 20; + table[21 * 256 + 182] = 20; + table[21 * 256 + 183] = 20; + table[21 * 256 + 184] = 20; + table[21 * 256 + 185] = 20; + table[21 * 256 + 186] = 20; + table[21 * 256 + 187] = 20; + table[21 * 256 + 188] = 20; + table[21 * 256 + 189] = 20; + table[21 * 256 + 190] = 20; + table[21 * 256 + 191] = 20; + table[22 * 256 + 160] = 21; + table[22 * 256 + 161] = 21; + table[22 * 256 + 162] = 21; + table[22 * 256 + 163] = 21; + table[22 * 256 + 164] = 21; + table[22 * 256 + 165] = 21; + table[22 * 256 + 166] = 21; + table[22 * 256 + 167] = 21; + table[22 * 256 + 168] = 21; + table[22 * 256 + 169] = 21; + table[22 * 256 + 170] = 21; + table[22 * 256 + 171] = 21; + table[22 * 256 + 172] = 21; + table[22 * 256 + 173] = 21; + table[22 * 256 + 174] = 21; + table[22 * 256 + 175] = 21; + table[22 * 256 + 176] = 21; + table[22 * 256 + 177] = 21; + table[22 * 256 + 178] = 21; + table[22 * 256 + 179] = 21; + table[22 * 256 + 180] = 21; + table[22 * 256 + 181] = 21; + table[22 * 256 + 182] = 21; + table[22 * 256 + 183] = 21; + table[22 * 256 + 184] = 21; + table[22 * 256 + 185] = 21; + table[22 * 256 + 186] = 21; + table[22 * 256 + 187] = 21; + table[22 * 256 + 188] = 21; + table[22 * 256 + 189] = 21; + table[22 * 256 + 190] = 21; + table[22 * 256 + 191] = 21; + table[23 * 256 + 128] = 21; + table[23 * 256 + 129] = 21; + table[23 * 256 + 130] = 21; + table[23 * 256 + 131] = 21; + table[23 * 256 + 132] = 21; + table[23 * 256 + 133] = 21; + table[23 * 256 + 134] = 21; + table[23 * 256 + 135] = 21; + table[23 * 256 + 136] = 21; + table[23 * 256 + 137] = 21; + table[23 * 256 + 138] = 21; + table[23 * 256 + 139] = 21; + table[23 * 256 + 140] = 21; + table[23 * 256 + 141] = 21; + table[23 * 256 + 142] = 21; + table[23 * 256 + 143] = 21; + table[23 * 256 + 144] = 21; + table[23 * 256 + 145] = 21; + table[23 * 256 + 146] = 21; + table[23 * 256 + 147] = 21; + table[23 * 256 + 148] = 21; + table[23 * 256 + 149] = 21; + table[23 * 256 + 150] = 21; + table[23 * 256 + 151] = 21; + table[23 * 256 + 152] = 21; + table[23 * 256 + 153] = 21; + table[23 * 256 + 154] = 21; + table[23 * 256 + 155] = 21; + table[23 * 256 + 156] = 21; + table[23 * 256 + 157] = 21; + table[23 * 256 + 158] = 21; + table[23 * 256 + 159] = 21; + table[23 * 256 + 160] = 21; + table[23 * 256 + 161] = 21; + table[23 * 256 + 162] = 21; + table[23 * 256 + 163] = 21; + table[23 * 256 + 164] = 21; + table[23 * 256 + 165] = 21; + table[23 * 256 + 166] = 21; + table[23 * 256 + 167] = 21; + table[23 * 256 + 168] = 21; + table[23 * 256 + 169] = 21; + table[23 * 256 + 170] = 21; + table[23 * 256 + 171] = 21; + table[23 * 256 + 172] = 21; + table[23 * 256 + 173] = 21; + table[23 * 256 + 174] = 21; + table[23 * 256 + 175] = 21; + table[23 * 256 + 176] = 21; + table[23 * 256 + 177] = 21; + table[23 * 256 + 178] = 21; + table[23 * 256 + 179] = 21; + table[23 * 256 + 180] = 21; + table[23 * 256 + 181] = 21; + table[23 * 256 + 182] = 21; + table[23 * 256 + 183] = 21; + table[23 * 256 + 184] = 21; + table[23 * 256 + 185] = 21; + table[23 * 256 + 186] = 21; + table[23 * 256 + 187] = 21; + table[23 * 256 + 188] = 21; + table[23 * 256 + 189] = 21; + table[23 * 256 + 190] = 21; + table[23 * 256 + 191] = 21; + table[24 * 256 + 128] = 21; + table[24 * 256 + 129] = 21; + table[24 * 256 + 130] = 21; + table[24 * 256 + 131] = 21; + table[24 * 256 + 132] = 21; + table[24 * 256 + 133] = 21; + table[24 * 256 + 134] = 21; + table[24 * 256 + 135] = 21; + table[24 * 256 + 136] = 21; + table[24 * 256 + 137] = 21; + table[24 * 256 + 138] = 21; + table[24 * 256 + 139] = 21; + table[24 * 256 + 140] = 21; + table[24 * 256 + 141] = 21; + table[24 * 256 + 142] = 21; + table[24 * 256 + 143] = 21; + table[24 * 256 + 144] = 21; + table[24 * 256 + 145] = 21; + table[24 * 256 + 146] = 21; + table[24 * 256 + 147] = 21; + table[24 * 256 + 148] = 21; + table[24 * 256 + 149] = 21; + table[24 * 256 + 150] = 21; + table[24 * 256 + 151] = 21; + table[24 * 256 + 152] = 21; + table[24 * 256 + 153] = 21; + table[24 * 256 + 154] = 21; + table[24 * 256 + 155] = 21; + table[24 * 256 + 156] = 21; + table[24 * 256 + 157] = 21; + table[24 * 256 + 158] = 21; + table[24 * 256 + 159] = 21; + table[25 * 256 + 144] = 23; + table[25 * 256 + 145] = 23; + table[25 * 256 + 146] = 23; + table[25 * 256 + 147] = 23; + table[25 * 256 + 148] = 23; + table[25 * 256 + 149] = 23; + table[25 * 256 + 150] = 23; + table[25 * 256 + 151] = 23; + table[25 * 256 + 152] = 23; + table[25 * 256 + 153] = 23; + table[25 * 256 + 154] = 23; + table[25 * 256 + 155] = 23; + table[25 * 256 + 156] = 23; + table[25 * 256 + 157] = 23; + table[25 * 256 + 158] = 23; + table[25 * 256 + 159] = 23; + table[25 * 256 + 160] = 23; + table[25 * 256 + 161] = 23; + table[25 * 256 + 162] = 23; + table[25 * 256 + 163] = 23; + table[25 * 256 + 164] = 23; + table[25 * 256 + 165] = 23; + table[25 * 256 + 166] = 23; + table[25 * 256 + 167] = 23; + table[25 * 256 + 168] = 23; + table[25 * 256 + 169] = 23; + table[25 * 256 + 170] = 23; + table[25 * 256 + 171] = 23; + table[25 * 256 + 172] = 23; + table[25 * 256 + 173] = 23; + table[25 * 256 + 174] = 23; + table[25 * 256 + 175] = 23; + table[25 * 256 + 176] = 23; + table[25 * 256 + 177] = 23; + table[25 * 256 + 178] = 23; + table[25 * 256 + 179] = 23; + table[25 * 256 + 180] = 23; + table[25 * 256 + 181] = 23; + table[25 * 256 + 182] = 23; + table[25 * 256 + 183] = 23; + table[25 * 256 + 184] = 23; + table[25 * 256 + 185] = 23; + table[25 * 256 + 186] = 23; + table[25 * 256 + 187] = 23; + table[25 * 256 + 188] = 23; + table[25 * 256 + 189] = 23; + table[25 * 256 + 190] = 23; + table[25 * 256 + 191] = 23; + table[26 * 256 + 128] = 23; + table[26 * 256 + 129] = 23; + table[26 * 256 + 130] = 23; + table[26 * 256 + 131] = 23; + table[26 * 256 + 132] = 23; + table[26 * 256 + 133] = 23; + table[26 * 256 + 134] = 23; + table[26 * 256 + 135] = 23; + table[26 * 256 + 136] = 23; + table[26 * 256 + 137] = 23; + table[26 * 256 + 138] = 23; + table[26 * 256 + 139] = 23; + table[26 * 256 + 140] = 23; + table[26 * 256 + 141] = 23; + table[26 * 256 + 142] = 23; + table[26 * 256 + 143] = 23; + table[26 * 256 + 144] = 23; + table[26 * 256 + 145] = 23; + table[26 * 256 + 146] = 23; + table[26 * 256 + 147] = 23; + table[26 * 256 + 148] = 23; + table[26 * 256 + 149] = 23; + table[26 * 256 + 150] = 23; + table[26 * 256 + 151] = 23; + table[26 * 256 + 152] = 23; + table[26 * 256 + 153] = 23; + table[26 * 256 + 154] = 23; + table[26 * 256 + 155] = 23; + table[26 * 256 + 156] = 23; + table[26 * 256 + 157] = 23; + table[26 * 256 + 158] = 23; + table[26 * 256 + 159] = 23; + table[26 * 256 + 160] = 23; + table[26 * 256 + 161] = 23; + table[26 * 256 + 162] = 23; + table[26 * 256 + 163] = 23; + table[26 * 256 + 164] = 23; + table[26 * 256 + 165] = 23; + table[26 * 256 + 166] = 23; + table[26 * 256 + 167] = 23; + table[26 * 256 + 168] = 23; + table[26 * 256 + 169] = 23; + table[26 * 256 + 170] = 23; + table[26 * 256 + 171] = 23; + table[26 * 256 + 172] = 23; + table[26 * 256 + 173] = 23; + table[26 * 256 + 174] = 23; + table[26 * 256 + 175] = 23; + table[26 * 256 + 176] = 23; + table[26 * 256 + 177] = 23; + table[26 * 256 + 178] = 23; + table[26 * 256 + 179] = 23; + table[26 * 256 + 180] = 23; + table[26 * 256 + 181] = 23; + table[26 * 256 + 182] = 23; + table[26 * 256 + 183] = 23; + table[26 * 256 + 184] = 23; + table[26 * 256 + 185] = 23; + table[26 * 256 + 186] = 23; + table[26 * 256 + 187] = 23; + table[26 * 256 + 188] = 23; + table[26 * 256 + 189] = 23; + table[26 * 256 + 190] = 23; + table[26 * 256 + 191] = 23; + table[27 * 256 + 128] = 23; + table[27 * 256 + 129] = 23; + table[27 * 256 + 130] = 23; + table[27 * 256 + 131] = 23; + table[27 * 256 + 132] = 23; + table[27 * 256 + 133] = 23; + table[27 * 256 + 134] = 23; + table[27 * 256 + 135] = 23; + table[27 * 256 + 136] = 23; + table[27 * 256 + 137] = 23; + table[27 * 256 + 138] = 23; + table[27 * 256 + 139] = 23; + table[27 * 256 + 140] = 23; + table[27 * 256 + 141] = 23; + table[27 * 256 + 142] = 23; + table[27 * 256 + 143] = 23; + table[28 * 256 + 32] = 29; + table[29 * 256 + 97] = 18; + table[29 * 256 + 99] = 18; + table[29 * 256 + 100] = 18; + table[29 * 256 + 101] = 18; + table[29 * 256 + 102] = 18; + table[29 * 256 + 103] = 18; + table[29 * 256 + 104] = 18; + table[29 * 256 + 105] = 18; + table[29 * 256 + 106] = 18; + table[29 * 256 + 107] = 18; + table[29 * 256 + 108] = 18; + table[29 * 256 + 109] = 18; + table[29 * 256 + 110] = 18; + table[29 * 256 + 111] = 18; + table[29 * 256 + 112] = 18; + table[29 * 256 + 113] = 18; + table[29 * 256 + 114] = 18; + table[29 * 256 + 115] = 18; + table[29 * 256 + 116] = 18; + table[29 * 256 + 117] = 18; + table[29 * 256 + 118] = 18; + table[29 * 256 + 119] = 18; + table[29 * 256 + 120] = 18; + table[29 * 256 + 121] = 18; + table[29 * 256 + 122] = 18; + table[29 * 256 + 98] = 30; + table[30 * 256 + 97] = 18; + table[30 * 256 + 98] = 18; + table[30 * 256 + 99] = 18; + table[30 * 256 + 100] = 18; + table[30 * 256 + 101] = 18; + table[30 * 256 + 102] = 18; + table[30 * 256 + 103] = 18; + table[30 * 256 + 105] = 18; + table[30 * 256 + 106] = 18; + table[30 * 256 + 107] = 18; + table[30 * 256 + 108] = 18; + table[30 * 256 + 109] = 18; + table[30 * 256 + 110] = 18; + table[30 * 256 + 111] = 18; + table[30 * 256 + 112] = 18; + table[30 * 256 + 113] = 18; + table[30 * 256 + 114] = 18; + table[30 * 256 + 115] = 18; + table[30 * 256 + 116] = 18; + table[30 * 256 + 117] = 18; + table[30 * 256 + 118] = 18; + table[30 * 256 + 119] = 18; + table[30 * 256 + 120] = 18; + table[30 * 256 + 121] = 18; + table[30 * 256 + 122] = 18; + table[30 * 256 + 61] = 19; + table[30 * 256 + 104] = 31; + table[31 * 256 + 97] = 18; + table[31 * 256 + 98] = 18; + table[31 * 256 + 99] = 18; + table[31 * 256 + 100] = 18; + table[31 * 256 + 101] = 18; + table[31 * 256 + 102] = 18; + table[31 * 256 + 103] = 18; + table[31 * 256 + 104] = 18; + table[31 * 256 + 105] = 18; + table[31 * 256 + 106] = 18; + table[31 * 256 + 107] = 18; + table[31 * 256 + 108] = 18; + table[31 * 256 + 109] = 18; + table[31 * 256 + 110] = 18; + table[31 * 256 + 111] = 18; + table[31 * 256 + 112] = 18; + table[31 * 256 + 113] = 18; + table[31 * 256 + 114] = 18; + table[31 * 256 + 115] = 18; + table[31 * 256 + 116] = 18; + table[31 * 256 + 117] = 18; + table[31 * 256 + 118] = 18; + table[31 * 256 + 119] = 18; + table[31 * 256 + 120] = 18; + table[31 * 256 + 121] = 18; + table[31 * 256 + 122] = 18; + table[31 * 256 + 61] = 32; + table[32 * 256 + 0] = 20; + table[32 * 256 + 1] = 20; + table[32 * 256 + 2] = 20; + table[32 * 256 + 3] = 20; + table[32 * 256 + 4] = 20; + table[32 * 256 + 5] = 20; + table[32 * 256 + 6] = 20; + table[32 * 256 + 7] = 20; + table[32 * 256 + 8] = 20; + table[32 * 256 + 9] = 20; + table[32 * 256 + 10] = 20; + table[32 * 256 + 11] = 20; + table[32 * 256 + 12] = 20; + table[32 * 256 + 13] = 20; + table[32 * 256 + 14] = 20; + table[32 * 256 + 15] = 20; + table[32 * 256 + 16] = 20; + table[32 * 256 + 17] = 20; + table[32 * 256 + 18] = 20; + table[32 * 256 + 19] = 20; + table[32 * 256 + 20] = 20; + table[32 * 256 + 21] = 20; + table[32 * 256 + 22] = 20; + table[32 * 256 + 23] = 20; + table[32 * 256 + 24] = 20; + table[32 * 256 + 25] = 20; + table[32 * 256 + 26] = 20; + table[32 * 256 + 27] = 20; + table[32 * 256 + 28] = 20; + table[32 * 256 + 29] = 20; + table[32 * 256 + 30] = 20; + table[32 * 256 + 31] = 20; + table[32 * 256 + 32] = 20; + table[32 * 256 + 33] = 20; + table[32 * 256 + 34] = 20; + table[32 * 256 + 35] = 20; + table[32 * 256 + 36] = 20; + table[32 * 256 + 37] = 20; + table[32 * 256 + 38] = 20; + table[32 * 256 + 39] = 20; + table[32 * 256 + 40] = 20; + table[32 * 256 + 41] = 20; + table[32 * 256 + 42] = 20; + table[32 * 256 + 44] = 20; + table[32 * 256 + 45] = 20; + table[32 * 256 + 46] = 20; + table[32 * 256 + 58] = 20; + table[32 * 256 + 60] = 20; + table[32 * 256 + 62] = 20; + table[32 * 256 + 63] = 20; + table[32 * 256 + 64] = 20; + table[32 * 256 + 91] = 20; + table[32 * 256 + 92] = 20; + table[32 * 256 + 93] = 20; + table[32 * 256 + 94] = 20; + table[32 * 256 + 95] = 20; + table[32 * 256 + 96] = 20; + table[32 * 256 + 123] = 20; + table[32 * 256 + 124] = 20; + table[32 * 256 + 125] = 20; + table[32 * 256 + 126] = 20; + table[32 * 256 + 127] = 20; + table[32 * 256 + 194] = 21; + table[32 * 256 + 195] = 21; + table[32 * 256 + 196] = 21; + table[32 * 256 + 197] = 21; + table[32 * 256 + 198] = 21; + table[32 * 256 + 199] = 21; + table[32 * 256 + 200] = 21; + table[32 * 256 + 201] = 21; + table[32 * 256 + 202] = 21; + table[32 * 256 + 203] = 21; + table[32 * 256 + 204] = 21; + table[32 * 256 + 205] = 21; + table[32 * 256 + 206] = 21; + table[32 * 256 + 207] = 21; + table[32 * 256 + 208] = 21; + table[32 * 256 + 209] = 21; + table[32 * 256 + 210] = 21; + table[32 * 256 + 211] = 21; + table[32 * 256 + 212] = 21; + table[32 * 256 + 213] = 21; + table[32 * 256 + 214] = 21; + table[32 * 256 + 215] = 21; + table[32 * 256 + 216] = 21; + table[32 * 256 + 217] = 21; + table[32 * 256 + 218] = 21; + table[32 * 256 + 219] = 21; + table[32 * 256 + 220] = 21; + table[32 * 256 + 221] = 21; + table[32 * 256 + 222] = 21; + table[32 * 256 + 223] = 21; + table[32 * 256 + 224] = 22; + table[32 * 256 + 225] = 23; + table[32 * 256 + 226] = 23; + table[32 * 256 + 227] = 23; + table[32 * 256 + 228] = 23; + table[32 * 256 + 229] = 23; + table[32 * 256 + 230] = 23; + table[32 * 256 + 231] = 23; + table[32 * 256 + 232] = 23; + table[32 * 256 + 233] = 23; + table[32 * 256 + 234] = 23; + table[32 * 256 + 235] = 23; + table[32 * 256 + 236] = 23; + table[32 * 256 + 238] = 23; + table[32 * 256 + 239] = 23; + table[32 * 256 + 237] = 24; + table[32 * 256 + 240] = 25; + table[32 * 256 + 241] = 26; + table[32 * 256 + 242] = 26; + table[32 * 256 + 243] = 26; + table[32 * 256 + 244] = 27; + table[32 * 256 + 43] = 33; + table[32 * 256 + 47] = 33; + table[32 * 256 + 48] = 33; + table[32 * 256 + 49] = 33; + table[32 * 256 + 50] = 33; + table[32 * 256 + 51] = 33; + table[32 * 256 + 52] = 33; + table[32 * 256 + 53] = 33; + table[32 * 256 + 54] = 33; + table[32 * 256 + 55] = 33; + table[32 * 256 + 56] = 33; + table[32 * 256 + 57] = 33; + table[32 * 256 + 61] = 33; + table[32 * 256 + 65] = 33; + table[32 * 256 + 66] = 33; + table[32 * 256 + 67] = 33; + table[32 * 256 + 68] = 33; + table[32 * 256 + 69] = 33; + table[32 * 256 + 70] = 33; + table[32 * 256 + 71] = 33; + table[32 * 256 + 72] = 33; + table[32 * 256 + 73] = 33; + table[32 * 256 + 74] = 33; + table[32 * 256 + 75] = 33; + table[32 * 256 + 76] = 33; + table[32 * 256 + 77] = 33; + table[32 * 256 + 78] = 33; + table[32 * 256 + 79] = 33; + table[32 * 256 + 80] = 33; + table[32 * 256 + 81] = 33; + table[32 * 256 + 82] = 33; + table[32 * 256 + 83] = 33; + table[32 * 256 + 84] = 33; + table[32 * 256 + 85] = 33; + table[32 * 256 + 86] = 33; + table[32 * 256 + 87] = 33; + table[32 * 256 + 88] = 33; + table[32 * 256 + 89] = 33; + table[32 * 256 + 90] = 33; + table[32 * 256 + 97] = 33; + table[32 * 256 + 98] = 33; + table[32 * 256 + 99] = 33; + table[32 * 256 + 100] = 33; + table[32 * 256 + 101] = 33; + table[32 * 256 + 102] = 33; + table[32 * 256 + 103] = 33; + table[32 * 256 + 104] = 33; + table[32 * 256 + 105] = 33; + table[32 * 256 + 106] = 33; + table[32 * 256 + 107] = 33; + table[32 * 256 + 108] = 33; + table[32 * 256 + 109] = 33; + table[32 * 256 + 110] = 33; + table[32 * 256 + 111] = 33; + table[32 * 256 + 112] = 33; + table[32 * 256 + 113] = 33; + table[32 * 256 + 114] = 33; + table[32 * 256 + 115] = 33; + table[32 * 256 + 116] = 33; + table[32 * 256 + 117] = 33; + table[32 * 256 + 118] = 33; + table[32 * 256 + 119] = 33; + table[32 * 256 + 120] = 33; + table[32 * 256 + 121] = 33; + table[32 * 256 + 122] = 33; + table[33 * 256 + 43] = 33; + table[33 * 256 + 47] = 33; + table[33 * 256 + 48] = 33; + table[33 * 256 + 49] = 33; + table[33 * 256 + 50] = 33; + table[33 * 256 + 51] = 33; + table[33 * 256 + 52] = 33; + table[33 * 256 + 53] = 33; + table[33 * 256 + 54] = 33; + table[33 * 256 + 55] = 33; + table[33 * 256 + 56] = 33; + table[33 * 256 + 57] = 33; + table[33 * 256 + 61] = 33; + table[33 * 256 + 65] = 33; + table[33 * 256 + 66] = 33; + table[33 * 256 + 67] = 33; + table[33 * 256 + 68] = 33; + table[33 * 256 + 69] = 33; + table[33 * 256 + 70] = 33; + table[33 * 256 + 71] = 33; + table[33 * 256 + 72] = 33; + table[33 * 256 + 73] = 33; + table[33 * 256 + 74] = 33; + table[33 * 256 + 75] = 33; + table[33 * 256 + 76] = 33; + table[33 * 256 + 77] = 33; + table[33 * 256 + 78] = 33; + table[33 * 256 + 79] = 33; + table[33 * 256 + 80] = 33; + table[33 * 256 + 81] = 33; + table[33 * 256 + 82] = 33; + table[33 * 256 + 83] = 33; + table[33 * 256 + 84] = 33; + table[33 * 256 + 85] = 33; + table[33 * 256 + 86] = 33; + table[33 * 256 + 87] = 33; + table[33 * 256 + 88] = 33; + table[33 * 256 + 89] = 33; + table[33 * 256 + 90] = 33; + table[33 * 256 + 97] = 33; + table[33 * 256 + 98] = 33; + table[33 * 256 + 99] = 33; + table[33 * 256 + 100] = 33; + table[33 * 256 + 101] = 33; + table[33 * 256 + 102] = 33; + table[33 * 256 + 103] = 33; + table[33 * 256 + 104] = 33; + table[33 * 256 + 105] = 33; + table[33 * 256 + 106] = 33; + table[33 * 256 + 107] = 33; + table[33 * 256 + 108] = 33; + table[33 * 256 + 109] = 33; + table[33 * 256 + 110] = 33; + table[33 * 256 + 111] = 33; + table[33 * 256 + 112] = 33; + table[33 * 256 + 113] = 33; + table[33 * 256 + 114] = 33; + table[33 * 256 + 115] = 33; + table[33 * 256 + 116] = 33; + table[33 * 256 + 117] = 33; + table[33 * 256 + 118] = 33; + table[33 * 256 + 119] = 33; + table[33 * 256 + 120] = 33; + table[33 * 256 + 121] = 33; + table[33 * 256 + 122] = 33; + table[33 * 256 + 59] = 34; + + table +} +pub fn regex_match(input: [u8; N]) -> bool { + // regex: (\r\n|^)dkim-signature:([a-z]+=[^;]+; )+bh=[a-zA-Z0-9+/=]+; + let mut s = 0; + s = table[255]; + for i in 0..input.len() { + let s_idx = s * 256 + input[i] as Field; + std::as_witness(s_idx); + s = table[s_idx]; + } + + let matched: bool = (s == 34) | (s == 35); + + matched +} + + \ No newline at end of file diff --git a/packages/noir/src/basic/email_addr.nr b/packages/noir/src/basic/email_addr.nr new file mode 100644 index 00000000..f036c6f0 --- /dev/null +++ b/packages/noir/src/basic/email_addr.nr @@ -0,0 +1,869 @@ + +use crate::common::Sequence; + + +global table: [Field; 1280] = comptime { make_lookup_table() }; + +comptime fn make_lookup_table() -> [Field; 1280] { + let mut table = [0; 1280]; + table[3 * 256 + 0] = 4; + table[4 * 256 + 0] = 4; + table[3 * 256 + 1] = 4; + table[4 * 256 + 1] = 4; + table[3 * 256 + 2] = 4; + table[4 * 256 + 2] = 4; + table[3 * 256 + 3] = 4; + table[4 * 256 + 3] = 4; + table[3 * 256 + 4] = 4; + table[4 * 256 + 4] = 4; + table[3 * 256 + 5] = 4; + table[4 * 256 + 5] = 4; + table[3 * 256 + 6] = 4; + table[4 * 256 + 6] = 4; + table[3 * 256 + 7] = 4; + table[4 * 256 + 7] = 4; + table[3 * 256 + 8] = 4; + table[4 * 256 + 8] = 4; + table[3 * 256 + 9] = 4; + table[4 * 256 + 9] = 4; + table[3 * 256 + 10] = 4; + table[4 * 256 + 10] = 4; + table[3 * 256 + 11] = 4; + table[4 * 256 + 11] = 4; + table[3 * 256 + 12] = 4; + table[4 * 256 + 12] = 4; + table[3 * 256 + 13] = 4; + table[4 * 256 + 13] = 4; + table[3 * 256 + 14] = 4; + table[4 * 256 + 14] = 4; + table[3 * 256 + 15] = 4; + table[4 * 256 + 15] = 4; + table[3 * 256 + 16] = 4; + table[4 * 256 + 16] = 4; + table[3 * 256 + 17] = 4; + table[4 * 256 + 17] = 4; + table[3 * 256 + 18] = 4; + table[4 * 256 + 18] = 4; + table[3 * 256 + 19] = 4; + table[4 * 256 + 19] = 4; + table[3 * 256 + 20] = 4; + table[4 * 256 + 20] = 4; + table[3 * 256 + 21] = 4; + table[4 * 256 + 21] = 4; + table[3 * 256 + 22] = 4; + table[4 * 256 + 22] = 4; + table[3 * 256 + 23] = 4; + table[4 * 256 + 23] = 4; + table[3 * 256 + 24] = 4; + table[4 * 256 + 24] = 4; + table[3 * 256 + 25] = 4; + table[4 * 256 + 25] = 4; + table[3 * 256 + 26] = 4; + table[4 * 256 + 26] = 4; + table[3 * 256 + 27] = 4; + table[4 * 256 + 27] = 4; + table[3 * 256 + 28] = 4; + table[4 * 256 + 28] = 4; + table[3 * 256 + 29] = 4; + table[4 * 256 + 29] = 4; + table[3 * 256 + 30] = 4; + table[4 * 256 + 30] = 4; + table[3 * 256 + 31] = 4; + table[4 * 256 + 31] = 4; + table[3 * 256 + 32] = 4; + table[4 * 256 + 32] = 4; + table[3 * 256 + 33] = 4; + table[4 * 256 + 33] = 4; + table[3 * 256 + 34] = 4; + table[4 * 256 + 34] = 4; + table[3 * 256 + 35] = 4; + table[4 * 256 + 35] = 4; + table[3 * 256 + 36] = 4; + table[4 * 256 + 36] = 4; + table[3 * 256 + 37] = 4; + table[4 * 256 + 37] = 4; + table[3 * 256 + 38] = 4; + table[4 * 256 + 38] = 4; + table[3 * 256 + 39] = 4; + table[4 * 256 + 39] = 4; + table[3 * 256 + 40] = 4; + table[4 * 256 + 40] = 4; + table[3 * 256 + 41] = 4; + table[4 * 256 + 41] = 4; + table[3 * 256 + 42] = 4; + table[4 * 256 + 42] = 4; + table[3 * 256 + 43] = 4; + table[4 * 256 + 43] = 4; + table[3 * 256 + 44] = 4; + table[4 * 256 + 44] = 4; + table[3 * 256 + 45] = 4; + table[4 * 256 + 45] = 4; + table[3 * 256 + 46] = 4; + table[4 * 256 + 46] = 4; + table[3 * 256 + 47] = 4; + table[4 * 256 + 47] = 4; + table[3 * 256 + 48] = 4; + table[4 * 256 + 48] = 4; + table[3 * 256 + 49] = 4; + table[4 * 256 + 49] = 4; + table[3 * 256 + 50] = 4; + table[4 * 256 + 50] = 4; + table[3 * 256 + 51] = 4; + table[4 * 256 + 51] = 4; + table[3 * 256 + 52] = 4; + table[4 * 256 + 52] = 4; + table[3 * 256 + 53] = 4; + table[4 * 256 + 53] = 4; + table[3 * 256 + 54] = 4; + table[4 * 256 + 54] = 4; + table[3 * 256 + 55] = 4; + table[4 * 256 + 55] = 4; + table[3 * 256 + 56] = 4; + table[4 * 256 + 56] = 4; + table[3 * 256 + 57] = 4; + table[4 * 256 + 57] = 4; + table[3 * 256 + 58] = 4; + table[4 * 256 + 58] = 4; + table[3 * 256 + 59] = 4; + table[4 * 256 + 59] = 4; + table[3 * 256 + 60] = 4; + table[4 * 256 + 60] = 4; + table[3 * 256 + 61] = 4; + table[4 * 256 + 61] = 4; + table[3 * 256 + 62] = 4; + table[4 * 256 + 62] = 4; + table[3 * 256 + 63] = 4; + table[4 * 256 + 63] = 4; + table[3 * 256 + 64] = 4; + table[4 * 256 + 64] = 4; + table[3 * 256 + 65] = 4; + table[4 * 256 + 65] = 4; + table[3 * 256 + 66] = 4; + table[4 * 256 + 66] = 4; + table[3 * 256 + 67] = 4; + table[4 * 256 + 67] = 4; + table[3 * 256 + 68] = 4; + table[4 * 256 + 68] = 4; + table[3 * 256 + 69] = 4; + table[4 * 256 + 69] = 4; + table[3 * 256 + 70] = 4; + table[4 * 256 + 70] = 4; + table[3 * 256 + 71] = 4; + table[4 * 256 + 71] = 4; + table[3 * 256 + 72] = 4; + table[4 * 256 + 72] = 4; + table[3 * 256 + 73] = 4; + table[4 * 256 + 73] = 4; + table[3 * 256 + 74] = 4; + table[4 * 256 + 74] = 4; + table[3 * 256 + 75] = 4; + table[4 * 256 + 75] = 4; + table[3 * 256 + 76] = 4; + table[4 * 256 + 76] = 4; + table[3 * 256 + 77] = 4; + table[4 * 256 + 77] = 4; + table[3 * 256 + 78] = 4; + table[4 * 256 + 78] = 4; + table[3 * 256 + 79] = 4; + table[4 * 256 + 79] = 4; + table[3 * 256 + 80] = 4; + table[4 * 256 + 80] = 4; + table[3 * 256 + 81] = 4; + table[4 * 256 + 81] = 4; + table[3 * 256 + 82] = 4; + table[4 * 256 + 82] = 4; + table[3 * 256 + 83] = 4; + table[4 * 256 + 83] = 4; + table[3 * 256 + 84] = 4; + table[4 * 256 + 84] = 4; + table[3 * 256 + 85] = 4; + table[4 * 256 + 85] = 4; + table[3 * 256 + 86] = 4; + table[4 * 256 + 86] = 4; + table[3 * 256 + 87] = 4; + table[4 * 256 + 87] = 4; + table[3 * 256 + 88] = 4; + table[4 * 256 + 88] = 4; + table[3 * 256 + 89] = 4; + table[4 * 256 + 89] = 4; + table[3 * 256 + 90] = 4; + table[4 * 256 + 90] = 4; + table[3 * 256 + 91] = 4; + table[4 * 256 + 91] = 4; + table[3 * 256 + 92] = 4; + table[4 * 256 + 92] = 4; + table[3 * 256 + 93] = 4; + table[4 * 256 + 93] = 4; + table[3 * 256 + 94] = 4; + table[4 * 256 + 94] = 4; + table[3 * 256 + 95] = 4; + table[4 * 256 + 95] = 4; + table[3 * 256 + 96] = 4; + table[4 * 256 + 96] = 4; + table[3 * 256 + 97] = 4; + table[4 * 256 + 97] = 4; + table[3 * 256 + 98] = 4; + table[4 * 256 + 98] = 4; + table[3 * 256 + 99] = 4; + table[4 * 256 + 99] = 4; + table[3 * 256 + 100] = 4; + table[4 * 256 + 100] = 4; + table[3 * 256 + 101] = 4; + table[4 * 256 + 101] = 4; + table[3 * 256 + 102] = 4; + table[4 * 256 + 102] = 4; + table[3 * 256 + 103] = 4; + table[4 * 256 + 103] = 4; + table[3 * 256 + 104] = 4; + table[4 * 256 + 104] = 4; + table[3 * 256 + 105] = 4; + table[4 * 256 + 105] = 4; + table[3 * 256 + 106] = 4; + table[4 * 256 + 106] = 4; + table[3 * 256 + 107] = 4; + table[4 * 256 + 107] = 4; + table[3 * 256 + 108] = 4; + table[4 * 256 + 108] = 4; + table[3 * 256 + 109] = 4; + table[4 * 256 + 109] = 4; + table[3 * 256 + 110] = 4; + table[4 * 256 + 110] = 4; + table[3 * 256 + 111] = 4; + table[4 * 256 + 111] = 4; + table[3 * 256 + 112] = 4; + table[4 * 256 + 112] = 4; + table[3 * 256 + 113] = 4; + table[4 * 256 + 113] = 4; + table[3 * 256 + 114] = 4; + table[4 * 256 + 114] = 4; + table[3 * 256 + 115] = 4; + table[4 * 256 + 115] = 4; + table[3 * 256 + 116] = 4; + table[4 * 256 + 116] = 4; + table[3 * 256 + 117] = 4; + table[4 * 256 + 117] = 4; + table[3 * 256 + 118] = 4; + table[4 * 256 + 118] = 4; + table[3 * 256 + 119] = 4; + table[4 * 256 + 119] = 4; + table[3 * 256 + 120] = 4; + table[4 * 256 + 120] = 4; + table[3 * 256 + 121] = 4; + table[4 * 256 + 121] = 4; + table[3 * 256 + 122] = 4; + table[4 * 256 + 122] = 4; + table[3 * 256 + 123] = 4; + table[4 * 256 + 123] = 4; + table[3 * 256 + 124] = 4; + table[4 * 256 + 124] = 4; + table[3 * 256 + 125] = 4; + table[4 * 256 + 125] = 4; + table[3 * 256 + 126] = 4; + table[4 * 256 + 126] = 4; + table[3 * 256 + 127] = 4; + table[4 * 256 + 127] = 4; + table[3 * 256 + 128] = 4; + table[4 * 256 + 128] = 4; + table[3 * 256 + 129] = 4; + table[4 * 256 + 129] = 4; + table[3 * 256 + 130] = 4; + table[4 * 256 + 130] = 4; + table[3 * 256 + 131] = 4; + table[4 * 256 + 131] = 4; + table[3 * 256 + 132] = 4; + table[4 * 256 + 132] = 4; + table[3 * 256 + 133] = 4; + table[4 * 256 + 133] = 4; + table[3 * 256 + 134] = 4; + table[4 * 256 + 134] = 4; + table[3 * 256 + 135] = 4; + table[4 * 256 + 135] = 4; + table[3 * 256 + 136] = 4; + table[4 * 256 + 136] = 4; + table[3 * 256 + 137] = 4; + table[4 * 256 + 137] = 4; + table[3 * 256 + 138] = 4; + table[4 * 256 + 138] = 4; + table[3 * 256 + 139] = 4; + table[4 * 256 + 139] = 4; + table[3 * 256 + 140] = 4; + table[4 * 256 + 140] = 4; + table[3 * 256 + 141] = 4; + table[4 * 256 + 141] = 4; + table[3 * 256 + 142] = 4; + table[4 * 256 + 142] = 4; + table[3 * 256 + 143] = 4; + table[4 * 256 + 143] = 4; + table[3 * 256 + 144] = 4; + table[4 * 256 + 144] = 4; + table[3 * 256 + 145] = 4; + table[4 * 256 + 145] = 4; + table[3 * 256 + 146] = 4; + table[4 * 256 + 146] = 4; + table[3 * 256 + 147] = 4; + table[4 * 256 + 147] = 4; + table[3 * 256 + 148] = 4; + table[4 * 256 + 148] = 4; + table[3 * 256 + 149] = 4; + table[4 * 256 + 149] = 4; + table[3 * 256 + 150] = 4; + table[4 * 256 + 150] = 4; + table[3 * 256 + 151] = 4; + table[4 * 256 + 151] = 4; + table[3 * 256 + 152] = 4; + table[4 * 256 + 152] = 4; + table[3 * 256 + 153] = 4; + table[4 * 256 + 153] = 4; + table[3 * 256 + 154] = 4; + table[4 * 256 + 154] = 4; + table[3 * 256 + 155] = 4; + table[4 * 256 + 155] = 4; + table[3 * 256 + 156] = 4; + table[4 * 256 + 156] = 4; + table[3 * 256 + 157] = 4; + table[4 * 256 + 157] = 4; + table[3 * 256 + 158] = 4; + table[4 * 256 + 158] = 4; + table[3 * 256 + 159] = 4; + table[4 * 256 + 159] = 4; + table[3 * 256 + 160] = 4; + table[4 * 256 + 160] = 4; + table[3 * 256 + 161] = 4; + table[4 * 256 + 161] = 4; + table[3 * 256 + 162] = 4; + table[4 * 256 + 162] = 4; + table[3 * 256 + 163] = 4; + table[4 * 256 + 163] = 4; + table[3 * 256 + 164] = 4; + table[4 * 256 + 164] = 4; + table[3 * 256 + 165] = 4; + table[4 * 256 + 165] = 4; + table[3 * 256 + 166] = 4; + table[4 * 256 + 166] = 4; + table[3 * 256 + 167] = 4; + table[4 * 256 + 167] = 4; + table[3 * 256 + 168] = 4; + table[4 * 256 + 168] = 4; + table[3 * 256 + 169] = 4; + table[4 * 256 + 169] = 4; + table[3 * 256 + 170] = 4; + table[4 * 256 + 170] = 4; + table[3 * 256 + 171] = 4; + table[4 * 256 + 171] = 4; + table[3 * 256 + 172] = 4; + table[4 * 256 + 172] = 4; + table[3 * 256 + 173] = 4; + table[4 * 256 + 173] = 4; + table[3 * 256 + 174] = 4; + table[4 * 256 + 174] = 4; + table[3 * 256 + 175] = 4; + table[4 * 256 + 175] = 4; + table[3 * 256 + 176] = 4; + table[4 * 256 + 176] = 4; + table[3 * 256 + 177] = 4; + table[4 * 256 + 177] = 4; + table[3 * 256 + 178] = 4; + table[4 * 256 + 178] = 4; + table[3 * 256 + 179] = 4; + table[4 * 256 + 179] = 4; + table[3 * 256 + 180] = 4; + table[4 * 256 + 180] = 4; + table[3 * 256 + 181] = 4; + table[4 * 256 + 181] = 4; + table[3 * 256 + 182] = 4; + table[4 * 256 + 182] = 4; + table[3 * 256 + 183] = 4; + table[4 * 256 + 183] = 4; + table[3 * 256 + 184] = 4; + table[4 * 256 + 184] = 4; + table[3 * 256 + 185] = 4; + table[4 * 256 + 185] = 4; + table[3 * 256 + 186] = 4; + table[4 * 256 + 186] = 4; + table[3 * 256 + 187] = 4; + table[4 * 256 + 187] = 4; + table[3 * 256 + 188] = 4; + table[4 * 256 + 188] = 4; + table[3 * 256 + 189] = 4; + table[4 * 256 + 189] = 4; + table[3 * 256 + 190] = 4; + table[4 * 256 + 190] = 4; + table[3 * 256 + 191] = 4; + table[4 * 256 + 191] = 4; + table[3 * 256 + 192] = 4; + table[4 * 256 + 192] = 4; + table[3 * 256 + 193] = 4; + table[4 * 256 + 193] = 4; + table[3 * 256 + 194] = 4; + table[4 * 256 + 194] = 4; + table[3 * 256 + 195] = 4; + table[4 * 256 + 195] = 4; + table[3 * 256 + 196] = 4; + table[4 * 256 + 196] = 4; + table[3 * 256 + 197] = 4; + table[4 * 256 + 197] = 4; + table[3 * 256 + 198] = 4; + table[4 * 256 + 198] = 4; + table[3 * 256 + 199] = 4; + table[4 * 256 + 199] = 4; + table[3 * 256 + 200] = 4; + table[4 * 256 + 200] = 4; + table[3 * 256 + 201] = 4; + table[4 * 256 + 201] = 4; + table[3 * 256 + 202] = 4; + table[4 * 256 + 202] = 4; + table[3 * 256 + 203] = 4; + table[4 * 256 + 203] = 4; + table[3 * 256 + 204] = 4; + table[4 * 256 + 204] = 4; + table[3 * 256 + 205] = 4; + table[4 * 256 + 205] = 4; + table[3 * 256 + 206] = 4; + table[4 * 256 + 206] = 4; + table[3 * 256 + 207] = 4; + table[4 * 256 + 207] = 4; + table[3 * 256 + 208] = 4; + table[4 * 256 + 208] = 4; + table[3 * 256 + 209] = 4; + table[4 * 256 + 209] = 4; + table[3 * 256 + 210] = 4; + table[4 * 256 + 210] = 4; + table[3 * 256 + 211] = 4; + table[4 * 256 + 211] = 4; + table[3 * 256 + 212] = 4; + table[4 * 256 + 212] = 4; + table[3 * 256 + 213] = 4; + table[4 * 256 + 213] = 4; + table[3 * 256 + 214] = 4; + table[4 * 256 + 214] = 4; + table[3 * 256 + 215] = 4; + table[4 * 256 + 215] = 4; + table[3 * 256 + 216] = 4; + table[4 * 256 + 216] = 4; + table[3 * 256 + 217] = 4; + table[4 * 256 + 217] = 4; + table[3 * 256 + 218] = 4; + table[4 * 256 + 218] = 4; + table[3 * 256 + 219] = 4; + table[4 * 256 + 219] = 4; + table[3 * 256 + 220] = 4; + table[4 * 256 + 220] = 4; + table[3 * 256 + 221] = 4; + table[4 * 256 + 221] = 4; + table[3 * 256 + 222] = 4; + table[4 * 256 + 222] = 4; + table[3 * 256 + 223] = 4; + table[4 * 256 + 223] = 4; + table[3 * 256 + 224] = 4; + table[4 * 256 + 224] = 4; + table[3 * 256 + 225] = 4; + table[4 * 256 + 225] = 4; + table[3 * 256 + 226] = 4; + table[4 * 256 + 226] = 4; + table[3 * 256 + 227] = 4; + table[4 * 256 + 227] = 4; + table[3 * 256 + 228] = 4; + table[4 * 256 + 228] = 4; + table[3 * 256 + 229] = 4; + table[4 * 256 + 229] = 4; + table[3 * 256 + 230] = 4; + table[4 * 256 + 230] = 4; + table[3 * 256 + 231] = 4; + table[4 * 256 + 231] = 4; + table[3 * 256 + 232] = 4; + table[4 * 256 + 232] = 4; + table[3 * 256 + 233] = 4; + table[4 * 256 + 233] = 4; + table[3 * 256 + 234] = 4; + table[4 * 256 + 234] = 4; + table[3 * 256 + 235] = 4; + table[4 * 256 + 235] = 4; + table[3 * 256 + 236] = 4; + table[4 * 256 + 236] = 4; + table[3 * 256 + 237] = 4; + table[4 * 256 + 237] = 4; + table[3 * 256 + 238] = 4; + table[4 * 256 + 238] = 4; + table[3 * 256 + 239] = 4; + table[4 * 256 + 239] = 4; + table[3 * 256 + 240] = 4; + table[4 * 256 + 240] = 4; + table[3 * 256 + 241] = 4; + table[4 * 256 + 241] = 4; + table[3 * 256 + 242] = 4; + table[4 * 256 + 242] = 4; + table[3 * 256 + 243] = 4; + table[4 * 256 + 243] = 4; + table[3 * 256 + 244] = 4; + table[4 * 256 + 244] = 4; + table[3 * 256 + 245] = 4; + table[4 * 256 + 245] = 4; + table[3 * 256 + 246] = 4; + table[4 * 256 + 246] = 4; + table[3 * 256 + 247] = 4; + table[4 * 256 + 247] = 4; + table[3 * 256 + 248] = 4; + table[4 * 256 + 248] = 4; + table[3 * 256 + 249] = 4; + table[4 * 256 + 249] = 4; + table[3 * 256 + 250] = 4; + table[4 * 256 + 250] = 4; + table[3 * 256 + 251] = 4; + table[4 * 256 + 251] = 4; + table[3 * 256 + 252] = 4; + table[4 * 256 + 252] = 4; + table[3 * 256 + 253] = 4; + table[4 * 256 + 253] = 4; + table[3 * 256 + 254] = 4; + table[4 * 256 + 254] = 4; + table[0 * 256 + 33] = 1; + table[0 * 256 + 35] = 1; + table[0 * 256 + 36] = 1; + table[0 * 256 + 37] = 1; + table[0 * 256 + 38] = 1; + table[0 * 256 + 39] = 1; + table[0 * 256 + 42] = 1; + table[0 * 256 + 43] = 1; + table[0 * 256 + 45] = 1; + table[0 * 256 + 46] = 1; + table[0 * 256 + 47] = 1; + table[0 * 256 + 48] = 1; + table[0 * 256 + 49] = 1; + table[0 * 256 + 50] = 1; + table[0 * 256 + 51] = 1; + table[0 * 256 + 52] = 1; + table[0 * 256 + 53] = 1; + table[0 * 256 + 54] = 1; + table[0 * 256 + 55] = 1; + table[0 * 256 + 56] = 1; + table[0 * 256 + 57] = 1; + table[0 * 256 + 61] = 1; + table[0 * 256 + 63] = 1; + table[0 * 256 + 64] = 1; + table[0 * 256 + 65] = 1; + table[0 * 256 + 66] = 1; + table[0 * 256 + 67] = 1; + table[0 * 256 + 68] = 1; + table[0 * 256 + 69] = 1; + table[0 * 256 + 70] = 1; + table[0 * 256 + 71] = 1; + table[0 * 256 + 72] = 1; + table[0 * 256 + 73] = 1; + table[0 * 256 + 74] = 1; + table[0 * 256 + 75] = 1; + table[0 * 256 + 76] = 1; + table[0 * 256 + 77] = 1; + table[0 * 256 + 78] = 1; + table[0 * 256 + 79] = 1; + table[0 * 256 + 80] = 1; + table[0 * 256 + 81] = 1; + table[0 * 256 + 82] = 1; + table[0 * 256 + 83] = 1; + table[0 * 256 + 84] = 1; + table[0 * 256 + 85] = 1; + table[0 * 256 + 86] = 1; + table[0 * 256 + 87] = 1; + table[0 * 256 + 88] = 1; + table[0 * 256 + 89] = 1; + table[0 * 256 + 90] = 1; + table[0 * 256 + 94] = 1; + table[0 * 256 + 95] = 1; + table[0 * 256 + 96] = 1; + table[0 * 256 + 97] = 1; + table[0 * 256 + 98] = 1; + table[0 * 256 + 99] = 1; + table[0 * 256 + 100] = 1; + table[0 * 256 + 101] = 1; + table[0 * 256 + 102] = 1; + table[0 * 256 + 103] = 1; + table[0 * 256 + 104] = 1; + table[0 * 256 + 105] = 1; + table[0 * 256 + 106] = 1; + table[0 * 256 + 107] = 1; + table[0 * 256 + 108] = 1; + table[0 * 256 + 109] = 1; + table[0 * 256 + 110] = 1; + table[0 * 256 + 111] = 1; + table[0 * 256 + 112] = 1; + table[0 * 256 + 113] = 1; + table[0 * 256 + 114] = 1; + table[0 * 256 + 115] = 1; + table[0 * 256 + 116] = 1; + table[0 * 256 + 117] = 1; + table[0 * 256 + 118] = 1; + table[0 * 256 + 119] = 1; + table[0 * 256 + 120] = 1; + table[0 * 256 + 121] = 1; + table[0 * 256 + 122] = 1; + table[0 * 256 + 123] = 1; + table[0 * 256 + 124] = 1; + table[0 * 256 + 125] = 1; + table[0 * 256 + 126] = 1; + table[1 * 256 + 33] = 1; + table[1 * 256 + 35] = 1; + table[1 * 256 + 36] = 1; + table[1 * 256 + 37] = 1; + table[1 * 256 + 38] = 1; + table[1 * 256 + 39] = 1; + table[1 * 256 + 42] = 1; + table[1 * 256 + 43] = 1; + table[1 * 256 + 45] = 1; + table[1 * 256 + 46] = 1; + table[1 * 256 + 47] = 1; + table[1 * 256 + 48] = 1; + table[1 * 256 + 49] = 1; + table[1 * 256 + 50] = 1; + table[1 * 256 + 51] = 1; + table[1 * 256 + 52] = 1; + table[1 * 256 + 53] = 1; + table[1 * 256 + 54] = 1; + table[1 * 256 + 55] = 1; + table[1 * 256 + 56] = 1; + table[1 * 256 + 57] = 1; + table[1 * 256 + 61] = 1; + table[1 * 256 + 63] = 1; + table[1 * 256 + 65] = 1; + table[1 * 256 + 66] = 1; + table[1 * 256 + 67] = 1; + table[1 * 256 + 68] = 1; + table[1 * 256 + 69] = 1; + table[1 * 256 + 70] = 1; + table[1 * 256 + 71] = 1; + table[1 * 256 + 72] = 1; + table[1 * 256 + 73] = 1; + table[1 * 256 + 74] = 1; + table[1 * 256 + 75] = 1; + table[1 * 256 + 76] = 1; + table[1 * 256 + 77] = 1; + table[1 * 256 + 78] = 1; + table[1 * 256 + 79] = 1; + table[1 * 256 + 80] = 1; + table[1 * 256 + 81] = 1; + table[1 * 256 + 82] = 1; + table[1 * 256 + 83] = 1; + table[1 * 256 + 84] = 1; + table[1 * 256 + 85] = 1; + table[1 * 256 + 86] = 1; + table[1 * 256 + 87] = 1; + table[1 * 256 + 88] = 1; + table[1 * 256 + 89] = 1; + table[1 * 256 + 90] = 1; + table[1 * 256 + 94] = 1; + table[1 * 256 + 95] = 1; + table[1 * 256 + 96] = 1; + table[1 * 256 + 97] = 1; + table[1 * 256 + 98] = 1; + table[1 * 256 + 99] = 1; + table[1 * 256 + 100] = 1; + table[1 * 256 + 101] = 1; + table[1 * 256 + 102] = 1; + table[1 * 256 + 103] = 1; + table[1 * 256 + 104] = 1; + table[1 * 256 + 105] = 1; + table[1 * 256 + 106] = 1; + table[1 * 256 + 107] = 1; + table[1 * 256 + 108] = 1; + table[1 * 256 + 109] = 1; + table[1 * 256 + 110] = 1; + table[1 * 256 + 111] = 1; + table[1 * 256 + 112] = 1; + table[1 * 256 + 113] = 1; + table[1 * 256 + 114] = 1; + table[1 * 256 + 115] = 1; + table[1 * 256 + 116] = 1; + table[1 * 256 + 117] = 1; + table[1 * 256 + 118] = 1; + table[1 * 256 + 119] = 1; + table[1 * 256 + 120] = 1; + table[1 * 256 + 121] = 1; + table[1 * 256 + 122] = 1; + table[1 * 256 + 123] = 1; + table[1 * 256 + 124] = 1; + table[1 * 256 + 125] = 1; + table[1 * 256 + 126] = 1; + table[1 * 256 + 64] = 2; + table[2 * 256 + 33] = 1; + table[2 * 256 + 35] = 1; + table[2 * 256 + 36] = 1; + table[2 * 256 + 37] = 1; + table[2 * 256 + 38] = 1; + table[2 * 256 + 39] = 1; + table[2 * 256 + 42] = 1; + table[2 * 256 + 43] = 1; + table[2 * 256 + 47] = 1; + table[2 * 256 + 61] = 1; + table[2 * 256 + 63] = 1; + table[2 * 256 + 94] = 1; + table[2 * 256 + 95] = 1; + table[2 * 256 + 96] = 1; + table[2 * 256 + 123] = 1; + table[2 * 256 + 124] = 1; + table[2 * 256 + 125] = 1; + table[2 * 256 + 126] = 1; + table[2 * 256 + 64] = 2; + table[2 * 256 + 45] = 3; + table[2 * 256 + 46] = 3; + table[2 * 256 + 48] = 3; + table[2 * 256 + 49] = 3; + table[2 * 256 + 50] = 3; + table[2 * 256 + 51] = 3; + table[2 * 256 + 52] = 3; + table[2 * 256 + 53] = 3; + table[2 * 256 + 54] = 3; + table[2 * 256 + 55] = 3; + table[2 * 256 + 56] = 3; + table[2 * 256 + 57] = 3; + table[2 * 256 + 65] = 3; + table[2 * 256 + 66] = 3; + table[2 * 256 + 67] = 3; + table[2 * 256 + 68] = 3; + table[2 * 256 + 69] = 3; + table[2 * 256 + 70] = 3; + table[2 * 256 + 71] = 3; + table[2 * 256 + 72] = 3; + table[2 * 256 + 73] = 3; + table[2 * 256 + 74] = 3; + table[2 * 256 + 75] = 3; + table[2 * 256 + 76] = 3; + table[2 * 256 + 77] = 3; + table[2 * 256 + 78] = 3; + table[2 * 256 + 79] = 3; + table[2 * 256 + 80] = 3; + table[2 * 256 + 81] = 3; + table[2 * 256 + 82] = 3; + table[2 * 256 + 83] = 3; + table[2 * 256 + 84] = 3; + table[2 * 256 + 85] = 3; + table[2 * 256 + 86] = 3; + table[2 * 256 + 87] = 3; + table[2 * 256 + 88] = 3; + table[2 * 256 + 89] = 3; + table[2 * 256 + 90] = 3; + table[2 * 256 + 97] = 3; + table[2 * 256 + 98] = 3; + table[2 * 256 + 99] = 3; + table[2 * 256 + 100] = 3; + table[2 * 256 + 101] = 3; + table[2 * 256 + 102] = 3; + table[2 * 256 + 103] = 3; + table[2 * 256 + 104] = 3; + table[2 * 256 + 105] = 3; + table[2 * 256 + 106] = 3; + table[2 * 256 + 107] = 3; + table[2 * 256 + 108] = 3; + table[2 * 256 + 109] = 3; + table[2 * 256 + 110] = 3; + table[2 * 256 + 111] = 3; + table[2 * 256 + 112] = 3; + table[2 * 256 + 113] = 3; + table[2 * 256 + 114] = 3; + table[2 * 256 + 115] = 3; + table[2 * 256 + 116] = 3; + table[2 * 256 + 117] = 3; + table[2 * 256 + 118] = 3; + table[2 * 256 + 119] = 3; + table[2 * 256 + 120] = 3; + table[2 * 256 + 121] = 3; + table[2 * 256 + 122] = 3; + table[3 * 256 + 33] = 1; + table[3 * 256 + 35] = 1; + table[3 * 256 + 36] = 1; + table[3 * 256 + 37] = 1; + table[3 * 256 + 38] = 1; + table[3 * 256 + 39] = 1; + table[3 * 256 + 42] = 1; + table[3 * 256 + 43] = 1; + table[3 * 256 + 47] = 1; + table[3 * 256 + 61] = 1; + table[3 * 256 + 63] = 1; + table[3 * 256 + 94] = 1; + table[3 * 256 + 95] = 1; + table[3 * 256 + 96] = 1; + table[3 * 256 + 123] = 1; + table[3 * 256 + 124] = 1; + table[3 * 256 + 125] = 1; + table[3 * 256 + 126] = 1; + table[3 * 256 + 64] = 2; + table[3 * 256 + 45] = 3; + table[3 * 256 + 46] = 3; + table[3 * 256 + 48] = 3; + table[3 * 256 + 49] = 3; + table[3 * 256 + 50] = 3; + table[3 * 256 + 51] = 3; + table[3 * 256 + 52] = 3; + table[3 * 256 + 53] = 3; + table[3 * 256 + 54] = 3; + table[3 * 256 + 55] = 3; + table[3 * 256 + 56] = 3; + table[3 * 256 + 57] = 3; + table[3 * 256 + 65] = 3; + table[3 * 256 + 66] = 3; + table[3 * 256 + 67] = 3; + table[3 * 256 + 68] = 3; + table[3 * 256 + 69] = 3; + table[3 * 256 + 70] = 3; + table[3 * 256 + 71] = 3; + table[3 * 256 + 72] = 3; + table[3 * 256 + 73] = 3; + table[3 * 256 + 74] = 3; + table[3 * 256 + 75] = 3; + table[3 * 256 + 76] = 3; + table[3 * 256 + 77] = 3; + table[3 * 256 + 78] = 3; + table[3 * 256 + 79] = 3; + table[3 * 256 + 80] = 3; + table[3 * 256 + 81] = 3; + table[3 * 256 + 82] = 3; + table[3 * 256 + 83] = 3; + table[3 * 256 + 84] = 3; + table[3 * 256 + 85] = 3; + table[3 * 256 + 86] = 3; + table[3 * 256 + 87] = 3; + table[3 * 256 + 88] = 3; + table[3 * 256 + 89] = 3; + table[3 * 256 + 90] = 3; + table[3 * 256 + 97] = 3; + table[3 * 256 + 98] = 3; + table[3 * 256 + 99] = 3; + table[3 * 256 + 100] = 3; + table[3 * 256 + 101] = 3; + table[3 * 256 + 102] = 3; + table[3 * 256 + 103] = 3; + table[3 * 256 + 104] = 3; + table[3 * 256 + 105] = 3; + table[3 * 256 + 106] = 3; + table[3 * 256 + 107] = 3; + table[3 * 256 + 108] = 3; + table[3 * 256 + 109] = 3; + table[3 * 256 + 110] = 3; + table[3 * 256 + 111] = 3; + table[3 * 256 + 112] = 3; + table[3 * 256 + 113] = 3; + table[3 * 256 + 114] = 3; + table[3 * 256 + 115] = 3; + table[3 * 256 + 116] = 3; + table[3 * 256 + 117] = 3; + table[3 * 256 + 118] = 3; + table[3 * 256 + 119] = 3; + table[3 * 256 + 120] = 3; + table[3 * 256 + 121] = 3; + table[3 * 256 + 122] = 3; + + table +} +pub fn regex_match(input: [u8; N]) -> bool { + // regex: [A-Za-z0-9!#$%&'*+=?\-\^_`{|}~./@]+@[A-Za-z0-9.\-]+ + let mut s = 0; + s = table[255]; + for i in 0..input.len() { + let s_idx = s * 256 + input[i] as Field; + std::as_witness(s_idx); + s = table[s_idx]; + } + + let matched: bool = (s == 3) | (s == 4); + + matched +} + + \ No newline at end of file diff --git a/packages/noir/src/basic/email_domain.nr b/packages/noir/src/basic/email_domain.nr new file mode 100644 index 00000000..f0d7c763 --- /dev/null +++ b/packages/noir/src/basic/email_domain.nr @@ -0,0 +1,832 @@ + +use crate::common::Sequence; + + +global table: [Field; 1280] = comptime { make_lookup_table() }; + +comptime fn make_lookup_table() -> [Field; 1280] { + let mut table = [0; 1280]; + table[3 * 256 + 0] = 4; + table[4 * 256 + 0] = 4; + table[3 * 256 + 1] = 4; + table[4 * 256 + 1] = 4; + table[3 * 256 + 2] = 4; + table[4 * 256 + 2] = 4; + table[3 * 256 + 3] = 4; + table[4 * 256 + 3] = 4; + table[3 * 256 + 4] = 4; + table[4 * 256 + 4] = 4; + table[3 * 256 + 5] = 4; + table[4 * 256 + 5] = 4; + table[3 * 256 + 6] = 4; + table[4 * 256 + 6] = 4; + table[3 * 256 + 7] = 4; + table[4 * 256 + 7] = 4; + table[3 * 256 + 8] = 4; + table[4 * 256 + 8] = 4; + table[3 * 256 + 9] = 4; + table[4 * 256 + 9] = 4; + table[3 * 256 + 10] = 4; + table[4 * 256 + 10] = 4; + table[3 * 256 + 11] = 4; + table[4 * 256 + 11] = 4; + table[3 * 256 + 12] = 4; + table[4 * 256 + 12] = 4; + table[3 * 256 + 13] = 4; + table[4 * 256 + 13] = 4; + table[3 * 256 + 14] = 4; + table[4 * 256 + 14] = 4; + table[3 * 256 + 15] = 4; + table[4 * 256 + 15] = 4; + table[3 * 256 + 16] = 4; + table[4 * 256 + 16] = 4; + table[3 * 256 + 17] = 4; + table[4 * 256 + 17] = 4; + table[3 * 256 + 18] = 4; + table[4 * 256 + 18] = 4; + table[3 * 256 + 19] = 4; + table[4 * 256 + 19] = 4; + table[3 * 256 + 20] = 4; + table[4 * 256 + 20] = 4; + table[3 * 256 + 21] = 4; + table[4 * 256 + 21] = 4; + table[3 * 256 + 22] = 4; + table[4 * 256 + 22] = 4; + table[3 * 256 + 23] = 4; + table[4 * 256 + 23] = 4; + table[3 * 256 + 24] = 4; + table[4 * 256 + 24] = 4; + table[3 * 256 + 25] = 4; + table[4 * 256 + 25] = 4; + table[3 * 256 + 26] = 4; + table[4 * 256 + 26] = 4; + table[3 * 256 + 27] = 4; + table[4 * 256 + 27] = 4; + table[3 * 256 + 28] = 4; + table[4 * 256 + 28] = 4; + table[3 * 256 + 29] = 4; + table[4 * 256 + 29] = 4; + table[3 * 256 + 30] = 4; + table[4 * 256 + 30] = 4; + table[3 * 256 + 31] = 4; + table[4 * 256 + 31] = 4; + table[3 * 256 + 32] = 4; + table[4 * 256 + 32] = 4; + table[3 * 256 + 33] = 4; + table[4 * 256 + 33] = 4; + table[3 * 256 + 34] = 4; + table[4 * 256 + 34] = 4; + table[3 * 256 + 35] = 4; + table[4 * 256 + 35] = 4; + table[3 * 256 + 36] = 4; + table[4 * 256 + 36] = 4; + table[3 * 256 + 37] = 4; + table[4 * 256 + 37] = 4; + table[3 * 256 + 38] = 4; + table[4 * 256 + 38] = 4; + table[3 * 256 + 39] = 4; + table[4 * 256 + 39] = 4; + table[3 * 256 + 40] = 4; + table[4 * 256 + 40] = 4; + table[3 * 256 + 41] = 4; + table[4 * 256 + 41] = 4; + table[3 * 256 + 42] = 4; + table[4 * 256 + 42] = 4; + table[3 * 256 + 43] = 4; + table[4 * 256 + 43] = 4; + table[3 * 256 + 44] = 4; + table[4 * 256 + 44] = 4; + table[3 * 256 + 45] = 4; + table[4 * 256 + 45] = 4; + table[3 * 256 + 46] = 4; + table[4 * 256 + 46] = 4; + table[3 * 256 + 47] = 4; + table[4 * 256 + 47] = 4; + table[3 * 256 + 48] = 4; + table[4 * 256 + 48] = 4; + table[3 * 256 + 49] = 4; + table[4 * 256 + 49] = 4; + table[3 * 256 + 50] = 4; + table[4 * 256 + 50] = 4; + table[3 * 256 + 51] = 4; + table[4 * 256 + 51] = 4; + table[3 * 256 + 52] = 4; + table[4 * 256 + 52] = 4; + table[3 * 256 + 53] = 4; + table[4 * 256 + 53] = 4; + table[3 * 256 + 54] = 4; + table[4 * 256 + 54] = 4; + table[3 * 256 + 55] = 4; + table[4 * 256 + 55] = 4; + table[3 * 256 + 56] = 4; + table[4 * 256 + 56] = 4; + table[3 * 256 + 57] = 4; + table[4 * 256 + 57] = 4; + table[3 * 256 + 58] = 4; + table[4 * 256 + 58] = 4; + table[3 * 256 + 59] = 4; + table[4 * 256 + 59] = 4; + table[3 * 256 + 60] = 4; + table[4 * 256 + 60] = 4; + table[3 * 256 + 61] = 4; + table[4 * 256 + 61] = 4; + table[3 * 256 + 62] = 4; + table[4 * 256 + 62] = 4; + table[3 * 256 + 63] = 4; + table[4 * 256 + 63] = 4; + table[3 * 256 + 64] = 4; + table[4 * 256 + 64] = 4; + table[3 * 256 + 65] = 4; + table[4 * 256 + 65] = 4; + table[3 * 256 + 66] = 4; + table[4 * 256 + 66] = 4; + table[3 * 256 + 67] = 4; + table[4 * 256 + 67] = 4; + table[3 * 256 + 68] = 4; + table[4 * 256 + 68] = 4; + table[3 * 256 + 69] = 4; + table[4 * 256 + 69] = 4; + table[3 * 256 + 70] = 4; + table[4 * 256 + 70] = 4; + table[3 * 256 + 71] = 4; + table[4 * 256 + 71] = 4; + table[3 * 256 + 72] = 4; + table[4 * 256 + 72] = 4; + table[3 * 256 + 73] = 4; + table[4 * 256 + 73] = 4; + table[3 * 256 + 74] = 4; + table[4 * 256 + 74] = 4; + table[3 * 256 + 75] = 4; + table[4 * 256 + 75] = 4; + table[3 * 256 + 76] = 4; + table[4 * 256 + 76] = 4; + table[3 * 256 + 77] = 4; + table[4 * 256 + 77] = 4; + table[3 * 256 + 78] = 4; + table[4 * 256 + 78] = 4; + table[3 * 256 + 79] = 4; + table[4 * 256 + 79] = 4; + table[3 * 256 + 80] = 4; + table[4 * 256 + 80] = 4; + table[3 * 256 + 81] = 4; + table[4 * 256 + 81] = 4; + table[3 * 256 + 82] = 4; + table[4 * 256 + 82] = 4; + table[3 * 256 + 83] = 4; + table[4 * 256 + 83] = 4; + table[3 * 256 + 84] = 4; + table[4 * 256 + 84] = 4; + table[3 * 256 + 85] = 4; + table[4 * 256 + 85] = 4; + table[3 * 256 + 86] = 4; + table[4 * 256 + 86] = 4; + table[3 * 256 + 87] = 4; + table[4 * 256 + 87] = 4; + table[3 * 256 + 88] = 4; + table[4 * 256 + 88] = 4; + table[3 * 256 + 89] = 4; + table[4 * 256 + 89] = 4; + table[3 * 256 + 90] = 4; + table[4 * 256 + 90] = 4; + table[3 * 256 + 91] = 4; + table[4 * 256 + 91] = 4; + table[3 * 256 + 92] = 4; + table[4 * 256 + 92] = 4; + table[3 * 256 + 93] = 4; + table[4 * 256 + 93] = 4; + table[3 * 256 + 94] = 4; + table[4 * 256 + 94] = 4; + table[3 * 256 + 95] = 4; + table[4 * 256 + 95] = 4; + table[3 * 256 + 96] = 4; + table[4 * 256 + 96] = 4; + table[3 * 256 + 97] = 4; + table[4 * 256 + 97] = 4; + table[3 * 256 + 98] = 4; + table[4 * 256 + 98] = 4; + table[3 * 256 + 99] = 4; + table[4 * 256 + 99] = 4; + table[3 * 256 + 100] = 4; + table[4 * 256 + 100] = 4; + table[3 * 256 + 101] = 4; + table[4 * 256 + 101] = 4; + table[3 * 256 + 102] = 4; + table[4 * 256 + 102] = 4; + table[3 * 256 + 103] = 4; + table[4 * 256 + 103] = 4; + table[3 * 256 + 104] = 4; + table[4 * 256 + 104] = 4; + table[3 * 256 + 105] = 4; + table[4 * 256 + 105] = 4; + table[3 * 256 + 106] = 4; + table[4 * 256 + 106] = 4; + table[3 * 256 + 107] = 4; + table[4 * 256 + 107] = 4; + table[3 * 256 + 108] = 4; + table[4 * 256 + 108] = 4; + table[3 * 256 + 109] = 4; + table[4 * 256 + 109] = 4; + table[3 * 256 + 110] = 4; + table[4 * 256 + 110] = 4; + table[3 * 256 + 111] = 4; + table[4 * 256 + 111] = 4; + table[3 * 256 + 112] = 4; + table[4 * 256 + 112] = 4; + table[3 * 256 + 113] = 4; + table[4 * 256 + 113] = 4; + table[3 * 256 + 114] = 4; + table[4 * 256 + 114] = 4; + table[3 * 256 + 115] = 4; + table[4 * 256 + 115] = 4; + table[3 * 256 + 116] = 4; + table[4 * 256 + 116] = 4; + table[3 * 256 + 117] = 4; + table[4 * 256 + 117] = 4; + table[3 * 256 + 118] = 4; + table[4 * 256 + 118] = 4; + table[3 * 256 + 119] = 4; + table[4 * 256 + 119] = 4; + table[3 * 256 + 120] = 4; + table[4 * 256 + 120] = 4; + table[3 * 256 + 121] = 4; + table[4 * 256 + 121] = 4; + table[3 * 256 + 122] = 4; + table[4 * 256 + 122] = 4; + table[3 * 256 + 123] = 4; + table[4 * 256 + 123] = 4; + table[3 * 256 + 124] = 4; + table[4 * 256 + 124] = 4; + table[3 * 256 + 125] = 4; + table[4 * 256 + 125] = 4; + table[3 * 256 + 126] = 4; + table[4 * 256 + 126] = 4; + table[3 * 256 + 127] = 4; + table[4 * 256 + 127] = 4; + table[3 * 256 + 128] = 4; + table[4 * 256 + 128] = 4; + table[3 * 256 + 129] = 4; + table[4 * 256 + 129] = 4; + table[3 * 256 + 130] = 4; + table[4 * 256 + 130] = 4; + table[3 * 256 + 131] = 4; + table[4 * 256 + 131] = 4; + table[3 * 256 + 132] = 4; + table[4 * 256 + 132] = 4; + table[3 * 256 + 133] = 4; + table[4 * 256 + 133] = 4; + table[3 * 256 + 134] = 4; + table[4 * 256 + 134] = 4; + table[3 * 256 + 135] = 4; + table[4 * 256 + 135] = 4; + table[3 * 256 + 136] = 4; + table[4 * 256 + 136] = 4; + table[3 * 256 + 137] = 4; + table[4 * 256 + 137] = 4; + table[3 * 256 + 138] = 4; + table[4 * 256 + 138] = 4; + table[3 * 256 + 139] = 4; + table[4 * 256 + 139] = 4; + table[3 * 256 + 140] = 4; + table[4 * 256 + 140] = 4; + table[3 * 256 + 141] = 4; + table[4 * 256 + 141] = 4; + table[3 * 256 + 142] = 4; + table[4 * 256 + 142] = 4; + table[3 * 256 + 143] = 4; + table[4 * 256 + 143] = 4; + table[3 * 256 + 144] = 4; + table[4 * 256 + 144] = 4; + table[3 * 256 + 145] = 4; + table[4 * 256 + 145] = 4; + table[3 * 256 + 146] = 4; + table[4 * 256 + 146] = 4; + table[3 * 256 + 147] = 4; + table[4 * 256 + 147] = 4; + table[3 * 256 + 148] = 4; + table[4 * 256 + 148] = 4; + table[3 * 256 + 149] = 4; + table[4 * 256 + 149] = 4; + table[3 * 256 + 150] = 4; + table[4 * 256 + 150] = 4; + table[3 * 256 + 151] = 4; + table[4 * 256 + 151] = 4; + table[3 * 256 + 152] = 4; + table[4 * 256 + 152] = 4; + table[3 * 256 + 153] = 4; + table[4 * 256 + 153] = 4; + table[3 * 256 + 154] = 4; + table[4 * 256 + 154] = 4; + table[3 * 256 + 155] = 4; + table[4 * 256 + 155] = 4; + table[3 * 256 + 156] = 4; + table[4 * 256 + 156] = 4; + table[3 * 256 + 157] = 4; + table[4 * 256 + 157] = 4; + table[3 * 256 + 158] = 4; + table[4 * 256 + 158] = 4; + table[3 * 256 + 159] = 4; + table[4 * 256 + 159] = 4; + table[3 * 256 + 160] = 4; + table[4 * 256 + 160] = 4; + table[3 * 256 + 161] = 4; + table[4 * 256 + 161] = 4; + table[3 * 256 + 162] = 4; + table[4 * 256 + 162] = 4; + table[3 * 256 + 163] = 4; + table[4 * 256 + 163] = 4; + table[3 * 256 + 164] = 4; + table[4 * 256 + 164] = 4; + table[3 * 256 + 165] = 4; + table[4 * 256 + 165] = 4; + table[3 * 256 + 166] = 4; + table[4 * 256 + 166] = 4; + table[3 * 256 + 167] = 4; + table[4 * 256 + 167] = 4; + table[3 * 256 + 168] = 4; + table[4 * 256 + 168] = 4; + table[3 * 256 + 169] = 4; + table[4 * 256 + 169] = 4; + table[3 * 256 + 170] = 4; + table[4 * 256 + 170] = 4; + table[3 * 256 + 171] = 4; + table[4 * 256 + 171] = 4; + table[3 * 256 + 172] = 4; + table[4 * 256 + 172] = 4; + table[3 * 256 + 173] = 4; + table[4 * 256 + 173] = 4; + table[3 * 256 + 174] = 4; + table[4 * 256 + 174] = 4; + table[3 * 256 + 175] = 4; + table[4 * 256 + 175] = 4; + table[3 * 256 + 176] = 4; + table[4 * 256 + 176] = 4; + table[3 * 256 + 177] = 4; + table[4 * 256 + 177] = 4; + table[3 * 256 + 178] = 4; + table[4 * 256 + 178] = 4; + table[3 * 256 + 179] = 4; + table[4 * 256 + 179] = 4; + table[3 * 256 + 180] = 4; + table[4 * 256 + 180] = 4; + table[3 * 256 + 181] = 4; + table[4 * 256 + 181] = 4; + table[3 * 256 + 182] = 4; + table[4 * 256 + 182] = 4; + table[3 * 256 + 183] = 4; + table[4 * 256 + 183] = 4; + table[3 * 256 + 184] = 4; + table[4 * 256 + 184] = 4; + table[3 * 256 + 185] = 4; + table[4 * 256 + 185] = 4; + table[3 * 256 + 186] = 4; + table[4 * 256 + 186] = 4; + table[3 * 256 + 187] = 4; + table[4 * 256 + 187] = 4; + table[3 * 256 + 188] = 4; + table[4 * 256 + 188] = 4; + table[3 * 256 + 189] = 4; + table[4 * 256 + 189] = 4; + table[3 * 256 + 190] = 4; + table[4 * 256 + 190] = 4; + table[3 * 256 + 191] = 4; + table[4 * 256 + 191] = 4; + table[3 * 256 + 192] = 4; + table[4 * 256 + 192] = 4; + table[3 * 256 + 193] = 4; + table[4 * 256 + 193] = 4; + table[3 * 256 + 194] = 4; + table[4 * 256 + 194] = 4; + table[3 * 256 + 195] = 4; + table[4 * 256 + 195] = 4; + table[3 * 256 + 196] = 4; + table[4 * 256 + 196] = 4; + table[3 * 256 + 197] = 4; + table[4 * 256 + 197] = 4; + table[3 * 256 + 198] = 4; + table[4 * 256 + 198] = 4; + table[3 * 256 + 199] = 4; + table[4 * 256 + 199] = 4; + table[3 * 256 + 200] = 4; + table[4 * 256 + 200] = 4; + table[3 * 256 + 201] = 4; + table[4 * 256 + 201] = 4; + table[3 * 256 + 202] = 4; + table[4 * 256 + 202] = 4; + table[3 * 256 + 203] = 4; + table[4 * 256 + 203] = 4; + table[3 * 256 + 204] = 4; + table[4 * 256 + 204] = 4; + table[3 * 256 + 205] = 4; + table[4 * 256 + 205] = 4; + table[3 * 256 + 206] = 4; + table[4 * 256 + 206] = 4; + table[3 * 256 + 207] = 4; + table[4 * 256 + 207] = 4; + table[3 * 256 + 208] = 4; + table[4 * 256 + 208] = 4; + table[3 * 256 + 209] = 4; + table[4 * 256 + 209] = 4; + table[3 * 256 + 210] = 4; + table[4 * 256 + 210] = 4; + table[3 * 256 + 211] = 4; + table[4 * 256 + 211] = 4; + table[3 * 256 + 212] = 4; + table[4 * 256 + 212] = 4; + table[3 * 256 + 213] = 4; + table[4 * 256 + 213] = 4; + table[3 * 256 + 214] = 4; + table[4 * 256 + 214] = 4; + table[3 * 256 + 215] = 4; + table[4 * 256 + 215] = 4; + table[3 * 256 + 216] = 4; + table[4 * 256 + 216] = 4; + table[3 * 256 + 217] = 4; + table[4 * 256 + 217] = 4; + table[3 * 256 + 218] = 4; + table[4 * 256 + 218] = 4; + table[3 * 256 + 219] = 4; + table[4 * 256 + 219] = 4; + table[3 * 256 + 220] = 4; + table[4 * 256 + 220] = 4; + table[3 * 256 + 221] = 4; + table[4 * 256 + 221] = 4; + table[3 * 256 + 222] = 4; + table[4 * 256 + 222] = 4; + table[3 * 256 + 223] = 4; + table[4 * 256 + 223] = 4; + table[3 * 256 + 224] = 4; + table[4 * 256 + 224] = 4; + table[3 * 256 + 225] = 4; + table[4 * 256 + 225] = 4; + table[3 * 256 + 226] = 4; + table[4 * 256 + 226] = 4; + table[3 * 256 + 227] = 4; + table[4 * 256 + 227] = 4; + table[3 * 256 + 228] = 4; + table[4 * 256 + 228] = 4; + table[3 * 256 + 229] = 4; + table[4 * 256 + 229] = 4; + table[3 * 256 + 230] = 4; + table[4 * 256 + 230] = 4; + table[3 * 256 + 231] = 4; + table[4 * 256 + 231] = 4; + table[3 * 256 + 232] = 4; + table[4 * 256 + 232] = 4; + table[3 * 256 + 233] = 4; + table[4 * 256 + 233] = 4; + table[3 * 256 + 234] = 4; + table[4 * 256 + 234] = 4; + table[3 * 256 + 235] = 4; + table[4 * 256 + 235] = 4; + table[3 * 256 + 236] = 4; + table[4 * 256 + 236] = 4; + table[3 * 256 + 237] = 4; + table[4 * 256 + 237] = 4; + table[3 * 256 + 238] = 4; + table[4 * 256 + 238] = 4; + table[3 * 256 + 239] = 4; + table[4 * 256 + 239] = 4; + table[3 * 256 + 240] = 4; + table[4 * 256 + 240] = 4; + table[3 * 256 + 241] = 4; + table[4 * 256 + 241] = 4; + table[3 * 256 + 242] = 4; + table[4 * 256 + 242] = 4; + table[3 * 256 + 243] = 4; + table[4 * 256 + 243] = 4; + table[3 * 256 + 244] = 4; + table[4 * 256 + 244] = 4; + table[3 * 256 + 245] = 4; + table[4 * 256 + 245] = 4; + table[3 * 256 + 246] = 4; + table[4 * 256 + 246] = 4; + table[3 * 256 + 247] = 4; + table[4 * 256 + 247] = 4; + table[3 * 256 + 248] = 4; + table[4 * 256 + 248] = 4; + table[3 * 256 + 249] = 4; + table[4 * 256 + 249] = 4; + table[3 * 256 + 250] = 4; + table[4 * 256 + 250] = 4; + table[3 * 256 + 251] = 4; + table[4 * 256 + 251] = 4; + table[3 * 256 + 252] = 4; + table[4 * 256 + 252] = 4; + table[3 * 256 + 253] = 4; + table[4 * 256 + 253] = 4; + table[3 * 256 + 254] = 4; + table[4 * 256 + 254] = 4; + table[0 * 256 + 33] = 1; + table[0 * 256 + 35] = 1; + table[0 * 256 + 36] = 1; + table[0 * 256 + 37] = 1; + table[0 * 256 + 38] = 1; + table[0 * 256 + 39] = 1; + table[0 * 256 + 42] = 1; + table[0 * 256 + 43] = 1; + table[0 * 256 + 45] = 1; + table[0 * 256 + 46] = 1; + table[0 * 256 + 47] = 1; + table[0 * 256 + 48] = 1; + table[0 * 256 + 49] = 1; + table[0 * 256 + 50] = 1; + table[0 * 256 + 51] = 1; + table[0 * 256 + 52] = 1; + table[0 * 256 + 53] = 1; + table[0 * 256 + 54] = 1; + table[0 * 256 + 55] = 1; + table[0 * 256 + 56] = 1; + table[0 * 256 + 57] = 1; + table[0 * 256 + 61] = 1; + table[0 * 256 + 63] = 1; + table[0 * 256 + 65] = 1; + table[0 * 256 + 66] = 1; + table[0 * 256 + 67] = 1; + table[0 * 256 + 68] = 1; + table[0 * 256 + 69] = 1; + table[0 * 256 + 70] = 1; + table[0 * 256 + 71] = 1; + table[0 * 256 + 72] = 1; + table[0 * 256 + 73] = 1; + table[0 * 256 + 74] = 1; + table[0 * 256 + 75] = 1; + table[0 * 256 + 76] = 1; + table[0 * 256 + 77] = 1; + table[0 * 256 + 78] = 1; + table[0 * 256 + 79] = 1; + table[0 * 256 + 80] = 1; + table[0 * 256 + 81] = 1; + table[0 * 256 + 82] = 1; + table[0 * 256 + 83] = 1; + table[0 * 256 + 84] = 1; + table[0 * 256 + 85] = 1; + table[0 * 256 + 86] = 1; + table[0 * 256 + 87] = 1; + table[0 * 256 + 88] = 1; + table[0 * 256 + 89] = 1; + table[0 * 256 + 90] = 1; + table[0 * 256 + 94] = 1; + table[0 * 256 + 95] = 1; + table[0 * 256 + 96] = 1; + table[0 * 256 + 97] = 1; + table[0 * 256 + 98] = 1; + table[0 * 256 + 99] = 1; + table[0 * 256 + 100] = 1; + table[0 * 256 + 101] = 1; + table[0 * 256 + 102] = 1; + table[0 * 256 + 103] = 1; + table[0 * 256 + 104] = 1; + table[0 * 256 + 105] = 1; + table[0 * 256 + 106] = 1; + table[0 * 256 + 107] = 1; + table[0 * 256 + 108] = 1; + table[0 * 256 + 109] = 1; + table[0 * 256 + 110] = 1; + table[0 * 256 + 111] = 1; + table[0 * 256 + 112] = 1; + table[0 * 256 + 113] = 1; + table[0 * 256 + 114] = 1; + table[0 * 256 + 115] = 1; + table[0 * 256 + 116] = 1; + table[0 * 256 + 117] = 1; + table[0 * 256 + 118] = 1; + table[0 * 256 + 119] = 1; + table[0 * 256 + 120] = 1; + table[0 * 256 + 121] = 1; + table[0 * 256 + 122] = 1; + table[0 * 256 + 123] = 1; + table[0 * 256 + 124] = 1; + table[0 * 256 + 125] = 1; + table[0 * 256 + 126] = 1; + table[1 * 256 + 33] = 1; + table[1 * 256 + 35] = 1; + table[1 * 256 + 36] = 1; + table[1 * 256 + 37] = 1; + table[1 * 256 + 38] = 1; + table[1 * 256 + 39] = 1; + table[1 * 256 + 42] = 1; + table[1 * 256 + 43] = 1; + table[1 * 256 + 45] = 1; + table[1 * 256 + 46] = 1; + table[1 * 256 + 47] = 1; + table[1 * 256 + 48] = 1; + table[1 * 256 + 49] = 1; + table[1 * 256 + 50] = 1; + table[1 * 256 + 51] = 1; + table[1 * 256 + 52] = 1; + table[1 * 256 + 53] = 1; + table[1 * 256 + 54] = 1; + table[1 * 256 + 55] = 1; + table[1 * 256 + 56] = 1; + table[1 * 256 + 57] = 1; + table[1 * 256 + 61] = 1; + table[1 * 256 + 63] = 1; + table[1 * 256 + 65] = 1; + table[1 * 256 + 66] = 1; + table[1 * 256 + 67] = 1; + table[1 * 256 + 68] = 1; + table[1 * 256 + 69] = 1; + table[1 * 256 + 70] = 1; + table[1 * 256 + 71] = 1; + table[1 * 256 + 72] = 1; + table[1 * 256 + 73] = 1; + table[1 * 256 + 74] = 1; + table[1 * 256 + 75] = 1; + table[1 * 256 + 76] = 1; + table[1 * 256 + 77] = 1; + table[1 * 256 + 78] = 1; + table[1 * 256 + 79] = 1; + table[1 * 256 + 80] = 1; + table[1 * 256 + 81] = 1; + table[1 * 256 + 82] = 1; + table[1 * 256 + 83] = 1; + table[1 * 256 + 84] = 1; + table[1 * 256 + 85] = 1; + table[1 * 256 + 86] = 1; + table[1 * 256 + 87] = 1; + table[1 * 256 + 88] = 1; + table[1 * 256 + 89] = 1; + table[1 * 256 + 90] = 1; + table[1 * 256 + 94] = 1; + table[1 * 256 + 95] = 1; + table[1 * 256 + 96] = 1; + table[1 * 256 + 97] = 1; + table[1 * 256 + 98] = 1; + table[1 * 256 + 99] = 1; + table[1 * 256 + 100] = 1; + table[1 * 256 + 101] = 1; + table[1 * 256 + 102] = 1; + table[1 * 256 + 103] = 1; + table[1 * 256 + 104] = 1; + table[1 * 256 + 105] = 1; + table[1 * 256 + 106] = 1; + table[1 * 256 + 107] = 1; + table[1 * 256 + 108] = 1; + table[1 * 256 + 109] = 1; + table[1 * 256 + 110] = 1; + table[1 * 256 + 111] = 1; + table[1 * 256 + 112] = 1; + table[1 * 256 + 113] = 1; + table[1 * 256 + 114] = 1; + table[1 * 256 + 115] = 1; + table[1 * 256 + 116] = 1; + table[1 * 256 + 117] = 1; + table[1 * 256 + 118] = 1; + table[1 * 256 + 119] = 1; + table[1 * 256 + 120] = 1; + table[1 * 256 + 121] = 1; + table[1 * 256 + 122] = 1; + table[1 * 256 + 123] = 1; + table[1 * 256 + 124] = 1; + table[1 * 256 + 125] = 1; + table[1 * 256 + 126] = 1; + table[1 * 256 + 64] = 2; + table[2 * 256 + 45] = 3; + table[2 * 256 + 46] = 3; + table[2 * 256 + 48] = 3; + table[2 * 256 + 49] = 3; + table[2 * 256 + 50] = 3; + table[2 * 256 + 51] = 3; + table[2 * 256 + 52] = 3; + table[2 * 256 + 53] = 3; + table[2 * 256 + 54] = 3; + table[2 * 256 + 55] = 3; + table[2 * 256 + 56] = 3; + table[2 * 256 + 57] = 3; + table[2 * 256 + 64] = 3; + table[2 * 256 + 65] = 3; + table[2 * 256 + 66] = 3; + table[2 * 256 + 67] = 3; + table[2 * 256 + 68] = 3; + table[2 * 256 + 69] = 3; + table[2 * 256 + 70] = 3; + table[2 * 256 + 71] = 3; + table[2 * 256 + 72] = 3; + table[2 * 256 + 73] = 3; + table[2 * 256 + 74] = 3; + table[2 * 256 + 75] = 3; + table[2 * 256 + 76] = 3; + table[2 * 256 + 77] = 3; + table[2 * 256 + 78] = 3; + table[2 * 256 + 79] = 3; + table[2 * 256 + 80] = 3; + table[2 * 256 + 81] = 3; + table[2 * 256 + 82] = 3; + table[2 * 256 + 83] = 3; + table[2 * 256 + 84] = 3; + table[2 * 256 + 85] = 3; + table[2 * 256 + 86] = 3; + table[2 * 256 + 87] = 3; + table[2 * 256 + 88] = 3; + table[2 * 256 + 89] = 3; + table[2 * 256 + 90] = 3; + table[2 * 256 + 97] = 3; + table[2 * 256 + 98] = 3; + table[2 * 256 + 99] = 3; + table[2 * 256 + 100] = 3; + table[2 * 256 + 101] = 3; + table[2 * 256 + 102] = 3; + table[2 * 256 + 103] = 3; + table[2 * 256 + 104] = 3; + table[2 * 256 + 105] = 3; + table[2 * 256 + 106] = 3; + table[2 * 256 + 107] = 3; + table[2 * 256 + 108] = 3; + table[2 * 256 + 109] = 3; + table[2 * 256 + 110] = 3; + table[2 * 256 + 111] = 3; + table[2 * 256 + 112] = 3; + table[2 * 256 + 113] = 3; + table[2 * 256 + 114] = 3; + table[2 * 256 + 115] = 3; + table[2 * 256 + 116] = 3; + table[2 * 256 + 117] = 3; + table[2 * 256 + 118] = 3; + table[2 * 256 + 119] = 3; + table[2 * 256 + 120] = 3; + table[2 * 256 + 121] = 3; + table[2 * 256 + 122] = 3; + table[3 * 256 + 45] = 3; + table[3 * 256 + 46] = 3; + table[3 * 256 + 48] = 3; + table[3 * 256 + 49] = 3; + table[3 * 256 + 50] = 3; + table[3 * 256 + 51] = 3; + table[3 * 256 + 52] = 3; + table[3 * 256 + 53] = 3; + table[3 * 256 + 54] = 3; + table[3 * 256 + 55] = 3; + table[3 * 256 + 56] = 3; + table[3 * 256 + 57] = 3; + table[3 * 256 + 64] = 3; + table[3 * 256 + 65] = 3; + table[3 * 256 + 66] = 3; + table[3 * 256 + 67] = 3; + table[3 * 256 + 68] = 3; + table[3 * 256 + 69] = 3; + table[3 * 256 + 70] = 3; + table[3 * 256 + 71] = 3; + table[3 * 256 + 72] = 3; + table[3 * 256 + 73] = 3; + table[3 * 256 + 74] = 3; + table[3 * 256 + 75] = 3; + table[3 * 256 + 76] = 3; + table[3 * 256 + 77] = 3; + table[3 * 256 + 78] = 3; + table[3 * 256 + 79] = 3; + table[3 * 256 + 80] = 3; + table[3 * 256 + 81] = 3; + table[3 * 256 + 82] = 3; + table[3 * 256 + 83] = 3; + table[3 * 256 + 84] = 3; + table[3 * 256 + 85] = 3; + table[3 * 256 + 86] = 3; + table[3 * 256 + 87] = 3; + table[3 * 256 + 88] = 3; + table[3 * 256 + 89] = 3; + table[3 * 256 + 90] = 3; + table[3 * 256 + 97] = 3; + table[3 * 256 + 98] = 3; + table[3 * 256 + 99] = 3; + table[3 * 256 + 100] = 3; + table[3 * 256 + 101] = 3; + table[3 * 256 + 102] = 3; + table[3 * 256 + 103] = 3; + table[3 * 256 + 104] = 3; + table[3 * 256 + 105] = 3; + table[3 * 256 + 106] = 3; + table[3 * 256 + 107] = 3; + table[3 * 256 + 108] = 3; + table[3 * 256 + 109] = 3; + table[3 * 256 + 110] = 3; + table[3 * 256 + 111] = 3; + table[3 * 256 + 112] = 3; + table[3 * 256 + 113] = 3; + table[3 * 256 + 114] = 3; + table[3 * 256 + 115] = 3; + table[3 * 256 + 116] = 3; + table[3 * 256 + 117] = 3; + table[3 * 256 + 118] = 3; + table[3 * 256 + 119] = 3; + table[3 * 256 + 120] = 3; + table[3 * 256 + 121] = 3; + table[3 * 256 + 122] = 3; + + table +} +pub fn regex_match(input: [u8; N]) -> bool { + // regex: [A-Za-z0-9!#$%&'*+=?\-\^_`{|}~./]+@[A-Za-z0-9.\-@]+ + let mut s = 0; + s = table[255]; + for i in 0..input.len() { + let s_idx = s * 256 + input[i] as Field; + std::as_witness(s_idx); + s = table[s_idx]; + } + + let matched: bool = (s == 3) | (s == 4); + + matched +} + + \ No newline at end of file diff --git a/packages/noir/src/basic/from_all.nr b/packages/noir/src/basic/from_all.nr new file mode 100644 index 00000000..484cf4eb --- /dev/null +++ b/packages/noir/src/basic/from_all.nr @@ -0,0 +1,1221 @@ + +use crate::common::Sequence; + + +global table: [Field; 4864] = comptime { make_lookup_table() }; + +comptime fn make_lookup_table() -> [Field; 4864] { + let mut table = [0; 4864]; + table[17 * 256 + 0] = 18; + table[18 * 256 + 0] = 18; + table[17 * 256 + 1] = 18; + table[18 * 256 + 1] = 18; + table[17 * 256 + 2] = 18; + table[18 * 256 + 2] = 18; + table[17 * 256 + 3] = 18; + table[18 * 256 + 3] = 18; + table[17 * 256 + 4] = 18; + table[18 * 256 + 4] = 18; + table[17 * 256 + 5] = 18; + table[18 * 256 + 5] = 18; + table[17 * 256 + 6] = 18; + table[18 * 256 + 6] = 18; + table[17 * 256 + 7] = 18; + table[18 * 256 + 7] = 18; + table[17 * 256 + 8] = 18; + table[18 * 256 + 8] = 18; + table[17 * 256 + 9] = 18; + table[18 * 256 + 9] = 18; + table[17 * 256 + 10] = 18; + table[18 * 256 + 10] = 18; + table[17 * 256 + 11] = 18; + table[18 * 256 + 11] = 18; + table[17 * 256 + 12] = 18; + table[18 * 256 + 12] = 18; + table[17 * 256 + 13] = 18; + table[18 * 256 + 13] = 18; + table[17 * 256 + 14] = 18; + table[18 * 256 + 14] = 18; + table[17 * 256 + 15] = 18; + table[18 * 256 + 15] = 18; + table[17 * 256 + 16] = 18; + table[18 * 256 + 16] = 18; + table[17 * 256 + 17] = 18; + table[18 * 256 + 17] = 18; + table[17 * 256 + 18] = 18; + table[18 * 256 + 18] = 18; + table[17 * 256 + 19] = 18; + table[18 * 256 + 19] = 18; + table[17 * 256 + 20] = 18; + table[18 * 256 + 20] = 18; + table[17 * 256 + 21] = 18; + table[18 * 256 + 21] = 18; + table[17 * 256 + 22] = 18; + table[18 * 256 + 22] = 18; + table[17 * 256 + 23] = 18; + table[18 * 256 + 23] = 18; + table[17 * 256 + 24] = 18; + table[18 * 256 + 24] = 18; + table[17 * 256 + 25] = 18; + table[18 * 256 + 25] = 18; + table[17 * 256 + 26] = 18; + table[18 * 256 + 26] = 18; + table[17 * 256 + 27] = 18; + table[18 * 256 + 27] = 18; + table[17 * 256 + 28] = 18; + table[18 * 256 + 28] = 18; + table[17 * 256 + 29] = 18; + table[18 * 256 + 29] = 18; + table[17 * 256 + 30] = 18; + table[18 * 256 + 30] = 18; + table[17 * 256 + 31] = 18; + table[18 * 256 + 31] = 18; + table[17 * 256 + 32] = 18; + table[18 * 256 + 32] = 18; + table[17 * 256 + 33] = 18; + table[18 * 256 + 33] = 18; + table[17 * 256 + 34] = 18; + table[18 * 256 + 34] = 18; + table[17 * 256 + 35] = 18; + table[18 * 256 + 35] = 18; + table[17 * 256 + 36] = 18; + table[18 * 256 + 36] = 18; + table[17 * 256 + 37] = 18; + table[18 * 256 + 37] = 18; + table[17 * 256 + 38] = 18; + table[18 * 256 + 38] = 18; + table[17 * 256 + 39] = 18; + table[18 * 256 + 39] = 18; + table[17 * 256 + 40] = 18; + table[18 * 256 + 40] = 18; + table[17 * 256 + 41] = 18; + table[18 * 256 + 41] = 18; + table[17 * 256 + 42] = 18; + table[18 * 256 + 42] = 18; + table[17 * 256 + 43] = 18; + table[18 * 256 + 43] = 18; + table[17 * 256 + 44] = 18; + table[18 * 256 + 44] = 18; + table[17 * 256 + 45] = 18; + table[18 * 256 + 45] = 18; + table[17 * 256 + 46] = 18; + table[18 * 256 + 46] = 18; + table[17 * 256 + 47] = 18; + table[18 * 256 + 47] = 18; + table[17 * 256 + 48] = 18; + table[18 * 256 + 48] = 18; + table[17 * 256 + 49] = 18; + table[18 * 256 + 49] = 18; + table[17 * 256 + 50] = 18; + table[18 * 256 + 50] = 18; + table[17 * 256 + 51] = 18; + table[18 * 256 + 51] = 18; + table[17 * 256 + 52] = 18; + table[18 * 256 + 52] = 18; + table[17 * 256 + 53] = 18; + table[18 * 256 + 53] = 18; + table[17 * 256 + 54] = 18; + table[18 * 256 + 54] = 18; + table[17 * 256 + 55] = 18; + table[18 * 256 + 55] = 18; + table[17 * 256 + 56] = 18; + table[18 * 256 + 56] = 18; + table[17 * 256 + 57] = 18; + table[18 * 256 + 57] = 18; + table[17 * 256 + 58] = 18; + table[18 * 256 + 58] = 18; + table[17 * 256 + 59] = 18; + table[18 * 256 + 59] = 18; + table[17 * 256 + 60] = 18; + table[18 * 256 + 60] = 18; + table[17 * 256 + 61] = 18; + table[18 * 256 + 61] = 18; + table[17 * 256 + 62] = 18; + table[18 * 256 + 62] = 18; + table[17 * 256 + 63] = 18; + table[18 * 256 + 63] = 18; + table[17 * 256 + 64] = 18; + table[18 * 256 + 64] = 18; + table[17 * 256 + 65] = 18; + table[18 * 256 + 65] = 18; + table[17 * 256 + 66] = 18; + table[18 * 256 + 66] = 18; + table[17 * 256 + 67] = 18; + table[18 * 256 + 67] = 18; + table[17 * 256 + 68] = 18; + table[18 * 256 + 68] = 18; + table[17 * 256 + 69] = 18; + table[18 * 256 + 69] = 18; + table[17 * 256 + 70] = 18; + table[18 * 256 + 70] = 18; + table[17 * 256 + 71] = 18; + table[18 * 256 + 71] = 18; + table[17 * 256 + 72] = 18; + table[18 * 256 + 72] = 18; + table[17 * 256 + 73] = 18; + table[18 * 256 + 73] = 18; + table[17 * 256 + 74] = 18; + table[18 * 256 + 74] = 18; + table[17 * 256 + 75] = 18; + table[18 * 256 + 75] = 18; + table[17 * 256 + 76] = 18; + table[18 * 256 + 76] = 18; + table[17 * 256 + 77] = 18; + table[18 * 256 + 77] = 18; + table[17 * 256 + 78] = 18; + table[18 * 256 + 78] = 18; + table[17 * 256 + 79] = 18; + table[18 * 256 + 79] = 18; + table[17 * 256 + 80] = 18; + table[18 * 256 + 80] = 18; + table[17 * 256 + 81] = 18; + table[18 * 256 + 81] = 18; + table[17 * 256 + 82] = 18; + table[18 * 256 + 82] = 18; + table[17 * 256 + 83] = 18; + table[18 * 256 + 83] = 18; + table[17 * 256 + 84] = 18; + table[18 * 256 + 84] = 18; + table[17 * 256 + 85] = 18; + table[18 * 256 + 85] = 18; + table[17 * 256 + 86] = 18; + table[18 * 256 + 86] = 18; + table[17 * 256 + 87] = 18; + table[18 * 256 + 87] = 18; + table[17 * 256 + 88] = 18; + table[18 * 256 + 88] = 18; + table[17 * 256 + 89] = 18; + table[18 * 256 + 89] = 18; + table[17 * 256 + 90] = 18; + table[18 * 256 + 90] = 18; + table[17 * 256 + 91] = 18; + table[18 * 256 + 91] = 18; + table[17 * 256 + 92] = 18; + table[18 * 256 + 92] = 18; + table[17 * 256 + 93] = 18; + table[18 * 256 + 93] = 18; + table[17 * 256 + 94] = 18; + table[18 * 256 + 94] = 18; + table[17 * 256 + 95] = 18; + table[18 * 256 + 95] = 18; + table[17 * 256 + 96] = 18; + table[18 * 256 + 96] = 18; + table[17 * 256 + 97] = 18; + table[18 * 256 + 97] = 18; + table[17 * 256 + 98] = 18; + table[18 * 256 + 98] = 18; + table[17 * 256 + 99] = 18; + table[18 * 256 + 99] = 18; + table[17 * 256 + 100] = 18; + table[18 * 256 + 100] = 18; + table[17 * 256 + 101] = 18; + table[18 * 256 + 101] = 18; + table[17 * 256 + 102] = 18; + table[18 * 256 + 102] = 18; + table[17 * 256 + 103] = 18; + table[18 * 256 + 103] = 18; + table[17 * 256 + 104] = 18; + table[18 * 256 + 104] = 18; + table[17 * 256 + 105] = 18; + table[18 * 256 + 105] = 18; + table[17 * 256 + 106] = 18; + table[18 * 256 + 106] = 18; + table[17 * 256 + 107] = 18; + table[18 * 256 + 107] = 18; + table[17 * 256 + 108] = 18; + table[18 * 256 + 108] = 18; + table[17 * 256 + 109] = 18; + table[18 * 256 + 109] = 18; + table[17 * 256 + 110] = 18; + table[18 * 256 + 110] = 18; + table[17 * 256 + 111] = 18; + table[18 * 256 + 111] = 18; + table[17 * 256 + 112] = 18; + table[18 * 256 + 112] = 18; + table[17 * 256 + 113] = 18; + table[18 * 256 + 113] = 18; + table[17 * 256 + 114] = 18; + table[18 * 256 + 114] = 18; + table[17 * 256 + 115] = 18; + table[18 * 256 + 115] = 18; + table[17 * 256 + 116] = 18; + table[18 * 256 + 116] = 18; + table[17 * 256 + 117] = 18; + table[18 * 256 + 117] = 18; + table[17 * 256 + 118] = 18; + table[18 * 256 + 118] = 18; + table[17 * 256 + 119] = 18; + table[18 * 256 + 119] = 18; + table[17 * 256 + 120] = 18; + table[18 * 256 + 120] = 18; + table[17 * 256 + 121] = 18; + table[18 * 256 + 121] = 18; + table[17 * 256 + 122] = 18; + table[18 * 256 + 122] = 18; + table[17 * 256 + 123] = 18; + table[18 * 256 + 123] = 18; + table[17 * 256 + 124] = 18; + table[18 * 256 + 124] = 18; + table[17 * 256 + 125] = 18; + table[18 * 256 + 125] = 18; + table[17 * 256 + 126] = 18; + table[18 * 256 + 126] = 18; + table[17 * 256 + 127] = 18; + table[18 * 256 + 127] = 18; + table[17 * 256 + 128] = 18; + table[18 * 256 + 128] = 18; + table[17 * 256 + 129] = 18; + table[18 * 256 + 129] = 18; + table[17 * 256 + 130] = 18; + table[18 * 256 + 130] = 18; + table[17 * 256 + 131] = 18; + table[18 * 256 + 131] = 18; + table[17 * 256 + 132] = 18; + table[18 * 256 + 132] = 18; + table[17 * 256 + 133] = 18; + table[18 * 256 + 133] = 18; + table[17 * 256 + 134] = 18; + table[18 * 256 + 134] = 18; + table[17 * 256 + 135] = 18; + table[18 * 256 + 135] = 18; + table[17 * 256 + 136] = 18; + table[18 * 256 + 136] = 18; + table[17 * 256 + 137] = 18; + table[18 * 256 + 137] = 18; + table[17 * 256 + 138] = 18; + table[18 * 256 + 138] = 18; + table[17 * 256 + 139] = 18; + table[18 * 256 + 139] = 18; + table[17 * 256 + 140] = 18; + table[18 * 256 + 140] = 18; + table[17 * 256 + 141] = 18; + table[18 * 256 + 141] = 18; + table[17 * 256 + 142] = 18; + table[18 * 256 + 142] = 18; + table[17 * 256 + 143] = 18; + table[18 * 256 + 143] = 18; + table[17 * 256 + 144] = 18; + table[18 * 256 + 144] = 18; + table[17 * 256 + 145] = 18; + table[18 * 256 + 145] = 18; + table[17 * 256 + 146] = 18; + table[18 * 256 + 146] = 18; + table[17 * 256 + 147] = 18; + table[18 * 256 + 147] = 18; + table[17 * 256 + 148] = 18; + table[18 * 256 + 148] = 18; + table[17 * 256 + 149] = 18; + table[18 * 256 + 149] = 18; + table[17 * 256 + 150] = 18; + table[18 * 256 + 150] = 18; + table[17 * 256 + 151] = 18; + table[18 * 256 + 151] = 18; + table[17 * 256 + 152] = 18; + table[18 * 256 + 152] = 18; + table[17 * 256 + 153] = 18; + table[18 * 256 + 153] = 18; + table[17 * 256 + 154] = 18; + table[18 * 256 + 154] = 18; + table[17 * 256 + 155] = 18; + table[18 * 256 + 155] = 18; + table[17 * 256 + 156] = 18; + table[18 * 256 + 156] = 18; + table[17 * 256 + 157] = 18; + table[18 * 256 + 157] = 18; + table[17 * 256 + 158] = 18; + table[18 * 256 + 158] = 18; + table[17 * 256 + 159] = 18; + table[18 * 256 + 159] = 18; + table[17 * 256 + 160] = 18; + table[18 * 256 + 160] = 18; + table[17 * 256 + 161] = 18; + table[18 * 256 + 161] = 18; + table[17 * 256 + 162] = 18; + table[18 * 256 + 162] = 18; + table[17 * 256 + 163] = 18; + table[18 * 256 + 163] = 18; + table[17 * 256 + 164] = 18; + table[18 * 256 + 164] = 18; + table[17 * 256 + 165] = 18; + table[18 * 256 + 165] = 18; + table[17 * 256 + 166] = 18; + table[18 * 256 + 166] = 18; + table[17 * 256 + 167] = 18; + table[18 * 256 + 167] = 18; + table[17 * 256 + 168] = 18; + table[18 * 256 + 168] = 18; + table[17 * 256 + 169] = 18; + table[18 * 256 + 169] = 18; + table[17 * 256 + 170] = 18; + table[18 * 256 + 170] = 18; + table[17 * 256 + 171] = 18; + table[18 * 256 + 171] = 18; + table[17 * 256 + 172] = 18; + table[18 * 256 + 172] = 18; + table[17 * 256 + 173] = 18; + table[18 * 256 + 173] = 18; + table[17 * 256 + 174] = 18; + table[18 * 256 + 174] = 18; + table[17 * 256 + 175] = 18; + table[18 * 256 + 175] = 18; + table[17 * 256 + 176] = 18; + table[18 * 256 + 176] = 18; + table[17 * 256 + 177] = 18; + table[18 * 256 + 177] = 18; + table[17 * 256 + 178] = 18; + table[18 * 256 + 178] = 18; + table[17 * 256 + 179] = 18; + table[18 * 256 + 179] = 18; + table[17 * 256 + 180] = 18; + table[18 * 256 + 180] = 18; + table[17 * 256 + 181] = 18; + table[18 * 256 + 181] = 18; + table[17 * 256 + 182] = 18; + table[18 * 256 + 182] = 18; + table[17 * 256 + 183] = 18; + table[18 * 256 + 183] = 18; + table[17 * 256 + 184] = 18; + table[18 * 256 + 184] = 18; + table[17 * 256 + 185] = 18; + table[18 * 256 + 185] = 18; + table[17 * 256 + 186] = 18; + table[18 * 256 + 186] = 18; + table[17 * 256 + 187] = 18; + table[18 * 256 + 187] = 18; + table[17 * 256 + 188] = 18; + table[18 * 256 + 188] = 18; + table[17 * 256 + 189] = 18; + table[18 * 256 + 189] = 18; + table[17 * 256 + 190] = 18; + table[18 * 256 + 190] = 18; + table[17 * 256 + 191] = 18; + table[18 * 256 + 191] = 18; + table[17 * 256 + 192] = 18; + table[18 * 256 + 192] = 18; + table[17 * 256 + 193] = 18; + table[18 * 256 + 193] = 18; + table[17 * 256 + 194] = 18; + table[18 * 256 + 194] = 18; + table[17 * 256 + 195] = 18; + table[18 * 256 + 195] = 18; + table[17 * 256 + 196] = 18; + table[18 * 256 + 196] = 18; + table[17 * 256 + 197] = 18; + table[18 * 256 + 197] = 18; + table[17 * 256 + 198] = 18; + table[18 * 256 + 198] = 18; + table[17 * 256 + 199] = 18; + table[18 * 256 + 199] = 18; + table[17 * 256 + 200] = 18; + table[18 * 256 + 200] = 18; + table[17 * 256 + 201] = 18; + table[18 * 256 + 201] = 18; + table[17 * 256 + 202] = 18; + table[18 * 256 + 202] = 18; + table[17 * 256 + 203] = 18; + table[18 * 256 + 203] = 18; + table[17 * 256 + 204] = 18; + table[18 * 256 + 204] = 18; + table[17 * 256 + 205] = 18; + table[18 * 256 + 205] = 18; + table[17 * 256 + 206] = 18; + table[18 * 256 + 206] = 18; + table[17 * 256 + 207] = 18; + table[18 * 256 + 207] = 18; + table[17 * 256 + 208] = 18; + table[18 * 256 + 208] = 18; + table[17 * 256 + 209] = 18; + table[18 * 256 + 209] = 18; + table[17 * 256 + 210] = 18; + table[18 * 256 + 210] = 18; + table[17 * 256 + 211] = 18; + table[18 * 256 + 211] = 18; + table[17 * 256 + 212] = 18; + table[18 * 256 + 212] = 18; + table[17 * 256 + 213] = 18; + table[18 * 256 + 213] = 18; + table[17 * 256 + 214] = 18; + table[18 * 256 + 214] = 18; + table[17 * 256 + 215] = 18; + table[18 * 256 + 215] = 18; + table[17 * 256 + 216] = 18; + table[18 * 256 + 216] = 18; + table[17 * 256 + 217] = 18; + table[18 * 256 + 217] = 18; + table[17 * 256 + 218] = 18; + table[18 * 256 + 218] = 18; + table[17 * 256 + 219] = 18; + table[18 * 256 + 219] = 18; + table[17 * 256 + 220] = 18; + table[18 * 256 + 220] = 18; + table[17 * 256 + 221] = 18; + table[18 * 256 + 221] = 18; + table[17 * 256 + 222] = 18; + table[18 * 256 + 222] = 18; + table[17 * 256 + 223] = 18; + table[18 * 256 + 223] = 18; + table[17 * 256 + 224] = 18; + table[18 * 256 + 224] = 18; + table[17 * 256 + 225] = 18; + table[18 * 256 + 225] = 18; + table[17 * 256 + 226] = 18; + table[18 * 256 + 226] = 18; + table[17 * 256 + 227] = 18; + table[18 * 256 + 227] = 18; + table[17 * 256 + 228] = 18; + table[18 * 256 + 228] = 18; + table[17 * 256 + 229] = 18; + table[18 * 256 + 229] = 18; + table[17 * 256 + 230] = 18; + table[18 * 256 + 230] = 18; + table[17 * 256 + 231] = 18; + table[18 * 256 + 231] = 18; + table[17 * 256 + 232] = 18; + table[18 * 256 + 232] = 18; + table[17 * 256 + 233] = 18; + table[18 * 256 + 233] = 18; + table[17 * 256 + 234] = 18; + table[18 * 256 + 234] = 18; + table[17 * 256 + 235] = 18; + table[18 * 256 + 235] = 18; + table[17 * 256 + 236] = 18; + table[18 * 256 + 236] = 18; + table[17 * 256 + 237] = 18; + table[18 * 256 + 237] = 18; + table[17 * 256 + 238] = 18; + table[18 * 256 + 238] = 18; + table[17 * 256 + 239] = 18; + table[18 * 256 + 239] = 18; + table[17 * 256 + 240] = 18; + table[18 * 256 + 240] = 18; + table[17 * 256 + 241] = 18; + table[18 * 256 + 241] = 18; + table[17 * 256 + 242] = 18; + table[18 * 256 + 242] = 18; + table[17 * 256 + 243] = 18; + table[18 * 256 + 243] = 18; + table[17 * 256 + 244] = 18; + table[18 * 256 + 244] = 18; + table[17 * 256 + 245] = 18; + table[18 * 256 + 245] = 18; + table[17 * 256 + 246] = 18; + table[18 * 256 + 246] = 18; + table[17 * 256 + 247] = 18; + table[18 * 256 + 247] = 18; + table[17 * 256 + 248] = 18; + table[18 * 256 + 248] = 18; + table[17 * 256 + 249] = 18; + table[18 * 256 + 249] = 18; + table[17 * 256 + 250] = 18; + table[18 * 256 + 250] = 18; + table[17 * 256 + 251] = 18; + table[18 * 256 + 251] = 18; + table[17 * 256 + 252] = 18; + table[18 * 256 + 252] = 18; + table[17 * 256 + 253] = 18; + table[18 * 256 + 253] = 18; + table[17 * 256 + 254] = 18; + table[18 * 256 + 254] = 18; + table[0 * 256 + 13] = 1; + table[0 * 256 + 255] = 2; + table[1 * 256 + 10] = 2; + table[2 * 256 + 102] = 3; + table[3 * 256 + 114] = 4; + table[4 * 256 + 111] = 5; + table[5 * 256 + 109] = 6; + table[6 * 256 + 58] = 7; + table[7 * 256 + 0] = 8; + table[7 * 256 + 1] = 8; + table[7 * 256 + 2] = 8; + table[7 * 256 + 3] = 8; + table[7 * 256 + 4] = 8; + table[7 * 256 + 5] = 8; + table[7 * 256 + 6] = 8; + table[7 * 256 + 7] = 8; + table[7 * 256 + 8] = 8; + table[7 * 256 + 9] = 8; + table[7 * 256 + 11] = 8; + table[7 * 256 + 12] = 8; + table[7 * 256 + 14] = 8; + table[7 * 256 + 15] = 8; + table[7 * 256 + 16] = 8; + table[7 * 256 + 17] = 8; + table[7 * 256 + 18] = 8; + table[7 * 256 + 19] = 8; + table[7 * 256 + 20] = 8; + table[7 * 256 + 21] = 8; + table[7 * 256 + 22] = 8; + table[7 * 256 + 23] = 8; + table[7 * 256 + 24] = 8; + table[7 * 256 + 25] = 8; + table[7 * 256 + 26] = 8; + table[7 * 256 + 27] = 8; + table[7 * 256 + 28] = 8; + table[7 * 256 + 29] = 8; + table[7 * 256 + 30] = 8; + table[7 * 256 + 31] = 8; + table[7 * 256 + 32] = 8; + table[7 * 256 + 33] = 8; + table[7 * 256 + 34] = 8; + table[7 * 256 + 35] = 8; + table[7 * 256 + 36] = 8; + table[7 * 256 + 37] = 8; + table[7 * 256 + 38] = 8; + table[7 * 256 + 39] = 8; + table[7 * 256 + 40] = 8; + table[7 * 256 + 41] = 8; + table[7 * 256 + 42] = 8; + table[7 * 256 + 43] = 8; + table[7 * 256 + 44] = 8; + table[7 * 256 + 45] = 8; + table[7 * 256 + 46] = 8; + table[7 * 256 + 47] = 8; + table[7 * 256 + 48] = 8; + table[7 * 256 + 49] = 8; + table[7 * 256 + 50] = 8; + table[7 * 256 + 51] = 8; + table[7 * 256 + 52] = 8; + table[7 * 256 + 53] = 8; + table[7 * 256 + 54] = 8; + table[7 * 256 + 55] = 8; + table[7 * 256 + 56] = 8; + table[7 * 256 + 57] = 8; + table[7 * 256 + 58] = 8; + table[7 * 256 + 59] = 8; + table[7 * 256 + 60] = 8; + table[7 * 256 + 61] = 8; + table[7 * 256 + 62] = 8; + table[7 * 256 + 63] = 8; + table[7 * 256 + 64] = 8; + table[7 * 256 + 65] = 8; + table[7 * 256 + 66] = 8; + table[7 * 256 + 67] = 8; + table[7 * 256 + 68] = 8; + table[7 * 256 + 69] = 8; + table[7 * 256 + 70] = 8; + table[7 * 256 + 71] = 8; + table[7 * 256 + 72] = 8; + table[7 * 256 + 73] = 8; + table[7 * 256 + 74] = 8; + table[7 * 256 + 75] = 8; + table[7 * 256 + 76] = 8; + table[7 * 256 + 77] = 8; + table[7 * 256 + 78] = 8; + table[7 * 256 + 79] = 8; + table[7 * 256 + 80] = 8; + table[7 * 256 + 81] = 8; + table[7 * 256 + 82] = 8; + table[7 * 256 + 83] = 8; + table[7 * 256 + 84] = 8; + table[7 * 256 + 85] = 8; + table[7 * 256 + 86] = 8; + table[7 * 256 + 87] = 8; + table[7 * 256 + 88] = 8; + table[7 * 256 + 89] = 8; + table[7 * 256 + 90] = 8; + table[7 * 256 + 91] = 8; + table[7 * 256 + 92] = 8; + table[7 * 256 + 93] = 8; + table[7 * 256 + 94] = 8; + table[7 * 256 + 95] = 8; + table[7 * 256 + 96] = 8; + table[7 * 256 + 97] = 8; + table[7 * 256 + 98] = 8; + table[7 * 256 + 99] = 8; + table[7 * 256 + 100] = 8; + table[7 * 256 + 101] = 8; + table[7 * 256 + 102] = 8; + table[7 * 256 + 103] = 8; + table[7 * 256 + 104] = 8; + table[7 * 256 + 105] = 8; + table[7 * 256 + 106] = 8; + table[7 * 256 + 107] = 8; + table[7 * 256 + 108] = 8; + table[7 * 256 + 109] = 8; + table[7 * 256 + 110] = 8; + table[7 * 256 + 111] = 8; + table[7 * 256 + 112] = 8; + table[7 * 256 + 113] = 8; + table[7 * 256 + 114] = 8; + table[7 * 256 + 115] = 8; + table[7 * 256 + 116] = 8; + table[7 * 256 + 117] = 8; + table[7 * 256 + 118] = 8; + table[7 * 256 + 119] = 8; + table[7 * 256 + 120] = 8; + table[7 * 256 + 121] = 8; + table[7 * 256 + 122] = 8; + table[7 * 256 + 123] = 8; + table[7 * 256 + 124] = 8; + table[7 * 256 + 125] = 8; + table[7 * 256 + 126] = 8; + table[7 * 256 + 127] = 8; + table[7 * 256 + 194] = 9; + table[7 * 256 + 195] = 9; + table[7 * 256 + 196] = 9; + table[7 * 256 + 197] = 9; + table[7 * 256 + 198] = 9; + table[7 * 256 + 199] = 9; + table[7 * 256 + 200] = 9; + table[7 * 256 + 201] = 9; + table[7 * 256 + 202] = 9; + table[7 * 256 + 203] = 9; + table[7 * 256 + 204] = 9; + table[7 * 256 + 205] = 9; + table[7 * 256 + 206] = 9; + table[7 * 256 + 207] = 9; + table[7 * 256 + 208] = 9; + table[7 * 256 + 209] = 9; + table[7 * 256 + 210] = 9; + table[7 * 256 + 211] = 9; + table[7 * 256 + 212] = 9; + table[7 * 256 + 213] = 9; + table[7 * 256 + 214] = 9; + table[7 * 256 + 215] = 9; + table[7 * 256 + 216] = 9; + table[7 * 256 + 217] = 9; + table[7 * 256 + 218] = 9; + table[7 * 256 + 219] = 9; + table[7 * 256 + 220] = 9; + table[7 * 256 + 221] = 9; + table[7 * 256 + 222] = 9; + table[7 * 256 + 223] = 9; + table[7 * 256 + 224] = 10; + table[7 * 256 + 225] = 11; + table[7 * 256 + 226] = 11; + table[7 * 256 + 227] = 11; + table[7 * 256 + 228] = 11; + table[7 * 256 + 229] = 11; + table[7 * 256 + 230] = 11; + table[7 * 256 + 231] = 11; + table[7 * 256 + 232] = 11; + table[7 * 256 + 233] = 11; + table[7 * 256 + 234] = 11; + table[7 * 256 + 235] = 11; + table[7 * 256 + 236] = 11; + table[7 * 256 + 238] = 11; + table[7 * 256 + 239] = 11; + table[7 * 256 + 237] = 12; + table[7 * 256 + 240] = 13; + table[7 * 256 + 241] = 14; + table[7 * 256 + 242] = 14; + table[7 * 256 + 243] = 14; + table[7 * 256 + 244] = 15; + table[8 * 256 + 0] = 8; + table[8 * 256 + 1] = 8; + table[8 * 256 + 2] = 8; + table[8 * 256 + 3] = 8; + table[8 * 256 + 4] = 8; + table[8 * 256 + 5] = 8; + table[8 * 256 + 6] = 8; + table[8 * 256 + 7] = 8; + table[8 * 256 + 8] = 8; + table[8 * 256 + 9] = 8; + table[8 * 256 + 11] = 8; + table[8 * 256 + 12] = 8; + table[8 * 256 + 14] = 8; + table[8 * 256 + 15] = 8; + table[8 * 256 + 16] = 8; + table[8 * 256 + 17] = 8; + table[8 * 256 + 18] = 8; + table[8 * 256 + 19] = 8; + table[8 * 256 + 20] = 8; + table[8 * 256 + 21] = 8; + table[8 * 256 + 22] = 8; + table[8 * 256 + 23] = 8; + table[8 * 256 + 24] = 8; + table[8 * 256 + 25] = 8; + table[8 * 256 + 26] = 8; + table[8 * 256 + 27] = 8; + table[8 * 256 + 28] = 8; + table[8 * 256 + 29] = 8; + table[8 * 256 + 30] = 8; + table[8 * 256 + 31] = 8; + table[8 * 256 + 32] = 8; + table[8 * 256 + 33] = 8; + table[8 * 256 + 34] = 8; + table[8 * 256 + 35] = 8; + table[8 * 256 + 36] = 8; + table[8 * 256 + 37] = 8; + table[8 * 256 + 38] = 8; + table[8 * 256 + 39] = 8; + table[8 * 256 + 40] = 8; + table[8 * 256 + 41] = 8; + table[8 * 256 + 42] = 8; + table[8 * 256 + 43] = 8; + table[8 * 256 + 44] = 8; + table[8 * 256 + 45] = 8; + table[8 * 256 + 46] = 8; + table[8 * 256 + 47] = 8; + table[8 * 256 + 48] = 8; + table[8 * 256 + 49] = 8; + table[8 * 256 + 50] = 8; + table[8 * 256 + 51] = 8; + table[8 * 256 + 52] = 8; + table[8 * 256 + 53] = 8; + table[8 * 256 + 54] = 8; + table[8 * 256 + 55] = 8; + table[8 * 256 + 56] = 8; + table[8 * 256 + 57] = 8; + table[8 * 256 + 58] = 8; + table[8 * 256 + 59] = 8; + table[8 * 256 + 60] = 8; + table[8 * 256 + 61] = 8; + table[8 * 256 + 62] = 8; + table[8 * 256 + 63] = 8; + table[8 * 256 + 64] = 8; + table[8 * 256 + 65] = 8; + table[8 * 256 + 66] = 8; + table[8 * 256 + 67] = 8; + table[8 * 256 + 68] = 8; + table[8 * 256 + 69] = 8; + table[8 * 256 + 70] = 8; + table[8 * 256 + 71] = 8; + table[8 * 256 + 72] = 8; + table[8 * 256 + 73] = 8; + table[8 * 256 + 74] = 8; + table[8 * 256 + 75] = 8; + table[8 * 256 + 76] = 8; + table[8 * 256 + 77] = 8; + table[8 * 256 + 78] = 8; + table[8 * 256 + 79] = 8; + table[8 * 256 + 80] = 8; + table[8 * 256 + 81] = 8; + table[8 * 256 + 82] = 8; + table[8 * 256 + 83] = 8; + table[8 * 256 + 84] = 8; + table[8 * 256 + 85] = 8; + table[8 * 256 + 86] = 8; + table[8 * 256 + 87] = 8; + table[8 * 256 + 88] = 8; + table[8 * 256 + 89] = 8; + table[8 * 256 + 90] = 8; + table[8 * 256 + 91] = 8; + table[8 * 256 + 92] = 8; + table[8 * 256 + 93] = 8; + table[8 * 256 + 94] = 8; + table[8 * 256 + 95] = 8; + table[8 * 256 + 96] = 8; + table[8 * 256 + 97] = 8; + table[8 * 256 + 98] = 8; + table[8 * 256 + 99] = 8; + table[8 * 256 + 100] = 8; + table[8 * 256 + 101] = 8; + table[8 * 256 + 102] = 8; + table[8 * 256 + 103] = 8; + table[8 * 256 + 104] = 8; + table[8 * 256 + 105] = 8; + table[8 * 256 + 106] = 8; + table[8 * 256 + 107] = 8; + table[8 * 256 + 108] = 8; + table[8 * 256 + 109] = 8; + table[8 * 256 + 110] = 8; + table[8 * 256 + 111] = 8; + table[8 * 256 + 112] = 8; + table[8 * 256 + 113] = 8; + table[8 * 256 + 114] = 8; + table[8 * 256 + 115] = 8; + table[8 * 256 + 116] = 8; + table[8 * 256 + 117] = 8; + table[8 * 256 + 118] = 8; + table[8 * 256 + 119] = 8; + table[8 * 256 + 120] = 8; + table[8 * 256 + 121] = 8; + table[8 * 256 + 122] = 8; + table[8 * 256 + 123] = 8; + table[8 * 256 + 124] = 8; + table[8 * 256 + 125] = 8; + table[8 * 256 + 126] = 8; + table[8 * 256 + 127] = 8; + table[8 * 256 + 194] = 9; + table[8 * 256 + 195] = 9; + table[8 * 256 + 196] = 9; + table[8 * 256 + 197] = 9; + table[8 * 256 + 198] = 9; + table[8 * 256 + 199] = 9; + table[8 * 256 + 200] = 9; + table[8 * 256 + 201] = 9; + table[8 * 256 + 202] = 9; + table[8 * 256 + 203] = 9; + table[8 * 256 + 204] = 9; + table[8 * 256 + 205] = 9; + table[8 * 256 + 206] = 9; + table[8 * 256 + 207] = 9; + table[8 * 256 + 208] = 9; + table[8 * 256 + 209] = 9; + table[8 * 256 + 210] = 9; + table[8 * 256 + 211] = 9; + table[8 * 256 + 212] = 9; + table[8 * 256 + 213] = 9; + table[8 * 256 + 214] = 9; + table[8 * 256 + 215] = 9; + table[8 * 256 + 216] = 9; + table[8 * 256 + 217] = 9; + table[8 * 256 + 218] = 9; + table[8 * 256 + 219] = 9; + table[8 * 256 + 220] = 9; + table[8 * 256 + 221] = 9; + table[8 * 256 + 222] = 9; + table[8 * 256 + 223] = 9; + table[8 * 256 + 224] = 10; + table[8 * 256 + 225] = 11; + table[8 * 256 + 226] = 11; + table[8 * 256 + 227] = 11; + table[8 * 256 + 228] = 11; + table[8 * 256 + 229] = 11; + table[8 * 256 + 230] = 11; + table[8 * 256 + 231] = 11; + table[8 * 256 + 232] = 11; + table[8 * 256 + 233] = 11; + table[8 * 256 + 234] = 11; + table[8 * 256 + 235] = 11; + table[8 * 256 + 236] = 11; + table[8 * 256 + 238] = 11; + table[8 * 256 + 239] = 11; + table[8 * 256 + 237] = 12; + table[8 * 256 + 240] = 13; + table[8 * 256 + 241] = 14; + table[8 * 256 + 242] = 14; + table[8 * 256 + 243] = 14; + table[8 * 256 + 244] = 15; + table[8 * 256 + 13] = 16; + table[9 * 256 + 128] = 8; + table[9 * 256 + 129] = 8; + table[9 * 256 + 130] = 8; + table[9 * 256 + 131] = 8; + table[9 * 256 + 132] = 8; + table[9 * 256 + 133] = 8; + table[9 * 256 + 134] = 8; + table[9 * 256 + 135] = 8; + table[9 * 256 + 136] = 8; + table[9 * 256 + 137] = 8; + table[9 * 256 + 138] = 8; + table[9 * 256 + 139] = 8; + table[9 * 256 + 140] = 8; + table[9 * 256 + 141] = 8; + table[9 * 256 + 142] = 8; + table[9 * 256 + 143] = 8; + table[9 * 256 + 144] = 8; + table[9 * 256 + 145] = 8; + table[9 * 256 + 146] = 8; + table[9 * 256 + 147] = 8; + table[9 * 256 + 148] = 8; + table[9 * 256 + 149] = 8; + table[9 * 256 + 150] = 8; + table[9 * 256 + 151] = 8; + table[9 * 256 + 152] = 8; + table[9 * 256 + 153] = 8; + table[9 * 256 + 154] = 8; + table[9 * 256 + 155] = 8; + table[9 * 256 + 156] = 8; + table[9 * 256 + 157] = 8; + table[9 * 256 + 158] = 8; + table[9 * 256 + 159] = 8; + table[9 * 256 + 160] = 8; + table[9 * 256 + 161] = 8; + table[9 * 256 + 162] = 8; + table[9 * 256 + 163] = 8; + table[9 * 256 + 164] = 8; + table[9 * 256 + 165] = 8; + table[9 * 256 + 166] = 8; + table[9 * 256 + 167] = 8; + table[9 * 256 + 168] = 8; + table[9 * 256 + 169] = 8; + table[9 * 256 + 170] = 8; + table[9 * 256 + 171] = 8; + table[9 * 256 + 172] = 8; + table[9 * 256 + 173] = 8; + table[9 * 256 + 174] = 8; + table[9 * 256 + 175] = 8; + table[9 * 256 + 176] = 8; + table[9 * 256 + 177] = 8; + table[9 * 256 + 178] = 8; + table[9 * 256 + 179] = 8; + table[9 * 256 + 180] = 8; + table[9 * 256 + 181] = 8; + table[9 * 256 + 182] = 8; + table[9 * 256 + 183] = 8; + table[9 * 256 + 184] = 8; + table[9 * 256 + 185] = 8; + table[9 * 256 + 186] = 8; + table[9 * 256 + 187] = 8; + table[9 * 256 + 188] = 8; + table[9 * 256 + 189] = 8; + table[9 * 256 + 190] = 8; + table[9 * 256 + 191] = 8; + table[10 * 256 + 160] = 9; + table[10 * 256 + 161] = 9; + table[10 * 256 + 162] = 9; + table[10 * 256 + 163] = 9; + table[10 * 256 + 164] = 9; + table[10 * 256 + 165] = 9; + table[10 * 256 + 166] = 9; + table[10 * 256 + 167] = 9; + table[10 * 256 + 168] = 9; + table[10 * 256 + 169] = 9; + table[10 * 256 + 170] = 9; + table[10 * 256 + 171] = 9; + table[10 * 256 + 172] = 9; + table[10 * 256 + 173] = 9; + table[10 * 256 + 174] = 9; + table[10 * 256 + 175] = 9; + table[10 * 256 + 176] = 9; + table[10 * 256 + 177] = 9; + table[10 * 256 + 178] = 9; + table[10 * 256 + 179] = 9; + table[10 * 256 + 180] = 9; + table[10 * 256 + 181] = 9; + table[10 * 256 + 182] = 9; + table[10 * 256 + 183] = 9; + table[10 * 256 + 184] = 9; + table[10 * 256 + 185] = 9; + table[10 * 256 + 186] = 9; + table[10 * 256 + 187] = 9; + table[10 * 256 + 188] = 9; + table[10 * 256 + 189] = 9; + table[10 * 256 + 190] = 9; + table[10 * 256 + 191] = 9; + table[11 * 256 + 128] = 9; + table[11 * 256 + 129] = 9; + table[11 * 256 + 130] = 9; + table[11 * 256 + 131] = 9; + table[11 * 256 + 132] = 9; + table[11 * 256 + 133] = 9; + table[11 * 256 + 134] = 9; + table[11 * 256 + 135] = 9; + table[11 * 256 + 136] = 9; + table[11 * 256 + 137] = 9; + table[11 * 256 + 138] = 9; + table[11 * 256 + 139] = 9; + table[11 * 256 + 140] = 9; + table[11 * 256 + 141] = 9; + table[11 * 256 + 142] = 9; + table[11 * 256 + 143] = 9; + table[11 * 256 + 144] = 9; + table[11 * 256 + 145] = 9; + table[11 * 256 + 146] = 9; + table[11 * 256 + 147] = 9; + table[11 * 256 + 148] = 9; + table[11 * 256 + 149] = 9; + table[11 * 256 + 150] = 9; + table[11 * 256 + 151] = 9; + table[11 * 256 + 152] = 9; + table[11 * 256 + 153] = 9; + table[11 * 256 + 154] = 9; + table[11 * 256 + 155] = 9; + table[11 * 256 + 156] = 9; + table[11 * 256 + 157] = 9; + table[11 * 256 + 158] = 9; + table[11 * 256 + 159] = 9; + table[11 * 256 + 160] = 9; + table[11 * 256 + 161] = 9; + table[11 * 256 + 162] = 9; + table[11 * 256 + 163] = 9; + table[11 * 256 + 164] = 9; + table[11 * 256 + 165] = 9; + table[11 * 256 + 166] = 9; + table[11 * 256 + 167] = 9; + table[11 * 256 + 168] = 9; + table[11 * 256 + 169] = 9; + table[11 * 256 + 170] = 9; + table[11 * 256 + 171] = 9; + table[11 * 256 + 172] = 9; + table[11 * 256 + 173] = 9; + table[11 * 256 + 174] = 9; + table[11 * 256 + 175] = 9; + table[11 * 256 + 176] = 9; + table[11 * 256 + 177] = 9; + table[11 * 256 + 178] = 9; + table[11 * 256 + 179] = 9; + table[11 * 256 + 180] = 9; + table[11 * 256 + 181] = 9; + table[11 * 256 + 182] = 9; + table[11 * 256 + 183] = 9; + table[11 * 256 + 184] = 9; + table[11 * 256 + 185] = 9; + table[11 * 256 + 186] = 9; + table[11 * 256 + 187] = 9; + table[11 * 256 + 188] = 9; + table[11 * 256 + 189] = 9; + table[11 * 256 + 190] = 9; + table[11 * 256 + 191] = 9; + table[12 * 256 + 128] = 9; + table[12 * 256 + 129] = 9; + table[12 * 256 + 130] = 9; + table[12 * 256 + 131] = 9; + table[12 * 256 + 132] = 9; + table[12 * 256 + 133] = 9; + table[12 * 256 + 134] = 9; + table[12 * 256 + 135] = 9; + table[12 * 256 + 136] = 9; + table[12 * 256 + 137] = 9; + table[12 * 256 + 138] = 9; + table[12 * 256 + 139] = 9; + table[12 * 256 + 140] = 9; + table[12 * 256 + 141] = 9; + table[12 * 256 + 142] = 9; + table[12 * 256 + 143] = 9; + table[12 * 256 + 144] = 9; + table[12 * 256 + 145] = 9; + table[12 * 256 + 146] = 9; + table[12 * 256 + 147] = 9; + table[12 * 256 + 148] = 9; + table[12 * 256 + 149] = 9; + table[12 * 256 + 150] = 9; + table[12 * 256 + 151] = 9; + table[12 * 256 + 152] = 9; + table[12 * 256 + 153] = 9; + table[12 * 256 + 154] = 9; + table[12 * 256 + 155] = 9; + table[12 * 256 + 156] = 9; + table[12 * 256 + 157] = 9; + table[12 * 256 + 158] = 9; + table[12 * 256 + 159] = 9; + table[13 * 256 + 144] = 11; + table[13 * 256 + 145] = 11; + table[13 * 256 + 146] = 11; + table[13 * 256 + 147] = 11; + table[13 * 256 + 148] = 11; + table[13 * 256 + 149] = 11; + table[13 * 256 + 150] = 11; + table[13 * 256 + 151] = 11; + table[13 * 256 + 152] = 11; + table[13 * 256 + 153] = 11; + table[13 * 256 + 154] = 11; + table[13 * 256 + 155] = 11; + table[13 * 256 + 156] = 11; + table[13 * 256 + 157] = 11; + table[13 * 256 + 158] = 11; + table[13 * 256 + 159] = 11; + table[13 * 256 + 160] = 11; + table[13 * 256 + 161] = 11; + table[13 * 256 + 162] = 11; + table[13 * 256 + 163] = 11; + table[13 * 256 + 164] = 11; + table[13 * 256 + 165] = 11; + table[13 * 256 + 166] = 11; + table[13 * 256 + 167] = 11; + table[13 * 256 + 168] = 11; + table[13 * 256 + 169] = 11; + table[13 * 256 + 170] = 11; + table[13 * 256 + 171] = 11; + table[13 * 256 + 172] = 11; + table[13 * 256 + 173] = 11; + table[13 * 256 + 174] = 11; + table[13 * 256 + 175] = 11; + table[13 * 256 + 176] = 11; + table[13 * 256 + 177] = 11; + table[13 * 256 + 178] = 11; + table[13 * 256 + 179] = 11; + table[13 * 256 + 180] = 11; + table[13 * 256 + 181] = 11; + table[13 * 256 + 182] = 11; + table[13 * 256 + 183] = 11; + table[13 * 256 + 184] = 11; + table[13 * 256 + 185] = 11; + table[13 * 256 + 186] = 11; + table[13 * 256 + 187] = 11; + table[13 * 256 + 188] = 11; + table[13 * 256 + 189] = 11; + table[13 * 256 + 190] = 11; + table[13 * 256 + 191] = 11; + table[14 * 256 + 128] = 11; + table[14 * 256 + 129] = 11; + table[14 * 256 + 130] = 11; + table[14 * 256 + 131] = 11; + table[14 * 256 + 132] = 11; + table[14 * 256 + 133] = 11; + table[14 * 256 + 134] = 11; + table[14 * 256 + 135] = 11; + table[14 * 256 + 136] = 11; + table[14 * 256 + 137] = 11; + table[14 * 256 + 138] = 11; + table[14 * 256 + 139] = 11; + table[14 * 256 + 140] = 11; + table[14 * 256 + 141] = 11; + table[14 * 256 + 142] = 11; + table[14 * 256 + 143] = 11; + table[14 * 256 + 144] = 11; + table[14 * 256 + 145] = 11; + table[14 * 256 + 146] = 11; + table[14 * 256 + 147] = 11; + table[14 * 256 + 148] = 11; + table[14 * 256 + 149] = 11; + table[14 * 256 + 150] = 11; + table[14 * 256 + 151] = 11; + table[14 * 256 + 152] = 11; + table[14 * 256 + 153] = 11; + table[14 * 256 + 154] = 11; + table[14 * 256 + 155] = 11; + table[14 * 256 + 156] = 11; + table[14 * 256 + 157] = 11; + table[14 * 256 + 158] = 11; + table[14 * 256 + 159] = 11; + table[14 * 256 + 160] = 11; + table[14 * 256 + 161] = 11; + table[14 * 256 + 162] = 11; + table[14 * 256 + 163] = 11; + table[14 * 256 + 164] = 11; + table[14 * 256 + 165] = 11; + table[14 * 256 + 166] = 11; + table[14 * 256 + 167] = 11; + table[14 * 256 + 168] = 11; + table[14 * 256 + 169] = 11; + table[14 * 256 + 170] = 11; + table[14 * 256 + 171] = 11; + table[14 * 256 + 172] = 11; + table[14 * 256 + 173] = 11; + table[14 * 256 + 174] = 11; + table[14 * 256 + 175] = 11; + table[14 * 256 + 176] = 11; + table[14 * 256 + 177] = 11; + table[14 * 256 + 178] = 11; + table[14 * 256 + 179] = 11; + table[14 * 256 + 180] = 11; + table[14 * 256 + 181] = 11; + table[14 * 256 + 182] = 11; + table[14 * 256 + 183] = 11; + table[14 * 256 + 184] = 11; + table[14 * 256 + 185] = 11; + table[14 * 256 + 186] = 11; + table[14 * 256 + 187] = 11; + table[14 * 256 + 188] = 11; + table[14 * 256 + 189] = 11; + table[14 * 256 + 190] = 11; + table[14 * 256 + 191] = 11; + table[15 * 256 + 128] = 11; + table[15 * 256 + 129] = 11; + table[15 * 256 + 130] = 11; + table[15 * 256 + 131] = 11; + table[15 * 256 + 132] = 11; + table[15 * 256 + 133] = 11; + table[15 * 256 + 134] = 11; + table[15 * 256 + 135] = 11; + table[15 * 256 + 136] = 11; + table[15 * 256 + 137] = 11; + table[15 * 256 + 138] = 11; + table[15 * 256 + 139] = 11; + table[15 * 256 + 140] = 11; + table[15 * 256 + 141] = 11; + table[15 * 256 + 142] = 11; + table[15 * 256 + 143] = 11; + table[16 * 256 + 10] = 17; + + table +} +pub fn regex_match(input: [u8; N]) -> bool { + // regex: (\r\n|^)from:[^\r\n]+\r\n + let mut s = 0; + s = table[255]; + for i in 0..input.len() { + let s_idx = s * 256 + input[i] as Field; + std::as_witness(s_idx); + s = table[s_idx]; + } + + let matched: bool = (s == 17) | (s == 18); + + matched +} + + \ No newline at end of file diff --git a/packages/noir/src/basic/message_id.nr b/packages/noir/src/basic/message_id.nr new file mode 100644 index 00000000..ad68eb58 --- /dev/null +++ b/packages/noir/src/basic/message_id.nr @@ -0,0 +1,691 @@ + +use crate::common::Sequence; + + +global table: [Field; 5120] = comptime { make_lookup_table() }; + +comptime fn make_lookup_table() -> [Field; 5120] { + let mut table = [0; 5120]; + table[18 * 256 + 0] = 19; + table[19 * 256 + 0] = 19; + table[18 * 256 + 1] = 19; + table[19 * 256 + 1] = 19; + table[18 * 256 + 2] = 19; + table[19 * 256 + 2] = 19; + table[18 * 256 + 3] = 19; + table[19 * 256 + 3] = 19; + table[18 * 256 + 4] = 19; + table[19 * 256 + 4] = 19; + table[18 * 256 + 5] = 19; + table[19 * 256 + 5] = 19; + table[18 * 256 + 6] = 19; + table[19 * 256 + 6] = 19; + table[18 * 256 + 7] = 19; + table[19 * 256 + 7] = 19; + table[18 * 256 + 8] = 19; + table[19 * 256 + 8] = 19; + table[18 * 256 + 9] = 19; + table[19 * 256 + 9] = 19; + table[18 * 256 + 10] = 19; + table[19 * 256 + 10] = 19; + table[18 * 256 + 11] = 19; + table[19 * 256 + 11] = 19; + table[18 * 256 + 12] = 19; + table[19 * 256 + 12] = 19; + table[18 * 256 + 13] = 19; + table[19 * 256 + 13] = 19; + table[18 * 256 + 14] = 19; + table[19 * 256 + 14] = 19; + table[18 * 256 + 15] = 19; + table[19 * 256 + 15] = 19; + table[18 * 256 + 16] = 19; + table[19 * 256 + 16] = 19; + table[18 * 256 + 17] = 19; + table[19 * 256 + 17] = 19; + table[18 * 256 + 18] = 19; + table[19 * 256 + 18] = 19; + table[18 * 256 + 19] = 19; + table[19 * 256 + 19] = 19; + table[18 * 256 + 20] = 19; + table[19 * 256 + 20] = 19; + table[18 * 256 + 21] = 19; + table[19 * 256 + 21] = 19; + table[18 * 256 + 22] = 19; + table[19 * 256 + 22] = 19; + table[18 * 256 + 23] = 19; + table[19 * 256 + 23] = 19; + table[18 * 256 + 24] = 19; + table[19 * 256 + 24] = 19; + table[18 * 256 + 25] = 19; + table[19 * 256 + 25] = 19; + table[18 * 256 + 26] = 19; + table[19 * 256 + 26] = 19; + table[18 * 256 + 27] = 19; + table[19 * 256 + 27] = 19; + table[18 * 256 + 28] = 19; + table[19 * 256 + 28] = 19; + table[18 * 256 + 29] = 19; + table[19 * 256 + 29] = 19; + table[18 * 256 + 30] = 19; + table[19 * 256 + 30] = 19; + table[18 * 256 + 31] = 19; + table[19 * 256 + 31] = 19; + table[18 * 256 + 32] = 19; + table[19 * 256 + 32] = 19; + table[18 * 256 + 33] = 19; + table[19 * 256 + 33] = 19; + table[18 * 256 + 34] = 19; + table[19 * 256 + 34] = 19; + table[18 * 256 + 35] = 19; + table[19 * 256 + 35] = 19; + table[18 * 256 + 36] = 19; + table[19 * 256 + 36] = 19; + table[18 * 256 + 37] = 19; + table[19 * 256 + 37] = 19; + table[18 * 256 + 38] = 19; + table[19 * 256 + 38] = 19; + table[18 * 256 + 39] = 19; + table[19 * 256 + 39] = 19; + table[18 * 256 + 40] = 19; + table[19 * 256 + 40] = 19; + table[18 * 256 + 41] = 19; + table[19 * 256 + 41] = 19; + table[18 * 256 + 42] = 19; + table[19 * 256 + 42] = 19; + table[18 * 256 + 43] = 19; + table[19 * 256 + 43] = 19; + table[18 * 256 + 44] = 19; + table[19 * 256 + 44] = 19; + table[18 * 256 + 45] = 19; + table[19 * 256 + 45] = 19; + table[18 * 256 + 46] = 19; + table[19 * 256 + 46] = 19; + table[18 * 256 + 47] = 19; + table[19 * 256 + 47] = 19; + table[18 * 256 + 48] = 19; + table[19 * 256 + 48] = 19; + table[18 * 256 + 49] = 19; + table[19 * 256 + 49] = 19; + table[18 * 256 + 50] = 19; + table[19 * 256 + 50] = 19; + table[18 * 256 + 51] = 19; + table[19 * 256 + 51] = 19; + table[18 * 256 + 52] = 19; + table[19 * 256 + 52] = 19; + table[18 * 256 + 53] = 19; + table[19 * 256 + 53] = 19; + table[18 * 256 + 54] = 19; + table[19 * 256 + 54] = 19; + table[18 * 256 + 55] = 19; + table[19 * 256 + 55] = 19; + table[18 * 256 + 56] = 19; + table[19 * 256 + 56] = 19; + table[18 * 256 + 57] = 19; + table[19 * 256 + 57] = 19; + table[18 * 256 + 58] = 19; + table[19 * 256 + 58] = 19; + table[18 * 256 + 59] = 19; + table[19 * 256 + 59] = 19; + table[18 * 256 + 60] = 19; + table[19 * 256 + 60] = 19; + table[18 * 256 + 61] = 19; + table[19 * 256 + 61] = 19; + table[18 * 256 + 62] = 19; + table[19 * 256 + 62] = 19; + table[18 * 256 + 63] = 19; + table[19 * 256 + 63] = 19; + table[18 * 256 + 64] = 19; + table[19 * 256 + 64] = 19; + table[18 * 256 + 65] = 19; + table[19 * 256 + 65] = 19; + table[18 * 256 + 66] = 19; + table[19 * 256 + 66] = 19; + table[18 * 256 + 67] = 19; + table[19 * 256 + 67] = 19; + table[18 * 256 + 68] = 19; + table[19 * 256 + 68] = 19; + table[18 * 256 + 69] = 19; + table[19 * 256 + 69] = 19; + table[18 * 256 + 70] = 19; + table[19 * 256 + 70] = 19; + table[18 * 256 + 71] = 19; + table[19 * 256 + 71] = 19; + table[18 * 256 + 72] = 19; + table[19 * 256 + 72] = 19; + table[18 * 256 + 73] = 19; + table[19 * 256 + 73] = 19; + table[18 * 256 + 74] = 19; + table[19 * 256 + 74] = 19; + table[18 * 256 + 75] = 19; + table[19 * 256 + 75] = 19; + table[18 * 256 + 76] = 19; + table[19 * 256 + 76] = 19; + table[18 * 256 + 77] = 19; + table[19 * 256 + 77] = 19; + table[18 * 256 + 78] = 19; + table[19 * 256 + 78] = 19; + table[18 * 256 + 79] = 19; + table[19 * 256 + 79] = 19; + table[18 * 256 + 80] = 19; + table[19 * 256 + 80] = 19; + table[18 * 256 + 81] = 19; + table[19 * 256 + 81] = 19; + table[18 * 256 + 82] = 19; + table[19 * 256 + 82] = 19; + table[18 * 256 + 83] = 19; + table[19 * 256 + 83] = 19; + table[18 * 256 + 84] = 19; + table[19 * 256 + 84] = 19; + table[18 * 256 + 85] = 19; + table[19 * 256 + 85] = 19; + table[18 * 256 + 86] = 19; + table[19 * 256 + 86] = 19; + table[18 * 256 + 87] = 19; + table[19 * 256 + 87] = 19; + table[18 * 256 + 88] = 19; + table[19 * 256 + 88] = 19; + table[18 * 256 + 89] = 19; + table[19 * 256 + 89] = 19; + table[18 * 256 + 90] = 19; + table[19 * 256 + 90] = 19; + table[18 * 256 + 91] = 19; + table[19 * 256 + 91] = 19; + table[18 * 256 + 92] = 19; + table[19 * 256 + 92] = 19; + table[18 * 256 + 93] = 19; + table[19 * 256 + 93] = 19; + table[18 * 256 + 94] = 19; + table[19 * 256 + 94] = 19; + table[18 * 256 + 95] = 19; + table[19 * 256 + 95] = 19; + table[18 * 256 + 96] = 19; + table[19 * 256 + 96] = 19; + table[18 * 256 + 97] = 19; + table[19 * 256 + 97] = 19; + table[18 * 256 + 98] = 19; + table[19 * 256 + 98] = 19; + table[18 * 256 + 99] = 19; + table[19 * 256 + 99] = 19; + table[18 * 256 + 100] = 19; + table[19 * 256 + 100] = 19; + table[18 * 256 + 101] = 19; + table[19 * 256 + 101] = 19; + table[18 * 256 + 102] = 19; + table[19 * 256 + 102] = 19; + table[18 * 256 + 103] = 19; + table[19 * 256 + 103] = 19; + table[18 * 256 + 104] = 19; + table[19 * 256 + 104] = 19; + table[18 * 256 + 105] = 19; + table[19 * 256 + 105] = 19; + table[18 * 256 + 106] = 19; + table[19 * 256 + 106] = 19; + table[18 * 256 + 107] = 19; + table[19 * 256 + 107] = 19; + table[18 * 256 + 108] = 19; + table[19 * 256 + 108] = 19; + table[18 * 256 + 109] = 19; + table[19 * 256 + 109] = 19; + table[18 * 256 + 110] = 19; + table[19 * 256 + 110] = 19; + table[18 * 256 + 111] = 19; + table[19 * 256 + 111] = 19; + table[18 * 256 + 112] = 19; + table[19 * 256 + 112] = 19; + table[18 * 256 + 113] = 19; + table[19 * 256 + 113] = 19; + table[18 * 256 + 114] = 19; + table[19 * 256 + 114] = 19; + table[18 * 256 + 115] = 19; + table[19 * 256 + 115] = 19; + table[18 * 256 + 116] = 19; + table[19 * 256 + 116] = 19; + table[18 * 256 + 117] = 19; + table[19 * 256 + 117] = 19; + table[18 * 256 + 118] = 19; + table[19 * 256 + 118] = 19; + table[18 * 256 + 119] = 19; + table[19 * 256 + 119] = 19; + table[18 * 256 + 120] = 19; + table[19 * 256 + 120] = 19; + table[18 * 256 + 121] = 19; + table[19 * 256 + 121] = 19; + table[18 * 256 + 122] = 19; + table[19 * 256 + 122] = 19; + table[18 * 256 + 123] = 19; + table[19 * 256 + 123] = 19; + table[18 * 256 + 124] = 19; + table[19 * 256 + 124] = 19; + table[18 * 256 + 125] = 19; + table[19 * 256 + 125] = 19; + table[18 * 256 + 126] = 19; + table[19 * 256 + 126] = 19; + table[18 * 256 + 127] = 19; + table[19 * 256 + 127] = 19; + table[18 * 256 + 128] = 19; + table[19 * 256 + 128] = 19; + table[18 * 256 + 129] = 19; + table[19 * 256 + 129] = 19; + table[18 * 256 + 130] = 19; + table[19 * 256 + 130] = 19; + table[18 * 256 + 131] = 19; + table[19 * 256 + 131] = 19; + table[18 * 256 + 132] = 19; + table[19 * 256 + 132] = 19; + table[18 * 256 + 133] = 19; + table[19 * 256 + 133] = 19; + table[18 * 256 + 134] = 19; + table[19 * 256 + 134] = 19; + table[18 * 256 + 135] = 19; + table[19 * 256 + 135] = 19; + table[18 * 256 + 136] = 19; + table[19 * 256 + 136] = 19; + table[18 * 256 + 137] = 19; + table[19 * 256 + 137] = 19; + table[18 * 256 + 138] = 19; + table[19 * 256 + 138] = 19; + table[18 * 256 + 139] = 19; + table[19 * 256 + 139] = 19; + table[18 * 256 + 140] = 19; + table[19 * 256 + 140] = 19; + table[18 * 256 + 141] = 19; + table[19 * 256 + 141] = 19; + table[18 * 256 + 142] = 19; + table[19 * 256 + 142] = 19; + table[18 * 256 + 143] = 19; + table[19 * 256 + 143] = 19; + table[18 * 256 + 144] = 19; + table[19 * 256 + 144] = 19; + table[18 * 256 + 145] = 19; + table[19 * 256 + 145] = 19; + table[18 * 256 + 146] = 19; + table[19 * 256 + 146] = 19; + table[18 * 256 + 147] = 19; + table[19 * 256 + 147] = 19; + table[18 * 256 + 148] = 19; + table[19 * 256 + 148] = 19; + table[18 * 256 + 149] = 19; + table[19 * 256 + 149] = 19; + table[18 * 256 + 150] = 19; + table[19 * 256 + 150] = 19; + table[18 * 256 + 151] = 19; + table[19 * 256 + 151] = 19; + table[18 * 256 + 152] = 19; + table[19 * 256 + 152] = 19; + table[18 * 256 + 153] = 19; + table[19 * 256 + 153] = 19; + table[18 * 256 + 154] = 19; + table[19 * 256 + 154] = 19; + table[18 * 256 + 155] = 19; + table[19 * 256 + 155] = 19; + table[18 * 256 + 156] = 19; + table[19 * 256 + 156] = 19; + table[18 * 256 + 157] = 19; + table[19 * 256 + 157] = 19; + table[18 * 256 + 158] = 19; + table[19 * 256 + 158] = 19; + table[18 * 256 + 159] = 19; + table[19 * 256 + 159] = 19; + table[18 * 256 + 160] = 19; + table[19 * 256 + 160] = 19; + table[18 * 256 + 161] = 19; + table[19 * 256 + 161] = 19; + table[18 * 256 + 162] = 19; + table[19 * 256 + 162] = 19; + table[18 * 256 + 163] = 19; + table[19 * 256 + 163] = 19; + table[18 * 256 + 164] = 19; + table[19 * 256 + 164] = 19; + table[18 * 256 + 165] = 19; + table[19 * 256 + 165] = 19; + table[18 * 256 + 166] = 19; + table[19 * 256 + 166] = 19; + table[18 * 256 + 167] = 19; + table[19 * 256 + 167] = 19; + table[18 * 256 + 168] = 19; + table[19 * 256 + 168] = 19; + table[18 * 256 + 169] = 19; + table[19 * 256 + 169] = 19; + table[18 * 256 + 170] = 19; + table[19 * 256 + 170] = 19; + table[18 * 256 + 171] = 19; + table[19 * 256 + 171] = 19; + table[18 * 256 + 172] = 19; + table[19 * 256 + 172] = 19; + table[18 * 256 + 173] = 19; + table[19 * 256 + 173] = 19; + table[18 * 256 + 174] = 19; + table[19 * 256 + 174] = 19; + table[18 * 256 + 175] = 19; + table[19 * 256 + 175] = 19; + table[18 * 256 + 176] = 19; + table[19 * 256 + 176] = 19; + table[18 * 256 + 177] = 19; + table[19 * 256 + 177] = 19; + table[18 * 256 + 178] = 19; + table[19 * 256 + 178] = 19; + table[18 * 256 + 179] = 19; + table[19 * 256 + 179] = 19; + table[18 * 256 + 180] = 19; + table[19 * 256 + 180] = 19; + table[18 * 256 + 181] = 19; + table[19 * 256 + 181] = 19; + table[18 * 256 + 182] = 19; + table[19 * 256 + 182] = 19; + table[18 * 256 + 183] = 19; + table[19 * 256 + 183] = 19; + table[18 * 256 + 184] = 19; + table[19 * 256 + 184] = 19; + table[18 * 256 + 185] = 19; + table[19 * 256 + 185] = 19; + table[18 * 256 + 186] = 19; + table[19 * 256 + 186] = 19; + table[18 * 256 + 187] = 19; + table[19 * 256 + 187] = 19; + table[18 * 256 + 188] = 19; + table[19 * 256 + 188] = 19; + table[18 * 256 + 189] = 19; + table[19 * 256 + 189] = 19; + table[18 * 256 + 190] = 19; + table[19 * 256 + 190] = 19; + table[18 * 256 + 191] = 19; + table[19 * 256 + 191] = 19; + table[18 * 256 + 192] = 19; + table[19 * 256 + 192] = 19; + table[18 * 256 + 193] = 19; + table[19 * 256 + 193] = 19; + table[18 * 256 + 194] = 19; + table[19 * 256 + 194] = 19; + table[18 * 256 + 195] = 19; + table[19 * 256 + 195] = 19; + table[18 * 256 + 196] = 19; + table[19 * 256 + 196] = 19; + table[18 * 256 + 197] = 19; + table[19 * 256 + 197] = 19; + table[18 * 256 + 198] = 19; + table[19 * 256 + 198] = 19; + table[18 * 256 + 199] = 19; + table[19 * 256 + 199] = 19; + table[18 * 256 + 200] = 19; + table[19 * 256 + 200] = 19; + table[18 * 256 + 201] = 19; + table[19 * 256 + 201] = 19; + table[18 * 256 + 202] = 19; + table[19 * 256 + 202] = 19; + table[18 * 256 + 203] = 19; + table[19 * 256 + 203] = 19; + table[18 * 256 + 204] = 19; + table[19 * 256 + 204] = 19; + table[18 * 256 + 205] = 19; + table[19 * 256 + 205] = 19; + table[18 * 256 + 206] = 19; + table[19 * 256 + 206] = 19; + table[18 * 256 + 207] = 19; + table[19 * 256 + 207] = 19; + table[18 * 256 + 208] = 19; + table[19 * 256 + 208] = 19; + table[18 * 256 + 209] = 19; + table[19 * 256 + 209] = 19; + table[18 * 256 + 210] = 19; + table[19 * 256 + 210] = 19; + table[18 * 256 + 211] = 19; + table[19 * 256 + 211] = 19; + table[18 * 256 + 212] = 19; + table[19 * 256 + 212] = 19; + table[18 * 256 + 213] = 19; + table[19 * 256 + 213] = 19; + table[18 * 256 + 214] = 19; + table[19 * 256 + 214] = 19; + table[18 * 256 + 215] = 19; + table[19 * 256 + 215] = 19; + table[18 * 256 + 216] = 19; + table[19 * 256 + 216] = 19; + table[18 * 256 + 217] = 19; + table[19 * 256 + 217] = 19; + table[18 * 256 + 218] = 19; + table[19 * 256 + 218] = 19; + table[18 * 256 + 219] = 19; + table[19 * 256 + 219] = 19; + table[18 * 256 + 220] = 19; + table[19 * 256 + 220] = 19; + table[18 * 256 + 221] = 19; + table[19 * 256 + 221] = 19; + table[18 * 256 + 222] = 19; + table[19 * 256 + 222] = 19; + table[18 * 256 + 223] = 19; + table[19 * 256 + 223] = 19; + table[18 * 256 + 224] = 19; + table[19 * 256 + 224] = 19; + table[18 * 256 + 225] = 19; + table[19 * 256 + 225] = 19; + table[18 * 256 + 226] = 19; + table[19 * 256 + 226] = 19; + table[18 * 256 + 227] = 19; + table[19 * 256 + 227] = 19; + table[18 * 256 + 228] = 19; + table[19 * 256 + 228] = 19; + table[18 * 256 + 229] = 19; + table[19 * 256 + 229] = 19; + table[18 * 256 + 230] = 19; + table[19 * 256 + 230] = 19; + table[18 * 256 + 231] = 19; + table[19 * 256 + 231] = 19; + table[18 * 256 + 232] = 19; + table[19 * 256 + 232] = 19; + table[18 * 256 + 233] = 19; + table[19 * 256 + 233] = 19; + table[18 * 256 + 234] = 19; + table[19 * 256 + 234] = 19; + table[18 * 256 + 235] = 19; + table[19 * 256 + 235] = 19; + table[18 * 256 + 236] = 19; + table[19 * 256 + 236] = 19; + table[18 * 256 + 237] = 19; + table[19 * 256 + 237] = 19; + table[18 * 256 + 238] = 19; + table[19 * 256 + 238] = 19; + table[18 * 256 + 239] = 19; + table[19 * 256 + 239] = 19; + table[18 * 256 + 240] = 19; + table[19 * 256 + 240] = 19; + table[18 * 256 + 241] = 19; + table[19 * 256 + 241] = 19; + table[18 * 256 + 242] = 19; + table[19 * 256 + 242] = 19; + table[18 * 256 + 243] = 19; + table[19 * 256 + 243] = 19; + table[18 * 256 + 244] = 19; + table[19 * 256 + 244] = 19; + table[18 * 256 + 245] = 19; + table[19 * 256 + 245] = 19; + table[18 * 256 + 246] = 19; + table[19 * 256 + 246] = 19; + table[18 * 256 + 247] = 19; + table[19 * 256 + 247] = 19; + table[18 * 256 + 248] = 19; + table[19 * 256 + 248] = 19; + table[18 * 256 + 249] = 19; + table[19 * 256 + 249] = 19; + table[18 * 256 + 250] = 19; + table[19 * 256 + 250] = 19; + table[18 * 256 + 251] = 19; + table[19 * 256 + 251] = 19; + table[18 * 256 + 252] = 19; + table[19 * 256 + 252] = 19; + table[18 * 256 + 253] = 19; + table[19 * 256 + 253] = 19; + table[18 * 256 + 254] = 19; + table[19 * 256 + 254] = 19; + table[0 * 256 + 13] = 1; + table[0 * 256 + 255] = 2; + table[1 * 256 + 10] = 2; + table[2 * 256 + 109] = 3; + table[3 * 256 + 101] = 4; + table[4 * 256 + 115] = 5; + table[5 * 256 + 115] = 6; + table[6 * 256 + 97] = 7; + table[7 * 256 + 103] = 8; + table[8 * 256 + 101] = 9; + table[9 * 256 + 45] = 10; + table[10 * 256 + 105] = 11; + table[11 * 256 + 100] = 12; + table[12 * 256 + 58] = 13; + table[13 * 256 + 60] = 14; + table[14 * 256 + 43] = 15; + table[14 * 256 + 45] = 15; + table[14 * 256 + 46] = 15; + table[14 * 256 + 48] = 15; + table[14 * 256 + 49] = 15; + table[14 * 256 + 50] = 15; + table[14 * 256 + 51] = 15; + table[14 * 256 + 52] = 15; + table[14 * 256 + 53] = 15; + table[14 * 256 + 54] = 15; + table[14 * 256 + 55] = 15; + table[14 * 256 + 56] = 15; + table[14 * 256 + 57] = 15; + table[14 * 256 + 61] = 15; + table[14 * 256 + 64] = 15; + table[14 * 256 + 65] = 15; + table[14 * 256 + 66] = 15; + table[14 * 256 + 67] = 15; + table[14 * 256 + 68] = 15; + table[14 * 256 + 69] = 15; + table[14 * 256 + 70] = 15; + table[14 * 256 + 71] = 15; + table[14 * 256 + 72] = 15; + table[14 * 256 + 73] = 15; + table[14 * 256 + 74] = 15; + table[14 * 256 + 75] = 15; + table[14 * 256 + 76] = 15; + table[14 * 256 + 77] = 15; + table[14 * 256 + 78] = 15; + table[14 * 256 + 79] = 15; + table[14 * 256 + 80] = 15; + table[14 * 256 + 81] = 15; + table[14 * 256 + 82] = 15; + table[14 * 256 + 83] = 15; + table[14 * 256 + 84] = 15; + table[14 * 256 + 85] = 15; + table[14 * 256 + 86] = 15; + table[14 * 256 + 87] = 15; + table[14 * 256 + 88] = 15; + table[14 * 256 + 89] = 15; + table[14 * 256 + 90] = 15; + table[14 * 256 + 95] = 15; + table[14 * 256 + 97] = 15; + table[14 * 256 + 98] = 15; + table[14 * 256 + 99] = 15; + table[14 * 256 + 100] = 15; + table[14 * 256 + 101] = 15; + table[14 * 256 + 102] = 15; + table[14 * 256 + 103] = 15; + table[14 * 256 + 104] = 15; + table[14 * 256 + 105] = 15; + table[14 * 256 + 106] = 15; + table[14 * 256 + 107] = 15; + table[14 * 256 + 108] = 15; + table[14 * 256 + 109] = 15; + table[14 * 256 + 110] = 15; + table[14 * 256 + 111] = 15; + table[14 * 256 + 112] = 15; + table[14 * 256 + 113] = 15; + table[14 * 256 + 114] = 15; + table[14 * 256 + 115] = 15; + table[14 * 256 + 116] = 15; + table[14 * 256 + 117] = 15; + table[14 * 256 + 118] = 15; + table[14 * 256 + 119] = 15; + table[14 * 256 + 120] = 15; + table[14 * 256 + 121] = 15; + table[14 * 256 + 122] = 15; + table[15 * 256 + 43] = 15; + table[15 * 256 + 45] = 15; + table[15 * 256 + 46] = 15; + table[15 * 256 + 48] = 15; + table[15 * 256 + 49] = 15; + table[15 * 256 + 50] = 15; + table[15 * 256 + 51] = 15; + table[15 * 256 + 52] = 15; + table[15 * 256 + 53] = 15; + table[15 * 256 + 54] = 15; + table[15 * 256 + 55] = 15; + table[15 * 256 + 56] = 15; + table[15 * 256 + 57] = 15; + table[15 * 256 + 61] = 15; + table[15 * 256 + 64] = 15; + table[15 * 256 + 65] = 15; + table[15 * 256 + 66] = 15; + table[15 * 256 + 67] = 15; + table[15 * 256 + 68] = 15; + table[15 * 256 + 69] = 15; + table[15 * 256 + 70] = 15; + table[15 * 256 + 71] = 15; + table[15 * 256 + 72] = 15; + table[15 * 256 + 73] = 15; + table[15 * 256 + 74] = 15; + table[15 * 256 + 75] = 15; + table[15 * 256 + 76] = 15; + table[15 * 256 + 77] = 15; + table[15 * 256 + 78] = 15; + table[15 * 256 + 79] = 15; + table[15 * 256 + 80] = 15; + table[15 * 256 + 81] = 15; + table[15 * 256 + 82] = 15; + table[15 * 256 + 83] = 15; + table[15 * 256 + 84] = 15; + table[15 * 256 + 85] = 15; + table[15 * 256 + 86] = 15; + table[15 * 256 + 87] = 15; + table[15 * 256 + 88] = 15; + table[15 * 256 + 89] = 15; + table[15 * 256 + 90] = 15; + table[15 * 256 + 95] = 15; + table[15 * 256 + 97] = 15; + table[15 * 256 + 98] = 15; + table[15 * 256 + 99] = 15; + table[15 * 256 + 100] = 15; + table[15 * 256 + 101] = 15; + table[15 * 256 + 102] = 15; + table[15 * 256 + 103] = 15; + table[15 * 256 + 104] = 15; + table[15 * 256 + 105] = 15; + table[15 * 256 + 106] = 15; + table[15 * 256 + 107] = 15; + table[15 * 256 + 108] = 15; + table[15 * 256 + 109] = 15; + table[15 * 256 + 110] = 15; + table[15 * 256 + 111] = 15; + table[15 * 256 + 112] = 15; + table[15 * 256 + 113] = 15; + table[15 * 256 + 114] = 15; + table[15 * 256 + 115] = 15; + table[15 * 256 + 116] = 15; + table[15 * 256 + 117] = 15; + table[15 * 256 + 118] = 15; + table[15 * 256 + 119] = 15; + table[15 * 256 + 120] = 15; + table[15 * 256 + 121] = 15; + table[15 * 256 + 122] = 15; + table[15 * 256 + 62] = 16; + table[16 * 256 + 13] = 17; + table[17 * 256 + 10] = 18; + + table +} +pub fn regex_match(input: [u8; N]) -> bool { + // regex: (\r\n|^)message-id:<[A-Za-z0-9=@\.\+_-]+>\r\n + let mut s = 0; + s = table[255]; + for i in 0..input.len() { + let s_idx = s * 256 + input[i] as Field; + std::as_witness(s_idx); + s = table[s_idx]; + } + + let matched: bool = (s == 18) | (s == 19); + + matched +} + + \ No newline at end of file diff --git a/packages/noir/src/basic/mod.nr b/packages/noir/src/basic/mod.nr new file mode 100644 index 00000000..08c90017 --- /dev/null +++ b/packages/noir/src/basic/mod.nr @@ -0,0 +1,9 @@ +pub mod body_hash; +pub mod email_addr; +pub mod email_domain; +pub mod from_all; +pub mod message_id; +pub mod reversed_bracket; +pub mod subject_all; +pub mod timestamp; +pub mod to_all; \ No newline at end of file diff --git a/packages/noir/src/basic/reversed_bracket.nr b/packages/noir/src/basic/reversed_bracket.nr new file mode 100644 index 00000000..b9245889 --- /dev/null +++ b/packages/noir/src/basic/reversed_bracket.nr @@ -0,0 +1,1711 @@ + +use crate::common::Sequence; + + +global table: [Field; 4864] = comptime { make_lookup_table() }; + +comptime fn make_lookup_table() -> [Field; 4864] { + let mut table = [0; 4864]; + table[10 * 256 + 0] = 18; + table[18 * 256 + 0] = 18; + table[10 * 256 + 1] = 18; + table[18 * 256 + 1] = 18; + table[10 * 256 + 2] = 18; + table[18 * 256 + 2] = 18; + table[10 * 256 + 3] = 18; + table[18 * 256 + 3] = 18; + table[10 * 256 + 4] = 18; + table[18 * 256 + 4] = 18; + table[10 * 256 + 5] = 18; + table[18 * 256 + 5] = 18; + table[10 * 256 + 6] = 18; + table[18 * 256 + 6] = 18; + table[10 * 256 + 7] = 18; + table[18 * 256 + 7] = 18; + table[10 * 256 + 8] = 18; + table[18 * 256 + 8] = 18; + table[10 * 256 + 9] = 18; + table[18 * 256 + 9] = 18; + table[10 * 256 + 10] = 18; + table[18 * 256 + 10] = 18; + table[10 * 256 + 11] = 18; + table[18 * 256 + 11] = 18; + table[10 * 256 + 12] = 18; + table[18 * 256 + 12] = 18; + table[10 * 256 + 13] = 18; + table[18 * 256 + 13] = 18; + table[10 * 256 + 14] = 18; + table[18 * 256 + 14] = 18; + table[10 * 256 + 15] = 18; + table[18 * 256 + 15] = 18; + table[10 * 256 + 16] = 18; + table[18 * 256 + 16] = 18; + table[10 * 256 + 17] = 18; + table[18 * 256 + 17] = 18; + table[10 * 256 + 18] = 18; + table[18 * 256 + 18] = 18; + table[10 * 256 + 19] = 18; + table[18 * 256 + 19] = 18; + table[10 * 256 + 20] = 18; + table[18 * 256 + 20] = 18; + table[10 * 256 + 21] = 18; + table[18 * 256 + 21] = 18; + table[10 * 256 + 22] = 18; + table[18 * 256 + 22] = 18; + table[10 * 256 + 23] = 18; + table[18 * 256 + 23] = 18; + table[10 * 256 + 24] = 18; + table[18 * 256 + 24] = 18; + table[10 * 256 + 25] = 18; + table[18 * 256 + 25] = 18; + table[10 * 256 + 26] = 18; + table[18 * 256 + 26] = 18; + table[10 * 256 + 27] = 18; + table[18 * 256 + 27] = 18; + table[10 * 256 + 28] = 18; + table[18 * 256 + 28] = 18; + table[10 * 256 + 29] = 18; + table[18 * 256 + 29] = 18; + table[10 * 256 + 30] = 18; + table[18 * 256 + 30] = 18; + table[10 * 256 + 31] = 18; + table[18 * 256 + 31] = 18; + table[10 * 256 + 32] = 18; + table[18 * 256 + 32] = 18; + table[10 * 256 + 33] = 18; + table[18 * 256 + 33] = 18; + table[10 * 256 + 34] = 18; + table[18 * 256 + 34] = 18; + table[10 * 256 + 35] = 18; + table[18 * 256 + 35] = 18; + table[10 * 256 + 36] = 18; + table[18 * 256 + 36] = 18; + table[10 * 256 + 37] = 18; + table[18 * 256 + 37] = 18; + table[10 * 256 + 38] = 18; + table[18 * 256 + 38] = 18; + table[10 * 256 + 39] = 18; + table[18 * 256 + 39] = 18; + table[10 * 256 + 40] = 18; + table[18 * 256 + 40] = 18; + table[10 * 256 + 41] = 18; + table[18 * 256 + 41] = 18; + table[10 * 256 + 42] = 18; + table[18 * 256 + 42] = 18; + table[10 * 256 + 43] = 18; + table[18 * 256 + 43] = 18; + table[10 * 256 + 44] = 18; + table[18 * 256 + 44] = 18; + table[10 * 256 + 45] = 18; + table[18 * 256 + 45] = 18; + table[10 * 256 + 46] = 18; + table[18 * 256 + 46] = 18; + table[10 * 256 + 47] = 18; + table[18 * 256 + 47] = 18; + table[10 * 256 + 48] = 18; + table[18 * 256 + 48] = 18; + table[10 * 256 + 49] = 18; + table[18 * 256 + 49] = 18; + table[10 * 256 + 50] = 18; + table[18 * 256 + 50] = 18; + table[10 * 256 + 51] = 18; + table[18 * 256 + 51] = 18; + table[10 * 256 + 52] = 18; + table[18 * 256 + 52] = 18; + table[10 * 256 + 53] = 18; + table[18 * 256 + 53] = 18; + table[10 * 256 + 54] = 18; + table[18 * 256 + 54] = 18; + table[10 * 256 + 55] = 18; + table[18 * 256 + 55] = 18; + table[10 * 256 + 56] = 18; + table[18 * 256 + 56] = 18; + table[10 * 256 + 57] = 18; + table[18 * 256 + 57] = 18; + table[10 * 256 + 58] = 18; + table[18 * 256 + 58] = 18; + table[10 * 256 + 59] = 18; + table[18 * 256 + 59] = 18; + table[10 * 256 + 60] = 18; + table[18 * 256 + 60] = 18; + table[10 * 256 + 61] = 18; + table[18 * 256 + 61] = 18; + table[10 * 256 + 62] = 18; + table[18 * 256 + 62] = 18; + table[10 * 256 + 63] = 18; + table[18 * 256 + 63] = 18; + table[10 * 256 + 64] = 18; + table[18 * 256 + 64] = 18; + table[10 * 256 + 65] = 18; + table[18 * 256 + 65] = 18; + table[10 * 256 + 66] = 18; + table[18 * 256 + 66] = 18; + table[10 * 256 + 67] = 18; + table[18 * 256 + 67] = 18; + table[10 * 256 + 68] = 18; + table[18 * 256 + 68] = 18; + table[10 * 256 + 69] = 18; + table[18 * 256 + 69] = 18; + table[10 * 256 + 70] = 18; + table[18 * 256 + 70] = 18; + table[10 * 256 + 71] = 18; + table[18 * 256 + 71] = 18; + table[10 * 256 + 72] = 18; + table[18 * 256 + 72] = 18; + table[10 * 256 + 73] = 18; + table[18 * 256 + 73] = 18; + table[10 * 256 + 74] = 18; + table[18 * 256 + 74] = 18; + table[10 * 256 + 75] = 18; + table[18 * 256 + 75] = 18; + table[10 * 256 + 76] = 18; + table[18 * 256 + 76] = 18; + table[10 * 256 + 77] = 18; + table[18 * 256 + 77] = 18; + table[10 * 256 + 78] = 18; + table[18 * 256 + 78] = 18; + table[10 * 256 + 79] = 18; + table[18 * 256 + 79] = 18; + table[10 * 256 + 80] = 18; + table[18 * 256 + 80] = 18; + table[10 * 256 + 81] = 18; + table[18 * 256 + 81] = 18; + table[10 * 256 + 82] = 18; + table[18 * 256 + 82] = 18; + table[10 * 256 + 83] = 18; + table[18 * 256 + 83] = 18; + table[10 * 256 + 84] = 18; + table[18 * 256 + 84] = 18; + table[10 * 256 + 85] = 18; + table[18 * 256 + 85] = 18; + table[10 * 256 + 86] = 18; + table[18 * 256 + 86] = 18; + table[10 * 256 + 87] = 18; + table[18 * 256 + 87] = 18; + table[10 * 256 + 88] = 18; + table[18 * 256 + 88] = 18; + table[10 * 256 + 89] = 18; + table[18 * 256 + 89] = 18; + table[10 * 256 + 90] = 18; + table[18 * 256 + 90] = 18; + table[10 * 256 + 91] = 18; + table[18 * 256 + 91] = 18; + table[10 * 256 + 92] = 18; + table[18 * 256 + 92] = 18; + table[10 * 256 + 93] = 18; + table[18 * 256 + 93] = 18; + table[10 * 256 + 94] = 18; + table[18 * 256 + 94] = 18; + table[10 * 256 + 95] = 18; + table[18 * 256 + 95] = 18; + table[10 * 256 + 96] = 18; + table[18 * 256 + 96] = 18; + table[10 * 256 + 97] = 18; + table[18 * 256 + 97] = 18; + table[10 * 256 + 98] = 18; + table[18 * 256 + 98] = 18; + table[10 * 256 + 99] = 18; + table[18 * 256 + 99] = 18; + table[10 * 256 + 100] = 18; + table[18 * 256 + 100] = 18; + table[10 * 256 + 101] = 18; + table[18 * 256 + 101] = 18; + table[10 * 256 + 102] = 18; + table[18 * 256 + 102] = 18; + table[10 * 256 + 103] = 18; + table[18 * 256 + 103] = 18; + table[10 * 256 + 104] = 18; + table[18 * 256 + 104] = 18; + table[10 * 256 + 105] = 18; + table[18 * 256 + 105] = 18; + table[10 * 256 + 106] = 18; + table[18 * 256 + 106] = 18; + table[10 * 256 + 107] = 18; + table[18 * 256 + 107] = 18; + table[10 * 256 + 108] = 18; + table[18 * 256 + 108] = 18; + table[10 * 256 + 109] = 18; + table[18 * 256 + 109] = 18; + table[10 * 256 + 110] = 18; + table[18 * 256 + 110] = 18; + table[10 * 256 + 111] = 18; + table[18 * 256 + 111] = 18; + table[10 * 256 + 112] = 18; + table[18 * 256 + 112] = 18; + table[10 * 256 + 113] = 18; + table[18 * 256 + 113] = 18; + table[10 * 256 + 114] = 18; + table[18 * 256 + 114] = 18; + table[10 * 256 + 115] = 18; + table[18 * 256 + 115] = 18; + table[10 * 256 + 116] = 18; + table[18 * 256 + 116] = 18; + table[10 * 256 + 117] = 18; + table[18 * 256 + 117] = 18; + table[10 * 256 + 118] = 18; + table[18 * 256 + 118] = 18; + table[10 * 256 + 119] = 18; + table[18 * 256 + 119] = 18; + table[10 * 256 + 120] = 18; + table[18 * 256 + 120] = 18; + table[10 * 256 + 121] = 18; + table[18 * 256 + 121] = 18; + table[10 * 256 + 122] = 18; + table[18 * 256 + 122] = 18; + table[10 * 256 + 123] = 18; + table[18 * 256 + 123] = 18; + table[10 * 256 + 124] = 18; + table[18 * 256 + 124] = 18; + table[10 * 256 + 125] = 18; + table[18 * 256 + 125] = 18; + table[10 * 256 + 126] = 18; + table[18 * 256 + 126] = 18; + table[10 * 256 + 127] = 18; + table[18 * 256 + 127] = 18; + table[10 * 256 + 128] = 18; + table[18 * 256 + 128] = 18; + table[10 * 256 + 129] = 18; + table[18 * 256 + 129] = 18; + table[10 * 256 + 130] = 18; + table[18 * 256 + 130] = 18; + table[10 * 256 + 131] = 18; + table[18 * 256 + 131] = 18; + table[10 * 256 + 132] = 18; + table[18 * 256 + 132] = 18; + table[10 * 256 + 133] = 18; + table[18 * 256 + 133] = 18; + table[10 * 256 + 134] = 18; + table[18 * 256 + 134] = 18; + table[10 * 256 + 135] = 18; + table[18 * 256 + 135] = 18; + table[10 * 256 + 136] = 18; + table[18 * 256 + 136] = 18; + table[10 * 256 + 137] = 18; + table[18 * 256 + 137] = 18; + table[10 * 256 + 138] = 18; + table[18 * 256 + 138] = 18; + table[10 * 256 + 139] = 18; + table[18 * 256 + 139] = 18; + table[10 * 256 + 140] = 18; + table[18 * 256 + 140] = 18; + table[10 * 256 + 141] = 18; + table[18 * 256 + 141] = 18; + table[10 * 256 + 142] = 18; + table[18 * 256 + 142] = 18; + table[10 * 256 + 143] = 18; + table[18 * 256 + 143] = 18; + table[10 * 256 + 144] = 18; + table[18 * 256 + 144] = 18; + table[10 * 256 + 145] = 18; + table[18 * 256 + 145] = 18; + table[10 * 256 + 146] = 18; + table[18 * 256 + 146] = 18; + table[10 * 256 + 147] = 18; + table[18 * 256 + 147] = 18; + table[10 * 256 + 148] = 18; + table[18 * 256 + 148] = 18; + table[10 * 256 + 149] = 18; + table[18 * 256 + 149] = 18; + table[10 * 256 + 150] = 18; + table[18 * 256 + 150] = 18; + table[10 * 256 + 151] = 18; + table[18 * 256 + 151] = 18; + table[10 * 256 + 152] = 18; + table[18 * 256 + 152] = 18; + table[10 * 256 + 153] = 18; + table[18 * 256 + 153] = 18; + table[10 * 256 + 154] = 18; + table[18 * 256 + 154] = 18; + table[10 * 256 + 155] = 18; + table[18 * 256 + 155] = 18; + table[10 * 256 + 156] = 18; + table[18 * 256 + 156] = 18; + table[10 * 256 + 157] = 18; + table[18 * 256 + 157] = 18; + table[10 * 256 + 158] = 18; + table[18 * 256 + 158] = 18; + table[10 * 256 + 159] = 18; + table[18 * 256 + 159] = 18; + table[10 * 256 + 160] = 18; + table[18 * 256 + 160] = 18; + table[10 * 256 + 161] = 18; + table[18 * 256 + 161] = 18; + table[10 * 256 + 162] = 18; + table[18 * 256 + 162] = 18; + table[10 * 256 + 163] = 18; + table[18 * 256 + 163] = 18; + table[10 * 256 + 164] = 18; + table[18 * 256 + 164] = 18; + table[10 * 256 + 165] = 18; + table[18 * 256 + 165] = 18; + table[10 * 256 + 166] = 18; + table[18 * 256 + 166] = 18; + table[10 * 256 + 167] = 18; + table[18 * 256 + 167] = 18; + table[10 * 256 + 168] = 18; + table[18 * 256 + 168] = 18; + table[10 * 256 + 169] = 18; + table[18 * 256 + 169] = 18; + table[10 * 256 + 170] = 18; + table[18 * 256 + 170] = 18; + table[10 * 256 + 171] = 18; + table[18 * 256 + 171] = 18; + table[10 * 256 + 172] = 18; + table[18 * 256 + 172] = 18; + table[10 * 256 + 173] = 18; + table[18 * 256 + 173] = 18; + table[10 * 256 + 174] = 18; + table[18 * 256 + 174] = 18; + table[10 * 256 + 175] = 18; + table[18 * 256 + 175] = 18; + table[10 * 256 + 176] = 18; + table[18 * 256 + 176] = 18; + table[10 * 256 + 177] = 18; + table[18 * 256 + 177] = 18; + table[10 * 256 + 178] = 18; + table[18 * 256 + 178] = 18; + table[10 * 256 + 179] = 18; + table[18 * 256 + 179] = 18; + table[10 * 256 + 180] = 18; + table[18 * 256 + 180] = 18; + table[10 * 256 + 181] = 18; + table[18 * 256 + 181] = 18; + table[10 * 256 + 182] = 18; + table[18 * 256 + 182] = 18; + table[10 * 256 + 183] = 18; + table[18 * 256 + 183] = 18; + table[10 * 256 + 184] = 18; + table[18 * 256 + 184] = 18; + table[10 * 256 + 185] = 18; + table[18 * 256 + 185] = 18; + table[10 * 256 + 186] = 18; + table[18 * 256 + 186] = 18; + table[10 * 256 + 187] = 18; + table[18 * 256 + 187] = 18; + table[10 * 256 + 188] = 18; + table[18 * 256 + 188] = 18; + table[10 * 256 + 189] = 18; + table[18 * 256 + 189] = 18; + table[10 * 256 + 190] = 18; + table[18 * 256 + 190] = 18; + table[10 * 256 + 191] = 18; + table[18 * 256 + 191] = 18; + table[10 * 256 + 192] = 18; + table[18 * 256 + 192] = 18; + table[10 * 256 + 193] = 18; + table[18 * 256 + 193] = 18; + table[10 * 256 + 194] = 18; + table[18 * 256 + 194] = 18; + table[10 * 256 + 195] = 18; + table[18 * 256 + 195] = 18; + table[10 * 256 + 196] = 18; + table[18 * 256 + 196] = 18; + table[10 * 256 + 197] = 18; + table[18 * 256 + 197] = 18; + table[10 * 256 + 198] = 18; + table[18 * 256 + 198] = 18; + table[10 * 256 + 199] = 18; + table[18 * 256 + 199] = 18; + table[10 * 256 + 200] = 18; + table[18 * 256 + 200] = 18; + table[10 * 256 + 201] = 18; + table[18 * 256 + 201] = 18; + table[10 * 256 + 202] = 18; + table[18 * 256 + 202] = 18; + table[10 * 256 + 203] = 18; + table[18 * 256 + 203] = 18; + table[10 * 256 + 204] = 18; + table[18 * 256 + 204] = 18; + table[10 * 256 + 205] = 18; + table[18 * 256 + 205] = 18; + table[10 * 256 + 206] = 18; + table[18 * 256 + 206] = 18; + table[10 * 256 + 207] = 18; + table[18 * 256 + 207] = 18; + table[10 * 256 + 208] = 18; + table[18 * 256 + 208] = 18; + table[10 * 256 + 209] = 18; + table[18 * 256 + 209] = 18; + table[10 * 256 + 210] = 18; + table[18 * 256 + 210] = 18; + table[10 * 256 + 211] = 18; + table[18 * 256 + 211] = 18; + table[10 * 256 + 212] = 18; + table[18 * 256 + 212] = 18; + table[10 * 256 + 213] = 18; + table[18 * 256 + 213] = 18; + table[10 * 256 + 214] = 18; + table[18 * 256 + 214] = 18; + table[10 * 256 + 215] = 18; + table[18 * 256 + 215] = 18; + table[10 * 256 + 216] = 18; + table[18 * 256 + 216] = 18; + table[10 * 256 + 217] = 18; + table[18 * 256 + 217] = 18; + table[10 * 256 + 218] = 18; + table[18 * 256 + 218] = 18; + table[10 * 256 + 219] = 18; + table[18 * 256 + 219] = 18; + table[10 * 256 + 220] = 18; + table[18 * 256 + 220] = 18; + table[10 * 256 + 221] = 18; + table[18 * 256 + 221] = 18; + table[10 * 256 + 222] = 18; + table[18 * 256 + 222] = 18; + table[10 * 256 + 223] = 18; + table[18 * 256 + 223] = 18; + table[10 * 256 + 224] = 18; + table[18 * 256 + 224] = 18; + table[10 * 256 + 225] = 18; + table[18 * 256 + 225] = 18; + table[10 * 256 + 226] = 18; + table[18 * 256 + 226] = 18; + table[10 * 256 + 227] = 18; + table[18 * 256 + 227] = 18; + table[10 * 256 + 228] = 18; + table[18 * 256 + 228] = 18; + table[10 * 256 + 229] = 18; + table[18 * 256 + 229] = 18; + table[10 * 256 + 230] = 18; + table[18 * 256 + 230] = 18; + table[10 * 256 + 231] = 18; + table[18 * 256 + 231] = 18; + table[10 * 256 + 232] = 18; + table[18 * 256 + 232] = 18; + table[10 * 256 + 233] = 18; + table[18 * 256 + 233] = 18; + table[10 * 256 + 234] = 18; + table[18 * 256 + 234] = 18; + table[10 * 256 + 235] = 18; + table[18 * 256 + 235] = 18; + table[10 * 256 + 236] = 18; + table[18 * 256 + 236] = 18; + table[10 * 256 + 237] = 18; + table[18 * 256 + 237] = 18; + table[10 * 256 + 238] = 18; + table[18 * 256 + 238] = 18; + table[10 * 256 + 239] = 18; + table[18 * 256 + 239] = 18; + table[10 * 256 + 240] = 18; + table[18 * 256 + 240] = 18; + table[10 * 256 + 241] = 18; + table[18 * 256 + 241] = 18; + table[10 * 256 + 242] = 18; + table[18 * 256 + 242] = 18; + table[10 * 256 + 243] = 18; + table[18 * 256 + 243] = 18; + table[10 * 256 + 244] = 18; + table[18 * 256 + 244] = 18; + table[10 * 256 + 245] = 18; + table[18 * 256 + 245] = 18; + table[10 * 256 + 246] = 18; + table[18 * 256 + 246] = 18; + table[10 * 256 + 247] = 18; + table[18 * 256 + 247] = 18; + table[10 * 256 + 248] = 18; + table[18 * 256 + 248] = 18; + table[10 * 256 + 249] = 18; + table[18 * 256 + 249] = 18; + table[10 * 256 + 250] = 18; + table[18 * 256 + 250] = 18; + table[10 * 256 + 251] = 18; + table[18 * 256 + 251] = 18; + table[10 * 256 + 252] = 18; + table[18 * 256 + 252] = 18; + table[10 * 256 + 253] = 18; + table[18 * 256 + 253] = 18; + table[10 * 256 + 254] = 18; + table[18 * 256 + 254] = 18; + table[0 * 256 + 62] = 1; + table[1 * 256 + 0] = 2; + table[1 * 256 + 1] = 2; + table[1 * 256 + 2] = 2; + table[1 * 256 + 3] = 2; + table[1 * 256 + 4] = 2; + table[1 * 256 + 5] = 2; + table[1 * 256 + 6] = 2; + table[1 * 256 + 7] = 2; + table[1 * 256 + 8] = 2; + table[1 * 256 + 9] = 2; + table[1 * 256 + 10] = 2; + table[1 * 256 + 11] = 2; + table[1 * 256 + 12] = 2; + table[1 * 256 + 13] = 2; + table[1 * 256 + 14] = 2; + table[1 * 256 + 15] = 2; + table[1 * 256 + 16] = 2; + table[1 * 256 + 17] = 2; + table[1 * 256 + 18] = 2; + table[1 * 256 + 19] = 2; + table[1 * 256 + 20] = 2; + table[1 * 256 + 21] = 2; + table[1 * 256 + 22] = 2; + table[1 * 256 + 23] = 2; + table[1 * 256 + 24] = 2; + table[1 * 256 + 25] = 2; + table[1 * 256 + 26] = 2; + table[1 * 256 + 27] = 2; + table[1 * 256 + 28] = 2; + table[1 * 256 + 29] = 2; + table[1 * 256 + 30] = 2; + table[1 * 256 + 31] = 2; + table[1 * 256 + 32] = 2; + table[1 * 256 + 33] = 2; + table[1 * 256 + 34] = 2; + table[1 * 256 + 35] = 2; + table[1 * 256 + 36] = 2; + table[1 * 256 + 37] = 2; + table[1 * 256 + 38] = 2; + table[1 * 256 + 39] = 2; + table[1 * 256 + 40] = 2; + table[1 * 256 + 41] = 2; + table[1 * 256 + 42] = 2; + table[1 * 256 + 43] = 2; + table[1 * 256 + 44] = 2; + table[1 * 256 + 45] = 2; + table[1 * 256 + 46] = 2; + table[1 * 256 + 47] = 2; + table[1 * 256 + 48] = 2; + table[1 * 256 + 49] = 2; + table[1 * 256 + 50] = 2; + table[1 * 256 + 51] = 2; + table[1 * 256 + 52] = 2; + table[1 * 256 + 53] = 2; + table[1 * 256 + 54] = 2; + table[1 * 256 + 55] = 2; + table[1 * 256 + 56] = 2; + table[1 * 256 + 57] = 2; + table[1 * 256 + 58] = 2; + table[1 * 256 + 59] = 2; + table[1 * 256 + 61] = 2; + table[1 * 256 + 63] = 2; + table[1 * 256 + 64] = 2; + table[1 * 256 + 65] = 2; + table[1 * 256 + 66] = 2; + table[1 * 256 + 67] = 2; + table[1 * 256 + 68] = 2; + table[1 * 256 + 69] = 2; + table[1 * 256 + 70] = 2; + table[1 * 256 + 71] = 2; + table[1 * 256 + 72] = 2; + table[1 * 256 + 73] = 2; + table[1 * 256 + 74] = 2; + table[1 * 256 + 75] = 2; + table[1 * 256 + 76] = 2; + table[1 * 256 + 77] = 2; + table[1 * 256 + 78] = 2; + table[1 * 256 + 79] = 2; + table[1 * 256 + 80] = 2; + table[1 * 256 + 81] = 2; + table[1 * 256 + 82] = 2; + table[1 * 256 + 83] = 2; + table[1 * 256 + 84] = 2; + table[1 * 256 + 85] = 2; + table[1 * 256 + 86] = 2; + table[1 * 256 + 87] = 2; + table[1 * 256 + 88] = 2; + table[1 * 256 + 89] = 2; + table[1 * 256 + 90] = 2; + table[1 * 256 + 91] = 2; + table[1 * 256 + 92] = 2; + table[1 * 256 + 93] = 2; + table[1 * 256 + 94] = 2; + table[1 * 256 + 95] = 2; + table[1 * 256 + 96] = 2; + table[1 * 256 + 97] = 2; + table[1 * 256 + 98] = 2; + table[1 * 256 + 99] = 2; + table[1 * 256 + 100] = 2; + table[1 * 256 + 101] = 2; + table[1 * 256 + 102] = 2; + table[1 * 256 + 103] = 2; + table[1 * 256 + 104] = 2; + table[1 * 256 + 105] = 2; + table[1 * 256 + 106] = 2; + table[1 * 256 + 107] = 2; + table[1 * 256 + 108] = 2; + table[1 * 256 + 109] = 2; + table[1 * 256 + 110] = 2; + table[1 * 256 + 111] = 2; + table[1 * 256 + 112] = 2; + table[1 * 256 + 113] = 2; + table[1 * 256 + 114] = 2; + table[1 * 256 + 115] = 2; + table[1 * 256 + 116] = 2; + table[1 * 256 + 117] = 2; + table[1 * 256 + 118] = 2; + table[1 * 256 + 119] = 2; + table[1 * 256 + 120] = 2; + table[1 * 256 + 121] = 2; + table[1 * 256 + 122] = 2; + table[1 * 256 + 123] = 2; + table[1 * 256 + 124] = 2; + table[1 * 256 + 125] = 2; + table[1 * 256 + 126] = 2; + table[1 * 256 + 127] = 2; + table[1 * 256 + 194] = 3; + table[1 * 256 + 195] = 3; + table[1 * 256 + 196] = 3; + table[1 * 256 + 197] = 3; + table[1 * 256 + 198] = 3; + table[1 * 256 + 199] = 3; + table[1 * 256 + 200] = 3; + table[1 * 256 + 201] = 3; + table[1 * 256 + 202] = 3; + table[1 * 256 + 203] = 3; + table[1 * 256 + 204] = 3; + table[1 * 256 + 205] = 3; + table[1 * 256 + 206] = 3; + table[1 * 256 + 207] = 3; + table[1 * 256 + 208] = 3; + table[1 * 256 + 209] = 3; + table[1 * 256 + 210] = 3; + table[1 * 256 + 211] = 3; + table[1 * 256 + 212] = 3; + table[1 * 256 + 213] = 3; + table[1 * 256 + 214] = 3; + table[1 * 256 + 215] = 3; + table[1 * 256 + 216] = 3; + table[1 * 256 + 217] = 3; + table[1 * 256 + 218] = 3; + table[1 * 256 + 219] = 3; + table[1 * 256 + 220] = 3; + table[1 * 256 + 221] = 3; + table[1 * 256 + 222] = 3; + table[1 * 256 + 223] = 3; + table[1 * 256 + 224] = 4; + table[1 * 256 + 225] = 5; + table[1 * 256 + 226] = 5; + table[1 * 256 + 227] = 5; + table[1 * 256 + 228] = 5; + table[1 * 256 + 229] = 5; + table[1 * 256 + 230] = 5; + table[1 * 256 + 231] = 5; + table[1 * 256 + 232] = 5; + table[1 * 256 + 233] = 5; + table[1 * 256 + 234] = 5; + table[1 * 256 + 235] = 5; + table[1 * 256 + 236] = 5; + table[1 * 256 + 238] = 5; + table[1 * 256 + 239] = 5; + table[1 * 256 + 237] = 6; + table[1 * 256 + 240] = 7; + table[1 * 256 + 241] = 8; + table[1 * 256 + 242] = 8; + table[1 * 256 + 243] = 8; + table[1 * 256 + 244] = 9; + table[2 * 256 + 0] = 2; + table[2 * 256 + 1] = 2; + table[2 * 256 + 2] = 2; + table[2 * 256 + 3] = 2; + table[2 * 256 + 4] = 2; + table[2 * 256 + 5] = 2; + table[2 * 256 + 6] = 2; + table[2 * 256 + 7] = 2; + table[2 * 256 + 8] = 2; + table[2 * 256 + 9] = 2; + table[2 * 256 + 10] = 2; + table[2 * 256 + 11] = 2; + table[2 * 256 + 12] = 2; + table[2 * 256 + 13] = 2; + table[2 * 256 + 14] = 2; + table[2 * 256 + 15] = 2; + table[2 * 256 + 16] = 2; + table[2 * 256 + 17] = 2; + table[2 * 256 + 18] = 2; + table[2 * 256 + 19] = 2; + table[2 * 256 + 20] = 2; + table[2 * 256 + 21] = 2; + table[2 * 256 + 22] = 2; + table[2 * 256 + 23] = 2; + table[2 * 256 + 24] = 2; + table[2 * 256 + 25] = 2; + table[2 * 256 + 26] = 2; + table[2 * 256 + 27] = 2; + table[2 * 256 + 28] = 2; + table[2 * 256 + 29] = 2; + table[2 * 256 + 30] = 2; + table[2 * 256 + 31] = 2; + table[2 * 256 + 32] = 2; + table[2 * 256 + 33] = 2; + table[2 * 256 + 34] = 2; + table[2 * 256 + 35] = 2; + table[2 * 256 + 36] = 2; + table[2 * 256 + 37] = 2; + table[2 * 256 + 38] = 2; + table[2 * 256 + 39] = 2; + table[2 * 256 + 40] = 2; + table[2 * 256 + 41] = 2; + table[2 * 256 + 42] = 2; + table[2 * 256 + 43] = 2; + table[2 * 256 + 44] = 2; + table[2 * 256 + 45] = 2; + table[2 * 256 + 46] = 2; + table[2 * 256 + 47] = 2; + table[2 * 256 + 48] = 2; + table[2 * 256 + 49] = 2; + table[2 * 256 + 50] = 2; + table[2 * 256 + 51] = 2; + table[2 * 256 + 52] = 2; + table[2 * 256 + 53] = 2; + table[2 * 256 + 54] = 2; + table[2 * 256 + 55] = 2; + table[2 * 256 + 56] = 2; + table[2 * 256 + 57] = 2; + table[2 * 256 + 58] = 2; + table[2 * 256 + 59] = 2; + table[2 * 256 + 61] = 2; + table[2 * 256 + 63] = 2; + table[2 * 256 + 64] = 2; + table[2 * 256 + 65] = 2; + table[2 * 256 + 66] = 2; + table[2 * 256 + 67] = 2; + table[2 * 256 + 68] = 2; + table[2 * 256 + 69] = 2; + table[2 * 256 + 70] = 2; + table[2 * 256 + 71] = 2; + table[2 * 256 + 72] = 2; + table[2 * 256 + 73] = 2; + table[2 * 256 + 74] = 2; + table[2 * 256 + 75] = 2; + table[2 * 256 + 76] = 2; + table[2 * 256 + 77] = 2; + table[2 * 256 + 78] = 2; + table[2 * 256 + 79] = 2; + table[2 * 256 + 80] = 2; + table[2 * 256 + 81] = 2; + table[2 * 256 + 82] = 2; + table[2 * 256 + 83] = 2; + table[2 * 256 + 84] = 2; + table[2 * 256 + 85] = 2; + table[2 * 256 + 86] = 2; + table[2 * 256 + 87] = 2; + table[2 * 256 + 88] = 2; + table[2 * 256 + 89] = 2; + table[2 * 256 + 90] = 2; + table[2 * 256 + 91] = 2; + table[2 * 256 + 92] = 2; + table[2 * 256 + 93] = 2; + table[2 * 256 + 94] = 2; + table[2 * 256 + 95] = 2; + table[2 * 256 + 96] = 2; + table[2 * 256 + 97] = 2; + table[2 * 256 + 98] = 2; + table[2 * 256 + 99] = 2; + table[2 * 256 + 100] = 2; + table[2 * 256 + 101] = 2; + table[2 * 256 + 102] = 2; + table[2 * 256 + 103] = 2; + table[2 * 256 + 104] = 2; + table[2 * 256 + 105] = 2; + table[2 * 256 + 106] = 2; + table[2 * 256 + 107] = 2; + table[2 * 256 + 108] = 2; + table[2 * 256 + 109] = 2; + table[2 * 256 + 110] = 2; + table[2 * 256 + 111] = 2; + table[2 * 256 + 112] = 2; + table[2 * 256 + 113] = 2; + table[2 * 256 + 114] = 2; + table[2 * 256 + 115] = 2; + table[2 * 256 + 116] = 2; + table[2 * 256 + 117] = 2; + table[2 * 256 + 118] = 2; + table[2 * 256 + 119] = 2; + table[2 * 256 + 120] = 2; + table[2 * 256 + 121] = 2; + table[2 * 256 + 122] = 2; + table[2 * 256 + 123] = 2; + table[2 * 256 + 124] = 2; + table[2 * 256 + 125] = 2; + table[2 * 256 + 126] = 2; + table[2 * 256 + 127] = 2; + table[2 * 256 + 194] = 3; + table[2 * 256 + 195] = 3; + table[2 * 256 + 196] = 3; + table[2 * 256 + 197] = 3; + table[2 * 256 + 198] = 3; + table[2 * 256 + 199] = 3; + table[2 * 256 + 200] = 3; + table[2 * 256 + 201] = 3; + table[2 * 256 + 202] = 3; + table[2 * 256 + 203] = 3; + table[2 * 256 + 204] = 3; + table[2 * 256 + 205] = 3; + table[2 * 256 + 206] = 3; + table[2 * 256 + 207] = 3; + table[2 * 256 + 208] = 3; + table[2 * 256 + 209] = 3; + table[2 * 256 + 210] = 3; + table[2 * 256 + 211] = 3; + table[2 * 256 + 212] = 3; + table[2 * 256 + 213] = 3; + table[2 * 256 + 214] = 3; + table[2 * 256 + 215] = 3; + table[2 * 256 + 216] = 3; + table[2 * 256 + 217] = 3; + table[2 * 256 + 218] = 3; + table[2 * 256 + 219] = 3; + table[2 * 256 + 220] = 3; + table[2 * 256 + 221] = 3; + table[2 * 256 + 222] = 3; + table[2 * 256 + 223] = 3; + table[2 * 256 + 224] = 4; + table[2 * 256 + 225] = 5; + table[2 * 256 + 226] = 5; + table[2 * 256 + 227] = 5; + table[2 * 256 + 228] = 5; + table[2 * 256 + 229] = 5; + table[2 * 256 + 230] = 5; + table[2 * 256 + 231] = 5; + table[2 * 256 + 232] = 5; + table[2 * 256 + 233] = 5; + table[2 * 256 + 234] = 5; + table[2 * 256 + 235] = 5; + table[2 * 256 + 236] = 5; + table[2 * 256 + 238] = 5; + table[2 * 256 + 239] = 5; + table[2 * 256 + 237] = 6; + table[2 * 256 + 240] = 7; + table[2 * 256 + 241] = 8; + table[2 * 256 + 242] = 8; + table[2 * 256 + 243] = 8; + table[2 * 256 + 244] = 9; + table[2 * 256 + 60] = 10; + table[3 * 256 + 128] = 2; + table[3 * 256 + 129] = 2; + table[3 * 256 + 130] = 2; + table[3 * 256 + 131] = 2; + table[3 * 256 + 132] = 2; + table[3 * 256 + 133] = 2; + table[3 * 256 + 134] = 2; + table[3 * 256 + 135] = 2; + table[3 * 256 + 136] = 2; + table[3 * 256 + 137] = 2; + table[3 * 256 + 138] = 2; + table[3 * 256 + 139] = 2; + table[3 * 256 + 140] = 2; + table[3 * 256 + 141] = 2; + table[3 * 256 + 142] = 2; + table[3 * 256 + 143] = 2; + table[3 * 256 + 144] = 2; + table[3 * 256 + 145] = 2; + table[3 * 256 + 146] = 2; + table[3 * 256 + 147] = 2; + table[3 * 256 + 148] = 2; + table[3 * 256 + 149] = 2; + table[3 * 256 + 150] = 2; + table[3 * 256 + 151] = 2; + table[3 * 256 + 152] = 2; + table[3 * 256 + 153] = 2; + table[3 * 256 + 154] = 2; + table[3 * 256 + 155] = 2; + table[3 * 256 + 156] = 2; + table[3 * 256 + 157] = 2; + table[3 * 256 + 158] = 2; + table[3 * 256 + 159] = 2; + table[3 * 256 + 160] = 2; + table[3 * 256 + 161] = 2; + table[3 * 256 + 162] = 2; + table[3 * 256 + 163] = 2; + table[3 * 256 + 164] = 2; + table[3 * 256 + 165] = 2; + table[3 * 256 + 166] = 2; + table[3 * 256 + 167] = 2; + table[3 * 256 + 168] = 2; + table[3 * 256 + 169] = 2; + table[3 * 256 + 170] = 2; + table[3 * 256 + 171] = 2; + table[3 * 256 + 172] = 2; + table[3 * 256 + 173] = 2; + table[3 * 256 + 174] = 2; + table[3 * 256 + 175] = 2; + table[3 * 256 + 176] = 2; + table[3 * 256 + 177] = 2; + table[3 * 256 + 178] = 2; + table[3 * 256 + 179] = 2; + table[3 * 256 + 180] = 2; + table[3 * 256 + 181] = 2; + table[3 * 256 + 182] = 2; + table[3 * 256 + 183] = 2; + table[3 * 256 + 184] = 2; + table[3 * 256 + 185] = 2; + table[3 * 256 + 186] = 2; + table[3 * 256 + 187] = 2; + table[3 * 256 + 188] = 2; + table[3 * 256 + 189] = 2; + table[3 * 256 + 190] = 2; + table[3 * 256 + 191] = 2; + table[4 * 256 + 160] = 3; + table[4 * 256 + 161] = 3; + table[4 * 256 + 162] = 3; + table[4 * 256 + 163] = 3; + table[4 * 256 + 164] = 3; + table[4 * 256 + 165] = 3; + table[4 * 256 + 166] = 3; + table[4 * 256 + 167] = 3; + table[4 * 256 + 168] = 3; + table[4 * 256 + 169] = 3; + table[4 * 256 + 170] = 3; + table[4 * 256 + 171] = 3; + table[4 * 256 + 172] = 3; + table[4 * 256 + 173] = 3; + table[4 * 256 + 174] = 3; + table[4 * 256 + 175] = 3; + table[4 * 256 + 176] = 3; + table[4 * 256 + 177] = 3; + table[4 * 256 + 178] = 3; + table[4 * 256 + 179] = 3; + table[4 * 256 + 180] = 3; + table[4 * 256 + 181] = 3; + table[4 * 256 + 182] = 3; + table[4 * 256 + 183] = 3; + table[4 * 256 + 184] = 3; + table[4 * 256 + 185] = 3; + table[4 * 256 + 186] = 3; + table[4 * 256 + 187] = 3; + table[4 * 256 + 188] = 3; + table[4 * 256 + 189] = 3; + table[4 * 256 + 190] = 3; + table[4 * 256 + 191] = 3; + table[5 * 256 + 128] = 3; + table[5 * 256 + 129] = 3; + table[5 * 256 + 130] = 3; + table[5 * 256 + 131] = 3; + table[5 * 256 + 132] = 3; + table[5 * 256 + 133] = 3; + table[5 * 256 + 134] = 3; + table[5 * 256 + 135] = 3; + table[5 * 256 + 136] = 3; + table[5 * 256 + 137] = 3; + table[5 * 256 + 138] = 3; + table[5 * 256 + 139] = 3; + table[5 * 256 + 140] = 3; + table[5 * 256 + 141] = 3; + table[5 * 256 + 142] = 3; + table[5 * 256 + 143] = 3; + table[5 * 256 + 144] = 3; + table[5 * 256 + 145] = 3; + table[5 * 256 + 146] = 3; + table[5 * 256 + 147] = 3; + table[5 * 256 + 148] = 3; + table[5 * 256 + 149] = 3; + table[5 * 256 + 150] = 3; + table[5 * 256 + 151] = 3; + table[5 * 256 + 152] = 3; + table[5 * 256 + 153] = 3; + table[5 * 256 + 154] = 3; + table[5 * 256 + 155] = 3; + table[5 * 256 + 156] = 3; + table[5 * 256 + 157] = 3; + table[5 * 256 + 158] = 3; + table[5 * 256 + 159] = 3; + table[5 * 256 + 160] = 3; + table[5 * 256 + 161] = 3; + table[5 * 256 + 162] = 3; + table[5 * 256 + 163] = 3; + table[5 * 256 + 164] = 3; + table[5 * 256 + 165] = 3; + table[5 * 256 + 166] = 3; + table[5 * 256 + 167] = 3; + table[5 * 256 + 168] = 3; + table[5 * 256 + 169] = 3; + table[5 * 256 + 170] = 3; + table[5 * 256 + 171] = 3; + table[5 * 256 + 172] = 3; + table[5 * 256 + 173] = 3; + table[5 * 256 + 174] = 3; + table[5 * 256 + 175] = 3; + table[5 * 256 + 176] = 3; + table[5 * 256 + 177] = 3; + table[5 * 256 + 178] = 3; + table[5 * 256 + 179] = 3; + table[5 * 256 + 180] = 3; + table[5 * 256 + 181] = 3; + table[5 * 256 + 182] = 3; + table[5 * 256 + 183] = 3; + table[5 * 256 + 184] = 3; + table[5 * 256 + 185] = 3; + table[5 * 256 + 186] = 3; + table[5 * 256 + 187] = 3; + table[5 * 256 + 188] = 3; + table[5 * 256 + 189] = 3; + table[5 * 256 + 190] = 3; + table[5 * 256 + 191] = 3; + table[6 * 256 + 128] = 3; + table[6 * 256 + 129] = 3; + table[6 * 256 + 130] = 3; + table[6 * 256 + 131] = 3; + table[6 * 256 + 132] = 3; + table[6 * 256 + 133] = 3; + table[6 * 256 + 134] = 3; + table[6 * 256 + 135] = 3; + table[6 * 256 + 136] = 3; + table[6 * 256 + 137] = 3; + table[6 * 256 + 138] = 3; + table[6 * 256 + 139] = 3; + table[6 * 256 + 140] = 3; + table[6 * 256 + 141] = 3; + table[6 * 256 + 142] = 3; + table[6 * 256 + 143] = 3; + table[6 * 256 + 144] = 3; + table[6 * 256 + 145] = 3; + table[6 * 256 + 146] = 3; + table[6 * 256 + 147] = 3; + table[6 * 256 + 148] = 3; + table[6 * 256 + 149] = 3; + table[6 * 256 + 150] = 3; + table[6 * 256 + 151] = 3; + table[6 * 256 + 152] = 3; + table[6 * 256 + 153] = 3; + table[6 * 256 + 154] = 3; + table[6 * 256 + 155] = 3; + table[6 * 256 + 156] = 3; + table[6 * 256 + 157] = 3; + table[6 * 256 + 158] = 3; + table[6 * 256 + 159] = 3; + table[7 * 256 + 144] = 5; + table[7 * 256 + 145] = 5; + table[7 * 256 + 146] = 5; + table[7 * 256 + 147] = 5; + table[7 * 256 + 148] = 5; + table[7 * 256 + 149] = 5; + table[7 * 256 + 150] = 5; + table[7 * 256 + 151] = 5; + table[7 * 256 + 152] = 5; + table[7 * 256 + 153] = 5; + table[7 * 256 + 154] = 5; + table[7 * 256 + 155] = 5; + table[7 * 256 + 156] = 5; + table[7 * 256 + 157] = 5; + table[7 * 256 + 158] = 5; + table[7 * 256 + 159] = 5; + table[7 * 256 + 160] = 5; + table[7 * 256 + 161] = 5; + table[7 * 256 + 162] = 5; + table[7 * 256 + 163] = 5; + table[7 * 256 + 164] = 5; + table[7 * 256 + 165] = 5; + table[7 * 256 + 166] = 5; + table[7 * 256 + 167] = 5; + table[7 * 256 + 168] = 5; + table[7 * 256 + 169] = 5; + table[7 * 256 + 170] = 5; + table[7 * 256 + 171] = 5; + table[7 * 256 + 172] = 5; + table[7 * 256 + 173] = 5; + table[7 * 256 + 174] = 5; + table[7 * 256 + 175] = 5; + table[7 * 256 + 176] = 5; + table[7 * 256 + 177] = 5; + table[7 * 256 + 178] = 5; + table[7 * 256 + 179] = 5; + table[7 * 256 + 180] = 5; + table[7 * 256 + 181] = 5; + table[7 * 256 + 182] = 5; + table[7 * 256 + 183] = 5; + table[7 * 256 + 184] = 5; + table[7 * 256 + 185] = 5; + table[7 * 256 + 186] = 5; + table[7 * 256 + 187] = 5; + table[7 * 256 + 188] = 5; + table[7 * 256 + 189] = 5; + table[7 * 256 + 190] = 5; + table[7 * 256 + 191] = 5; + table[8 * 256 + 128] = 5; + table[8 * 256 + 129] = 5; + table[8 * 256 + 130] = 5; + table[8 * 256 + 131] = 5; + table[8 * 256 + 132] = 5; + table[8 * 256 + 133] = 5; + table[8 * 256 + 134] = 5; + table[8 * 256 + 135] = 5; + table[8 * 256 + 136] = 5; + table[8 * 256 + 137] = 5; + table[8 * 256 + 138] = 5; + table[8 * 256 + 139] = 5; + table[8 * 256 + 140] = 5; + table[8 * 256 + 141] = 5; + table[8 * 256 + 142] = 5; + table[8 * 256 + 143] = 5; + table[8 * 256 + 144] = 5; + table[8 * 256 + 145] = 5; + table[8 * 256 + 146] = 5; + table[8 * 256 + 147] = 5; + table[8 * 256 + 148] = 5; + table[8 * 256 + 149] = 5; + table[8 * 256 + 150] = 5; + table[8 * 256 + 151] = 5; + table[8 * 256 + 152] = 5; + table[8 * 256 + 153] = 5; + table[8 * 256 + 154] = 5; + table[8 * 256 + 155] = 5; + table[8 * 256 + 156] = 5; + table[8 * 256 + 157] = 5; + table[8 * 256 + 158] = 5; + table[8 * 256 + 159] = 5; + table[8 * 256 + 160] = 5; + table[8 * 256 + 161] = 5; + table[8 * 256 + 162] = 5; + table[8 * 256 + 163] = 5; + table[8 * 256 + 164] = 5; + table[8 * 256 + 165] = 5; + table[8 * 256 + 166] = 5; + table[8 * 256 + 167] = 5; + table[8 * 256 + 168] = 5; + table[8 * 256 + 169] = 5; + table[8 * 256 + 170] = 5; + table[8 * 256 + 171] = 5; + table[8 * 256 + 172] = 5; + table[8 * 256 + 173] = 5; + table[8 * 256 + 174] = 5; + table[8 * 256 + 175] = 5; + table[8 * 256 + 176] = 5; + table[8 * 256 + 177] = 5; + table[8 * 256 + 178] = 5; + table[8 * 256 + 179] = 5; + table[8 * 256 + 180] = 5; + table[8 * 256 + 181] = 5; + table[8 * 256 + 182] = 5; + table[8 * 256 + 183] = 5; + table[8 * 256 + 184] = 5; + table[8 * 256 + 185] = 5; + table[8 * 256 + 186] = 5; + table[8 * 256 + 187] = 5; + table[8 * 256 + 188] = 5; + table[8 * 256 + 189] = 5; + table[8 * 256 + 190] = 5; + table[8 * 256 + 191] = 5; + table[9 * 256 + 128] = 5; + table[9 * 256 + 129] = 5; + table[9 * 256 + 130] = 5; + table[9 * 256 + 131] = 5; + table[9 * 256 + 132] = 5; + table[9 * 256 + 133] = 5; + table[9 * 256 + 134] = 5; + table[9 * 256 + 135] = 5; + table[9 * 256 + 136] = 5; + table[9 * 256 + 137] = 5; + table[9 * 256 + 138] = 5; + table[9 * 256 + 139] = 5; + table[9 * 256 + 140] = 5; + table[9 * 256 + 141] = 5; + table[9 * 256 + 142] = 5; + table[9 * 256 + 143] = 5; + table[10 * 256 + 0] = 10; + table[10 * 256 + 1] = 10; + table[10 * 256 + 2] = 10; + table[10 * 256 + 3] = 10; + table[10 * 256 + 4] = 10; + table[10 * 256 + 5] = 10; + table[10 * 256 + 6] = 10; + table[10 * 256 + 7] = 10; + table[10 * 256 + 8] = 10; + table[10 * 256 + 9] = 10; + table[10 * 256 + 11] = 10; + table[10 * 256 + 12] = 10; + table[10 * 256 + 13] = 10; + table[10 * 256 + 14] = 10; + table[10 * 256 + 15] = 10; + table[10 * 256 + 16] = 10; + table[10 * 256 + 17] = 10; + table[10 * 256 + 18] = 10; + table[10 * 256 + 19] = 10; + table[10 * 256 + 20] = 10; + table[10 * 256 + 21] = 10; + table[10 * 256 + 22] = 10; + table[10 * 256 + 23] = 10; + table[10 * 256 + 24] = 10; + table[10 * 256 + 25] = 10; + table[10 * 256 + 26] = 10; + table[10 * 256 + 27] = 10; + table[10 * 256 + 28] = 10; + table[10 * 256 + 29] = 10; + table[10 * 256 + 30] = 10; + table[10 * 256 + 31] = 10; + table[10 * 256 + 32] = 10; + table[10 * 256 + 33] = 10; + table[10 * 256 + 34] = 10; + table[10 * 256 + 35] = 10; + table[10 * 256 + 36] = 10; + table[10 * 256 + 37] = 10; + table[10 * 256 + 38] = 10; + table[10 * 256 + 39] = 10; + table[10 * 256 + 40] = 10; + table[10 * 256 + 41] = 10; + table[10 * 256 + 42] = 10; + table[10 * 256 + 43] = 10; + table[10 * 256 + 44] = 10; + table[10 * 256 + 45] = 10; + table[10 * 256 + 46] = 10; + table[10 * 256 + 47] = 10; + table[10 * 256 + 48] = 10; + table[10 * 256 + 49] = 10; + table[10 * 256 + 50] = 10; + table[10 * 256 + 51] = 10; + table[10 * 256 + 52] = 10; + table[10 * 256 + 53] = 10; + table[10 * 256 + 54] = 10; + table[10 * 256 + 55] = 10; + table[10 * 256 + 56] = 10; + table[10 * 256 + 57] = 10; + table[10 * 256 + 58] = 10; + table[10 * 256 + 59] = 10; + table[10 * 256 + 60] = 10; + table[10 * 256 + 61] = 10; + table[10 * 256 + 62] = 10; + table[10 * 256 + 63] = 10; + table[10 * 256 + 64] = 10; + table[10 * 256 + 65] = 10; + table[10 * 256 + 66] = 10; + table[10 * 256 + 67] = 10; + table[10 * 256 + 68] = 10; + table[10 * 256 + 69] = 10; + table[10 * 256 + 70] = 10; + table[10 * 256 + 71] = 10; + table[10 * 256 + 72] = 10; + table[10 * 256 + 73] = 10; + table[10 * 256 + 74] = 10; + table[10 * 256 + 75] = 10; + table[10 * 256 + 76] = 10; + table[10 * 256 + 77] = 10; + table[10 * 256 + 78] = 10; + table[10 * 256 + 79] = 10; + table[10 * 256 + 80] = 10; + table[10 * 256 + 81] = 10; + table[10 * 256 + 82] = 10; + table[10 * 256 + 83] = 10; + table[10 * 256 + 84] = 10; + table[10 * 256 + 85] = 10; + table[10 * 256 + 86] = 10; + table[10 * 256 + 87] = 10; + table[10 * 256 + 88] = 10; + table[10 * 256 + 89] = 10; + table[10 * 256 + 90] = 10; + table[10 * 256 + 91] = 10; + table[10 * 256 + 92] = 10; + table[10 * 256 + 93] = 10; + table[10 * 256 + 94] = 10; + table[10 * 256 + 95] = 10; + table[10 * 256 + 96] = 10; + table[10 * 256 + 97] = 10; + table[10 * 256 + 98] = 10; + table[10 * 256 + 99] = 10; + table[10 * 256 + 100] = 10; + table[10 * 256 + 101] = 10; + table[10 * 256 + 102] = 10; + table[10 * 256 + 103] = 10; + table[10 * 256 + 104] = 10; + table[10 * 256 + 105] = 10; + table[10 * 256 + 106] = 10; + table[10 * 256 + 107] = 10; + table[10 * 256 + 108] = 10; + table[10 * 256 + 109] = 10; + table[10 * 256 + 110] = 10; + table[10 * 256 + 111] = 10; + table[10 * 256 + 112] = 10; + table[10 * 256 + 113] = 10; + table[10 * 256 + 114] = 10; + table[10 * 256 + 115] = 10; + table[10 * 256 + 116] = 10; + table[10 * 256 + 117] = 10; + table[10 * 256 + 118] = 10; + table[10 * 256 + 119] = 10; + table[10 * 256 + 120] = 10; + table[10 * 256 + 121] = 10; + table[10 * 256 + 122] = 10; + table[10 * 256 + 123] = 10; + table[10 * 256 + 124] = 10; + table[10 * 256 + 125] = 10; + table[10 * 256 + 126] = 10; + table[10 * 256 + 127] = 10; + table[10 * 256 + 194] = 11; + table[10 * 256 + 195] = 11; + table[10 * 256 + 196] = 11; + table[10 * 256 + 197] = 11; + table[10 * 256 + 198] = 11; + table[10 * 256 + 199] = 11; + table[10 * 256 + 200] = 11; + table[10 * 256 + 201] = 11; + table[10 * 256 + 202] = 11; + table[10 * 256 + 203] = 11; + table[10 * 256 + 204] = 11; + table[10 * 256 + 205] = 11; + table[10 * 256 + 206] = 11; + table[10 * 256 + 207] = 11; + table[10 * 256 + 208] = 11; + table[10 * 256 + 209] = 11; + table[10 * 256 + 210] = 11; + table[10 * 256 + 211] = 11; + table[10 * 256 + 212] = 11; + table[10 * 256 + 213] = 11; + table[10 * 256 + 214] = 11; + table[10 * 256 + 215] = 11; + table[10 * 256 + 216] = 11; + table[10 * 256 + 217] = 11; + table[10 * 256 + 218] = 11; + table[10 * 256 + 219] = 11; + table[10 * 256 + 220] = 11; + table[10 * 256 + 221] = 11; + table[10 * 256 + 222] = 11; + table[10 * 256 + 223] = 11; + table[10 * 256 + 224] = 12; + table[10 * 256 + 225] = 13; + table[10 * 256 + 226] = 13; + table[10 * 256 + 227] = 13; + table[10 * 256 + 228] = 13; + table[10 * 256 + 229] = 13; + table[10 * 256 + 230] = 13; + table[10 * 256 + 231] = 13; + table[10 * 256 + 232] = 13; + table[10 * 256 + 233] = 13; + table[10 * 256 + 234] = 13; + table[10 * 256 + 235] = 13; + table[10 * 256 + 236] = 13; + table[10 * 256 + 238] = 13; + table[10 * 256 + 239] = 13; + table[10 * 256 + 237] = 14; + table[10 * 256 + 240] = 15; + table[10 * 256 + 241] = 16; + table[10 * 256 + 242] = 16; + table[10 * 256 + 243] = 16; + table[10 * 256 + 244] = 17; + table[11 * 256 + 128] = 10; + table[11 * 256 + 129] = 10; + table[11 * 256 + 130] = 10; + table[11 * 256 + 131] = 10; + table[11 * 256 + 132] = 10; + table[11 * 256 + 133] = 10; + table[11 * 256 + 134] = 10; + table[11 * 256 + 135] = 10; + table[11 * 256 + 136] = 10; + table[11 * 256 + 137] = 10; + table[11 * 256 + 138] = 10; + table[11 * 256 + 139] = 10; + table[11 * 256 + 140] = 10; + table[11 * 256 + 141] = 10; + table[11 * 256 + 142] = 10; + table[11 * 256 + 143] = 10; + table[11 * 256 + 144] = 10; + table[11 * 256 + 145] = 10; + table[11 * 256 + 146] = 10; + table[11 * 256 + 147] = 10; + table[11 * 256 + 148] = 10; + table[11 * 256 + 149] = 10; + table[11 * 256 + 150] = 10; + table[11 * 256 + 151] = 10; + table[11 * 256 + 152] = 10; + table[11 * 256 + 153] = 10; + table[11 * 256 + 154] = 10; + table[11 * 256 + 155] = 10; + table[11 * 256 + 156] = 10; + table[11 * 256 + 157] = 10; + table[11 * 256 + 158] = 10; + table[11 * 256 + 159] = 10; + table[11 * 256 + 160] = 10; + table[11 * 256 + 161] = 10; + table[11 * 256 + 162] = 10; + table[11 * 256 + 163] = 10; + table[11 * 256 + 164] = 10; + table[11 * 256 + 165] = 10; + table[11 * 256 + 166] = 10; + table[11 * 256 + 167] = 10; + table[11 * 256 + 168] = 10; + table[11 * 256 + 169] = 10; + table[11 * 256 + 170] = 10; + table[11 * 256 + 171] = 10; + table[11 * 256 + 172] = 10; + table[11 * 256 + 173] = 10; + table[11 * 256 + 174] = 10; + table[11 * 256 + 175] = 10; + table[11 * 256 + 176] = 10; + table[11 * 256 + 177] = 10; + table[11 * 256 + 178] = 10; + table[11 * 256 + 179] = 10; + table[11 * 256 + 180] = 10; + table[11 * 256 + 181] = 10; + table[11 * 256 + 182] = 10; + table[11 * 256 + 183] = 10; + table[11 * 256 + 184] = 10; + table[11 * 256 + 185] = 10; + table[11 * 256 + 186] = 10; + table[11 * 256 + 187] = 10; + table[11 * 256 + 188] = 10; + table[11 * 256 + 189] = 10; + table[11 * 256 + 190] = 10; + table[11 * 256 + 191] = 10; + table[12 * 256 + 160] = 11; + table[12 * 256 + 161] = 11; + table[12 * 256 + 162] = 11; + table[12 * 256 + 163] = 11; + table[12 * 256 + 164] = 11; + table[12 * 256 + 165] = 11; + table[12 * 256 + 166] = 11; + table[12 * 256 + 167] = 11; + table[12 * 256 + 168] = 11; + table[12 * 256 + 169] = 11; + table[12 * 256 + 170] = 11; + table[12 * 256 + 171] = 11; + table[12 * 256 + 172] = 11; + table[12 * 256 + 173] = 11; + table[12 * 256 + 174] = 11; + table[12 * 256 + 175] = 11; + table[12 * 256 + 176] = 11; + table[12 * 256 + 177] = 11; + table[12 * 256 + 178] = 11; + table[12 * 256 + 179] = 11; + table[12 * 256 + 180] = 11; + table[12 * 256 + 181] = 11; + table[12 * 256 + 182] = 11; + table[12 * 256 + 183] = 11; + table[12 * 256 + 184] = 11; + table[12 * 256 + 185] = 11; + table[12 * 256 + 186] = 11; + table[12 * 256 + 187] = 11; + table[12 * 256 + 188] = 11; + table[12 * 256 + 189] = 11; + table[12 * 256 + 190] = 11; + table[12 * 256 + 191] = 11; + table[13 * 256 + 128] = 11; + table[13 * 256 + 129] = 11; + table[13 * 256 + 130] = 11; + table[13 * 256 + 131] = 11; + table[13 * 256 + 132] = 11; + table[13 * 256 + 133] = 11; + table[13 * 256 + 134] = 11; + table[13 * 256 + 135] = 11; + table[13 * 256 + 136] = 11; + table[13 * 256 + 137] = 11; + table[13 * 256 + 138] = 11; + table[13 * 256 + 139] = 11; + table[13 * 256 + 140] = 11; + table[13 * 256 + 141] = 11; + table[13 * 256 + 142] = 11; + table[13 * 256 + 143] = 11; + table[13 * 256 + 144] = 11; + table[13 * 256 + 145] = 11; + table[13 * 256 + 146] = 11; + table[13 * 256 + 147] = 11; + table[13 * 256 + 148] = 11; + table[13 * 256 + 149] = 11; + table[13 * 256 + 150] = 11; + table[13 * 256 + 151] = 11; + table[13 * 256 + 152] = 11; + table[13 * 256 + 153] = 11; + table[13 * 256 + 154] = 11; + table[13 * 256 + 155] = 11; + table[13 * 256 + 156] = 11; + table[13 * 256 + 157] = 11; + table[13 * 256 + 158] = 11; + table[13 * 256 + 159] = 11; + table[13 * 256 + 160] = 11; + table[13 * 256 + 161] = 11; + table[13 * 256 + 162] = 11; + table[13 * 256 + 163] = 11; + table[13 * 256 + 164] = 11; + table[13 * 256 + 165] = 11; + table[13 * 256 + 166] = 11; + table[13 * 256 + 167] = 11; + table[13 * 256 + 168] = 11; + table[13 * 256 + 169] = 11; + table[13 * 256 + 170] = 11; + table[13 * 256 + 171] = 11; + table[13 * 256 + 172] = 11; + table[13 * 256 + 173] = 11; + table[13 * 256 + 174] = 11; + table[13 * 256 + 175] = 11; + table[13 * 256 + 176] = 11; + table[13 * 256 + 177] = 11; + table[13 * 256 + 178] = 11; + table[13 * 256 + 179] = 11; + table[13 * 256 + 180] = 11; + table[13 * 256 + 181] = 11; + table[13 * 256 + 182] = 11; + table[13 * 256 + 183] = 11; + table[13 * 256 + 184] = 11; + table[13 * 256 + 185] = 11; + table[13 * 256 + 186] = 11; + table[13 * 256 + 187] = 11; + table[13 * 256 + 188] = 11; + table[13 * 256 + 189] = 11; + table[13 * 256 + 190] = 11; + table[13 * 256 + 191] = 11; + table[14 * 256 + 128] = 11; + table[14 * 256 + 129] = 11; + table[14 * 256 + 130] = 11; + table[14 * 256 + 131] = 11; + table[14 * 256 + 132] = 11; + table[14 * 256 + 133] = 11; + table[14 * 256 + 134] = 11; + table[14 * 256 + 135] = 11; + table[14 * 256 + 136] = 11; + table[14 * 256 + 137] = 11; + table[14 * 256 + 138] = 11; + table[14 * 256 + 139] = 11; + table[14 * 256 + 140] = 11; + table[14 * 256 + 141] = 11; + table[14 * 256 + 142] = 11; + table[14 * 256 + 143] = 11; + table[14 * 256 + 144] = 11; + table[14 * 256 + 145] = 11; + table[14 * 256 + 146] = 11; + table[14 * 256 + 147] = 11; + table[14 * 256 + 148] = 11; + table[14 * 256 + 149] = 11; + table[14 * 256 + 150] = 11; + table[14 * 256 + 151] = 11; + table[14 * 256 + 152] = 11; + table[14 * 256 + 153] = 11; + table[14 * 256 + 154] = 11; + table[14 * 256 + 155] = 11; + table[14 * 256 + 156] = 11; + table[14 * 256 + 157] = 11; + table[14 * 256 + 158] = 11; + table[14 * 256 + 159] = 11; + table[15 * 256 + 144] = 13; + table[15 * 256 + 145] = 13; + table[15 * 256 + 146] = 13; + table[15 * 256 + 147] = 13; + table[15 * 256 + 148] = 13; + table[15 * 256 + 149] = 13; + table[15 * 256 + 150] = 13; + table[15 * 256 + 151] = 13; + table[15 * 256 + 152] = 13; + table[15 * 256 + 153] = 13; + table[15 * 256 + 154] = 13; + table[15 * 256 + 155] = 13; + table[15 * 256 + 156] = 13; + table[15 * 256 + 157] = 13; + table[15 * 256 + 158] = 13; + table[15 * 256 + 159] = 13; + table[15 * 256 + 160] = 13; + table[15 * 256 + 161] = 13; + table[15 * 256 + 162] = 13; + table[15 * 256 + 163] = 13; + table[15 * 256 + 164] = 13; + table[15 * 256 + 165] = 13; + table[15 * 256 + 166] = 13; + table[15 * 256 + 167] = 13; + table[15 * 256 + 168] = 13; + table[15 * 256 + 169] = 13; + table[15 * 256 + 170] = 13; + table[15 * 256 + 171] = 13; + table[15 * 256 + 172] = 13; + table[15 * 256 + 173] = 13; + table[15 * 256 + 174] = 13; + table[15 * 256 + 175] = 13; + table[15 * 256 + 176] = 13; + table[15 * 256 + 177] = 13; + table[15 * 256 + 178] = 13; + table[15 * 256 + 179] = 13; + table[15 * 256 + 180] = 13; + table[15 * 256 + 181] = 13; + table[15 * 256 + 182] = 13; + table[15 * 256 + 183] = 13; + table[15 * 256 + 184] = 13; + table[15 * 256 + 185] = 13; + table[15 * 256 + 186] = 13; + table[15 * 256 + 187] = 13; + table[15 * 256 + 188] = 13; + table[15 * 256 + 189] = 13; + table[15 * 256 + 190] = 13; + table[15 * 256 + 191] = 13; + table[16 * 256 + 128] = 13; + table[16 * 256 + 129] = 13; + table[16 * 256 + 130] = 13; + table[16 * 256 + 131] = 13; + table[16 * 256 + 132] = 13; + table[16 * 256 + 133] = 13; + table[16 * 256 + 134] = 13; + table[16 * 256 + 135] = 13; + table[16 * 256 + 136] = 13; + table[16 * 256 + 137] = 13; + table[16 * 256 + 138] = 13; + table[16 * 256 + 139] = 13; + table[16 * 256 + 140] = 13; + table[16 * 256 + 141] = 13; + table[16 * 256 + 142] = 13; + table[16 * 256 + 143] = 13; + table[16 * 256 + 144] = 13; + table[16 * 256 + 145] = 13; + table[16 * 256 + 146] = 13; + table[16 * 256 + 147] = 13; + table[16 * 256 + 148] = 13; + table[16 * 256 + 149] = 13; + table[16 * 256 + 150] = 13; + table[16 * 256 + 151] = 13; + table[16 * 256 + 152] = 13; + table[16 * 256 + 153] = 13; + table[16 * 256 + 154] = 13; + table[16 * 256 + 155] = 13; + table[16 * 256 + 156] = 13; + table[16 * 256 + 157] = 13; + table[16 * 256 + 158] = 13; + table[16 * 256 + 159] = 13; + table[16 * 256 + 160] = 13; + table[16 * 256 + 161] = 13; + table[16 * 256 + 162] = 13; + table[16 * 256 + 163] = 13; + table[16 * 256 + 164] = 13; + table[16 * 256 + 165] = 13; + table[16 * 256 + 166] = 13; + table[16 * 256 + 167] = 13; + table[16 * 256 + 168] = 13; + table[16 * 256 + 169] = 13; + table[16 * 256 + 170] = 13; + table[16 * 256 + 171] = 13; + table[16 * 256 + 172] = 13; + table[16 * 256 + 173] = 13; + table[16 * 256 + 174] = 13; + table[16 * 256 + 175] = 13; + table[16 * 256 + 176] = 13; + table[16 * 256 + 177] = 13; + table[16 * 256 + 178] = 13; + table[16 * 256 + 179] = 13; + table[16 * 256 + 180] = 13; + table[16 * 256 + 181] = 13; + table[16 * 256 + 182] = 13; + table[16 * 256 + 183] = 13; + table[16 * 256 + 184] = 13; + table[16 * 256 + 185] = 13; + table[16 * 256 + 186] = 13; + table[16 * 256 + 187] = 13; + table[16 * 256 + 188] = 13; + table[16 * 256 + 189] = 13; + table[16 * 256 + 190] = 13; + table[16 * 256 + 191] = 13; + table[17 * 256 + 128] = 13; + table[17 * 256 + 129] = 13; + table[17 * 256 + 130] = 13; + table[17 * 256 + 131] = 13; + table[17 * 256 + 132] = 13; + table[17 * 256 + 133] = 13; + table[17 * 256 + 134] = 13; + table[17 * 256 + 135] = 13; + table[17 * 256 + 136] = 13; + table[17 * 256 + 137] = 13; + table[17 * 256 + 138] = 13; + table[17 * 256 + 139] = 13; + table[17 * 256 + 140] = 13; + table[17 * 256 + 141] = 13; + table[17 * 256 + 142] = 13; + table[17 * 256 + 143] = 13; + + table +} +pub fn regex_match(input: [u8; N]) -> bool { + // regex: >[^<>]+<.* + let mut s = 0; + s = table[255]; + for i in 0..input.len() { + let s_idx = s * 256 + input[i] as Field; + std::as_witness(s_idx); + s = table[s_idx]; + } + + let matched: bool = (s == 10) | (s == 18); + + matched +} + + \ No newline at end of file diff --git a/packages/noir/src/basic/subject_all.nr b/packages/noir/src/basic/subject_all.nr new file mode 100644 index 00000000..c082a91d --- /dev/null +++ b/packages/noir/src/basic/subject_all.nr @@ -0,0 +1,1224 @@ + +use crate::common::Sequence; + + +global table: [Field; 5632] = comptime { make_lookup_table() }; + +comptime fn make_lookup_table() -> [Field; 5632] { + let mut table = [0; 5632]; + table[20 * 256 + 0] = 21; + table[21 * 256 + 0] = 21; + table[20 * 256 + 1] = 21; + table[21 * 256 + 1] = 21; + table[20 * 256 + 2] = 21; + table[21 * 256 + 2] = 21; + table[20 * 256 + 3] = 21; + table[21 * 256 + 3] = 21; + table[20 * 256 + 4] = 21; + table[21 * 256 + 4] = 21; + table[20 * 256 + 5] = 21; + table[21 * 256 + 5] = 21; + table[20 * 256 + 6] = 21; + table[21 * 256 + 6] = 21; + table[20 * 256 + 7] = 21; + table[21 * 256 + 7] = 21; + table[20 * 256 + 8] = 21; + table[21 * 256 + 8] = 21; + table[20 * 256 + 9] = 21; + table[21 * 256 + 9] = 21; + table[20 * 256 + 10] = 21; + table[21 * 256 + 10] = 21; + table[20 * 256 + 11] = 21; + table[21 * 256 + 11] = 21; + table[20 * 256 + 12] = 21; + table[21 * 256 + 12] = 21; + table[20 * 256 + 13] = 21; + table[21 * 256 + 13] = 21; + table[20 * 256 + 14] = 21; + table[21 * 256 + 14] = 21; + table[20 * 256 + 15] = 21; + table[21 * 256 + 15] = 21; + table[20 * 256 + 16] = 21; + table[21 * 256 + 16] = 21; + table[20 * 256 + 17] = 21; + table[21 * 256 + 17] = 21; + table[20 * 256 + 18] = 21; + table[21 * 256 + 18] = 21; + table[20 * 256 + 19] = 21; + table[21 * 256 + 19] = 21; + table[20 * 256 + 20] = 21; + table[21 * 256 + 20] = 21; + table[20 * 256 + 21] = 21; + table[21 * 256 + 21] = 21; + table[20 * 256 + 22] = 21; + table[21 * 256 + 22] = 21; + table[20 * 256 + 23] = 21; + table[21 * 256 + 23] = 21; + table[20 * 256 + 24] = 21; + table[21 * 256 + 24] = 21; + table[20 * 256 + 25] = 21; + table[21 * 256 + 25] = 21; + table[20 * 256 + 26] = 21; + table[21 * 256 + 26] = 21; + table[20 * 256 + 27] = 21; + table[21 * 256 + 27] = 21; + table[20 * 256 + 28] = 21; + table[21 * 256 + 28] = 21; + table[20 * 256 + 29] = 21; + table[21 * 256 + 29] = 21; + table[20 * 256 + 30] = 21; + table[21 * 256 + 30] = 21; + table[20 * 256 + 31] = 21; + table[21 * 256 + 31] = 21; + table[20 * 256 + 32] = 21; + table[21 * 256 + 32] = 21; + table[20 * 256 + 33] = 21; + table[21 * 256 + 33] = 21; + table[20 * 256 + 34] = 21; + table[21 * 256 + 34] = 21; + table[20 * 256 + 35] = 21; + table[21 * 256 + 35] = 21; + table[20 * 256 + 36] = 21; + table[21 * 256 + 36] = 21; + table[20 * 256 + 37] = 21; + table[21 * 256 + 37] = 21; + table[20 * 256 + 38] = 21; + table[21 * 256 + 38] = 21; + table[20 * 256 + 39] = 21; + table[21 * 256 + 39] = 21; + table[20 * 256 + 40] = 21; + table[21 * 256 + 40] = 21; + table[20 * 256 + 41] = 21; + table[21 * 256 + 41] = 21; + table[20 * 256 + 42] = 21; + table[21 * 256 + 42] = 21; + table[20 * 256 + 43] = 21; + table[21 * 256 + 43] = 21; + table[20 * 256 + 44] = 21; + table[21 * 256 + 44] = 21; + table[20 * 256 + 45] = 21; + table[21 * 256 + 45] = 21; + table[20 * 256 + 46] = 21; + table[21 * 256 + 46] = 21; + table[20 * 256 + 47] = 21; + table[21 * 256 + 47] = 21; + table[20 * 256 + 48] = 21; + table[21 * 256 + 48] = 21; + table[20 * 256 + 49] = 21; + table[21 * 256 + 49] = 21; + table[20 * 256 + 50] = 21; + table[21 * 256 + 50] = 21; + table[20 * 256 + 51] = 21; + table[21 * 256 + 51] = 21; + table[20 * 256 + 52] = 21; + table[21 * 256 + 52] = 21; + table[20 * 256 + 53] = 21; + table[21 * 256 + 53] = 21; + table[20 * 256 + 54] = 21; + table[21 * 256 + 54] = 21; + table[20 * 256 + 55] = 21; + table[21 * 256 + 55] = 21; + table[20 * 256 + 56] = 21; + table[21 * 256 + 56] = 21; + table[20 * 256 + 57] = 21; + table[21 * 256 + 57] = 21; + table[20 * 256 + 58] = 21; + table[21 * 256 + 58] = 21; + table[20 * 256 + 59] = 21; + table[21 * 256 + 59] = 21; + table[20 * 256 + 60] = 21; + table[21 * 256 + 60] = 21; + table[20 * 256 + 61] = 21; + table[21 * 256 + 61] = 21; + table[20 * 256 + 62] = 21; + table[21 * 256 + 62] = 21; + table[20 * 256 + 63] = 21; + table[21 * 256 + 63] = 21; + table[20 * 256 + 64] = 21; + table[21 * 256 + 64] = 21; + table[20 * 256 + 65] = 21; + table[21 * 256 + 65] = 21; + table[20 * 256 + 66] = 21; + table[21 * 256 + 66] = 21; + table[20 * 256 + 67] = 21; + table[21 * 256 + 67] = 21; + table[20 * 256 + 68] = 21; + table[21 * 256 + 68] = 21; + table[20 * 256 + 69] = 21; + table[21 * 256 + 69] = 21; + table[20 * 256 + 70] = 21; + table[21 * 256 + 70] = 21; + table[20 * 256 + 71] = 21; + table[21 * 256 + 71] = 21; + table[20 * 256 + 72] = 21; + table[21 * 256 + 72] = 21; + table[20 * 256 + 73] = 21; + table[21 * 256 + 73] = 21; + table[20 * 256 + 74] = 21; + table[21 * 256 + 74] = 21; + table[20 * 256 + 75] = 21; + table[21 * 256 + 75] = 21; + table[20 * 256 + 76] = 21; + table[21 * 256 + 76] = 21; + table[20 * 256 + 77] = 21; + table[21 * 256 + 77] = 21; + table[20 * 256 + 78] = 21; + table[21 * 256 + 78] = 21; + table[20 * 256 + 79] = 21; + table[21 * 256 + 79] = 21; + table[20 * 256 + 80] = 21; + table[21 * 256 + 80] = 21; + table[20 * 256 + 81] = 21; + table[21 * 256 + 81] = 21; + table[20 * 256 + 82] = 21; + table[21 * 256 + 82] = 21; + table[20 * 256 + 83] = 21; + table[21 * 256 + 83] = 21; + table[20 * 256 + 84] = 21; + table[21 * 256 + 84] = 21; + table[20 * 256 + 85] = 21; + table[21 * 256 + 85] = 21; + table[20 * 256 + 86] = 21; + table[21 * 256 + 86] = 21; + table[20 * 256 + 87] = 21; + table[21 * 256 + 87] = 21; + table[20 * 256 + 88] = 21; + table[21 * 256 + 88] = 21; + table[20 * 256 + 89] = 21; + table[21 * 256 + 89] = 21; + table[20 * 256 + 90] = 21; + table[21 * 256 + 90] = 21; + table[20 * 256 + 91] = 21; + table[21 * 256 + 91] = 21; + table[20 * 256 + 92] = 21; + table[21 * 256 + 92] = 21; + table[20 * 256 + 93] = 21; + table[21 * 256 + 93] = 21; + table[20 * 256 + 94] = 21; + table[21 * 256 + 94] = 21; + table[20 * 256 + 95] = 21; + table[21 * 256 + 95] = 21; + table[20 * 256 + 96] = 21; + table[21 * 256 + 96] = 21; + table[20 * 256 + 97] = 21; + table[21 * 256 + 97] = 21; + table[20 * 256 + 98] = 21; + table[21 * 256 + 98] = 21; + table[20 * 256 + 99] = 21; + table[21 * 256 + 99] = 21; + table[20 * 256 + 100] = 21; + table[21 * 256 + 100] = 21; + table[20 * 256 + 101] = 21; + table[21 * 256 + 101] = 21; + table[20 * 256 + 102] = 21; + table[21 * 256 + 102] = 21; + table[20 * 256 + 103] = 21; + table[21 * 256 + 103] = 21; + table[20 * 256 + 104] = 21; + table[21 * 256 + 104] = 21; + table[20 * 256 + 105] = 21; + table[21 * 256 + 105] = 21; + table[20 * 256 + 106] = 21; + table[21 * 256 + 106] = 21; + table[20 * 256 + 107] = 21; + table[21 * 256 + 107] = 21; + table[20 * 256 + 108] = 21; + table[21 * 256 + 108] = 21; + table[20 * 256 + 109] = 21; + table[21 * 256 + 109] = 21; + table[20 * 256 + 110] = 21; + table[21 * 256 + 110] = 21; + table[20 * 256 + 111] = 21; + table[21 * 256 + 111] = 21; + table[20 * 256 + 112] = 21; + table[21 * 256 + 112] = 21; + table[20 * 256 + 113] = 21; + table[21 * 256 + 113] = 21; + table[20 * 256 + 114] = 21; + table[21 * 256 + 114] = 21; + table[20 * 256 + 115] = 21; + table[21 * 256 + 115] = 21; + table[20 * 256 + 116] = 21; + table[21 * 256 + 116] = 21; + table[20 * 256 + 117] = 21; + table[21 * 256 + 117] = 21; + table[20 * 256 + 118] = 21; + table[21 * 256 + 118] = 21; + table[20 * 256 + 119] = 21; + table[21 * 256 + 119] = 21; + table[20 * 256 + 120] = 21; + table[21 * 256 + 120] = 21; + table[20 * 256 + 121] = 21; + table[21 * 256 + 121] = 21; + table[20 * 256 + 122] = 21; + table[21 * 256 + 122] = 21; + table[20 * 256 + 123] = 21; + table[21 * 256 + 123] = 21; + table[20 * 256 + 124] = 21; + table[21 * 256 + 124] = 21; + table[20 * 256 + 125] = 21; + table[21 * 256 + 125] = 21; + table[20 * 256 + 126] = 21; + table[21 * 256 + 126] = 21; + table[20 * 256 + 127] = 21; + table[21 * 256 + 127] = 21; + table[20 * 256 + 128] = 21; + table[21 * 256 + 128] = 21; + table[20 * 256 + 129] = 21; + table[21 * 256 + 129] = 21; + table[20 * 256 + 130] = 21; + table[21 * 256 + 130] = 21; + table[20 * 256 + 131] = 21; + table[21 * 256 + 131] = 21; + table[20 * 256 + 132] = 21; + table[21 * 256 + 132] = 21; + table[20 * 256 + 133] = 21; + table[21 * 256 + 133] = 21; + table[20 * 256 + 134] = 21; + table[21 * 256 + 134] = 21; + table[20 * 256 + 135] = 21; + table[21 * 256 + 135] = 21; + table[20 * 256 + 136] = 21; + table[21 * 256 + 136] = 21; + table[20 * 256 + 137] = 21; + table[21 * 256 + 137] = 21; + table[20 * 256 + 138] = 21; + table[21 * 256 + 138] = 21; + table[20 * 256 + 139] = 21; + table[21 * 256 + 139] = 21; + table[20 * 256 + 140] = 21; + table[21 * 256 + 140] = 21; + table[20 * 256 + 141] = 21; + table[21 * 256 + 141] = 21; + table[20 * 256 + 142] = 21; + table[21 * 256 + 142] = 21; + table[20 * 256 + 143] = 21; + table[21 * 256 + 143] = 21; + table[20 * 256 + 144] = 21; + table[21 * 256 + 144] = 21; + table[20 * 256 + 145] = 21; + table[21 * 256 + 145] = 21; + table[20 * 256 + 146] = 21; + table[21 * 256 + 146] = 21; + table[20 * 256 + 147] = 21; + table[21 * 256 + 147] = 21; + table[20 * 256 + 148] = 21; + table[21 * 256 + 148] = 21; + table[20 * 256 + 149] = 21; + table[21 * 256 + 149] = 21; + table[20 * 256 + 150] = 21; + table[21 * 256 + 150] = 21; + table[20 * 256 + 151] = 21; + table[21 * 256 + 151] = 21; + table[20 * 256 + 152] = 21; + table[21 * 256 + 152] = 21; + table[20 * 256 + 153] = 21; + table[21 * 256 + 153] = 21; + table[20 * 256 + 154] = 21; + table[21 * 256 + 154] = 21; + table[20 * 256 + 155] = 21; + table[21 * 256 + 155] = 21; + table[20 * 256 + 156] = 21; + table[21 * 256 + 156] = 21; + table[20 * 256 + 157] = 21; + table[21 * 256 + 157] = 21; + table[20 * 256 + 158] = 21; + table[21 * 256 + 158] = 21; + table[20 * 256 + 159] = 21; + table[21 * 256 + 159] = 21; + table[20 * 256 + 160] = 21; + table[21 * 256 + 160] = 21; + table[20 * 256 + 161] = 21; + table[21 * 256 + 161] = 21; + table[20 * 256 + 162] = 21; + table[21 * 256 + 162] = 21; + table[20 * 256 + 163] = 21; + table[21 * 256 + 163] = 21; + table[20 * 256 + 164] = 21; + table[21 * 256 + 164] = 21; + table[20 * 256 + 165] = 21; + table[21 * 256 + 165] = 21; + table[20 * 256 + 166] = 21; + table[21 * 256 + 166] = 21; + table[20 * 256 + 167] = 21; + table[21 * 256 + 167] = 21; + table[20 * 256 + 168] = 21; + table[21 * 256 + 168] = 21; + table[20 * 256 + 169] = 21; + table[21 * 256 + 169] = 21; + table[20 * 256 + 170] = 21; + table[21 * 256 + 170] = 21; + table[20 * 256 + 171] = 21; + table[21 * 256 + 171] = 21; + table[20 * 256 + 172] = 21; + table[21 * 256 + 172] = 21; + table[20 * 256 + 173] = 21; + table[21 * 256 + 173] = 21; + table[20 * 256 + 174] = 21; + table[21 * 256 + 174] = 21; + table[20 * 256 + 175] = 21; + table[21 * 256 + 175] = 21; + table[20 * 256 + 176] = 21; + table[21 * 256 + 176] = 21; + table[20 * 256 + 177] = 21; + table[21 * 256 + 177] = 21; + table[20 * 256 + 178] = 21; + table[21 * 256 + 178] = 21; + table[20 * 256 + 179] = 21; + table[21 * 256 + 179] = 21; + table[20 * 256 + 180] = 21; + table[21 * 256 + 180] = 21; + table[20 * 256 + 181] = 21; + table[21 * 256 + 181] = 21; + table[20 * 256 + 182] = 21; + table[21 * 256 + 182] = 21; + table[20 * 256 + 183] = 21; + table[21 * 256 + 183] = 21; + table[20 * 256 + 184] = 21; + table[21 * 256 + 184] = 21; + table[20 * 256 + 185] = 21; + table[21 * 256 + 185] = 21; + table[20 * 256 + 186] = 21; + table[21 * 256 + 186] = 21; + table[20 * 256 + 187] = 21; + table[21 * 256 + 187] = 21; + table[20 * 256 + 188] = 21; + table[21 * 256 + 188] = 21; + table[20 * 256 + 189] = 21; + table[21 * 256 + 189] = 21; + table[20 * 256 + 190] = 21; + table[21 * 256 + 190] = 21; + table[20 * 256 + 191] = 21; + table[21 * 256 + 191] = 21; + table[20 * 256 + 192] = 21; + table[21 * 256 + 192] = 21; + table[20 * 256 + 193] = 21; + table[21 * 256 + 193] = 21; + table[20 * 256 + 194] = 21; + table[21 * 256 + 194] = 21; + table[20 * 256 + 195] = 21; + table[21 * 256 + 195] = 21; + table[20 * 256 + 196] = 21; + table[21 * 256 + 196] = 21; + table[20 * 256 + 197] = 21; + table[21 * 256 + 197] = 21; + table[20 * 256 + 198] = 21; + table[21 * 256 + 198] = 21; + table[20 * 256 + 199] = 21; + table[21 * 256 + 199] = 21; + table[20 * 256 + 200] = 21; + table[21 * 256 + 200] = 21; + table[20 * 256 + 201] = 21; + table[21 * 256 + 201] = 21; + table[20 * 256 + 202] = 21; + table[21 * 256 + 202] = 21; + table[20 * 256 + 203] = 21; + table[21 * 256 + 203] = 21; + table[20 * 256 + 204] = 21; + table[21 * 256 + 204] = 21; + table[20 * 256 + 205] = 21; + table[21 * 256 + 205] = 21; + table[20 * 256 + 206] = 21; + table[21 * 256 + 206] = 21; + table[20 * 256 + 207] = 21; + table[21 * 256 + 207] = 21; + table[20 * 256 + 208] = 21; + table[21 * 256 + 208] = 21; + table[20 * 256 + 209] = 21; + table[21 * 256 + 209] = 21; + table[20 * 256 + 210] = 21; + table[21 * 256 + 210] = 21; + table[20 * 256 + 211] = 21; + table[21 * 256 + 211] = 21; + table[20 * 256 + 212] = 21; + table[21 * 256 + 212] = 21; + table[20 * 256 + 213] = 21; + table[21 * 256 + 213] = 21; + table[20 * 256 + 214] = 21; + table[21 * 256 + 214] = 21; + table[20 * 256 + 215] = 21; + table[21 * 256 + 215] = 21; + table[20 * 256 + 216] = 21; + table[21 * 256 + 216] = 21; + table[20 * 256 + 217] = 21; + table[21 * 256 + 217] = 21; + table[20 * 256 + 218] = 21; + table[21 * 256 + 218] = 21; + table[20 * 256 + 219] = 21; + table[21 * 256 + 219] = 21; + table[20 * 256 + 220] = 21; + table[21 * 256 + 220] = 21; + table[20 * 256 + 221] = 21; + table[21 * 256 + 221] = 21; + table[20 * 256 + 222] = 21; + table[21 * 256 + 222] = 21; + table[20 * 256 + 223] = 21; + table[21 * 256 + 223] = 21; + table[20 * 256 + 224] = 21; + table[21 * 256 + 224] = 21; + table[20 * 256 + 225] = 21; + table[21 * 256 + 225] = 21; + table[20 * 256 + 226] = 21; + table[21 * 256 + 226] = 21; + table[20 * 256 + 227] = 21; + table[21 * 256 + 227] = 21; + table[20 * 256 + 228] = 21; + table[21 * 256 + 228] = 21; + table[20 * 256 + 229] = 21; + table[21 * 256 + 229] = 21; + table[20 * 256 + 230] = 21; + table[21 * 256 + 230] = 21; + table[20 * 256 + 231] = 21; + table[21 * 256 + 231] = 21; + table[20 * 256 + 232] = 21; + table[21 * 256 + 232] = 21; + table[20 * 256 + 233] = 21; + table[21 * 256 + 233] = 21; + table[20 * 256 + 234] = 21; + table[21 * 256 + 234] = 21; + table[20 * 256 + 235] = 21; + table[21 * 256 + 235] = 21; + table[20 * 256 + 236] = 21; + table[21 * 256 + 236] = 21; + table[20 * 256 + 237] = 21; + table[21 * 256 + 237] = 21; + table[20 * 256 + 238] = 21; + table[21 * 256 + 238] = 21; + table[20 * 256 + 239] = 21; + table[21 * 256 + 239] = 21; + table[20 * 256 + 240] = 21; + table[21 * 256 + 240] = 21; + table[20 * 256 + 241] = 21; + table[21 * 256 + 241] = 21; + table[20 * 256 + 242] = 21; + table[21 * 256 + 242] = 21; + table[20 * 256 + 243] = 21; + table[21 * 256 + 243] = 21; + table[20 * 256 + 244] = 21; + table[21 * 256 + 244] = 21; + table[20 * 256 + 245] = 21; + table[21 * 256 + 245] = 21; + table[20 * 256 + 246] = 21; + table[21 * 256 + 246] = 21; + table[20 * 256 + 247] = 21; + table[21 * 256 + 247] = 21; + table[20 * 256 + 248] = 21; + table[21 * 256 + 248] = 21; + table[20 * 256 + 249] = 21; + table[21 * 256 + 249] = 21; + table[20 * 256 + 250] = 21; + table[21 * 256 + 250] = 21; + table[20 * 256 + 251] = 21; + table[21 * 256 + 251] = 21; + table[20 * 256 + 252] = 21; + table[21 * 256 + 252] = 21; + table[20 * 256 + 253] = 21; + table[21 * 256 + 253] = 21; + table[20 * 256 + 254] = 21; + table[21 * 256 + 254] = 21; + table[0 * 256 + 13] = 1; + table[0 * 256 + 255] = 2; + table[1 * 256 + 10] = 2; + table[2 * 256 + 115] = 3; + table[3 * 256 + 117] = 4; + table[4 * 256 + 98] = 5; + table[5 * 256 + 106] = 6; + table[6 * 256 + 101] = 7; + table[7 * 256 + 99] = 8; + table[8 * 256 + 116] = 9; + table[9 * 256 + 58] = 10; + table[10 * 256 + 0] = 11; + table[10 * 256 + 1] = 11; + table[10 * 256 + 2] = 11; + table[10 * 256 + 3] = 11; + table[10 * 256 + 4] = 11; + table[10 * 256 + 5] = 11; + table[10 * 256 + 6] = 11; + table[10 * 256 + 7] = 11; + table[10 * 256 + 8] = 11; + table[10 * 256 + 9] = 11; + table[10 * 256 + 11] = 11; + table[10 * 256 + 12] = 11; + table[10 * 256 + 14] = 11; + table[10 * 256 + 15] = 11; + table[10 * 256 + 16] = 11; + table[10 * 256 + 17] = 11; + table[10 * 256 + 18] = 11; + table[10 * 256 + 19] = 11; + table[10 * 256 + 20] = 11; + table[10 * 256 + 21] = 11; + table[10 * 256 + 22] = 11; + table[10 * 256 + 23] = 11; + table[10 * 256 + 24] = 11; + table[10 * 256 + 25] = 11; + table[10 * 256 + 26] = 11; + table[10 * 256 + 27] = 11; + table[10 * 256 + 28] = 11; + table[10 * 256 + 29] = 11; + table[10 * 256 + 30] = 11; + table[10 * 256 + 31] = 11; + table[10 * 256 + 32] = 11; + table[10 * 256 + 33] = 11; + table[10 * 256 + 34] = 11; + table[10 * 256 + 35] = 11; + table[10 * 256 + 36] = 11; + table[10 * 256 + 37] = 11; + table[10 * 256 + 38] = 11; + table[10 * 256 + 39] = 11; + table[10 * 256 + 40] = 11; + table[10 * 256 + 41] = 11; + table[10 * 256 + 42] = 11; + table[10 * 256 + 43] = 11; + table[10 * 256 + 44] = 11; + table[10 * 256 + 45] = 11; + table[10 * 256 + 46] = 11; + table[10 * 256 + 47] = 11; + table[10 * 256 + 48] = 11; + table[10 * 256 + 49] = 11; + table[10 * 256 + 50] = 11; + table[10 * 256 + 51] = 11; + table[10 * 256 + 52] = 11; + table[10 * 256 + 53] = 11; + table[10 * 256 + 54] = 11; + table[10 * 256 + 55] = 11; + table[10 * 256 + 56] = 11; + table[10 * 256 + 57] = 11; + table[10 * 256 + 58] = 11; + table[10 * 256 + 59] = 11; + table[10 * 256 + 60] = 11; + table[10 * 256 + 61] = 11; + table[10 * 256 + 62] = 11; + table[10 * 256 + 63] = 11; + table[10 * 256 + 64] = 11; + table[10 * 256 + 65] = 11; + table[10 * 256 + 66] = 11; + table[10 * 256 + 67] = 11; + table[10 * 256 + 68] = 11; + table[10 * 256 + 69] = 11; + table[10 * 256 + 70] = 11; + table[10 * 256 + 71] = 11; + table[10 * 256 + 72] = 11; + table[10 * 256 + 73] = 11; + table[10 * 256 + 74] = 11; + table[10 * 256 + 75] = 11; + table[10 * 256 + 76] = 11; + table[10 * 256 + 77] = 11; + table[10 * 256 + 78] = 11; + table[10 * 256 + 79] = 11; + table[10 * 256 + 80] = 11; + table[10 * 256 + 81] = 11; + table[10 * 256 + 82] = 11; + table[10 * 256 + 83] = 11; + table[10 * 256 + 84] = 11; + table[10 * 256 + 85] = 11; + table[10 * 256 + 86] = 11; + table[10 * 256 + 87] = 11; + table[10 * 256 + 88] = 11; + table[10 * 256 + 89] = 11; + table[10 * 256 + 90] = 11; + table[10 * 256 + 91] = 11; + table[10 * 256 + 92] = 11; + table[10 * 256 + 93] = 11; + table[10 * 256 + 94] = 11; + table[10 * 256 + 95] = 11; + table[10 * 256 + 96] = 11; + table[10 * 256 + 97] = 11; + table[10 * 256 + 98] = 11; + table[10 * 256 + 99] = 11; + table[10 * 256 + 100] = 11; + table[10 * 256 + 101] = 11; + table[10 * 256 + 102] = 11; + table[10 * 256 + 103] = 11; + table[10 * 256 + 104] = 11; + table[10 * 256 + 105] = 11; + table[10 * 256 + 106] = 11; + table[10 * 256 + 107] = 11; + table[10 * 256 + 108] = 11; + table[10 * 256 + 109] = 11; + table[10 * 256 + 110] = 11; + table[10 * 256 + 111] = 11; + table[10 * 256 + 112] = 11; + table[10 * 256 + 113] = 11; + table[10 * 256 + 114] = 11; + table[10 * 256 + 115] = 11; + table[10 * 256 + 116] = 11; + table[10 * 256 + 117] = 11; + table[10 * 256 + 118] = 11; + table[10 * 256 + 119] = 11; + table[10 * 256 + 120] = 11; + table[10 * 256 + 121] = 11; + table[10 * 256 + 122] = 11; + table[10 * 256 + 123] = 11; + table[10 * 256 + 124] = 11; + table[10 * 256 + 125] = 11; + table[10 * 256 + 126] = 11; + table[10 * 256 + 127] = 11; + table[10 * 256 + 194] = 12; + table[10 * 256 + 195] = 12; + table[10 * 256 + 196] = 12; + table[10 * 256 + 197] = 12; + table[10 * 256 + 198] = 12; + table[10 * 256 + 199] = 12; + table[10 * 256 + 200] = 12; + table[10 * 256 + 201] = 12; + table[10 * 256 + 202] = 12; + table[10 * 256 + 203] = 12; + table[10 * 256 + 204] = 12; + table[10 * 256 + 205] = 12; + table[10 * 256 + 206] = 12; + table[10 * 256 + 207] = 12; + table[10 * 256 + 208] = 12; + table[10 * 256 + 209] = 12; + table[10 * 256 + 210] = 12; + table[10 * 256 + 211] = 12; + table[10 * 256 + 212] = 12; + table[10 * 256 + 213] = 12; + table[10 * 256 + 214] = 12; + table[10 * 256 + 215] = 12; + table[10 * 256 + 216] = 12; + table[10 * 256 + 217] = 12; + table[10 * 256 + 218] = 12; + table[10 * 256 + 219] = 12; + table[10 * 256 + 220] = 12; + table[10 * 256 + 221] = 12; + table[10 * 256 + 222] = 12; + table[10 * 256 + 223] = 12; + table[10 * 256 + 224] = 13; + table[10 * 256 + 225] = 14; + table[10 * 256 + 226] = 14; + table[10 * 256 + 227] = 14; + table[10 * 256 + 228] = 14; + table[10 * 256 + 229] = 14; + table[10 * 256 + 230] = 14; + table[10 * 256 + 231] = 14; + table[10 * 256 + 232] = 14; + table[10 * 256 + 233] = 14; + table[10 * 256 + 234] = 14; + table[10 * 256 + 235] = 14; + table[10 * 256 + 236] = 14; + table[10 * 256 + 238] = 14; + table[10 * 256 + 239] = 14; + table[10 * 256 + 237] = 15; + table[10 * 256 + 240] = 16; + table[10 * 256 + 241] = 17; + table[10 * 256 + 242] = 17; + table[10 * 256 + 243] = 17; + table[10 * 256 + 244] = 18; + table[11 * 256 + 0] = 11; + table[11 * 256 + 1] = 11; + table[11 * 256 + 2] = 11; + table[11 * 256 + 3] = 11; + table[11 * 256 + 4] = 11; + table[11 * 256 + 5] = 11; + table[11 * 256 + 6] = 11; + table[11 * 256 + 7] = 11; + table[11 * 256 + 8] = 11; + table[11 * 256 + 9] = 11; + table[11 * 256 + 11] = 11; + table[11 * 256 + 12] = 11; + table[11 * 256 + 14] = 11; + table[11 * 256 + 15] = 11; + table[11 * 256 + 16] = 11; + table[11 * 256 + 17] = 11; + table[11 * 256 + 18] = 11; + table[11 * 256 + 19] = 11; + table[11 * 256 + 20] = 11; + table[11 * 256 + 21] = 11; + table[11 * 256 + 22] = 11; + table[11 * 256 + 23] = 11; + table[11 * 256 + 24] = 11; + table[11 * 256 + 25] = 11; + table[11 * 256 + 26] = 11; + table[11 * 256 + 27] = 11; + table[11 * 256 + 28] = 11; + table[11 * 256 + 29] = 11; + table[11 * 256 + 30] = 11; + table[11 * 256 + 31] = 11; + table[11 * 256 + 32] = 11; + table[11 * 256 + 33] = 11; + table[11 * 256 + 34] = 11; + table[11 * 256 + 35] = 11; + table[11 * 256 + 36] = 11; + table[11 * 256 + 37] = 11; + table[11 * 256 + 38] = 11; + table[11 * 256 + 39] = 11; + table[11 * 256 + 40] = 11; + table[11 * 256 + 41] = 11; + table[11 * 256 + 42] = 11; + table[11 * 256 + 43] = 11; + table[11 * 256 + 44] = 11; + table[11 * 256 + 45] = 11; + table[11 * 256 + 46] = 11; + table[11 * 256 + 47] = 11; + table[11 * 256 + 48] = 11; + table[11 * 256 + 49] = 11; + table[11 * 256 + 50] = 11; + table[11 * 256 + 51] = 11; + table[11 * 256 + 52] = 11; + table[11 * 256 + 53] = 11; + table[11 * 256 + 54] = 11; + table[11 * 256 + 55] = 11; + table[11 * 256 + 56] = 11; + table[11 * 256 + 57] = 11; + table[11 * 256 + 58] = 11; + table[11 * 256 + 59] = 11; + table[11 * 256 + 60] = 11; + table[11 * 256 + 61] = 11; + table[11 * 256 + 62] = 11; + table[11 * 256 + 63] = 11; + table[11 * 256 + 64] = 11; + table[11 * 256 + 65] = 11; + table[11 * 256 + 66] = 11; + table[11 * 256 + 67] = 11; + table[11 * 256 + 68] = 11; + table[11 * 256 + 69] = 11; + table[11 * 256 + 70] = 11; + table[11 * 256 + 71] = 11; + table[11 * 256 + 72] = 11; + table[11 * 256 + 73] = 11; + table[11 * 256 + 74] = 11; + table[11 * 256 + 75] = 11; + table[11 * 256 + 76] = 11; + table[11 * 256 + 77] = 11; + table[11 * 256 + 78] = 11; + table[11 * 256 + 79] = 11; + table[11 * 256 + 80] = 11; + table[11 * 256 + 81] = 11; + table[11 * 256 + 82] = 11; + table[11 * 256 + 83] = 11; + table[11 * 256 + 84] = 11; + table[11 * 256 + 85] = 11; + table[11 * 256 + 86] = 11; + table[11 * 256 + 87] = 11; + table[11 * 256 + 88] = 11; + table[11 * 256 + 89] = 11; + table[11 * 256 + 90] = 11; + table[11 * 256 + 91] = 11; + table[11 * 256 + 92] = 11; + table[11 * 256 + 93] = 11; + table[11 * 256 + 94] = 11; + table[11 * 256 + 95] = 11; + table[11 * 256 + 96] = 11; + table[11 * 256 + 97] = 11; + table[11 * 256 + 98] = 11; + table[11 * 256 + 99] = 11; + table[11 * 256 + 100] = 11; + table[11 * 256 + 101] = 11; + table[11 * 256 + 102] = 11; + table[11 * 256 + 103] = 11; + table[11 * 256 + 104] = 11; + table[11 * 256 + 105] = 11; + table[11 * 256 + 106] = 11; + table[11 * 256 + 107] = 11; + table[11 * 256 + 108] = 11; + table[11 * 256 + 109] = 11; + table[11 * 256 + 110] = 11; + table[11 * 256 + 111] = 11; + table[11 * 256 + 112] = 11; + table[11 * 256 + 113] = 11; + table[11 * 256 + 114] = 11; + table[11 * 256 + 115] = 11; + table[11 * 256 + 116] = 11; + table[11 * 256 + 117] = 11; + table[11 * 256 + 118] = 11; + table[11 * 256 + 119] = 11; + table[11 * 256 + 120] = 11; + table[11 * 256 + 121] = 11; + table[11 * 256 + 122] = 11; + table[11 * 256 + 123] = 11; + table[11 * 256 + 124] = 11; + table[11 * 256 + 125] = 11; + table[11 * 256 + 126] = 11; + table[11 * 256 + 127] = 11; + table[11 * 256 + 194] = 12; + table[11 * 256 + 195] = 12; + table[11 * 256 + 196] = 12; + table[11 * 256 + 197] = 12; + table[11 * 256 + 198] = 12; + table[11 * 256 + 199] = 12; + table[11 * 256 + 200] = 12; + table[11 * 256 + 201] = 12; + table[11 * 256 + 202] = 12; + table[11 * 256 + 203] = 12; + table[11 * 256 + 204] = 12; + table[11 * 256 + 205] = 12; + table[11 * 256 + 206] = 12; + table[11 * 256 + 207] = 12; + table[11 * 256 + 208] = 12; + table[11 * 256 + 209] = 12; + table[11 * 256 + 210] = 12; + table[11 * 256 + 211] = 12; + table[11 * 256 + 212] = 12; + table[11 * 256 + 213] = 12; + table[11 * 256 + 214] = 12; + table[11 * 256 + 215] = 12; + table[11 * 256 + 216] = 12; + table[11 * 256 + 217] = 12; + table[11 * 256 + 218] = 12; + table[11 * 256 + 219] = 12; + table[11 * 256 + 220] = 12; + table[11 * 256 + 221] = 12; + table[11 * 256 + 222] = 12; + table[11 * 256 + 223] = 12; + table[11 * 256 + 224] = 13; + table[11 * 256 + 225] = 14; + table[11 * 256 + 226] = 14; + table[11 * 256 + 227] = 14; + table[11 * 256 + 228] = 14; + table[11 * 256 + 229] = 14; + table[11 * 256 + 230] = 14; + table[11 * 256 + 231] = 14; + table[11 * 256 + 232] = 14; + table[11 * 256 + 233] = 14; + table[11 * 256 + 234] = 14; + table[11 * 256 + 235] = 14; + table[11 * 256 + 236] = 14; + table[11 * 256 + 238] = 14; + table[11 * 256 + 239] = 14; + table[11 * 256 + 237] = 15; + table[11 * 256 + 240] = 16; + table[11 * 256 + 241] = 17; + table[11 * 256 + 242] = 17; + table[11 * 256 + 243] = 17; + table[11 * 256 + 244] = 18; + table[11 * 256 + 13] = 19; + table[12 * 256 + 128] = 11; + table[12 * 256 + 129] = 11; + table[12 * 256 + 130] = 11; + table[12 * 256 + 131] = 11; + table[12 * 256 + 132] = 11; + table[12 * 256 + 133] = 11; + table[12 * 256 + 134] = 11; + table[12 * 256 + 135] = 11; + table[12 * 256 + 136] = 11; + table[12 * 256 + 137] = 11; + table[12 * 256 + 138] = 11; + table[12 * 256 + 139] = 11; + table[12 * 256 + 140] = 11; + table[12 * 256 + 141] = 11; + table[12 * 256 + 142] = 11; + table[12 * 256 + 143] = 11; + table[12 * 256 + 144] = 11; + table[12 * 256 + 145] = 11; + table[12 * 256 + 146] = 11; + table[12 * 256 + 147] = 11; + table[12 * 256 + 148] = 11; + table[12 * 256 + 149] = 11; + table[12 * 256 + 150] = 11; + table[12 * 256 + 151] = 11; + table[12 * 256 + 152] = 11; + table[12 * 256 + 153] = 11; + table[12 * 256 + 154] = 11; + table[12 * 256 + 155] = 11; + table[12 * 256 + 156] = 11; + table[12 * 256 + 157] = 11; + table[12 * 256 + 158] = 11; + table[12 * 256 + 159] = 11; + table[12 * 256 + 160] = 11; + table[12 * 256 + 161] = 11; + table[12 * 256 + 162] = 11; + table[12 * 256 + 163] = 11; + table[12 * 256 + 164] = 11; + table[12 * 256 + 165] = 11; + table[12 * 256 + 166] = 11; + table[12 * 256 + 167] = 11; + table[12 * 256 + 168] = 11; + table[12 * 256 + 169] = 11; + table[12 * 256 + 170] = 11; + table[12 * 256 + 171] = 11; + table[12 * 256 + 172] = 11; + table[12 * 256 + 173] = 11; + table[12 * 256 + 174] = 11; + table[12 * 256 + 175] = 11; + table[12 * 256 + 176] = 11; + table[12 * 256 + 177] = 11; + table[12 * 256 + 178] = 11; + table[12 * 256 + 179] = 11; + table[12 * 256 + 180] = 11; + table[12 * 256 + 181] = 11; + table[12 * 256 + 182] = 11; + table[12 * 256 + 183] = 11; + table[12 * 256 + 184] = 11; + table[12 * 256 + 185] = 11; + table[12 * 256 + 186] = 11; + table[12 * 256 + 187] = 11; + table[12 * 256 + 188] = 11; + table[12 * 256 + 189] = 11; + table[12 * 256 + 190] = 11; + table[12 * 256 + 191] = 11; + table[13 * 256 + 160] = 12; + table[13 * 256 + 161] = 12; + table[13 * 256 + 162] = 12; + table[13 * 256 + 163] = 12; + table[13 * 256 + 164] = 12; + table[13 * 256 + 165] = 12; + table[13 * 256 + 166] = 12; + table[13 * 256 + 167] = 12; + table[13 * 256 + 168] = 12; + table[13 * 256 + 169] = 12; + table[13 * 256 + 170] = 12; + table[13 * 256 + 171] = 12; + table[13 * 256 + 172] = 12; + table[13 * 256 + 173] = 12; + table[13 * 256 + 174] = 12; + table[13 * 256 + 175] = 12; + table[13 * 256 + 176] = 12; + table[13 * 256 + 177] = 12; + table[13 * 256 + 178] = 12; + table[13 * 256 + 179] = 12; + table[13 * 256 + 180] = 12; + table[13 * 256 + 181] = 12; + table[13 * 256 + 182] = 12; + table[13 * 256 + 183] = 12; + table[13 * 256 + 184] = 12; + table[13 * 256 + 185] = 12; + table[13 * 256 + 186] = 12; + table[13 * 256 + 187] = 12; + table[13 * 256 + 188] = 12; + table[13 * 256 + 189] = 12; + table[13 * 256 + 190] = 12; + table[13 * 256 + 191] = 12; + table[14 * 256 + 128] = 12; + table[14 * 256 + 129] = 12; + table[14 * 256 + 130] = 12; + table[14 * 256 + 131] = 12; + table[14 * 256 + 132] = 12; + table[14 * 256 + 133] = 12; + table[14 * 256 + 134] = 12; + table[14 * 256 + 135] = 12; + table[14 * 256 + 136] = 12; + table[14 * 256 + 137] = 12; + table[14 * 256 + 138] = 12; + table[14 * 256 + 139] = 12; + table[14 * 256 + 140] = 12; + table[14 * 256 + 141] = 12; + table[14 * 256 + 142] = 12; + table[14 * 256 + 143] = 12; + table[14 * 256 + 144] = 12; + table[14 * 256 + 145] = 12; + table[14 * 256 + 146] = 12; + table[14 * 256 + 147] = 12; + table[14 * 256 + 148] = 12; + table[14 * 256 + 149] = 12; + table[14 * 256 + 150] = 12; + table[14 * 256 + 151] = 12; + table[14 * 256 + 152] = 12; + table[14 * 256 + 153] = 12; + table[14 * 256 + 154] = 12; + table[14 * 256 + 155] = 12; + table[14 * 256 + 156] = 12; + table[14 * 256 + 157] = 12; + table[14 * 256 + 158] = 12; + table[14 * 256 + 159] = 12; + table[14 * 256 + 160] = 12; + table[14 * 256 + 161] = 12; + table[14 * 256 + 162] = 12; + table[14 * 256 + 163] = 12; + table[14 * 256 + 164] = 12; + table[14 * 256 + 165] = 12; + table[14 * 256 + 166] = 12; + table[14 * 256 + 167] = 12; + table[14 * 256 + 168] = 12; + table[14 * 256 + 169] = 12; + table[14 * 256 + 170] = 12; + table[14 * 256 + 171] = 12; + table[14 * 256 + 172] = 12; + table[14 * 256 + 173] = 12; + table[14 * 256 + 174] = 12; + table[14 * 256 + 175] = 12; + table[14 * 256 + 176] = 12; + table[14 * 256 + 177] = 12; + table[14 * 256 + 178] = 12; + table[14 * 256 + 179] = 12; + table[14 * 256 + 180] = 12; + table[14 * 256 + 181] = 12; + table[14 * 256 + 182] = 12; + table[14 * 256 + 183] = 12; + table[14 * 256 + 184] = 12; + table[14 * 256 + 185] = 12; + table[14 * 256 + 186] = 12; + table[14 * 256 + 187] = 12; + table[14 * 256 + 188] = 12; + table[14 * 256 + 189] = 12; + table[14 * 256 + 190] = 12; + table[14 * 256 + 191] = 12; + table[15 * 256 + 128] = 12; + table[15 * 256 + 129] = 12; + table[15 * 256 + 130] = 12; + table[15 * 256 + 131] = 12; + table[15 * 256 + 132] = 12; + table[15 * 256 + 133] = 12; + table[15 * 256 + 134] = 12; + table[15 * 256 + 135] = 12; + table[15 * 256 + 136] = 12; + table[15 * 256 + 137] = 12; + table[15 * 256 + 138] = 12; + table[15 * 256 + 139] = 12; + table[15 * 256 + 140] = 12; + table[15 * 256 + 141] = 12; + table[15 * 256 + 142] = 12; + table[15 * 256 + 143] = 12; + table[15 * 256 + 144] = 12; + table[15 * 256 + 145] = 12; + table[15 * 256 + 146] = 12; + table[15 * 256 + 147] = 12; + table[15 * 256 + 148] = 12; + table[15 * 256 + 149] = 12; + table[15 * 256 + 150] = 12; + table[15 * 256 + 151] = 12; + table[15 * 256 + 152] = 12; + table[15 * 256 + 153] = 12; + table[15 * 256 + 154] = 12; + table[15 * 256 + 155] = 12; + table[15 * 256 + 156] = 12; + table[15 * 256 + 157] = 12; + table[15 * 256 + 158] = 12; + table[15 * 256 + 159] = 12; + table[16 * 256 + 144] = 14; + table[16 * 256 + 145] = 14; + table[16 * 256 + 146] = 14; + table[16 * 256 + 147] = 14; + table[16 * 256 + 148] = 14; + table[16 * 256 + 149] = 14; + table[16 * 256 + 150] = 14; + table[16 * 256 + 151] = 14; + table[16 * 256 + 152] = 14; + table[16 * 256 + 153] = 14; + table[16 * 256 + 154] = 14; + table[16 * 256 + 155] = 14; + table[16 * 256 + 156] = 14; + table[16 * 256 + 157] = 14; + table[16 * 256 + 158] = 14; + table[16 * 256 + 159] = 14; + table[16 * 256 + 160] = 14; + table[16 * 256 + 161] = 14; + table[16 * 256 + 162] = 14; + table[16 * 256 + 163] = 14; + table[16 * 256 + 164] = 14; + table[16 * 256 + 165] = 14; + table[16 * 256 + 166] = 14; + table[16 * 256 + 167] = 14; + table[16 * 256 + 168] = 14; + table[16 * 256 + 169] = 14; + table[16 * 256 + 170] = 14; + table[16 * 256 + 171] = 14; + table[16 * 256 + 172] = 14; + table[16 * 256 + 173] = 14; + table[16 * 256 + 174] = 14; + table[16 * 256 + 175] = 14; + table[16 * 256 + 176] = 14; + table[16 * 256 + 177] = 14; + table[16 * 256 + 178] = 14; + table[16 * 256 + 179] = 14; + table[16 * 256 + 180] = 14; + table[16 * 256 + 181] = 14; + table[16 * 256 + 182] = 14; + table[16 * 256 + 183] = 14; + table[16 * 256 + 184] = 14; + table[16 * 256 + 185] = 14; + table[16 * 256 + 186] = 14; + table[16 * 256 + 187] = 14; + table[16 * 256 + 188] = 14; + table[16 * 256 + 189] = 14; + table[16 * 256 + 190] = 14; + table[16 * 256 + 191] = 14; + table[17 * 256 + 128] = 14; + table[17 * 256 + 129] = 14; + table[17 * 256 + 130] = 14; + table[17 * 256 + 131] = 14; + table[17 * 256 + 132] = 14; + table[17 * 256 + 133] = 14; + table[17 * 256 + 134] = 14; + table[17 * 256 + 135] = 14; + table[17 * 256 + 136] = 14; + table[17 * 256 + 137] = 14; + table[17 * 256 + 138] = 14; + table[17 * 256 + 139] = 14; + table[17 * 256 + 140] = 14; + table[17 * 256 + 141] = 14; + table[17 * 256 + 142] = 14; + table[17 * 256 + 143] = 14; + table[17 * 256 + 144] = 14; + table[17 * 256 + 145] = 14; + table[17 * 256 + 146] = 14; + table[17 * 256 + 147] = 14; + table[17 * 256 + 148] = 14; + table[17 * 256 + 149] = 14; + table[17 * 256 + 150] = 14; + table[17 * 256 + 151] = 14; + table[17 * 256 + 152] = 14; + table[17 * 256 + 153] = 14; + table[17 * 256 + 154] = 14; + table[17 * 256 + 155] = 14; + table[17 * 256 + 156] = 14; + table[17 * 256 + 157] = 14; + table[17 * 256 + 158] = 14; + table[17 * 256 + 159] = 14; + table[17 * 256 + 160] = 14; + table[17 * 256 + 161] = 14; + table[17 * 256 + 162] = 14; + table[17 * 256 + 163] = 14; + table[17 * 256 + 164] = 14; + table[17 * 256 + 165] = 14; + table[17 * 256 + 166] = 14; + table[17 * 256 + 167] = 14; + table[17 * 256 + 168] = 14; + table[17 * 256 + 169] = 14; + table[17 * 256 + 170] = 14; + table[17 * 256 + 171] = 14; + table[17 * 256 + 172] = 14; + table[17 * 256 + 173] = 14; + table[17 * 256 + 174] = 14; + table[17 * 256 + 175] = 14; + table[17 * 256 + 176] = 14; + table[17 * 256 + 177] = 14; + table[17 * 256 + 178] = 14; + table[17 * 256 + 179] = 14; + table[17 * 256 + 180] = 14; + table[17 * 256 + 181] = 14; + table[17 * 256 + 182] = 14; + table[17 * 256 + 183] = 14; + table[17 * 256 + 184] = 14; + table[17 * 256 + 185] = 14; + table[17 * 256 + 186] = 14; + table[17 * 256 + 187] = 14; + table[17 * 256 + 188] = 14; + table[17 * 256 + 189] = 14; + table[17 * 256 + 190] = 14; + table[17 * 256 + 191] = 14; + table[18 * 256 + 128] = 14; + table[18 * 256 + 129] = 14; + table[18 * 256 + 130] = 14; + table[18 * 256 + 131] = 14; + table[18 * 256 + 132] = 14; + table[18 * 256 + 133] = 14; + table[18 * 256 + 134] = 14; + table[18 * 256 + 135] = 14; + table[18 * 256 + 136] = 14; + table[18 * 256 + 137] = 14; + table[18 * 256 + 138] = 14; + table[18 * 256 + 139] = 14; + table[18 * 256 + 140] = 14; + table[18 * 256 + 141] = 14; + table[18 * 256 + 142] = 14; + table[18 * 256 + 143] = 14; + table[19 * 256 + 10] = 20; + + table +} +pub fn regex_match(input: [u8; N]) -> bool { + // regex: (\r\n|^)subject:[^\r\n]+\r\n + let mut s = 0; + s = table[255]; + for i in 0..input.len() { + let s_idx = s * 256 + input[i] as Field; + std::as_witness(s_idx); + s = table[s_idx]; + } + + let matched: bool = (s == 20) | (s == 21); + + matched +} + + \ No newline at end of file diff --git a/packages/noir/src/basic/timestamp.nr b/packages/noir/src/basic/timestamp.nr new file mode 100644 index 00000000..eff1eb02 --- /dev/null +++ b/packages/noir/src/basic/timestamp.nr @@ -0,0 +1,1528 @@ + +use crate::common::Sequence; + + +global table: [Field; 8960] = comptime { make_lookup_table() }; + +comptime fn make_lookup_table() -> [Field; 8960] { + let mut table = [0; 8960]; + table[33 * 256 + 0] = 34; + table[34 * 256 + 0] = 34; + table[33 * 256 + 1] = 34; + table[34 * 256 + 1] = 34; + table[33 * 256 + 2] = 34; + table[34 * 256 + 2] = 34; + table[33 * 256 + 3] = 34; + table[34 * 256 + 3] = 34; + table[33 * 256 + 4] = 34; + table[34 * 256 + 4] = 34; + table[33 * 256 + 5] = 34; + table[34 * 256 + 5] = 34; + table[33 * 256 + 6] = 34; + table[34 * 256 + 6] = 34; + table[33 * 256 + 7] = 34; + table[34 * 256 + 7] = 34; + table[33 * 256 + 8] = 34; + table[34 * 256 + 8] = 34; + table[33 * 256 + 9] = 34; + table[34 * 256 + 9] = 34; + table[33 * 256 + 10] = 34; + table[34 * 256 + 10] = 34; + table[33 * 256 + 11] = 34; + table[34 * 256 + 11] = 34; + table[33 * 256 + 12] = 34; + table[34 * 256 + 12] = 34; + table[33 * 256 + 13] = 34; + table[34 * 256 + 13] = 34; + table[33 * 256 + 14] = 34; + table[34 * 256 + 14] = 34; + table[33 * 256 + 15] = 34; + table[34 * 256 + 15] = 34; + table[33 * 256 + 16] = 34; + table[34 * 256 + 16] = 34; + table[33 * 256 + 17] = 34; + table[34 * 256 + 17] = 34; + table[33 * 256 + 18] = 34; + table[34 * 256 + 18] = 34; + table[33 * 256 + 19] = 34; + table[34 * 256 + 19] = 34; + table[33 * 256 + 20] = 34; + table[34 * 256 + 20] = 34; + table[33 * 256 + 21] = 34; + table[34 * 256 + 21] = 34; + table[33 * 256 + 22] = 34; + table[34 * 256 + 22] = 34; + table[33 * 256 + 23] = 34; + table[34 * 256 + 23] = 34; + table[33 * 256 + 24] = 34; + table[34 * 256 + 24] = 34; + table[33 * 256 + 25] = 34; + table[34 * 256 + 25] = 34; + table[33 * 256 + 26] = 34; + table[34 * 256 + 26] = 34; + table[33 * 256 + 27] = 34; + table[34 * 256 + 27] = 34; + table[33 * 256 + 28] = 34; + table[34 * 256 + 28] = 34; + table[33 * 256 + 29] = 34; + table[34 * 256 + 29] = 34; + table[33 * 256 + 30] = 34; + table[34 * 256 + 30] = 34; + table[33 * 256 + 31] = 34; + table[34 * 256 + 31] = 34; + table[33 * 256 + 32] = 34; + table[34 * 256 + 32] = 34; + table[33 * 256 + 33] = 34; + table[34 * 256 + 33] = 34; + table[33 * 256 + 34] = 34; + table[34 * 256 + 34] = 34; + table[33 * 256 + 35] = 34; + table[34 * 256 + 35] = 34; + table[33 * 256 + 36] = 34; + table[34 * 256 + 36] = 34; + table[33 * 256 + 37] = 34; + table[34 * 256 + 37] = 34; + table[33 * 256 + 38] = 34; + table[34 * 256 + 38] = 34; + table[33 * 256 + 39] = 34; + table[34 * 256 + 39] = 34; + table[33 * 256 + 40] = 34; + table[34 * 256 + 40] = 34; + table[33 * 256 + 41] = 34; + table[34 * 256 + 41] = 34; + table[33 * 256 + 42] = 34; + table[34 * 256 + 42] = 34; + table[33 * 256 + 43] = 34; + table[34 * 256 + 43] = 34; + table[33 * 256 + 44] = 34; + table[34 * 256 + 44] = 34; + table[33 * 256 + 45] = 34; + table[34 * 256 + 45] = 34; + table[33 * 256 + 46] = 34; + table[34 * 256 + 46] = 34; + table[33 * 256 + 47] = 34; + table[34 * 256 + 47] = 34; + table[33 * 256 + 48] = 34; + table[34 * 256 + 48] = 34; + table[33 * 256 + 49] = 34; + table[34 * 256 + 49] = 34; + table[33 * 256 + 50] = 34; + table[34 * 256 + 50] = 34; + table[33 * 256 + 51] = 34; + table[34 * 256 + 51] = 34; + table[33 * 256 + 52] = 34; + table[34 * 256 + 52] = 34; + table[33 * 256 + 53] = 34; + table[34 * 256 + 53] = 34; + table[33 * 256 + 54] = 34; + table[34 * 256 + 54] = 34; + table[33 * 256 + 55] = 34; + table[34 * 256 + 55] = 34; + table[33 * 256 + 56] = 34; + table[34 * 256 + 56] = 34; + table[33 * 256 + 57] = 34; + table[34 * 256 + 57] = 34; + table[33 * 256 + 58] = 34; + table[34 * 256 + 58] = 34; + table[33 * 256 + 59] = 34; + table[34 * 256 + 59] = 34; + table[33 * 256 + 60] = 34; + table[34 * 256 + 60] = 34; + table[33 * 256 + 61] = 34; + table[34 * 256 + 61] = 34; + table[33 * 256 + 62] = 34; + table[34 * 256 + 62] = 34; + table[33 * 256 + 63] = 34; + table[34 * 256 + 63] = 34; + table[33 * 256 + 64] = 34; + table[34 * 256 + 64] = 34; + table[33 * 256 + 65] = 34; + table[34 * 256 + 65] = 34; + table[33 * 256 + 66] = 34; + table[34 * 256 + 66] = 34; + table[33 * 256 + 67] = 34; + table[34 * 256 + 67] = 34; + table[33 * 256 + 68] = 34; + table[34 * 256 + 68] = 34; + table[33 * 256 + 69] = 34; + table[34 * 256 + 69] = 34; + table[33 * 256 + 70] = 34; + table[34 * 256 + 70] = 34; + table[33 * 256 + 71] = 34; + table[34 * 256 + 71] = 34; + table[33 * 256 + 72] = 34; + table[34 * 256 + 72] = 34; + table[33 * 256 + 73] = 34; + table[34 * 256 + 73] = 34; + table[33 * 256 + 74] = 34; + table[34 * 256 + 74] = 34; + table[33 * 256 + 75] = 34; + table[34 * 256 + 75] = 34; + table[33 * 256 + 76] = 34; + table[34 * 256 + 76] = 34; + table[33 * 256 + 77] = 34; + table[34 * 256 + 77] = 34; + table[33 * 256 + 78] = 34; + table[34 * 256 + 78] = 34; + table[33 * 256 + 79] = 34; + table[34 * 256 + 79] = 34; + table[33 * 256 + 80] = 34; + table[34 * 256 + 80] = 34; + table[33 * 256 + 81] = 34; + table[34 * 256 + 81] = 34; + table[33 * 256 + 82] = 34; + table[34 * 256 + 82] = 34; + table[33 * 256 + 83] = 34; + table[34 * 256 + 83] = 34; + table[33 * 256 + 84] = 34; + table[34 * 256 + 84] = 34; + table[33 * 256 + 85] = 34; + table[34 * 256 + 85] = 34; + table[33 * 256 + 86] = 34; + table[34 * 256 + 86] = 34; + table[33 * 256 + 87] = 34; + table[34 * 256 + 87] = 34; + table[33 * 256 + 88] = 34; + table[34 * 256 + 88] = 34; + table[33 * 256 + 89] = 34; + table[34 * 256 + 89] = 34; + table[33 * 256 + 90] = 34; + table[34 * 256 + 90] = 34; + table[33 * 256 + 91] = 34; + table[34 * 256 + 91] = 34; + table[33 * 256 + 92] = 34; + table[34 * 256 + 92] = 34; + table[33 * 256 + 93] = 34; + table[34 * 256 + 93] = 34; + table[33 * 256 + 94] = 34; + table[34 * 256 + 94] = 34; + table[33 * 256 + 95] = 34; + table[34 * 256 + 95] = 34; + table[33 * 256 + 96] = 34; + table[34 * 256 + 96] = 34; + table[33 * 256 + 97] = 34; + table[34 * 256 + 97] = 34; + table[33 * 256 + 98] = 34; + table[34 * 256 + 98] = 34; + table[33 * 256 + 99] = 34; + table[34 * 256 + 99] = 34; + table[33 * 256 + 100] = 34; + table[34 * 256 + 100] = 34; + table[33 * 256 + 101] = 34; + table[34 * 256 + 101] = 34; + table[33 * 256 + 102] = 34; + table[34 * 256 + 102] = 34; + table[33 * 256 + 103] = 34; + table[34 * 256 + 103] = 34; + table[33 * 256 + 104] = 34; + table[34 * 256 + 104] = 34; + table[33 * 256 + 105] = 34; + table[34 * 256 + 105] = 34; + table[33 * 256 + 106] = 34; + table[34 * 256 + 106] = 34; + table[33 * 256 + 107] = 34; + table[34 * 256 + 107] = 34; + table[33 * 256 + 108] = 34; + table[34 * 256 + 108] = 34; + table[33 * 256 + 109] = 34; + table[34 * 256 + 109] = 34; + table[33 * 256 + 110] = 34; + table[34 * 256 + 110] = 34; + table[33 * 256 + 111] = 34; + table[34 * 256 + 111] = 34; + table[33 * 256 + 112] = 34; + table[34 * 256 + 112] = 34; + table[33 * 256 + 113] = 34; + table[34 * 256 + 113] = 34; + table[33 * 256 + 114] = 34; + table[34 * 256 + 114] = 34; + table[33 * 256 + 115] = 34; + table[34 * 256 + 115] = 34; + table[33 * 256 + 116] = 34; + table[34 * 256 + 116] = 34; + table[33 * 256 + 117] = 34; + table[34 * 256 + 117] = 34; + table[33 * 256 + 118] = 34; + table[34 * 256 + 118] = 34; + table[33 * 256 + 119] = 34; + table[34 * 256 + 119] = 34; + table[33 * 256 + 120] = 34; + table[34 * 256 + 120] = 34; + table[33 * 256 + 121] = 34; + table[34 * 256 + 121] = 34; + table[33 * 256 + 122] = 34; + table[34 * 256 + 122] = 34; + table[33 * 256 + 123] = 34; + table[34 * 256 + 123] = 34; + table[33 * 256 + 124] = 34; + table[34 * 256 + 124] = 34; + table[33 * 256 + 125] = 34; + table[34 * 256 + 125] = 34; + table[33 * 256 + 126] = 34; + table[34 * 256 + 126] = 34; + table[33 * 256 + 127] = 34; + table[34 * 256 + 127] = 34; + table[33 * 256 + 128] = 34; + table[34 * 256 + 128] = 34; + table[33 * 256 + 129] = 34; + table[34 * 256 + 129] = 34; + table[33 * 256 + 130] = 34; + table[34 * 256 + 130] = 34; + table[33 * 256 + 131] = 34; + table[34 * 256 + 131] = 34; + table[33 * 256 + 132] = 34; + table[34 * 256 + 132] = 34; + table[33 * 256 + 133] = 34; + table[34 * 256 + 133] = 34; + table[33 * 256 + 134] = 34; + table[34 * 256 + 134] = 34; + table[33 * 256 + 135] = 34; + table[34 * 256 + 135] = 34; + table[33 * 256 + 136] = 34; + table[34 * 256 + 136] = 34; + table[33 * 256 + 137] = 34; + table[34 * 256 + 137] = 34; + table[33 * 256 + 138] = 34; + table[34 * 256 + 138] = 34; + table[33 * 256 + 139] = 34; + table[34 * 256 + 139] = 34; + table[33 * 256 + 140] = 34; + table[34 * 256 + 140] = 34; + table[33 * 256 + 141] = 34; + table[34 * 256 + 141] = 34; + table[33 * 256 + 142] = 34; + table[34 * 256 + 142] = 34; + table[33 * 256 + 143] = 34; + table[34 * 256 + 143] = 34; + table[33 * 256 + 144] = 34; + table[34 * 256 + 144] = 34; + table[33 * 256 + 145] = 34; + table[34 * 256 + 145] = 34; + table[33 * 256 + 146] = 34; + table[34 * 256 + 146] = 34; + table[33 * 256 + 147] = 34; + table[34 * 256 + 147] = 34; + table[33 * 256 + 148] = 34; + table[34 * 256 + 148] = 34; + table[33 * 256 + 149] = 34; + table[34 * 256 + 149] = 34; + table[33 * 256 + 150] = 34; + table[34 * 256 + 150] = 34; + table[33 * 256 + 151] = 34; + table[34 * 256 + 151] = 34; + table[33 * 256 + 152] = 34; + table[34 * 256 + 152] = 34; + table[33 * 256 + 153] = 34; + table[34 * 256 + 153] = 34; + table[33 * 256 + 154] = 34; + table[34 * 256 + 154] = 34; + table[33 * 256 + 155] = 34; + table[34 * 256 + 155] = 34; + table[33 * 256 + 156] = 34; + table[34 * 256 + 156] = 34; + table[33 * 256 + 157] = 34; + table[34 * 256 + 157] = 34; + table[33 * 256 + 158] = 34; + table[34 * 256 + 158] = 34; + table[33 * 256 + 159] = 34; + table[34 * 256 + 159] = 34; + table[33 * 256 + 160] = 34; + table[34 * 256 + 160] = 34; + table[33 * 256 + 161] = 34; + table[34 * 256 + 161] = 34; + table[33 * 256 + 162] = 34; + table[34 * 256 + 162] = 34; + table[33 * 256 + 163] = 34; + table[34 * 256 + 163] = 34; + table[33 * 256 + 164] = 34; + table[34 * 256 + 164] = 34; + table[33 * 256 + 165] = 34; + table[34 * 256 + 165] = 34; + table[33 * 256 + 166] = 34; + table[34 * 256 + 166] = 34; + table[33 * 256 + 167] = 34; + table[34 * 256 + 167] = 34; + table[33 * 256 + 168] = 34; + table[34 * 256 + 168] = 34; + table[33 * 256 + 169] = 34; + table[34 * 256 + 169] = 34; + table[33 * 256 + 170] = 34; + table[34 * 256 + 170] = 34; + table[33 * 256 + 171] = 34; + table[34 * 256 + 171] = 34; + table[33 * 256 + 172] = 34; + table[34 * 256 + 172] = 34; + table[33 * 256 + 173] = 34; + table[34 * 256 + 173] = 34; + table[33 * 256 + 174] = 34; + table[34 * 256 + 174] = 34; + table[33 * 256 + 175] = 34; + table[34 * 256 + 175] = 34; + table[33 * 256 + 176] = 34; + table[34 * 256 + 176] = 34; + table[33 * 256 + 177] = 34; + table[34 * 256 + 177] = 34; + table[33 * 256 + 178] = 34; + table[34 * 256 + 178] = 34; + table[33 * 256 + 179] = 34; + table[34 * 256 + 179] = 34; + table[33 * 256 + 180] = 34; + table[34 * 256 + 180] = 34; + table[33 * 256 + 181] = 34; + table[34 * 256 + 181] = 34; + table[33 * 256 + 182] = 34; + table[34 * 256 + 182] = 34; + table[33 * 256 + 183] = 34; + table[34 * 256 + 183] = 34; + table[33 * 256 + 184] = 34; + table[34 * 256 + 184] = 34; + table[33 * 256 + 185] = 34; + table[34 * 256 + 185] = 34; + table[33 * 256 + 186] = 34; + table[34 * 256 + 186] = 34; + table[33 * 256 + 187] = 34; + table[34 * 256 + 187] = 34; + table[33 * 256 + 188] = 34; + table[34 * 256 + 188] = 34; + table[33 * 256 + 189] = 34; + table[34 * 256 + 189] = 34; + table[33 * 256 + 190] = 34; + table[34 * 256 + 190] = 34; + table[33 * 256 + 191] = 34; + table[34 * 256 + 191] = 34; + table[33 * 256 + 192] = 34; + table[34 * 256 + 192] = 34; + table[33 * 256 + 193] = 34; + table[34 * 256 + 193] = 34; + table[33 * 256 + 194] = 34; + table[34 * 256 + 194] = 34; + table[33 * 256 + 195] = 34; + table[34 * 256 + 195] = 34; + table[33 * 256 + 196] = 34; + table[34 * 256 + 196] = 34; + table[33 * 256 + 197] = 34; + table[34 * 256 + 197] = 34; + table[33 * 256 + 198] = 34; + table[34 * 256 + 198] = 34; + table[33 * 256 + 199] = 34; + table[34 * 256 + 199] = 34; + table[33 * 256 + 200] = 34; + table[34 * 256 + 200] = 34; + table[33 * 256 + 201] = 34; + table[34 * 256 + 201] = 34; + table[33 * 256 + 202] = 34; + table[34 * 256 + 202] = 34; + table[33 * 256 + 203] = 34; + table[34 * 256 + 203] = 34; + table[33 * 256 + 204] = 34; + table[34 * 256 + 204] = 34; + table[33 * 256 + 205] = 34; + table[34 * 256 + 205] = 34; + table[33 * 256 + 206] = 34; + table[34 * 256 + 206] = 34; + table[33 * 256 + 207] = 34; + table[34 * 256 + 207] = 34; + table[33 * 256 + 208] = 34; + table[34 * 256 + 208] = 34; + table[33 * 256 + 209] = 34; + table[34 * 256 + 209] = 34; + table[33 * 256 + 210] = 34; + table[34 * 256 + 210] = 34; + table[33 * 256 + 211] = 34; + table[34 * 256 + 211] = 34; + table[33 * 256 + 212] = 34; + table[34 * 256 + 212] = 34; + table[33 * 256 + 213] = 34; + table[34 * 256 + 213] = 34; + table[33 * 256 + 214] = 34; + table[34 * 256 + 214] = 34; + table[33 * 256 + 215] = 34; + table[34 * 256 + 215] = 34; + table[33 * 256 + 216] = 34; + table[34 * 256 + 216] = 34; + table[33 * 256 + 217] = 34; + table[34 * 256 + 217] = 34; + table[33 * 256 + 218] = 34; + table[34 * 256 + 218] = 34; + table[33 * 256 + 219] = 34; + table[34 * 256 + 219] = 34; + table[33 * 256 + 220] = 34; + table[34 * 256 + 220] = 34; + table[33 * 256 + 221] = 34; + table[34 * 256 + 221] = 34; + table[33 * 256 + 222] = 34; + table[34 * 256 + 222] = 34; + table[33 * 256 + 223] = 34; + table[34 * 256 + 223] = 34; + table[33 * 256 + 224] = 34; + table[34 * 256 + 224] = 34; + table[33 * 256 + 225] = 34; + table[34 * 256 + 225] = 34; + table[33 * 256 + 226] = 34; + table[34 * 256 + 226] = 34; + table[33 * 256 + 227] = 34; + table[34 * 256 + 227] = 34; + table[33 * 256 + 228] = 34; + table[34 * 256 + 228] = 34; + table[33 * 256 + 229] = 34; + table[34 * 256 + 229] = 34; + table[33 * 256 + 230] = 34; + table[34 * 256 + 230] = 34; + table[33 * 256 + 231] = 34; + table[34 * 256 + 231] = 34; + table[33 * 256 + 232] = 34; + table[34 * 256 + 232] = 34; + table[33 * 256 + 233] = 34; + table[34 * 256 + 233] = 34; + table[33 * 256 + 234] = 34; + table[34 * 256 + 234] = 34; + table[33 * 256 + 235] = 34; + table[34 * 256 + 235] = 34; + table[33 * 256 + 236] = 34; + table[34 * 256 + 236] = 34; + table[33 * 256 + 237] = 34; + table[34 * 256 + 237] = 34; + table[33 * 256 + 238] = 34; + table[34 * 256 + 238] = 34; + table[33 * 256 + 239] = 34; + table[34 * 256 + 239] = 34; + table[33 * 256 + 240] = 34; + table[34 * 256 + 240] = 34; + table[33 * 256 + 241] = 34; + table[34 * 256 + 241] = 34; + table[33 * 256 + 242] = 34; + table[34 * 256 + 242] = 34; + table[33 * 256 + 243] = 34; + table[34 * 256 + 243] = 34; + table[33 * 256 + 244] = 34; + table[34 * 256 + 244] = 34; + table[33 * 256 + 245] = 34; + table[34 * 256 + 245] = 34; + table[33 * 256 + 246] = 34; + table[34 * 256 + 246] = 34; + table[33 * 256 + 247] = 34; + table[34 * 256 + 247] = 34; + table[33 * 256 + 248] = 34; + table[34 * 256 + 248] = 34; + table[33 * 256 + 249] = 34; + table[34 * 256 + 249] = 34; + table[33 * 256 + 250] = 34; + table[34 * 256 + 250] = 34; + table[33 * 256 + 251] = 34; + table[34 * 256 + 251] = 34; + table[33 * 256 + 252] = 34; + table[34 * 256 + 252] = 34; + table[33 * 256 + 253] = 34; + table[34 * 256 + 253] = 34; + table[33 * 256 + 254] = 34; + table[34 * 256 + 254] = 34; + table[0 * 256 + 13] = 1; + table[0 * 256 + 255] = 2; + table[1 * 256 + 10] = 2; + table[2 * 256 + 100] = 3; + table[3 * 256 + 107] = 4; + table[4 * 256 + 105] = 5; + table[5 * 256 + 109] = 6; + table[6 * 256 + 45] = 7; + table[7 * 256 + 115] = 8; + table[8 * 256 + 105] = 9; + table[9 * 256 + 103] = 10; + table[10 * 256 + 110] = 11; + table[11 * 256 + 97] = 12; + table[12 * 256 + 116] = 13; + table[13 * 256 + 117] = 14; + table[14 * 256 + 114] = 15; + table[15 * 256 + 101] = 16; + table[16 * 256 + 58] = 17; + table[17 * 256 + 97] = 18; + table[17 * 256 + 98] = 18; + table[17 * 256 + 99] = 18; + table[17 * 256 + 100] = 18; + table[17 * 256 + 101] = 18; + table[17 * 256 + 102] = 18; + table[17 * 256 + 103] = 18; + table[17 * 256 + 104] = 18; + table[17 * 256 + 105] = 18; + table[17 * 256 + 106] = 18; + table[17 * 256 + 107] = 18; + table[17 * 256 + 108] = 18; + table[17 * 256 + 109] = 18; + table[17 * 256 + 110] = 18; + table[17 * 256 + 111] = 18; + table[17 * 256 + 112] = 18; + table[17 * 256 + 113] = 18; + table[17 * 256 + 114] = 18; + table[17 * 256 + 115] = 18; + table[17 * 256 + 116] = 18; + table[17 * 256 + 117] = 18; + table[17 * 256 + 118] = 18; + table[17 * 256 + 119] = 18; + table[17 * 256 + 120] = 18; + table[17 * 256 + 121] = 18; + table[17 * 256 + 122] = 18; + table[18 * 256 + 97] = 18; + table[18 * 256 + 98] = 18; + table[18 * 256 + 99] = 18; + table[18 * 256 + 100] = 18; + table[18 * 256 + 101] = 18; + table[18 * 256 + 102] = 18; + table[18 * 256 + 103] = 18; + table[18 * 256 + 104] = 18; + table[18 * 256 + 105] = 18; + table[18 * 256 + 106] = 18; + table[18 * 256 + 107] = 18; + table[18 * 256 + 108] = 18; + table[18 * 256 + 109] = 18; + table[18 * 256 + 110] = 18; + table[18 * 256 + 111] = 18; + table[18 * 256 + 112] = 18; + table[18 * 256 + 113] = 18; + table[18 * 256 + 114] = 18; + table[18 * 256 + 115] = 18; + table[18 * 256 + 116] = 18; + table[18 * 256 + 117] = 18; + table[18 * 256 + 118] = 18; + table[18 * 256 + 119] = 18; + table[18 * 256 + 120] = 18; + table[18 * 256 + 121] = 18; + table[18 * 256 + 122] = 18; + table[18 * 256 + 61] = 19; + table[19 * 256 + 0] = 20; + table[19 * 256 + 1] = 20; + table[19 * 256 + 2] = 20; + table[19 * 256 + 3] = 20; + table[19 * 256 + 4] = 20; + table[19 * 256 + 5] = 20; + table[19 * 256 + 6] = 20; + table[19 * 256 + 7] = 20; + table[19 * 256 + 8] = 20; + table[19 * 256 + 9] = 20; + table[19 * 256 + 10] = 20; + table[19 * 256 + 11] = 20; + table[19 * 256 + 12] = 20; + table[19 * 256 + 13] = 20; + table[19 * 256 + 14] = 20; + table[19 * 256 + 15] = 20; + table[19 * 256 + 16] = 20; + table[19 * 256 + 17] = 20; + table[19 * 256 + 18] = 20; + table[19 * 256 + 19] = 20; + table[19 * 256 + 20] = 20; + table[19 * 256 + 21] = 20; + table[19 * 256 + 22] = 20; + table[19 * 256 + 23] = 20; + table[19 * 256 + 24] = 20; + table[19 * 256 + 25] = 20; + table[19 * 256 + 26] = 20; + table[19 * 256 + 27] = 20; + table[19 * 256 + 28] = 20; + table[19 * 256 + 29] = 20; + table[19 * 256 + 30] = 20; + table[19 * 256 + 31] = 20; + table[19 * 256 + 32] = 20; + table[19 * 256 + 33] = 20; + table[19 * 256 + 34] = 20; + table[19 * 256 + 35] = 20; + table[19 * 256 + 36] = 20; + table[19 * 256 + 37] = 20; + table[19 * 256 + 38] = 20; + table[19 * 256 + 39] = 20; + table[19 * 256 + 40] = 20; + table[19 * 256 + 41] = 20; + table[19 * 256 + 42] = 20; + table[19 * 256 + 43] = 20; + table[19 * 256 + 44] = 20; + table[19 * 256 + 45] = 20; + table[19 * 256 + 46] = 20; + table[19 * 256 + 47] = 20; + table[19 * 256 + 48] = 20; + table[19 * 256 + 49] = 20; + table[19 * 256 + 50] = 20; + table[19 * 256 + 51] = 20; + table[19 * 256 + 52] = 20; + table[19 * 256 + 53] = 20; + table[19 * 256 + 54] = 20; + table[19 * 256 + 55] = 20; + table[19 * 256 + 56] = 20; + table[19 * 256 + 57] = 20; + table[19 * 256 + 58] = 20; + table[19 * 256 + 60] = 20; + table[19 * 256 + 61] = 20; + table[19 * 256 + 62] = 20; + table[19 * 256 + 63] = 20; + table[19 * 256 + 64] = 20; + table[19 * 256 + 65] = 20; + table[19 * 256 + 66] = 20; + table[19 * 256 + 67] = 20; + table[19 * 256 + 68] = 20; + table[19 * 256 + 69] = 20; + table[19 * 256 + 70] = 20; + table[19 * 256 + 71] = 20; + table[19 * 256 + 72] = 20; + table[19 * 256 + 73] = 20; + table[19 * 256 + 74] = 20; + table[19 * 256 + 75] = 20; + table[19 * 256 + 76] = 20; + table[19 * 256 + 77] = 20; + table[19 * 256 + 78] = 20; + table[19 * 256 + 79] = 20; + table[19 * 256 + 80] = 20; + table[19 * 256 + 81] = 20; + table[19 * 256 + 82] = 20; + table[19 * 256 + 83] = 20; + table[19 * 256 + 84] = 20; + table[19 * 256 + 85] = 20; + table[19 * 256 + 86] = 20; + table[19 * 256 + 87] = 20; + table[19 * 256 + 88] = 20; + table[19 * 256 + 89] = 20; + table[19 * 256 + 90] = 20; + table[19 * 256 + 91] = 20; + table[19 * 256 + 92] = 20; + table[19 * 256 + 93] = 20; + table[19 * 256 + 94] = 20; + table[19 * 256 + 95] = 20; + table[19 * 256 + 96] = 20; + table[19 * 256 + 97] = 20; + table[19 * 256 + 98] = 20; + table[19 * 256 + 99] = 20; + table[19 * 256 + 100] = 20; + table[19 * 256 + 101] = 20; + table[19 * 256 + 102] = 20; + table[19 * 256 + 103] = 20; + table[19 * 256 + 104] = 20; + table[19 * 256 + 105] = 20; + table[19 * 256 + 106] = 20; + table[19 * 256 + 107] = 20; + table[19 * 256 + 108] = 20; + table[19 * 256 + 109] = 20; + table[19 * 256 + 110] = 20; + table[19 * 256 + 111] = 20; + table[19 * 256 + 112] = 20; + table[19 * 256 + 113] = 20; + table[19 * 256 + 114] = 20; + table[19 * 256 + 115] = 20; + table[19 * 256 + 116] = 20; + table[19 * 256 + 117] = 20; + table[19 * 256 + 118] = 20; + table[19 * 256 + 119] = 20; + table[19 * 256 + 120] = 20; + table[19 * 256 + 121] = 20; + table[19 * 256 + 122] = 20; + table[19 * 256 + 123] = 20; + table[19 * 256 + 124] = 20; + table[19 * 256 + 125] = 20; + table[19 * 256 + 126] = 20; + table[19 * 256 + 127] = 20; + table[19 * 256 + 194] = 21; + table[19 * 256 + 195] = 21; + table[19 * 256 + 196] = 21; + table[19 * 256 + 197] = 21; + table[19 * 256 + 198] = 21; + table[19 * 256 + 199] = 21; + table[19 * 256 + 200] = 21; + table[19 * 256 + 201] = 21; + table[19 * 256 + 202] = 21; + table[19 * 256 + 203] = 21; + table[19 * 256 + 204] = 21; + table[19 * 256 + 205] = 21; + table[19 * 256 + 206] = 21; + table[19 * 256 + 207] = 21; + table[19 * 256 + 208] = 21; + table[19 * 256 + 209] = 21; + table[19 * 256 + 210] = 21; + table[19 * 256 + 211] = 21; + table[19 * 256 + 212] = 21; + table[19 * 256 + 213] = 21; + table[19 * 256 + 214] = 21; + table[19 * 256 + 215] = 21; + table[19 * 256 + 216] = 21; + table[19 * 256 + 217] = 21; + table[19 * 256 + 218] = 21; + table[19 * 256 + 219] = 21; + table[19 * 256 + 220] = 21; + table[19 * 256 + 221] = 21; + table[19 * 256 + 222] = 21; + table[19 * 256 + 223] = 21; + table[19 * 256 + 224] = 22; + table[19 * 256 + 225] = 23; + table[19 * 256 + 226] = 23; + table[19 * 256 + 227] = 23; + table[19 * 256 + 228] = 23; + table[19 * 256 + 229] = 23; + table[19 * 256 + 230] = 23; + table[19 * 256 + 231] = 23; + table[19 * 256 + 232] = 23; + table[19 * 256 + 233] = 23; + table[19 * 256 + 234] = 23; + table[19 * 256 + 235] = 23; + table[19 * 256 + 236] = 23; + table[19 * 256 + 238] = 23; + table[19 * 256 + 239] = 23; + table[19 * 256 + 237] = 24; + table[19 * 256 + 240] = 25; + table[19 * 256 + 241] = 26; + table[19 * 256 + 242] = 26; + table[19 * 256 + 243] = 26; + table[19 * 256 + 244] = 27; + table[20 * 256 + 0] = 20; + table[20 * 256 + 1] = 20; + table[20 * 256 + 2] = 20; + table[20 * 256 + 3] = 20; + table[20 * 256 + 4] = 20; + table[20 * 256 + 5] = 20; + table[20 * 256 + 6] = 20; + table[20 * 256 + 7] = 20; + table[20 * 256 + 8] = 20; + table[20 * 256 + 9] = 20; + table[20 * 256 + 10] = 20; + table[20 * 256 + 11] = 20; + table[20 * 256 + 12] = 20; + table[20 * 256 + 13] = 20; + table[20 * 256 + 14] = 20; + table[20 * 256 + 15] = 20; + table[20 * 256 + 16] = 20; + table[20 * 256 + 17] = 20; + table[20 * 256 + 18] = 20; + table[20 * 256 + 19] = 20; + table[20 * 256 + 20] = 20; + table[20 * 256 + 21] = 20; + table[20 * 256 + 22] = 20; + table[20 * 256 + 23] = 20; + table[20 * 256 + 24] = 20; + table[20 * 256 + 25] = 20; + table[20 * 256 + 26] = 20; + table[20 * 256 + 27] = 20; + table[20 * 256 + 28] = 20; + table[20 * 256 + 29] = 20; + table[20 * 256 + 30] = 20; + table[20 * 256 + 31] = 20; + table[20 * 256 + 32] = 20; + table[20 * 256 + 33] = 20; + table[20 * 256 + 34] = 20; + table[20 * 256 + 35] = 20; + table[20 * 256 + 36] = 20; + table[20 * 256 + 37] = 20; + table[20 * 256 + 38] = 20; + table[20 * 256 + 39] = 20; + table[20 * 256 + 40] = 20; + table[20 * 256 + 41] = 20; + table[20 * 256 + 42] = 20; + table[20 * 256 + 43] = 20; + table[20 * 256 + 44] = 20; + table[20 * 256 + 45] = 20; + table[20 * 256 + 46] = 20; + table[20 * 256 + 47] = 20; + table[20 * 256 + 48] = 20; + table[20 * 256 + 49] = 20; + table[20 * 256 + 50] = 20; + table[20 * 256 + 51] = 20; + table[20 * 256 + 52] = 20; + table[20 * 256 + 53] = 20; + table[20 * 256 + 54] = 20; + table[20 * 256 + 55] = 20; + table[20 * 256 + 56] = 20; + table[20 * 256 + 57] = 20; + table[20 * 256 + 58] = 20; + table[20 * 256 + 60] = 20; + table[20 * 256 + 61] = 20; + table[20 * 256 + 62] = 20; + table[20 * 256 + 63] = 20; + table[20 * 256 + 64] = 20; + table[20 * 256 + 65] = 20; + table[20 * 256 + 66] = 20; + table[20 * 256 + 67] = 20; + table[20 * 256 + 68] = 20; + table[20 * 256 + 69] = 20; + table[20 * 256 + 70] = 20; + table[20 * 256 + 71] = 20; + table[20 * 256 + 72] = 20; + table[20 * 256 + 73] = 20; + table[20 * 256 + 74] = 20; + table[20 * 256 + 75] = 20; + table[20 * 256 + 76] = 20; + table[20 * 256 + 77] = 20; + table[20 * 256 + 78] = 20; + table[20 * 256 + 79] = 20; + table[20 * 256 + 80] = 20; + table[20 * 256 + 81] = 20; + table[20 * 256 + 82] = 20; + table[20 * 256 + 83] = 20; + table[20 * 256 + 84] = 20; + table[20 * 256 + 85] = 20; + table[20 * 256 + 86] = 20; + table[20 * 256 + 87] = 20; + table[20 * 256 + 88] = 20; + table[20 * 256 + 89] = 20; + table[20 * 256 + 90] = 20; + table[20 * 256 + 91] = 20; + table[20 * 256 + 92] = 20; + table[20 * 256 + 93] = 20; + table[20 * 256 + 94] = 20; + table[20 * 256 + 95] = 20; + table[20 * 256 + 96] = 20; + table[20 * 256 + 97] = 20; + table[20 * 256 + 98] = 20; + table[20 * 256 + 99] = 20; + table[20 * 256 + 100] = 20; + table[20 * 256 + 101] = 20; + table[20 * 256 + 102] = 20; + table[20 * 256 + 103] = 20; + table[20 * 256 + 104] = 20; + table[20 * 256 + 105] = 20; + table[20 * 256 + 106] = 20; + table[20 * 256 + 107] = 20; + table[20 * 256 + 108] = 20; + table[20 * 256 + 109] = 20; + table[20 * 256 + 110] = 20; + table[20 * 256 + 111] = 20; + table[20 * 256 + 112] = 20; + table[20 * 256 + 113] = 20; + table[20 * 256 + 114] = 20; + table[20 * 256 + 115] = 20; + table[20 * 256 + 116] = 20; + table[20 * 256 + 117] = 20; + table[20 * 256 + 118] = 20; + table[20 * 256 + 119] = 20; + table[20 * 256 + 120] = 20; + table[20 * 256 + 121] = 20; + table[20 * 256 + 122] = 20; + table[20 * 256 + 123] = 20; + table[20 * 256 + 124] = 20; + table[20 * 256 + 125] = 20; + table[20 * 256 + 126] = 20; + table[20 * 256 + 127] = 20; + table[20 * 256 + 194] = 21; + table[20 * 256 + 195] = 21; + table[20 * 256 + 196] = 21; + table[20 * 256 + 197] = 21; + table[20 * 256 + 198] = 21; + table[20 * 256 + 199] = 21; + table[20 * 256 + 200] = 21; + table[20 * 256 + 201] = 21; + table[20 * 256 + 202] = 21; + table[20 * 256 + 203] = 21; + table[20 * 256 + 204] = 21; + table[20 * 256 + 205] = 21; + table[20 * 256 + 206] = 21; + table[20 * 256 + 207] = 21; + table[20 * 256 + 208] = 21; + table[20 * 256 + 209] = 21; + table[20 * 256 + 210] = 21; + table[20 * 256 + 211] = 21; + table[20 * 256 + 212] = 21; + table[20 * 256 + 213] = 21; + table[20 * 256 + 214] = 21; + table[20 * 256 + 215] = 21; + table[20 * 256 + 216] = 21; + table[20 * 256 + 217] = 21; + table[20 * 256 + 218] = 21; + table[20 * 256 + 219] = 21; + table[20 * 256 + 220] = 21; + table[20 * 256 + 221] = 21; + table[20 * 256 + 222] = 21; + table[20 * 256 + 223] = 21; + table[20 * 256 + 224] = 22; + table[20 * 256 + 225] = 23; + table[20 * 256 + 226] = 23; + table[20 * 256 + 227] = 23; + table[20 * 256 + 228] = 23; + table[20 * 256 + 229] = 23; + table[20 * 256 + 230] = 23; + table[20 * 256 + 231] = 23; + table[20 * 256 + 232] = 23; + table[20 * 256 + 233] = 23; + table[20 * 256 + 234] = 23; + table[20 * 256 + 235] = 23; + table[20 * 256 + 236] = 23; + table[20 * 256 + 238] = 23; + table[20 * 256 + 239] = 23; + table[20 * 256 + 237] = 24; + table[20 * 256 + 240] = 25; + table[20 * 256 + 241] = 26; + table[20 * 256 + 242] = 26; + table[20 * 256 + 243] = 26; + table[20 * 256 + 244] = 27; + table[20 * 256 + 59] = 28; + table[21 * 256 + 128] = 20; + table[21 * 256 + 129] = 20; + table[21 * 256 + 130] = 20; + table[21 * 256 + 131] = 20; + table[21 * 256 + 132] = 20; + table[21 * 256 + 133] = 20; + table[21 * 256 + 134] = 20; + table[21 * 256 + 135] = 20; + table[21 * 256 + 136] = 20; + table[21 * 256 + 137] = 20; + table[21 * 256 + 138] = 20; + table[21 * 256 + 139] = 20; + table[21 * 256 + 140] = 20; + table[21 * 256 + 141] = 20; + table[21 * 256 + 142] = 20; + table[21 * 256 + 143] = 20; + table[21 * 256 + 144] = 20; + table[21 * 256 + 145] = 20; + table[21 * 256 + 146] = 20; + table[21 * 256 + 147] = 20; + table[21 * 256 + 148] = 20; + table[21 * 256 + 149] = 20; + table[21 * 256 + 150] = 20; + table[21 * 256 + 151] = 20; + table[21 * 256 + 152] = 20; + table[21 * 256 + 153] = 20; + table[21 * 256 + 154] = 20; + table[21 * 256 + 155] = 20; + table[21 * 256 + 156] = 20; + table[21 * 256 + 157] = 20; + table[21 * 256 + 158] = 20; + table[21 * 256 + 159] = 20; + table[21 * 256 + 160] = 20; + table[21 * 256 + 161] = 20; + table[21 * 256 + 162] = 20; + table[21 * 256 + 163] = 20; + table[21 * 256 + 164] = 20; + table[21 * 256 + 165] = 20; + table[21 * 256 + 166] = 20; + table[21 * 256 + 167] = 20; + table[21 * 256 + 168] = 20; + table[21 * 256 + 169] = 20; + table[21 * 256 + 170] = 20; + table[21 * 256 + 171] = 20; + table[21 * 256 + 172] = 20; + table[21 * 256 + 173] = 20; + table[21 * 256 + 174] = 20; + table[21 * 256 + 175] = 20; + table[21 * 256 + 176] = 20; + table[21 * 256 + 177] = 20; + table[21 * 256 + 178] = 20; + table[21 * 256 + 179] = 20; + table[21 * 256 + 180] = 20; + table[21 * 256 + 181] = 20; + table[21 * 256 + 182] = 20; + table[21 * 256 + 183] = 20; + table[21 * 256 + 184] = 20; + table[21 * 256 + 185] = 20; + table[21 * 256 + 186] = 20; + table[21 * 256 + 187] = 20; + table[21 * 256 + 188] = 20; + table[21 * 256 + 189] = 20; + table[21 * 256 + 190] = 20; + table[21 * 256 + 191] = 20; + table[22 * 256 + 160] = 21; + table[22 * 256 + 161] = 21; + table[22 * 256 + 162] = 21; + table[22 * 256 + 163] = 21; + table[22 * 256 + 164] = 21; + table[22 * 256 + 165] = 21; + table[22 * 256 + 166] = 21; + table[22 * 256 + 167] = 21; + table[22 * 256 + 168] = 21; + table[22 * 256 + 169] = 21; + table[22 * 256 + 170] = 21; + table[22 * 256 + 171] = 21; + table[22 * 256 + 172] = 21; + table[22 * 256 + 173] = 21; + table[22 * 256 + 174] = 21; + table[22 * 256 + 175] = 21; + table[22 * 256 + 176] = 21; + table[22 * 256 + 177] = 21; + table[22 * 256 + 178] = 21; + table[22 * 256 + 179] = 21; + table[22 * 256 + 180] = 21; + table[22 * 256 + 181] = 21; + table[22 * 256 + 182] = 21; + table[22 * 256 + 183] = 21; + table[22 * 256 + 184] = 21; + table[22 * 256 + 185] = 21; + table[22 * 256 + 186] = 21; + table[22 * 256 + 187] = 21; + table[22 * 256 + 188] = 21; + table[22 * 256 + 189] = 21; + table[22 * 256 + 190] = 21; + table[22 * 256 + 191] = 21; + table[23 * 256 + 128] = 21; + table[23 * 256 + 129] = 21; + table[23 * 256 + 130] = 21; + table[23 * 256 + 131] = 21; + table[23 * 256 + 132] = 21; + table[23 * 256 + 133] = 21; + table[23 * 256 + 134] = 21; + table[23 * 256 + 135] = 21; + table[23 * 256 + 136] = 21; + table[23 * 256 + 137] = 21; + table[23 * 256 + 138] = 21; + table[23 * 256 + 139] = 21; + table[23 * 256 + 140] = 21; + table[23 * 256 + 141] = 21; + table[23 * 256 + 142] = 21; + table[23 * 256 + 143] = 21; + table[23 * 256 + 144] = 21; + table[23 * 256 + 145] = 21; + table[23 * 256 + 146] = 21; + table[23 * 256 + 147] = 21; + table[23 * 256 + 148] = 21; + table[23 * 256 + 149] = 21; + table[23 * 256 + 150] = 21; + table[23 * 256 + 151] = 21; + table[23 * 256 + 152] = 21; + table[23 * 256 + 153] = 21; + table[23 * 256 + 154] = 21; + table[23 * 256 + 155] = 21; + table[23 * 256 + 156] = 21; + table[23 * 256 + 157] = 21; + table[23 * 256 + 158] = 21; + table[23 * 256 + 159] = 21; + table[23 * 256 + 160] = 21; + table[23 * 256 + 161] = 21; + table[23 * 256 + 162] = 21; + table[23 * 256 + 163] = 21; + table[23 * 256 + 164] = 21; + table[23 * 256 + 165] = 21; + table[23 * 256 + 166] = 21; + table[23 * 256 + 167] = 21; + table[23 * 256 + 168] = 21; + table[23 * 256 + 169] = 21; + table[23 * 256 + 170] = 21; + table[23 * 256 + 171] = 21; + table[23 * 256 + 172] = 21; + table[23 * 256 + 173] = 21; + table[23 * 256 + 174] = 21; + table[23 * 256 + 175] = 21; + table[23 * 256 + 176] = 21; + table[23 * 256 + 177] = 21; + table[23 * 256 + 178] = 21; + table[23 * 256 + 179] = 21; + table[23 * 256 + 180] = 21; + table[23 * 256 + 181] = 21; + table[23 * 256 + 182] = 21; + table[23 * 256 + 183] = 21; + table[23 * 256 + 184] = 21; + table[23 * 256 + 185] = 21; + table[23 * 256 + 186] = 21; + table[23 * 256 + 187] = 21; + table[23 * 256 + 188] = 21; + table[23 * 256 + 189] = 21; + table[23 * 256 + 190] = 21; + table[23 * 256 + 191] = 21; + table[24 * 256 + 128] = 21; + table[24 * 256 + 129] = 21; + table[24 * 256 + 130] = 21; + table[24 * 256 + 131] = 21; + table[24 * 256 + 132] = 21; + table[24 * 256 + 133] = 21; + table[24 * 256 + 134] = 21; + table[24 * 256 + 135] = 21; + table[24 * 256 + 136] = 21; + table[24 * 256 + 137] = 21; + table[24 * 256 + 138] = 21; + table[24 * 256 + 139] = 21; + table[24 * 256 + 140] = 21; + table[24 * 256 + 141] = 21; + table[24 * 256 + 142] = 21; + table[24 * 256 + 143] = 21; + table[24 * 256 + 144] = 21; + table[24 * 256 + 145] = 21; + table[24 * 256 + 146] = 21; + table[24 * 256 + 147] = 21; + table[24 * 256 + 148] = 21; + table[24 * 256 + 149] = 21; + table[24 * 256 + 150] = 21; + table[24 * 256 + 151] = 21; + table[24 * 256 + 152] = 21; + table[24 * 256 + 153] = 21; + table[24 * 256 + 154] = 21; + table[24 * 256 + 155] = 21; + table[24 * 256 + 156] = 21; + table[24 * 256 + 157] = 21; + table[24 * 256 + 158] = 21; + table[24 * 256 + 159] = 21; + table[25 * 256 + 144] = 23; + table[25 * 256 + 145] = 23; + table[25 * 256 + 146] = 23; + table[25 * 256 + 147] = 23; + table[25 * 256 + 148] = 23; + table[25 * 256 + 149] = 23; + table[25 * 256 + 150] = 23; + table[25 * 256 + 151] = 23; + table[25 * 256 + 152] = 23; + table[25 * 256 + 153] = 23; + table[25 * 256 + 154] = 23; + table[25 * 256 + 155] = 23; + table[25 * 256 + 156] = 23; + table[25 * 256 + 157] = 23; + table[25 * 256 + 158] = 23; + table[25 * 256 + 159] = 23; + table[25 * 256 + 160] = 23; + table[25 * 256 + 161] = 23; + table[25 * 256 + 162] = 23; + table[25 * 256 + 163] = 23; + table[25 * 256 + 164] = 23; + table[25 * 256 + 165] = 23; + table[25 * 256 + 166] = 23; + table[25 * 256 + 167] = 23; + table[25 * 256 + 168] = 23; + table[25 * 256 + 169] = 23; + table[25 * 256 + 170] = 23; + table[25 * 256 + 171] = 23; + table[25 * 256 + 172] = 23; + table[25 * 256 + 173] = 23; + table[25 * 256 + 174] = 23; + table[25 * 256 + 175] = 23; + table[25 * 256 + 176] = 23; + table[25 * 256 + 177] = 23; + table[25 * 256 + 178] = 23; + table[25 * 256 + 179] = 23; + table[25 * 256 + 180] = 23; + table[25 * 256 + 181] = 23; + table[25 * 256 + 182] = 23; + table[25 * 256 + 183] = 23; + table[25 * 256 + 184] = 23; + table[25 * 256 + 185] = 23; + table[25 * 256 + 186] = 23; + table[25 * 256 + 187] = 23; + table[25 * 256 + 188] = 23; + table[25 * 256 + 189] = 23; + table[25 * 256 + 190] = 23; + table[25 * 256 + 191] = 23; + table[26 * 256 + 128] = 23; + table[26 * 256 + 129] = 23; + table[26 * 256 + 130] = 23; + table[26 * 256 + 131] = 23; + table[26 * 256 + 132] = 23; + table[26 * 256 + 133] = 23; + table[26 * 256 + 134] = 23; + table[26 * 256 + 135] = 23; + table[26 * 256 + 136] = 23; + table[26 * 256 + 137] = 23; + table[26 * 256 + 138] = 23; + table[26 * 256 + 139] = 23; + table[26 * 256 + 140] = 23; + table[26 * 256 + 141] = 23; + table[26 * 256 + 142] = 23; + table[26 * 256 + 143] = 23; + table[26 * 256 + 144] = 23; + table[26 * 256 + 145] = 23; + table[26 * 256 + 146] = 23; + table[26 * 256 + 147] = 23; + table[26 * 256 + 148] = 23; + table[26 * 256 + 149] = 23; + table[26 * 256 + 150] = 23; + table[26 * 256 + 151] = 23; + table[26 * 256 + 152] = 23; + table[26 * 256 + 153] = 23; + table[26 * 256 + 154] = 23; + table[26 * 256 + 155] = 23; + table[26 * 256 + 156] = 23; + table[26 * 256 + 157] = 23; + table[26 * 256 + 158] = 23; + table[26 * 256 + 159] = 23; + table[26 * 256 + 160] = 23; + table[26 * 256 + 161] = 23; + table[26 * 256 + 162] = 23; + table[26 * 256 + 163] = 23; + table[26 * 256 + 164] = 23; + table[26 * 256 + 165] = 23; + table[26 * 256 + 166] = 23; + table[26 * 256 + 167] = 23; + table[26 * 256 + 168] = 23; + table[26 * 256 + 169] = 23; + table[26 * 256 + 170] = 23; + table[26 * 256 + 171] = 23; + table[26 * 256 + 172] = 23; + table[26 * 256 + 173] = 23; + table[26 * 256 + 174] = 23; + table[26 * 256 + 175] = 23; + table[26 * 256 + 176] = 23; + table[26 * 256 + 177] = 23; + table[26 * 256 + 178] = 23; + table[26 * 256 + 179] = 23; + table[26 * 256 + 180] = 23; + table[26 * 256 + 181] = 23; + table[26 * 256 + 182] = 23; + table[26 * 256 + 183] = 23; + table[26 * 256 + 184] = 23; + table[26 * 256 + 185] = 23; + table[26 * 256 + 186] = 23; + table[26 * 256 + 187] = 23; + table[26 * 256 + 188] = 23; + table[26 * 256 + 189] = 23; + table[26 * 256 + 190] = 23; + table[26 * 256 + 191] = 23; + table[27 * 256 + 128] = 23; + table[27 * 256 + 129] = 23; + table[27 * 256 + 130] = 23; + table[27 * 256 + 131] = 23; + table[27 * 256 + 132] = 23; + table[27 * 256 + 133] = 23; + table[27 * 256 + 134] = 23; + table[27 * 256 + 135] = 23; + table[27 * 256 + 136] = 23; + table[27 * 256 + 137] = 23; + table[27 * 256 + 138] = 23; + table[27 * 256 + 139] = 23; + table[27 * 256 + 140] = 23; + table[27 * 256 + 141] = 23; + table[27 * 256 + 142] = 23; + table[27 * 256 + 143] = 23; + table[28 * 256 + 32] = 29; + table[29 * 256 + 97] = 18; + table[29 * 256 + 98] = 18; + table[29 * 256 + 99] = 18; + table[29 * 256 + 100] = 18; + table[29 * 256 + 101] = 18; + table[29 * 256 + 102] = 18; + table[29 * 256 + 103] = 18; + table[29 * 256 + 104] = 18; + table[29 * 256 + 105] = 18; + table[29 * 256 + 106] = 18; + table[29 * 256 + 107] = 18; + table[29 * 256 + 108] = 18; + table[29 * 256 + 109] = 18; + table[29 * 256 + 110] = 18; + table[29 * 256 + 111] = 18; + table[29 * 256 + 112] = 18; + table[29 * 256 + 113] = 18; + table[29 * 256 + 114] = 18; + table[29 * 256 + 115] = 18; + table[29 * 256 + 117] = 18; + table[29 * 256 + 118] = 18; + table[29 * 256 + 119] = 18; + table[29 * 256 + 120] = 18; + table[29 * 256 + 121] = 18; + table[29 * 256 + 122] = 18; + table[29 * 256 + 116] = 30; + table[30 * 256 + 97] = 18; + table[30 * 256 + 98] = 18; + table[30 * 256 + 99] = 18; + table[30 * 256 + 100] = 18; + table[30 * 256 + 101] = 18; + table[30 * 256 + 102] = 18; + table[30 * 256 + 103] = 18; + table[30 * 256 + 104] = 18; + table[30 * 256 + 105] = 18; + table[30 * 256 + 106] = 18; + table[30 * 256 + 107] = 18; + table[30 * 256 + 108] = 18; + table[30 * 256 + 109] = 18; + table[30 * 256 + 110] = 18; + table[30 * 256 + 111] = 18; + table[30 * 256 + 112] = 18; + table[30 * 256 + 113] = 18; + table[30 * 256 + 114] = 18; + table[30 * 256 + 115] = 18; + table[30 * 256 + 116] = 18; + table[30 * 256 + 117] = 18; + table[30 * 256 + 118] = 18; + table[30 * 256 + 119] = 18; + table[30 * 256 + 120] = 18; + table[30 * 256 + 121] = 18; + table[30 * 256 + 122] = 18; + table[30 * 256 + 61] = 31; + table[31 * 256 + 0] = 20; + table[31 * 256 + 1] = 20; + table[31 * 256 + 2] = 20; + table[31 * 256 + 3] = 20; + table[31 * 256 + 4] = 20; + table[31 * 256 + 5] = 20; + table[31 * 256 + 6] = 20; + table[31 * 256 + 7] = 20; + table[31 * 256 + 8] = 20; + table[31 * 256 + 9] = 20; + table[31 * 256 + 10] = 20; + table[31 * 256 + 11] = 20; + table[31 * 256 + 12] = 20; + table[31 * 256 + 13] = 20; + table[31 * 256 + 14] = 20; + table[31 * 256 + 15] = 20; + table[31 * 256 + 16] = 20; + table[31 * 256 + 17] = 20; + table[31 * 256 + 18] = 20; + table[31 * 256 + 19] = 20; + table[31 * 256 + 20] = 20; + table[31 * 256 + 21] = 20; + table[31 * 256 + 22] = 20; + table[31 * 256 + 23] = 20; + table[31 * 256 + 24] = 20; + table[31 * 256 + 25] = 20; + table[31 * 256 + 26] = 20; + table[31 * 256 + 27] = 20; + table[31 * 256 + 28] = 20; + table[31 * 256 + 29] = 20; + table[31 * 256 + 30] = 20; + table[31 * 256 + 31] = 20; + table[31 * 256 + 32] = 20; + table[31 * 256 + 33] = 20; + table[31 * 256 + 34] = 20; + table[31 * 256 + 35] = 20; + table[31 * 256 + 36] = 20; + table[31 * 256 + 37] = 20; + table[31 * 256 + 38] = 20; + table[31 * 256 + 39] = 20; + table[31 * 256 + 40] = 20; + table[31 * 256 + 41] = 20; + table[31 * 256 + 42] = 20; + table[31 * 256 + 43] = 20; + table[31 * 256 + 44] = 20; + table[31 * 256 + 45] = 20; + table[31 * 256 + 46] = 20; + table[31 * 256 + 47] = 20; + table[31 * 256 + 58] = 20; + table[31 * 256 + 60] = 20; + table[31 * 256 + 61] = 20; + table[31 * 256 + 62] = 20; + table[31 * 256 + 63] = 20; + table[31 * 256 + 64] = 20; + table[31 * 256 + 65] = 20; + table[31 * 256 + 66] = 20; + table[31 * 256 + 67] = 20; + table[31 * 256 + 68] = 20; + table[31 * 256 + 69] = 20; + table[31 * 256 + 70] = 20; + table[31 * 256 + 71] = 20; + table[31 * 256 + 72] = 20; + table[31 * 256 + 73] = 20; + table[31 * 256 + 74] = 20; + table[31 * 256 + 75] = 20; + table[31 * 256 + 76] = 20; + table[31 * 256 + 77] = 20; + table[31 * 256 + 78] = 20; + table[31 * 256 + 79] = 20; + table[31 * 256 + 80] = 20; + table[31 * 256 + 81] = 20; + table[31 * 256 + 82] = 20; + table[31 * 256 + 83] = 20; + table[31 * 256 + 84] = 20; + table[31 * 256 + 85] = 20; + table[31 * 256 + 86] = 20; + table[31 * 256 + 87] = 20; + table[31 * 256 + 88] = 20; + table[31 * 256 + 89] = 20; + table[31 * 256 + 90] = 20; + table[31 * 256 + 91] = 20; + table[31 * 256 + 92] = 20; + table[31 * 256 + 93] = 20; + table[31 * 256 + 94] = 20; + table[31 * 256 + 95] = 20; + table[31 * 256 + 96] = 20; + table[31 * 256 + 97] = 20; + table[31 * 256 + 98] = 20; + table[31 * 256 + 99] = 20; + table[31 * 256 + 100] = 20; + table[31 * 256 + 101] = 20; + table[31 * 256 + 102] = 20; + table[31 * 256 + 103] = 20; + table[31 * 256 + 104] = 20; + table[31 * 256 + 105] = 20; + table[31 * 256 + 106] = 20; + table[31 * 256 + 107] = 20; + table[31 * 256 + 108] = 20; + table[31 * 256 + 109] = 20; + table[31 * 256 + 110] = 20; + table[31 * 256 + 111] = 20; + table[31 * 256 + 112] = 20; + table[31 * 256 + 113] = 20; + table[31 * 256 + 114] = 20; + table[31 * 256 + 115] = 20; + table[31 * 256 + 116] = 20; + table[31 * 256 + 117] = 20; + table[31 * 256 + 118] = 20; + table[31 * 256 + 119] = 20; + table[31 * 256 + 120] = 20; + table[31 * 256 + 121] = 20; + table[31 * 256 + 122] = 20; + table[31 * 256 + 123] = 20; + table[31 * 256 + 124] = 20; + table[31 * 256 + 125] = 20; + table[31 * 256 + 126] = 20; + table[31 * 256 + 127] = 20; + table[31 * 256 + 194] = 21; + table[31 * 256 + 195] = 21; + table[31 * 256 + 196] = 21; + table[31 * 256 + 197] = 21; + table[31 * 256 + 198] = 21; + table[31 * 256 + 199] = 21; + table[31 * 256 + 200] = 21; + table[31 * 256 + 201] = 21; + table[31 * 256 + 202] = 21; + table[31 * 256 + 203] = 21; + table[31 * 256 + 204] = 21; + table[31 * 256 + 205] = 21; + table[31 * 256 + 206] = 21; + table[31 * 256 + 207] = 21; + table[31 * 256 + 208] = 21; + table[31 * 256 + 209] = 21; + table[31 * 256 + 210] = 21; + table[31 * 256 + 211] = 21; + table[31 * 256 + 212] = 21; + table[31 * 256 + 213] = 21; + table[31 * 256 + 214] = 21; + table[31 * 256 + 215] = 21; + table[31 * 256 + 216] = 21; + table[31 * 256 + 217] = 21; + table[31 * 256 + 218] = 21; + table[31 * 256 + 219] = 21; + table[31 * 256 + 220] = 21; + table[31 * 256 + 221] = 21; + table[31 * 256 + 222] = 21; + table[31 * 256 + 223] = 21; + table[31 * 256 + 224] = 22; + table[31 * 256 + 225] = 23; + table[31 * 256 + 226] = 23; + table[31 * 256 + 227] = 23; + table[31 * 256 + 228] = 23; + table[31 * 256 + 229] = 23; + table[31 * 256 + 230] = 23; + table[31 * 256 + 231] = 23; + table[31 * 256 + 232] = 23; + table[31 * 256 + 233] = 23; + table[31 * 256 + 234] = 23; + table[31 * 256 + 235] = 23; + table[31 * 256 + 236] = 23; + table[31 * 256 + 238] = 23; + table[31 * 256 + 239] = 23; + table[31 * 256 + 237] = 24; + table[31 * 256 + 240] = 25; + table[31 * 256 + 241] = 26; + table[31 * 256 + 242] = 26; + table[31 * 256 + 243] = 26; + table[31 * 256 + 244] = 27; + table[31 * 256 + 48] = 32; + table[31 * 256 + 49] = 32; + table[31 * 256 + 50] = 32; + table[31 * 256 + 51] = 32; + table[31 * 256 + 52] = 32; + table[31 * 256 + 53] = 32; + table[31 * 256 + 54] = 32; + table[31 * 256 + 55] = 32; + table[31 * 256 + 56] = 32; + table[31 * 256 + 57] = 32; + table[32 * 256 + 48] = 32; + table[32 * 256 + 49] = 32; + table[32 * 256 + 50] = 32; + table[32 * 256 + 51] = 32; + table[32 * 256 + 52] = 32; + table[32 * 256 + 53] = 32; + table[32 * 256 + 54] = 32; + table[32 * 256 + 55] = 32; + table[32 * 256 + 56] = 32; + table[32 * 256 + 57] = 32; + table[32 * 256 + 59] = 33; + + table +} +pub fn regex_match(input: [u8; N]) -> bool { + // regex: (\r\n|^)dkim-signature:([a-z]+=[^;]+; )+t=[0-9]+; + let mut s = 0; + s = table[255]; + for i in 0..input.len() { + let s_idx = s * 256 + input[i] as Field; + std::as_witness(s_idx); + s = table[s_idx]; + } + + let matched: bool = (s == 33) | (s == 34); + + matched +} + + \ No newline at end of file diff --git a/packages/noir/src/basic/to_all.nr b/packages/noir/src/basic/to_all.nr new file mode 100644 index 00000000..4fc902d0 --- /dev/null +++ b/packages/noir/src/basic/to_all.nr @@ -0,0 +1,1219 @@ + +use crate::common::Sequence; + + +global table: [Field; 4352] = comptime { make_lookup_table() }; + +comptime fn make_lookup_table() -> [Field; 4352] { + let mut table = [0; 4352]; + table[15 * 256 + 0] = 16; + table[16 * 256 + 0] = 16; + table[15 * 256 + 1] = 16; + table[16 * 256 + 1] = 16; + table[15 * 256 + 2] = 16; + table[16 * 256 + 2] = 16; + table[15 * 256 + 3] = 16; + table[16 * 256 + 3] = 16; + table[15 * 256 + 4] = 16; + table[16 * 256 + 4] = 16; + table[15 * 256 + 5] = 16; + table[16 * 256 + 5] = 16; + table[15 * 256 + 6] = 16; + table[16 * 256 + 6] = 16; + table[15 * 256 + 7] = 16; + table[16 * 256 + 7] = 16; + table[15 * 256 + 8] = 16; + table[16 * 256 + 8] = 16; + table[15 * 256 + 9] = 16; + table[16 * 256 + 9] = 16; + table[15 * 256 + 10] = 16; + table[16 * 256 + 10] = 16; + table[15 * 256 + 11] = 16; + table[16 * 256 + 11] = 16; + table[15 * 256 + 12] = 16; + table[16 * 256 + 12] = 16; + table[15 * 256 + 13] = 16; + table[16 * 256 + 13] = 16; + table[15 * 256 + 14] = 16; + table[16 * 256 + 14] = 16; + table[15 * 256 + 15] = 16; + table[16 * 256 + 15] = 16; + table[15 * 256 + 16] = 16; + table[16 * 256 + 16] = 16; + table[15 * 256 + 17] = 16; + table[16 * 256 + 17] = 16; + table[15 * 256 + 18] = 16; + table[16 * 256 + 18] = 16; + table[15 * 256 + 19] = 16; + table[16 * 256 + 19] = 16; + table[15 * 256 + 20] = 16; + table[16 * 256 + 20] = 16; + table[15 * 256 + 21] = 16; + table[16 * 256 + 21] = 16; + table[15 * 256 + 22] = 16; + table[16 * 256 + 22] = 16; + table[15 * 256 + 23] = 16; + table[16 * 256 + 23] = 16; + table[15 * 256 + 24] = 16; + table[16 * 256 + 24] = 16; + table[15 * 256 + 25] = 16; + table[16 * 256 + 25] = 16; + table[15 * 256 + 26] = 16; + table[16 * 256 + 26] = 16; + table[15 * 256 + 27] = 16; + table[16 * 256 + 27] = 16; + table[15 * 256 + 28] = 16; + table[16 * 256 + 28] = 16; + table[15 * 256 + 29] = 16; + table[16 * 256 + 29] = 16; + table[15 * 256 + 30] = 16; + table[16 * 256 + 30] = 16; + table[15 * 256 + 31] = 16; + table[16 * 256 + 31] = 16; + table[15 * 256 + 32] = 16; + table[16 * 256 + 32] = 16; + table[15 * 256 + 33] = 16; + table[16 * 256 + 33] = 16; + table[15 * 256 + 34] = 16; + table[16 * 256 + 34] = 16; + table[15 * 256 + 35] = 16; + table[16 * 256 + 35] = 16; + table[15 * 256 + 36] = 16; + table[16 * 256 + 36] = 16; + table[15 * 256 + 37] = 16; + table[16 * 256 + 37] = 16; + table[15 * 256 + 38] = 16; + table[16 * 256 + 38] = 16; + table[15 * 256 + 39] = 16; + table[16 * 256 + 39] = 16; + table[15 * 256 + 40] = 16; + table[16 * 256 + 40] = 16; + table[15 * 256 + 41] = 16; + table[16 * 256 + 41] = 16; + table[15 * 256 + 42] = 16; + table[16 * 256 + 42] = 16; + table[15 * 256 + 43] = 16; + table[16 * 256 + 43] = 16; + table[15 * 256 + 44] = 16; + table[16 * 256 + 44] = 16; + table[15 * 256 + 45] = 16; + table[16 * 256 + 45] = 16; + table[15 * 256 + 46] = 16; + table[16 * 256 + 46] = 16; + table[15 * 256 + 47] = 16; + table[16 * 256 + 47] = 16; + table[15 * 256 + 48] = 16; + table[16 * 256 + 48] = 16; + table[15 * 256 + 49] = 16; + table[16 * 256 + 49] = 16; + table[15 * 256 + 50] = 16; + table[16 * 256 + 50] = 16; + table[15 * 256 + 51] = 16; + table[16 * 256 + 51] = 16; + table[15 * 256 + 52] = 16; + table[16 * 256 + 52] = 16; + table[15 * 256 + 53] = 16; + table[16 * 256 + 53] = 16; + table[15 * 256 + 54] = 16; + table[16 * 256 + 54] = 16; + table[15 * 256 + 55] = 16; + table[16 * 256 + 55] = 16; + table[15 * 256 + 56] = 16; + table[16 * 256 + 56] = 16; + table[15 * 256 + 57] = 16; + table[16 * 256 + 57] = 16; + table[15 * 256 + 58] = 16; + table[16 * 256 + 58] = 16; + table[15 * 256 + 59] = 16; + table[16 * 256 + 59] = 16; + table[15 * 256 + 60] = 16; + table[16 * 256 + 60] = 16; + table[15 * 256 + 61] = 16; + table[16 * 256 + 61] = 16; + table[15 * 256 + 62] = 16; + table[16 * 256 + 62] = 16; + table[15 * 256 + 63] = 16; + table[16 * 256 + 63] = 16; + table[15 * 256 + 64] = 16; + table[16 * 256 + 64] = 16; + table[15 * 256 + 65] = 16; + table[16 * 256 + 65] = 16; + table[15 * 256 + 66] = 16; + table[16 * 256 + 66] = 16; + table[15 * 256 + 67] = 16; + table[16 * 256 + 67] = 16; + table[15 * 256 + 68] = 16; + table[16 * 256 + 68] = 16; + table[15 * 256 + 69] = 16; + table[16 * 256 + 69] = 16; + table[15 * 256 + 70] = 16; + table[16 * 256 + 70] = 16; + table[15 * 256 + 71] = 16; + table[16 * 256 + 71] = 16; + table[15 * 256 + 72] = 16; + table[16 * 256 + 72] = 16; + table[15 * 256 + 73] = 16; + table[16 * 256 + 73] = 16; + table[15 * 256 + 74] = 16; + table[16 * 256 + 74] = 16; + table[15 * 256 + 75] = 16; + table[16 * 256 + 75] = 16; + table[15 * 256 + 76] = 16; + table[16 * 256 + 76] = 16; + table[15 * 256 + 77] = 16; + table[16 * 256 + 77] = 16; + table[15 * 256 + 78] = 16; + table[16 * 256 + 78] = 16; + table[15 * 256 + 79] = 16; + table[16 * 256 + 79] = 16; + table[15 * 256 + 80] = 16; + table[16 * 256 + 80] = 16; + table[15 * 256 + 81] = 16; + table[16 * 256 + 81] = 16; + table[15 * 256 + 82] = 16; + table[16 * 256 + 82] = 16; + table[15 * 256 + 83] = 16; + table[16 * 256 + 83] = 16; + table[15 * 256 + 84] = 16; + table[16 * 256 + 84] = 16; + table[15 * 256 + 85] = 16; + table[16 * 256 + 85] = 16; + table[15 * 256 + 86] = 16; + table[16 * 256 + 86] = 16; + table[15 * 256 + 87] = 16; + table[16 * 256 + 87] = 16; + table[15 * 256 + 88] = 16; + table[16 * 256 + 88] = 16; + table[15 * 256 + 89] = 16; + table[16 * 256 + 89] = 16; + table[15 * 256 + 90] = 16; + table[16 * 256 + 90] = 16; + table[15 * 256 + 91] = 16; + table[16 * 256 + 91] = 16; + table[15 * 256 + 92] = 16; + table[16 * 256 + 92] = 16; + table[15 * 256 + 93] = 16; + table[16 * 256 + 93] = 16; + table[15 * 256 + 94] = 16; + table[16 * 256 + 94] = 16; + table[15 * 256 + 95] = 16; + table[16 * 256 + 95] = 16; + table[15 * 256 + 96] = 16; + table[16 * 256 + 96] = 16; + table[15 * 256 + 97] = 16; + table[16 * 256 + 97] = 16; + table[15 * 256 + 98] = 16; + table[16 * 256 + 98] = 16; + table[15 * 256 + 99] = 16; + table[16 * 256 + 99] = 16; + table[15 * 256 + 100] = 16; + table[16 * 256 + 100] = 16; + table[15 * 256 + 101] = 16; + table[16 * 256 + 101] = 16; + table[15 * 256 + 102] = 16; + table[16 * 256 + 102] = 16; + table[15 * 256 + 103] = 16; + table[16 * 256 + 103] = 16; + table[15 * 256 + 104] = 16; + table[16 * 256 + 104] = 16; + table[15 * 256 + 105] = 16; + table[16 * 256 + 105] = 16; + table[15 * 256 + 106] = 16; + table[16 * 256 + 106] = 16; + table[15 * 256 + 107] = 16; + table[16 * 256 + 107] = 16; + table[15 * 256 + 108] = 16; + table[16 * 256 + 108] = 16; + table[15 * 256 + 109] = 16; + table[16 * 256 + 109] = 16; + table[15 * 256 + 110] = 16; + table[16 * 256 + 110] = 16; + table[15 * 256 + 111] = 16; + table[16 * 256 + 111] = 16; + table[15 * 256 + 112] = 16; + table[16 * 256 + 112] = 16; + table[15 * 256 + 113] = 16; + table[16 * 256 + 113] = 16; + table[15 * 256 + 114] = 16; + table[16 * 256 + 114] = 16; + table[15 * 256 + 115] = 16; + table[16 * 256 + 115] = 16; + table[15 * 256 + 116] = 16; + table[16 * 256 + 116] = 16; + table[15 * 256 + 117] = 16; + table[16 * 256 + 117] = 16; + table[15 * 256 + 118] = 16; + table[16 * 256 + 118] = 16; + table[15 * 256 + 119] = 16; + table[16 * 256 + 119] = 16; + table[15 * 256 + 120] = 16; + table[16 * 256 + 120] = 16; + table[15 * 256 + 121] = 16; + table[16 * 256 + 121] = 16; + table[15 * 256 + 122] = 16; + table[16 * 256 + 122] = 16; + table[15 * 256 + 123] = 16; + table[16 * 256 + 123] = 16; + table[15 * 256 + 124] = 16; + table[16 * 256 + 124] = 16; + table[15 * 256 + 125] = 16; + table[16 * 256 + 125] = 16; + table[15 * 256 + 126] = 16; + table[16 * 256 + 126] = 16; + table[15 * 256 + 127] = 16; + table[16 * 256 + 127] = 16; + table[15 * 256 + 128] = 16; + table[16 * 256 + 128] = 16; + table[15 * 256 + 129] = 16; + table[16 * 256 + 129] = 16; + table[15 * 256 + 130] = 16; + table[16 * 256 + 130] = 16; + table[15 * 256 + 131] = 16; + table[16 * 256 + 131] = 16; + table[15 * 256 + 132] = 16; + table[16 * 256 + 132] = 16; + table[15 * 256 + 133] = 16; + table[16 * 256 + 133] = 16; + table[15 * 256 + 134] = 16; + table[16 * 256 + 134] = 16; + table[15 * 256 + 135] = 16; + table[16 * 256 + 135] = 16; + table[15 * 256 + 136] = 16; + table[16 * 256 + 136] = 16; + table[15 * 256 + 137] = 16; + table[16 * 256 + 137] = 16; + table[15 * 256 + 138] = 16; + table[16 * 256 + 138] = 16; + table[15 * 256 + 139] = 16; + table[16 * 256 + 139] = 16; + table[15 * 256 + 140] = 16; + table[16 * 256 + 140] = 16; + table[15 * 256 + 141] = 16; + table[16 * 256 + 141] = 16; + table[15 * 256 + 142] = 16; + table[16 * 256 + 142] = 16; + table[15 * 256 + 143] = 16; + table[16 * 256 + 143] = 16; + table[15 * 256 + 144] = 16; + table[16 * 256 + 144] = 16; + table[15 * 256 + 145] = 16; + table[16 * 256 + 145] = 16; + table[15 * 256 + 146] = 16; + table[16 * 256 + 146] = 16; + table[15 * 256 + 147] = 16; + table[16 * 256 + 147] = 16; + table[15 * 256 + 148] = 16; + table[16 * 256 + 148] = 16; + table[15 * 256 + 149] = 16; + table[16 * 256 + 149] = 16; + table[15 * 256 + 150] = 16; + table[16 * 256 + 150] = 16; + table[15 * 256 + 151] = 16; + table[16 * 256 + 151] = 16; + table[15 * 256 + 152] = 16; + table[16 * 256 + 152] = 16; + table[15 * 256 + 153] = 16; + table[16 * 256 + 153] = 16; + table[15 * 256 + 154] = 16; + table[16 * 256 + 154] = 16; + table[15 * 256 + 155] = 16; + table[16 * 256 + 155] = 16; + table[15 * 256 + 156] = 16; + table[16 * 256 + 156] = 16; + table[15 * 256 + 157] = 16; + table[16 * 256 + 157] = 16; + table[15 * 256 + 158] = 16; + table[16 * 256 + 158] = 16; + table[15 * 256 + 159] = 16; + table[16 * 256 + 159] = 16; + table[15 * 256 + 160] = 16; + table[16 * 256 + 160] = 16; + table[15 * 256 + 161] = 16; + table[16 * 256 + 161] = 16; + table[15 * 256 + 162] = 16; + table[16 * 256 + 162] = 16; + table[15 * 256 + 163] = 16; + table[16 * 256 + 163] = 16; + table[15 * 256 + 164] = 16; + table[16 * 256 + 164] = 16; + table[15 * 256 + 165] = 16; + table[16 * 256 + 165] = 16; + table[15 * 256 + 166] = 16; + table[16 * 256 + 166] = 16; + table[15 * 256 + 167] = 16; + table[16 * 256 + 167] = 16; + table[15 * 256 + 168] = 16; + table[16 * 256 + 168] = 16; + table[15 * 256 + 169] = 16; + table[16 * 256 + 169] = 16; + table[15 * 256 + 170] = 16; + table[16 * 256 + 170] = 16; + table[15 * 256 + 171] = 16; + table[16 * 256 + 171] = 16; + table[15 * 256 + 172] = 16; + table[16 * 256 + 172] = 16; + table[15 * 256 + 173] = 16; + table[16 * 256 + 173] = 16; + table[15 * 256 + 174] = 16; + table[16 * 256 + 174] = 16; + table[15 * 256 + 175] = 16; + table[16 * 256 + 175] = 16; + table[15 * 256 + 176] = 16; + table[16 * 256 + 176] = 16; + table[15 * 256 + 177] = 16; + table[16 * 256 + 177] = 16; + table[15 * 256 + 178] = 16; + table[16 * 256 + 178] = 16; + table[15 * 256 + 179] = 16; + table[16 * 256 + 179] = 16; + table[15 * 256 + 180] = 16; + table[16 * 256 + 180] = 16; + table[15 * 256 + 181] = 16; + table[16 * 256 + 181] = 16; + table[15 * 256 + 182] = 16; + table[16 * 256 + 182] = 16; + table[15 * 256 + 183] = 16; + table[16 * 256 + 183] = 16; + table[15 * 256 + 184] = 16; + table[16 * 256 + 184] = 16; + table[15 * 256 + 185] = 16; + table[16 * 256 + 185] = 16; + table[15 * 256 + 186] = 16; + table[16 * 256 + 186] = 16; + table[15 * 256 + 187] = 16; + table[16 * 256 + 187] = 16; + table[15 * 256 + 188] = 16; + table[16 * 256 + 188] = 16; + table[15 * 256 + 189] = 16; + table[16 * 256 + 189] = 16; + table[15 * 256 + 190] = 16; + table[16 * 256 + 190] = 16; + table[15 * 256 + 191] = 16; + table[16 * 256 + 191] = 16; + table[15 * 256 + 192] = 16; + table[16 * 256 + 192] = 16; + table[15 * 256 + 193] = 16; + table[16 * 256 + 193] = 16; + table[15 * 256 + 194] = 16; + table[16 * 256 + 194] = 16; + table[15 * 256 + 195] = 16; + table[16 * 256 + 195] = 16; + table[15 * 256 + 196] = 16; + table[16 * 256 + 196] = 16; + table[15 * 256 + 197] = 16; + table[16 * 256 + 197] = 16; + table[15 * 256 + 198] = 16; + table[16 * 256 + 198] = 16; + table[15 * 256 + 199] = 16; + table[16 * 256 + 199] = 16; + table[15 * 256 + 200] = 16; + table[16 * 256 + 200] = 16; + table[15 * 256 + 201] = 16; + table[16 * 256 + 201] = 16; + table[15 * 256 + 202] = 16; + table[16 * 256 + 202] = 16; + table[15 * 256 + 203] = 16; + table[16 * 256 + 203] = 16; + table[15 * 256 + 204] = 16; + table[16 * 256 + 204] = 16; + table[15 * 256 + 205] = 16; + table[16 * 256 + 205] = 16; + table[15 * 256 + 206] = 16; + table[16 * 256 + 206] = 16; + table[15 * 256 + 207] = 16; + table[16 * 256 + 207] = 16; + table[15 * 256 + 208] = 16; + table[16 * 256 + 208] = 16; + table[15 * 256 + 209] = 16; + table[16 * 256 + 209] = 16; + table[15 * 256 + 210] = 16; + table[16 * 256 + 210] = 16; + table[15 * 256 + 211] = 16; + table[16 * 256 + 211] = 16; + table[15 * 256 + 212] = 16; + table[16 * 256 + 212] = 16; + table[15 * 256 + 213] = 16; + table[16 * 256 + 213] = 16; + table[15 * 256 + 214] = 16; + table[16 * 256 + 214] = 16; + table[15 * 256 + 215] = 16; + table[16 * 256 + 215] = 16; + table[15 * 256 + 216] = 16; + table[16 * 256 + 216] = 16; + table[15 * 256 + 217] = 16; + table[16 * 256 + 217] = 16; + table[15 * 256 + 218] = 16; + table[16 * 256 + 218] = 16; + table[15 * 256 + 219] = 16; + table[16 * 256 + 219] = 16; + table[15 * 256 + 220] = 16; + table[16 * 256 + 220] = 16; + table[15 * 256 + 221] = 16; + table[16 * 256 + 221] = 16; + table[15 * 256 + 222] = 16; + table[16 * 256 + 222] = 16; + table[15 * 256 + 223] = 16; + table[16 * 256 + 223] = 16; + table[15 * 256 + 224] = 16; + table[16 * 256 + 224] = 16; + table[15 * 256 + 225] = 16; + table[16 * 256 + 225] = 16; + table[15 * 256 + 226] = 16; + table[16 * 256 + 226] = 16; + table[15 * 256 + 227] = 16; + table[16 * 256 + 227] = 16; + table[15 * 256 + 228] = 16; + table[16 * 256 + 228] = 16; + table[15 * 256 + 229] = 16; + table[16 * 256 + 229] = 16; + table[15 * 256 + 230] = 16; + table[16 * 256 + 230] = 16; + table[15 * 256 + 231] = 16; + table[16 * 256 + 231] = 16; + table[15 * 256 + 232] = 16; + table[16 * 256 + 232] = 16; + table[15 * 256 + 233] = 16; + table[16 * 256 + 233] = 16; + table[15 * 256 + 234] = 16; + table[16 * 256 + 234] = 16; + table[15 * 256 + 235] = 16; + table[16 * 256 + 235] = 16; + table[15 * 256 + 236] = 16; + table[16 * 256 + 236] = 16; + table[15 * 256 + 237] = 16; + table[16 * 256 + 237] = 16; + table[15 * 256 + 238] = 16; + table[16 * 256 + 238] = 16; + table[15 * 256 + 239] = 16; + table[16 * 256 + 239] = 16; + table[15 * 256 + 240] = 16; + table[16 * 256 + 240] = 16; + table[15 * 256 + 241] = 16; + table[16 * 256 + 241] = 16; + table[15 * 256 + 242] = 16; + table[16 * 256 + 242] = 16; + table[15 * 256 + 243] = 16; + table[16 * 256 + 243] = 16; + table[15 * 256 + 244] = 16; + table[16 * 256 + 244] = 16; + table[15 * 256 + 245] = 16; + table[16 * 256 + 245] = 16; + table[15 * 256 + 246] = 16; + table[16 * 256 + 246] = 16; + table[15 * 256 + 247] = 16; + table[16 * 256 + 247] = 16; + table[15 * 256 + 248] = 16; + table[16 * 256 + 248] = 16; + table[15 * 256 + 249] = 16; + table[16 * 256 + 249] = 16; + table[15 * 256 + 250] = 16; + table[16 * 256 + 250] = 16; + table[15 * 256 + 251] = 16; + table[16 * 256 + 251] = 16; + table[15 * 256 + 252] = 16; + table[16 * 256 + 252] = 16; + table[15 * 256 + 253] = 16; + table[16 * 256 + 253] = 16; + table[15 * 256 + 254] = 16; + table[16 * 256 + 254] = 16; + table[0 * 256 + 13] = 1; + table[0 * 256 + 255] = 2; + table[1 * 256 + 10] = 2; + table[2 * 256 + 116] = 3; + table[3 * 256 + 111] = 4; + table[4 * 256 + 58] = 5; + table[5 * 256 + 0] = 6; + table[5 * 256 + 1] = 6; + table[5 * 256 + 2] = 6; + table[5 * 256 + 3] = 6; + table[5 * 256 + 4] = 6; + table[5 * 256 + 5] = 6; + table[5 * 256 + 6] = 6; + table[5 * 256 + 7] = 6; + table[5 * 256 + 8] = 6; + table[5 * 256 + 9] = 6; + table[5 * 256 + 11] = 6; + table[5 * 256 + 12] = 6; + table[5 * 256 + 14] = 6; + table[5 * 256 + 15] = 6; + table[5 * 256 + 16] = 6; + table[5 * 256 + 17] = 6; + table[5 * 256 + 18] = 6; + table[5 * 256 + 19] = 6; + table[5 * 256 + 20] = 6; + table[5 * 256 + 21] = 6; + table[5 * 256 + 22] = 6; + table[5 * 256 + 23] = 6; + table[5 * 256 + 24] = 6; + table[5 * 256 + 25] = 6; + table[5 * 256 + 26] = 6; + table[5 * 256 + 27] = 6; + table[5 * 256 + 28] = 6; + table[5 * 256 + 29] = 6; + table[5 * 256 + 30] = 6; + table[5 * 256 + 31] = 6; + table[5 * 256 + 32] = 6; + table[5 * 256 + 33] = 6; + table[5 * 256 + 34] = 6; + table[5 * 256 + 35] = 6; + table[5 * 256 + 36] = 6; + table[5 * 256 + 37] = 6; + table[5 * 256 + 38] = 6; + table[5 * 256 + 39] = 6; + table[5 * 256 + 40] = 6; + table[5 * 256 + 41] = 6; + table[5 * 256 + 42] = 6; + table[5 * 256 + 43] = 6; + table[5 * 256 + 44] = 6; + table[5 * 256 + 45] = 6; + table[5 * 256 + 46] = 6; + table[5 * 256 + 47] = 6; + table[5 * 256 + 48] = 6; + table[5 * 256 + 49] = 6; + table[5 * 256 + 50] = 6; + table[5 * 256 + 51] = 6; + table[5 * 256 + 52] = 6; + table[5 * 256 + 53] = 6; + table[5 * 256 + 54] = 6; + table[5 * 256 + 55] = 6; + table[5 * 256 + 56] = 6; + table[5 * 256 + 57] = 6; + table[5 * 256 + 58] = 6; + table[5 * 256 + 59] = 6; + table[5 * 256 + 60] = 6; + table[5 * 256 + 61] = 6; + table[5 * 256 + 62] = 6; + table[5 * 256 + 63] = 6; + table[5 * 256 + 64] = 6; + table[5 * 256 + 65] = 6; + table[5 * 256 + 66] = 6; + table[5 * 256 + 67] = 6; + table[5 * 256 + 68] = 6; + table[5 * 256 + 69] = 6; + table[5 * 256 + 70] = 6; + table[5 * 256 + 71] = 6; + table[5 * 256 + 72] = 6; + table[5 * 256 + 73] = 6; + table[5 * 256 + 74] = 6; + table[5 * 256 + 75] = 6; + table[5 * 256 + 76] = 6; + table[5 * 256 + 77] = 6; + table[5 * 256 + 78] = 6; + table[5 * 256 + 79] = 6; + table[5 * 256 + 80] = 6; + table[5 * 256 + 81] = 6; + table[5 * 256 + 82] = 6; + table[5 * 256 + 83] = 6; + table[5 * 256 + 84] = 6; + table[5 * 256 + 85] = 6; + table[5 * 256 + 86] = 6; + table[5 * 256 + 87] = 6; + table[5 * 256 + 88] = 6; + table[5 * 256 + 89] = 6; + table[5 * 256 + 90] = 6; + table[5 * 256 + 91] = 6; + table[5 * 256 + 92] = 6; + table[5 * 256 + 93] = 6; + table[5 * 256 + 94] = 6; + table[5 * 256 + 95] = 6; + table[5 * 256 + 96] = 6; + table[5 * 256 + 97] = 6; + table[5 * 256 + 98] = 6; + table[5 * 256 + 99] = 6; + table[5 * 256 + 100] = 6; + table[5 * 256 + 101] = 6; + table[5 * 256 + 102] = 6; + table[5 * 256 + 103] = 6; + table[5 * 256 + 104] = 6; + table[5 * 256 + 105] = 6; + table[5 * 256 + 106] = 6; + table[5 * 256 + 107] = 6; + table[5 * 256 + 108] = 6; + table[5 * 256 + 109] = 6; + table[5 * 256 + 110] = 6; + table[5 * 256 + 111] = 6; + table[5 * 256 + 112] = 6; + table[5 * 256 + 113] = 6; + table[5 * 256 + 114] = 6; + table[5 * 256 + 115] = 6; + table[5 * 256 + 116] = 6; + table[5 * 256 + 117] = 6; + table[5 * 256 + 118] = 6; + table[5 * 256 + 119] = 6; + table[5 * 256 + 120] = 6; + table[5 * 256 + 121] = 6; + table[5 * 256 + 122] = 6; + table[5 * 256 + 123] = 6; + table[5 * 256 + 124] = 6; + table[5 * 256 + 125] = 6; + table[5 * 256 + 126] = 6; + table[5 * 256 + 127] = 6; + table[5 * 256 + 194] = 7; + table[5 * 256 + 195] = 7; + table[5 * 256 + 196] = 7; + table[5 * 256 + 197] = 7; + table[5 * 256 + 198] = 7; + table[5 * 256 + 199] = 7; + table[5 * 256 + 200] = 7; + table[5 * 256 + 201] = 7; + table[5 * 256 + 202] = 7; + table[5 * 256 + 203] = 7; + table[5 * 256 + 204] = 7; + table[5 * 256 + 205] = 7; + table[5 * 256 + 206] = 7; + table[5 * 256 + 207] = 7; + table[5 * 256 + 208] = 7; + table[5 * 256 + 209] = 7; + table[5 * 256 + 210] = 7; + table[5 * 256 + 211] = 7; + table[5 * 256 + 212] = 7; + table[5 * 256 + 213] = 7; + table[5 * 256 + 214] = 7; + table[5 * 256 + 215] = 7; + table[5 * 256 + 216] = 7; + table[5 * 256 + 217] = 7; + table[5 * 256 + 218] = 7; + table[5 * 256 + 219] = 7; + table[5 * 256 + 220] = 7; + table[5 * 256 + 221] = 7; + table[5 * 256 + 222] = 7; + table[5 * 256 + 223] = 7; + table[5 * 256 + 224] = 8; + table[5 * 256 + 225] = 9; + table[5 * 256 + 226] = 9; + table[5 * 256 + 227] = 9; + table[5 * 256 + 228] = 9; + table[5 * 256 + 229] = 9; + table[5 * 256 + 230] = 9; + table[5 * 256 + 231] = 9; + table[5 * 256 + 232] = 9; + table[5 * 256 + 233] = 9; + table[5 * 256 + 234] = 9; + table[5 * 256 + 235] = 9; + table[5 * 256 + 236] = 9; + table[5 * 256 + 238] = 9; + table[5 * 256 + 239] = 9; + table[5 * 256 + 237] = 10; + table[5 * 256 + 240] = 11; + table[5 * 256 + 241] = 12; + table[5 * 256 + 242] = 12; + table[5 * 256 + 243] = 12; + table[5 * 256 + 244] = 13; + table[6 * 256 + 0] = 6; + table[6 * 256 + 1] = 6; + table[6 * 256 + 2] = 6; + table[6 * 256 + 3] = 6; + table[6 * 256 + 4] = 6; + table[6 * 256 + 5] = 6; + table[6 * 256 + 6] = 6; + table[6 * 256 + 7] = 6; + table[6 * 256 + 8] = 6; + table[6 * 256 + 9] = 6; + table[6 * 256 + 11] = 6; + table[6 * 256 + 12] = 6; + table[6 * 256 + 14] = 6; + table[6 * 256 + 15] = 6; + table[6 * 256 + 16] = 6; + table[6 * 256 + 17] = 6; + table[6 * 256 + 18] = 6; + table[6 * 256 + 19] = 6; + table[6 * 256 + 20] = 6; + table[6 * 256 + 21] = 6; + table[6 * 256 + 22] = 6; + table[6 * 256 + 23] = 6; + table[6 * 256 + 24] = 6; + table[6 * 256 + 25] = 6; + table[6 * 256 + 26] = 6; + table[6 * 256 + 27] = 6; + table[6 * 256 + 28] = 6; + table[6 * 256 + 29] = 6; + table[6 * 256 + 30] = 6; + table[6 * 256 + 31] = 6; + table[6 * 256 + 32] = 6; + table[6 * 256 + 33] = 6; + table[6 * 256 + 34] = 6; + table[6 * 256 + 35] = 6; + table[6 * 256 + 36] = 6; + table[6 * 256 + 37] = 6; + table[6 * 256 + 38] = 6; + table[6 * 256 + 39] = 6; + table[6 * 256 + 40] = 6; + table[6 * 256 + 41] = 6; + table[6 * 256 + 42] = 6; + table[6 * 256 + 43] = 6; + table[6 * 256 + 44] = 6; + table[6 * 256 + 45] = 6; + table[6 * 256 + 46] = 6; + table[6 * 256 + 47] = 6; + table[6 * 256 + 48] = 6; + table[6 * 256 + 49] = 6; + table[6 * 256 + 50] = 6; + table[6 * 256 + 51] = 6; + table[6 * 256 + 52] = 6; + table[6 * 256 + 53] = 6; + table[6 * 256 + 54] = 6; + table[6 * 256 + 55] = 6; + table[6 * 256 + 56] = 6; + table[6 * 256 + 57] = 6; + table[6 * 256 + 58] = 6; + table[6 * 256 + 59] = 6; + table[6 * 256 + 60] = 6; + table[6 * 256 + 61] = 6; + table[6 * 256 + 62] = 6; + table[6 * 256 + 63] = 6; + table[6 * 256 + 64] = 6; + table[6 * 256 + 65] = 6; + table[6 * 256 + 66] = 6; + table[6 * 256 + 67] = 6; + table[6 * 256 + 68] = 6; + table[6 * 256 + 69] = 6; + table[6 * 256 + 70] = 6; + table[6 * 256 + 71] = 6; + table[6 * 256 + 72] = 6; + table[6 * 256 + 73] = 6; + table[6 * 256 + 74] = 6; + table[6 * 256 + 75] = 6; + table[6 * 256 + 76] = 6; + table[6 * 256 + 77] = 6; + table[6 * 256 + 78] = 6; + table[6 * 256 + 79] = 6; + table[6 * 256 + 80] = 6; + table[6 * 256 + 81] = 6; + table[6 * 256 + 82] = 6; + table[6 * 256 + 83] = 6; + table[6 * 256 + 84] = 6; + table[6 * 256 + 85] = 6; + table[6 * 256 + 86] = 6; + table[6 * 256 + 87] = 6; + table[6 * 256 + 88] = 6; + table[6 * 256 + 89] = 6; + table[6 * 256 + 90] = 6; + table[6 * 256 + 91] = 6; + table[6 * 256 + 92] = 6; + table[6 * 256 + 93] = 6; + table[6 * 256 + 94] = 6; + table[6 * 256 + 95] = 6; + table[6 * 256 + 96] = 6; + table[6 * 256 + 97] = 6; + table[6 * 256 + 98] = 6; + table[6 * 256 + 99] = 6; + table[6 * 256 + 100] = 6; + table[6 * 256 + 101] = 6; + table[6 * 256 + 102] = 6; + table[6 * 256 + 103] = 6; + table[6 * 256 + 104] = 6; + table[6 * 256 + 105] = 6; + table[6 * 256 + 106] = 6; + table[6 * 256 + 107] = 6; + table[6 * 256 + 108] = 6; + table[6 * 256 + 109] = 6; + table[6 * 256 + 110] = 6; + table[6 * 256 + 111] = 6; + table[6 * 256 + 112] = 6; + table[6 * 256 + 113] = 6; + table[6 * 256 + 114] = 6; + table[6 * 256 + 115] = 6; + table[6 * 256 + 116] = 6; + table[6 * 256 + 117] = 6; + table[6 * 256 + 118] = 6; + table[6 * 256 + 119] = 6; + table[6 * 256 + 120] = 6; + table[6 * 256 + 121] = 6; + table[6 * 256 + 122] = 6; + table[6 * 256 + 123] = 6; + table[6 * 256 + 124] = 6; + table[6 * 256 + 125] = 6; + table[6 * 256 + 126] = 6; + table[6 * 256 + 127] = 6; + table[6 * 256 + 194] = 7; + table[6 * 256 + 195] = 7; + table[6 * 256 + 196] = 7; + table[6 * 256 + 197] = 7; + table[6 * 256 + 198] = 7; + table[6 * 256 + 199] = 7; + table[6 * 256 + 200] = 7; + table[6 * 256 + 201] = 7; + table[6 * 256 + 202] = 7; + table[6 * 256 + 203] = 7; + table[6 * 256 + 204] = 7; + table[6 * 256 + 205] = 7; + table[6 * 256 + 206] = 7; + table[6 * 256 + 207] = 7; + table[6 * 256 + 208] = 7; + table[6 * 256 + 209] = 7; + table[6 * 256 + 210] = 7; + table[6 * 256 + 211] = 7; + table[6 * 256 + 212] = 7; + table[6 * 256 + 213] = 7; + table[6 * 256 + 214] = 7; + table[6 * 256 + 215] = 7; + table[6 * 256 + 216] = 7; + table[6 * 256 + 217] = 7; + table[6 * 256 + 218] = 7; + table[6 * 256 + 219] = 7; + table[6 * 256 + 220] = 7; + table[6 * 256 + 221] = 7; + table[6 * 256 + 222] = 7; + table[6 * 256 + 223] = 7; + table[6 * 256 + 224] = 8; + table[6 * 256 + 225] = 9; + table[6 * 256 + 226] = 9; + table[6 * 256 + 227] = 9; + table[6 * 256 + 228] = 9; + table[6 * 256 + 229] = 9; + table[6 * 256 + 230] = 9; + table[6 * 256 + 231] = 9; + table[6 * 256 + 232] = 9; + table[6 * 256 + 233] = 9; + table[6 * 256 + 234] = 9; + table[6 * 256 + 235] = 9; + table[6 * 256 + 236] = 9; + table[6 * 256 + 238] = 9; + table[6 * 256 + 239] = 9; + table[6 * 256 + 237] = 10; + table[6 * 256 + 240] = 11; + table[6 * 256 + 241] = 12; + table[6 * 256 + 242] = 12; + table[6 * 256 + 243] = 12; + table[6 * 256 + 244] = 13; + table[6 * 256 + 13] = 14; + table[7 * 256 + 128] = 6; + table[7 * 256 + 129] = 6; + table[7 * 256 + 130] = 6; + table[7 * 256 + 131] = 6; + table[7 * 256 + 132] = 6; + table[7 * 256 + 133] = 6; + table[7 * 256 + 134] = 6; + table[7 * 256 + 135] = 6; + table[7 * 256 + 136] = 6; + table[7 * 256 + 137] = 6; + table[7 * 256 + 138] = 6; + table[7 * 256 + 139] = 6; + table[7 * 256 + 140] = 6; + table[7 * 256 + 141] = 6; + table[7 * 256 + 142] = 6; + table[7 * 256 + 143] = 6; + table[7 * 256 + 144] = 6; + table[7 * 256 + 145] = 6; + table[7 * 256 + 146] = 6; + table[7 * 256 + 147] = 6; + table[7 * 256 + 148] = 6; + table[7 * 256 + 149] = 6; + table[7 * 256 + 150] = 6; + table[7 * 256 + 151] = 6; + table[7 * 256 + 152] = 6; + table[7 * 256 + 153] = 6; + table[7 * 256 + 154] = 6; + table[7 * 256 + 155] = 6; + table[7 * 256 + 156] = 6; + table[7 * 256 + 157] = 6; + table[7 * 256 + 158] = 6; + table[7 * 256 + 159] = 6; + table[7 * 256 + 160] = 6; + table[7 * 256 + 161] = 6; + table[7 * 256 + 162] = 6; + table[7 * 256 + 163] = 6; + table[7 * 256 + 164] = 6; + table[7 * 256 + 165] = 6; + table[7 * 256 + 166] = 6; + table[7 * 256 + 167] = 6; + table[7 * 256 + 168] = 6; + table[7 * 256 + 169] = 6; + table[7 * 256 + 170] = 6; + table[7 * 256 + 171] = 6; + table[7 * 256 + 172] = 6; + table[7 * 256 + 173] = 6; + table[7 * 256 + 174] = 6; + table[7 * 256 + 175] = 6; + table[7 * 256 + 176] = 6; + table[7 * 256 + 177] = 6; + table[7 * 256 + 178] = 6; + table[7 * 256 + 179] = 6; + table[7 * 256 + 180] = 6; + table[7 * 256 + 181] = 6; + table[7 * 256 + 182] = 6; + table[7 * 256 + 183] = 6; + table[7 * 256 + 184] = 6; + table[7 * 256 + 185] = 6; + table[7 * 256 + 186] = 6; + table[7 * 256 + 187] = 6; + table[7 * 256 + 188] = 6; + table[7 * 256 + 189] = 6; + table[7 * 256 + 190] = 6; + table[7 * 256 + 191] = 6; + table[8 * 256 + 160] = 7; + table[8 * 256 + 161] = 7; + table[8 * 256 + 162] = 7; + table[8 * 256 + 163] = 7; + table[8 * 256 + 164] = 7; + table[8 * 256 + 165] = 7; + table[8 * 256 + 166] = 7; + table[8 * 256 + 167] = 7; + table[8 * 256 + 168] = 7; + table[8 * 256 + 169] = 7; + table[8 * 256 + 170] = 7; + table[8 * 256 + 171] = 7; + table[8 * 256 + 172] = 7; + table[8 * 256 + 173] = 7; + table[8 * 256 + 174] = 7; + table[8 * 256 + 175] = 7; + table[8 * 256 + 176] = 7; + table[8 * 256 + 177] = 7; + table[8 * 256 + 178] = 7; + table[8 * 256 + 179] = 7; + table[8 * 256 + 180] = 7; + table[8 * 256 + 181] = 7; + table[8 * 256 + 182] = 7; + table[8 * 256 + 183] = 7; + table[8 * 256 + 184] = 7; + table[8 * 256 + 185] = 7; + table[8 * 256 + 186] = 7; + table[8 * 256 + 187] = 7; + table[8 * 256 + 188] = 7; + table[8 * 256 + 189] = 7; + table[8 * 256 + 190] = 7; + table[8 * 256 + 191] = 7; + table[9 * 256 + 128] = 7; + table[9 * 256 + 129] = 7; + table[9 * 256 + 130] = 7; + table[9 * 256 + 131] = 7; + table[9 * 256 + 132] = 7; + table[9 * 256 + 133] = 7; + table[9 * 256 + 134] = 7; + table[9 * 256 + 135] = 7; + table[9 * 256 + 136] = 7; + table[9 * 256 + 137] = 7; + table[9 * 256 + 138] = 7; + table[9 * 256 + 139] = 7; + table[9 * 256 + 140] = 7; + table[9 * 256 + 141] = 7; + table[9 * 256 + 142] = 7; + table[9 * 256 + 143] = 7; + table[9 * 256 + 144] = 7; + table[9 * 256 + 145] = 7; + table[9 * 256 + 146] = 7; + table[9 * 256 + 147] = 7; + table[9 * 256 + 148] = 7; + table[9 * 256 + 149] = 7; + table[9 * 256 + 150] = 7; + table[9 * 256 + 151] = 7; + table[9 * 256 + 152] = 7; + table[9 * 256 + 153] = 7; + table[9 * 256 + 154] = 7; + table[9 * 256 + 155] = 7; + table[9 * 256 + 156] = 7; + table[9 * 256 + 157] = 7; + table[9 * 256 + 158] = 7; + table[9 * 256 + 159] = 7; + table[9 * 256 + 160] = 7; + table[9 * 256 + 161] = 7; + table[9 * 256 + 162] = 7; + table[9 * 256 + 163] = 7; + table[9 * 256 + 164] = 7; + table[9 * 256 + 165] = 7; + table[9 * 256 + 166] = 7; + table[9 * 256 + 167] = 7; + table[9 * 256 + 168] = 7; + table[9 * 256 + 169] = 7; + table[9 * 256 + 170] = 7; + table[9 * 256 + 171] = 7; + table[9 * 256 + 172] = 7; + table[9 * 256 + 173] = 7; + table[9 * 256 + 174] = 7; + table[9 * 256 + 175] = 7; + table[9 * 256 + 176] = 7; + table[9 * 256 + 177] = 7; + table[9 * 256 + 178] = 7; + table[9 * 256 + 179] = 7; + table[9 * 256 + 180] = 7; + table[9 * 256 + 181] = 7; + table[9 * 256 + 182] = 7; + table[9 * 256 + 183] = 7; + table[9 * 256 + 184] = 7; + table[9 * 256 + 185] = 7; + table[9 * 256 + 186] = 7; + table[9 * 256 + 187] = 7; + table[9 * 256 + 188] = 7; + table[9 * 256 + 189] = 7; + table[9 * 256 + 190] = 7; + table[9 * 256 + 191] = 7; + table[10 * 256 + 128] = 7; + table[10 * 256 + 129] = 7; + table[10 * 256 + 130] = 7; + table[10 * 256 + 131] = 7; + table[10 * 256 + 132] = 7; + table[10 * 256 + 133] = 7; + table[10 * 256 + 134] = 7; + table[10 * 256 + 135] = 7; + table[10 * 256 + 136] = 7; + table[10 * 256 + 137] = 7; + table[10 * 256 + 138] = 7; + table[10 * 256 + 139] = 7; + table[10 * 256 + 140] = 7; + table[10 * 256 + 141] = 7; + table[10 * 256 + 142] = 7; + table[10 * 256 + 143] = 7; + table[10 * 256 + 144] = 7; + table[10 * 256 + 145] = 7; + table[10 * 256 + 146] = 7; + table[10 * 256 + 147] = 7; + table[10 * 256 + 148] = 7; + table[10 * 256 + 149] = 7; + table[10 * 256 + 150] = 7; + table[10 * 256 + 151] = 7; + table[10 * 256 + 152] = 7; + table[10 * 256 + 153] = 7; + table[10 * 256 + 154] = 7; + table[10 * 256 + 155] = 7; + table[10 * 256 + 156] = 7; + table[10 * 256 + 157] = 7; + table[10 * 256 + 158] = 7; + table[10 * 256 + 159] = 7; + table[11 * 256 + 144] = 9; + table[11 * 256 + 145] = 9; + table[11 * 256 + 146] = 9; + table[11 * 256 + 147] = 9; + table[11 * 256 + 148] = 9; + table[11 * 256 + 149] = 9; + table[11 * 256 + 150] = 9; + table[11 * 256 + 151] = 9; + table[11 * 256 + 152] = 9; + table[11 * 256 + 153] = 9; + table[11 * 256 + 154] = 9; + table[11 * 256 + 155] = 9; + table[11 * 256 + 156] = 9; + table[11 * 256 + 157] = 9; + table[11 * 256 + 158] = 9; + table[11 * 256 + 159] = 9; + table[11 * 256 + 160] = 9; + table[11 * 256 + 161] = 9; + table[11 * 256 + 162] = 9; + table[11 * 256 + 163] = 9; + table[11 * 256 + 164] = 9; + table[11 * 256 + 165] = 9; + table[11 * 256 + 166] = 9; + table[11 * 256 + 167] = 9; + table[11 * 256 + 168] = 9; + table[11 * 256 + 169] = 9; + table[11 * 256 + 170] = 9; + table[11 * 256 + 171] = 9; + table[11 * 256 + 172] = 9; + table[11 * 256 + 173] = 9; + table[11 * 256 + 174] = 9; + table[11 * 256 + 175] = 9; + table[11 * 256 + 176] = 9; + table[11 * 256 + 177] = 9; + table[11 * 256 + 178] = 9; + table[11 * 256 + 179] = 9; + table[11 * 256 + 180] = 9; + table[11 * 256 + 181] = 9; + table[11 * 256 + 182] = 9; + table[11 * 256 + 183] = 9; + table[11 * 256 + 184] = 9; + table[11 * 256 + 185] = 9; + table[11 * 256 + 186] = 9; + table[11 * 256 + 187] = 9; + table[11 * 256 + 188] = 9; + table[11 * 256 + 189] = 9; + table[11 * 256 + 190] = 9; + table[11 * 256 + 191] = 9; + table[12 * 256 + 128] = 9; + table[12 * 256 + 129] = 9; + table[12 * 256 + 130] = 9; + table[12 * 256 + 131] = 9; + table[12 * 256 + 132] = 9; + table[12 * 256 + 133] = 9; + table[12 * 256 + 134] = 9; + table[12 * 256 + 135] = 9; + table[12 * 256 + 136] = 9; + table[12 * 256 + 137] = 9; + table[12 * 256 + 138] = 9; + table[12 * 256 + 139] = 9; + table[12 * 256 + 140] = 9; + table[12 * 256 + 141] = 9; + table[12 * 256 + 142] = 9; + table[12 * 256 + 143] = 9; + table[12 * 256 + 144] = 9; + table[12 * 256 + 145] = 9; + table[12 * 256 + 146] = 9; + table[12 * 256 + 147] = 9; + table[12 * 256 + 148] = 9; + table[12 * 256 + 149] = 9; + table[12 * 256 + 150] = 9; + table[12 * 256 + 151] = 9; + table[12 * 256 + 152] = 9; + table[12 * 256 + 153] = 9; + table[12 * 256 + 154] = 9; + table[12 * 256 + 155] = 9; + table[12 * 256 + 156] = 9; + table[12 * 256 + 157] = 9; + table[12 * 256 + 158] = 9; + table[12 * 256 + 159] = 9; + table[12 * 256 + 160] = 9; + table[12 * 256 + 161] = 9; + table[12 * 256 + 162] = 9; + table[12 * 256 + 163] = 9; + table[12 * 256 + 164] = 9; + table[12 * 256 + 165] = 9; + table[12 * 256 + 166] = 9; + table[12 * 256 + 167] = 9; + table[12 * 256 + 168] = 9; + table[12 * 256 + 169] = 9; + table[12 * 256 + 170] = 9; + table[12 * 256 + 171] = 9; + table[12 * 256 + 172] = 9; + table[12 * 256 + 173] = 9; + table[12 * 256 + 174] = 9; + table[12 * 256 + 175] = 9; + table[12 * 256 + 176] = 9; + table[12 * 256 + 177] = 9; + table[12 * 256 + 178] = 9; + table[12 * 256 + 179] = 9; + table[12 * 256 + 180] = 9; + table[12 * 256 + 181] = 9; + table[12 * 256 + 182] = 9; + table[12 * 256 + 183] = 9; + table[12 * 256 + 184] = 9; + table[12 * 256 + 185] = 9; + table[12 * 256 + 186] = 9; + table[12 * 256 + 187] = 9; + table[12 * 256 + 188] = 9; + table[12 * 256 + 189] = 9; + table[12 * 256 + 190] = 9; + table[12 * 256 + 191] = 9; + table[13 * 256 + 128] = 9; + table[13 * 256 + 129] = 9; + table[13 * 256 + 130] = 9; + table[13 * 256 + 131] = 9; + table[13 * 256 + 132] = 9; + table[13 * 256 + 133] = 9; + table[13 * 256 + 134] = 9; + table[13 * 256 + 135] = 9; + table[13 * 256 + 136] = 9; + table[13 * 256 + 137] = 9; + table[13 * 256 + 138] = 9; + table[13 * 256 + 139] = 9; + table[13 * 256 + 140] = 9; + table[13 * 256 + 141] = 9; + table[13 * 256 + 142] = 9; + table[13 * 256 + 143] = 9; + table[14 * 256 + 10] = 15; + + table +} +pub fn regex_match(input: [u8; N]) -> bool { + // regex: (\r\n|^)to:[^\r\n]+\r\n + let mut s = 0; + s = table[255]; + for i in 0..input.len() { + let s_idx = s * 256 + input[i] as Field; + std::as_witness(s_idx); + s = table[s_idx]; + } + + let matched: bool = (s == 15) | (s == 16); + + matched +} + + \ No newline at end of file diff --git a/packages/noir/src/capture/composite/decoded_body_hash.nr b/packages/noir/src/capture/composite/decoded_body_hash.nr new file mode 100644 index 00000000..a17da2e0 --- /dev/null +++ b/packages/noir/src/capture/composite/decoded_body_hash.nr @@ -0,0 +1,60 @@ +use crate::{ + capture::raw::body_hash, + common::Sequence, + constants::{BODY_HASH_BASE64_LEN, BODY_HASH_LEN}, +}; +use base64::BASE64_DECODER; + +/** + * Extract body hash from input given a sequence using regex match and capture + * @dev function performs base64 decoding and returns exact array length since length always the same + * + * @param input: input to extract body hash from + * @returns the extracted body hash after base64 decoding + */ +pub fn regex_match(input: BoundedVec) -> [u8; BODY_HASH_LEN] { + let (sequence, found) = body_hash::regex_match(input.storage()); + assert(found, "Body hash regex match failure over input"); + extract_body_hash(input, sequence.get(0)) +} + +/** + * Extract body hash from input given a sequence + * + * @param input: input to extract body hash from + * @param bh_sequence: sequence to extract body hash from + */ +fn extract_body_hash( + input: BoundedVec, + sequence: Sequence, +) -> [u8; BODY_HASH_LEN] { + // constrain extraction of body hash from input given sequence + let encoded_body_hash = unsafe { __extract_encoded_body_hash(input, sequence.index()) }; + assert(sequence.end() < input.len(), "Body hash sequence out of input boundary"); + for i in 0..BODY_HASH_BASE64_LEN { + let expected_byte = input.get_unchecked(sequence.index() + i) as Field; + let byte = encoded_body_hash[i] as Field; + assert(expected_byte == byte, "Could not properly construct body hash array"); + } + // base64 decode body hash + BASE64_DECODER.decode(encoded_body_hash) +} + +/** + * Unconstrained extraction of b64-encoded body hash sequence given starting index and input to extract from + * @dev SHOULD NOT BE USED EXCEPT FROM `extract_body_hash` + * + * @param input - input to extract body hash from + * @param index - starting index to extract body hash from + * @returns the b64-encoded body hash sequence + */ +unconstrained fn __extract_encoded_body_hash( + input: BoundedVec, + index: u32 +) -> [u8; BODY_HASH_BASE64_LEN] { + let mut body_hash_encoded: [u8; BODY_HASH_BASE64_LEN] = [0; BODY_HASH_BASE64_LEN]; + for i in 0..BODY_HASH_BASE64_LEN { + body_hash_encoded[i] = input.get_unchecked(index + i); + } + body_hash_encoded +} \ No newline at end of file diff --git a/packages/noir/src/capture/composite/from_addr.nr b/packages/noir/src/capture/composite/from_addr.nr new file mode 100644 index 00000000..ff567a70 --- /dev/null +++ b/packages/noir/src/capture/composite/from_addr.nr @@ -0,0 +1,193 @@ +use crate::{ + capture::raw::{from_all, email_addr as email_addr_capture}, + basic::email_addr, + common::{extract_substring, reverse_vec}, + constants::{ADDR_REGEX_MAX_CAPTURE_LEN, FROM_ALL_MAX_LEN} +}; + +fn regex_match(input: [u8; N]) -> (BoundedVec, bool) { + let (from_all_sequence, from_all_match) = from_all::regex_match(input); + assert(from_all_sequence.len() == 1, "Expected sequence found to from_all match"); + assert(from_all_match, "Expected match found to from_all match"); + let from_all_substring: BoundedVec = extract_substring(from_all_sequence.get_unchecked(0), input); + + let reversed_from_all_substring = reverse_vec(from_all_substring); + + // At least 1 of the 2 should return true + // This extracts the first occurence of an email address between brackets <> of the reversed string + // (this ensure the last occurrence of an email is extracted) + let addr_found = email_addr::regex_match(from_all_substring.storage()); + let addr_reversed_found = email_addr::regex_match(reversed_from_all_substring.storage()); + + let mut input_to_use = from_all_substring; + if addr_reversed_found { + input_to_use = reversed_from_all_substring; + } + let (sequence, _) = email_addr_capture::regex_match(input_to_use.storage()); + + // If email between "<>" was obtained, return that + // otherwise return any email that was encountered + // otherwise this should fail since no valid email was found + + // check reversed + let mut substring = extract_substring(sequence.get_unchecked(0), input_to_use.storage()); + let unreversed = reverse_vec(substring); + if addr_reversed_found { + substring = unreversed; + } + (substring, addr_reversed_found | addr_found) +} + +#[test] +fn test_valid_1() { + // "from field from beginning case 1" + let expected_match: BoundedVec = BoundedVec::from_array("suegamisora@gmail.com".as_bytes()); + let input = "from:suegamisora@gmail.com\r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_2() { + // "from field from beginning case 2" + let expected_match: BoundedVec = BoundedVec::from_array("suegamisora@gmail.com".as_bytes()); + let input = "from:Sora Suegami \r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_3() { + // "from field from beginning case 3 (email address as a name)" + let expected_match: BoundedVec = BoundedVec::from_array("suegamisora@gmail.com".as_bytes()); + let input = "from:dummy@example.com\r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_4() { + // "from field from beginning case 4 (non-English string is used as a name)" + let expected_match: BoundedVec = BoundedVec::from_array("suegamisora@gmail.com".as_bytes()); + let input = "from: \"末神奏宙\" \r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_5() { + // "from field after new line case 1" + let expected_match: BoundedVec = BoundedVec::from_array("suegamisora@gmail.com".as_bytes()); + let input = "dummy\r\nfrom:suegamisora@gmail.com\r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_6() { + // "from field after new line case 2" + let expected_match: BoundedVec = BoundedVec::from_array("suegamisora@gmail.com".as_bytes()); + let input = "dummy\r\nfrom:Sora Suegami \r\n".as_bytes(); + +} + +#[test] +fn test_valid_7() { + // "from field after new line case 3 (email address as a name)" + let expected_match: BoundedVec = BoundedVec::from_array("suegamisora@gmail.com".as_bytes()); + let input = "dummy\r\nfrom:dummy@example.com\r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_8() { + // "from field after new line case 4 (non-English string is used as a name)" + let expected_match: BoundedVec = BoundedVec::from_array("suegamisora@gmail.com".as_bytes()); + let input = "dummy\r\nfrom: \"末神奏宙\" \r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_9() { + // "from field containing @ in the name part" + let expected_match: BoundedVec = BoundedVec::from_array("suegamisora@gmail.com@dummy.com".as_bytes()); + let input = "from:Sora Suegami \r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_10() { + // "from field containing @ in the name part" + let expected_match: BoundedVec = BoundedVec::from_array("@gmail.com@dummy.com".as_bytes()); + let input = "from:Sora Suegami <@gmail.com@dummy.com>\r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_11() { + // "from field with double <> 1" + let expected_match: BoundedVec = BoundedVec::from_array("attacker@outlook.com".as_bytes()); + let input = "from:\"Some name \" \r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_12() { + // "from field with double <> 2" + let expected_match: BoundedVec = BoundedVec::from_array("attacker@outlook.com".as_bytes()); + let input = "from:\"Some name \" < attacker@outlook.com>\r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_13() { + // "from field with double <> 3" + let expected_match: BoundedVec = BoundedVec::from_array("attacker@outlook.com".as_bytes()); + let input = "from:\"Some name \" \r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_14() { // "from field with triple <>" + let expected_match: BoundedVec = BoundedVec::from_array("attacker@outlook.com".as_bytes()); + let input = "from:\"Some name >\" \r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + + +// #[test(should_fail)] +fn test_invalid_1() { + // why does it error? commenting line 19 and 20 (and further down changes) makes it pass so not super worried + // same as to_addr + // "from field in the invalid field" + let input = "\r\nto:from:Sora Suegami \r\n".as_bytes(); + let _ = regex_match(input); +} + +#[test(should_fail)] +fn test_invalid_2() { + // "invalid from field with 255" + let input = &[255, 49].append("from:Sora Suegami \r\n".as_bytes()).as_array(); + let _ = regex_match(input); +} \ No newline at end of file diff --git a/packages/noir/src/capture/composite/mod.nr b/packages/noir/src/capture/composite/mod.nr new file mode 100644 index 00000000..94b3e81d --- /dev/null +++ b/packages/noir/src/capture/composite/mod.nr @@ -0,0 +1,4 @@ +pub mod from_addr; +pub mod to_addr; +pub mod decoded_body_hash; +pub mod timestamp; \ No newline at end of file diff --git a/packages/noir/src/capture/composite/timestamp.nr b/packages/noir/src/capture/composite/timestamp.nr new file mode 100644 index 00000000..f0b73c85 --- /dev/null +++ b/packages/noir/src/capture/composite/timestamp.nr @@ -0,0 +1,74 @@ +use crate::{ + capture::raw::timestamp as timestamp_regex, + common::Sequence, + constants::{TIMESTAMP_LEN}, +}; + +/** + * Extract timestamp + * + * @param input: input to extract timestamp from + * @returns the timestamp given to the email by the MTA + */ +pub fn regex_match(input: BoundedVec) -> [u8; TIMESTAMP_LEN] { + let (sequence, found) = timestamp_regex::regex_match(input.storage()); + assert(found, "Body hash regex match failure over input"); + extract_timestamp(input, sequence.get(0)) +} + +/** + * Converts an extracted unix timestamp to the numerical representation + * + * @param timestamp: timestamp to convert to number + * @returns the same timestamp as a field element (cast as needed) + */ +pub fn parse_timestamp(timestamp: [u8; N]) -> Field { + let mut number: Field = 0; + for i in 0..N { + let byte = timestamp[N - i - 1]; + assert((0x30 <= byte) & (byte <= 0x39), "Timestamp byte is not a UTF-8 digit"); + let digit = byte as Field - 0x30; + number += digit * 10.pow_32(i as Field); + } + number +} + +/** + * Extract timestamp from input given a sequence + * + * @param input: input to extract timestamp from + * @param sequence: sequence to extract timestamp from + */ +fn extract_timestamp( + input: BoundedVec, + sequence: Sequence, +) -> [u8; TIMESTAMP_LEN] { + // constrain extraction of timestamp from input given sequence + let timestamp = unsafe { __extract_timestamp(input, sequence.index()) }; + assert(sequence.end() < input.len(), "Timestamp sequence out of input boundary"); + for i in 0..TIMESTAMP_LEN { + let expected_byte = input.get_unchecked(sequence.index() + i) as Field; + let byte = timestamp[i] as Field; + assert(expected_byte == byte, "Could not properly construct timestamp array"); + } + timestamp +} + +/** + * Unconstrained extraction of timestamp from email header + * @dev SHOULD NOT BE USED EXCEPT FROM `extract_timestamp` + * + * @param input - input to extract timestamp from + * @param index - starting index to extract timestamp from + * @returns the timestamp given to the email by the MTA + */ +unconstrained fn __extract_timestamp( + input: BoundedVec, + index: u32, +) -> [u8; TIMESTAMP_LEN] { + let mut timestamp: [u8; TIMESTAMP_LEN] = [0; TIMESTAMP_LEN]; + for i in 0..TIMESTAMP_LEN { + timestamp[i] = input.get_unchecked(index + i); + } + timestamp +} \ No newline at end of file diff --git a/packages/noir/src/capture/composite/to_addr.nr b/packages/noir/src/capture/composite/to_addr.nr new file mode 100644 index 00000000..79f943d7 --- /dev/null +++ b/packages/noir/src/capture/composite/to_addr.nr @@ -0,0 +1,197 @@ +use crate::{ + capture::raw::{to_all, email_addr as email_addr_capture}, + basic::email_addr, + common::{extract_substring, reverse_vec}, + constants::{ADDR_REGEX_MAX_CAPTURE_LEN, TO_ALL_MAX_LEN} +}; + +fn regex_match(input: [u8; N]) -> (BoundedVec, bool) { + let (to_all_sequence, to_all_match) = to_all::regex_match(input); + assert(to_all_sequence.len() == 1, "Expected sequence found to to_all match"); + assert(to_all_match, "Expected match found to to_all match"); + let to_all_substring: BoundedVec = extract_substring(to_all_sequence.get_unchecked(0), input); + + let reversed_to_all_substring = reverse_vec(to_all_substring); + + // At least 1 of the 2 should return true + // This extracts the first occurence of an email address between brackets <> of the reversed string + // (this ensure the last occurrence of an email is extracted) + let addr_found = email_addr::regex_match(to_all_substring.storage()); + let addr_reversed_found = email_addr::regex_match(reversed_to_all_substring.storage()); + + let mut input_to_use = to_all_substring; + if addr_reversed_found { + input_to_use = reversed_to_all_substring; + } + let (sequence, _) = email_addr_capture::regex_match(input_to_use.storage()); + + // If email between "<>" was obtained, return that + // otherwise return any email that was encountered + // otherwise this should fail since no valid email was found + + // check reversed + let mut substring = extract_substring(sequence.get_unchecked(0), input_to_use.storage()); + let unreversed = reverse_vec(substring); + if addr_reversed_found { + substring = unreversed; + } + (substring, addr_reversed_found | addr_found) +} + +/// TESTS /// + +#[test] +fn test_valid_1() { + // "to field from beginning case 1" + let expected_match: BoundedVec = BoundedVec::from_array("adityabisht@gmail.com".as_bytes()); + let input = "to:adityabisht@gmail.com\r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_2() { + // "to field from beginning case 2" + let expected_match: BoundedVec = BoundedVec::from_array("adityabisht@gmail.com".as_bytes()); + let input = "to:Aditya Bisht \r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_3() { + // "to field from beginning case 3 (email address as a name)" + let expected_match: BoundedVec = BoundedVec::from_array("adityabisht@gmail.com".as_bytes()); + let input = "to:dummy@example.com\r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_4() { + // "to field from beginning case 4 (non-English string is used as a name)" + let expected_match: BoundedVec = BoundedVec::from_array("adityabisht@gmail.com".as_bytes()); + let input = "to: \"忠片返年\" \r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_5() { + // "to field after new line case 1" + let expected_match: BoundedVec = BoundedVec::from_array("adityabisht@gmail.com".as_bytes()); + let input = "dummy\r\nto:adityabisht@gmail.com\r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_6() { + // "to field after new line case 2" + let expected_match: BoundedVec = BoundedVec::from_array("adityabisht@gmail.com".as_bytes()); + let input = "dummy\r\nto:Sora Suegami \r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_7() { + // "to field after new line case 3 (email address as a name)" + let expected_match: BoundedVec = BoundedVec::from_array("adityabisht@gmail.com".as_bytes()); + let input = "dummy\r\nto:dummy@example.com\r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_8() { + // "to field after new line case 4 (non-English string is used as a name)" + let expected_match: BoundedVec = BoundedVec::from_array("adityabisht@gmail.com".as_bytes()); + let input = "dummy\r\nto: \"忠片返年\" \r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_9() { + // "to field containing @ in the name part" + let expected_match: BoundedVec = BoundedVec::from_array("adityabisht@gmail.com@dummy.com".as_bytes()); + let input = "to:Aditya Bisht \r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_10() { + // FAILS + let expected_match: BoundedVec = BoundedVec::from_array("@gmail.com@dummy.com".as_bytes()); + let input = "to:Aditya Bisht <@gmail.com@dummy.com>\r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_11() { + // "to field with double <> 1" + let expected_match: BoundedVec = BoundedVec::from_array("attacker@outlook.com".as_bytes()); + let input = "to:\"Some name \" \r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_12() { + // "to field with double <> 2" + let expected_match: BoundedVec = BoundedVec::from_array("attacker@outlook.com".as_bytes()); + let input = "to:\"Some name \" < attacker@outlook.com>\r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_13() { + // "to field with double <> 3" + let expected_match: BoundedVec = BoundedVec::from_array("attacker@outlook.com".as_bytes()); + let input = "to:\"Some name \" \r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +#[test] +fn test_valid_14() { + // "to field with triple <>" + let expected_match: BoundedVec = BoundedVec::from_array("attacker@outlook.com".as_bytes()); + let input = "to:\"Some name >\" \r\n".as_bytes(); + let (matched_substr, found) = regex_match(input); + assert(found, "Match not found"); + assert_eq(matched_substr, expected_match, "Extracted substring does not match expected substring"); +} + +// #[test(should_fail)] +fn test_invalid_1() { + // why does it error? commenting line 19 and 20 (and further down changes) makes it pass so not super worried + // same as from_addr + // "to field in the invalid field" + let input = "subject:to:adityabisht@gmail.com\r\n".as_bytes(); + let _ = regex_match(input); +} + +#[test(should_fail)] +fn test_invalid_2() { + // "invalid to field with 255" + let input = &[255, 49].append("to:adityabisht@gmail.com\r\n".as_bytes()).as_array(); + let _ = regex_match(input); +} diff --git a/packages/noir/src/capture/mod.nr b/packages/noir/src/capture/mod.nr new file mode 100644 index 00000000..c3355e55 --- /dev/null +++ b/packages/noir/src/capture/mod.nr @@ -0,0 +1,2 @@ +pub mod composite; +pub mod raw; \ No newline at end of file diff --git a/packages/noir/src/capture/raw/basic.nr b/packages/noir/src/capture/raw/basic.nr new file mode 100644 index 00000000..ed81d4ac --- /dev/null +++ b/packages/noir/src/capture/raw/basic.nr @@ -0,0 +1,690 @@ + +use crate::common::Sequence; + + +global table: [Field; 1280] = comptime { make_lookup_table() }; + +comptime fn make_lookup_table() -> [Field; 1280] { + let mut table = [0; 1280]; + table[3 * 256 + 0] = 4; + table[4 * 256 + 0] = 4; + table[3 * 256 + 1] = 4; + table[4 * 256 + 1] = 4; + table[3 * 256 + 2] = 4; + table[4 * 256 + 2] = 4; + table[3 * 256 + 3] = 4; + table[4 * 256 + 3] = 4; + table[3 * 256 + 4] = 4; + table[4 * 256 + 4] = 4; + table[3 * 256 + 5] = 4; + table[4 * 256 + 5] = 4; + table[3 * 256 + 6] = 4; + table[4 * 256 + 6] = 4; + table[3 * 256 + 7] = 4; + table[4 * 256 + 7] = 4; + table[3 * 256 + 8] = 4; + table[4 * 256 + 8] = 4; + table[3 * 256 + 9] = 4; + table[4 * 256 + 9] = 4; + table[3 * 256 + 10] = 4; + table[4 * 256 + 10] = 4; + table[3 * 256 + 11] = 4; + table[4 * 256 + 11] = 4; + table[3 * 256 + 12] = 4; + table[4 * 256 + 12] = 4; + table[3 * 256 + 13] = 4; + table[4 * 256 + 13] = 4; + table[3 * 256 + 14] = 4; + table[4 * 256 + 14] = 4; + table[3 * 256 + 15] = 4; + table[4 * 256 + 15] = 4; + table[3 * 256 + 16] = 4; + table[4 * 256 + 16] = 4; + table[3 * 256 + 17] = 4; + table[4 * 256 + 17] = 4; + table[3 * 256 + 18] = 4; + table[4 * 256 + 18] = 4; + table[3 * 256 + 19] = 4; + table[4 * 256 + 19] = 4; + table[3 * 256 + 20] = 4; + table[4 * 256 + 20] = 4; + table[3 * 256 + 21] = 4; + table[4 * 256 + 21] = 4; + table[3 * 256 + 22] = 4; + table[4 * 256 + 22] = 4; + table[3 * 256 + 23] = 4; + table[4 * 256 + 23] = 4; + table[3 * 256 + 24] = 4; + table[4 * 256 + 24] = 4; + table[3 * 256 + 25] = 4; + table[4 * 256 + 25] = 4; + table[3 * 256 + 26] = 4; + table[4 * 256 + 26] = 4; + table[3 * 256 + 27] = 4; + table[4 * 256 + 27] = 4; + table[3 * 256 + 28] = 4; + table[4 * 256 + 28] = 4; + table[3 * 256 + 29] = 4; + table[4 * 256 + 29] = 4; + table[3 * 256 + 30] = 4; + table[4 * 256 + 30] = 4; + table[3 * 256 + 31] = 4; + table[4 * 256 + 31] = 4; + table[3 * 256 + 32] = 4; + table[4 * 256 + 32] = 4; + table[3 * 256 + 33] = 4; + table[4 * 256 + 33] = 4; + table[3 * 256 + 34] = 4; + table[4 * 256 + 34] = 4; + table[3 * 256 + 35] = 4; + table[4 * 256 + 35] = 4; + table[3 * 256 + 36] = 4; + table[4 * 256 + 36] = 4; + table[3 * 256 + 37] = 4; + table[4 * 256 + 37] = 4; + table[3 * 256 + 38] = 4; + table[4 * 256 + 38] = 4; + table[3 * 256 + 39] = 4; + table[4 * 256 + 39] = 4; + table[3 * 256 + 40] = 4; + table[4 * 256 + 40] = 4; + table[3 * 256 + 41] = 4; + table[4 * 256 + 41] = 4; + table[3 * 256 + 42] = 4; + table[4 * 256 + 42] = 4; + table[3 * 256 + 43] = 4; + table[4 * 256 + 43] = 4; + table[3 * 256 + 44] = 4; + table[4 * 256 + 44] = 4; + table[3 * 256 + 45] = 4; + table[4 * 256 + 45] = 4; + table[3 * 256 + 46] = 4; + table[4 * 256 + 46] = 4; + table[3 * 256 + 47] = 4; + table[4 * 256 + 47] = 4; + table[3 * 256 + 48] = 4; + table[4 * 256 + 48] = 4; + table[3 * 256 + 49] = 4; + table[4 * 256 + 49] = 4; + table[3 * 256 + 50] = 4; + table[4 * 256 + 50] = 4; + table[3 * 256 + 51] = 4; + table[4 * 256 + 51] = 4; + table[3 * 256 + 52] = 4; + table[4 * 256 + 52] = 4; + table[3 * 256 + 53] = 4; + table[4 * 256 + 53] = 4; + table[3 * 256 + 54] = 4; + table[4 * 256 + 54] = 4; + table[3 * 256 + 55] = 4; + table[4 * 256 + 55] = 4; + table[3 * 256 + 56] = 4; + table[4 * 256 + 56] = 4; + table[3 * 256 + 57] = 4; + table[4 * 256 + 57] = 4; + table[3 * 256 + 58] = 4; + table[4 * 256 + 58] = 4; + table[3 * 256 + 59] = 4; + table[4 * 256 + 59] = 4; + table[3 * 256 + 60] = 4; + table[4 * 256 + 60] = 4; + table[3 * 256 + 61] = 4; + table[4 * 256 + 61] = 4; + table[3 * 256 + 62] = 4; + table[4 * 256 + 62] = 4; + table[3 * 256 + 63] = 4; + table[4 * 256 + 63] = 4; + table[3 * 256 + 64] = 4; + table[4 * 256 + 64] = 4; + table[3 * 256 + 65] = 4; + table[4 * 256 + 65] = 4; + table[3 * 256 + 66] = 4; + table[4 * 256 + 66] = 4; + table[3 * 256 + 67] = 4; + table[4 * 256 + 67] = 4; + table[3 * 256 + 68] = 4; + table[4 * 256 + 68] = 4; + table[3 * 256 + 69] = 4; + table[4 * 256 + 69] = 4; + table[3 * 256 + 70] = 4; + table[4 * 256 + 70] = 4; + table[3 * 256 + 71] = 4; + table[4 * 256 + 71] = 4; + table[3 * 256 + 72] = 4; + table[4 * 256 + 72] = 4; + table[3 * 256 + 73] = 4; + table[4 * 256 + 73] = 4; + table[3 * 256 + 74] = 4; + table[4 * 256 + 74] = 4; + table[3 * 256 + 75] = 4; + table[4 * 256 + 75] = 4; + table[3 * 256 + 76] = 4; + table[4 * 256 + 76] = 4; + table[3 * 256 + 77] = 4; + table[4 * 256 + 77] = 4; + table[3 * 256 + 78] = 4; + table[4 * 256 + 78] = 4; + table[3 * 256 + 79] = 4; + table[4 * 256 + 79] = 4; + table[3 * 256 + 80] = 4; + table[4 * 256 + 80] = 4; + table[3 * 256 + 81] = 4; + table[4 * 256 + 81] = 4; + table[3 * 256 + 82] = 4; + table[4 * 256 + 82] = 4; + table[3 * 256 + 83] = 4; + table[4 * 256 + 83] = 4; + table[3 * 256 + 84] = 4; + table[4 * 256 + 84] = 4; + table[3 * 256 + 85] = 4; + table[4 * 256 + 85] = 4; + table[3 * 256 + 86] = 4; + table[4 * 256 + 86] = 4; + table[3 * 256 + 87] = 4; + table[4 * 256 + 87] = 4; + table[3 * 256 + 88] = 4; + table[4 * 256 + 88] = 4; + table[3 * 256 + 89] = 4; + table[4 * 256 + 89] = 4; + table[3 * 256 + 90] = 4; + table[4 * 256 + 90] = 4; + table[3 * 256 + 91] = 4; + table[4 * 256 + 91] = 4; + table[3 * 256 + 92] = 4; + table[4 * 256 + 92] = 4; + table[3 * 256 + 93] = 4; + table[4 * 256 + 93] = 4; + table[3 * 256 + 94] = 4; + table[4 * 256 + 94] = 4; + table[3 * 256 + 95] = 4; + table[4 * 256 + 95] = 4; + table[3 * 256 + 96] = 4; + table[4 * 256 + 96] = 4; + table[3 * 256 + 97] = 4; + table[4 * 256 + 97] = 4; + table[3 * 256 + 98] = 4; + table[4 * 256 + 98] = 4; + table[3 * 256 + 99] = 4; + table[4 * 256 + 99] = 4; + table[3 * 256 + 100] = 4; + table[4 * 256 + 100] = 4; + table[3 * 256 + 101] = 4; + table[4 * 256 + 101] = 4; + table[3 * 256 + 102] = 4; + table[4 * 256 + 102] = 4; + table[3 * 256 + 103] = 4; + table[4 * 256 + 103] = 4; + table[3 * 256 + 104] = 4; + table[4 * 256 + 104] = 4; + table[3 * 256 + 105] = 4; + table[4 * 256 + 105] = 4; + table[3 * 256 + 106] = 4; + table[4 * 256 + 106] = 4; + table[3 * 256 + 107] = 4; + table[4 * 256 + 107] = 4; + table[3 * 256 + 108] = 4; + table[4 * 256 + 108] = 4; + table[3 * 256 + 109] = 4; + table[4 * 256 + 109] = 4; + table[3 * 256 + 110] = 4; + table[4 * 256 + 110] = 4; + table[3 * 256 + 111] = 4; + table[4 * 256 + 111] = 4; + table[3 * 256 + 112] = 4; + table[4 * 256 + 112] = 4; + table[3 * 256 + 113] = 4; + table[4 * 256 + 113] = 4; + table[3 * 256 + 114] = 4; + table[4 * 256 + 114] = 4; + table[3 * 256 + 115] = 4; + table[4 * 256 + 115] = 4; + table[3 * 256 + 116] = 4; + table[4 * 256 + 116] = 4; + table[3 * 256 + 117] = 4; + table[4 * 256 + 117] = 4; + table[3 * 256 + 118] = 4; + table[4 * 256 + 118] = 4; + table[3 * 256 + 119] = 4; + table[4 * 256 + 119] = 4; + table[3 * 256 + 120] = 4; + table[4 * 256 + 120] = 4; + table[3 * 256 + 121] = 4; + table[4 * 256 + 121] = 4; + table[3 * 256 + 122] = 4; + table[4 * 256 + 122] = 4; + table[3 * 256 + 123] = 4; + table[4 * 256 + 123] = 4; + table[3 * 256 + 124] = 4; + table[4 * 256 + 124] = 4; + table[3 * 256 + 125] = 4; + table[4 * 256 + 125] = 4; + table[3 * 256 + 126] = 4; + table[4 * 256 + 126] = 4; + table[3 * 256 + 127] = 4; + table[4 * 256 + 127] = 4; + table[3 * 256 + 128] = 4; + table[4 * 256 + 128] = 4; + table[3 * 256 + 129] = 4; + table[4 * 256 + 129] = 4; + table[3 * 256 + 130] = 4; + table[4 * 256 + 130] = 4; + table[3 * 256 + 131] = 4; + table[4 * 256 + 131] = 4; + table[3 * 256 + 132] = 4; + table[4 * 256 + 132] = 4; + table[3 * 256 + 133] = 4; + table[4 * 256 + 133] = 4; + table[3 * 256 + 134] = 4; + table[4 * 256 + 134] = 4; + table[3 * 256 + 135] = 4; + table[4 * 256 + 135] = 4; + table[3 * 256 + 136] = 4; + table[4 * 256 + 136] = 4; + table[3 * 256 + 137] = 4; + table[4 * 256 + 137] = 4; + table[3 * 256 + 138] = 4; + table[4 * 256 + 138] = 4; + table[3 * 256 + 139] = 4; + table[4 * 256 + 139] = 4; + table[3 * 256 + 140] = 4; + table[4 * 256 + 140] = 4; + table[3 * 256 + 141] = 4; + table[4 * 256 + 141] = 4; + table[3 * 256 + 142] = 4; + table[4 * 256 + 142] = 4; + table[3 * 256 + 143] = 4; + table[4 * 256 + 143] = 4; + table[3 * 256 + 144] = 4; + table[4 * 256 + 144] = 4; + table[3 * 256 + 145] = 4; + table[4 * 256 + 145] = 4; + table[3 * 256 + 146] = 4; + table[4 * 256 + 146] = 4; + table[3 * 256 + 147] = 4; + table[4 * 256 + 147] = 4; + table[3 * 256 + 148] = 4; + table[4 * 256 + 148] = 4; + table[3 * 256 + 149] = 4; + table[4 * 256 + 149] = 4; + table[3 * 256 + 150] = 4; + table[4 * 256 + 150] = 4; + table[3 * 256 + 151] = 4; + table[4 * 256 + 151] = 4; + table[3 * 256 + 152] = 4; + table[4 * 256 + 152] = 4; + table[3 * 256 + 153] = 4; + table[4 * 256 + 153] = 4; + table[3 * 256 + 154] = 4; + table[4 * 256 + 154] = 4; + table[3 * 256 + 155] = 4; + table[4 * 256 + 155] = 4; + table[3 * 256 + 156] = 4; + table[4 * 256 + 156] = 4; + table[3 * 256 + 157] = 4; + table[4 * 256 + 157] = 4; + table[3 * 256 + 158] = 4; + table[4 * 256 + 158] = 4; + table[3 * 256 + 159] = 4; + table[4 * 256 + 159] = 4; + table[3 * 256 + 160] = 4; + table[4 * 256 + 160] = 4; + table[3 * 256 + 161] = 4; + table[4 * 256 + 161] = 4; + table[3 * 256 + 162] = 4; + table[4 * 256 + 162] = 4; + table[3 * 256 + 163] = 4; + table[4 * 256 + 163] = 4; + table[3 * 256 + 164] = 4; + table[4 * 256 + 164] = 4; + table[3 * 256 + 165] = 4; + table[4 * 256 + 165] = 4; + table[3 * 256 + 166] = 4; + table[4 * 256 + 166] = 4; + table[3 * 256 + 167] = 4; + table[4 * 256 + 167] = 4; + table[3 * 256 + 168] = 4; + table[4 * 256 + 168] = 4; + table[3 * 256 + 169] = 4; + table[4 * 256 + 169] = 4; + table[3 * 256 + 170] = 4; + table[4 * 256 + 170] = 4; + table[3 * 256 + 171] = 4; + table[4 * 256 + 171] = 4; + table[3 * 256 + 172] = 4; + table[4 * 256 + 172] = 4; + table[3 * 256 + 173] = 4; + table[4 * 256 + 173] = 4; + table[3 * 256 + 174] = 4; + table[4 * 256 + 174] = 4; + table[3 * 256 + 175] = 4; + table[4 * 256 + 175] = 4; + table[3 * 256 + 176] = 4; + table[4 * 256 + 176] = 4; + table[3 * 256 + 177] = 4; + table[4 * 256 + 177] = 4; + table[3 * 256 + 178] = 4; + table[4 * 256 + 178] = 4; + table[3 * 256 + 179] = 4; + table[4 * 256 + 179] = 4; + table[3 * 256 + 180] = 4; + table[4 * 256 + 180] = 4; + table[3 * 256 + 181] = 4; + table[4 * 256 + 181] = 4; + table[3 * 256 + 182] = 4; + table[4 * 256 + 182] = 4; + table[3 * 256 + 183] = 4; + table[4 * 256 + 183] = 4; + table[3 * 256 + 184] = 4; + table[4 * 256 + 184] = 4; + table[3 * 256 + 185] = 4; + table[4 * 256 + 185] = 4; + table[3 * 256 + 186] = 4; + table[4 * 256 + 186] = 4; + table[3 * 256 + 187] = 4; + table[4 * 256 + 187] = 4; + table[3 * 256 + 188] = 4; + table[4 * 256 + 188] = 4; + table[3 * 256 + 189] = 4; + table[4 * 256 + 189] = 4; + table[3 * 256 + 190] = 4; + table[4 * 256 + 190] = 4; + table[3 * 256 + 191] = 4; + table[4 * 256 + 191] = 4; + table[3 * 256 + 192] = 4; + table[4 * 256 + 192] = 4; + table[3 * 256 + 193] = 4; + table[4 * 256 + 193] = 4; + table[3 * 256 + 194] = 4; + table[4 * 256 + 194] = 4; + table[3 * 256 + 195] = 4; + table[4 * 256 + 195] = 4; + table[3 * 256 + 196] = 4; + table[4 * 256 + 196] = 4; + table[3 * 256 + 197] = 4; + table[4 * 256 + 197] = 4; + table[3 * 256 + 198] = 4; + table[4 * 256 + 198] = 4; + table[3 * 256 + 199] = 4; + table[4 * 256 + 199] = 4; + table[3 * 256 + 200] = 4; + table[4 * 256 + 200] = 4; + table[3 * 256 + 201] = 4; + table[4 * 256 + 201] = 4; + table[3 * 256 + 202] = 4; + table[4 * 256 + 202] = 4; + table[3 * 256 + 203] = 4; + table[4 * 256 + 203] = 4; + table[3 * 256 + 204] = 4; + table[4 * 256 + 204] = 4; + table[3 * 256 + 205] = 4; + table[4 * 256 + 205] = 4; + table[3 * 256 + 206] = 4; + table[4 * 256 + 206] = 4; + table[3 * 256 + 207] = 4; + table[4 * 256 + 207] = 4; + table[3 * 256 + 208] = 4; + table[4 * 256 + 208] = 4; + table[3 * 256 + 209] = 4; + table[4 * 256 + 209] = 4; + table[3 * 256 + 210] = 4; + table[4 * 256 + 210] = 4; + table[3 * 256 + 211] = 4; + table[4 * 256 + 211] = 4; + table[3 * 256 + 212] = 4; + table[4 * 256 + 212] = 4; + table[3 * 256 + 213] = 4; + table[4 * 256 + 213] = 4; + table[3 * 256 + 214] = 4; + table[4 * 256 + 214] = 4; + table[3 * 256 + 215] = 4; + table[4 * 256 + 215] = 4; + table[3 * 256 + 216] = 4; + table[4 * 256 + 216] = 4; + table[3 * 256 + 217] = 4; + table[4 * 256 + 217] = 4; + table[3 * 256 + 218] = 4; + table[4 * 256 + 218] = 4; + table[3 * 256 + 219] = 4; + table[4 * 256 + 219] = 4; + table[3 * 256 + 220] = 4; + table[4 * 256 + 220] = 4; + table[3 * 256 + 221] = 4; + table[4 * 256 + 221] = 4; + table[3 * 256 + 222] = 4; + table[4 * 256 + 222] = 4; + table[3 * 256 + 223] = 4; + table[4 * 256 + 223] = 4; + table[3 * 256 + 224] = 4; + table[4 * 256 + 224] = 4; + table[3 * 256 + 225] = 4; + table[4 * 256 + 225] = 4; + table[3 * 256 + 226] = 4; + table[4 * 256 + 226] = 4; + table[3 * 256 + 227] = 4; + table[4 * 256 + 227] = 4; + table[3 * 256 + 228] = 4; + table[4 * 256 + 228] = 4; + table[3 * 256 + 229] = 4; + table[4 * 256 + 229] = 4; + table[3 * 256 + 230] = 4; + table[4 * 256 + 230] = 4; + table[3 * 256 + 231] = 4; + table[4 * 256 + 231] = 4; + table[3 * 256 + 232] = 4; + table[4 * 256 + 232] = 4; + table[3 * 256 + 233] = 4; + table[4 * 256 + 233] = 4; + table[3 * 256 + 234] = 4; + table[4 * 256 + 234] = 4; + table[3 * 256 + 235] = 4; + table[4 * 256 + 235] = 4; + table[3 * 256 + 236] = 4; + table[4 * 256 + 236] = 4; + table[3 * 256 + 237] = 4; + table[4 * 256 + 237] = 4; + table[3 * 256 + 238] = 4; + table[4 * 256 + 238] = 4; + table[3 * 256 + 239] = 4; + table[4 * 256 + 239] = 4; + table[3 * 256 + 240] = 4; + table[4 * 256 + 240] = 4; + table[3 * 256 + 241] = 4; + table[4 * 256 + 241] = 4; + table[3 * 256 + 242] = 4; + table[4 * 256 + 242] = 4; + table[3 * 256 + 243] = 4; + table[4 * 256 + 243] = 4; + table[3 * 256 + 244] = 4; + table[4 * 256 + 244] = 4; + table[3 * 256 + 245] = 4; + table[4 * 256 + 245] = 4; + table[3 * 256 + 246] = 4; + table[4 * 256 + 246] = 4; + table[3 * 256 + 247] = 4; + table[4 * 256 + 247] = 4; + table[3 * 256 + 248] = 4; + table[4 * 256 + 248] = 4; + table[3 * 256 + 249] = 4; + table[4 * 256 + 249] = 4; + table[3 * 256 + 250] = 4; + table[4 * 256 + 250] = 4; + table[3 * 256 + 251] = 4; + table[4 * 256 + 251] = 4; + table[3 * 256 + 252] = 4; + table[4 * 256 + 252] = 4; + table[3 * 256 + 253] = 4; + table[4 * 256 + 253] = 4; + table[3 * 256 + 254] = 4; + table[4 * 256 + 254] = 4; + table[0 * 256 + 97] = 1; + table[1 * 256 + 98] = 2; + table[2 * 256 + 99] = 3; + + table +} + + +pub fn regex_match(input: [u8; N]) -> (BoundedVec, bool) { + let substrings = unsafe { __regex_match(input) }; + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + let mut start_range = 0; + let mut end_range = 0; + + // check the match + for i in 0..N { + // state transition + let temp = input[i] as Field; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + s = 0; + s_next = potential_s_next; + } + std::as_witness(s_next); + + // range conditions for substring matches + if ((start_range == 0) & (end_range == 0)) { + start_range = i as Field; + } + if (((s == 3) & (s_next == 4)) & (end_range == 0)) { + end_range = i as Field + 1; + } + + + let range_0 = substrings.get_unchecked(0).in_range(i); + let case_0 = [ + (s_next == 1) & ((s == 0)) + ].any(|case| case == true) | !range_0; + + let range_1 = substrings.get_unchecked(1).in_range(i); + let case_1 = [ + (s_next == 2) & ((s == 1)) + ].any(|case| case == true) | !range_1; + + let range_2 = substrings.get_unchecked(2).in_range(i); + let case_2 = [ + (s_next == 3) & ((s == 2)) + ].any(|case| case == true) | !range_2; + + + + let substring_range_check = [case_0, case_1, case_2] + .all(|case| case == true); + + assert(substring_range_check, "substr array ranges wrong"); + + + s = s_next; + } + // check final state + + let matched: bool = (s == 3) | (s == 4); + + // constrain extracted substrings to be in match range + //let full_match = Sequence::new(start_range as u32, end_range as u32 - start_range as u32); + //let full_match_end = full_match.end(); + // for i in 0..3 { + // let substring = substrings.get_unchecked(i); + // let is_not_valid = i >= substrings.len(); + // let index_check = substring.index >= full_match.index; + // let length_check = substring.end() <= full_match_end; + // let check = (index_check) | is_not_valid; + // assert(check, f"Substring {i} range is out of bounds of the full match found"); + // } + (substrings, matched) +} + + +pub unconstrained fn __regex_match(input: [u8; N]) -> BoundedVec { + // regex: abc + let mut substrings: BoundedVec = BoundedVec::new(); + let mut current_substring = Sequence::default(); + let mut full_match = Sequence::default(); + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + + let mut consecutive_substr = 0; + let mut complete = false; + + for i in 0..input.len() { + let temp = input[i] as Field; + let mut reset = false; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + reset = true; + s = 0; + s_next = potential_s_next; + } + // If a substring was in the making, but the state was reset + // we disregard previous progress because apparently it is invalid + if (reset & (consecutive_substr == 1)) { + current_substring = Sequence::default(); + consecutive_substr = 0; + } + // Fill up substrings + + + if ((s == 0) & (s_next == 1)) { + + if (consecutive_substr == 0) { + current_substring.index = i; + }; + current_substring.length += 1; + consecutive_substr = 1; + } + + else if ((s == 1) & (s_next == 2)) { + + current_substring.length += 1; + consecutive_substr = 1; + } + + else if ((s == 2) & (s_next == 3)) { + + current_substring.length += 1; + consecutive_substr = 1; + } else if ((consecutive_substr == 1) & (s_next == 0)) { + current_substring = Sequence::default(); + full_match = Sequence::default(); + substrings = BoundedVec::new(); + consecutive_substr = 0; + } else if (s == 3) & (s_next == 4) { + full_match.length = i - full_match.index + 1; + complete = true; + } else if (consecutive_substr == 1) { + // The substring is done so "save" it + substrings.push(current_substring); + // reset the substring holder for next use + current_substring = Sequence::default(); + consecutive_substr = 0; + } + s = s_next; + if complete == true { + break; + } + } + assert((s == 3) | (s == 4), f"no match: {s}"); + // Add pending substring that hasn't been added + if consecutive_substr == 1 { + substrings.push(current_substring); + full_match.length = input.len() - full_match.index; + } + + + + substrings +} + + + + \ No newline at end of file diff --git a/packages/noir/src/capture/raw/body_hash.nr b/packages/noir/src/capture/raw/body_hash.nr new file mode 100644 index 00000000..6a1d6437 --- /dev/null +++ b/packages/noir/src/capture/raw/body_hash.nr @@ -0,0 +1,1738 @@ + +use crate::common::Sequence; + + +global table: [Field; 9216] = comptime { make_lookup_table() }; + +comptime fn make_lookup_table() -> [Field; 9216] { + let mut table = [0; 9216]; + table[34 * 256 + 0] = 35; + table[35 * 256 + 0] = 35; + table[34 * 256 + 1] = 35; + table[35 * 256 + 1] = 35; + table[34 * 256 + 2] = 35; + table[35 * 256 + 2] = 35; + table[34 * 256 + 3] = 35; + table[35 * 256 + 3] = 35; + table[34 * 256 + 4] = 35; + table[35 * 256 + 4] = 35; + table[34 * 256 + 5] = 35; + table[35 * 256 + 5] = 35; + table[34 * 256 + 6] = 35; + table[35 * 256 + 6] = 35; + table[34 * 256 + 7] = 35; + table[35 * 256 + 7] = 35; + table[34 * 256 + 8] = 35; + table[35 * 256 + 8] = 35; + table[34 * 256 + 9] = 35; + table[35 * 256 + 9] = 35; + table[34 * 256 + 10] = 35; + table[35 * 256 + 10] = 35; + table[34 * 256 + 11] = 35; + table[35 * 256 + 11] = 35; + table[34 * 256 + 12] = 35; + table[35 * 256 + 12] = 35; + table[34 * 256 + 13] = 35; + table[35 * 256 + 13] = 35; + table[34 * 256 + 14] = 35; + table[35 * 256 + 14] = 35; + table[34 * 256 + 15] = 35; + table[35 * 256 + 15] = 35; + table[34 * 256 + 16] = 35; + table[35 * 256 + 16] = 35; + table[34 * 256 + 17] = 35; + table[35 * 256 + 17] = 35; + table[34 * 256 + 18] = 35; + table[35 * 256 + 18] = 35; + table[34 * 256 + 19] = 35; + table[35 * 256 + 19] = 35; + table[34 * 256 + 20] = 35; + table[35 * 256 + 20] = 35; + table[34 * 256 + 21] = 35; + table[35 * 256 + 21] = 35; + table[34 * 256 + 22] = 35; + table[35 * 256 + 22] = 35; + table[34 * 256 + 23] = 35; + table[35 * 256 + 23] = 35; + table[34 * 256 + 24] = 35; + table[35 * 256 + 24] = 35; + table[34 * 256 + 25] = 35; + table[35 * 256 + 25] = 35; + table[34 * 256 + 26] = 35; + table[35 * 256 + 26] = 35; + table[34 * 256 + 27] = 35; + table[35 * 256 + 27] = 35; + table[34 * 256 + 28] = 35; + table[35 * 256 + 28] = 35; + table[34 * 256 + 29] = 35; + table[35 * 256 + 29] = 35; + table[34 * 256 + 30] = 35; + table[35 * 256 + 30] = 35; + table[34 * 256 + 31] = 35; + table[35 * 256 + 31] = 35; + table[34 * 256 + 32] = 35; + table[35 * 256 + 32] = 35; + table[34 * 256 + 33] = 35; + table[35 * 256 + 33] = 35; + table[34 * 256 + 34] = 35; + table[35 * 256 + 34] = 35; + table[34 * 256 + 35] = 35; + table[35 * 256 + 35] = 35; + table[34 * 256 + 36] = 35; + table[35 * 256 + 36] = 35; + table[34 * 256 + 37] = 35; + table[35 * 256 + 37] = 35; + table[34 * 256 + 38] = 35; + table[35 * 256 + 38] = 35; + table[34 * 256 + 39] = 35; + table[35 * 256 + 39] = 35; + table[34 * 256 + 40] = 35; + table[35 * 256 + 40] = 35; + table[34 * 256 + 41] = 35; + table[35 * 256 + 41] = 35; + table[34 * 256 + 42] = 35; + table[35 * 256 + 42] = 35; + table[34 * 256 + 43] = 35; + table[35 * 256 + 43] = 35; + table[34 * 256 + 44] = 35; + table[35 * 256 + 44] = 35; + table[34 * 256 + 45] = 35; + table[35 * 256 + 45] = 35; + table[34 * 256 + 46] = 35; + table[35 * 256 + 46] = 35; + table[34 * 256 + 47] = 35; + table[35 * 256 + 47] = 35; + table[34 * 256 + 48] = 35; + table[35 * 256 + 48] = 35; + table[34 * 256 + 49] = 35; + table[35 * 256 + 49] = 35; + table[34 * 256 + 50] = 35; + table[35 * 256 + 50] = 35; + table[34 * 256 + 51] = 35; + table[35 * 256 + 51] = 35; + table[34 * 256 + 52] = 35; + table[35 * 256 + 52] = 35; + table[34 * 256 + 53] = 35; + table[35 * 256 + 53] = 35; + table[34 * 256 + 54] = 35; + table[35 * 256 + 54] = 35; + table[34 * 256 + 55] = 35; + table[35 * 256 + 55] = 35; + table[34 * 256 + 56] = 35; + table[35 * 256 + 56] = 35; + table[34 * 256 + 57] = 35; + table[35 * 256 + 57] = 35; + table[34 * 256 + 58] = 35; + table[35 * 256 + 58] = 35; + table[34 * 256 + 59] = 35; + table[35 * 256 + 59] = 35; + table[34 * 256 + 60] = 35; + table[35 * 256 + 60] = 35; + table[34 * 256 + 61] = 35; + table[35 * 256 + 61] = 35; + table[34 * 256 + 62] = 35; + table[35 * 256 + 62] = 35; + table[34 * 256 + 63] = 35; + table[35 * 256 + 63] = 35; + table[34 * 256 + 64] = 35; + table[35 * 256 + 64] = 35; + table[34 * 256 + 65] = 35; + table[35 * 256 + 65] = 35; + table[34 * 256 + 66] = 35; + table[35 * 256 + 66] = 35; + table[34 * 256 + 67] = 35; + table[35 * 256 + 67] = 35; + table[34 * 256 + 68] = 35; + table[35 * 256 + 68] = 35; + table[34 * 256 + 69] = 35; + table[35 * 256 + 69] = 35; + table[34 * 256 + 70] = 35; + table[35 * 256 + 70] = 35; + table[34 * 256 + 71] = 35; + table[35 * 256 + 71] = 35; + table[34 * 256 + 72] = 35; + table[35 * 256 + 72] = 35; + table[34 * 256 + 73] = 35; + table[35 * 256 + 73] = 35; + table[34 * 256 + 74] = 35; + table[35 * 256 + 74] = 35; + table[34 * 256 + 75] = 35; + table[35 * 256 + 75] = 35; + table[34 * 256 + 76] = 35; + table[35 * 256 + 76] = 35; + table[34 * 256 + 77] = 35; + table[35 * 256 + 77] = 35; + table[34 * 256 + 78] = 35; + table[35 * 256 + 78] = 35; + table[34 * 256 + 79] = 35; + table[35 * 256 + 79] = 35; + table[34 * 256 + 80] = 35; + table[35 * 256 + 80] = 35; + table[34 * 256 + 81] = 35; + table[35 * 256 + 81] = 35; + table[34 * 256 + 82] = 35; + table[35 * 256 + 82] = 35; + table[34 * 256 + 83] = 35; + table[35 * 256 + 83] = 35; + table[34 * 256 + 84] = 35; + table[35 * 256 + 84] = 35; + table[34 * 256 + 85] = 35; + table[35 * 256 + 85] = 35; + table[34 * 256 + 86] = 35; + table[35 * 256 + 86] = 35; + table[34 * 256 + 87] = 35; + table[35 * 256 + 87] = 35; + table[34 * 256 + 88] = 35; + table[35 * 256 + 88] = 35; + table[34 * 256 + 89] = 35; + table[35 * 256 + 89] = 35; + table[34 * 256 + 90] = 35; + table[35 * 256 + 90] = 35; + table[34 * 256 + 91] = 35; + table[35 * 256 + 91] = 35; + table[34 * 256 + 92] = 35; + table[35 * 256 + 92] = 35; + table[34 * 256 + 93] = 35; + table[35 * 256 + 93] = 35; + table[34 * 256 + 94] = 35; + table[35 * 256 + 94] = 35; + table[34 * 256 + 95] = 35; + table[35 * 256 + 95] = 35; + table[34 * 256 + 96] = 35; + table[35 * 256 + 96] = 35; + table[34 * 256 + 97] = 35; + table[35 * 256 + 97] = 35; + table[34 * 256 + 98] = 35; + table[35 * 256 + 98] = 35; + table[34 * 256 + 99] = 35; + table[35 * 256 + 99] = 35; + table[34 * 256 + 100] = 35; + table[35 * 256 + 100] = 35; + table[34 * 256 + 101] = 35; + table[35 * 256 + 101] = 35; + table[34 * 256 + 102] = 35; + table[35 * 256 + 102] = 35; + table[34 * 256 + 103] = 35; + table[35 * 256 + 103] = 35; + table[34 * 256 + 104] = 35; + table[35 * 256 + 104] = 35; + table[34 * 256 + 105] = 35; + table[35 * 256 + 105] = 35; + table[34 * 256 + 106] = 35; + table[35 * 256 + 106] = 35; + table[34 * 256 + 107] = 35; + table[35 * 256 + 107] = 35; + table[34 * 256 + 108] = 35; + table[35 * 256 + 108] = 35; + table[34 * 256 + 109] = 35; + table[35 * 256 + 109] = 35; + table[34 * 256 + 110] = 35; + table[35 * 256 + 110] = 35; + table[34 * 256 + 111] = 35; + table[35 * 256 + 111] = 35; + table[34 * 256 + 112] = 35; + table[35 * 256 + 112] = 35; + table[34 * 256 + 113] = 35; + table[35 * 256 + 113] = 35; + table[34 * 256 + 114] = 35; + table[35 * 256 + 114] = 35; + table[34 * 256 + 115] = 35; + table[35 * 256 + 115] = 35; + table[34 * 256 + 116] = 35; + table[35 * 256 + 116] = 35; + table[34 * 256 + 117] = 35; + table[35 * 256 + 117] = 35; + table[34 * 256 + 118] = 35; + table[35 * 256 + 118] = 35; + table[34 * 256 + 119] = 35; + table[35 * 256 + 119] = 35; + table[34 * 256 + 120] = 35; + table[35 * 256 + 120] = 35; + table[34 * 256 + 121] = 35; + table[35 * 256 + 121] = 35; + table[34 * 256 + 122] = 35; + table[35 * 256 + 122] = 35; + table[34 * 256 + 123] = 35; + table[35 * 256 + 123] = 35; + table[34 * 256 + 124] = 35; + table[35 * 256 + 124] = 35; + table[34 * 256 + 125] = 35; + table[35 * 256 + 125] = 35; + table[34 * 256 + 126] = 35; + table[35 * 256 + 126] = 35; + table[34 * 256 + 127] = 35; + table[35 * 256 + 127] = 35; + table[34 * 256 + 128] = 35; + table[35 * 256 + 128] = 35; + table[34 * 256 + 129] = 35; + table[35 * 256 + 129] = 35; + table[34 * 256 + 130] = 35; + table[35 * 256 + 130] = 35; + table[34 * 256 + 131] = 35; + table[35 * 256 + 131] = 35; + table[34 * 256 + 132] = 35; + table[35 * 256 + 132] = 35; + table[34 * 256 + 133] = 35; + table[35 * 256 + 133] = 35; + table[34 * 256 + 134] = 35; + table[35 * 256 + 134] = 35; + table[34 * 256 + 135] = 35; + table[35 * 256 + 135] = 35; + table[34 * 256 + 136] = 35; + table[35 * 256 + 136] = 35; + table[34 * 256 + 137] = 35; + table[35 * 256 + 137] = 35; + table[34 * 256 + 138] = 35; + table[35 * 256 + 138] = 35; + table[34 * 256 + 139] = 35; + table[35 * 256 + 139] = 35; + table[34 * 256 + 140] = 35; + table[35 * 256 + 140] = 35; + table[34 * 256 + 141] = 35; + table[35 * 256 + 141] = 35; + table[34 * 256 + 142] = 35; + table[35 * 256 + 142] = 35; + table[34 * 256 + 143] = 35; + table[35 * 256 + 143] = 35; + table[34 * 256 + 144] = 35; + table[35 * 256 + 144] = 35; + table[34 * 256 + 145] = 35; + table[35 * 256 + 145] = 35; + table[34 * 256 + 146] = 35; + table[35 * 256 + 146] = 35; + table[34 * 256 + 147] = 35; + table[35 * 256 + 147] = 35; + table[34 * 256 + 148] = 35; + table[35 * 256 + 148] = 35; + table[34 * 256 + 149] = 35; + table[35 * 256 + 149] = 35; + table[34 * 256 + 150] = 35; + table[35 * 256 + 150] = 35; + table[34 * 256 + 151] = 35; + table[35 * 256 + 151] = 35; + table[34 * 256 + 152] = 35; + table[35 * 256 + 152] = 35; + table[34 * 256 + 153] = 35; + table[35 * 256 + 153] = 35; + table[34 * 256 + 154] = 35; + table[35 * 256 + 154] = 35; + table[34 * 256 + 155] = 35; + table[35 * 256 + 155] = 35; + table[34 * 256 + 156] = 35; + table[35 * 256 + 156] = 35; + table[34 * 256 + 157] = 35; + table[35 * 256 + 157] = 35; + table[34 * 256 + 158] = 35; + table[35 * 256 + 158] = 35; + table[34 * 256 + 159] = 35; + table[35 * 256 + 159] = 35; + table[34 * 256 + 160] = 35; + table[35 * 256 + 160] = 35; + table[34 * 256 + 161] = 35; + table[35 * 256 + 161] = 35; + table[34 * 256 + 162] = 35; + table[35 * 256 + 162] = 35; + table[34 * 256 + 163] = 35; + table[35 * 256 + 163] = 35; + table[34 * 256 + 164] = 35; + table[35 * 256 + 164] = 35; + table[34 * 256 + 165] = 35; + table[35 * 256 + 165] = 35; + table[34 * 256 + 166] = 35; + table[35 * 256 + 166] = 35; + table[34 * 256 + 167] = 35; + table[35 * 256 + 167] = 35; + table[34 * 256 + 168] = 35; + table[35 * 256 + 168] = 35; + table[34 * 256 + 169] = 35; + table[35 * 256 + 169] = 35; + table[34 * 256 + 170] = 35; + table[35 * 256 + 170] = 35; + table[34 * 256 + 171] = 35; + table[35 * 256 + 171] = 35; + table[34 * 256 + 172] = 35; + table[35 * 256 + 172] = 35; + table[34 * 256 + 173] = 35; + table[35 * 256 + 173] = 35; + table[34 * 256 + 174] = 35; + table[35 * 256 + 174] = 35; + table[34 * 256 + 175] = 35; + table[35 * 256 + 175] = 35; + table[34 * 256 + 176] = 35; + table[35 * 256 + 176] = 35; + table[34 * 256 + 177] = 35; + table[35 * 256 + 177] = 35; + table[34 * 256 + 178] = 35; + table[35 * 256 + 178] = 35; + table[34 * 256 + 179] = 35; + table[35 * 256 + 179] = 35; + table[34 * 256 + 180] = 35; + table[35 * 256 + 180] = 35; + table[34 * 256 + 181] = 35; + table[35 * 256 + 181] = 35; + table[34 * 256 + 182] = 35; + table[35 * 256 + 182] = 35; + table[34 * 256 + 183] = 35; + table[35 * 256 + 183] = 35; + table[34 * 256 + 184] = 35; + table[35 * 256 + 184] = 35; + table[34 * 256 + 185] = 35; + table[35 * 256 + 185] = 35; + table[34 * 256 + 186] = 35; + table[35 * 256 + 186] = 35; + table[34 * 256 + 187] = 35; + table[35 * 256 + 187] = 35; + table[34 * 256 + 188] = 35; + table[35 * 256 + 188] = 35; + table[34 * 256 + 189] = 35; + table[35 * 256 + 189] = 35; + table[34 * 256 + 190] = 35; + table[35 * 256 + 190] = 35; + table[34 * 256 + 191] = 35; + table[35 * 256 + 191] = 35; + table[34 * 256 + 192] = 35; + table[35 * 256 + 192] = 35; + table[34 * 256 + 193] = 35; + table[35 * 256 + 193] = 35; + table[34 * 256 + 194] = 35; + table[35 * 256 + 194] = 35; + table[34 * 256 + 195] = 35; + table[35 * 256 + 195] = 35; + table[34 * 256 + 196] = 35; + table[35 * 256 + 196] = 35; + table[34 * 256 + 197] = 35; + table[35 * 256 + 197] = 35; + table[34 * 256 + 198] = 35; + table[35 * 256 + 198] = 35; + table[34 * 256 + 199] = 35; + table[35 * 256 + 199] = 35; + table[34 * 256 + 200] = 35; + table[35 * 256 + 200] = 35; + table[34 * 256 + 201] = 35; + table[35 * 256 + 201] = 35; + table[34 * 256 + 202] = 35; + table[35 * 256 + 202] = 35; + table[34 * 256 + 203] = 35; + table[35 * 256 + 203] = 35; + table[34 * 256 + 204] = 35; + table[35 * 256 + 204] = 35; + table[34 * 256 + 205] = 35; + table[35 * 256 + 205] = 35; + table[34 * 256 + 206] = 35; + table[35 * 256 + 206] = 35; + table[34 * 256 + 207] = 35; + table[35 * 256 + 207] = 35; + table[34 * 256 + 208] = 35; + table[35 * 256 + 208] = 35; + table[34 * 256 + 209] = 35; + table[35 * 256 + 209] = 35; + table[34 * 256 + 210] = 35; + table[35 * 256 + 210] = 35; + table[34 * 256 + 211] = 35; + table[35 * 256 + 211] = 35; + table[34 * 256 + 212] = 35; + table[35 * 256 + 212] = 35; + table[34 * 256 + 213] = 35; + table[35 * 256 + 213] = 35; + table[34 * 256 + 214] = 35; + table[35 * 256 + 214] = 35; + table[34 * 256 + 215] = 35; + table[35 * 256 + 215] = 35; + table[34 * 256 + 216] = 35; + table[35 * 256 + 216] = 35; + table[34 * 256 + 217] = 35; + table[35 * 256 + 217] = 35; + table[34 * 256 + 218] = 35; + table[35 * 256 + 218] = 35; + table[34 * 256 + 219] = 35; + table[35 * 256 + 219] = 35; + table[34 * 256 + 220] = 35; + table[35 * 256 + 220] = 35; + table[34 * 256 + 221] = 35; + table[35 * 256 + 221] = 35; + table[34 * 256 + 222] = 35; + table[35 * 256 + 222] = 35; + table[34 * 256 + 223] = 35; + table[35 * 256 + 223] = 35; + table[34 * 256 + 224] = 35; + table[35 * 256 + 224] = 35; + table[34 * 256 + 225] = 35; + table[35 * 256 + 225] = 35; + table[34 * 256 + 226] = 35; + table[35 * 256 + 226] = 35; + table[34 * 256 + 227] = 35; + table[35 * 256 + 227] = 35; + table[34 * 256 + 228] = 35; + table[35 * 256 + 228] = 35; + table[34 * 256 + 229] = 35; + table[35 * 256 + 229] = 35; + table[34 * 256 + 230] = 35; + table[35 * 256 + 230] = 35; + table[34 * 256 + 231] = 35; + table[35 * 256 + 231] = 35; + table[34 * 256 + 232] = 35; + table[35 * 256 + 232] = 35; + table[34 * 256 + 233] = 35; + table[35 * 256 + 233] = 35; + table[34 * 256 + 234] = 35; + table[35 * 256 + 234] = 35; + table[34 * 256 + 235] = 35; + table[35 * 256 + 235] = 35; + table[34 * 256 + 236] = 35; + table[35 * 256 + 236] = 35; + table[34 * 256 + 237] = 35; + table[35 * 256 + 237] = 35; + table[34 * 256 + 238] = 35; + table[35 * 256 + 238] = 35; + table[34 * 256 + 239] = 35; + table[35 * 256 + 239] = 35; + table[34 * 256 + 240] = 35; + table[35 * 256 + 240] = 35; + table[34 * 256 + 241] = 35; + table[35 * 256 + 241] = 35; + table[34 * 256 + 242] = 35; + table[35 * 256 + 242] = 35; + table[34 * 256 + 243] = 35; + table[35 * 256 + 243] = 35; + table[34 * 256 + 244] = 35; + table[35 * 256 + 244] = 35; + table[34 * 256 + 245] = 35; + table[35 * 256 + 245] = 35; + table[34 * 256 + 246] = 35; + table[35 * 256 + 246] = 35; + table[34 * 256 + 247] = 35; + table[35 * 256 + 247] = 35; + table[34 * 256 + 248] = 35; + table[35 * 256 + 248] = 35; + table[34 * 256 + 249] = 35; + table[35 * 256 + 249] = 35; + table[34 * 256 + 250] = 35; + table[35 * 256 + 250] = 35; + table[34 * 256 + 251] = 35; + table[35 * 256 + 251] = 35; + table[34 * 256 + 252] = 35; + table[35 * 256 + 252] = 35; + table[34 * 256 + 253] = 35; + table[35 * 256 + 253] = 35; + table[34 * 256 + 254] = 35; + table[35 * 256 + 254] = 35; + table[0 * 256 + 13] = 1; + table[0 * 256 + 255] = 2; + table[1 * 256 + 10] = 2; + table[2 * 256 + 100] = 3; + table[3 * 256 + 107] = 4; + table[4 * 256 + 105] = 5; + table[5 * 256 + 109] = 6; + table[6 * 256 + 45] = 7; + table[7 * 256 + 115] = 8; + table[8 * 256 + 105] = 9; + table[9 * 256 + 103] = 10; + table[10 * 256 + 110] = 11; + table[11 * 256 + 97] = 12; + table[12 * 256 + 116] = 13; + table[13 * 256 + 117] = 14; + table[14 * 256 + 114] = 15; + table[15 * 256 + 101] = 16; + table[16 * 256 + 58] = 17; + table[17 * 256 + 97] = 18; + table[17 * 256 + 98] = 18; + table[17 * 256 + 99] = 18; + table[17 * 256 + 100] = 18; + table[17 * 256 + 101] = 18; + table[17 * 256 + 102] = 18; + table[17 * 256 + 103] = 18; + table[17 * 256 + 104] = 18; + table[17 * 256 + 105] = 18; + table[17 * 256 + 106] = 18; + table[17 * 256 + 107] = 18; + table[17 * 256 + 108] = 18; + table[17 * 256 + 109] = 18; + table[17 * 256 + 110] = 18; + table[17 * 256 + 111] = 18; + table[17 * 256 + 112] = 18; + table[17 * 256 + 113] = 18; + table[17 * 256 + 114] = 18; + table[17 * 256 + 115] = 18; + table[17 * 256 + 116] = 18; + table[17 * 256 + 117] = 18; + table[17 * 256 + 118] = 18; + table[17 * 256 + 119] = 18; + table[17 * 256 + 120] = 18; + table[17 * 256 + 121] = 18; + table[17 * 256 + 122] = 18; + table[18 * 256 + 97] = 18; + table[18 * 256 + 98] = 18; + table[18 * 256 + 99] = 18; + table[18 * 256 + 100] = 18; + table[18 * 256 + 101] = 18; + table[18 * 256 + 102] = 18; + table[18 * 256 + 103] = 18; + table[18 * 256 + 104] = 18; + table[18 * 256 + 105] = 18; + table[18 * 256 + 106] = 18; + table[18 * 256 + 107] = 18; + table[18 * 256 + 108] = 18; + table[18 * 256 + 109] = 18; + table[18 * 256 + 110] = 18; + table[18 * 256 + 111] = 18; + table[18 * 256 + 112] = 18; + table[18 * 256 + 113] = 18; + table[18 * 256 + 114] = 18; + table[18 * 256 + 115] = 18; + table[18 * 256 + 116] = 18; + table[18 * 256 + 117] = 18; + table[18 * 256 + 118] = 18; + table[18 * 256 + 119] = 18; + table[18 * 256 + 120] = 18; + table[18 * 256 + 121] = 18; + table[18 * 256 + 122] = 18; + table[18 * 256 + 61] = 19; + table[19 * 256 + 0] = 20; + table[19 * 256 + 1] = 20; + table[19 * 256 + 2] = 20; + table[19 * 256 + 3] = 20; + table[19 * 256 + 4] = 20; + table[19 * 256 + 5] = 20; + table[19 * 256 + 6] = 20; + table[19 * 256 + 7] = 20; + table[19 * 256 + 8] = 20; + table[19 * 256 + 9] = 20; + table[19 * 256 + 10] = 20; + table[19 * 256 + 11] = 20; + table[19 * 256 + 12] = 20; + table[19 * 256 + 13] = 20; + table[19 * 256 + 14] = 20; + table[19 * 256 + 15] = 20; + table[19 * 256 + 16] = 20; + table[19 * 256 + 17] = 20; + table[19 * 256 + 18] = 20; + table[19 * 256 + 19] = 20; + table[19 * 256 + 20] = 20; + table[19 * 256 + 21] = 20; + table[19 * 256 + 22] = 20; + table[19 * 256 + 23] = 20; + table[19 * 256 + 24] = 20; + table[19 * 256 + 25] = 20; + table[19 * 256 + 26] = 20; + table[19 * 256 + 27] = 20; + table[19 * 256 + 28] = 20; + table[19 * 256 + 29] = 20; + table[19 * 256 + 30] = 20; + table[19 * 256 + 31] = 20; + table[19 * 256 + 32] = 20; + table[19 * 256 + 33] = 20; + table[19 * 256 + 34] = 20; + table[19 * 256 + 35] = 20; + table[19 * 256 + 36] = 20; + table[19 * 256 + 37] = 20; + table[19 * 256 + 38] = 20; + table[19 * 256 + 39] = 20; + table[19 * 256 + 40] = 20; + table[19 * 256 + 41] = 20; + table[19 * 256 + 42] = 20; + table[19 * 256 + 43] = 20; + table[19 * 256 + 44] = 20; + table[19 * 256 + 45] = 20; + table[19 * 256 + 46] = 20; + table[19 * 256 + 47] = 20; + table[19 * 256 + 48] = 20; + table[19 * 256 + 49] = 20; + table[19 * 256 + 50] = 20; + table[19 * 256 + 51] = 20; + table[19 * 256 + 52] = 20; + table[19 * 256 + 53] = 20; + table[19 * 256 + 54] = 20; + table[19 * 256 + 55] = 20; + table[19 * 256 + 56] = 20; + table[19 * 256 + 57] = 20; + table[19 * 256 + 58] = 20; + table[19 * 256 + 60] = 20; + table[19 * 256 + 61] = 20; + table[19 * 256 + 62] = 20; + table[19 * 256 + 63] = 20; + table[19 * 256 + 64] = 20; + table[19 * 256 + 65] = 20; + table[19 * 256 + 66] = 20; + table[19 * 256 + 67] = 20; + table[19 * 256 + 68] = 20; + table[19 * 256 + 69] = 20; + table[19 * 256 + 70] = 20; + table[19 * 256 + 71] = 20; + table[19 * 256 + 72] = 20; + table[19 * 256 + 73] = 20; + table[19 * 256 + 74] = 20; + table[19 * 256 + 75] = 20; + table[19 * 256 + 76] = 20; + table[19 * 256 + 77] = 20; + table[19 * 256 + 78] = 20; + table[19 * 256 + 79] = 20; + table[19 * 256 + 80] = 20; + table[19 * 256 + 81] = 20; + table[19 * 256 + 82] = 20; + table[19 * 256 + 83] = 20; + table[19 * 256 + 84] = 20; + table[19 * 256 + 85] = 20; + table[19 * 256 + 86] = 20; + table[19 * 256 + 87] = 20; + table[19 * 256 + 88] = 20; + table[19 * 256 + 89] = 20; + table[19 * 256 + 90] = 20; + table[19 * 256 + 91] = 20; + table[19 * 256 + 92] = 20; + table[19 * 256 + 93] = 20; + table[19 * 256 + 94] = 20; + table[19 * 256 + 95] = 20; + table[19 * 256 + 96] = 20; + table[19 * 256 + 97] = 20; + table[19 * 256 + 98] = 20; + table[19 * 256 + 99] = 20; + table[19 * 256 + 100] = 20; + table[19 * 256 + 101] = 20; + table[19 * 256 + 102] = 20; + table[19 * 256 + 103] = 20; + table[19 * 256 + 104] = 20; + table[19 * 256 + 105] = 20; + table[19 * 256 + 106] = 20; + table[19 * 256 + 107] = 20; + table[19 * 256 + 108] = 20; + table[19 * 256 + 109] = 20; + table[19 * 256 + 110] = 20; + table[19 * 256 + 111] = 20; + table[19 * 256 + 112] = 20; + table[19 * 256 + 113] = 20; + table[19 * 256 + 114] = 20; + table[19 * 256 + 115] = 20; + table[19 * 256 + 116] = 20; + table[19 * 256 + 117] = 20; + table[19 * 256 + 118] = 20; + table[19 * 256 + 119] = 20; + table[19 * 256 + 120] = 20; + table[19 * 256 + 121] = 20; + table[19 * 256 + 122] = 20; + table[19 * 256 + 123] = 20; + table[19 * 256 + 124] = 20; + table[19 * 256 + 125] = 20; + table[19 * 256 + 126] = 20; + table[19 * 256 + 127] = 20; + table[19 * 256 + 194] = 21; + table[19 * 256 + 195] = 21; + table[19 * 256 + 196] = 21; + table[19 * 256 + 197] = 21; + table[19 * 256 + 198] = 21; + table[19 * 256 + 199] = 21; + table[19 * 256 + 200] = 21; + table[19 * 256 + 201] = 21; + table[19 * 256 + 202] = 21; + table[19 * 256 + 203] = 21; + table[19 * 256 + 204] = 21; + table[19 * 256 + 205] = 21; + table[19 * 256 + 206] = 21; + table[19 * 256 + 207] = 21; + table[19 * 256 + 208] = 21; + table[19 * 256 + 209] = 21; + table[19 * 256 + 210] = 21; + table[19 * 256 + 211] = 21; + table[19 * 256 + 212] = 21; + table[19 * 256 + 213] = 21; + table[19 * 256 + 214] = 21; + table[19 * 256 + 215] = 21; + table[19 * 256 + 216] = 21; + table[19 * 256 + 217] = 21; + table[19 * 256 + 218] = 21; + table[19 * 256 + 219] = 21; + table[19 * 256 + 220] = 21; + table[19 * 256 + 221] = 21; + table[19 * 256 + 222] = 21; + table[19 * 256 + 223] = 21; + table[19 * 256 + 224] = 22; + table[19 * 256 + 225] = 23; + table[19 * 256 + 226] = 23; + table[19 * 256 + 227] = 23; + table[19 * 256 + 228] = 23; + table[19 * 256 + 229] = 23; + table[19 * 256 + 230] = 23; + table[19 * 256 + 231] = 23; + table[19 * 256 + 232] = 23; + table[19 * 256 + 233] = 23; + table[19 * 256 + 234] = 23; + table[19 * 256 + 235] = 23; + table[19 * 256 + 236] = 23; + table[19 * 256 + 238] = 23; + table[19 * 256 + 239] = 23; + table[19 * 256 + 237] = 24; + table[19 * 256 + 240] = 25; + table[19 * 256 + 241] = 26; + table[19 * 256 + 242] = 26; + table[19 * 256 + 243] = 26; + table[19 * 256 + 244] = 27; + table[20 * 256 + 0] = 20; + table[20 * 256 + 1] = 20; + table[20 * 256 + 2] = 20; + table[20 * 256 + 3] = 20; + table[20 * 256 + 4] = 20; + table[20 * 256 + 5] = 20; + table[20 * 256 + 6] = 20; + table[20 * 256 + 7] = 20; + table[20 * 256 + 8] = 20; + table[20 * 256 + 9] = 20; + table[20 * 256 + 10] = 20; + table[20 * 256 + 11] = 20; + table[20 * 256 + 12] = 20; + table[20 * 256 + 13] = 20; + table[20 * 256 + 14] = 20; + table[20 * 256 + 15] = 20; + table[20 * 256 + 16] = 20; + table[20 * 256 + 17] = 20; + table[20 * 256 + 18] = 20; + table[20 * 256 + 19] = 20; + table[20 * 256 + 20] = 20; + table[20 * 256 + 21] = 20; + table[20 * 256 + 22] = 20; + table[20 * 256 + 23] = 20; + table[20 * 256 + 24] = 20; + table[20 * 256 + 25] = 20; + table[20 * 256 + 26] = 20; + table[20 * 256 + 27] = 20; + table[20 * 256 + 28] = 20; + table[20 * 256 + 29] = 20; + table[20 * 256 + 30] = 20; + table[20 * 256 + 31] = 20; + table[20 * 256 + 32] = 20; + table[20 * 256 + 33] = 20; + table[20 * 256 + 34] = 20; + table[20 * 256 + 35] = 20; + table[20 * 256 + 36] = 20; + table[20 * 256 + 37] = 20; + table[20 * 256 + 38] = 20; + table[20 * 256 + 39] = 20; + table[20 * 256 + 40] = 20; + table[20 * 256 + 41] = 20; + table[20 * 256 + 42] = 20; + table[20 * 256 + 43] = 20; + table[20 * 256 + 44] = 20; + table[20 * 256 + 45] = 20; + table[20 * 256 + 46] = 20; + table[20 * 256 + 47] = 20; + table[20 * 256 + 48] = 20; + table[20 * 256 + 49] = 20; + table[20 * 256 + 50] = 20; + table[20 * 256 + 51] = 20; + table[20 * 256 + 52] = 20; + table[20 * 256 + 53] = 20; + table[20 * 256 + 54] = 20; + table[20 * 256 + 55] = 20; + table[20 * 256 + 56] = 20; + table[20 * 256 + 57] = 20; + table[20 * 256 + 58] = 20; + table[20 * 256 + 60] = 20; + table[20 * 256 + 61] = 20; + table[20 * 256 + 62] = 20; + table[20 * 256 + 63] = 20; + table[20 * 256 + 64] = 20; + table[20 * 256 + 65] = 20; + table[20 * 256 + 66] = 20; + table[20 * 256 + 67] = 20; + table[20 * 256 + 68] = 20; + table[20 * 256 + 69] = 20; + table[20 * 256 + 70] = 20; + table[20 * 256 + 71] = 20; + table[20 * 256 + 72] = 20; + table[20 * 256 + 73] = 20; + table[20 * 256 + 74] = 20; + table[20 * 256 + 75] = 20; + table[20 * 256 + 76] = 20; + table[20 * 256 + 77] = 20; + table[20 * 256 + 78] = 20; + table[20 * 256 + 79] = 20; + table[20 * 256 + 80] = 20; + table[20 * 256 + 81] = 20; + table[20 * 256 + 82] = 20; + table[20 * 256 + 83] = 20; + table[20 * 256 + 84] = 20; + table[20 * 256 + 85] = 20; + table[20 * 256 + 86] = 20; + table[20 * 256 + 87] = 20; + table[20 * 256 + 88] = 20; + table[20 * 256 + 89] = 20; + table[20 * 256 + 90] = 20; + table[20 * 256 + 91] = 20; + table[20 * 256 + 92] = 20; + table[20 * 256 + 93] = 20; + table[20 * 256 + 94] = 20; + table[20 * 256 + 95] = 20; + table[20 * 256 + 96] = 20; + table[20 * 256 + 97] = 20; + table[20 * 256 + 98] = 20; + table[20 * 256 + 99] = 20; + table[20 * 256 + 100] = 20; + table[20 * 256 + 101] = 20; + table[20 * 256 + 102] = 20; + table[20 * 256 + 103] = 20; + table[20 * 256 + 104] = 20; + table[20 * 256 + 105] = 20; + table[20 * 256 + 106] = 20; + table[20 * 256 + 107] = 20; + table[20 * 256 + 108] = 20; + table[20 * 256 + 109] = 20; + table[20 * 256 + 110] = 20; + table[20 * 256 + 111] = 20; + table[20 * 256 + 112] = 20; + table[20 * 256 + 113] = 20; + table[20 * 256 + 114] = 20; + table[20 * 256 + 115] = 20; + table[20 * 256 + 116] = 20; + table[20 * 256 + 117] = 20; + table[20 * 256 + 118] = 20; + table[20 * 256 + 119] = 20; + table[20 * 256 + 120] = 20; + table[20 * 256 + 121] = 20; + table[20 * 256 + 122] = 20; + table[20 * 256 + 123] = 20; + table[20 * 256 + 124] = 20; + table[20 * 256 + 125] = 20; + table[20 * 256 + 126] = 20; + table[20 * 256 + 127] = 20; + table[20 * 256 + 194] = 21; + table[20 * 256 + 195] = 21; + table[20 * 256 + 196] = 21; + table[20 * 256 + 197] = 21; + table[20 * 256 + 198] = 21; + table[20 * 256 + 199] = 21; + table[20 * 256 + 200] = 21; + table[20 * 256 + 201] = 21; + table[20 * 256 + 202] = 21; + table[20 * 256 + 203] = 21; + table[20 * 256 + 204] = 21; + table[20 * 256 + 205] = 21; + table[20 * 256 + 206] = 21; + table[20 * 256 + 207] = 21; + table[20 * 256 + 208] = 21; + table[20 * 256 + 209] = 21; + table[20 * 256 + 210] = 21; + table[20 * 256 + 211] = 21; + table[20 * 256 + 212] = 21; + table[20 * 256 + 213] = 21; + table[20 * 256 + 214] = 21; + table[20 * 256 + 215] = 21; + table[20 * 256 + 216] = 21; + table[20 * 256 + 217] = 21; + table[20 * 256 + 218] = 21; + table[20 * 256 + 219] = 21; + table[20 * 256 + 220] = 21; + table[20 * 256 + 221] = 21; + table[20 * 256 + 222] = 21; + table[20 * 256 + 223] = 21; + table[20 * 256 + 224] = 22; + table[20 * 256 + 225] = 23; + table[20 * 256 + 226] = 23; + table[20 * 256 + 227] = 23; + table[20 * 256 + 228] = 23; + table[20 * 256 + 229] = 23; + table[20 * 256 + 230] = 23; + table[20 * 256 + 231] = 23; + table[20 * 256 + 232] = 23; + table[20 * 256 + 233] = 23; + table[20 * 256 + 234] = 23; + table[20 * 256 + 235] = 23; + table[20 * 256 + 236] = 23; + table[20 * 256 + 238] = 23; + table[20 * 256 + 239] = 23; + table[20 * 256 + 237] = 24; + table[20 * 256 + 240] = 25; + table[20 * 256 + 241] = 26; + table[20 * 256 + 242] = 26; + table[20 * 256 + 243] = 26; + table[20 * 256 + 244] = 27; + table[20 * 256 + 59] = 28; + table[21 * 256 + 128] = 20; + table[21 * 256 + 129] = 20; + table[21 * 256 + 130] = 20; + table[21 * 256 + 131] = 20; + table[21 * 256 + 132] = 20; + table[21 * 256 + 133] = 20; + table[21 * 256 + 134] = 20; + table[21 * 256 + 135] = 20; + table[21 * 256 + 136] = 20; + table[21 * 256 + 137] = 20; + table[21 * 256 + 138] = 20; + table[21 * 256 + 139] = 20; + table[21 * 256 + 140] = 20; + table[21 * 256 + 141] = 20; + table[21 * 256 + 142] = 20; + table[21 * 256 + 143] = 20; + table[21 * 256 + 144] = 20; + table[21 * 256 + 145] = 20; + table[21 * 256 + 146] = 20; + table[21 * 256 + 147] = 20; + table[21 * 256 + 148] = 20; + table[21 * 256 + 149] = 20; + table[21 * 256 + 150] = 20; + table[21 * 256 + 151] = 20; + table[21 * 256 + 152] = 20; + table[21 * 256 + 153] = 20; + table[21 * 256 + 154] = 20; + table[21 * 256 + 155] = 20; + table[21 * 256 + 156] = 20; + table[21 * 256 + 157] = 20; + table[21 * 256 + 158] = 20; + table[21 * 256 + 159] = 20; + table[21 * 256 + 160] = 20; + table[21 * 256 + 161] = 20; + table[21 * 256 + 162] = 20; + table[21 * 256 + 163] = 20; + table[21 * 256 + 164] = 20; + table[21 * 256 + 165] = 20; + table[21 * 256 + 166] = 20; + table[21 * 256 + 167] = 20; + table[21 * 256 + 168] = 20; + table[21 * 256 + 169] = 20; + table[21 * 256 + 170] = 20; + table[21 * 256 + 171] = 20; + table[21 * 256 + 172] = 20; + table[21 * 256 + 173] = 20; + table[21 * 256 + 174] = 20; + table[21 * 256 + 175] = 20; + table[21 * 256 + 176] = 20; + table[21 * 256 + 177] = 20; + table[21 * 256 + 178] = 20; + table[21 * 256 + 179] = 20; + table[21 * 256 + 180] = 20; + table[21 * 256 + 181] = 20; + table[21 * 256 + 182] = 20; + table[21 * 256 + 183] = 20; + table[21 * 256 + 184] = 20; + table[21 * 256 + 185] = 20; + table[21 * 256 + 186] = 20; + table[21 * 256 + 187] = 20; + table[21 * 256 + 188] = 20; + table[21 * 256 + 189] = 20; + table[21 * 256 + 190] = 20; + table[21 * 256 + 191] = 20; + table[22 * 256 + 160] = 21; + table[22 * 256 + 161] = 21; + table[22 * 256 + 162] = 21; + table[22 * 256 + 163] = 21; + table[22 * 256 + 164] = 21; + table[22 * 256 + 165] = 21; + table[22 * 256 + 166] = 21; + table[22 * 256 + 167] = 21; + table[22 * 256 + 168] = 21; + table[22 * 256 + 169] = 21; + table[22 * 256 + 170] = 21; + table[22 * 256 + 171] = 21; + table[22 * 256 + 172] = 21; + table[22 * 256 + 173] = 21; + table[22 * 256 + 174] = 21; + table[22 * 256 + 175] = 21; + table[22 * 256 + 176] = 21; + table[22 * 256 + 177] = 21; + table[22 * 256 + 178] = 21; + table[22 * 256 + 179] = 21; + table[22 * 256 + 180] = 21; + table[22 * 256 + 181] = 21; + table[22 * 256 + 182] = 21; + table[22 * 256 + 183] = 21; + table[22 * 256 + 184] = 21; + table[22 * 256 + 185] = 21; + table[22 * 256 + 186] = 21; + table[22 * 256 + 187] = 21; + table[22 * 256 + 188] = 21; + table[22 * 256 + 189] = 21; + table[22 * 256 + 190] = 21; + table[22 * 256 + 191] = 21; + table[23 * 256 + 128] = 21; + table[23 * 256 + 129] = 21; + table[23 * 256 + 130] = 21; + table[23 * 256 + 131] = 21; + table[23 * 256 + 132] = 21; + table[23 * 256 + 133] = 21; + table[23 * 256 + 134] = 21; + table[23 * 256 + 135] = 21; + table[23 * 256 + 136] = 21; + table[23 * 256 + 137] = 21; + table[23 * 256 + 138] = 21; + table[23 * 256 + 139] = 21; + table[23 * 256 + 140] = 21; + table[23 * 256 + 141] = 21; + table[23 * 256 + 142] = 21; + table[23 * 256 + 143] = 21; + table[23 * 256 + 144] = 21; + table[23 * 256 + 145] = 21; + table[23 * 256 + 146] = 21; + table[23 * 256 + 147] = 21; + table[23 * 256 + 148] = 21; + table[23 * 256 + 149] = 21; + table[23 * 256 + 150] = 21; + table[23 * 256 + 151] = 21; + table[23 * 256 + 152] = 21; + table[23 * 256 + 153] = 21; + table[23 * 256 + 154] = 21; + table[23 * 256 + 155] = 21; + table[23 * 256 + 156] = 21; + table[23 * 256 + 157] = 21; + table[23 * 256 + 158] = 21; + table[23 * 256 + 159] = 21; + table[23 * 256 + 160] = 21; + table[23 * 256 + 161] = 21; + table[23 * 256 + 162] = 21; + table[23 * 256 + 163] = 21; + table[23 * 256 + 164] = 21; + table[23 * 256 + 165] = 21; + table[23 * 256 + 166] = 21; + table[23 * 256 + 167] = 21; + table[23 * 256 + 168] = 21; + table[23 * 256 + 169] = 21; + table[23 * 256 + 170] = 21; + table[23 * 256 + 171] = 21; + table[23 * 256 + 172] = 21; + table[23 * 256 + 173] = 21; + table[23 * 256 + 174] = 21; + table[23 * 256 + 175] = 21; + table[23 * 256 + 176] = 21; + table[23 * 256 + 177] = 21; + table[23 * 256 + 178] = 21; + table[23 * 256 + 179] = 21; + table[23 * 256 + 180] = 21; + table[23 * 256 + 181] = 21; + table[23 * 256 + 182] = 21; + table[23 * 256 + 183] = 21; + table[23 * 256 + 184] = 21; + table[23 * 256 + 185] = 21; + table[23 * 256 + 186] = 21; + table[23 * 256 + 187] = 21; + table[23 * 256 + 188] = 21; + table[23 * 256 + 189] = 21; + table[23 * 256 + 190] = 21; + table[23 * 256 + 191] = 21; + table[24 * 256 + 128] = 21; + table[24 * 256 + 129] = 21; + table[24 * 256 + 130] = 21; + table[24 * 256 + 131] = 21; + table[24 * 256 + 132] = 21; + table[24 * 256 + 133] = 21; + table[24 * 256 + 134] = 21; + table[24 * 256 + 135] = 21; + table[24 * 256 + 136] = 21; + table[24 * 256 + 137] = 21; + table[24 * 256 + 138] = 21; + table[24 * 256 + 139] = 21; + table[24 * 256 + 140] = 21; + table[24 * 256 + 141] = 21; + table[24 * 256 + 142] = 21; + table[24 * 256 + 143] = 21; + table[24 * 256 + 144] = 21; + table[24 * 256 + 145] = 21; + table[24 * 256 + 146] = 21; + table[24 * 256 + 147] = 21; + table[24 * 256 + 148] = 21; + table[24 * 256 + 149] = 21; + table[24 * 256 + 150] = 21; + table[24 * 256 + 151] = 21; + table[24 * 256 + 152] = 21; + table[24 * 256 + 153] = 21; + table[24 * 256 + 154] = 21; + table[24 * 256 + 155] = 21; + table[24 * 256 + 156] = 21; + table[24 * 256 + 157] = 21; + table[24 * 256 + 158] = 21; + table[24 * 256 + 159] = 21; + table[25 * 256 + 144] = 23; + table[25 * 256 + 145] = 23; + table[25 * 256 + 146] = 23; + table[25 * 256 + 147] = 23; + table[25 * 256 + 148] = 23; + table[25 * 256 + 149] = 23; + table[25 * 256 + 150] = 23; + table[25 * 256 + 151] = 23; + table[25 * 256 + 152] = 23; + table[25 * 256 + 153] = 23; + table[25 * 256 + 154] = 23; + table[25 * 256 + 155] = 23; + table[25 * 256 + 156] = 23; + table[25 * 256 + 157] = 23; + table[25 * 256 + 158] = 23; + table[25 * 256 + 159] = 23; + table[25 * 256 + 160] = 23; + table[25 * 256 + 161] = 23; + table[25 * 256 + 162] = 23; + table[25 * 256 + 163] = 23; + table[25 * 256 + 164] = 23; + table[25 * 256 + 165] = 23; + table[25 * 256 + 166] = 23; + table[25 * 256 + 167] = 23; + table[25 * 256 + 168] = 23; + table[25 * 256 + 169] = 23; + table[25 * 256 + 170] = 23; + table[25 * 256 + 171] = 23; + table[25 * 256 + 172] = 23; + table[25 * 256 + 173] = 23; + table[25 * 256 + 174] = 23; + table[25 * 256 + 175] = 23; + table[25 * 256 + 176] = 23; + table[25 * 256 + 177] = 23; + table[25 * 256 + 178] = 23; + table[25 * 256 + 179] = 23; + table[25 * 256 + 180] = 23; + table[25 * 256 + 181] = 23; + table[25 * 256 + 182] = 23; + table[25 * 256 + 183] = 23; + table[25 * 256 + 184] = 23; + table[25 * 256 + 185] = 23; + table[25 * 256 + 186] = 23; + table[25 * 256 + 187] = 23; + table[25 * 256 + 188] = 23; + table[25 * 256 + 189] = 23; + table[25 * 256 + 190] = 23; + table[25 * 256 + 191] = 23; + table[26 * 256 + 128] = 23; + table[26 * 256 + 129] = 23; + table[26 * 256 + 130] = 23; + table[26 * 256 + 131] = 23; + table[26 * 256 + 132] = 23; + table[26 * 256 + 133] = 23; + table[26 * 256 + 134] = 23; + table[26 * 256 + 135] = 23; + table[26 * 256 + 136] = 23; + table[26 * 256 + 137] = 23; + table[26 * 256 + 138] = 23; + table[26 * 256 + 139] = 23; + table[26 * 256 + 140] = 23; + table[26 * 256 + 141] = 23; + table[26 * 256 + 142] = 23; + table[26 * 256 + 143] = 23; + table[26 * 256 + 144] = 23; + table[26 * 256 + 145] = 23; + table[26 * 256 + 146] = 23; + table[26 * 256 + 147] = 23; + table[26 * 256 + 148] = 23; + table[26 * 256 + 149] = 23; + table[26 * 256 + 150] = 23; + table[26 * 256 + 151] = 23; + table[26 * 256 + 152] = 23; + table[26 * 256 + 153] = 23; + table[26 * 256 + 154] = 23; + table[26 * 256 + 155] = 23; + table[26 * 256 + 156] = 23; + table[26 * 256 + 157] = 23; + table[26 * 256 + 158] = 23; + table[26 * 256 + 159] = 23; + table[26 * 256 + 160] = 23; + table[26 * 256 + 161] = 23; + table[26 * 256 + 162] = 23; + table[26 * 256 + 163] = 23; + table[26 * 256 + 164] = 23; + table[26 * 256 + 165] = 23; + table[26 * 256 + 166] = 23; + table[26 * 256 + 167] = 23; + table[26 * 256 + 168] = 23; + table[26 * 256 + 169] = 23; + table[26 * 256 + 170] = 23; + table[26 * 256 + 171] = 23; + table[26 * 256 + 172] = 23; + table[26 * 256 + 173] = 23; + table[26 * 256 + 174] = 23; + table[26 * 256 + 175] = 23; + table[26 * 256 + 176] = 23; + table[26 * 256 + 177] = 23; + table[26 * 256 + 178] = 23; + table[26 * 256 + 179] = 23; + table[26 * 256 + 180] = 23; + table[26 * 256 + 181] = 23; + table[26 * 256 + 182] = 23; + table[26 * 256 + 183] = 23; + table[26 * 256 + 184] = 23; + table[26 * 256 + 185] = 23; + table[26 * 256 + 186] = 23; + table[26 * 256 + 187] = 23; + table[26 * 256 + 188] = 23; + table[26 * 256 + 189] = 23; + table[26 * 256 + 190] = 23; + table[26 * 256 + 191] = 23; + table[27 * 256 + 128] = 23; + table[27 * 256 + 129] = 23; + table[27 * 256 + 130] = 23; + table[27 * 256 + 131] = 23; + table[27 * 256 + 132] = 23; + table[27 * 256 + 133] = 23; + table[27 * 256 + 134] = 23; + table[27 * 256 + 135] = 23; + table[27 * 256 + 136] = 23; + table[27 * 256 + 137] = 23; + table[27 * 256 + 138] = 23; + table[27 * 256 + 139] = 23; + table[27 * 256 + 140] = 23; + table[27 * 256 + 141] = 23; + table[27 * 256 + 142] = 23; + table[27 * 256 + 143] = 23; + table[28 * 256 + 32] = 29; + table[29 * 256 + 97] = 18; + table[29 * 256 + 99] = 18; + table[29 * 256 + 100] = 18; + table[29 * 256 + 101] = 18; + table[29 * 256 + 102] = 18; + table[29 * 256 + 103] = 18; + table[29 * 256 + 104] = 18; + table[29 * 256 + 105] = 18; + table[29 * 256 + 106] = 18; + table[29 * 256 + 107] = 18; + table[29 * 256 + 108] = 18; + table[29 * 256 + 109] = 18; + table[29 * 256 + 110] = 18; + table[29 * 256 + 111] = 18; + table[29 * 256 + 112] = 18; + table[29 * 256 + 113] = 18; + table[29 * 256 + 114] = 18; + table[29 * 256 + 115] = 18; + table[29 * 256 + 116] = 18; + table[29 * 256 + 117] = 18; + table[29 * 256 + 118] = 18; + table[29 * 256 + 119] = 18; + table[29 * 256 + 120] = 18; + table[29 * 256 + 121] = 18; + table[29 * 256 + 122] = 18; + table[29 * 256 + 98] = 30; + table[30 * 256 + 97] = 18; + table[30 * 256 + 98] = 18; + table[30 * 256 + 99] = 18; + table[30 * 256 + 100] = 18; + table[30 * 256 + 101] = 18; + table[30 * 256 + 102] = 18; + table[30 * 256 + 103] = 18; + table[30 * 256 + 105] = 18; + table[30 * 256 + 106] = 18; + table[30 * 256 + 107] = 18; + table[30 * 256 + 108] = 18; + table[30 * 256 + 109] = 18; + table[30 * 256 + 110] = 18; + table[30 * 256 + 111] = 18; + table[30 * 256 + 112] = 18; + table[30 * 256 + 113] = 18; + table[30 * 256 + 114] = 18; + table[30 * 256 + 115] = 18; + table[30 * 256 + 116] = 18; + table[30 * 256 + 117] = 18; + table[30 * 256 + 118] = 18; + table[30 * 256 + 119] = 18; + table[30 * 256 + 120] = 18; + table[30 * 256 + 121] = 18; + table[30 * 256 + 122] = 18; + table[30 * 256 + 61] = 19; + table[30 * 256 + 104] = 31; + table[31 * 256 + 97] = 18; + table[31 * 256 + 98] = 18; + table[31 * 256 + 99] = 18; + table[31 * 256 + 100] = 18; + table[31 * 256 + 101] = 18; + table[31 * 256 + 102] = 18; + table[31 * 256 + 103] = 18; + table[31 * 256 + 104] = 18; + table[31 * 256 + 105] = 18; + table[31 * 256 + 106] = 18; + table[31 * 256 + 107] = 18; + table[31 * 256 + 108] = 18; + table[31 * 256 + 109] = 18; + table[31 * 256 + 110] = 18; + table[31 * 256 + 111] = 18; + table[31 * 256 + 112] = 18; + table[31 * 256 + 113] = 18; + table[31 * 256 + 114] = 18; + table[31 * 256 + 115] = 18; + table[31 * 256 + 116] = 18; + table[31 * 256 + 117] = 18; + table[31 * 256 + 118] = 18; + table[31 * 256 + 119] = 18; + table[31 * 256 + 120] = 18; + table[31 * 256 + 121] = 18; + table[31 * 256 + 122] = 18; + table[31 * 256 + 61] = 32; + table[32 * 256 + 0] = 20; + table[32 * 256 + 1] = 20; + table[32 * 256 + 2] = 20; + table[32 * 256 + 3] = 20; + table[32 * 256 + 4] = 20; + table[32 * 256 + 5] = 20; + table[32 * 256 + 6] = 20; + table[32 * 256 + 7] = 20; + table[32 * 256 + 8] = 20; + table[32 * 256 + 9] = 20; + table[32 * 256 + 10] = 20; + table[32 * 256 + 11] = 20; + table[32 * 256 + 12] = 20; + table[32 * 256 + 13] = 20; + table[32 * 256 + 14] = 20; + table[32 * 256 + 15] = 20; + table[32 * 256 + 16] = 20; + table[32 * 256 + 17] = 20; + table[32 * 256 + 18] = 20; + table[32 * 256 + 19] = 20; + table[32 * 256 + 20] = 20; + table[32 * 256 + 21] = 20; + table[32 * 256 + 22] = 20; + table[32 * 256 + 23] = 20; + table[32 * 256 + 24] = 20; + table[32 * 256 + 25] = 20; + table[32 * 256 + 26] = 20; + table[32 * 256 + 27] = 20; + table[32 * 256 + 28] = 20; + table[32 * 256 + 29] = 20; + table[32 * 256 + 30] = 20; + table[32 * 256 + 31] = 20; + table[32 * 256 + 32] = 20; + table[32 * 256 + 33] = 20; + table[32 * 256 + 34] = 20; + table[32 * 256 + 35] = 20; + table[32 * 256 + 36] = 20; + table[32 * 256 + 37] = 20; + table[32 * 256 + 38] = 20; + table[32 * 256 + 39] = 20; + table[32 * 256 + 40] = 20; + table[32 * 256 + 41] = 20; + table[32 * 256 + 42] = 20; + table[32 * 256 + 44] = 20; + table[32 * 256 + 45] = 20; + table[32 * 256 + 46] = 20; + table[32 * 256 + 58] = 20; + table[32 * 256 + 60] = 20; + table[32 * 256 + 62] = 20; + table[32 * 256 + 63] = 20; + table[32 * 256 + 64] = 20; + table[32 * 256 + 91] = 20; + table[32 * 256 + 92] = 20; + table[32 * 256 + 93] = 20; + table[32 * 256 + 94] = 20; + table[32 * 256 + 95] = 20; + table[32 * 256 + 96] = 20; + table[32 * 256 + 123] = 20; + table[32 * 256 + 124] = 20; + table[32 * 256 + 125] = 20; + table[32 * 256 + 126] = 20; + table[32 * 256 + 127] = 20; + table[32 * 256 + 194] = 21; + table[32 * 256 + 195] = 21; + table[32 * 256 + 196] = 21; + table[32 * 256 + 197] = 21; + table[32 * 256 + 198] = 21; + table[32 * 256 + 199] = 21; + table[32 * 256 + 200] = 21; + table[32 * 256 + 201] = 21; + table[32 * 256 + 202] = 21; + table[32 * 256 + 203] = 21; + table[32 * 256 + 204] = 21; + table[32 * 256 + 205] = 21; + table[32 * 256 + 206] = 21; + table[32 * 256 + 207] = 21; + table[32 * 256 + 208] = 21; + table[32 * 256 + 209] = 21; + table[32 * 256 + 210] = 21; + table[32 * 256 + 211] = 21; + table[32 * 256 + 212] = 21; + table[32 * 256 + 213] = 21; + table[32 * 256 + 214] = 21; + table[32 * 256 + 215] = 21; + table[32 * 256 + 216] = 21; + table[32 * 256 + 217] = 21; + table[32 * 256 + 218] = 21; + table[32 * 256 + 219] = 21; + table[32 * 256 + 220] = 21; + table[32 * 256 + 221] = 21; + table[32 * 256 + 222] = 21; + table[32 * 256 + 223] = 21; + table[32 * 256 + 224] = 22; + table[32 * 256 + 225] = 23; + table[32 * 256 + 226] = 23; + table[32 * 256 + 227] = 23; + table[32 * 256 + 228] = 23; + table[32 * 256 + 229] = 23; + table[32 * 256 + 230] = 23; + table[32 * 256 + 231] = 23; + table[32 * 256 + 232] = 23; + table[32 * 256 + 233] = 23; + table[32 * 256 + 234] = 23; + table[32 * 256 + 235] = 23; + table[32 * 256 + 236] = 23; + table[32 * 256 + 238] = 23; + table[32 * 256 + 239] = 23; + table[32 * 256 + 237] = 24; + table[32 * 256 + 240] = 25; + table[32 * 256 + 241] = 26; + table[32 * 256 + 242] = 26; + table[32 * 256 + 243] = 26; + table[32 * 256 + 244] = 27; + table[32 * 256 + 43] = 33; + table[32 * 256 + 47] = 33; + table[32 * 256 + 48] = 33; + table[32 * 256 + 49] = 33; + table[32 * 256 + 50] = 33; + table[32 * 256 + 51] = 33; + table[32 * 256 + 52] = 33; + table[32 * 256 + 53] = 33; + table[32 * 256 + 54] = 33; + table[32 * 256 + 55] = 33; + table[32 * 256 + 56] = 33; + table[32 * 256 + 57] = 33; + table[32 * 256 + 61] = 33; + table[32 * 256 + 65] = 33; + table[32 * 256 + 66] = 33; + table[32 * 256 + 67] = 33; + table[32 * 256 + 68] = 33; + table[32 * 256 + 69] = 33; + table[32 * 256 + 70] = 33; + table[32 * 256 + 71] = 33; + table[32 * 256 + 72] = 33; + table[32 * 256 + 73] = 33; + table[32 * 256 + 74] = 33; + table[32 * 256 + 75] = 33; + table[32 * 256 + 76] = 33; + table[32 * 256 + 77] = 33; + table[32 * 256 + 78] = 33; + table[32 * 256 + 79] = 33; + table[32 * 256 + 80] = 33; + table[32 * 256 + 81] = 33; + table[32 * 256 + 82] = 33; + table[32 * 256 + 83] = 33; + table[32 * 256 + 84] = 33; + table[32 * 256 + 85] = 33; + table[32 * 256 + 86] = 33; + table[32 * 256 + 87] = 33; + table[32 * 256 + 88] = 33; + table[32 * 256 + 89] = 33; + table[32 * 256 + 90] = 33; + table[32 * 256 + 97] = 33; + table[32 * 256 + 98] = 33; + table[32 * 256 + 99] = 33; + table[32 * 256 + 100] = 33; + table[32 * 256 + 101] = 33; + table[32 * 256 + 102] = 33; + table[32 * 256 + 103] = 33; + table[32 * 256 + 104] = 33; + table[32 * 256 + 105] = 33; + table[32 * 256 + 106] = 33; + table[32 * 256 + 107] = 33; + table[32 * 256 + 108] = 33; + table[32 * 256 + 109] = 33; + table[32 * 256 + 110] = 33; + table[32 * 256 + 111] = 33; + table[32 * 256 + 112] = 33; + table[32 * 256 + 113] = 33; + table[32 * 256 + 114] = 33; + table[32 * 256 + 115] = 33; + table[32 * 256 + 116] = 33; + table[32 * 256 + 117] = 33; + table[32 * 256 + 118] = 33; + table[32 * 256 + 119] = 33; + table[32 * 256 + 120] = 33; + table[32 * 256 + 121] = 33; + table[32 * 256 + 122] = 33; + table[33 * 256 + 43] = 33; + table[33 * 256 + 47] = 33; + table[33 * 256 + 48] = 33; + table[33 * 256 + 49] = 33; + table[33 * 256 + 50] = 33; + table[33 * 256 + 51] = 33; + table[33 * 256 + 52] = 33; + table[33 * 256 + 53] = 33; + table[33 * 256 + 54] = 33; + table[33 * 256 + 55] = 33; + table[33 * 256 + 56] = 33; + table[33 * 256 + 57] = 33; + table[33 * 256 + 61] = 33; + table[33 * 256 + 65] = 33; + table[33 * 256 + 66] = 33; + table[33 * 256 + 67] = 33; + table[33 * 256 + 68] = 33; + table[33 * 256 + 69] = 33; + table[33 * 256 + 70] = 33; + table[33 * 256 + 71] = 33; + table[33 * 256 + 72] = 33; + table[33 * 256 + 73] = 33; + table[33 * 256 + 74] = 33; + table[33 * 256 + 75] = 33; + table[33 * 256 + 76] = 33; + table[33 * 256 + 77] = 33; + table[33 * 256 + 78] = 33; + table[33 * 256 + 79] = 33; + table[33 * 256 + 80] = 33; + table[33 * 256 + 81] = 33; + table[33 * 256 + 82] = 33; + table[33 * 256 + 83] = 33; + table[33 * 256 + 84] = 33; + table[33 * 256 + 85] = 33; + table[33 * 256 + 86] = 33; + table[33 * 256 + 87] = 33; + table[33 * 256 + 88] = 33; + table[33 * 256 + 89] = 33; + table[33 * 256 + 90] = 33; + table[33 * 256 + 97] = 33; + table[33 * 256 + 98] = 33; + table[33 * 256 + 99] = 33; + table[33 * 256 + 100] = 33; + table[33 * 256 + 101] = 33; + table[33 * 256 + 102] = 33; + table[33 * 256 + 103] = 33; + table[33 * 256 + 104] = 33; + table[33 * 256 + 105] = 33; + table[33 * 256 + 106] = 33; + table[33 * 256 + 107] = 33; + table[33 * 256 + 108] = 33; + table[33 * 256 + 109] = 33; + table[33 * 256 + 110] = 33; + table[33 * 256 + 111] = 33; + table[33 * 256 + 112] = 33; + table[33 * 256 + 113] = 33; + table[33 * 256 + 114] = 33; + table[33 * 256 + 115] = 33; + table[33 * 256 + 116] = 33; + table[33 * 256 + 117] = 33; + table[33 * 256 + 118] = 33; + table[33 * 256 + 119] = 33; + table[33 * 256 + 120] = 33; + table[33 * 256 + 121] = 33; + table[33 * 256 + 122] = 33; + table[33 * 256 + 59] = 34; + + table +} + + +pub fn regex_match(input: [u8; N]) -> (BoundedVec, bool) { + let substrings = unsafe { __regex_match(input) }; + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + let mut start_range = 0; + let mut end_range = 0; + + // check the match + for i in 0..N { + // state transition + let temp = input[i] as Field; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + s = 0; + s_next = potential_s_next; + } + std::as_witness(s_next); + + // range conditions for substring matches + if ((start_range == 0) & (end_range == 0)) { + start_range = i as Field; + } + if (((s == 34) & (s_next == 35)) & (end_range == 0)) { + end_range = i as Field + 1; + } + + + let range_0 = substrings.get_unchecked(0).in_range(i); + let case_0 = [ + (s_next == 33) & ((s == 32) | (s == 33)) + ].any(|case| case == true) | !range_0; + + + + let substring_range_check = [case_0] + .all(|case| case == true); + + assert(substring_range_check, "substr array ranges wrong"); + + + s = s_next; + } + // check final state + + let matched: bool = (s == 34) | (s == 35); + + // constrain extracted substrings to be in match range + //let full_match = Sequence::new(start_range as u32, end_range as u32 - start_range as u32); + //let full_match_end = full_match.end(); + // for i in 0..1 { + // let substring = substrings.get_unchecked(i); + // let is_not_valid = i >= substrings.len(); + // let index_check = substring.index >= full_match.index; + // let length_check = substring.end() <= full_match_end; + // let check = (index_check) | is_not_valid; + // assert(check, f"Substring {i} range is out of bounds of the full match found"); + // } + (substrings, matched) +} + + +pub unconstrained fn __regex_match(input: [u8; N]) -> BoundedVec { + // regex: (\r\n|^)dkim-signature:([a-z]+=[^;]+; )+bh=[a-zA-Z0-9+/=]+; + let mut substrings: BoundedVec = BoundedVec::new(); + let mut current_substring = Sequence::default(); + let mut full_match = Sequence::default(); + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + + let mut consecutive_substr = 0; + let mut complete = false; + + for i in 0..input.len() { + let temp = input[i] as Field; + let mut reset = false; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + reset = true; + s = 0; + s_next = potential_s_next; + } + // If a substring was in the making, but the state was reset + // we disregard previous progress because apparently it is invalid + if (reset & (consecutive_substr == 1)) { + current_substring = Sequence::default(); + consecutive_substr = 0; + } + // Fill up substrings + + + if ((s == 32) & (s_next == 33) | (s == 33) & (s_next == 33)) { + + if (consecutive_substr == 0) { + current_substring.index = i; + }; + current_substring.length += 1; + consecutive_substr = 1; + } else if ((consecutive_substr == 1) & (s_next == 0)) { + current_substring = Sequence::default(); + full_match = Sequence::default(); + substrings = BoundedVec::new(); + consecutive_substr = 0; + } else if (s == 34) & (s_next == 35) { + full_match.length = i - full_match.index + 1; + complete = true; + } else if (consecutive_substr == 1) { + // The substring is done so "save" it + substrings.push(current_substring); + // reset the substring holder for next use + current_substring = Sequence::default(); + consecutive_substr = 0; + } + s = s_next; + if complete == true { + break; + } + } + assert((s == 34) | (s == 35), f"no match: {s}"); + // Add pending substring that hasn't been added + if consecutive_substr == 1 { + substrings.push(current_substring); + full_match.length = input.len() - full_match.index; + } + + + + substrings +} + + + + \ No newline at end of file diff --git a/packages/noir/src/capture/raw/email_addr.nr b/packages/noir/src/capture/raw/email_addr.nr new file mode 100644 index 00000000..9d7b98c9 --- /dev/null +++ b/packages/noir/src/capture/raw/email_addr.nr @@ -0,0 +1,1000 @@ + +use crate::common::Sequence; + + +global table: [Field; 1280] = comptime { make_lookup_table() }; + +comptime fn make_lookup_table() -> [Field; 1280] { + let mut table = [0; 1280]; + table[3 * 256 + 0] = 4; + table[4 * 256 + 0] = 4; + table[3 * 256 + 1] = 4; + table[4 * 256 + 1] = 4; + table[3 * 256 + 2] = 4; + table[4 * 256 + 2] = 4; + table[3 * 256 + 3] = 4; + table[4 * 256 + 3] = 4; + table[3 * 256 + 4] = 4; + table[4 * 256 + 4] = 4; + table[3 * 256 + 5] = 4; + table[4 * 256 + 5] = 4; + table[3 * 256 + 6] = 4; + table[4 * 256 + 6] = 4; + table[3 * 256 + 7] = 4; + table[4 * 256 + 7] = 4; + table[3 * 256 + 8] = 4; + table[4 * 256 + 8] = 4; + table[3 * 256 + 9] = 4; + table[4 * 256 + 9] = 4; + table[3 * 256 + 10] = 4; + table[4 * 256 + 10] = 4; + table[3 * 256 + 11] = 4; + table[4 * 256 + 11] = 4; + table[3 * 256 + 12] = 4; + table[4 * 256 + 12] = 4; + table[3 * 256 + 13] = 4; + table[4 * 256 + 13] = 4; + table[3 * 256 + 14] = 4; + table[4 * 256 + 14] = 4; + table[3 * 256 + 15] = 4; + table[4 * 256 + 15] = 4; + table[3 * 256 + 16] = 4; + table[4 * 256 + 16] = 4; + table[3 * 256 + 17] = 4; + table[4 * 256 + 17] = 4; + table[3 * 256 + 18] = 4; + table[4 * 256 + 18] = 4; + table[3 * 256 + 19] = 4; + table[4 * 256 + 19] = 4; + table[3 * 256 + 20] = 4; + table[4 * 256 + 20] = 4; + table[3 * 256 + 21] = 4; + table[4 * 256 + 21] = 4; + table[3 * 256 + 22] = 4; + table[4 * 256 + 22] = 4; + table[3 * 256 + 23] = 4; + table[4 * 256 + 23] = 4; + table[3 * 256 + 24] = 4; + table[4 * 256 + 24] = 4; + table[3 * 256 + 25] = 4; + table[4 * 256 + 25] = 4; + table[3 * 256 + 26] = 4; + table[4 * 256 + 26] = 4; + table[3 * 256 + 27] = 4; + table[4 * 256 + 27] = 4; + table[3 * 256 + 28] = 4; + table[4 * 256 + 28] = 4; + table[3 * 256 + 29] = 4; + table[4 * 256 + 29] = 4; + table[3 * 256 + 30] = 4; + table[4 * 256 + 30] = 4; + table[3 * 256 + 31] = 4; + table[4 * 256 + 31] = 4; + table[3 * 256 + 32] = 4; + table[4 * 256 + 32] = 4; + table[3 * 256 + 33] = 4; + table[4 * 256 + 33] = 4; + table[3 * 256 + 34] = 4; + table[4 * 256 + 34] = 4; + table[3 * 256 + 35] = 4; + table[4 * 256 + 35] = 4; + table[3 * 256 + 36] = 4; + table[4 * 256 + 36] = 4; + table[3 * 256 + 37] = 4; + table[4 * 256 + 37] = 4; + table[3 * 256 + 38] = 4; + table[4 * 256 + 38] = 4; + table[3 * 256 + 39] = 4; + table[4 * 256 + 39] = 4; + table[3 * 256 + 40] = 4; + table[4 * 256 + 40] = 4; + table[3 * 256 + 41] = 4; + table[4 * 256 + 41] = 4; + table[3 * 256 + 42] = 4; + table[4 * 256 + 42] = 4; + table[3 * 256 + 43] = 4; + table[4 * 256 + 43] = 4; + table[3 * 256 + 44] = 4; + table[4 * 256 + 44] = 4; + table[3 * 256 + 45] = 4; + table[4 * 256 + 45] = 4; + table[3 * 256 + 46] = 4; + table[4 * 256 + 46] = 4; + table[3 * 256 + 47] = 4; + table[4 * 256 + 47] = 4; + table[3 * 256 + 48] = 4; + table[4 * 256 + 48] = 4; + table[3 * 256 + 49] = 4; + table[4 * 256 + 49] = 4; + table[3 * 256 + 50] = 4; + table[4 * 256 + 50] = 4; + table[3 * 256 + 51] = 4; + table[4 * 256 + 51] = 4; + table[3 * 256 + 52] = 4; + table[4 * 256 + 52] = 4; + table[3 * 256 + 53] = 4; + table[4 * 256 + 53] = 4; + table[3 * 256 + 54] = 4; + table[4 * 256 + 54] = 4; + table[3 * 256 + 55] = 4; + table[4 * 256 + 55] = 4; + table[3 * 256 + 56] = 4; + table[4 * 256 + 56] = 4; + table[3 * 256 + 57] = 4; + table[4 * 256 + 57] = 4; + table[3 * 256 + 58] = 4; + table[4 * 256 + 58] = 4; + table[3 * 256 + 59] = 4; + table[4 * 256 + 59] = 4; + table[3 * 256 + 60] = 4; + table[4 * 256 + 60] = 4; + table[3 * 256 + 61] = 4; + table[4 * 256 + 61] = 4; + table[3 * 256 + 62] = 4; + table[4 * 256 + 62] = 4; + table[3 * 256 + 63] = 4; + table[4 * 256 + 63] = 4; + table[3 * 256 + 64] = 4; + table[4 * 256 + 64] = 4; + table[3 * 256 + 65] = 4; + table[4 * 256 + 65] = 4; + table[3 * 256 + 66] = 4; + table[4 * 256 + 66] = 4; + table[3 * 256 + 67] = 4; + table[4 * 256 + 67] = 4; + table[3 * 256 + 68] = 4; + table[4 * 256 + 68] = 4; + table[3 * 256 + 69] = 4; + table[4 * 256 + 69] = 4; + table[3 * 256 + 70] = 4; + table[4 * 256 + 70] = 4; + table[3 * 256 + 71] = 4; + table[4 * 256 + 71] = 4; + table[3 * 256 + 72] = 4; + table[4 * 256 + 72] = 4; + table[3 * 256 + 73] = 4; + table[4 * 256 + 73] = 4; + table[3 * 256 + 74] = 4; + table[4 * 256 + 74] = 4; + table[3 * 256 + 75] = 4; + table[4 * 256 + 75] = 4; + table[3 * 256 + 76] = 4; + table[4 * 256 + 76] = 4; + table[3 * 256 + 77] = 4; + table[4 * 256 + 77] = 4; + table[3 * 256 + 78] = 4; + table[4 * 256 + 78] = 4; + table[3 * 256 + 79] = 4; + table[4 * 256 + 79] = 4; + table[3 * 256 + 80] = 4; + table[4 * 256 + 80] = 4; + table[3 * 256 + 81] = 4; + table[4 * 256 + 81] = 4; + table[3 * 256 + 82] = 4; + table[4 * 256 + 82] = 4; + table[3 * 256 + 83] = 4; + table[4 * 256 + 83] = 4; + table[3 * 256 + 84] = 4; + table[4 * 256 + 84] = 4; + table[3 * 256 + 85] = 4; + table[4 * 256 + 85] = 4; + table[3 * 256 + 86] = 4; + table[4 * 256 + 86] = 4; + table[3 * 256 + 87] = 4; + table[4 * 256 + 87] = 4; + table[3 * 256 + 88] = 4; + table[4 * 256 + 88] = 4; + table[3 * 256 + 89] = 4; + table[4 * 256 + 89] = 4; + table[3 * 256 + 90] = 4; + table[4 * 256 + 90] = 4; + table[3 * 256 + 91] = 4; + table[4 * 256 + 91] = 4; + table[3 * 256 + 92] = 4; + table[4 * 256 + 92] = 4; + table[3 * 256 + 93] = 4; + table[4 * 256 + 93] = 4; + table[3 * 256 + 94] = 4; + table[4 * 256 + 94] = 4; + table[3 * 256 + 95] = 4; + table[4 * 256 + 95] = 4; + table[3 * 256 + 96] = 4; + table[4 * 256 + 96] = 4; + table[3 * 256 + 97] = 4; + table[4 * 256 + 97] = 4; + table[3 * 256 + 98] = 4; + table[4 * 256 + 98] = 4; + table[3 * 256 + 99] = 4; + table[4 * 256 + 99] = 4; + table[3 * 256 + 100] = 4; + table[4 * 256 + 100] = 4; + table[3 * 256 + 101] = 4; + table[4 * 256 + 101] = 4; + table[3 * 256 + 102] = 4; + table[4 * 256 + 102] = 4; + table[3 * 256 + 103] = 4; + table[4 * 256 + 103] = 4; + table[3 * 256 + 104] = 4; + table[4 * 256 + 104] = 4; + table[3 * 256 + 105] = 4; + table[4 * 256 + 105] = 4; + table[3 * 256 + 106] = 4; + table[4 * 256 + 106] = 4; + table[3 * 256 + 107] = 4; + table[4 * 256 + 107] = 4; + table[3 * 256 + 108] = 4; + table[4 * 256 + 108] = 4; + table[3 * 256 + 109] = 4; + table[4 * 256 + 109] = 4; + table[3 * 256 + 110] = 4; + table[4 * 256 + 110] = 4; + table[3 * 256 + 111] = 4; + table[4 * 256 + 111] = 4; + table[3 * 256 + 112] = 4; + table[4 * 256 + 112] = 4; + table[3 * 256 + 113] = 4; + table[4 * 256 + 113] = 4; + table[3 * 256 + 114] = 4; + table[4 * 256 + 114] = 4; + table[3 * 256 + 115] = 4; + table[4 * 256 + 115] = 4; + table[3 * 256 + 116] = 4; + table[4 * 256 + 116] = 4; + table[3 * 256 + 117] = 4; + table[4 * 256 + 117] = 4; + table[3 * 256 + 118] = 4; + table[4 * 256 + 118] = 4; + table[3 * 256 + 119] = 4; + table[4 * 256 + 119] = 4; + table[3 * 256 + 120] = 4; + table[4 * 256 + 120] = 4; + table[3 * 256 + 121] = 4; + table[4 * 256 + 121] = 4; + table[3 * 256 + 122] = 4; + table[4 * 256 + 122] = 4; + table[3 * 256 + 123] = 4; + table[4 * 256 + 123] = 4; + table[3 * 256 + 124] = 4; + table[4 * 256 + 124] = 4; + table[3 * 256 + 125] = 4; + table[4 * 256 + 125] = 4; + table[3 * 256 + 126] = 4; + table[4 * 256 + 126] = 4; + table[3 * 256 + 127] = 4; + table[4 * 256 + 127] = 4; + table[3 * 256 + 128] = 4; + table[4 * 256 + 128] = 4; + table[3 * 256 + 129] = 4; + table[4 * 256 + 129] = 4; + table[3 * 256 + 130] = 4; + table[4 * 256 + 130] = 4; + table[3 * 256 + 131] = 4; + table[4 * 256 + 131] = 4; + table[3 * 256 + 132] = 4; + table[4 * 256 + 132] = 4; + table[3 * 256 + 133] = 4; + table[4 * 256 + 133] = 4; + table[3 * 256 + 134] = 4; + table[4 * 256 + 134] = 4; + table[3 * 256 + 135] = 4; + table[4 * 256 + 135] = 4; + table[3 * 256 + 136] = 4; + table[4 * 256 + 136] = 4; + table[3 * 256 + 137] = 4; + table[4 * 256 + 137] = 4; + table[3 * 256 + 138] = 4; + table[4 * 256 + 138] = 4; + table[3 * 256 + 139] = 4; + table[4 * 256 + 139] = 4; + table[3 * 256 + 140] = 4; + table[4 * 256 + 140] = 4; + table[3 * 256 + 141] = 4; + table[4 * 256 + 141] = 4; + table[3 * 256 + 142] = 4; + table[4 * 256 + 142] = 4; + table[3 * 256 + 143] = 4; + table[4 * 256 + 143] = 4; + table[3 * 256 + 144] = 4; + table[4 * 256 + 144] = 4; + table[3 * 256 + 145] = 4; + table[4 * 256 + 145] = 4; + table[3 * 256 + 146] = 4; + table[4 * 256 + 146] = 4; + table[3 * 256 + 147] = 4; + table[4 * 256 + 147] = 4; + table[3 * 256 + 148] = 4; + table[4 * 256 + 148] = 4; + table[3 * 256 + 149] = 4; + table[4 * 256 + 149] = 4; + table[3 * 256 + 150] = 4; + table[4 * 256 + 150] = 4; + table[3 * 256 + 151] = 4; + table[4 * 256 + 151] = 4; + table[3 * 256 + 152] = 4; + table[4 * 256 + 152] = 4; + table[3 * 256 + 153] = 4; + table[4 * 256 + 153] = 4; + table[3 * 256 + 154] = 4; + table[4 * 256 + 154] = 4; + table[3 * 256 + 155] = 4; + table[4 * 256 + 155] = 4; + table[3 * 256 + 156] = 4; + table[4 * 256 + 156] = 4; + table[3 * 256 + 157] = 4; + table[4 * 256 + 157] = 4; + table[3 * 256 + 158] = 4; + table[4 * 256 + 158] = 4; + table[3 * 256 + 159] = 4; + table[4 * 256 + 159] = 4; + table[3 * 256 + 160] = 4; + table[4 * 256 + 160] = 4; + table[3 * 256 + 161] = 4; + table[4 * 256 + 161] = 4; + table[3 * 256 + 162] = 4; + table[4 * 256 + 162] = 4; + table[3 * 256 + 163] = 4; + table[4 * 256 + 163] = 4; + table[3 * 256 + 164] = 4; + table[4 * 256 + 164] = 4; + table[3 * 256 + 165] = 4; + table[4 * 256 + 165] = 4; + table[3 * 256 + 166] = 4; + table[4 * 256 + 166] = 4; + table[3 * 256 + 167] = 4; + table[4 * 256 + 167] = 4; + table[3 * 256 + 168] = 4; + table[4 * 256 + 168] = 4; + table[3 * 256 + 169] = 4; + table[4 * 256 + 169] = 4; + table[3 * 256 + 170] = 4; + table[4 * 256 + 170] = 4; + table[3 * 256 + 171] = 4; + table[4 * 256 + 171] = 4; + table[3 * 256 + 172] = 4; + table[4 * 256 + 172] = 4; + table[3 * 256 + 173] = 4; + table[4 * 256 + 173] = 4; + table[3 * 256 + 174] = 4; + table[4 * 256 + 174] = 4; + table[3 * 256 + 175] = 4; + table[4 * 256 + 175] = 4; + table[3 * 256 + 176] = 4; + table[4 * 256 + 176] = 4; + table[3 * 256 + 177] = 4; + table[4 * 256 + 177] = 4; + table[3 * 256 + 178] = 4; + table[4 * 256 + 178] = 4; + table[3 * 256 + 179] = 4; + table[4 * 256 + 179] = 4; + table[3 * 256 + 180] = 4; + table[4 * 256 + 180] = 4; + table[3 * 256 + 181] = 4; + table[4 * 256 + 181] = 4; + table[3 * 256 + 182] = 4; + table[4 * 256 + 182] = 4; + table[3 * 256 + 183] = 4; + table[4 * 256 + 183] = 4; + table[3 * 256 + 184] = 4; + table[4 * 256 + 184] = 4; + table[3 * 256 + 185] = 4; + table[4 * 256 + 185] = 4; + table[3 * 256 + 186] = 4; + table[4 * 256 + 186] = 4; + table[3 * 256 + 187] = 4; + table[4 * 256 + 187] = 4; + table[3 * 256 + 188] = 4; + table[4 * 256 + 188] = 4; + table[3 * 256 + 189] = 4; + table[4 * 256 + 189] = 4; + table[3 * 256 + 190] = 4; + table[4 * 256 + 190] = 4; + table[3 * 256 + 191] = 4; + table[4 * 256 + 191] = 4; + table[3 * 256 + 192] = 4; + table[4 * 256 + 192] = 4; + table[3 * 256 + 193] = 4; + table[4 * 256 + 193] = 4; + table[3 * 256 + 194] = 4; + table[4 * 256 + 194] = 4; + table[3 * 256 + 195] = 4; + table[4 * 256 + 195] = 4; + table[3 * 256 + 196] = 4; + table[4 * 256 + 196] = 4; + table[3 * 256 + 197] = 4; + table[4 * 256 + 197] = 4; + table[3 * 256 + 198] = 4; + table[4 * 256 + 198] = 4; + table[3 * 256 + 199] = 4; + table[4 * 256 + 199] = 4; + table[3 * 256 + 200] = 4; + table[4 * 256 + 200] = 4; + table[3 * 256 + 201] = 4; + table[4 * 256 + 201] = 4; + table[3 * 256 + 202] = 4; + table[4 * 256 + 202] = 4; + table[3 * 256 + 203] = 4; + table[4 * 256 + 203] = 4; + table[3 * 256 + 204] = 4; + table[4 * 256 + 204] = 4; + table[3 * 256 + 205] = 4; + table[4 * 256 + 205] = 4; + table[3 * 256 + 206] = 4; + table[4 * 256 + 206] = 4; + table[3 * 256 + 207] = 4; + table[4 * 256 + 207] = 4; + table[3 * 256 + 208] = 4; + table[4 * 256 + 208] = 4; + table[3 * 256 + 209] = 4; + table[4 * 256 + 209] = 4; + table[3 * 256 + 210] = 4; + table[4 * 256 + 210] = 4; + table[3 * 256 + 211] = 4; + table[4 * 256 + 211] = 4; + table[3 * 256 + 212] = 4; + table[4 * 256 + 212] = 4; + table[3 * 256 + 213] = 4; + table[4 * 256 + 213] = 4; + table[3 * 256 + 214] = 4; + table[4 * 256 + 214] = 4; + table[3 * 256 + 215] = 4; + table[4 * 256 + 215] = 4; + table[3 * 256 + 216] = 4; + table[4 * 256 + 216] = 4; + table[3 * 256 + 217] = 4; + table[4 * 256 + 217] = 4; + table[3 * 256 + 218] = 4; + table[4 * 256 + 218] = 4; + table[3 * 256 + 219] = 4; + table[4 * 256 + 219] = 4; + table[3 * 256 + 220] = 4; + table[4 * 256 + 220] = 4; + table[3 * 256 + 221] = 4; + table[4 * 256 + 221] = 4; + table[3 * 256 + 222] = 4; + table[4 * 256 + 222] = 4; + table[3 * 256 + 223] = 4; + table[4 * 256 + 223] = 4; + table[3 * 256 + 224] = 4; + table[4 * 256 + 224] = 4; + table[3 * 256 + 225] = 4; + table[4 * 256 + 225] = 4; + table[3 * 256 + 226] = 4; + table[4 * 256 + 226] = 4; + table[3 * 256 + 227] = 4; + table[4 * 256 + 227] = 4; + table[3 * 256 + 228] = 4; + table[4 * 256 + 228] = 4; + table[3 * 256 + 229] = 4; + table[4 * 256 + 229] = 4; + table[3 * 256 + 230] = 4; + table[4 * 256 + 230] = 4; + table[3 * 256 + 231] = 4; + table[4 * 256 + 231] = 4; + table[3 * 256 + 232] = 4; + table[4 * 256 + 232] = 4; + table[3 * 256 + 233] = 4; + table[4 * 256 + 233] = 4; + table[3 * 256 + 234] = 4; + table[4 * 256 + 234] = 4; + table[3 * 256 + 235] = 4; + table[4 * 256 + 235] = 4; + table[3 * 256 + 236] = 4; + table[4 * 256 + 236] = 4; + table[3 * 256 + 237] = 4; + table[4 * 256 + 237] = 4; + table[3 * 256 + 238] = 4; + table[4 * 256 + 238] = 4; + table[3 * 256 + 239] = 4; + table[4 * 256 + 239] = 4; + table[3 * 256 + 240] = 4; + table[4 * 256 + 240] = 4; + table[3 * 256 + 241] = 4; + table[4 * 256 + 241] = 4; + table[3 * 256 + 242] = 4; + table[4 * 256 + 242] = 4; + table[3 * 256 + 243] = 4; + table[4 * 256 + 243] = 4; + table[3 * 256 + 244] = 4; + table[4 * 256 + 244] = 4; + table[3 * 256 + 245] = 4; + table[4 * 256 + 245] = 4; + table[3 * 256 + 246] = 4; + table[4 * 256 + 246] = 4; + table[3 * 256 + 247] = 4; + table[4 * 256 + 247] = 4; + table[3 * 256 + 248] = 4; + table[4 * 256 + 248] = 4; + table[3 * 256 + 249] = 4; + table[4 * 256 + 249] = 4; + table[3 * 256 + 250] = 4; + table[4 * 256 + 250] = 4; + table[3 * 256 + 251] = 4; + table[4 * 256 + 251] = 4; + table[3 * 256 + 252] = 4; + table[4 * 256 + 252] = 4; + table[3 * 256 + 253] = 4; + table[4 * 256 + 253] = 4; + table[3 * 256 + 254] = 4; + table[4 * 256 + 254] = 4; + table[0 * 256 + 33] = 1; + table[0 * 256 + 35] = 1; + table[0 * 256 + 36] = 1; + table[0 * 256 + 37] = 1; + table[0 * 256 + 38] = 1; + table[0 * 256 + 39] = 1; + table[0 * 256 + 42] = 1; + table[0 * 256 + 43] = 1; + table[0 * 256 + 45] = 1; + table[0 * 256 + 46] = 1; + table[0 * 256 + 47] = 1; + table[0 * 256 + 48] = 1; + table[0 * 256 + 49] = 1; + table[0 * 256 + 50] = 1; + table[0 * 256 + 51] = 1; + table[0 * 256 + 52] = 1; + table[0 * 256 + 53] = 1; + table[0 * 256 + 54] = 1; + table[0 * 256 + 55] = 1; + table[0 * 256 + 56] = 1; + table[0 * 256 + 57] = 1; + table[0 * 256 + 61] = 1; + table[0 * 256 + 63] = 1; + table[0 * 256 + 64] = 1; + table[0 * 256 + 65] = 1; + table[0 * 256 + 66] = 1; + table[0 * 256 + 67] = 1; + table[0 * 256 + 68] = 1; + table[0 * 256 + 69] = 1; + table[0 * 256 + 70] = 1; + table[0 * 256 + 71] = 1; + table[0 * 256 + 72] = 1; + table[0 * 256 + 73] = 1; + table[0 * 256 + 74] = 1; + table[0 * 256 + 75] = 1; + table[0 * 256 + 76] = 1; + table[0 * 256 + 77] = 1; + table[0 * 256 + 78] = 1; + table[0 * 256 + 79] = 1; + table[0 * 256 + 80] = 1; + table[0 * 256 + 81] = 1; + table[0 * 256 + 82] = 1; + table[0 * 256 + 83] = 1; + table[0 * 256 + 84] = 1; + table[0 * 256 + 85] = 1; + table[0 * 256 + 86] = 1; + table[0 * 256 + 87] = 1; + table[0 * 256 + 88] = 1; + table[0 * 256 + 89] = 1; + table[0 * 256 + 90] = 1; + table[0 * 256 + 94] = 1; + table[0 * 256 + 95] = 1; + table[0 * 256 + 96] = 1; + table[0 * 256 + 97] = 1; + table[0 * 256 + 98] = 1; + table[0 * 256 + 99] = 1; + table[0 * 256 + 100] = 1; + table[0 * 256 + 101] = 1; + table[0 * 256 + 102] = 1; + table[0 * 256 + 103] = 1; + table[0 * 256 + 104] = 1; + table[0 * 256 + 105] = 1; + table[0 * 256 + 106] = 1; + table[0 * 256 + 107] = 1; + table[0 * 256 + 108] = 1; + table[0 * 256 + 109] = 1; + table[0 * 256 + 110] = 1; + table[0 * 256 + 111] = 1; + table[0 * 256 + 112] = 1; + table[0 * 256 + 113] = 1; + table[0 * 256 + 114] = 1; + table[0 * 256 + 115] = 1; + table[0 * 256 + 116] = 1; + table[0 * 256 + 117] = 1; + table[0 * 256 + 118] = 1; + table[0 * 256 + 119] = 1; + table[0 * 256 + 120] = 1; + table[0 * 256 + 121] = 1; + table[0 * 256 + 122] = 1; + table[0 * 256 + 123] = 1; + table[0 * 256 + 124] = 1; + table[0 * 256 + 125] = 1; + table[0 * 256 + 126] = 1; + table[1 * 256 + 33] = 1; + table[1 * 256 + 35] = 1; + table[1 * 256 + 36] = 1; + table[1 * 256 + 37] = 1; + table[1 * 256 + 38] = 1; + table[1 * 256 + 39] = 1; + table[1 * 256 + 42] = 1; + table[1 * 256 + 43] = 1; + table[1 * 256 + 45] = 1; + table[1 * 256 + 46] = 1; + table[1 * 256 + 47] = 1; + table[1 * 256 + 48] = 1; + table[1 * 256 + 49] = 1; + table[1 * 256 + 50] = 1; + table[1 * 256 + 51] = 1; + table[1 * 256 + 52] = 1; + table[1 * 256 + 53] = 1; + table[1 * 256 + 54] = 1; + table[1 * 256 + 55] = 1; + table[1 * 256 + 56] = 1; + table[1 * 256 + 57] = 1; + table[1 * 256 + 61] = 1; + table[1 * 256 + 63] = 1; + table[1 * 256 + 65] = 1; + table[1 * 256 + 66] = 1; + table[1 * 256 + 67] = 1; + table[1 * 256 + 68] = 1; + table[1 * 256 + 69] = 1; + table[1 * 256 + 70] = 1; + table[1 * 256 + 71] = 1; + table[1 * 256 + 72] = 1; + table[1 * 256 + 73] = 1; + table[1 * 256 + 74] = 1; + table[1 * 256 + 75] = 1; + table[1 * 256 + 76] = 1; + table[1 * 256 + 77] = 1; + table[1 * 256 + 78] = 1; + table[1 * 256 + 79] = 1; + table[1 * 256 + 80] = 1; + table[1 * 256 + 81] = 1; + table[1 * 256 + 82] = 1; + table[1 * 256 + 83] = 1; + table[1 * 256 + 84] = 1; + table[1 * 256 + 85] = 1; + table[1 * 256 + 86] = 1; + table[1 * 256 + 87] = 1; + table[1 * 256 + 88] = 1; + table[1 * 256 + 89] = 1; + table[1 * 256 + 90] = 1; + table[1 * 256 + 94] = 1; + table[1 * 256 + 95] = 1; + table[1 * 256 + 96] = 1; + table[1 * 256 + 97] = 1; + table[1 * 256 + 98] = 1; + table[1 * 256 + 99] = 1; + table[1 * 256 + 100] = 1; + table[1 * 256 + 101] = 1; + table[1 * 256 + 102] = 1; + table[1 * 256 + 103] = 1; + table[1 * 256 + 104] = 1; + table[1 * 256 + 105] = 1; + table[1 * 256 + 106] = 1; + table[1 * 256 + 107] = 1; + table[1 * 256 + 108] = 1; + table[1 * 256 + 109] = 1; + table[1 * 256 + 110] = 1; + table[1 * 256 + 111] = 1; + table[1 * 256 + 112] = 1; + table[1 * 256 + 113] = 1; + table[1 * 256 + 114] = 1; + table[1 * 256 + 115] = 1; + table[1 * 256 + 116] = 1; + table[1 * 256 + 117] = 1; + table[1 * 256 + 118] = 1; + table[1 * 256 + 119] = 1; + table[1 * 256 + 120] = 1; + table[1 * 256 + 121] = 1; + table[1 * 256 + 122] = 1; + table[1 * 256 + 123] = 1; + table[1 * 256 + 124] = 1; + table[1 * 256 + 125] = 1; + table[1 * 256 + 126] = 1; + table[1 * 256 + 64] = 2; + table[2 * 256 + 33] = 1; + table[2 * 256 + 35] = 1; + table[2 * 256 + 36] = 1; + table[2 * 256 + 37] = 1; + table[2 * 256 + 38] = 1; + table[2 * 256 + 39] = 1; + table[2 * 256 + 42] = 1; + table[2 * 256 + 43] = 1; + table[2 * 256 + 47] = 1; + table[2 * 256 + 61] = 1; + table[2 * 256 + 63] = 1; + table[2 * 256 + 94] = 1; + table[2 * 256 + 95] = 1; + table[2 * 256 + 96] = 1; + table[2 * 256 + 123] = 1; + table[2 * 256 + 124] = 1; + table[2 * 256 + 125] = 1; + table[2 * 256 + 126] = 1; + table[2 * 256 + 64] = 2; + table[2 * 256 + 45] = 3; + table[2 * 256 + 46] = 3; + table[2 * 256 + 48] = 3; + table[2 * 256 + 49] = 3; + table[2 * 256 + 50] = 3; + table[2 * 256 + 51] = 3; + table[2 * 256 + 52] = 3; + table[2 * 256 + 53] = 3; + table[2 * 256 + 54] = 3; + table[2 * 256 + 55] = 3; + table[2 * 256 + 56] = 3; + table[2 * 256 + 57] = 3; + table[2 * 256 + 65] = 3; + table[2 * 256 + 66] = 3; + table[2 * 256 + 67] = 3; + table[2 * 256 + 68] = 3; + table[2 * 256 + 69] = 3; + table[2 * 256 + 70] = 3; + table[2 * 256 + 71] = 3; + table[2 * 256 + 72] = 3; + table[2 * 256 + 73] = 3; + table[2 * 256 + 74] = 3; + table[2 * 256 + 75] = 3; + table[2 * 256 + 76] = 3; + table[2 * 256 + 77] = 3; + table[2 * 256 + 78] = 3; + table[2 * 256 + 79] = 3; + table[2 * 256 + 80] = 3; + table[2 * 256 + 81] = 3; + table[2 * 256 + 82] = 3; + table[2 * 256 + 83] = 3; + table[2 * 256 + 84] = 3; + table[2 * 256 + 85] = 3; + table[2 * 256 + 86] = 3; + table[2 * 256 + 87] = 3; + table[2 * 256 + 88] = 3; + table[2 * 256 + 89] = 3; + table[2 * 256 + 90] = 3; + table[2 * 256 + 97] = 3; + table[2 * 256 + 98] = 3; + table[2 * 256 + 99] = 3; + table[2 * 256 + 100] = 3; + table[2 * 256 + 101] = 3; + table[2 * 256 + 102] = 3; + table[2 * 256 + 103] = 3; + table[2 * 256 + 104] = 3; + table[2 * 256 + 105] = 3; + table[2 * 256 + 106] = 3; + table[2 * 256 + 107] = 3; + table[2 * 256 + 108] = 3; + table[2 * 256 + 109] = 3; + table[2 * 256 + 110] = 3; + table[2 * 256 + 111] = 3; + table[2 * 256 + 112] = 3; + table[2 * 256 + 113] = 3; + table[2 * 256 + 114] = 3; + table[2 * 256 + 115] = 3; + table[2 * 256 + 116] = 3; + table[2 * 256 + 117] = 3; + table[2 * 256 + 118] = 3; + table[2 * 256 + 119] = 3; + table[2 * 256 + 120] = 3; + table[2 * 256 + 121] = 3; + table[2 * 256 + 122] = 3; + table[3 * 256 + 33] = 1; + table[3 * 256 + 35] = 1; + table[3 * 256 + 36] = 1; + table[3 * 256 + 37] = 1; + table[3 * 256 + 38] = 1; + table[3 * 256 + 39] = 1; + table[3 * 256 + 42] = 1; + table[3 * 256 + 43] = 1; + table[3 * 256 + 47] = 1; + table[3 * 256 + 61] = 1; + table[3 * 256 + 63] = 1; + table[3 * 256 + 94] = 1; + table[3 * 256 + 95] = 1; + table[3 * 256 + 96] = 1; + table[3 * 256 + 123] = 1; + table[3 * 256 + 124] = 1; + table[3 * 256 + 125] = 1; + table[3 * 256 + 126] = 1; + table[3 * 256 + 64] = 2; + table[3 * 256 + 45] = 3; + table[3 * 256 + 46] = 3; + table[3 * 256 + 48] = 3; + table[3 * 256 + 49] = 3; + table[3 * 256 + 50] = 3; + table[3 * 256 + 51] = 3; + table[3 * 256 + 52] = 3; + table[3 * 256 + 53] = 3; + table[3 * 256 + 54] = 3; + table[3 * 256 + 55] = 3; + table[3 * 256 + 56] = 3; + table[3 * 256 + 57] = 3; + table[3 * 256 + 65] = 3; + table[3 * 256 + 66] = 3; + table[3 * 256 + 67] = 3; + table[3 * 256 + 68] = 3; + table[3 * 256 + 69] = 3; + table[3 * 256 + 70] = 3; + table[3 * 256 + 71] = 3; + table[3 * 256 + 72] = 3; + table[3 * 256 + 73] = 3; + table[3 * 256 + 74] = 3; + table[3 * 256 + 75] = 3; + table[3 * 256 + 76] = 3; + table[3 * 256 + 77] = 3; + table[3 * 256 + 78] = 3; + table[3 * 256 + 79] = 3; + table[3 * 256 + 80] = 3; + table[3 * 256 + 81] = 3; + table[3 * 256 + 82] = 3; + table[3 * 256 + 83] = 3; + table[3 * 256 + 84] = 3; + table[3 * 256 + 85] = 3; + table[3 * 256 + 86] = 3; + table[3 * 256 + 87] = 3; + table[3 * 256 + 88] = 3; + table[3 * 256 + 89] = 3; + table[3 * 256 + 90] = 3; + table[3 * 256 + 97] = 3; + table[3 * 256 + 98] = 3; + table[3 * 256 + 99] = 3; + table[3 * 256 + 100] = 3; + table[3 * 256 + 101] = 3; + table[3 * 256 + 102] = 3; + table[3 * 256 + 103] = 3; + table[3 * 256 + 104] = 3; + table[3 * 256 + 105] = 3; + table[3 * 256 + 106] = 3; + table[3 * 256 + 107] = 3; + table[3 * 256 + 108] = 3; + table[3 * 256 + 109] = 3; + table[3 * 256 + 110] = 3; + table[3 * 256 + 111] = 3; + table[3 * 256 + 112] = 3; + table[3 * 256 + 113] = 3; + table[3 * 256 + 114] = 3; + table[3 * 256 + 115] = 3; + table[3 * 256 + 116] = 3; + table[3 * 256 + 117] = 3; + table[3 * 256 + 118] = 3; + table[3 * 256 + 119] = 3; + table[3 * 256 + 120] = 3; + table[3 * 256 + 121] = 3; + table[3 * 256 + 122] = 3; + + table +} + + +pub fn regex_match(input: [u8; N]) -> (BoundedVec, bool) { + let substrings = unsafe { __regex_match(input) }; + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + let mut start_range = 0; + let mut end_range = 0; + + // check the match + for i in 0..N { + // state transition + let temp = input[i] as Field; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + s = 0; + s_next = potential_s_next; + } + std::as_witness(s_next); + + // range conditions for substring matches + if ((start_range == 0) & (end_range == 0)) { + start_range = i as Field; + } + if (((s == 3) & (s_next == 4)) & (end_range == 0)) { + end_range = i as Field + 1; + } + + + let range_0 = substrings.get_unchecked(0).in_range(i); + let case_0 = [ + (s == 1) & ((s_next == 1) | (s_next == 2)), + (s_next == 1) & ((s == 0)), + (s == 2) & ((s_next == 1) | (s_next == 2) | (s_next == 3)), + (s == 3) & ((s_next == 1) | (s_next == 2) | (s_next == 3)) + ].any(|case| case == true) | !range_0; + + + + let substring_range_check = [case_0] + .all(|case| case == true); + + assert(substring_range_check, "substr array ranges wrong"); + + + s = s_next; + } + // check final state + + let matched: bool = (s == 3) | (s == 4); + + // constrain extracted substrings to be in match range + //let full_match = Sequence::new(start_range as u32, end_range as u32 - start_range as u32); + //let full_match_end = full_match.end(); + // for i in 0..1 { + // let substring = substrings.get_unchecked(i); + // let is_not_valid = i >= substrings.len(); + // let index_check = substring.index >= full_match.index; + // let length_check = substring.end() <= full_match_end; + // let check = (index_check) | is_not_valid; + // assert(check, f"Substring {i} range is out of bounds of the full match found"); + // } + (substrings, matched) +} + + +pub unconstrained fn __regex_match(input: [u8; N]) -> BoundedVec { + // regex: [A-Za-z0-9!#$%&'*+=?\-\^_`{|}~./@]+@[A-Za-z0-9.\-]+ + let mut substrings: BoundedVec = BoundedVec::new(); + let mut current_substring = Sequence::default(); + let mut full_match = Sequence::default(); + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + + let mut consecutive_substr = 0; + let mut complete = false; + + for i in 0..input.len() { + let temp = input[i] as Field; + let mut reset = false; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + reset = true; + s = 0; + s_next = potential_s_next; + } + // If a substring was in the making, but the state was reset + // we disregard previous progress because apparently it is invalid + if (reset & (consecutive_substr == 1)) { + current_substring = Sequence::default(); + consecutive_substr = 0; + } + // Fill up substrings + + + if ((s == 0) & (s_next == 1) | (s == 1) & (s_next == 1) | (s == 1) & (s_next == 2) | (s == 2) & (s_next == 1) | (s == 2) & (s_next == 2) | (s == 2) & (s_next == 3) | (s == 3) & (s_next == 1) | (s == 3) & (s_next == 2) | (s == 3) & (s_next == 3)) { + + if (consecutive_substr == 0) { + current_substring.index = i; + }; + current_substring.length += 1; + consecutive_substr = 1; + } else if ((consecutive_substr == 1) & (s_next == 0)) { + current_substring = Sequence::default(); + full_match = Sequence::default(); + substrings = BoundedVec::new(); + consecutive_substr = 0; + } else if (s == 3) & (s_next == 4) { + full_match.length = i - full_match.index + 1; + complete = true; + } else if (consecutive_substr == 1) { + // The substring is done so "save" it + substrings.push(current_substring); + // reset the substring holder for next use + current_substring = Sequence::default(); + consecutive_substr = 0; + } + s = s_next; + if complete == true { + break; + } + } + assert((s == 3) | (s == 4), f"no match: {s}"); + // Add pending substring that hasn't been added + if consecutive_substr == 1 { + substrings.push(current_substring); + full_match.length = input.len() - full_match.index; + } + + + + substrings +} + + + + \ No newline at end of file diff --git a/packages/noir/src/capture/raw/email_domain.nr b/packages/noir/src/capture/raw/email_domain.nr new file mode 100644 index 00000000..773e393f --- /dev/null +++ b/packages/noir/src/capture/raw/email_domain.nr @@ -0,0 +1,960 @@ + +use crate::common::Sequence; + + +global table: [Field; 1280] = comptime { make_lookup_table() }; + +comptime fn make_lookup_table() -> [Field; 1280] { + let mut table = [0; 1280]; + table[3 * 256 + 0] = 4; + table[4 * 256 + 0] = 4; + table[3 * 256 + 1] = 4; + table[4 * 256 + 1] = 4; + table[3 * 256 + 2] = 4; + table[4 * 256 + 2] = 4; + table[3 * 256 + 3] = 4; + table[4 * 256 + 3] = 4; + table[3 * 256 + 4] = 4; + table[4 * 256 + 4] = 4; + table[3 * 256 + 5] = 4; + table[4 * 256 + 5] = 4; + table[3 * 256 + 6] = 4; + table[4 * 256 + 6] = 4; + table[3 * 256 + 7] = 4; + table[4 * 256 + 7] = 4; + table[3 * 256 + 8] = 4; + table[4 * 256 + 8] = 4; + table[3 * 256 + 9] = 4; + table[4 * 256 + 9] = 4; + table[3 * 256 + 10] = 4; + table[4 * 256 + 10] = 4; + table[3 * 256 + 11] = 4; + table[4 * 256 + 11] = 4; + table[3 * 256 + 12] = 4; + table[4 * 256 + 12] = 4; + table[3 * 256 + 13] = 4; + table[4 * 256 + 13] = 4; + table[3 * 256 + 14] = 4; + table[4 * 256 + 14] = 4; + table[3 * 256 + 15] = 4; + table[4 * 256 + 15] = 4; + table[3 * 256 + 16] = 4; + table[4 * 256 + 16] = 4; + table[3 * 256 + 17] = 4; + table[4 * 256 + 17] = 4; + table[3 * 256 + 18] = 4; + table[4 * 256 + 18] = 4; + table[3 * 256 + 19] = 4; + table[4 * 256 + 19] = 4; + table[3 * 256 + 20] = 4; + table[4 * 256 + 20] = 4; + table[3 * 256 + 21] = 4; + table[4 * 256 + 21] = 4; + table[3 * 256 + 22] = 4; + table[4 * 256 + 22] = 4; + table[3 * 256 + 23] = 4; + table[4 * 256 + 23] = 4; + table[3 * 256 + 24] = 4; + table[4 * 256 + 24] = 4; + table[3 * 256 + 25] = 4; + table[4 * 256 + 25] = 4; + table[3 * 256 + 26] = 4; + table[4 * 256 + 26] = 4; + table[3 * 256 + 27] = 4; + table[4 * 256 + 27] = 4; + table[3 * 256 + 28] = 4; + table[4 * 256 + 28] = 4; + table[3 * 256 + 29] = 4; + table[4 * 256 + 29] = 4; + table[3 * 256 + 30] = 4; + table[4 * 256 + 30] = 4; + table[3 * 256 + 31] = 4; + table[4 * 256 + 31] = 4; + table[3 * 256 + 32] = 4; + table[4 * 256 + 32] = 4; + table[3 * 256 + 33] = 4; + table[4 * 256 + 33] = 4; + table[3 * 256 + 34] = 4; + table[4 * 256 + 34] = 4; + table[3 * 256 + 35] = 4; + table[4 * 256 + 35] = 4; + table[3 * 256 + 36] = 4; + table[4 * 256 + 36] = 4; + table[3 * 256 + 37] = 4; + table[4 * 256 + 37] = 4; + table[3 * 256 + 38] = 4; + table[4 * 256 + 38] = 4; + table[3 * 256 + 39] = 4; + table[4 * 256 + 39] = 4; + table[3 * 256 + 40] = 4; + table[4 * 256 + 40] = 4; + table[3 * 256 + 41] = 4; + table[4 * 256 + 41] = 4; + table[3 * 256 + 42] = 4; + table[4 * 256 + 42] = 4; + table[3 * 256 + 43] = 4; + table[4 * 256 + 43] = 4; + table[3 * 256 + 44] = 4; + table[4 * 256 + 44] = 4; + table[3 * 256 + 45] = 4; + table[4 * 256 + 45] = 4; + table[3 * 256 + 46] = 4; + table[4 * 256 + 46] = 4; + table[3 * 256 + 47] = 4; + table[4 * 256 + 47] = 4; + table[3 * 256 + 48] = 4; + table[4 * 256 + 48] = 4; + table[3 * 256 + 49] = 4; + table[4 * 256 + 49] = 4; + table[3 * 256 + 50] = 4; + table[4 * 256 + 50] = 4; + table[3 * 256 + 51] = 4; + table[4 * 256 + 51] = 4; + table[3 * 256 + 52] = 4; + table[4 * 256 + 52] = 4; + table[3 * 256 + 53] = 4; + table[4 * 256 + 53] = 4; + table[3 * 256 + 54] = 4; + table[4 * 256 + 54] = 4; + table[3 * 256 + 55] = 4; + table[4 * 256 + 55] = 4; + table[3 * 256 + 56] = 4; + table[4 * 256 + 56] = 4; + table[3 * 256 + 57] = 4; + table[4 * 256 + 57] = 4; + table[3 * 256 + 58] = 4; + table[4 * 256 + 58] = 4; + table[3 * 256 + 59] = 4; + table[4 * 256 + 59] = 4; + table[3 * 256 + 60] = 4; + table[4 * 256 + 60] = 4; + table[3 * 256 + 61] = 4; + table[4 * 256 + 61] = 4; + table[3 * 256 + 62] = 4; + table[4 * 256 + 62] = 4; + table[3 * 256 + 63] = 4; + table[4 * 256 + 63] = 4; + table[3 * 256 + 64] = 4; + table[4 * 256 + 64] = 4; + table[3 * 256 + 65] = 4; + table[4 * 256 + 65] = 4; + table[3 * 256 + 66] = 4; + table[4 * 256 + 66] = 4; + table[3 * 256 + 67] = 4; + table[4 * 256 + 67] = 4; + table[3 * 256 + 68] = 4; + table[4 * 256 + 68] = 4; + table[3 * 256 + 69] = 4; + table[4 * 256 + 69] = 4; + table[3 * 256 + 70] = 4; + table[4 * 256 + 70] = 4; + table[3 * 256 + 71] = 4; + table[4 * 256 + 71] = 4; + table[3 * 256 + 72] = 4; + table[4 * 256 + 72] = 4; + table[3 * 256 + 73] = 4; + table[4 * 256 + 73] = 4; + table[3 * 256 + 74] = 4; + table[4 * 256 + 74] = 4; + table[3 * 256 + 75] = 4; + table[4 * 256 + 75] = 4; + table[3 * 256 + 76] = 4; + table[4 * 256 + 76] = 4; + table[3 * 256 + 77] = 4; + table[4 * 256 + 77] = 4; + table[3 * 256 + 78] = 4; + table[4 * 256 + 78] = 4; + table[3 * 256 + 79] = 4; + table[4 * 256 + 79] = 4; + table[3 * 256 + 80] = 4; + table[4 * 256 + 80] = 4; + table[3 * 256 + 81] = 4; + table[4 * 256 + 81] = 4; + table[3 * 256 + 82] = 4; + table[4 * 256 + 82] = 4; + table[3 * 256 + 83] = 4; + table[4 * 256 + 83] = 4; + table[3 * 256 + 84] = 4; + table[4 * 256 + 84] = 4; + table[3 * 256 + 85] = 4; + table[4 * 256 + 85] = 4; + table[3 * 256 + 86] = 4; + table[4 * 256 + 86] = 4; + table[3 * 256 + 87] = 4; + table[4 * 256 + 87] = 4; + table[3 * 256 + 88] = 4; + table[4 * 256 + 88] = 4; + table[3 * 256 + 89] = 4; + table[4 * 256 + 89] = 4; + table[3 * 256 + 90] = 4; + table[4 * 256 + 90] = 4; + table[3 * 256 + 91] = 4; + table[4 * 256 + 91] = 4; + table[3 * 256 + 92] = 4; + table[4 * 256 + 92] = 4; + table[3 * 256 + 93] = 4; + table[4 * 256 + 93] = 4; + table[3 * 256 + 94] = 4; + table[4 * 256 + 94] = 4; + table[3 * 256 + 95] = 4; + table[4 * 256 + 95] = 4; + table[3 * 256 + 96] = 4; + table[4 * 256 + 96] = 4; + table[3 * 256 + 97] = 4; + table[4 * 256 + 97] = 4; + table[3 * 256 + 98] = 4; + table[4 * 256 + 98] = 4; + table[3 * 256 + 99] = 4; + table[4 * 256 + 99] = 4; + table[3 * 256 + 100] = 4; + table[4 * 256 + 100] = 4; + table[3 * 256 + 101] = 4; + table[4 * 256 + 101] = 4; + table[3 * 256 + 102] = 4; + table[4 * 256 + 102] = 4; + table[3 * 256 + 103] = 4; + table[4 * 256 + 103] = 4; + table[3 * 256 + 104] = 4; + table[4 * 256 + 104] = 4; + table[3 * 256 + 105] = 4; + table[4 * 256 + 105] = 4; + table[3 * 256 + 106] = 4; + table[4 * 256 + 106] = 4; + table[3 * 256 + 107] = 4; + table[4 * 256 + 107] = 4; + table[3 * 256 + 108] = 4; + table[4 * 256 + 108] = 4; + table[3 * 256 + 109] = 4; + table[4 * 256 + 109] = 4; + table[3 * 256 + 110] = 4; + table[4 * 256 + 110] = 4; + table[3 * 256 + 111] = 4; + table[4 * 256 + 111] = 4; + table[3 * 256 + 112] = 4; + table[4 * 256 + 112] = 4; + table[3 * 256 + 113] = 4; + table[4 * 256 + 113] = 4; + table[3 * 256 + 114] = 4; + table[4 * 256 + 114] = 4; + table[3 * 256 + 115] = 4; + table[4 * 256 + 115] = 4; + table[3 * 256 + 116] = 4; + table[4 * 256 + 116] = 4; + table[3 * 256 + 117] = 4; + table[4 * 256 + 117] = 4; + table[3 * 256 + 118] = 4; + table[4 * 256 + 118] = 4; + table[3 * 256 + 119] = 4; + table[4 * 256 + 119] = 4; + table[3 * 256 + 120] = 4; + table[4 * 256 + 120] = 4; + table[3 * 256 + 121] = 4; + table[4 * 256 + 121] = 4; + table[3 * 256 + 122] = 4; + table[4 * 256 + 122] = 4; + table[3 * 256 + 123] = 4; + table[4 * 256 + 123] = 4; + table[3 * 256 + 124] = 4; + table[4 * 256 + 124] = 4; + table[3 * 256 + 125] = 4; + table[4 * 256 + 125] = 4; + table[3 * 256 + 126] = 4; + table[4 * 256 + 126] = 4; + table[3 * 256 + 127] = 4; + table[4 * 256 + 127] = 4; + table[3 * 256 + 128] = 4; + table[4 * 256 + 128] = 4; + table[3 * 256 + 129] = 4; + table[4 * 256 + 129] = 4; + table[3 * 256 + 130] = 4; + table[4 * 256 + 130] = 4; + table[3 * 256 + 131] = 4; + table[4 * 256 + 131] = 4; + table[3 * 256 + 132] = 4; + table[4 * 256 + 132] = 4; + table[3 * 256 + 133] = 4; + table[4 * 256 + 133] = 4; + table[3 * 256 + 134] = 4; + table[4 * 256 + 134] = 4; + table[3 * 256 + 135] = 4; + table[4 * 256 + 135] = 4; + table[3 * 256 + 136] = 4; + table[4 * 256 + 136] = 4; + table[3 * 256 + 137] = 4; + table[4 * 256 + 137] = 4; + table[3 * 256 + 138] = 4; + table[4 * 256 + 138] = 4; + table[3 * 256 + 139] = 4; + table[4 * 256 + 139] = 4; + table[3 * 256 + 140] = 4; + table[4 * 256 + 140] = 4; + table[3 * 256 + 141] = 4; + table[4 * 256 + 141] = 4; + table[3 * 256 + 142] = 4; + table[4 * 256 + 142] = 4; + table[3 * 256 + 143] = 4; + table[4 * 256 + 143] = 4; + table[3 * 256 + 144] = 4; + table[4 * 256 + 144] = 4; + table[3 * 256 + 145] = 4; + table[4 * 256 + 145] = 4; + table[3 * 256 + 146] = 4; + table[4 * 256 + 146] = 4; + table[3 * 256 + 147] = 4; + table[4 * 256 + 147] = 4; + table[3 * 256 + 148] = 4; + table[4 * 256 + 148] = 4; + table[3 * 256 + 149] = 4; + table[4 * 256 + 149] = 4; + table[3 * 256 + 150] = 4; + table[4 * 256 + 150] = 4; + table[3 * 256 + 151] = 4; + table[4 * 256 + 151] = 4; + table[3 * 256 + 152] = 4; + table[4 * 256 + 152] = 4; + table[3 * 256 + 153] = 4; + table[4 * 256 + 153] = 4; + table[3 * 256 + 154] = 4; + table[4 * 256 + 154] = 4; + table[3 * 256 + 155] = 4; + table[4 * 256 + 155] = 4; + table[3 * 256 + 156] = 4; + table[4 * 256 + 156] = 4; + table[3 * 256 + 157] = 4; + table[4 * 256 + 157] = 4; + table[3 * 256 + 158] = 4; + table[4 * 256 + 158] = 4; + table[3 * 256 + 159] = 4; + table[4 * 256 + 159] = 4; + table[3 * 256 + 160] = 4; + table[4 * 256 + 160] = 4; + table[3 * 256 + 161] = 4; + table[4 * 256 + 161] = 4; + table[3 * 256 + 162] = 4; + table[4 * 256 + 162] = 4; + table[3 * 256 + 163] = 4; + table[4 * 256 + 163] = 4; + table[3 * 256 + 164] = 4; + table[4 * 256 + 164] = 4; + table[3 * 256 + 165] = 4; + table[4 * 256 + 165] = 4; + table[3 * 256 + 166] = 4; + table[4 * 256 + 166] = 4; + table[3 * 256 + 167] = 4; + table[4 * 256 + 167] = 4; + table[3 * 256 + 168] = 4; + table[4 * 256 + 168] = 4; + table[3 * 256 + 169] = 4; + table[4 * 256 + 169] = 4; + table[3 * 256 + 170] = 4; + table[4 * 256 + 170] = 4; + table[3 * 256 + 171] = 4; + table[4 * 256 + 171] = 4; + table[3 * 256 + 172] = 4; + table[4 * 256 + 172] = 4; + table[3 * 256 + 173] = 4; + table[4 * 256 + 173] = 4; + table[3 * 256 + 174] = 4; + table[4 * 256 + 174] = 4; + table[3 * 256 + 175] = 4; + table[4 * 256 + 175] = 4; + table[3 * 256 + 176] = 4; + table[4 * 256 + 176] = 4; + table[3 * 256 + 177] = 4; + table[4 * 256 + 177] = 4; + table[3 * 256 + 178] = 4; + table[4 * 256 + 178] = 4; + table[3 * 256 + 179] = 4; + table[4 * 256 + 179] = 4; + table[3 * 256 + 180] = 4; + table[4 * 256 + 180] = 4; + table[3 * 256 + 181] = 4; + table[4 * 256 + 181] = 4; + table[3 * 256 + 182] = 4; + table[4 * 256 + 182] = 4; + table[3 * 256 + 183] = 4; + table[4 * 256 + 183] = 4; + table[3 * 256 + 184] = 4; + table[4 * 256 + 184] = 4; + table[3 * 256 + 185] = 4; + table[4 * 256 + 185] = 4; + table[3 * 256 + 186] = 4; + table[4 * 256 + 186] = 4; + table[3 * 256 + 187] = 4; + table[4 * 256 + 187] = 4; + table[3 * 256 + 188] = 4; + table[4 * 256 + 188] = 4; + table[3 * 256 + 189] = 4; + table[4 * 256 + 189] = 4; + table[3 * 256 + 190] = 4; + table[4 * 256 + 190] = 4; + table[3 * 256 + 191] = 4; + table[4 * 256 + 191] = 4; + table[3 * 256 + 192] = 4; + table[4 * 256 + 192] = 4; + table[3 * 256 + 193] = 4; + table[4 * 256 + 193] = 4; + table[3 * 256 + 194] = 4; + table[4 * 256 + 194] = 4; + table[3 * 256 + 195] = 4; + table[4 * 256 + 195] = 4; + table[3 * 256 + 196] = 4; + table[4 * 256 + 196] = 4; + table[3 * 256 + 197] = 4; + table[4 * 256 + 197] = 4; + table[3 * 256 + 198] = 4; + table[4 * 256 + 198] = 4; + table[3 * 256 + 199] = 4; + table[4 * 256 + 199] = 4; + table[3 * 256 + 200] = 4; + table[4 * 256 + 200] = 4; + table[3 * 256 + 201] = 4; + table[4 * 256 + 201] = 4; + table[3 * 256 + 202] = 4; + table[4 * 256 + 202] = 4; + table[3 * 256 + 203] = 4; + table[4 * 256 + 203] = 4; + table[3 * 256 + 204] = 4; + table[4 * 256 + 204] = 4; + table[3 * 256 + 205] = 4; + table[4 * 256 + 205] = 4; + table[3 * 256 + 206] = 4; + table[4 * 256 + 206] = 4; + table[3 * 256 + 207] = 4; + table[4 * 256 + 207] = 4; + table[3 * 256 + 208] = 4; + table[4 * 256 + 208] = 4; + table[3 * 256 + 209] = 4; + table[4 * 256 + 209] = 4; + table[3 * 256 + 210] = 4; + table[4 * 256 + 210] = 4; + table[3 * 256 + 211] = 4; + table[4 * 256 + 211] = 4; + table[3 * 256 + 212] = 4; + table[4 * 256 + 212] = 4; + table[3 * 256 + 213] = 4; + table[4 * 256 + 213] = 4; + table[3 * 256 + 214] = 4; + table[4 * 256 + 214] = 4; + table[3 * 256 + 215] = 4; + table[4 * 256 + 215] = 4; + table[3 * 256 + 216] = 4; + table[4 * 256 + 216] = 4; + table[3 * 256 + 217] = 4; + table[4 * 256 + 217] = 4; + table[3 * 256 + 218] = 4; + table[4 * 256 + 218] = 4; + table[3 * 256 + 219] = 4; + table[4 * 256 + 219] = 4; + table[3 * 256 + 220] = 4; + table[4 * 256 + 220] = 4; + table[3 * 256 + 221] = 4; + table[4 * 256 + 221] = 4; + table[3 * 256 + 222] = 4; + table[4 * 256 + 222] = 4; + table[3 * 256 + 223] = 4; + table[4 * 256 + 223] = 4; + table[3 * 256 + 224] = 4; + table[4 * 256 + 224] = 4; + table[3 * 256 + 225] = 4; + table[4 * 256 + 225] = 4; + table[3 * 256 + 226] = 4; + table[4 * 256 + 226] = 4; + table[3 * 256 + 227] = 4; + table[4 * 256 + 227] = 4; + table[3 * 256 + 228] = 4; + table[4 * 256 + 228] = 4; + table[3 * 256 + 229] = 4; + table[4 * 256 + 229] = 4; + table[3 * 256 + 230] = 4; + table[4 * 256 + 230] = 4; + table[3 * 256 + 231] = 4; + table[4 * 256 + 231] = 4; + table[3 * 256 + 232] = 4; + table[4 * 256 + 232] = 4; + table[3 * 256 + 233] = 4; + table[4 * 256 + 233] = 4; + table[3 * 256 + 234] = 4; + table[4 * 256 + 234] = 4; + table[3 * 256 + 235] = 4; + table[4 * 256 + 235] = 4; + table[3 * 256 + 236] = 4; + table[4 * 256 + 236] = 4; + table[3 * 256 + 237] = 4; + table[4 * 256 + 237] = 4; + table[3 * 256 + 238] = 4; + table[4 * 256 + 238] = 4; + table[3 * 256 + 239] = 4; + table[4 * 256 + 239] = 4; + table[3 * 256 + 240] = 4; + table[4 * 256 + 240] = 4; + table[3 * 256 + 241] = 4; + table[4 * 256 + 241] = 4; + table[3 * 256 + 242] = 4; + table[4 * 256 + 242] = 4; + table[3 * 256 + 243] = 4; + table[4 * 256 + 243] = 4; + table[3 * 256 + 244] = 4; + table[4 * 256 + 244] = 4; + table[3 * 256 + 245] = 4; + table[4 * 256 + 245] = 4; + table[3 * 256 + 246] = 4; + table[4 * 256 + 246] = 4; + table[3 * 256 + 247] = 4; + table[4 * 256 + 247] = 4; + table[3 * 256 + 248] = 4; + table[4 * 256 + 248] = 4; + table[3 * 256 + 249] = 4; + table[4 * 256 + 249] = 4; + table[3 * 256 + 250] = 4; + table[4 * 256 + 250] = 4; + table[3 * 256 + 251] = 4; + table[4 * 256 + 251] = 4; + table[3 * 256 + 252] = 4; + table[4 * 256 + 252] = 4; + table[3 * 256 + 253] = 4; + table[4 * 256 + 253] = 4; + table[3 * 256 + 254] = 4; + table[4 * 256 + 254] = 4; + table[0 * 256 + 33] = 1; + table[0 * 256 + 35] = 1; + table[0 * 256 + 36] = 1; + table[0 * 256 + 37] = 1; + table[0 * 256 + 38] = 1; + table[0 * 256 + 39] = 1; + table[0 * 256 + 42] = 1; + table[0 * 256 + 43] = 1; + table[0 * 256 + 45] = 1; + table[0 * 256 + 46] = 1; + table[0 * 256 + 47] = 1; + table[0 * 256 + 48] = 1; + table[0 * 256 + 49] = 1; + table[0 * 256 + 50] = 1; + table[0 * 256 + 51] = 1; + table[0 * 256 + 52] = 1; + table[0 * 256 + 53] = 1; + table[0 * 256 + 54] = 1; + table[0 * 256 + 55] = 1; + table[0 * 256 + 56] = 1; + table[0 * 256 + 57] = 1; + table[0 * 256 + 61] = 1; + table[0 * 256 + 63] = 1; + table[0 * 256 + 65] = 1; + table[0 * 256 + 66] = 1; + table[0 * 256 + 67] = 1; + table[0 * 256 + 68] = 1; + table[0 * 256 + 69] = 1; + table[0 * 256 + 70] = 1; + table[0 * 256 + 71] = 1; + table[0 * 256 + 72] = 1; + table[0 * 256 + 73] = 1; + table[0 * 256 + 74] = 1; + table[0 * 256 + 75] = 1; + table[0 * 256 + 76] = 1; + table[0 * 256 + 77] = 1; + table[0 * 256 + 78] = 1; + table[0 * 256 + 79] = 1; + table[0 * 256 + 80] = 1; + table[0 * 256 + 81] = 1; + table[0 * 256 + 82] = 1; + table[0 * 256 + 83] = 1; + table[0 * 256 + 84] = 1; + table[0 * 256 + 85] = 1; + table[0 * 256 + 86] = 1; + table[0 * 256 + 87] = 1; + table[0 * 256 + 88] = 1; + table[0 * 256 + 89] = 1; + table[0 * 256 + 90] = 1; + table[0 * 256 + 94] = 1; + table[0 * 256 + 95] = 1; + table[0 * 256 + 96] = 1; + table[0 * 256 + 97] = 1; + table[0 * 256 + 98] = 1; + table[0 * 256 + 99] = 1; + table[0 * 256 + 100] = 1; + table[0 * 256 + 101] = 1; + table[0 * 256 + 102] = 1; + table[0 * 256 + 103] = 1; + table[0 * 256 + 104] = 1; + table[0 * 256 + 105] = 1; + table[0 * 256 + 106] = 1; + table[0 * 256 + 107] = 1; + table[0 * 256 + 108] = 1; + table[0 * 256 + 109] = 1; + table[0 * 256 + 110] = 1; + table[0 * 256 + 111] = 1; + table[0 * 256 + 112] = 1; + table[0 * 256 + 113] = 1; + table[0 * 256 + 114] = 1; + table[0 * 256 + 115] = 1; + table[0 * 256 + 116] = 1; + table[0 * 256 + 117] = 1; + table[0 * 256 + 118] = 1; + table[0 * 256 + 119] = 1; + table[0 * 256 + 120] = 1; + table[0 * 256 + 121] = 1; + table[0 * 256 + 122] = 1; + table[0 * 256 + 123] = 1; + table[0 * 256 + 124] = 1; + table[0 * 256 + 125] = 1; + table[0 * 256 + 126] = 1; + table[1 * 256 + 33] = 1; + table[1 * 256 + 35] = 1; + table[1 * 256 + 36] = 1; + table[1 * 256 + 37] = 1; + table[1 * 256 + 38] = 1; + table[1 * 256 + 39] = 1; + table[1 * 256 + 42] = 1; + table[1 * 256 + 43] = 1; + table[1 * 256 + 45] = 1; + table[1 * 256 + 46] = 1; + table[1 * 256 + 47] = 1; + table[1 * 256 + 48] = 1; + table[1 * 256 + 49] = 1; + table[1 * 256 + 50] = 1; + table[1 * 256 + 51] = 1; + table[1 * 256 + 52] = 1; + table[1 * 256 + 53] = 1; + table[1 * 256 + 54] = 1; + table[1 * 256 + 55] = 1; + table[1 * 256 + 56] = 1; + table[1 * 256 + 57] = 1; + table[1 * 256 + 61] = 1; + table[1 * 256 + 63] = 1; + table[1 * 256 + 65] = 1; + table[1 * 256 + 66] = 1; + table[1 * 256 + 67] = 1; + table[1 * 256 + 68] = 1; + table[1 * 256 + 69] = 1; + table[1 * 256 + 70] = 1; + table[1 * 256 + 71] = 1; + table[1 * 256 + 72] = 1; + table[1 * 256 + 73] = 1; + table[1 * 256 + 74] = 1; + table[1 * 256 + 75] = 1; + table[1 * 256 + 76] = 1; + table[1 * 256 + 77] = 1; + table[1 * 256 + 78] = 1; + table[1 * 256 + 79] = 1; + table[1 * 256 + 80] = 1; + table[1 * 256 + 81] = 1; + table[1 * 256 + 82] = 1; + table[1 * 256 + 83] = 1; + table[1 * 256 + 84] = 1; + table[1 * 256 + 85] = 1; + table[1 * 256 + 86] = 1; + table[1 * 256 + 87] = 1; + table[1 * 256 + 88] = 1; + table[1 * 256 + 89] = 1; + table[1 * 256 + 90] = 1; + table[1 * 256 + 94] = 1; + table[1 * 256 + 95] = 1; + table[1 * 256 + 96] = 1; + table[1 * 256 + 97] = 1; + table[1 * 256 + 98] = 1; + table[1 * 256 + 99] = 1; + table[1 * 256 + 100] = 1; + table[1 * 256 + 101] = 1; + table[1 * 256 + 102] = 1; + table[1 * 256 + 103] = 1; + table[1 * 256 + 104] = 1; + table[1 * 256 + 105] = 1; + table[1 * 256 + 106] = 1; + table[1 * 256 + 107] = 1; + table[1 * 256 + 108] = 1; + table[1 * 256 + 109] = 1; + table[1 * 256 + 110] = 1; + table[1 * 256 + 111] = 1; + table[1 * 256 + 112] = 1; + table[1 * 256 + 113] = 1; + table[1 * 256 + 114] = 1; + table[1 * 256 + 115] = 1; + table[1 * 256 + 116] = 1; + table[1 * 256 + 117] = 1; + table[1 * 256 + 118] = 1; + table[1 * 256 + 119] = 1; + table[1 * 256 + 120] = 1; + table[1 * 256 + 121] = 1; + table[1 * 256 + 122] = 1; + table[1 * 256 + 123] = 1; + table[1 * 256 + 124] = 1; + table[1 * 256 + 125] = 1; + table[1 * 256 + 126] = 1; + table[1 * 256 + 64] = 2; + table[2 * 256 + 45] = 3; + table[2 * 256 + 46] = 3; + table[2 * 256 + 48] = 3; + table[2 * 256 + 49] = 3; + table[2 * 256 + 50] = 3; + table[2 * 256 + 51] = 3; + table[2 * 256 + 52] = 3; + table[2 * 256 + 53] = 3; + table[2 * 256 + 54] = 3; + table[2 * 256 + 55] = 3; + table[2 * 256 + 56] = 3; + table[2 * 256 + 57] = 3; + table[2 * 256 + 64] = 3; + table[2 * 256 + 65] = 3; + table[2 * 256 + 66] = 3; + table[2 * 256 + 67] = 3; + table[2 * 256 + 68] = 3; + table[2 * 256 + 69] = 3; + table[2 * 256 + 70] = 3; + table[2 * 256 + 71] = 3; + table[2 * 256 + 72] = 3; + table[2 * 256 + 73] = 3; + table[2 * 256 + 74] = 3; + table[2 * 256 + 75] = 3; + table[2 * 256 + 76] = 3; + table[2 * 256 + 77] = 3; + table[2 * 256 + 78] = 3; + table[2 * 256 + 79] = 3; + table[2 * 256 + 80] = 3; + table[2 * 256 + 81] = 3; + table[2 * 256 + 82] = 3; + table[2 * 256 + 83] = 3; + table[2 * 256 + 84] = 3; + table[2 * 256 + 85] = 3; + table[2 * 256 + 86] = 3; + table[2 * 256 + 87] = 3; + table[2 * 256 + 88] = 3; + table[2 * 256 + 89] = 3; + table[2 * 256 + 90] = 3; + table[2 * 256 + 97] = 3; + table[2 * 256 + 98] = 3; + table[2 * 256 + 99] = 3; + table[2 * 256 + 100] = 3; + table[2 * 256 + 101] = 3; + table[2 * 256 + 102] = 3; + table[2 * 256 + 103] = 3; + table[2 * 256 + 104] = 3; + table[2 * 256 + 105] = 3; + table[2 * 256 + 106] = 3; + table[2 * 256 + 107] = 3; + table[2 * 256 + 108] = 3; + table[2 * 256 + 109] = 3; + table[2 * 256 + 110] = 3; + table[2 * 256 + 111] = 3; + table[2 * 256 + 112] = 3; + table[2 * 256 + 113] = 3; + table[2 * 256 + 114] = 3; + table[2 * 256 + 115] = 3; + table[2 * 256 + 116] = 3; + table[2 * 256 + 117] = 3; + table[2 * 256 + 118] = 3; + table[2 * 256 + 119] = 3; + table[2 * 256 + 120] = 3; + table[2 * 256 + 121] = 3; + table[2 * 256 + 122] = 3; + table[3 * 256 + 45] = 3; + table[3 * 256 + 46] = 3; + table[3 * 256 + 48] = 3; + table[3 * 256 + 49] = 3; + table[3 * 256 + 50] = 3; + table[3 * 256 + 51] = 3; + table[3 * 256 + 52] = 3; + table[3 * 256 + 53] = 3; + table[3 * 256 + 54] = 3; + table[3 * 256 + 55] = 3; + table[3 * 256 + 56] = 3; + table[3 * 256 + 57] = 3; + table[3 * 256 + 64] = 3; + table[3 * 256 + 65] = 3; + table[3 * 256 + 66] = 3; + table[3 * 256 + 67] = 3; + table[3 * 256 + 68] = 3; + table[3 * 256 + 69] = 3; + table[3 * 256 + 70] = 3; + table[3 * 256 + 71] = 3; + table[3 * 256 + 72] = 3; + table[3 * 256 + 73] = 3; + table[3 * 256 + 74] = 3; + table[3 * 256 + 75] = 3; + table[3 * 256 + 76] = 3; + table[3 * 256 + 77] = 3; + table[3 * 256 + 78] = 3; + table[3 * 256 + 79] = 3; + table[3 * 256 + 80] = 3; + table[3 * 256 + 81] = 3; + table[3 * 256 + 82] = 3; + table[3 * 256 + 83] = 3; + table[3 * 256 + 84] = 3; + table[3 * 256 + 85] = 3; + table[3 * 256 + 86] = 3; + table[3 * 256 + 87] = 3; + table[3 * 256 + 88] = 3; + table[3 * 256 + 89] = 3; + table[3 * 256 + 90] = 3; + table[3 * 256 + 97] = 3; + table[3 * 256 + 98] = 3; + table[3 * 256 + 99] = 3; + table[3 * 256 + 100] = 3; + table[3 * 256 + 101] = 3; + table[3 * 256 + 102] = 3; + table[3 * 256 + 103] = 3; + table[3 * 256 + 104] = 3; + table[3 * 256 + 105] = 3; + table[3 * 256 + 106] = 3; + table[3 * 256 + 107] = 3; + table[3 * 256 + 108] = 3; + table[3 * 256 + 109] = 3; + table[3 * 256 + 110] = 3; + table[3 * 256 + 111] = 3; + table[3 * 256 + 112] = 3; + table[3 * 256 + 113] = 3; + table[3 * 256 + 114] = 3; + table[3 * 256 + 115] = 3; + table[3 * 256 + 116] = 3; + table[3 * 256 + 117] = 3; + table[3 * 256 + 118] = 3; + table[3 * 256 + 119] = 3; + table[3 * 256 + 120] = 3; + table[3 * 256 + 121] = 3; + table[3 * 256 + 122] = 3; + + table +} + + +pub fn regex_match(input: [u8; N]) -> (BoundedVec, bool) { + let substrings = unsafe { __regex_match(input) }; + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + let mut start_range = 0; + let mut end_range = 0; + + // check the match + for i in 0..N { + // state transition + let temp = input[i] as Field; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + s = 0; + s_next = potential_s_next; + } + std::as_witness(s_next); + + // range conditions for substring matches + if ((start_range == 0) & (end_range == 0)) { + start_range = i as Field; + } + if (((s == 3) & (s_next == 4)) & (end_range == 0)) { + end_range = i as Field + 1; + } + + + let range_0 = substrings.get_unchecked(0).in_range(i); + let case_0 = [ + (s_next == 3) & ((s == 2) | (s == 3)) + ].any(|case| case == true) | !range_0; + + + + let substring_range_check = [case_0] + .all(|case| case == true); + + assert(substring_range_check, "substr array ranges wrong"); + + + s = s_next; + } + // check final state + + let matched: bool = (s == 3) | (s == 4); + + // constrain extracted substrings to be in match range + //let full_match = Sequence::new(start_range as u32, end_range as u32 - start_range as u32); + //let full_match_end = full_match.end(); + // for i in 0..1 { + // let substring = substrings.get_unchecked(i); + // let is_not_valid = i >= substrings.len(); + // let index_check = substring.index >= full_match.index; + // let length_check = substring.end() <= full_match_end; + // let check = (index_check) | is_not_valid; + // assert(check, f"Substring {i} range is out of bounds of the full match found"); + // } + (substrings, matched) +} + + +pub unconstrained fn __regex_match(input: [u8; N]) -> BoundedVec { + // regex: [A-Za-z0-9!#$%&'*+=?\-\^_`{|}~./]+@[A-Za-z0-9.\-@]+ + let mut substrings: BoundedVec = BoundedVec::new(); + let mut current_substring = Sequence::default(); + let mut full_match = Sequence::default(); + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + + let mut consecutive_substr = 0; + let mut complete = false; + + for i in 0..input.len() { + let temp = input[i] as Field; + let mut reset = false; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + reset = true; + s = 0; + s_next = potential_s_next; + } + // If a substring was in the making, but the state was reset + // we disregard previous progress because apparently it is invalid + if (reset & (consecutive_substr == 1)) { + current_substring = Sequence::default(); + consecutive_substr = 0; + } + // Fill up substrings + + + if ((s == 2) & (s_next == 3) | (s == 3) & (s_next == 3)) { + + if (consecutive_substr == 0) { + current_substring.index = i; + }; + current_substring.length += 1; + consecutive_substr = 1; + } else if ((consecutive_substr == 1) & (s_next == 0)) { + current_substring = Sequence::default(); + full_match = Sequence::default(); + substrings = BoundedVec::new(); + consecutive_substr = 0; + } else if (s == 3) & (s_next == 4) { + full_match.length = i - full_match.index + 1; + complete = true; + } else if (consecutive_substr == 1) { + // The substring is done so "save" it + substrings.push(current_substring); + // reset the substring holder for next use + current_substring = Sequence::default(); + consecutive_substr = 0; + } + s = s_next; + if complete == true { + break; + } + } + assert((s == 3) | (s == 4), f"no match: {s}"); + // Add pending substring that hasn't been added + if consecutive_substr == 1 { + substrings.push(current_substring); + full_match.length = input.len() - full_match.index; + } + + + + substrings +} + + + + \ No newline at end of file diff --git a/packages/noir/src/capture/raw/from_all.nr b/packages/noir/src/capture/raw/from_all.nr new file mode 100644 index 00000000..7032e647 --- /dev/null +++ b/packages/noir/src/capture/raw/from_all.nr @@ -0,0 +1,1353 @@ + +use crate::common::Sequence; + + +global table: [Field; 4864] = comptime { make_lookup_table() }; + +comptime fn make_lookup_table() -> [Field; 4864] { + let mut table = [0; 4864]; + table[17 * 256 + 0] = 18; + table[18 * 256 + 0] = 18; + table[17 * 256 + 1] = 18; + table[18 * 256 + 1] = 18; + table[17 * 256 + 2] = 18; + table[18 * 256 + 2] = 18; + table[17 * 256 + 3] = 18; + table[18 * 256 + 3] = 18; + table[17 * 256 + 4] = 18; + table[18 * 256 + 4] = 18; + table[17 * 256 + 5] = 18; + table[18 * 256 + 5] = 18; + table[17 * 256 + 6] = 18; + table[18 * 256 + 6] = 18; + table[17 * 256 + 7] = 18; + table[18 * 256 + 7] = 18; + table[17 * 256 + 8] = 18; + table[18 * 256 + 8] = 18; + table[17 * 256 + 9] = 18; + table[18 * 256 + 9] = 18; + table[17 * 256 + 10] = 18; + table[18 * 256 + 10] = 18; + table[17 * 256 + 11] = 18; + table[18 * 256 + 11] = 18; + table[17 * 256 + 12] = 18; + table[18 * 256 + 12] = 18; + table[17 * 256 + 13] = 18; + table[18 * 256 + 13] = 18; + table[17 * 256 + 14] = 18; + table[18 * 256 + 14] = 18; + table[17 * 256 + 15] = 18; + table[18 * 256 + 15] = 18; + table[17 * 256 + 16] = 18; + table[18 * 256 + 16] = 18; + table[17 * 256 + 17] = 18; + table[18 * 256 + 17] = 18; + table[17 * 256 + 18] = 18; + table[18 * 256 + 18] = 18; + table[17 * 256 + 19] = 18; + table[18 * 256 + 19] = 18; + table[17 * 256 + 20] = 18; + table[18 * 256 + 20] = 18; + table[17 * 256 + 21] = 18; + table[18 * 256 + 21] = 18; + table[17 * 256 + 22] = 18; + table[18 * 256 + 22] = 18; + table[17 * 256 + 23] = 18; + table[18 * 256 + 23] = 18; + table[17 * 256 + 24] = 18; + table[18 * 256 + 24] = 18; + table[17 * 256 + 25] = 18; + table[18 * 256 + 25] = 18; + table[17 * 256 + 26] = 18; + table[18 * 256 + 26] = 18; + table[17 * 256 + 27] = 18; + table[18 * 256 + 27] = 18; + table[17 * 256 + 28] = 18; + table[18 * 256 + 28] = 18; + table[17 * 256 + 29] = 18; + table[18 * 256 + 29] = 18; + table[17 * 256 + 30] = 18; + table[18 * 256 + 30] = 18; + table[17 * 256 + 31] = 18; + table[18 * 256 + 31] = 18; + table[17 * 256 + 32] = 18; + table[18 * 256 + 32] = 18; + table[17 * 256 + 33] = 18; + table[18 * 256 + 33] = 18; + table[17 * 256 + 34] = 18; + table[18 * 256 + 34] = 18; + table[17 * 256 + 35] = 18; + table[18 * 256 + 35] = 18; + table[17 * 256 + 36] = 18; + table[18 * 256 + 36] = 18; + table[17 * 256 + 37] = 18; + table[18 * 256 + 37] = 18; + table[17 * 256 + 38] = 18; + table[18 * 256 + 38] = 18; + table[17 * 256 + 39] = 18; + table[18 * 256 + 39] = 18; + table[17 * 256 + 40] = 18; + table[18 * 256 + 40] = 18; + table[17 * 256 + 41] = 18; + table[18 * 256 + 41] = 18; + table[17 * 256 + 42] = 18; + table[18 * 256 + 42] = 18; + table[17 * 256 + 43] = 18; + table[18 * 256 + 43] = 18; + table[17 * 256 + 44] = 18; + table[18 * 256 + 44] = 18; + table[17 * 256 + 45] = 18; + table[18 * 256 + 45] = 18; + table[17 * 256 + 46] = 18; + table[18 * 256 + 46] = 18; + table[17 * 256 + 47] = 18; + table[18 * 256 + 47] = 18; + table[17 * 256 + 48] = 18; + table[18 * 256 + 48] = 18; + table[17 * 256 + 49] = 18; + table[18 * 256 + 49] = 18; + table[17 * 256 + 50] = 18; + table[18 * 256 + 50] = 18; + table[17 * 256 + 51] = 18; + table[18 * 256 + 51] = 18; + table[17 * 256 + 52] = 18; + table[18 * 256 + 52] = 18; + table[17 * 256 + 53] = 18; + table[18 * 256 + 53] = 18; + table[17 * 256 + 54] = 18; + table[18 * 256 + 54] = 18; + table[17 * 256 + 55] = 18; + table[18 * 256 + 55] = 18; + table[17 * 256 + 56] = 18; + table[18 * 256 + 56] = 18; + table[17 * 256 + 57] = 18; + table[18 * 256 + 57] = 18; + table[17 * 256 + 58] = 18; + table[18 * 256 + 58] = 18; + table[17 * 256 + 59] = 18; + table[18 * 256 + 59] = 18; + table[17 * 256 + 60] = 18; + table[18 * 256 + 60] = 18; + table[17 * 256 + 61] = 18; + table[18 * 256 + 61] = 18; + table[17 * 256 + 62] = 18; + table[18 * 256 + 62] = 18; + table[17 * 256 + 63] = 18; + table[18 * 256 + 63] = 18; + table[17 * 256 + 64] = 18; + table[18 * 256 + 64] = 18; + table[17 * 256 + 65] = 18; + table[18 * 256 + 65] = 18; + table[17 * 256 + 66] = 18; + table[18 * 256 + 66] = 18; + table[17 * 256 + 67] = 18; + table[18 * 256 + 67] = 18; + table[17 * 256 + 68] = 18; + table[18 * 256 + 68] = 18; + table[17 * 256 + 69] = 18; + table[18 * 256 + 69] = 18; + table[17 * 256 + 70] = 18; + table[18 * 256 + 70] = 18; + table[17 * 256 + 71] = 18; + table[18 * 256 + 71] = 18; + table[17 * 256 + 72] = 18; + table[18 * 256 + 72] = 18; + table[17 * 256 + 73] = 18; + table[18 * 256 + 73] = 18; + table[17 * 256 + 74] = 18; + table[18 * 256 + 74] = 18; + table[17 * 256 + 75] = 18; + table[18 * 256 + 75] = 18; + table[17 * 256 + 76] = 18; + table[18 * 256 + 76] = 18; + table[17 * 256 + 77] = 18; + table[18 * 256 + 77] = 18; + table[17 * 256 + 78] = 18; + table[18 * 256 + 78] = 18; + table[17 * 256 + 79] = 18; + table[18 * 256 + 79] = 18; + table[17 * 256 + 80] = 18; + table[18 * 256 + 80] = 18; + table[17 * 256 + 81] = 18; + table[18 * 256 + 81] = 18; + table[17 * 256 + 82] = 18; + table[18 * 256 + 82] = 18; + table[17 * 256 + 83] = 18; + table[18 * 256 + 83] = 18; + table[17 * 256 + 84] = 18; + table[18 * 256 + 84] = 18; + table[17 * 256 + 85] = 18; + table[18 * 256 + 85] = 18; + table[17 * 256 + 86] = 18; + table[18 * 256 + 86] = 18; + table[17 * 256 + 87] = 18; + table[18 * 256 + 87] = 18; + table[17 * 256 + 88] = 18; + table[18 * 256 + 88] = 18; + table[17 * 256 + 89] = 18; + table[18 * 256 + 89] = 18; + table[17 * 256 + 90] = 18; + table[18 * 256 + 90] = 18; + table[17 * 256 + 91] = 18; + table[18 * 256 + 91] = 18; + table[17 * 256 + 92] = 18; + table[18 * 256 + 92] = 18; + table[17 * 256 + 93] = 18; + table[18 * 256 + 93] = 18; + table[17 * 256 + 94] = 18; + table[18 * 256 + 94] = 18; + table[17 * 256 + 95] = 18; + table[18 * 256 + 95] = 18; + table[17 * 256 + 96] = 18; + table[18 * 256 + 96] = 18; + table[17 * 256 + 97] = 18; + table[18 * 256 + 97] = 18; + table[17 * 256 + 98] = 18; + table[18 * 256 + 98] = 18; + table[17 * 256 + 99] = 18; + table[18 * 256 + 99] = 18; + table[17 * 256 + 100] = 18; + table[18 * 256 + 100] = 18; + table[17 * 256 + 101] = 18; + table[18 * 256 + 101] = 18; + table[17 * 256 + 102] = 18; + table[18 * 256 + 102] = 18; + table[17 * 256 + 103] = 18; + table[18 * 256 + 103] = 18; + table[17 * 256 + 104] = 18; + table[18 * 256 + 104] = 18; + table[17 * 256 + 105] = 18; + table[18 * 256 + 105] = 18; + table[17 * 256 + 106] = 18; + table[18 * 256 + 106] = 18; + table[17 * 256 + 107] = 18; + table[18 * 256 + 107] = 18; + table[17 * 256 + 108] = 18; + table[18 * 256 + 108] = 18; + table[17 * 256 + 109] = 18; + table[18 * 256 + 109] = 18; + table[17 * 256 + 110] = 18; + table[18 * 256 + 110] = 18; + table[17 * 256 + 111] = 18; + table[18 * 256 + 111] = 18; + table[17 * 256 + 112] = 18; + table[18 * 256 + 112] = 18; + table[17 * 256 + 113] = 18; + table[18 * 256 + 113] = 18; + table[17 * 256 + 114] = 18; + table[18 * 256 + 114] = 18; + table[17 * 256 + 115] = 18; + table[18 * 256 + 115] = 18; + table[17 * 256 + 116] = 18; + table[18 * 256 + 116] = 18; + table[17 * 256 + 117] = 18; + table[18 * 256 + 117] = 18; + table[17 * 256 + 118] = 18; + table[18 * 256 + 118] = 18; + table[17 * 256 + 119] = 18; + table[18 * 256 + 119] = 18; + table[17 * 256 + 120] = 18; + table[18 * 256 + 120] = 18; + table[17 * 256 + 121] = 18; + table[18 * 256 + 121] = 18; + table[17 * 256 + 122] = 18; + table[18 * 256 + 122] = 18; + table[17 * 256 + 123] = 18; + table[18 * 256 + 123] = 18; + table[17 * 256 + 124] = 18; + table[18 * 256 + 124] = 18; + table[17 * 256 + 125] = 18; + table[18 * 256 + 125] = 18; + table[17 * 256 + 126] = 18; + table[18 * 256 + 126] = 18; + table[17 * 256 + 127] = 18; + table[18 * 256 + 127] = 18; + table[17 * 256 + 128] = 18; + table[18 * 256 + 128] = 18; + table[17 * 256 + 129] = 18; + table[18 * 256 + 129] = 18; + table[17 * 256 + 130] = 18; + table[18 * 256 + 130] = 18; + table[17 * 256 + 131] = 18; + table[18 * 256 + 131] = 18; + table[17 * 256 + 132] = 18; + table[18 * 256 + 132] = 18; + table[17 * 256 + 133] = 18; + table[18 * 256 + 133] = 18; + table[17 * 256 + 134] = 18; + table[18 * 256 + 134] = 18; + table[17 * 256 + 135] = 18; + table[18 * 256 + 135] = 18; + table[17 * 256 + 136] = 18; + table[18 * 256 + 136] = 18; + table[17 * 256 + 137] = 18; + table[18 * 256 + 137] = 18; + table[17 * 256 + 138] = 18; + table[18 * 256 + 138] = 18; + table[17 * 256 + 139] = 18; + table[18 * 256 + 139] = 18; + table[17 * 256 + 140] = 18; + table[18 * 256 + 140] = 18; + table[17 * 256 + 141] = 18; + table[18 * 256 + 141] = 18; + table[17 * 256 + 142] = 18; + table[18 * 256 + 142] = 18; + table[17 * 256 + 143] = 18; + table[18 * 256 + 143] = 18; + table[17 * 256 + 144] = 18; + table[18 * 256 + 144] = 18; + table[17 * 256 + 145] = 18; + table[18 * 256 + 145] = 18; + table[17 * 256 + 146] = 18; + table[18 * 256 + 146] = 18; + table[17 * 256 + 147] = 18; + table[18 * 256 + 147] = 18; + table[17 * 256 + 148] = 18; + table[18 * 256 + 148] = 18; + table[17 * 256 + 149] = 18; + table[18 * 256 + 149] = 18; + table[17 * 256 + 150] = 18; + table[18 * 256 + 150] = 18; + table[17 * 256 + 151] = 18; + table[18 * 256 + 151] = 18; + table[17 * 256 + 152] = 18; + table[18 * 256 + 152] = 18; + table[17 * 256 + 153] = 18; + table[18 * 256 + 153] = 18; + table[17 * 256 + 154] = 18; + table[18 * 256 + 154] = 18; + table[17 * 256 + 155] = 18; + table[18 * 256 + 155] = 18; + table[17 * 256 + 156] = 18; + table[18 * 256 + 156] = 18; + table[17 * 256 + 157] = 18; + table[18 * 256 + 157] = 18; + table[17 * 256 + 158] = 18; + table[18 * 256 + 158] = 18; + table[17 * 256 + 159] = 18; + table[18 * 256 + 159] = 18; + table[17 * 256 + 160] = 18; + table[18 * 256 + 160] = 18; + table[17 * 256 + 161] = 18; + table[18 * 256 + 161] = 18; + table[17 * 256 + 162] = 18; + table[18 * 256 + 162] = 18; + table[17 * 256 + 163] = 18; + table[18 * 256 + 163] = 18; + table[17 * 256 + 164] = 18; + table[18 * 256 + 164] = 18; + table[17 * 256 + 165] = 18; + table[18 * 256 + 165] = 18; + table[17 * 256 + 166] = 18; + table[18 * 256 + 166] = 18; + table[17 * 256 + 167] = 18; + table[18 * 256 + 167] = 18; + table[17 * 256 + 168] = 18; + table[18 * 256 + 168] = 18; + table[17 * 256 + 169] = 18; + table[18 * 256 + 169] = 18; + table[17 * 256 + 170] = 18; + table[18 * 256 + 170] = 18; + table[17 * 256 + 171] = 18; + table[18 * 256 + 171] = 18; + table[17 * 256 + 172] = 18; + table[18 * 256 + 172] = 18; + table[17 * 256 + 173] = 18; + table[18 * 256 + 173] = 18; + table[17 * 256 + 174] = 18; + table[18 * 256 + 174] = 18; + table[17 * 256 + 175] = 18; + table[18 * 256 + 175] = 18; + table[17 * 256 + 176] = 18; + table[18 * 256 + 176] = 18; + table[17 * 256 + 177] = 18; + table[18 * 256 + 177] = 18; + table[17 * 256 + 178] = 18; + table[18 * 256 + 178] = 18; + table[17 * 256 + 179] = 18; + table[18 * 256 + 179] = 18; + table[17 * 256 + 180] = 18; + table[18 * 256 + 180] = 18; + table[17 * 256 + 181] = 18; + table[18 * 256 + 181] = 18; + table[17 * 256 + 182] = 18; + table[18 * 256 + 182] = 18; + table[17 * 256 + 183] = 18; + table[18 * 256 + 183] = 18; + table[17 * 256 + 184] = 18; + table[18 * 256 + 184] = 18; + table[17 * 256 + 185] = 18; + table[18 * 256 + 185] = 18; + table[17 * 256 + 186] = 18; + table[18 * 256 + 186] = 18; + table[17 * 256 + 187] = 18; + table[18 * 256 + 187] = 18; + table[17 * 256 + 188] = 18; + table[18 * 256 + 188] = 18; + table[17 * 256 + 189] = 18; + table[18 * 256 + 189] = 18; + table[17 * 256 + 190] = 18; + table[18 * 256 + 190] = 18; + table[17 * 256 + 191] = 18; + table[18 * 256 + 191] = 18; + table[17 * 256 + 192] = 18; + table[18 * 256 + 192] = 18; + table[17 * 256 + 193] = 18; + table[18 * 256 + 193] = 18; + table[17 * 256 + 194] = 18; + table[18 * 256 + 194] = 18; + table[17 * 256 + 195] = 18; + table[18 * 256 + 195] = 18; + table[17 * 256 + 196] = 18; + table[18 * 256 + 196] = 18; + table[17 * 256 + 197] = 18; + table[18 * 256 + 197] = 18; + table[17 * 256 + 198] = 18; + table[18 * 256 + 198] = 18; + table[17 * 256 + 199] = 18; + table[18 * 256 + 199] = 18; + table[17 * 256 + 200] = 18; + table[18 * 256 + 200] = 18; + table[17 * 256 + 201] = 18; + table[18 * 256 + 201] = 18; + table[17 * 256 + 202] = 18; + table[18 * 256 + 202] = 18; + table[17 * 256 + 203] = 18; + table[18 * 256 + 203] = 18; + table[17 * 256 + 204] = 18; + table[18 * 256 + 204] = 18; + table[17 * 256 + 205] = 18; + table[18 * 256 + 205] = 18; + table[17 * 256 + 206] = 18; + table[18 * 256 + 206] = 18; + table[17 * 256 + 207] = 18; + table[18 * 256 + 207] = 18; + table[17 * 256 + 208] = 18; + table[18 * 256 + 208] = 18; + table[17 * 256 + 209] = 18; + table[18 * 256 + 209] = 18; + table[17 * 256 + 210] = 18; + table[18 * 256 + 210] = 18; + table[17 * 256 + 211] = 18; + table[18 * 256 + 211] = 18; + table[17 * 256 + 212] = 18; + table[18 * 256 + 212] = 18; + table[17 * 256 + 213] = 18; + table[18 * 256 + 213] = 18; + table[17 * 256 + 214] = 18; + table[18 * 256 + 214] = 18; + table[17 * 256 + 215] = 18; + table[18 * 256 + 215] = 18; + table[17 * 256 + 216] = 18; + table[18 * 256 + 216] = 18; + table[17 * 256 + 217] = 18; + table[18 * 256 + 217] = 18; + table[17 * 256 + 218] = 18; + table[18 * 256 + 218] = 18; + table[17 * 256 + 219] = 18; + table[18 * 256 + 219] = 18; + table[17 * 256 + 220] = 18; + table[18 * 256 + 220] = 18; + table[17 * 256 + 221] = 18; + table[18 * 256 + 221] = 18; + table[17 * 256 + 222] = 18; + table[18 * 256 + 222] = 18; + table[17 * 256 + 223] = 18; + table[18 * 256 + 223] = 18; + table[17 * 256 + 224] = 18; + table[18 * 256 + 224] = 18; + table[17 * 256 + 225] = 18; + table[18 * 256 + 225] = 18; + table[17 * 256 + 226] = 18; + table[18 * 256 + 226] = 18; + table[17 * 256 + 227] = 18; + table[18 * 256 + 227] = 18; + table[17 * 256 + 228] = 18; + table[18 * 256 + 228] = 18; + table[17 * 256 + 229] = 18; + table[18 * 256 + 229] = 18; + table[17 * 256 + 230] = 18; + table[18 * 256 + 230] = 18; + table[17 * 256 + 231] = 18; + table[18 * 256 + 231] = 18; + table[17 * 256 + 232] = 18; + table[18 * 256 + 232] = 18; + table[17 * 256 + 233] = 18; + table[18 * 256 + 233] = 18; + table[17 * 256 + 234] = 18; + table[18 * 256 + 234] = 18; + table[17 * 256 + 235] = 18; + table[18 * 256 + 235] = 18; + table[17 * 256 + 236] = 18; + table[18 * 256 + 236] = 18; + table[17 * 256 + 237] = 18; + table[18 * 256 + 237] = 18; + table[17 * 256 + 238] = 18; + table[18 * 256 + 238] = 18; + table[17 * 256 + 239] = 18; + table[18 * 256 + 239] = 18; + table[17 * 256 + 240] = 18; + table[18 * 256 + 240] = 18; + table[17 * 256 + 241] = 18; + table[18 * 256 + 241] = 18; + table[17 * 256 + 242] = 18; + table[18 * 256 + 242] = 18; + table[17 * 256 + 243] = 18; + table[18 * 256 + 243] = 18; + table[17 * 256 + 244] = 18; + table[18 * 256 + 244] = 18; + table[17 * 256 + 245] = 18; + table[18 * 256 + 245] = 18; + table[17 * 256 + 246] = 18; + table[18 * 256 + 246] = 18; + table[17 * 256 + 247] = 18; + table[18 * 256 + 247] = 18; + table[17 * 256 + 248] = 18; + table[18 * 256 + 248] = 18; + table[17 * 256 + 249] = 18; + table[18 * 256 + 249] = 18; + table[17 * 256 + 250] = 18; + table[18 * 256 + 250] = 18; + table[17 * 256 + 251] = 18; + table[18 * 256 + 251] = 18; + table[17 * 256 + 252] = 18; + table[18 * 256 + 252] = 18; + table[17 * 256 + 253] = 18; + table[18 * 256 + 253] = 18; + table[17 * 256 + 254] = 18; + table[18 * 256 + 254] = 18; + table[0 * 256 + 13] = 1; + table[0 * 256 + 255] = 2; + table[1 * 256 + 10] = 2; + table[2 * 256 + 102] = 3; + table[3 * 256 + 114] = 4; + table[4 * 256 + 111] = 5; + table[5 * 256 + 109] = 6; + table[6 * 256 + 58] = 7; + table[7 * 256 + 0] = 8; + table[7 * 256 + 1] = 8; + table[7 * 256 + 2] = 8; + table[7 * 256 + 3] = 8; + table[7 * 256 + 4] = 8; + table[7 * 256 + 5] = 8; + table[7 * 256 + 6] = 8; + table[7 * 256 + 7] = 8; + table[7 * 256 + 8] = 8; + table[7 * 256 + 9] = 8; + table[7 * 256 + 11] = 8; + table[7 * 256 + 12] = 8; + table[7 * 256 + 14] = 8; + table[7 * 256 + 15] = 8; + table[7 * 256 + 16] = 8; + table[7 * 256 + 17] = 8; + table[7 * 256 + 18] = 8; + table[7 * 256 + 19] = 8; + table[7 * 256 + 20] = 8; + table[7 * 256 + 21] = 8; + table[7 * 256 + 22] = 8; + table[7 * 256 + 23] = 8; + table[7 * 256 + 24] = 8; + table[7 * 256 + 25] = 8; + table[7 * 256 + 26] = 8; + table[7 * 256 + 27] = 8; + table[7 * 256 + 28] = 8; + table[7 * 256 + 29] = 8; + table[7 * 256 + 30] = 8; + table[7 * 256 + 31] = 8; + table[7 * 256 + 32] = 8; + table[7 * 256 + 33] = 8; + table[7 * 256 + 34] = 8; + table[7 * 256 + 35] = 8; + table[7 * 256 + 36] = 8; + table[7 * 256 + 37] = 8; + table[7 * 256 + 38] = 8; + table[7 * 256 + 39] = 8; + table[7 * 256 + 40] = 8; + table[7 * 256 + 41] = 8; + table[7 * 256 + 42] = 8; + table[7 * 256 + 43] = 8; + table[7 * 256 + 44] = 8; + table[7 * 256 + 45] = 8; + table[7 * 256 + 46] = 8; + table[7 * 256 + 47] = 8; + table[7 * 256 + 48] = 8; + table[7 * 256 + 49] = 8; + table[7 * 256 + 50] = 8; + table[7 * 256 + 51] = 8; + table[7 * 256 + 52] = 8; + table[7 * 256 + 53] = 8; + table[7 * 256 + 54] = 8; + table[7 * 256 + 55] = 8; + table[7 * 256 + 56] = 8; + table[7 * 256 + 57] = 8; + table[7 * 256 + 58] = 8; + table[7 * 256 + 59] = 8; + table[7 * 256 + 60] = 8; + table[7 * 256 + 61] = 8; + table[7 * 256 + 62] = 8; + table[7 * 256 + 63] = 8; + table[7 * 256 + 64] = 8; + table[7 * 256 + 65] = 8; + table[7 * 256 + 66] = 8; + table[7 * 256 + 67] = 8; + table[7 * 256 + 68] = 8; + table[7 * 256 + 69] = 8; + table[7 * 256 + 70] = 8; + table[7 * 256 + 71] = 8; + table[7 * 256 + 72] = 8; + table[7 * 256 + 73] = 8; + table[7 * 256 + 74] = 8; + table[7 * 256 + 75] = 8; + table[7 * 256 + 76] = 8; + table[7 * 256 + 77] = 8; + table[7 * 256 + 78] = 8; + table[7 * 256 + 79] = 8; + table[7 * 256 + 80] = 8; + table[7 * 256 + 81] = 8; + table[7 * 256 + 82] = 8; + table[7 * 256 + 83] = 8; + table[7 * 256 + 84] = 8; + table[7 * 256 + 85] = 8; + table[7 * 256 + 86] = 8; + table[7 * 256 + 87] = 8; + table[7 * 256 + 88] = 8; + table[7 * 256 + 89] = 8; + table[7 * 256 + 90] = 8; + table[7 * 256 + 91] = 8; + table[7 * 256 + 92] = 8; + table[7 * 256 + 93] = 8; + table[7 * 256 + 94] = 8; + table[7 * 256 + 95] = 8; + table[7 * 256 + 96] = 8; + table[7 * 256 + 97] = 8; + table[7 * 256 + 98] = 8; + table[7 * 256 + 99] = 8; + table[7 * 256 + 100] = 8; + table[7 * 256 + 101] = 8; + table[7 * 256 + 102] = 8; + table[7 * 256 + 103] = 8; + table[7 * 256 + 104] = 8; + table[7 * 256 + 105] = 8; + table[7 * 256 + 106] = 8; + table[7 * 256 + 107] = 8; + table[7 * 256 + 108] = 8; + table[7 * 256 + 109] = 8; + table[7 * 256 + 110] = 8; + table[7 * 256 + 111] = 8; + table[7 * 256 + 112] = 8; + table[7 * 256 + 113] = 8; + table[7 * 256 + 114] = 8; + table[7 * 256 + 115] = 8; + table[7 * 256 + 116] = 8; + table[7 * 256 + 117] = 8; + table[7 * 256 + 118] = 8; + table[7 * 256 + 119] = 8; + table[7 * 256 + 120] = 8; + table[7 * 256 + 121] = 8; + table[7 * 256 + 122] = 8; + table[7 * 256 + 123] = 8; + table[7 * 256 + 124] = 8; + table[7 * 256 + 125] = 8; + table[7 * 256 + 126] = 8; + table[7 * 256 + 127] = 8; + table[7 * 256 + 194] = 9; + table[7 * 256 + 195] = 9; + table[7 * 256 + 196] = 9; + table[7 * 256 + 197] = 9; + table[7 * 256 + 198] = 9; + table[7 * 256 + 199] = 9; + table[7 * 256 + 200] = 9; + table[7 * 256 + 201] = 9; + table[7 * 256 + 202] = 9; + table[7 * 256 + 203] = 9; + table[7 * 256 + 204] = 9; + table[7 * 256 + 205] = 9; + table[7 * 256 + 206] = 9; + table[7 * 256 + 207] = 9; + table[7 * 256 + 208] = 9; + table[7 * 256 + 209] = 9; + table[7 * 256 + 210] = 9; + table[7 * 256 + 211] = 9; + table[7 * 256 + 212] = 9; + table[7 * 256 + 213] = 9; + table[7 * 256 + 214] = 9; + table[7 * 256 + 215] = 9; + table[7 * 256 + 216] = 9; + table[7 * 256 + 217] = 9; + table[7 * 256 + 218] = 9; + table[7 * 256 + 219] = 9; + table[7 * 256 + 220] = 9; + table[7 * 256 + 221] = 9; + table[7 * 256 + 222] = 9; + table[7 * 256 + 223] = 9; + table[7 * 256 + 224] = 10; + table[7 * 256 + 225] = 11; + table[7 * 256 + 226] = 11; + table[7 * 256 + 227] = 11; + table[7 * 256 + 228] = 11; + table[7 * 256 + 229] = 11; + table[7 * 256 + 230] = 11; + table[7 * 256 + 231] = 11; + table[7 * 256 + 232] = 11; + table[7 * 256 + 233] = 11; + table[7 * 256 + 234] = 11; + table[7 * 256 + 235] = 11; + table[7 * 256 + 236] = 11; + table[7 * 256 + 238] = 11; + table[7 * 256 + 239] = 11; + table[7 * 256 + 237] = 12; + table[7 * 256 + 240] = 13; + table[7 * 256 + 241] = 14; + table[7 * 256 + 242] = 14; + table[7 * 256 + 243] = 14; + table[7 * 256 + 244] = 15; + table[8 * 256 + 0] = 8; + table[8 * 256 + 1] = 8; + table[8 * 256 + 2] = 8; + table[8 * 256 + 3] = 8; + table[8 * 256 + 4] = 8; + table[8 * 256 + 5] = 8; + table[8 * 256 + 6] = 8; + table[8 * 256 + 7] = 8; + table[8 * 256 + 8] = 8; + table[8 * 256 + 9] = 8; + table[8 * 256 + 11] = 8; + table[8 * 256 + 12] = 8; + table[8 * 256 + 14] = 8; + table[8 * 256 + 15] = 8; + table[8 * 256 + 16] = 8; + table[8 * 256 + 17] = 8; + table[8 * 256 + 18] = 8; + table[8 * 256 + 19] = 8; + table[8 * 256 + 20] = 8; + table[8 * 256 + 21] = 8; + table[8 * 256 + 22] = 8; + table[8 * 256 + 23] = 8; + table[8 * 256 + 24] = 8; + table[8 * 256 + 25] = 8; + table[8 * 256 + 26] = 8; + table[8 * 256 + 27] = 8; + table[8 * 256 + 28] = 8; + table[8 * 256 + 29] = 8; + table[8 * 256 + 30] = 8; + table[8 * 256 + 31] = 8; + table[8 * 256 + 32] = 8; + table[8 * 256 + 33] = 8; + table[8 * 256 + 34] = 8; + table[8 * 256 + 35] = 8; + table[8 * 256 + 36] = 8; + table[8 * 256 + 37] = 8; + table[8 * 256 + 38] = 8; + table[8 * 256 + 39] = 8; + table[8 * 256 + 40] = 8; + table[8 * 256 + 41] = 8; + table[8 * 256 + 42] = 8; + table[8 * 256 + 43] = 8; + table[8 * 256 + 44] = 8; + table[8 * 256 + 45] = 8; + table[8 * 256 + 46] = 8; + table[8 * 256 + 47] = 8; + table[8 * 256 + 48] = 8; + table[8 * 256 + 49] = 8; + table[8 * 256 + 50] = 8; + table[8 * 256 + 51] = 8; + table[8 * 256 + 52] = 8; + table[8 * 256 + 53] = 8; + table[8 * 256 + 54] = 8; + table[8 * 256 + 55] = 8; + table[8 * 256 + 56] = 8; + table[8 * 256 + 57] = 8; + table[8 * 256 + 58] = 8; + table[8 * 256 + 59] = 8; + table[8 * 256 + 60] = 8; + table[8 * 256 + 61] = 8; + table[8 * 256 + 62] = 8; + table[8 * 256 + 63] = 8; + table[8 * 256 + 64] = 8; + table[8 * 256 + 65] = 8; + table[8 * 256 + 66] = 8; + table[8 * 256 + 67] = 8; + table[8 * 256 + 68] = 8; + table[8 * 256 + 69] = 8; + table[8 * 256 + 70] = 8; + table[8 * 256 + 71] = 8; + table[8 * 256 + 72] = 8; + table[8 * 256 + 73] = 8; + table[8 * 256 + 74] = 8; + table[8 * 256 + 75] = 8; + table[8 * 256 + 76] = 8; + table[8 * 256 + 77] = 8; + table[8 * 256 + 78] = 8; + table[8 * 256 + 79] = 8; + table[8 * 256 + 80] = 8; + table[8 * 256 + 81] = 8; + table[8 * 256 + 82] = 8; + table[8 * 256 + 83] = 8; + table[8 * 256 + 84] = 8; + table[8 * 256 + 85] = 8; + table[8 * 256 + 86] = 8; + table[8 * 256 + 87] = 8; + table[8 * 256 + 88] = 8; + table[8 * 256 + 89] = 8; + table[8 * 256 + 90] = 8; + table[8 * 256 + 91] = 8; + table[8 * 256 + 92] = 8; + table[8 * 256 + 93] = 8; + table[8 * 256 + 94] = 8; + table[8 * 256 + 95] = 8; + table[8 * 256 + 96] = 8; + table[8 * 256 + 97] = 8; + table[8 * 256 + 98] = 8; + table[8 * 256 + 99] = 8; + table[8 * 256 + 100] = 8; + table[8 * 256 + 101] = 8; + table[8 * 256 + 102] = 8; + table[8 * 256 + 103] = 8; + table[8 * 256 + 104] = 8; + table[8 * 256 + 105] = 8; + table[8 * 256 + 106] = 8; + table[8 * 256 + 107] = 8; + table[8 * 256 + 108] = 8; + table[8 * 256 + 109] = 8; + table[8 * 256 + 110] = 8; + table[8 * 256 + 111] = 8; + table[8 * 256 + 112] = 8; + table[8 * 256 + 113] = 8; + table[8 * 256 + 114] = 8; + table[8 * 256 + 115] = 8; + table[8 * 256 + 116] = 8; + table[8 * 256 + 117] = 8; + table[8 * 256 + 118] = 8; + table[8 * 256 + 119] = 8; + table[8 * 256 + 120] = 8; + table[8 * 256 + 121] = 8; + table[8 * 256 + 122] = 8; + table[8 * 256 + 123] = 8; + table[8 * 256 + 124] = 8; + table[8 * 256 + 125] = 8; + table[8 * 256 + 126] = 8; + table[8 * 256 + 127] = 8; + table[8 * 256 + 194] = 9; + table[8 * 256 + 195] = 9; + table[8 * 256 + 196] = 9; + table[8 * 256 + 197] = 9; + table[8 * 256 + 198] = 9; + table[8 * 256 + 199] = 9; + table[8 * 256 + 200] = 9; + table[8 * 256 + 201] = 9; + table[8 * 256 + 202] = 9; + table[8 * 256 + 203] = 9; + table[8 * 256 + 204] = 9; + table[8 * 256 + 205] = 9; + table[8 * 256 + 206] = 9; + table[8 * 256 + 207] = 9; + table[8 * 256 + 208] = 9; + table[8 * 256 + 209] = 9; + table[8 * 256 + 210] = 9; + table[8 * 256 + 211] = 9; + table[8 * 256 + 212] = 9; + table[8 * 256 + 213] = 9; + table[8 * 256 + 214] = 9; + table[8 * 256 + 215] = 9; + table[8 * 256 + 216] = 9; + table[8 * 256 + 217] = 9; + table[8 * 256 + 218] = 9; + table[8 * 256 + 219] = 9; + table[8 * 256 + 220] = 9; + table[8 * 256 + 221] = 9; + table[8 * 256 + 222] = 9; + table[8 * 256 + 223] = 9; + table[8 * 256 + 224] = 10; + table[8 * 256 + 225] = 11; + table[8 * 256 + 226] = 11; + table[8 * 256 + 227] = 11; + table[8 * 256 + 228] = 11; + table[8 * 256 + 229] = 11; + table[8 * 256 + 230] = 11; + table[8 * 256 + 231] = 11; + table[8 * 256 + 232] = 11; + table[8 * 256 + 233] = 11; + table[8 * 256 + 234] = 11; + table[8 * 256 + 235] = 11; + table[8 * 256 + 236] = 11; + table[8 * 256 + 238] = 11; + table[8 * 256 + 239] = 11; + table[8 * 256 + 237] = 12; + table[8 * 256 + 240] = 13; + table[8 * 256 + 241] = 14; + table[8 * 256 + 242] = 14; + table[8 * 256 + 243] = 14; + table[8 * 256 + 244] = 15; + table[8 * 256 + 13] = 16; + table[9 * 256 + 128] = 8; + table[9 * 256 + 129] = 8; + table[9 * 256 + 130] = 8; + table[9 * 256 + 131] = 8; + table[9 * 256 + 132] = 8; + table[9 * 256 + 133] = 8; + table[9 * 256 + 134] = 8; + table[9 * 256 + 135] = 8; + table[9 * 256 + 136] = 8; + table[9 * 256 + 137] = 8; + table[9 * 256 + 138] = 8; + table[9 * 256 + 139] = 8; + table[9 * 256 + 140] = 8; + table[9 * 256 + 141] = 8; + table[9 * 256 + 142] = 8; + table[9 * 256 + 143] = 8; + table[9 * 256 + 144] = 8; + table[9 * 256 + 145] = 8; + table[9 * 256 + 146] = 8; + table[9 * 256 + 147] = 8; + table[9 * 256 + 148] = 8; + table[9 * 256 + 149] = 8; + table[9 * 256 + 150] = 8; + table[9 * 256 + 151] = 8; + table[9 * 256 + 152] = 8; + table[9 * 256 + 153] = 8; + table[9 * 256 + 154] = 8; + table[9 * 256 + 155] = 8; + table[9 * 256 + 156] = 8; + table[9 * 256 + 157] = 8; + table[9 * 256 + 158] = 8; + table[9 * 256 + 159] = 8; + table[9 * 256 + 160] = 8; + table[9 * 256 + 161] = 8; + table[9 * 256 + 162] = 8; + table[9 * 256 + 163] = 8; + table[9 * 256 + 164] = 8; + table[9 * 256 + 165] = 8; + table[9 * 256 + 166] = 8; + table[9 * 256 + 167] = 8; + table[9 * 256 + 168] = 8; + table[9 * 256 + 169] = 8; + table[9 * 256 + 170] = 8; + table[9 * 256 + 171] = 8; + table[9 * 256 + 172] = 8; + table[9 * 256 + 173] = 8; + table[9 * 256 + 174] = 8; + table[9 * 256 + 175] = 8; + table[9 * 256 + 176] = 8; + table[9 * 256 + 177] = 8; + table[9 * 256 + 178] = 8; + table[9 * 256 + 179] = 8; + table[9 * 256 + 180] = 8; + table[9 * 256 + 181] = 8; + table[9 * 256 + 182] = 8; + table[9 * 256 + 183] = 8; + table[9 * 256 + 184] = 8; + table[9 * 256 + 185] = 8; + table[9 * 256 + 186] = 8; + table[9 * 256 + 187] = 8; + table[9 * 256 + 188] = 8; + table[9 * 256 + 189] = 8; + table[9 * 256 + 190] = 8; + table[9 * 256 + 191] = 8; + table[10 * 256 + 160] = 9; + table[10 * 256 + 161] = 9; + table[10 * 256 + 162] = 9; + table[10 * 256 + 163] = 9; + table[10 * 256 + 164] = 9; + table[10 * 256 + 165] = 9; + table[10 * 256 + 166] = 9; + table[10 * 256 + 167] = 9; + table[10 * 256 + 168] = 9; + table[10 * 256 + 169] = 9; + table[10 * 256 + 170] = 9; + table[10 * 256 + 171] = 9; + table[10 * 256 + 172] = 9; + table[10 * 256 + 173] = 9; + table[10 * 256 + 174] = 9; + table[10 * 256 + 175] = 9; + table[10 * 256 + 176] = 9; + table[10 * 256 + 177] = 9; + table[10 * 256 + 178] = 9; + table[10 * 256 + 179] = 9; + table[10 * 256 + 180] = 9; + table[10 * 256 + 181] = 9; + table[10 * 256 + 182] = 9; + table[10 * 256 + 183] = 9; + table[10 * 256 + 184] = 9; + table[10 * 256 + 185] = 9; + table[10 * 256 + 186] = 9; + table[10 * 256 + 187] = 9; + table[10 * 256 + 188] = 9; + table[10 * 256 + 189] = 9; + table[10 * 256 + 190] = 9; + table[10 * 256 + 191] = 9; + table[11 * 256 + 128] = 9; + table[11 * 256 + 129] = 9; + table[11 * 256 + 130] = 9; + table[11 * 256 + 131] = 9; + table[11 * 256 + 132] = 9; + table[11 * 256 + 133] = 9; + table[11 * 256 + 134] = 9; + table[11 * 256 + 135] = 9; + table[11 * 256 + 136] = 9; + table[11 * 256 + 137] = 9; + table[11 * 256 + 138] = 9; + table[11 * 256 + 139] = 9; + table[11 * 256 + 140] = 9; + table[11 * 256 + 141] = 9; + table[11 * 256 + 142] = 9; + table[11 * 256 + 143] = 9; + table[11 * 256 + 144] = 9; + table[11 * 256 + 145] = 9; + table[11 * 256 + 146] = 9; + table[11 * 256 + 147] = 9; + table[11 * 256 + 148] = 9; + table[11 * 256 + 149] = 9; + table[11 * 256 + 150] = 9; + table[11 * 256 + 151] = 9; + table[11 * 256 + 152] = 9; + table[11 * 256 + 153] = 9; + table[11 * 256 + 154] = 9; + table[11 * 256 + 155] = 9; + table[11 * 256 + 156] = 9; + table[11 * 256 + 157] = 9; + table[11 * 256 + 158] = 9; + table[11 * 256 + 159] = 9; + table[11 * 256 + 160] = 9; + table[11 * 256 + 161] = 9; + table[11 * 256 + 162] = 9; + table[11 * 256 + 163] = 9; + table[11 * 256 + 164] = 9; + table[11 * 256 + 165] = 9; + table[11 * 256 + 166] = 9; + table[11 * 256 + 167] = 9; + table[11 * 256 + 168] = 9; + table[11 * 256 + 169] = 9; + table[11 * 256 + 170] = 9; + table[11 * 256 + 171] = 9; + table[11 * 256 + 172] = 9; + table[11 * 256 + 173] = 9; + table[11 * 256 + 174] = 9; + table[11 * 256 + 175] = 9; + table[11 * 256 + 176] = 9; + table[11 * 256 + 177] = 9; + table[11 * 256 + 178] = 9; + table[11 * 256 + 179] = 9; + table[11 * 256 + 180] = 9; + table[11 * 256 + 181] = 9; + table[11 * 256 + 182] = 9; + table[11 * 256 + 183] = 9; + table[11 * 256 + 184] = 9; + table[11 * 256 + 185] = 9; + table[11 * 256 + 186] = 9; + table[11 * 256 + 187] = 9; + table[11 * 256 + 188] = 9; + table[11 * 256 + 189] = 9; + table[11 * 256 + 190] = 9; + table[11 * 256 + 191] = 9; + table[12 * 256 + 128] = 9; + table[12 * 256 + 129] = 9; + table[12 * 256 + 130] = 9; + table[12 * 256 + 131] = 9; + table[12 * 256 + 132] = 9; + table[12 * 256 + 133] = 9; + table[12 * 256 + 134] = 9; + table[12 * 256 + 135] = 9; + table[12 * 256 + 136] = 9; + table[12 * 256 + 137] = 9; + table[12 * 256 + 138] = 9; + table[12 * 256 + 139] = 9; + table[12 * 256 + 140] = 9; + table[12 * 256 + 141] = 9; + table[12 * 256 + 142] = 9; + table[12 * 256 + 143] = 9; + table[12 * 256 + 144] = 9; + table[12 * 256 + 145] = 9; + table[12 * 256 + 146] = 9; + table[12 * 256 + 147] = 9; + table[12 * 256 + 148] = 9; + table[12 * 256 + 149] = 9; + table[12 * 256 + 150] = 9; + table[12 * 256 + 151] = 9; + table[12 * 256 + 152] = 9; + table[12 * 256 + 153] = 9; + table[12 * 256 + 154] = 9; + table[12 * 256 + 155] = 9; + table[12 * 256 + 156] = 9; + table[12 * 256 + 157] = 9; + table[12 * 256 + 158] = 9; + table[12 * 256 + 159] = 9; + table[13 * 256 + 144] = 11; + table[13 * 256 + 145] = 11; + table[13 * 256 + 146] = 11; + table[13 * 256 + 147] = 11; + table[13 * 256 + 148] = 11; + table[13 * 256 + 149] = 11; + table[13 * 256 + 150] = 11; + table[13 * 256 + 151] = 11; + table[13 * 256 + 152] = 11; + table[13 * 256 + 153] = 11; + table[13 * 256 + 154] = 11; + table[13 * 256 + 155] = 11; + table[13 * 256 + 156] = 11; + table[13 * 256 + 157] = 11; + table[13 * 256 + 158] = 11; + table[13 * 256 + 159] = 11; + table[13 * 256 + 160] = 11; + table[13 * 256 + 161] = 11; + table[13 * 256 + 162] = 11; + table[13 * 256 + 163] = 11; + table[13 * 256 + 164] = 11; + table[13 * 256 + 165] = 11; + table[13 * 256 + 166] = 11; + table[13 * 256 + 167] = 11; + table[13 * 256 + 168] = 11; + table[13 * 256 + 169] = 11; + table[13 * 256 + 170] = 11; + table[13 * 256 + 171] = 11; + table[13 * 256 + 172] = 11; + table[13 * 256 + 173] = 11; + table[13 * 256 + 174] = 11; + table[13 * 256 + 175] = 11; + table[13 * 256 + 176] = 11; + table[13 * 256 + 177] = 11; + table[13 * 256 + 178] = 11; + table[13 * 256 + 179] = 11; + table[13 * 256 + 180] = 11; + table[13 * 256 + 181] = 11; + table[13 * 256 + 182] = 11; + table[13 * 256 + 183] = 11; + table[13 * 256 + 184] = 11; + table[13 * 256 + 185] = 11; + table[13 * 256 + 186] = 11; + table[13 * 256 + 187] = 11; + table[13 * 256 + 188] = 11; + table[13 * 256 + 189] = 11; + table[13 * 256 + 190] = 11; + table[13 * 256 + 191] = 11; + table[14 * 256 + 128] = 11; + table[14 * 256 + 129] = 11; + table[14 * 256 + 130] = 11; + table[14 * 256 + 131] = 11; + table[14 * 256 + 132] = 11; + table[14 * 256 + 133] = 11; + table[14 * 256 + 134] = 11; + table[14 * 256 + 135] = 11; + table[14 * 256 + 136] = 11; + table[14 * 256 + 137] = 11; + table[14 * 256 + 138] = 11; + table[14 * 256 + 139] = 11; + table[14 * 256 + 140] = 11; + table[14 * 256 + 141] = 11; + table[14 * 256 + 142] = 11; + table[14 * 256 + 143] = 11; + table[14 * 256 + 144] = 11; + table[14 * 256 + 145] = 11; + table[14 * 256 + 146] = 11; + table[14 * 256 + 147] = 11; + table[14 * 256 + 148] = 11; + table[14 * 256 + 149] = 11; + table[14 * 256 + 150] = 11; + table[14 * 256 + 151] = 11; + table[14 * 256 + 152] = 11; + table[14 * 256 + 153] = 11; + table[14 * 256 + 154] = 11; + table[14 * 256 + 155] = 11; + table[14 * 256 + 156] = 11; + table[14 * 256 + 157] = 11; + table[14 * 256 + 158] = 11; + table[14 * 256 + 159] = 11; + table[14 * 256 + 160] = 11; + table[14 * 256 + 161] = 11; + table[14 * 256 + 162] = 11; + table[14 * 256 + 163] = 11; + table[14 * 256 + 164] = 11; + table[14 * 256 + 165] = 11; + table[14 * 256 + 166] = 11; + table[14 * 256 + 167] = 11; + table[14 * 256 + 168] = 11; + table[14 * 256 + 169] = 11; + table[14 * 256 + 170] = 11; + table[14 * 256 + 171] = 11; + table[14 * 256 + 172] = 11; + table[14 * 256 + 173] = 11; + table[14 * 256 + 174] = 11; + table[14 * 256 + 175] = 11; + table[14 * 256 + 176] = 11; + table[14 * 256 + 177] = 11; + table[14 * 256 + 178] = 11; + table[14 * 256 + 179] = 11; + table[14 * 256 + 180] = 11; + table[14 * 256 + 181] = 11; + table[14 * 256 + 182] = 11; + table[14 * 256 + 183] = 11; + table[14 * 256 + 184] = 11; + table[14 * 256 + 185] = 11; + table[14 * 256 + 186] = 11; + table[14 * 256 + 187] = 11; + table[14 * 256 + 188] = 11; + table[14 * 256 + 189] = 11; + table[14 * 256 + 190] = 11; + table[14 * 256 + 191] = 11; + table[15 * 256 + 128] = 11; + table[15 * 256 + 129] = 11; + table[15 * 256 + 130] = 11; + table[15 * 256 + 131] = 11; + table[15 * 256 + 132] = 11; + table[15 * 256 + 133] = 11; + table[15 * 256 + 134] = 11; + table[15 * 256 + 135] = 11; + table[15 * 256 + 136] = 11; + table[15 * 256 + 137] = 11; + table[15 * 256 + 138] = 11; + table[15 * 256 + 139] = 11; + table[15 * 256 + 140] = 11; + table[15 * 256 + 141] = 11; + table[15 * 256 + 142] = 11; + table[15 * 256 + 143] = 11; + table[16 * 256 + 10] = 17; + + table +} + + +pub fn regex_match(input: [u8; N]) -> (BoundedVec, bool) { + let substrings = unsafe { __regex_match(input) }; + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + let mut start_range = 0; + let mut end_range = 0; + + // check the match + for i in 0..N { + // state transition + let temp = input[i] as Field; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + s = 0; + s_next = potential_s_next; + } + std::as_witness(s_next); + + // range conditions for substring matches + if ((start_range == 0) & (end_range == 0)) { + start_range = i as Field; + } + if (((s == 17) & (s_next == 18)) & (end_range == 0)) { + end_range = i as Field + 1; + } + + + let range_0 = substrings.get_unchecked(0).in_range(i); + let case_0 = [ + (s == 7) & ((s_next == 8) | (s_next == 9) | (s_next == 10) | (s_next == 11) | (s_next == 12) | (s_next == 13) | (s_next == 14) | (s_next == 15)), + (s == 8) & ((s_next == 8) | (s_next == 9) | (s_next == 10) | (s_next == 11) | (s_next == 12) | (s_next == 13) | (s_next == 14) | (s_next == 15)), + (s_next == 8) & ((s == 9)), + (s_next == 9) & ((s == 10) | (s == 11) | (s == 12)), + (s_next == 11) & ((s == 13) | (s == 14) | (s == 15)) + ].any(|case| case == true) | !range_0; + + + + let substring_range_check = [case_0] + .all(|case| case == true); + + assert(substring_range_check, "substr array ranges wrong"); + + + s = s_next; + } + // check final state + + let matched: bool = (s == 17) | (s == 18); + + // constrain extracted substrings to be in match range + //let full_match = Sequence::new(start_range as u32, end_range as u32 - start_range as u32); + //let full_match_end = full_match.end(); + // for i in 0..1 { + // let substring = substrings.get_unchecked(i); + // let is_not_valid = i >= substrings.len(); + // let index_check = substring.index >= full_match.index; + // let length_check = substring.end() <= full_match_end; + // let check = (index_check) | is_not_valid; + // assert(check, f"Substring {i} range is out of bounds of the full match found"); + // } + (substrings, matched) +} + + +pub unconstrained fn __regex_match(input: [u8; N]) -> BoundedVec { + // regex: (\r\n|^)from:[^\r\n]+\r\n + let mut substrings: BoundedVec = BoundedVec::new(); + let mut current_substring = Sequence::default(); + let mut full_match = Sequence::default(); + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + + let mut consecutive_substr = 0; + let mut complete = false; + + for i in 0..input.len() { + let temp = input[i] as Field; + let mut reset = false; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + reset = true; + s = 0; + s_next = potential_s_next; + } + // If a substring was in the making, but the state was reset + // we disregard previous progress because apparently it is invalid + if (reset & (consecutive_substr == 1)) { + current_substring = Sequence::default(); + consecutive_substr = 0; + } + // Fill up substrings + + + if ((s == 7) & (s_next == 8) | (s == 7) & (s_next == 9) | (s == 7) & (s_next == 10) | (s == 7) & (s_next == 11) | (s == 7) & (s_next == 12) | (s == 7) & (s_next == 13) | (s == 7) & (s_next == 14) | (s == 7) & (s_next == 15) | (s == 8) & (s_next == 8) | (s == 8) & (s_next == 9) | (s == 8) & (s_next == 10) | (s == 8) & (s_next == 11) | (s == 8) & (s_next == 12) | (s == 8) & (s_next == 13) | (s == 8) & (s_next == 14) | (s == 8) & (s_next == 15) | (s == 9) & (s_next == 8) | (s == 10) & (s_next == 9) | (s == 11) & (s_next == 9) | (s == 12) & (s_next == 9) | (s == 13) & (s_next == 11) | (s == 14) & (s_next == 11) | (s == 15) & (s_next == 11)) { + + if (consecutive_substr == 0) { + current_substring.index = i; + }; + current_substring.length += 1; + consecutive_substr = 1; + } else if ((consecutive_substr == 1) & (s_next == 0)) { + current_substring = Sequence::default(); + full_match = Sequence::default(); + substrings = BoundedVec::new(); + consecutive_substr = 0; + } else if (s == 17) & (s_next == 18) { + full_match.length = i - full_match.index + 1; + complete = true; + } else if (consecutive_substr == 1) { + // The substring is done so "save" it + substrings.push(current_substring); + // reset the substring holder for next use + current_substring = Sequence::default(); + consecutive_substr = 0; + } + s = s_next; + if complete == true { + break; + } + } + assert((s == 17) | (s == 18), f"no match: {s}"); + // Add pending substring that hasn't been added + if consecutive_substr == 1 { + substrings.push(current_substring); + full_match.length = input.len() - full_match.index; + } + + + + substrings +} + + + + \ No newline at end of file diff --git a/packages/noir/src/capture/raw/message_id.nr b/packages/noir/src/capture/raw/message_id.nr new file mode 100644 index 00000000..c06dd139 --- /dev/null +++ b/packages/noir/src/capture/raw/message_id.nr @@ -0,0 +1,821 @@ + +use crate::common::Sequence; + + +global table: [Field; 5120] = comptime { make_lookup_table() }; + +comptime fn make_lookup_table() -> [Field; 5120] { + let mut table = [0; 5120]; + table[18 * 256 + 0] = 19; + table[19 * 256 + 0] = 19; + table[18 * 256 + 1] = 19; + table[19 * 256 + 1] = 19; + table[18 * 256 + 2] = 19; + table[19 * 256 + 2] = 19; + table[18 * 256 + 3] = 19; + table[19 * 256 + 3] = 19; + table[18 * 256 + 4] = 19; + table[19 * 256 + 4] = 19; + table[18 * 256 + 5] = 19; + table[19 * 256 + 5] = 19; + table[18 * 256 + 6] = 19; + table[19 * 256 + 6] = 19; + table[18 * 256 + 7] = 19; + table[19 * 256 + 7] = 19; + table[18 * 256 + 8] = 19; + table[19 * 256 + 8] = 19; + table[18 * 256 + 9] = 19; + table[19 * 256 + 9] = 19; + table[18 * 256 + 10] = 19; + table[19 * 256 + 10] = 19; + table[18 * 256 + 11] = 19; + table[19 * 256 + 11] = 19; + table[18 * 256 + 12] = 19; + table[19 * 256 + 12] = 19; + table[18 * 256 + 13] = 19; + table[19 * 256 + 13] = 19; + table[18 * 256 + 14] = 19; + table[19 * 256 + 14] = 19; + table[18 * 256 + 15] = 19; + table[19 * 256 + 15] = 19; + table[18 * 256 + 16] = 19; + table[19 * 256 + 16] = 19; + table[18 * 256 + 17] = 19; + table[19 * 256 + 17] = 19; + table[18 * 256 + 18] = 19; + table[19 * 256 + 18] = 19; + table[18 * 256 + 19] = 19; + table[19 * 256 + 19] = 19; + table[18 * 256 + 20] = 19; + table[19 * 256 + 20] = 19; + table[18 * 256 + 21] = 19; + table[19 * 256 + 21] = 19; + table[18 * 256 + 22] = 19; + table[19 * 256 + 22] = 19; + table[18 * 256 + 23] = 19; + table[19 * 256 + 23] = 19; + table[18 * 256 + 24] = 19; + table[19 * 256 + 24] = 19; + table[18 * 256 + 25] = 19; + table[19 * 256 + 25] = 19; + table[18 * 256 + 26] = 19; + table[19 * 256 + 26] = 19; + table[18 * 256 + 27] = 19; + table[19 * 256 + 27] = 19; + table[18 * 256 + 28] = 19; + table[19 * 256 + 28] = 19; + table[18 * 256 + 29] = 19; + table[19 * 256 + 29] = 19; + table[18 * 256 + 30] = 19; + table[19 * 256 + 30] = 19; + table[18 * 256 + 31] = 19; + table[19 * 256 + 31] = 19; + table[18 * 256 + 32] = 19; + table[19 * 256 + 32] = 19; + table[18 * 256 + 33] = 19; + table[19 * 256 + 33] = 19; + table[18 * 256 + 34] = 19; + table[19 * 256 + 34] = 19; + table[18 * 256 + 35] = 19; + table[19 * 256 + 35] = 19; + table[18 * 256 + 36] = 19; + table[19 * 256 + 36] = 19; + table[18 * 256 + 37] = 19; + table[19 * 256 + 37] = 19; + table[18 * 256 + 38] = 19; + table[19 * 256 + 38] = 19; + table[18 * 256 + 39] = 19; + table[19 * 256 + 39] = 19; + table[18 * 256 + 40] = 19; + table[19 * 256 + 40] = 19; + table[18 * 256 + 41] = 19; + table[19 * 256 + 41] = 19; + table[18 * 256 + 42] = 19; + table[19 * 256 + 42] = 19; + table[18 * 256 + 43] = 19; + table[19 * 256 + 43] = 19; + table[18 * 256 + 44] = 19; + table[19 * 256 + 44] = 19; + table[18 * 256 + 45] = 19; + table[19 * 256 + 45] = 19; + table[18 * 256 + 46] = 19; + table[19 * 256 + 46] = 19; + table[18 * 256 + 47] = 19; + table[19 * 256 + 47] = 19; + table[18 * 256 + 48] = 19; + table[19 * 256 + 48] = 19; + table[18 * 256 + 49] = 19; + table[19 * 256 + 49] = 19; + table[18 * 256 + 50] = 19; + table[19 * 256 + 50] = 19; + table[18 * 256 + 51] = 19; + table[19 * 256 + 51] = 19; + table[18 * 256 + 52] = 19; + table[19 * 256 + 52] = 19; + table[18 * 256 + 53] = 19; + table[19 * 256 + 53] = 19; + table[18 * 256 + 54] = 19; + table[19 * 256 + 54] = 19; + table[18 * 256 + 55] = 19; + table[19 * 256 + 55] = 19; + table[18 * 256 + 56] = 19; + table[19 * 256 + 56] = 19; + table[18 * 256 + 57] = 19; + table[19 * 256 + 57] = 19; + table[18 * 256 + 58] = 19; + table[19 * 256 + 58] = 19; + table[18 * 256 + 59] = 19; + table[19 * 256 + 59] = 19; + table[18 * 256 + 60] = 19; + table[19 * 256 + 60] = 19; + table[18 * 256 + 61] = 19; + table[19 * 256 + 61] = 19; + table[18 * 256 + 62] = 19; + table[19 * 256 + 62] = 19; + table[18 * 256 + 63] = 19; + table[19 * 256 + 63] = 19; + table[18 * 256 + 64] = 19; + table[19 * 256 + 64] = 19; + table[18 * 256 + 65] = 19; + table[19 * 256 + 65] = 19; + table[18 * 256 + 66] = 19; + table[19 * 256 + 66] = 19; + table[18 * 256 + 67] = 19; + table[19 * 256 + 67] = 19; + table[18 * 256 + 68] = 19; + table[19 * 256 + 68] = 19; + table[18 * 256 + 69] = 19; + table[19 * 256 + 69] = 19; + table[18 * 256 + 70] = 19; + table[19 * 256 + 70] = 19; + table[18 * 256 + 71] = 19; + table[19 * 256 + 71] = 19; + table[18 * 256 + 72] = 19; + table[19 * 256 + 72] = 19; + table[18 * 256 + 73] = 19; + table[19 * 256 + 73] = 19; + table[18 * 256 + 74] = 19; + table[19 * 256 + 74] = 19; + table[18 * 256 + 75] = 19; + table[19 * 256 + 75] = 19; + table[18 * 256 + 76] = 19; + table[19 * 256 + 76] = 19; + table[18 * 256 + 77] = 19; + table[19 * 256 + 77] = 19; + table[18 * 256 + 78] = 19; + table[19 * 256 + 78] = 19; + table[18 * 256 + 79] = 19; + table[19 * 256 + 79] = 19; + table[18 * 256 + 80] = 19; + table[19 * 256 + 80] = 19; + table[18 * 256 + 81] = 19; + table[19 * 256 + 81] = 19; + table[18 * 256 + 82] = 19; + table[19 * 256 + 82] = 19; + table[18 * 256 + 83] = 19; + table[19 * 256 + 83] = 19; + table[18 * 256 + 84] = 19; + table[19 * 256 + 84] = 19; + table[18 * 256 + 85] = 19; + table[19 * 256 + 85] = 19; + table[18 * 256 + 86] = 19; + table[19 * 256 + 86] = 19; + table[18 * 256 + 87] = 19; + table[19 * 256 + 87] = 19; + table[18 * 256 + 88] = 19; + table[19 * 256 + 88] = 19; + table[18 * 256 + 89] = 19; + table[19 * 256 + 89] = 19; + table[18 * 256 + 90] = 19; + table[19 * 256 + 90] = 19; + table[18 * 256 + 91] = 19; + table[19 * 256 + 91] = 19; + table[18 * 256 + 92] = 19; + table[19 * 256 + 92] = 19; + table[18 * 256 + 93] = 19; + table[19 * 256 + 93] = 19; + table[18 * 256 + 94] = 19; + table[19 * 256 + 94] = 19; + table[18 * 256 + 95] = 19; + table[19 * 256 + 95] = 19; + table[18 * 256 + 96] = 19; + table[19 * 256 + 96] = 19; + table[18 * 256 + 97] = 19; + table[19 * 256 + 97] = 19; + table[18 * 256 + 98] = 19; + table[19 * 256 + 98] = 19; + table[18 * 256 + 99] = 19; + table[19 * 256 + 99] = 19; + table[18 * 256 + 100] = 19; + table[19 * 256 + 100] = 19; + table[18 * 256 + 101] = 19; + table[19 * 256 + 101] = 19; + table[18 * 256 + 102] = 19; + table[19 * 256 + 102] = 19; + table[18 * 256 + 103] = 19; + table[19 * 256 + 103] = 19; + table[18 * 256 + 104] = 19; + table[19 * 256 + 104] = 19; + table[18 * 256 + 105] = 19; + table[19 * 256 + 105] = 19; + table[18 * 256 + 106] = 19; + table[19 * 256 + 106] = 19; + table[18 * 256 + 107] = 19; + table[19 * 256 + 107] = 19; + table[18 * 256 + 108] = 19; + table[19 * 256 + 108] = 19; + table[18 * 256 + 109] = 19; + table[19 * 256 + 109] = 19; + table[18 * 256 + 110] = 19; + table[19 * 256 + 110] = 19; + table[18 * 256 + 111] = 19; + table[19 * 256 + 111] = 19; + table[18 * 256 + 112] = 19; + table[19 * 256 + 112] = 19; + table[18 * 256 + 113] = 19; + table[19 * 256 + 113] = 19; + table[18 * 256 + 114] = 19; + table[19 * 256 + 114] = 19; + table[18 * 256 + 115] = 19; + table[19 * 256 + 115] = 19; + table[18 * 256 + 116] = 19; + table[19 * 256 + 116] = 19; + table[18 * 256 + 117] = 19; + table[19 * 256 + 117] = 19; + table[18 * 256 + 118] = 19; + table[19 * 256 + 118] = 19; + table[18 * 256 + 119] = 19; + table[19 * 256 + 119] = 19; + table[18 * 256 + 120] = 19; + table[19 * 256 + 120] = 19; + table[18 * 256 + 121] = 19; + table[19 * 256 + 121] = 19; + table[18 * 256 + 122] = 19; + table[19 * 256 + 122] = 19; + table[18 * 256 + 123] = 19; + table[19 * 256 + 123] = 19; + table[18 * 256 + 124] = 19; + table[19 * 256 + 124] = 19; + table[18 * 256 + 125] = 19; + table[19 * 256 + 125] = 19; + table[18 * 256 + 126] = 19; + table[19 * 256 + 126] = 19; + table[18 * 256 + 127] = 19; + table[19 * 256 + 127] = 19; + table[18 * 256 + 128] = 19; + table[19 * 256 + 128] = 19; + table[18 * 256 + 129] = 19; + table[19 * 256 + 129] = 19; + table[18 * 256 + 130] = 19; + table[19 * 256 + 130] = 19; + table[18 * 256 + 131] = 19; + table[19 * 256 + 131] = 19; + table[18 * 256 + 132] = 19; + table[19 * 256 + 132] = 19; + table[18 * 256 + 133] = 19; + table[19 * 256 + 133] = 19; + table[18 * 256 + 134] = 19; + table[19 * 256 + 134] = 19; + table[18 * 256 + 135] = 19; + table[19 * 256 + 135] = 19; + table[18 * 256 + 136] = 19; + table[19 * 256 + 136] = 19; + table[18 * 256 + 137] = 19; + table[19 * 256 + 137] = 19; + table[18 * 256 + 138] = 19; + table[19 * 256 + 138] = 19; + table[18 * 256 + 139] = 19; + table[19 * 256 + 139] = 19; + table[18 * 256 + 140] = 19; + table[19 * 256 + 140] = 19; + table[18 * 256 + 141] = 19; + table[19 * 256 + 141] = 19; + table[18 * 256 + 142] = 19; + table[19 * 256 + 142] = 19; + table[18 * 256 + 143] = 19; + table[19 * 256 + 143] = 19; + table[18 * 256 + 144] = 19; + table[19 * 256 + 144] = 19; + table[18 * 256 + 145] = 19; + table[19 * 256 + 145] = 19; + table[18 * 256 + 146] = 19; + table[19 * 256 + 146] = 19; + table[18 * 256 + 147] = 19; + table[19 * 256 + 147] = 19; + table[18 * 256 + 148] = 19; + table[19 * 256 + 148] = 19; + table[18 * 256 + 149] = 19; + table[19 * 256 + 149] = 19; + table[18 * 256 + 150] = 19; + table[19 * 256 + 150] = 19; + table[18 * 256 + 151] = 19; + table[19 * 256 + 151] = 19; + table[18 * 256 + 152] = 19; + table[19 * 256 + 152] = 19; + table[18 * 256 + 153] = 19; + table[19 * 256 + 153] = 19; + table[18 * 256 + 154] = 19; + table[19 * 256 + 154] = 19; + table[18 * 256 + 155] = 19; + table[19 * 256 + 155] = 19; + table[18 * 256 + 156] = 19; + table[19 * 256 + 156] = 19; + table[18 * 256 + 157] = 19; + table[19 * 256 + 157] = 19; + table[18 * 256 + 158] = 19; + table[19 * 256 + 158] = 19; + table[18 * 256 + 159] = 19; + table[19 * 256 + 159] = 19; + table[18 * 256 + 160] = 19; + table[19 * 256 + 160] = 19; + table[18 * 256 + 161] = 19; + table[19 * 256 + 161] = 19; + table[18 * 256 + 162] = 19; + table[19 * 256 + 162] = 19; + table[18 * 256 + 163] = 19; + table[19 * 256 + 163] = 19; + table[18 * 256 + 164] = 19; + table[19 * 256 + 164] = 19; + table[18 * 256 + 165] = 19; + table[19 * 256 + 165] = 19; + table[18 * 256 + 166] = 19; + table[19 * 256 + 166] = 19; + table[18 * 256 + 167] = 19; + table[19 * 256 + 167] = 19; + table[18 * 256 + 168] = 19; + table[19 * 256 + 168] = 19; + table[18 * 256 + 169] = 19; + table[19 * 256 + 169] = 19; + table[18 * 256 + 170] = 19; + table[19 * 256 + 170] = 19; + table[18 * 256 + 171] = 19; + table[19 * 256 + 171] = 19; + table[18 * 256 + 172] = 19; + table[19 * 256 + 172] = 19; + table[18 * 256 + 173] = 19; + table[19 * 256 + 173] = 19; + table[18 * 256 + 174] = 19; + table[19 * 256 + 174] = 19; + table[18 * 256 + 175] = 19; + table[19 * 256 + 175] = 19; + table[18 * 256 + 176] = 19; + table[19 * 256 + 176] = 19; + table[18 * 256 + 177] = 19; + table[19 * 256 + 177] = 19; + table[18 * 256 + 178] = 19; + table[19 * 256 + 178] = 19; + table[18 * 256 + 179] = 19; + table[19 * 256 + 179] = 19; + table[18 * 256 + 180] = 19; + table[19 * 256 + 180] = 19; + table[18 * 256 + 181] = 19; + table[19 * 256 + 181] = 19; + table[18 * 256 + 182] = 19; + table[19 * 256 + 182] = 19; + table[18 * 256 + 183] = 19; + table[19 * 256 + 183] = 19; + table[18 * 256 + 184] = 19; + table[19 * 256 + 184] = 19; + table[18 * 256 + 185] = 19; + table[19 * 256 + 185] = 19; + table[18 * 256 + 186] = 19; + table[19 * 256 + 186] = 19; + table[18 * 256 + 187] = 19; + table[19 * 256 + 187] = 19; + table[18 * 256 + 188] = 19; + table[19 * 256 + 188] = 19; + table[18 * 256 + 189] = 19; + table[19 * 256 + 189] = 19; + table[18 * 256 + 190] = 19; + table[19 * 256 + 190] = 19; + table[18 * 256 + 191] = 19; + table[19 * 256 + 191] = 19; + table[18 * 256 + 192] = 19; + table[19 * 256 + 192] = 19; + table[18 * 256 + 193] = 19; + table[19 * 256 + 193] = 19; + table[18 * 256 + 194] = 19; + table[19 * 256 + 194] = 19; + table[18 * 256 + 195] = 19; + table[19 * 256 + 195] = 19; + table[18 * 256 + 196] = 19; + table[19 * 256 + 196] = 19; + table[18 * 256 + 197] = 19; + table[19 * 256 + 197] = 19; + table[18 * 256 + 198] = 19; + table[19 * 256 + 198] = 19; + table[18 * 256 + 199] = 19; + table[19 * 256 + 199] = 19; + table[18 * 256 + 200] = 19; + table[19 * 256 + 200] = 19; + table[18 * 256 + 201] = 19; + table[19 * 256 + 201] = 19; + table[18 * 256 + 202] = 19; + table[19 * 256 + 202] = 19; + table[18 * 256 + 203] = 19; + table[19 * 256 + 203] = 19; + table[18 * 256 + 204] = 19; + table[19 * 256 + 204] = 19; + table[18 * 256 + 205] = 19; + table[19 * 256 + 205] = 19; + table[18 * 256 + 206] = 19; + table[19 * 256 + 206] = 19; + table[18 * 256 + 207] = 19; + table[19 * 256 + 207] = 19; + table[18 * 256 + 208] = 19; + table[19 * 256 + 208] = 19; + table[18 * 256 + 209] = 19; + table[19 * 256 + 209] = 19; + table[18 * 256 + 210] = 19; + table[19 * 256 + 210] = 19; + table[18 * 256 + 211] = 19; + table[19 * 256 + 211] = 19; + table[18 * 256 + 212] = 19; + table[19 * 256 + 212] = 19; + table[18 * 256 + 213] = 19; + table[19 * 256 + 213] = 19; + table[18 * 256 + 214] = 19; + table[19 * 256 + 214] = 19; + table[18 * 256 + 215] = 19; + table[19 * 256 + 215] = 19; + table[18 * 256 + 216] = 19; + table[19 * 256 + 216] = 19; + table[18 * 256 + 217] = 19; + table[19 * 256 + 217] = 19; + table[18 * 256 + 218] = 19; + table[19 * 256 + 218] = 19; + table[18 * 256 + 219] = 19; + table[19 * 256 + 219] = 19; + table[18 * 256 + 220] = 19; + table[19 * 256 + 220] = 19; + table[18 * 256 + 221] = 19; + table[19 * 256 + 221] = 19; + table[18 * 256 + 222] = 19; + table[19 * 256 + 222] = 19; + table[18 * 256 + 223] = 19; + table[19 * 256 + 223] = 19; + table[18 * 256 + 224] = 19; + table[19 * 256 + 224] = 19; + table[18 * 256 + 225] = 19; + table[19 * 256 + 225] = 19; + table[18 * 256 + 226] = 19; + table[19 * 256 + 226] = 19; + table[18 * 256 + 227] = 19; + table[19 * 256 + 227] = 19; + table[18 * 256 + 228] = 19; + table[19 * 256 + 228] = 19; + table[18 * 256 + 229] = 19; + table[19 * 256 + 229] = 19; + table[18 * 256 + 230] = 19; + table[19 * 256 + 230] = 19; + table[18 * 256 + 231] = 19; + table[19 * 256 + 231] = 19; + table[18 * 256 + 232] = 19; + table[19 * 256 + 232] = 19; + table[18 * 256 + 233] = 19; + table[19 * 256 + 233] = 19; + table[18 * 256 + 234] = 19; + table[19 * 256 + 234] = 19; + table[18 * 256 + 235] = 19; + table[19 * 256 + 235] = 19; + table[18 * 256 + 236] = 19; + table[19 * 256 + 236] = 19; + table[18 * 256 + 237] = 19; + table[19 * 256 + 237] = 19; + table[18 * 256 + 238] = 19; + table[19 * 256 + 238] = 19; + table[18 * 256 + 239] = 19; + table[19 * 256 + 239] = 19; + table[18 * 256 + 240] = 19; + table[19 * 256 + 240] = 19; + table[18 * 256 + 241] = 19; + table[19 * 256 + 241] = 19; + table[18 * 256 + 242] = 19; + table[19 * 256 + 242] = 19; + table[18 * 256 + 243] = 19; + table[19 * 256 + 243] = 19; + table[18 * 256 + 244] = 19; + table[19 * 256 + 244] = 19; + table[18 * 256 + 245] = 19; + table[19 * 256 + 245] = 19; + table[18 * 256 + 246] = 19; + table[19 * 256 + 246] = 19; + table[18 * 256 + 247] = 19; + table[19 * 256 + 247] = 19; + table[18 * 256 + 248] = 19; + table[19 * 256 + 248] = 19; + table[18 * 256 + 249] = 19; + table[19 * 256 + 249] = 19; + table[18 * 256 + 250] = 19; + table[19 * 256 + 250] = 19; + table[18 * 256 + 251] = 19; + table[19 * 256 + 251] = 19; + table[18 * 256 + 252] = 19; + table[19 * 256 + 252] = 19; + table[18 * 256 + 253] = 19; + table[19 * 256 + 253] = 19; + table[18 * 256 + 254] = 19; + table[19 * 256 + 254] = 19; + table[0 * 256 + 13] = 1; + table[0 * 256 + 255] = 2; + table[1 * 256 + 10] = 2; + table[2 * 256 + 109] = 3; + table[3 * 256 + 101] = 4; + table[4 * 256 + 115] = 5; + table[5 * 256 + 115] = 6; + table[6 * 256 + 97] = 7; + table[7 * 256 + 103] = 8; + table[8 * 256 + 101] = 9; + table[9 * 256 + 45] = 10; + table[10 * 256 + 105] = 11; + table[11 * 256 + 100] = 12; + table[12 * 256 + 58] = 13; + table[13 * 256 + 60] = 14; + table[14 * 256 + 43] = 15; + table[14 * 256 + 45] = 15; + table[14 * 256 + 46] = 15; + table[14 * 256 + 48] = 15; + table[14 * 256 + 49] = 15; + table[14 * 256 + 50] = 15; + table[14 * 256 + 51] = 15; + table[14 * 256 + 52] = 15; + table[14 * 256 + 53] = 15; + table[14 * 256 + 54] = 15; + table[14 * 256 + 55] = 15; + table[14 * 256 + 56] = 15; + table[14 * 256 + 57] = 15; + table[14 * 256 + 61] = 15; + table[14 * 256 + 64] = 15; + table[14 * 256 + 65] = 15; + table[14 * 256 + 66] = 15; + table[14 * 256 + 67] = 15; + table[14 * 256 + 68] = 15; + table[14 * 256 + 69] = 15; + table[14 * 256 + 70] = 15; + table[14 * 256 + 71] = 15; + table[14 * 256 + 72] = 15; + table[14 * 256 + 73] = 15; + table[14 * 256 + 74] = 15; + table[14 * 256 + 75] = 15; + table[14 * 256 + 76] = 15; + table[14 * 256 + 77] = 15; + table[14 * 256 + 78] = 15; + table[14 * 256 + 79] = 15; + table[14 * 256 + 80] = 15; + table[14 * 256 + 81] = 15; + table[14 * 256 + 82] = 15; + table[14 * 256 + 83] = 15; + table[14 * 256 + 84] = 15; + table[14 * 256 + 85] = 15; + table[14 * 256 + 86] = 15; + table[14 * 256 + 87] = 15; + table[14 * 256 + 88] = 15; + table[14 * 256 + 89] = 15; + table[14 * 256 + 90] = 15; + table[14 * 256 + 95] = 15; + table[14 * 256 + 97] = 15; + table[14 * 256 + 98] = 15; + table[14 * 256 + 99] = 15; + table[14 * 256 + 100] = 15; + table[14 * 256 + 101] = 15; + table[14 * 256 + 102] = 15; + table[14 * 256 + 103] = 15; + table[14 * 256 + 104] = 15; + table[14 * 256 + 105] = 15; + table[14 * 256 + 106] = 15; + table[14 * 256 + 107] = 15; + table[14 * 256 + 108] = 15; + table[14 * 256 + 109] = 15; + table[14 * 256 + 110] = 15; + table[14 * 256 + 111] = 15; + table[14 * 256 + 112] = 15; + table[14 * 256 + 113] = 15; + table[14 * 256 + 114] = 15; + table[14 * 256 + 115] = 15; + table[14 * 256 + 116] = 15; + table[14 * 256 + 117] = 15; + table[14 * 256 + 118] = 15; + table[14 * 256 + 119] = 15; + table[14 * 256 + 120] = 15; + table[14 * 256 + 121] = 15; + table[14 * 256 + 122] = 15; + table[15 * 256 + 43] = 15; + table[15 * 256 + 45] = 15; + table[15 * 256 + 46] = 15; + table[15 * 256 + 48] = 15; + table[15 * 256 + 49] = 15; + table[15 * 256 + 50] = 15; + table[15 * 256 + 51] = 15; + table[15 * 256 + 52] = 15; + table[15 * 256 + 53] = 15; + table[15 * 256 + 54] = 15; + table[15 * 256 + 55] = 15; + table[15 * 256 + 56] = 15; + table[15 * 256 + 57] = 15; + table[15 * 256 + 61] = 15; + table[15 * 256 + 64] = 15; + table[15 * 256 + 65] = 15; + table[15 * 256 + 66] = 15; + table[15 * 256 + 67] = 15; + table[15 * 256 + 68] = 15; + table[15 * 256 + 69] = 15; + table[15 * 256 + 70] = 15; + table[15 * 256 + 71] = 15; + table[15 * 256 + 72] = 15; + table[15 * 256 + 73] = 15; + table[15 * 256 + 74] = 15; + table[15 * 256 + 75] = 15; + table[15 * 256 + 76] = 15; + table[15 * 256 + 77] = 15; + table[15 * 256 + 78] = 15; + table[15 * 256 + 79] = 15; + table[15 * 256 + 80] = 15; + table[15 * 256 + 81] = 15; + table[15 * 256 + 82] = 15; + table[15 * 256 + 83] = 15; + table[15 * 256 + 84] = 15; + table[15 * 256 + 85] = 15; + table[15 * 256 + 86] = 15; + table[15 * 256 + 87] = 15; + table[15 * 256 + 88] = 15; + table[15 * 256 + 89] = 15; + table[15 * 256 + 90] = 15; + table[15 * 256 + 95] = 15; + table[15 * 256 + 97] = 15; + table[15 * 256 + 98] = 15; + table[15 * 256 + 99] = 15; + table[15 * 256 + 100] = 15; + table[15 * 256 + 101] = 15; + table[15 * 256 + 102] = 15; + table[15 * 256 + 103] = 15; + table[15 * 256 + 104] = 15; + table[15 * 256 + 105] = 15; + table[15 * 256 + 106] = 15; + table[15 * 256 + 107] = 15; + table[15 * 256 + 108] = 15; + table[15 * 256 + 109] = 15; + table[15 * 256 + 110] = 15; + table[15 * 256 + 111] = 15; + table[15 * 256 + 112] = 15; + table[15 * 256 + 113] = 15; + table[15 * 256 + 114] = 15; + table[15 * 256 + 115] = 15; + table[15 * 256 + 116] = 15; + table[15 * 256 + 117] = 15; + table[15 * 256 + 118] = 15; + table[15 * 256 + 119] = 15; + table[15 * 256 + 120] = 15; + table[15 * 256 + 121] = 15; + table[15 * 256 + 122] = 15; + table[15 * 256 + 62] = 16; + table[16 * 256 + 13] = 17; + table[17 * 256 + 10] = 18; + + table +} + + +pub fn regex_match(input: [u8; N]) -> (BoundedVec, bool) { + let substrings = unsafe { __regex_match(input) }; + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + let mut start_range = 0; + let mut end_range = 0; + + // check the match + for i in 0..N { + // state transition + let temp = input[i] as Field; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + s = 0; + s_next = potential_s_next; + } + std::as_witness(s_next); + + // range conditions for substring matches + if ((start_range == 0) & (end_range == 0)) { + start_range = i as Field; + } + if (((s == 18) & (s_next == 19)) & (end_range == 0)) { + end_range = i as Field + 1; + } + + + let range_0 = substrings.get_unchecked(0).in_range(i); + let case_0 = [ + (s_next == 14) & ((s == 13)), + (s == 15) & ((s_next == 15) | (s_next == 16)), + (s_next == 15) & ((s == 14)) + ].any(|case| case == true) | !range_0; + + + + let substring_range_check = [case_0] + .all(|case| case == true); + + assert(substring_range_check, "substr array ranges wrong"); + + + s = s_next; + } + // check final state + + let matched: bool = (s == 18) | (s == 19); + + // constrain extracted substrings to be in match range + //let full_match = Sequence::new(start_range as u32, end_range as u32 - start_range as u32); + //let full_match_end = full_match.end(); + // for i in 0..1 { + // let substring = substrings.get_unchecked(i); + // let is_not_valid = i >= substrings.len(); + // let index_check = substring.index >= full_match.index; + // let length_check = substring.end() <= full_match_end; + // let check = (index_check) | is_not_valid; + // assert(check, f"Substring {i} range is out of bounds of the full match found"); + // } + (substrings, matched) +} + + +pub unconstrained fn __regex_match(input: [u8; N]) -> BoundedVec { + // regex: (\r\n|^)message-id:<[A-Za-z0-9=@\.\+_-]+>\r\n + let mut substrings: BoundedVec = BoundedVec::new(); + let mut current_substring = Sequence::default(); + let mut full_match = Sequence::default(); + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + + let mut consecutive_substr = 0; + let mut complete = false; + + for i in 0..input.len() { + let temp = input[i] as Field; + let mut reset = false; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + reset = true; + s = 0; + s_next = potential_s_next; + } + // If a substring was in the making, but the state was reset + // we disregard previous progress because apparently it is invalid + if (reset & (consecutive_substr == 1)) { + current_substring = Sequence::default(); + consecutive_substr = 0; + } + // Fill up substrings + + + if ((s == 13) & (s_next == 14) | (s == 14) & (s_next == 15) | (s == 15) & (s_next == 15) | (s == 15) & (s_next == 16)) { + + if (consecutive_substr == 0) { + current_substring.index = i; + }; + current_substring.length += 1; + consecutive_substr = 1; + } else if ((consecutive_substr == 1) & (s_next == 0)) { + current_substring = Sequence::default(); + full_match = Sequence::default(); + substrings = BoundedVec::new(); + consecutive_substr = 0; + } else if (s == 18) & (s_next == 19) { + full_match.length = i - full_match.index + 1; + complete = true; + } else if (consecutive_substr == 1) { + // The substring is done so "save" it + substrings.push(current_substring); + // reset the substring holder for next use + current_substring = Sequence::default(); + consecutive_substr = 0; + } + s = s_next; + if complete == true { + break; + } + } + assert((s == 18) | (s == 19), f"no match: {s}"); + // Add pending substring that hasn't been added + if consecutive_substr == 1 { + substrings.push(current_substring); + full_match.length = input.len() - full_match.index; + } + + + + substrings +} + + + + \ No newline at end of file diff --git a/packages/noir/src/capture/raw/mod.nr b/packages/noir/src/capture/raw/mod.nr new file mode 100644 index 00000000..08c90017 --- /dev/null +++ b/packages/noir/src/capture/raw/mod.nr @@ -0,0 +1,9 @@ +pub mod body_hash; +pub mod email_addr; +pub mod email_domain; +pub mod from_all; +pub mod message_id; +pub mod reversed_bracket; +pub mod subject_all; +pub mod timestamp; +pub mod to_all; \ No newline at end of file diff --git a/packages/noir/src/capture/raw/reversed_bracket.nr b/packages/noir/src/capture/raw/reversed_bracket.nr new file mode 100644 index 00000000..0bc49271 --- /dev/null +++ b/packages/noir/src/capture/raw/reversed_bracket.nr @@ -0,0 +1,1843 @@ + +use crate::common::Sequence; + + +global table: [Field; 4864] = comptime { make_lookup_table() }; + +comptime fn make_lookup_table() -> [Field; 4864] { + let mut table = [0; 4864]; + table[10 * 256 + 0] = 18; + table[18 * 256 + 0] = 18; + table[10 * 256 + 1] = 18; + table[18 * 256 + 1] = 18; + table[10 * 256 + 2] = 18; + table[18 * 256 + 2] = 18; + table[10 * 256 + 3] = 18; + table[18 * 256 + 3] = 18; + table[10 * 256 + 4] = 18; + table[18 * 256 + 4] = 18; + table[10 * 256 + 5] = 18; + table[18 * 256 + 5] = 18; + table[10 * 256 + 6] = 18; + table[18 * 256 + 6] = 18; + table[10 * 256 + 7] = 18; + table[18 * 256 + 7] = 18; + table[10 * 256 + 8] = 18; + table[18 * 256 + 8] = 18; + table[10 * 256 + 9] = 18; + table[18 * 256 + 9] = 18; + table[10 * 256 + 10] = 18; + table[18 * 256 + 10] = 18; + table[10 * 256 + 11] = 18; + table[18 * 256 + 11] = 18; + table[10 * 256 + 12] = 18; + table[18 * 256 + 12] = 18; + table[10 * 256 + 13] = 18; + table[18 * 256 + 13] = 18; + table[10 * 256 + 14] = 18; + table[18 * 256 + 14] = 18; + table[10 * 256 + 15] = 18; + table[18 * 256 + 15] = 18; + table[10 * 256 + 16] = 18; + table[18 * 256 + 16] = 18; + table[10 * 256 + 17] = 18; + table[18 * 256 + 17] = 18; + table[10 * 256 + 18] = 18; + table[18 * 256 + 18] = 18; + table[10 * 256 + 19] = 18; + table[18 * 256 + 19] = 18; + table[10 * 256 + 20] = 18; + table[18 * 256 + 20] = 18; + table[10 * 256 + 21] = 18; + table[18 * 256 + 21] = 18; + table[10 * 256 + 22] = 18; + table[18 * 256 + 22] = 18; + table[10 * 256 + 23] = 18; + table[18 * 256 + 23] = 18; + table[10 * 256 + 24] = 18; + table[18 * 256 + 24] = 18; + table[10 * 256 + 25] = 18; + table[18 * 256 + 25] = 18; + table[10 * 256 + 26] = 18; + table[18 * 256 + 26] = 18; + table[10 * 256 + 27] = 18; + table[18 * 256 + 27] = 18; + table[10 * 256 + 28] = 18; + table[18 * 256 + 28] = 18; + table[10 * 256 + 29] = 18; + table[18 * 256 + 29] = 18; + table[10 * 256 + 30] = 18; + table[18 * 256 + 30] = 18; + table[10 * 256 + 31] = 18; + table[18 * 256 + 31] = 18; + table[10 * 256 + 32] = 18; + table[18 * 256 + 32] = 18; + table[10 * 256 + 33] = 18; + table[18 * 256 + 33] = 18; + table[10 * 256 + 34] = 18; + table[18 * 256 + 34] = 18; + table[10 * 256 + 35] = 18; + table[18 * 256 + 35] = 18; + table[10 * 256 + 36] = 18; + table[18 * 256 + 36] = 18; + table[10 * 256 + 37] = 18; + table[18 * 256 + 37] = 18; + table[10 * 256 + 38] = 18; + table[18 * 256 + 38] = 18; + table[10 * 256 + 39] = 18; + table[18 * 256 + 39] = 18; + table[10 * 256 + 40] = 18; + table[18 * 256 + 40] = 18; + table[10 * 256 + 41] = 18; + table[18 * 256 + 41] = 18; + table[10 * 256 + 42] = 18; + table[18 * 256 + 42] = 18; + table[10 * 256 + 43] = 18; + table[18 * 256 + 43] = 18; + table[10 * 256 + 44] = 18; + table[18 * 256 + 44] = 18; + table[10 * 256 + 45] = 18; + table[18 * 256 + 45] = 18; + table[10 * 256 + 46] = 18; + table[18 * 256 + 46] = 18; + table[10 * 256 + 47] = 18; + table[18 * 256 + 47] = 18; + table[10 * 256 + 48] = 18; + table[18 * 256 + 48] = 18; + table[10 * 256 + 49] = 18; + table[18 * 256 + 49] = 18; + table[10 * 256 + 50] = 18; + table[18 * 256 + 50] = 18; + table[10 * 256 + 51] = 18; + table[18 * 256 + 51] = 18; + table[10 * 256 + 52] = 18; + table[18 * 256 + 52] = 18; + table[10 * 256 + 53] = 18; + table[18 * 256 + 53] = 18; + table[10 * 256 + 54] = 18; + table[18 * 256 + 54] = 18; + table[10 * 256 + 55] = 18; + table[18 * 256 + 55] = 18; + table[10 * 256 + 56] = 18; + table[18 * 256 + 56] = 18; + table[10 * 256 + 57] = 18; + table[18 * 256 + 57] = 18; + table[10 * 256 + 58] = 18; + table[18 * 256 + 58] = 18; + table[10 * 256 + 59] = 18; + table[18 * 256 + 59] = 18; + table[10 * 256 + 60] = 18; + table[18 * 256 + 60] = 18; + table[10 * 256 + 61] = 18; + table[18 * 256 + 61] = 18; + table[10 * 256 + 62] = 18; + table[18 * 256 + 62] = 18; + table[10 * 256 + 63] = 18; + table[18 * 256 + 63] = 18; + table[10 * 256 + 64] = 18; + table[18 * 256 + 64] = 18; + table[10 * 256 + 65] = 18; + table[18 * 256 + 65] = 18; + table[10 * 256 + 66] = 18; + table[18 * 256 + 66] = 18; + table[10 * 256 + 67] = 18; + table[18 * 256 + 67] = 18; + table[10 * 256 + 68] = 18; + table[18 * 256 + 68] = 18; + table[10 * 256 + 69] = 18; + table[18 * 256 + 69] = 18; + table[10 * 256 + 70] = 18; + table[18 * 256 + 70] = 18; + table[10 * 256 + 71] = 18; + table[18 * 256 + 71] = 18; + table[10 * 256 + 72] = 18; + table[18 * 256 + 72] = 18; + table[10 * 256 + 73] = 18; + table[18 * 256 + 73] = 18; + table[10 * 256 + 74] = 18; + table[18 * 256 + 74] = 18; + table[10 * 256 + 75] = 18; + table[18 * 256 + 75] = 18; + table[10 * 256 + 76] = 18; + table[18 * 256 + 76] = 18; + table[10 * 256 + 77] = 18; + table[18 * 256 + 77] = 18; + table[10 * 256 + 78] = 18; + table[18 * 256 + 78] = 18; + table[10 * 256 + 79] = 18; + table[18 * 256 + 79] = 18; + table[10 * 256 + 80] = 18; + table[18 * 256 + 80] = 18; + table[10 * 256 + 81] = 18; + table[18 * 256 + 81] = 18; + table[10 * 256 + 82] = 18; + table[18 * 256 + 82] = 18; + table[10 * 256 + 83] = 18; + table[18 * 256 + 83] = 18; + table[10 * 256 + 84] = 18; + table[18 * 256 + 84] = 18; + table[10 * 256 + 85] = 18; + table[18 * 256 + 85] = 18; + table[10 * 256 + 86] = 18; + table[18 * 256 + 86] = 18; + table[10 * 256 + 87] = 18; + table[18 * 256 + 87] = 18; + table[10 * 256 + 88] = 18; + table[18 * 256 + 88] = 18; + table[10 * 256 + 89] = 18; + table[18 * 256 + 89] = 18; + table[10 * 256 + 90] = 18; + table[18 * 256 + 90] = 18; + table[10 * 256 + 91] = 18; + table[18 * 256 + 91] = 18; + table[10 * 256 + 92] = 18; + table[18 * 256 + 92] = 18; + table[10 * 256 + 93] = 18; + table[18 * 256 + 93] = 18; + table[10 * 256 + 94] = 18; + table[18 * 256 + 94] = 18; + table[10 * 256 + 95] = 18; + table[18 * 256 + 95] = 18; + table[10 * 256 + 96] = 18; + table[18 * 256 + 96] = 18; + table[10 * 256 + 97] = 18; + table[18 * 256 + 97] = 18; + table[10 * 256 + 98] = 18; + table[18 * 256 + 98] = 18; + table[10 * 256 + 99] = 18; + table[18 * 256 + 99] = 18; + table[10 * 256 + 100] = 18; + table[18 * 256 + 100] = 18; + table[10 * 256 + 101] = 18; + table[18 * 256 + 101] = 18; + table[10 * 256 + 102] = 18; + table[18 * 256 + 102] = 18; + table[10 * 256 + 103] = 18; + table[18 * 256 + 103] = 18; + table[10 * 256 + 104] = 18; + table[18 * 256 + 104] = 18; + table[10 * 256 + 105] = 18; + table[18 * 256 + 105] = 18; + table[10 * 256 + 106] = 18; + table[18 * 256 + 106] = 18; + table[10 * 256 + 107] = 18; + table[18 * 256 + 107] = 18; + table[10 * 256 + 108] = 18; + table[18 * 256 + 108] = 18; + table[10 * 256 + 109] = 18; + table[18 * 256 + 109] = 18; + table[10 * 256 + 110] = 18; + table[18 * 256 + 110] = 18; + table[10 * 256 + 111] = 18; + table[18 * 256 + 111] = 18; + table[10 * 256 + 112] = 18; + table[18 * 256 + 112] = 18; + table[10 * 256 + 113] = 18; + table[18 * 256 + 113] = 18; + table[10 * 256 + 114] = 18; + table[18 * 256 + 114] = 18; + table[10 * 256 + 115] = 18; + table[18 * 256 + 115] = 18; + table[10 * 256 + 116] = 18; + table[18 * 256 + 116] = 18; + table[10 * 256 + 117] = 18; + table[18 * 256 + 117] = 18; + table[10 * 256 + 118] = 18; + table[18 * 256 + 118] = 18; + table[10 * 256 + 119] = 18; + table[18 * 256 + 119] = 18; + table[10 * 256 + 120] = 18; + table[18 * 256 + 120] = 18; + table[10 * 256 + 121] = 18; + table[18 * 256 + 121] = 18; + table[10 * 256 + 122] = 18; + table[18 * 256 + 122] = 18; + table[10 * 256 + 123] = 18; + table[18 * 256 + 123] = 18; + table[10 * 256 + 124] = 18; + table[18 * 256 + 124] = 18; + table[10 * 256 + 125] = 18; + table[18 * 256 + 125] = 18; + table[10 * 256 + 126] = 18; + table[18 * 256 + 126] = 18; + table[10 * 256 + 127] = 18; + table[18 * 256 + 127] = 18; + table[10 * 256 + 128] = 18; + table[18 * 256 + 128] = 18; + table[10 * 256 + 129] = 18; + table[18 * 256 + 129] = 18; + table[10 * 256 + 130] = 18; + table[18 * 256 + 130] = 18; + table[10 * 256 + 131] = 18; + table[18 * 256 + 131] = 18; + table[10 * 256 + 132] = 18; + table[18 * 256 + 132] = 18; + table[10 * 256 + 133] = 18; + table[18 * 256 + 133] = 18; + table[10 * 256 + 134] = 18; + table[18 * 256 + 134] = 18; + table[10 * 256 + 135] = 18; + table[18 * 256 + 135] = 18; + table[10 * 256 + 136] = 18; + table[18 * 256 + 136] = 18; + table[10 * 256 + 137] = 18; + table[18 * 256 + 137] = 18; + table[10 * 256 + 138] = 18; + table[18 * 256 + 138] = 18; + table[10 * 256 + 139] = 18; + table[18 * 256 + 139] = 18; + table[10 * 256 + 140] = 18; + table[18 * 256 + 140] = 18; + table[10 * 256 + 141] = 18; + table[18 * 256 + 141] = 18; + table[10 * 256 + 142] = 18; + table[18 * 256 + 142] = 18; + table[10 * 256 + 143] = 18; + table[18 * 256 + 143] = 18; + table[10 * 256 + 144] = 18; + table[18 * 256 + 144] = 18; + table[10 * 256 + 145] = 18; + table[18 * 256 + 145] = 18; + table[10 * 256 + 146] = 18; + table[18 * 256 + 146] = 18; + table[10 * 256 + 147] = 18; + table[18 * 256 + 147] = 18; + table[10 * 256 + 148] = 18; + table[18 * 256 + 148] = 18; + table[10 * 256 + 149] = 18; + table[18 * 256 + 149] = 18; + table[10 * 256 + 150] = 18; + table[18 * 256 + 150] = 18; + table[10 * 256 + 151] = 18; + table[18 * 256 + 151] = 18; + table[10 * 256 + 152] = 18; + table[18 * 256 + 152] = 18; + table[10 * 256 + 153] = 18; + table[18 * 256 + 153] = 18; + table[10 * 256 + 154] = 18; + table[18 * 256 + 154] = 18; + table[10 * 256 + 155] = 18; + table[18 * 256 + 155] = 18; + table[10 * 256 + 156] = 18; + table[18 * 256 + 156] = 18; + table[10 * 256 + 157] = 18; + table[18 * 256 + 157] = 18; + table[10 * 256 + 158] = 18; + table[18 * 256 + 158] = 18; + table[10 * 256 + 159] = 18; + table[18 * 256 + 159] = 18; + table[10 * 256 + 160] = 18; + table[18 * 256 + 160] = 18; + table[10 * 256 + 161] = 18; + table[18 * 256 + 161] = 18; + table[10 * 256 + 162] = 18; + table[18 * 256 + 162] = 18; + table[10 * 256 + 163] = 18; + table[18 * 256 + 163] = 18; + table[10 * 256 + 164] = 18; + table[18 * 256 + 164] = 18; + table[10 * 256 + 165] = 18; + table[18 * 256 + 165] = 18; + table[10 * 256 + 166] = 18; + table[18 * 256 + 166] = 18; + table[10 * 256 + 167] = 18; + table[18 * 256 + 167] = 18; + table[10 * 256 + 168] = 18; + table[18 * 256 + 168] = 18; + table[10 * 256 + 169] = 18; + table[18 * 256 + 169] = 18; + table[10 * 256 + 170] = 18; + table[18 * 256 + 170] = 18; + table[10 * 256 + 171] = 18; + table[18 * 256 + 171] = 18; + table[10 * 256 + 172] = 18; + table[18 * 256 + 172] = 18; + table[10 * 256 + 173] = 18; + table[18 * 256 + 173] = 18; + table[10 * 256 + 174] = 18; + table[18 * 256 + 174] = 18; + table[10 * 256 + 175] = 18; + table[18 * 256 + 175] = 18; + table[10 * 256 + 176] = 18; + table[18 * 256 + 176] = 18; + table[10 * 256 + 177] = 18; + table[18 * 256 + 177] = 18; + table[10 * 256 + 178] = 18; + table[18 * 256 + 178] = 18; + table[10 * 256 + 179] = 18; + table[18 * 256 + 179] = 18; + table[10 * 256 + 180] = 18; + table[18 * 256 + 180] = 18; + table[10 * 256 + 181] = 18; + table[18 * 256 + 181] = 18; + table[10 * 256 + 182] = 18; + table[18 * 256 + 182] = 18; + table[10 * 256 + 183] = 18; + table[18 * 256 + 183] = 18; + table[10 * 256 + 184] = 18; + table[18 * 256 + 184] = 18; + table[10 * 256 + 185] = 18; + table[18 * 256 + 185] = 18; + table[10 * 256 + 186] = 18; + table[18 * 256 + 186] = 18; + table[10 * 256 + 187] = 18; + table[18 * 256 + 187] = 18; + table[10 * 256 + 188] = 18; + table[18 * 256 + 188] = 18; + table[10 * 256 + 189] = 18; + table[18 * 256 + 189] = 18; + table[10 * 256 + 190] = 18; + table[18 * 256 + 190] = 18; + table[10 * 256 + 191] = 18; + table[18 * 256 + 191] = 18; + table[10 * 256 + 192] = 18; + table[18 * 256 + 192] = 18; + table[10 * 256 + 193] = 18; + table[18 * 256 + 193] = 18; + table[10 * 256 + 194] = 18; + table[18 * 256 + 194] = 18; + table[10 * 256 + 195] = 18; + table[18 * 256 + 195] = 18; + table[10 * 256 + 196] = 18; + table[18 * 256 + 196] = 18; + table[10 * 256 + 197] = 18; + table[18 * 256 + 197] = 18; + table[10 * 256 + 198] = 18; + table[18 * 256 + 198] = 18; + table[10 * 256 + 199] = 18; + table[18 * 256 + 199] = 18; + table[10 * 256 + 200] = 18; + table[18 * 256 + 200] = 18; + table[10 * 256 + 201] = 18; + table[18 * 256 + 201] = 18; + table[10 * 256 + 202] = 18; + table[18 * 256 + 202] = 18; + table[10 * 256 + 203] = 18; + table[18 * 256 + 203] = 18; + table[10 * 256 + 204] = 18; + table[18 * 256 + 204] = 18; + table[10 * 256 + 205] = 18; + table[18 * 256 + 205] = 18; + table[10 * 256 + 206] = 18; + table[18 * 256 + 206] = 18; + table[10 * 256 + 207] = 18; + table[18 * 256 + 207] = 18; + table[10 * 256 + 208] = 18; + table[18 * 256 + 208] = 18; + table[10 * 256 + 209] = 18; + table[18 * 256 + 209] = 18; + table[10 * 256 + 210] = 18; + table[18 * 256 + 210] = 18; + table[10 * 256 + 211] = 18; + table[18 * 256 + 211] = 18; + table[10 * 256 + 212] = 18; + table[18 * 256 + 212] = 18; + table[10 * 256 + 213] = 18; + table[18 * 256 + 213] = 18; + table[10 * 256 + 214] = 18; + table[18 * 256 + 214] = 18; + table[10 * 256 + 215] = 18; + table[18 * 256 + 215] = 18; + table[10 * 256 + 216] = 18; + table[18 * 256 + 216] = 18; + table[10 * 256 + 217] = 18; + table[18 * 256 + 217] = 18; + table[10 * 256 + 218] = 18; + table[18 * 256 + 218] = 18; + table[10 * 256 + 219] = 18; + table[18 * 256 + 219] = 18; + table[10 * 256 + 220] = 18; + table[18 * 256 + 220] = 18; + table[10 * 256 + 221] = 18; + table[18 * 256 + 221] = 18; + table[10 * 256 + 222] = 18; + table[18 * 256 + 222] = 18; + table[10 * 256 + 223] = 18; + table[18 * 256 + 223] = 18; + table[10 * 256 + 224] = 18; + table[18 * 256 + 224] = 18; + table[10 * 256 + 225] = 18; + table[18 * 256 + 225] = 18; + table[10 * 256 + 226] = 18; + table[18 * 256 + 226] = 18; + table[10 * 256 + 227] = 18; + table[18 * 256 + 227] = 18; + table[10 * 256 + 228] = 18; + table[18 * 256 + 228] = 18; + table[10 * 256 + 229] = 18; + table[18 * 256 + 229] = 18; + table[10 * 256 + 230] = 18; + table[18 * 256 + 230] = 18; + table[10 * 256 + 231] = 18; + table[18 * 256 + 231] = 18; + table[10 * 256 + 232] = 18; + table[18 * 256 + 232] = 18; + table[10 * 256 + 233] = 18; + table[18 * 256 + 233] = 18; + table[10 * 256 + 234] = 18; + table[18 * 256 + 234] = 18; + table[10 * 256 + 235] = 18; + table[18 * 256 + 235] = 18; + table[10 * 256 + 236] = 18; + table[18 * 256 + 236] = 18; + table[10 * 256 + 237] = 18; + table[18 * 256 + 237] = 18; + table[10 * 256 + 238] = 18; + table[18 * 256 + 238] = 18; + table[10 * 256 + 239] = 18; + table[18 * 256 + 239] = 18; + table[10 * 256 + 240] = 18; + table[18 * 256 + 240] = 18; + table[10 * 256 + 241] = 18; + table[18 * 256 + 241] = 18; + table[10 * 256 + 242] = 18; + table[18 * 256 + 242] = 18; + table[10 * 256 + 243] = 18; + table[18 * 256 + 243] = 18; + table[10 * 256 + 244] = 18; + table[18 * 256 + 244] = 18; + table[10 * 256 + 245] = 18; + table[18 * 256 + 245] = 18; + table[10 * 256 + 246] = 18; + table[18 * 256 + 246] = 18; + table[10 * 256 + 247] = 18; + table[18 * 256 + 247] = 18; + table[10 * 256 + 248] = 18; + table[18 * 256 + 248] = 18; + table[10 * 256 + 249] = 18; + table[18 * 256 + 249] = 18; + table[10 * 256 + 250] = 18; + table[18 * 256 + 250] = 18; + table[10 * 256 + 251] = 18; + table[18 * 256 + 251] = 18; + table[10 * 256 + 252] = 18; + table[18 * 256 + 252] = 18; + table[10 * 256 + 253] = 18; + table[18 * 256 + 253] = 18; + table[10 * 256 + 254] = 18; + table[18 * 256 + 254] = 18; + table[0 * 256 + 62] = 1; + table[1 * 256 + 0] = 2; + table[1 * 256 + 1] = 2; + table[1 * 256 + 2] = 2; + table[1 * 256 + 3] = 2; + table[1 * 256 + 4] = 2; + table[1 * 256 + 5] = 2; + table[1 * 256 + 6] = 2; + table[1 * 256 + 7] = 2; + table[1 * 256 + 8] = 2; + table[1 * 256 + 9] = 2; + table[1 * 256 + 10] = 2; + table[1 * 256 + 11] = 2; + table[1 * 256 + 12] = 2; + table[1 * 256 + 13] = 2; + table[1 * 256 + 14] = 2; + table[1 * 256 + 15] = 2; + table[1 * 256 + 16] = 2; + table[1 * 256 + 17] = 2; + table[1 * 256 + 18] = 2; + table[1 * 256 + 19] = 2; + table[1 * 256 + 20] = 2; + table[1 * 256 + 21] = 2; + table[1 * 256 + 22] = 2; + table[1 * 256 + 23] = 2; + table[1 * 256 + 24] = 2; + table[1 * 256 + 25] = 2; + table[1 * 256 + 26] = 2; + table[1 * 256 + 27] = 2; + table[1 * 256 + 28] = 2; + table[1 * 256 + 29] = 2; + table[1 * 256 + 30] = 2; + table[1 * 256 + 31] = 2; + table[1 * 256 + 32] = 2; + table[1 * 256 + 33] = 2; + table[1 * 256 + 34] = 2; + table[1 * 256 + 35] = 2; + table[1 * 256 + 36] = 2; + table[1 * 256 + 37] = 2; + table[1 * 256 + 38] = 2; + table[1 * 256 + 39] = 2; + table[1 * 256 + 40] = 2; + table[1 * 256 + 41] = 2; + table[1 * 256 + 42] = 2; + table[1 * 256 + 43] = 2; + table[1 * 256 + 44] = 2; + table[1 * 256 + 45] = 2; + table[1 * 256 + 46] = 2; + table[1 * 256 + 47] = 2; + table[1 * 256 + 48] = 2; + table[1 * 256 + 49] = 2; + table[1 * 256 + 50] = 2; + table[1 * 256 + 51] = 2; + table[1 * 256 + 52] = 2; + table[1 * 256 + 53] = 2; + table[1 * 256 + 54] = 2; + table[1 * 256 + 55] = 2; + table[1 * 256 + 56] = 2; + table[1 * 256 + 57] = 2; + table[1 * 256 + 58] = 2; + table[1 * 256 + 59] = 2; + table[1 * 256 + 61] = 2; + table[1 * 256 + 63] = 2; + table[1 * 256 + 64] = 2; + table[1 * 256 + 65] = 2; + table[1 * 256 + 66] = 2; + table[1 * 256 + 67] = 2; + table[1 * 256 + 68] = 2; + table[1 * 256 + 69] = 2; + table[1 * 256 + 70] = 2; + table[1 * 256 + 71] = 2; + table[1 * 256 + 72] = 2; + table[1 * 256 + 73] = 2; + table[1 * 256 + 74] = 2; + table[1 * 256 + 75] = 2; + table[1 * 256 + 76] = 2; + table[1 * 256 + 77] = 2; + table[1 * 256 + 78] = 2; + table[1 * 256 + 79] = 2; + table[1 * 256 + 80] = 2; + table[1 * 256 + 81] = 2; + table[1 * 256 + 82] = 2; + table[1 * 256 + 83] = 2; + table[1 * 256 + 84] = 2; + table[1 * 256 + 85] = 2; + table[1 * 256 + 86] = 2; + table[1 * 256 + 87] = 2; + table[1 * 256 + 88] = 2; + table[1 * 256 + 89] = 2; + table[1 * 256 + 90] = 2; + table[1 * 256 + 91] = 2; + table[1 * 256 + 92] = 2; + table[1 * 256 + 93] = 2; + table[1 * 256 + 94] = 2; + table[1 * 256 + 95] = 2; + table[1 * 256 + 96] = 2; + table[1 * 256 + 97] = 2; + table[1 * 256 + 98] = 2; + table[1 * 256 + 99] = 2; + table[1 * 256 + 100] = 2; + table[1 * 256 + 101] = 2; + table[1 * 256 + 102] = 2; + table[1 * 256 + 103] = 2; + table[1 * 256 + 104] = 2; + table[1 * 256 + 105] = 2; + table[1 * 256 + 106] = 2; + table[1 * 256 + 107] = 2; + table[1 * 256 + 108] = 2; + table[1 * 256 + 109] = 2; + table[1 * 256 + 110] = 2; + table[1 * 256 + 111] = 2; + table[1 * 256 + 112] = 2; + table[1 * 256 + 113] = 2; + table[1 * 256 + 114] = 2; + table[1 * 256 + 115] = 2; + table[1 * 256 + 116] = 2; + table[1 * 256 + 117] = 2; + table[1 * 256 + 118] = 2; + table[1 * 256 + 119] = 2; + table[1 * 256 + 120] = 2; + table[1 * 256 + 121] = 2; + table[1 * 256 + 122] = 2; + table[1 * 256 + 123] = 2; + table[1 * 256 + 124] = 2; + table[1 * 256 + 125] = 2; + table[1 * 256 + 126] = 2; + table[1 * 256 + 127] = 2; + table[1 * 256 + 194] = 3; + table[1 * 256 + 195] = 3; + table[1 * 256 + 196] = 3; + table[1 * 256 + 197] = 3; + table[1 * 256 + 198] = 3; + table[1 * 256 + 199] = 3; + table[1 * 256 + 200] = 3; + table[1 * 256 + 201] = 3; + table[1 * 256 + 202] = 3; + table[1 * 256 + 203] = 3; + table[1 * 256 + 204] = 3; + table[1 * 256 + 205] = 3; + table[1 * 256 + 206] = 3; + table[1 * 256 + 207] = 3; + table[1 * 256 + 208] = 3; + table[1 * 256 + 209] = 3; + table[1 * 256 + 210] = 3; + table[1 * 256 + 211] = 3; + table[1 * 256 + 212] = 3; + table[1 * 256 + 213] = 3; + table[1 * 256 + 214] = 3; + table[1 * 256 + 215] = 3; + table[1 * 256 + 216] = 3; + table[1 * 256 + 217] = 3; + table[1 * 256 + 218] = 3; + table[1 * 256 + 219] = 3; + table[1 * 256 + 220] = 3; + table[1 * 256 + 221] = 3; + table[1 * 256 + 222] = 3; + table[1 * 256 + 223] = 3; + table[1 * 256 + 224] = 4; + table[1 * 256 + 225] = 5; + table[1 * 256 + 226] = 5; + table[1 * 256 + 227] = 5; + table[1 * 256 + 228] = 5; + table[1 * 256 + 229] = 5; + table[1 * 256 + 230] = 5; + table[1 * 256 + 231] = 5; + table[1 * 256 + 232] = 5; + table[1 * 256 + 233] = 5; + table[1 * 256 + 234] = 5; + table[1 * 256 + 235] = 5; + table[1 * 256 + 236] = 5; + table[1 * 256 + 238] = 5; + table[1 * 256 + 239] = 5; + table[1 * 256 + 237] = 6; + table[1 * 256 + 240] = 7; + table[1 * 256 + 241] = 8; + table[1 * 256 + 242] = 8; + table[1 * 256 + 243] = 8; + table[1 * 256 + 244] = 9; + table[2 * 256 + 0] = 2; + table[2 * 256 + 1] = 2; + table[2 * 256 + 2] = 2; + table[2 * 256 + 3] = 2; + table[2 * 256 + 4] = 2; + table[2 * 256 + 5] = 2; + table[2 * 256 + 6] = 2; + table[2 * 256 + 7] = 2; + table[2 * 256 + 8] = 2; + table[2 * 256 + 9] = 2; + table[2 * 256 + 10] = 2; + table[2 * 256 + 11] = 2; + table[2 * 256 + 12] = 2; + table[2 * 256 + 13] = 2; + table[2 * 256 + 14] = 2; + table[2 * 256 + 15] = 2; + table[2 * 256 + 16] = 2; + table[2 * 256 + 17] = 2; + table[2 * 256 + 18] = 2; + table[2 * 256 + 19] = 2; + table[2 * 256 + 20] = 2; + table[2 * 256 + 21] = 2; + table[2 * 256 + 22] = 2; + table[2 * 256 + 23] = 2; + table[2 * 256 + 24] = 2; + table[2 * 256 + 25] = 2; + table[2 * 256 + 26] = 2; + table[2 * 256 + 27] = 2; + table[2 * 256 + 28] = 2; + table[2 * 256 + 29] = 2; + table[2 * 256 + 30] = 2; + table[2 * 256 + 31] = 2; + table[2 * 256 + 32] = 2; + table[2 * 256 + 33] = 2; + table[2 * 256 + 34] = 2; + table[2 * 256 + 35] = 2; + table[2 * 256 + 36] = 2; + table[2 * 256 + 37] = 2; + table[2 * 256 + 38] = 2; + table[2 * 256 + 39] = 2; + table[2 * 256 + 40] = 2; + table[2 * 256 + 41] = 2; + table[2 * 256 + 42] = 2; + table[2 * 256 + 43] = 2; + table[2 * 256 + 44] = 2; + table[2 * 256 + 45] = 2; + table[2 * 256 + 46] = 2; + table[2 * 256 + 47] = 2; + table[2 * 256 + 48] = 2; + table[2 * 256 + 49] = 2; + table[2 * 256 + 50] = 2; + table[2 * 256 + 51] = 2; + table[2 * 256 + 52] = 2; + table[2 * 256 + 53] = 2; + table[2 * 256 + 54] = 2; + table[2 * 256 + 55] = 2; + table[2 * 256 + 56] = 2; + table[2 * 256 + 57] = 2; + table[2 * 256 + 58] = 2; + table[2 * 256 + 59] = 2; + table[2 * 256 + 61] = 2; + table[2 * 256 + 63] = 2; + table[2 * 256 + 64] = 2; + table[2 * 256 + 65] = 2; + table[2 * 256 + 66] = 2; + table[2 * 256 + 67] = 2; + table[2 * 256 + 68] = 2; + table[2 * 256 + 69] = 2; + table[2 * 256 + 70] = 2; + table[2 * 256 + 71] = 2; + table[2 * 256 + 72] = 2; + table[2 * 256 + 73] = 2; + table[2 * 256 + 74] = 2; + table[2 * 256 + 75] = 2; + table[2 * 256 + 76] = 2; + table[2 * 256 + 77] = 2; + table[2 * 256 + 78] = 2; + table[2 * 256 + 79] = 2; + table[2 * 256 + 80] = 2; + table[2 * 256 + 81] = 2; + table[2 * 256 + 82] = 2; + table[2 * 256 + 83] = 2; + table[2 * 256 + 84] = 2; + table[2 * 256 + 85] = 2; + table[2 * 256 + 86] = 2; + table[2 * 256 + 87] = 2; + table[2 * 256 + 88] = 2; + table[2 * 256 + 89] = 2; + table[2 * 256 + 90] = 2; + table[2 * 256 + 91] = 2; + table[2 * 256 + 92] = 2; + table[2 * 256 + 93] = 2; + table[2 * 256 + 94] = 2; + table[2 * 256 + 95] = 2; + table[2 * 256 + 96] = 2; + table[2 * 256 + 97] = 2; + table[2 * 256 + 98] = 2; + table[2 * 256 + 99] = 2; + table[2 * 256 + 100] = 2; + table[2 * 256 + 101] = 2; + table[2 * 256 + 102] = 2; + table[2 * 256 + 103] = 2; + table[2 * 256 + 104] = 2; + table[2 * 256 + 105] = 2; + table[2 * 256 + 106] = 2; + table[2 * 256 + 107] = 2; + table[2 * 256 + 108] = 2; + table[2 * 256 + 109] = 2; + table[2 * 256 + 110] = 2; + table[2 * 256 + 111] = 2; + table[2 * 256 + 112] = 2; + table[2 * 256 + 113] = 2; + table[2 * 256 + 114] = 2; + table[2 * 256 + 115] = 2; + table[2 * 256 + 116] = 2; + table[2 * 256 + 117] = 2; + table[2 * 256 + 118] = 2; + table[2 * 256 + 119] = 2; + table[2 * 256 + 120] = 2; + table[2 * 256 + 121] = 2; + table[2 * 256 + 122] = 2; + table[2 * 256 + 123] = 2; + table[2 * 256 + 124] = 2; + table[2 * 256 + 125] = 2; + table[2 * 256 + 126] = 2; + table[2 * 256 + 127] = 2; + table[2 * 256 + 194] = 3; + table[2 * 256 + 195] = 3; + table[2 * 256 + 196] = 3; + table[2 * 256 + 197] = 3; + table[2 * 256 + 198] = 3; + table[2 * 256 + 199] = 3; + table[2 * 256 + 200] = 3; + table[2 * 256 + 201] = 3; + table[2 * 256 + 202] = 3; + table[2 * 256 + 203] = 3; + table[2 * 256 + 204] = 3; + table[2 * 256 + 205] = 3; + table[2 * 256 + 206] = 3; + table[2 * 256 + 207] = 3; + table[2 * 256 + 208] = 3; + table[2 * 256 + 209] = 3; + table[2 * 256 + 210] = 3; + table[2 * 256 + 211] = 3; + table[2 * 256 + 212] = 3; + table[2 * 256 + 213] = 3; + table[2 * 256 + 214] = 3; + table[2 * 256 + 215] = 3; + table[2 * 256 + 216] = 3; + table[2 * 256 + 217] = 3; + table[2 * 256 + 218] = 3; + table[2 * 256 + 219] = 3; + table[2 * 256 + 220] = 3; + table[2 * 256 + 221] = 3; + table[2 * 256 + 222] = 3; + table[2 * 256 + 223] = 3; + table[2 * 256 + 224] = 4; + table[2 * 256 + 225] = 5; + table[2 * 256 + 226] = 5; + table[2 * 256 + 227] = 5; + table[2 * 256 + 228] = 5; + table[2 * 256 + 229] = 5; + table[2 * 256 + 230] = 5; + table[2 * 256 + 231] = 5; + table[2 * 256 + 232] = 5; + table[2 * 256 + 233] = 5; + table[2 * 256 + 234] = 5; + table[2 * 256 + 235] = 5; + table[2 * 256 + 236] = 5; + table[2 * 256 + 238] = 5; + table[2 * 256 + 239] = 5; + table[2 * 256 + 237] = 6; + table[2 * 256 + 240] = 7; + table[2 * 256 + 241] = 8; + table[2 * 256 + 242] = 8; + table[2 * 256 + 243] = 8; + table[2 * 256 + 244] = 9; + table[2 * 256 + 60] = 10; + table[3 * 256 + 128] = 2; + table[3 * 256 + 129] = 2; + table[3 * 256 + 130] = 2; + table[3 * 256 + 131] = 2; + table[3 * 256 + 132] = 2; + table[3 * 256 + 133] = 2; + table[3 * 256 + 134] = 2; + table[3 * 256 + 135] = 2; + table[3 * 256 + 136] = 2; + table[3 * 256 + 137] = 2; + table[3 * 256 + 138] = 2; + table[3 * 256 + 139] = 2; + table[3 * 256 + 140] = 2; + table[3 * 256 + 141] = 2; + table[3 * 256 + 142] = 2; + table[3 * 256 + 143] = 2; + table[3 * 256 + 144] = 2; + table[3 * 256 + 145] = 2; + table[3 * 256 + 146] = 2; + table[3 * 256 + 147] = 2; + table[3 * 256 + 148] = 2; + table[3 * 256 + 149] = 2; + table[3 * 256 + 150] = 2; + table[3 * 256 + 151] = 2; + table[3 * 256 + 152] = 2; + table[3 * 256 + 153] = 2; + table[3 * 256 + 154] = 2; + table[3 * 256 + 155] = 2; + table[3 * 256 + 156] = 2; + table[3 * 256 + 157] = 2; + table[3 * 256 + 158] = 2; + table[3 * 256 + 159] = 2; + table[3 * 256 + 160] = 2; + table[3 * 256 + 161] = 2; + table[3 * 256 + 162] = 2; + table[3 * 256 + 163] = 2; + table[3 * 256 + 164] = 2; + table[3 * 256 + 165] = 2; + table[3 * 256 + 166] = 2; + table[3 * 256 + 167] = 2; + table[3 * 256 + 168] = 2; + table[3 * 256 + 169] = 2; + table[3 * 256 + 170] = 2; + table[3 * 256 + 171] = 2; + table[3 * 256 + 172] = 2; + table[3 * 256 + 173] = 2; + table[3 * 256 + 174] = 2; + table[3 * 256 + 175] = 2; + table[3 * 256 + 176] = 2; + table[3 * 256 + 177] = 2; + table[3 * 256 + 178] = 2; + table[3 * 256 + 179] = 2; + table[3 * 256 + 180] = 2; + table[3 * 256 + 181] = 2; + table[3 * 256 + 182] = 2; + table[3 * 256 + 183] = 2; + table[3 * 256 + 184] = 2; + table[3 * 256 + 185] = 2; + table[3 * 256 + 186] = 2; + table[3 * 256 + 187] = 2; + table[3 * 256 + 188] = 2; + table[3 * 256 + 189] = 2; + table[3 * 256 + 190] = 2; + table[3 * 256 + 191] = 2; + table[4 * 256 + 160] = 3; + table[4 * 256 + 161] = 3; + table[4 * 256 + 162] = 3; + table[4 * 256 + 163] = 3; + table[4 * 256 + 164] = 3; + table[4 * 256 + 165] = 3; + table[4 * 256 + 166] = 3; + table[4 * 256 + 167] = 3; + table[4 * 256 + 168] = 3; + table[4 * 256 + 169] = 3; + table[4 * 256 + 170] = 3; + table[4 * 256 + 171] = 3; + table[4 * 256 + 172] = 3; + table[4 * 256 + 173] = 3; + table[4 * 256 + 174] = 3; + table[4 * 256 + 175] = 3; + table[4 * 256 + 176] = 3; + table[4 * 256 + 177] = 3; + table[4 * 256 + 178] = 3; + table[4 * 256 + 179] = 3; + table[4 * 256 + 180] = 3; + table[4 * 256 + 181] = 3; + table[4 * 256 + 182] = 3; + table[4 * 256 + 183] = 3; + table[4 * 256 + 184] = 3; + table[4 * 256 + 185] = 3; + table[4 * 256 + 186] = 3; + table[4 * 256 + 187] = 3; + table[4 * 256 + 188] = 3; + table[4 * 256 + 189] = 3; + table[4 * 256 + 190] = 3; + table[4 * 256 + 191] = 3; + table[5 * 256 + 128] = 3; + table[5 * 256 + 129] = 3; + table[5 * 256 + 130] = 3; + table[5 * 256 + 131] = 3; + table[5 * 256 + 132] = 3; + table[5 * 256 + 133] = 3; + table[5 * 256 + 134] = 3; + table[5 * 256 + 135] = 3; + table[5 * 256 + 136] = 3; + table[5 * 256 + 137] = 3; + table[5 * 256 + 138] = 3; + table[5 * 256 + 139] = 3; + table[5 * 256 + 140] = 3; + table[5 * 256 + 141] = 3; + table[5 * 256 + 142] = 3; + table[5 * 256 + 143] = 3; + table[5 * 256 + 144] = 3; + table[5 * 256 + 145] = 3; + table[5 * 256 + 146] = 3; + table[5 * 256 + 147] = 3; + table[5 * 256 + 148] = 3; + table[5 * 256 + 149] = 3; + table[5 * 256 + 150] = 3; + table[5 * 256 + 151] = 3; + table[5 * 256 + 152] = 3; + table[5 * 256 + 153] = 3; + table[5 * 256 + 154] = 3; + table[5 * 256 + 155] = 3; + table[5 * 256 + 156] = 3; + table[5 * 256 + 157] = 3; + table[5 * 256 + 158] = 3; + table[5 * 256 + 159] = 3; + table[5 * 256 + 160] = 3; + table[5 * 256 + 161] = 3; + table[5 * 256 + 162] = 3; + table[5 * 256 + 163] = 3; + table[5 * 256 + 164] = 3; + table[5 * 256 + 165] = 3; + table[5 * 256 + 166] = 3; + table[5 * 256 + 167] = 3; + table[5 * 256 + 168] = 3; + table[5 * 256 + 169] = 3; + table[5 * 256 + 170] = 3; + table[5 * 256 + 171] = 3; + table[5 * 256 + 172] = 3; + table[5 * 256 + 173] = 3; + table[5 * 256 + 174] = 3; + table[5 * 256 + 175] = 3; + table[5 * 256 + 176] = 3; + table[5 * 256 + 177] = 3; + table[5 * 256 + 178] = 3; + table[5 * 256 + 179] = 3; + table[5 * 256 + 180] = 3; + table[5 * 256 + 181] = 3; + table[5 * 256 + 182] = 3; + table[5 * 256 + 183] = 3; + table[5 * 256 + 184] = 3; + table[5 * 256 + 185] = 3; + table[5 * 256 + 186] = 3; + table[5 * 256 + 187] = 3; + table[5 * 256 + 188] = 3; + table[5 * 256 + 189] = 3; + table[5 * 256 + 190] = 3; + table[5 * 256 + 191] = 3; + table[6 * 256 + 128] = 3; + table[6 * 256 + 129] = 3; + table[6 * 256 + 130] = 3; + table[6 * 256 + 131] = 3; + table[6 * 256 + 132] = 3; + table[6 * 256 + 133] = 3; + table[6 * 256 + 134] = 3; + table[6 * 256 + 135] = 3; + table[6 * 256 + 136] = 3; + table[6 * 256 + 137] = 3; + table[6 * 256 + 138] = 3; + table[6 * 256 + 139] = 3; + table[6 * 256 + 140] = 3; + table[6 * 256 + 141] = 3; + table[6 * 256 + 142] = 3; + table[6 * 256 + 143] = 3; + table[6 * 256 + 144] = 3; + table[6 * 256 + 145] = 3; + table[6 * 256 + 146] = 3; + table[6 * 256 + 147] = 3; + table[6 * 256 + 148] = 3; + table[6 * 256 + 149] = 3; + table[6 * 256 + 150] = 3; + table[6 * 256 + 151] = 3; + table[6 * 256 + 152] = 3; + table[6 * 256 + 153] = 3; + table[6 * 256 + 154] = 3; + table[6 * 256 + 155] = 3; + table[6 * 256 + 156] = 3; + table[6 * 256 + 157] = 3; + table[6 * 256 + 158] = 3; + table[6 * 256 + 159] = 3; + table[7 * 256 + 144] = 5; + table[7 * 256 + 145] = 5; + table[7 * 256 + 146] = 5; + table[7 * 256 + 147] = 5; + table[7 * 256 + 148] = 5; + table[7 * 256 + 149] = 5; + table[7 * 256 + 150] = 5; + table[7 * 256 + 151] = 5; + table[7 * 256 + 152] = 5; + table[7 * 256 + 153] = 5; + table[7 * 256 + 154] = 5; + table[7 * 256 + 155] = 5; + table[7 * 256 + 156] = 5; + table[7 * 256 + 157] = 5; + table[7 * 256 + 158] = 5; + table[7 * 256 + 159] = 5; + table[7 * 256 + 160] = 5; + table[7 * 256 + 161] = 5; + table[7 * 256 + 162] = 5; + table[7 * 256 + 163] = 5; + table[7 * 256 + 164] = 5; + table[7 * 256 + 165] = 5; + table[7 * 256 + 166] = 5; + table[7 * 256 + 167] = 5; + table[7 * 256 + 168] = 5; + table[7 * 256 + 169] = 5; + table[7 * 256 + 170] = 5; + table[7 * 256 + 171] = 5; + table[7 * 256 + 172] = 5; + table[7 * 256 + 173] = 5; + table[7 * 256 + 174] = 5; + table[7 * 256 + 175] = 5; + table[7 * 256 + 176] = 5; + table[7 * 256 + 177] = 5; + table[7 * 256 + 178] = 5; + table[7 * 256 + 179] = 5; + table[7 * 256 + 180] = 5; + table[7 * 256 + 181] = 5; + table[7 * 256 + 182] = 5; + table[7 * 256 + 183] = 5; + table[7 * 256 + 184] = 5; + table[7 * 256 + 185] = 5; + table[7 * 256 + 186] = 5; + table[7 * 256 + 187] = 5; + table[7 * 256 + 188] = 5; + table[7 * 256 + 189] = 5; + table[7 * 256 + 190] = 5; + table[7 * 256 + 191] = 5; + table[8 * 256 + 128] = 5; + table[8 * 256 + 129] = 5; + table[8 * 256 + 130] = 5; + table[8 * 256 + 131] = 5; + table[8 * 256 + 132] = 5; + table[8 * 256 + 133] = 5; + table[8 * 256 + 134] = 5; + table[8 * 256 + 135] = 5; + table[8 * 256 + 136] = 5; + table[8 * 256 + 137] = 5; + table[8 * 256 + 138] = 5; + table[8 * 256 + 139] = 5; + table[8 * 256 + 140] = 5; + table[8 * 256 + 141] = 5; + table[8 * 256 + 142] = 5; + table[8 * 256 + 143] = 5; + table[8 * 256 + 144] = 5; + table[8 * 256 + 145] = 5; + table[8 * 256 + 146] = 5; + table[8 * 256 + 147] = 5; + table[8 * 256 + 148] = 5; + table[8 * 256 + 149] = 5; + table[8 * 256 + 150] = 5; + table[8 * 256 + 151] = 5; + table[8 * 256 + 152] = 5; + table[8 * 256 + 153] = 5; + table[8 * 256 + 154] = 5; + table[8 * 256 + 155] = 5; + table[8 * 256 + 156] = 5; + table[8 * 256 + 157] = 5; + table[8 * 256 + 158] = 5; + table[8 * 256 + 159] = 5; + table[8 * 256 + 160] = 5; + table[8 * 256 + 161] = 5; + table[8 * 256 + 162] = 5; + table[8 * 256 + 163] = 5; + table[8 * 256 + 164] = 5; + table[8 * 256 + 165] = 5; + table[8 * 256 + 166] = 5; + table[8 * 256 + 167] = 5; + table[8 * 256 + 168] = 5; + table[8 * 256 + 169] = 5; + table[8 * 256 + 170] = 5; + table[8 * 256 + 171] = 5; + table[8 * 256 + 172] = 5; + table[8 * 256 + 173] = 5; + table[8 * 256 + 174] = 5; + table[8 * 256 + 175] = 5; + table[8 * 256 + 176] = 5; + table[8 * 256 + 177] = 5; + table[8 * 256 + 178] = 5; + table[8 * 256 + 179] = 5; + table[8 * 256 + 180] = 5; + table[8 * 256 + 181] = 5; + table[8 * 256 + 182] = 5; + table[8 * 256 + 183] = 5; + table[8 * 256 + 184] = 5; + table[8 * 256 + 185] = 5; + table[8 * 256 + 186] = 5; + table[8 * 256 + 187] = 5; + table[8 * 256 + 188] = 5; + table[8 * 256 + 189] = 5; + table[8 * 256 + 190] = 5; + table[8 * 256 + 191] = 5; + table[9 * 256 + 128] = 5; + table[9 * 256 + 129] = 5; + table[9 * 256 + 130] = 5; + table[9 * 256 + 131] = 5; + table[9 * 256 + 132] = 5; + table[9 * 256 + 133] = 5; + table[9 * 256 + 134] = 5; + table[9 * 256 + 135] = 5; + table[9 * 256 + 136] = 5; + table[9 * 256 + 137] = 5; + table[9 * 256 + 138] = 5; + table[9 * 256 + 139] = 5; + table[9 * 256 + 140] = 5; + table[9 * 256 + 141] = 5; + table[9 * 256 + 142] = 5; + table[9 * 256 + 143] = 5; + table[10 * 256 + 0] = 10; + table[10 * 256 + 1] = 10; + table[10 * 256 + 2] = 10; + table[10 * 256 + 3] = 10; + table[10 * 256 + 4] = 10; + table[10 * 256 + 5] = 10; + table[10 * 256 + 6] = 10; + table[10 * 256 + 7] = 10; + table[10 * 256 + 8] = 10; + table[10 * 256 + 9] = 10; + table[10 * 256 + 11] = 10; + table[10 * 256 + 12] = 10; + table[10 * 256 + 13] = 10; + table[10 * 256 + 14] = 10; + table[10 * 256 + 15] = 10; + table[10 * 256 + 16] = 10; + table[10 * 256 + 17] = 10; + table[10 * 256 + 18] = 10; + table[10 * 256 + 19] = 10; + table[10 * 256 + 20] = 10; + table[10 * 256 + 21] = 10; + table[10 * 256 + 22] = 10; + table[10 * 256 + 23] = 10; + table[10 * 256 + 24] = 10; + table[10 * 256 + 25] = 10; + table[10 * 256 + 26] = 10; + table[10 * 256 + 27] = 10; + table[10 * 256 + 28] = 10; + table[10 * 256 + 29] = 10; + table[10 * 256 + 30] = 10; + table[10 * 256 + 31] = 10; + table[10 * 256 + 32] = 10; + table[10 * 256 + 33] = 10; + table[10 * 256 + 34] = 10; + table[10 * 256 + 35] = 10; + table[10 * 256 + 36] = 10; + table[10 * 256 + 37] = 10; + table[10 * 256 + 38] = 10; + table[10 * 256 + 39] = 10; + table[10 * 256 + 40] = 10; + table[10 * 256 + 41] = 10; + table[10 * 256 + 42] = 10; + table[10 * 256 + 43] = 10; + table[10 * 256 + 44] = 10; + table[10 * 256 + 45] = 10; + table[10 * 256 + 46] = 10; + table[10 * 256 + 47] = 10; + table[10 * 256 + 48] = 10; + table[10 * 256 + 49] = 10; + table[10 * 256 + 50] = 10; + table[10 * 256 + 51] = 10; + table[10 * 256 + 52] = 10; + table[10 * 256 + 53] = 10; + table[10 * 256 + 54] = 10; + table[10 * 256 + 55] = 10; + table[10 * 256 + 56] = 10; + table[10 * 256 + 57] = 10; + table[10 * 256 + 58] = 10; + table[10 * 256 + 59] = 10; + table[10 * 256 + 60] = 10; + table[10 * 256 + 61] = 10; + table[10 * 256 + 62] = 10; + table[10 * 256 + 63] = 10; + table[10 * 256 + 64] = 10; + table[10 * 256 + 65] = 10; + table[10 * 256 + 66] = 10; + table[10 * 256 + 67] = 10; + table[10 * 256 + 68] = 10; + table[10 * 256 + 69] = 10; + table[10 * 256 + 70] = 10; + table[10 * 256 + 71] = 10; + table[10 * 256 + 72] = 10; + table[10 * 256 + 73] = 10; + table[10 * 256 + 74] = 10; + table[10 * 256 + 75] = 10; + table[10 * 256 + 76] = 10; + table[10 * 256 + 77] = 10; + table[10 * 256 + 78] = 10; + table[10 * 256 + 79] = 10; + table[10 * 256 + 80] = 10; + table[10 * 256 + 81] = 10; + table[10 * 256 + 82] = 10; + table[10 * 256 + 83] = 10; + table[10 * 256 + 84] = 10; + table[10 * 256 + 85] = 10; + table[10 * 256 + 86] = 10; + table[10 * 256 + 87] = 10; + table[10 * 256 + 88] = 10; + table[10 * 256 + 89] = 10; + table[10 * 256 + 90] = 10; + table[10 * 256 + 91] = 10; + table[10 * 256 + 92] = 10; + table[10 * 256 + 93] = 10; + table[10 * 256 + 94] = 10; + table[10 * 256 + 95] = 10; + table[10 * 256 + 96] = 10; + table[10 * 256 + 97] = 10; + table[10 * 256 + 98] = 10; + table[10 * 256 + 99] = 10; + table[10 * 256 + 100] = 10; + table[10 * 256 + 101] = 10; + table[10 * 256 + 102] = 10; + table[10 * 256 + 103] = 10; + table[10 * 256 + 104] = 10; + table[10 * 256 + 105] = 10; + table[10 * 256 + 106] = 10; + table[10 * 256 + 107] = 10; + table[10 * 256 + 108] = 10; + table[10 * 256 + 109] = 10; + table[10 * 256 + 110] = 10; + table[10 * 256 + 111] = 10; + table[10 * 256 + 112] = 10; + table[10 * 256 + 113] = 10; + table[10 * 256 + 114] = 10; + table[10 * 256 + 115] = 10; + table[10 * 256 + 116] = 10; + table[10 * 256 + 117] = 10; + table[10 * 256 + 118] = 10; + table[10 * 256 + 119] = 10; + table[10 * 256 + 120] = 10; + table[10 * 256 + 121] = 10; + table[10 * 256 + 122] = 10; + table[10 * 256 + 123] = 10; + table[10 * 256 + 124] = 10; + table[10 * 256 + 125] = 10; + table[10 * 256 + 126] = 10; + table[10 * 256 + 127] = 10; + table[10 * 256 + 194] = 11; + table[10 * 256 + 195] = 11; + table[10 * 256 + 196] = 11; + table[10 * 256 + 197] = 11; + table[10 * 256 + 198] = 11; + table[10 * 256 + 199] = 11; + table[10 * 256 + 200] = 11; + table[10 * 256 + 201] = 11; + table[10 * 256 + 202] = 11; + table[10 * 256 + 203] = 11; + table[10 * 256 + 204] = 11; + table[10 * 256 + 205] = 11; + table[10 * 256 + 206] = 11; + table[10 * 256 + 207] = 11; + table[10 * 256 + 208] = 11; + table[10 * 256 + 209] = 11; + table[10 * 256 + 210] = 11; + table[10 * 256 + 211] = 11; + table[10 * 256 + 212] = 11; + table[10 * 256 + 213] = 11; + table[10 * 256 + 214] = 11; + table[10 * 256 + 215] = 11; + table[10 * 256 + 216] = 11; + table[10 * 256 + 217] = 11; + table[10 * 256 + 218] = 11; + table[10 * 256 + 219] = 11; + table[10 * 256 + 220] = 11; + table[10 * 256 + 221] = 11; + table[10 * 256 + 222] = 11; + table[10 * 256 + 223] = 11; + table[10 * 256 + 224] = 12; + table[10 * 256 + 225] = 13; + table[10 * 256 + 226] = 13; + table[10 * 256 + 227] = 13; + table[10 * 256 + 228] = 13; + table[10 * 256 + 229] = 13; + table[10 * 256 + 230] = 13; + table[10 * 256 + 231] = 13; + table[10 * 256 + 232] = 13; + table[10 * 256 + 233] = 13; + table[10 * 256 + 234] = 13; + table[10 * 256 + 235] = 13; + table[10 * 256 + 236] = 13; + table[10 * 256 + 238] = 13; + table[10 * 256 + 239] = 13; + table[10 * 256 + 237] = 14; + table[10 * 256 + 240] = 15; + table[10 * 256 + 241] = 16; + table[10 * 256 + 242] = 16; + table[10 * 256 + 243] = 16; + table[10 * 256 + 244] = 17; + table[11 * 256 + 128] = 10; + table[11 * 256 + 129] = 10; + table[11 * 256 + 130] = 10; + table[11 * 256 + 131] = 10; + table[11 * 256 + 132] = 10; + table[11 * 256 + 133] = 10; + table[11 * 256 + 134] = 10; + table[11 * 256 + 135] = 10; + table[11 * 256 + 136] = 10; + table[11 * 256 + 137] = 10; + table[11 * 256 + 138] = 10; + table[11 * 256 + 139] = 10; + table[11 * 256 + 140] = 10; + table[11 * 256 + 141] = 10; + table[11 * 256 + 142] = 10; + table[11 * 256 + 143] = 10; + table[11 * 256 + 144] = 10; + table[11 * 256 + 145] = 10; + table[11 * 256 + 146] = 10; + table[11 * 256 + 147] = 10; + table[11 * 256 + 148] = 10; + table[11 * 256 + 149] = 10; + table[11 * 256 + 150] = 10; + table[11 * 256 + 151] = 10; + table[11 * 256 + 152] = 10; + table[11 * 256 + 153] = 10; + table[11 * 256 + 154] = 10; + table[11 * 256 + 155] = 10; + table[11 * 256 + 156] = 10; + table[11 * 256 + 157] = 10; + table[11 * 256 + 158] = 10; + table[11 * 256 + 159] = 10; + table[11 * 256 + 160] = 10; + table[11 * 256 + 161] = 10; + table[11 * 256 + 162] = 10; + table[11 * 256 + 163] = 10; + table[11 * 256 + 164] = 10; + table[11 * 256 + 165] = 10; + table[11 * 256 + 166] = 10; + table[11 * 256 + 167] = 10; + table[11 * 256 + 168] = 10; + table[11 * 256 + 169] = 10; + table[11 * 256 + 170] = 10; + table[11 * 256 + 171] = 10; + table[11 * 256 + 172] = 10; + table[11 * 256 + 173] = 10; + table[11 * 256 + 174] = 10; + table[11 * 256 + 175] = 10; + table[11 * 256 + 176] = 10; + table[11 * 256 + 177] = 10; + table[11 * 256 + 178] = 10; + table[11 * 256 + 179] = 10; + table[11 * 256 + 180] = 10; + table[11 * 256 + 181] = 10; + table[11 * 256 + 182] = 10; + table[11 * 256 + 183] = 10; + table[11 * 256 + 184] = 10; + table[11 * 256 + 185] = 10; + table[11 * 256 + 186] = 10; + table[11 * 256 + 187] = 10; + table[11 * 256 + 188] = 10; + table[11 * 256 + 189] = 10; + table[11 * 256 + 190] = 10; + table[11 * 256 + 191] = 10; + table[12 * 256 + 160] = 11; + table[12 * 256 + 161] = 11; + table[12 * 256 + 162] = 11; + table[12 * 256 + 163] = 11; + table[12 * 256 + 164] = 11; + table[12 * 256 + 165] = 11; + table[12 * 256 + 166] = 11; + table[12 * 256 + 167] = 11; + table[12 * 256 + 168] = 11; + table[12 * 256 + 169] = 11; + table[12 * 256 + 170] = 11; + table[12 * 256 + 171] = 11; + table[12 * 256 + 172] = 11; + table[12 * 256 + 173] = 11; + table[12 * 256 + 174] = 11; + table[12 * 256 + 175] = 11; + table[12 * 256 + 176] = 11; + table[12 * 256 + 177] = 11; + table[12 * 256 + 178] = 11; + table[12 * 256 + 179] = 11; + table[12 * 256 + 180] = 11; + table[12 * 256 + 181] = 11; + table[12 * 256 + 182] = 11; + table[12 * 256 + 183] = 11; + table[12 * 256 + 184] = 11; + table[12 * 256 + 185] = 11; + table[12 * 256 + 186] = 11; + table[12 * 256 + 187] = 11; + table[12 * 256 + 188] = 11; + table[12 * 256 + 189] = 11; + table[12 * 256 + 190] = 11; + table[12 * 256 + 191] = 11; + table[13 * 256 + 128] = 11; + table[13 * 256 + 129] = 11; + table[13 * 256 + 130] = 11; + table[13 * 256 + 131] = 11; + table[13 * 256 + 132] = 11; + table[13 * 256 + 133] = 11; + table[13 * 256 + 134] = 11; + table[13 * 256 + 135] = 11; + table[13 * 256 + 136] = 11; + table[13 * 256 + 137] = 11; + table[13 * 256 + 138] = 11; + table[13 * 256 + 139] = 11; + table[13 * 256 + 140] = 11; + table[13 * 256 + 141] = 11; + table[13 * 256 + 142] = 11; + table[13 * 256 + 143] = 11; + table[13 * 256 + 144] = 11; + table[13 * 256 + 145] = 11; + table[13 * 256 + 146] = 11; + table[13 * 256 + 147] = 11; + table[13 * 256 + 148] = 11; + table[13 * 256 + 149] = 11; + table[13 * 256 + 150] = 11; + table[13 * 256 + 151] = 11; + table[13 * 256 + 152] = 11; + table[13 * 256 + 153] = 11; + table[13 * 256 + 154] = 11; + table[13 * 256 + 155] = 11; + table[13 * 256 + 156] = 11; + table[13 * 256 + 157] = 11; + table[13 * 256 + 158] = 11; + table[13 * 256 + 159] = 11; + table[13 * 256 + 160] = 11; + table[13 * 256 + 161] = 11; + table[13 * 256 + 162] = 11; + table[13 * 256 + 163] = 11; + table[13 * 256 + 164] = 11; + table[13 * 256 + 165] = 11; + table[13 * 256 + 166] = 11; + table[13 * 256 + 167] = 11; + table[13 * 256 + 168] = 11; + table[13 * 256 + 169] = 11; + table[13 * 256 + 170] = 11; + table[13 * 256 + 171] = 11; + table[13 * 256 + 172] = 11; + table[13 * 256 + 173] = 11; + table[13 * 256 + 174] = 11; + table[13 * 256 + 175] = 11; + table[13 * 256 + 176] = 11; + table[13 * 256 + 177] = 11; + table[13 * 256 + 178] = 11; + table[13 * 256 + 179] = 11; + table[13 * 256 + 180] = 11; + table[13 * 256 + 181] = 11; + table[13 * 256 + 182] = 11; + table[13 * 256 + 183] = 11; + table[13 * 256 + 184] = 11; + table[13 * 256 + 185] = 11; + table[13 * 256 + 186] = 11; + table[13 * 256 + 187] = 11; + table[13 * 256 + 188] = 11; + table[13 * 256 + 189] = 11; + table[13 * 256 + 190] = 11; + table[13 * 256 + 191] = 11; + table[14 * 256 + 128] = 11; + table[14 * 256 + 129] = 11; + table[14 * 256 + 130] = 11; + table[14 * 256 + 131] = 11; + table[14 * 256 + 132] = 11; + table[14 * 256 + 133] = 11; + table[14 * 256 + 134] = 11; + table[14 * 256 + 135] = 11; + table[14 * 256 + 136] = 11; + table[14 * 256 + 137] = 11; + table[14 * 256 + 138] = 11; + table[14 * 256 + 139] = 11; + table[14 * 256 + 140] = 11; + table[14 * 256 + 141] = 11; + table[14 * 256 + 142] = 11; + table[14 * 256 + 143] = 11; + table[14 * 256 + 144] = 11; + table[14 * 256 + 145] = 11; + table[14 * 256 + 146] = 11; + table[14 * 256 + 147] = 11; + table[14 * 256 + 148] = 11; + table[14 * 256 + 149] = 11; + table[14 * 256 + 150] = 11; + table[14 * 256 + 151] = 11; + table[14 * 256 + 152] = 11; + table[14 * 256 + 153] = 11; + table[14 * 256 + 154] = 11; + table[14 * 256 + 155] = 11; + table[14 * 256 + 156] = 11; + table[14 * 256 + 157] = 11; + table[14 * 256 + 158] = 11; + table[14 * 256 + 159] = 11; + table[15 * 256 + 144] = 13; + table[15 * 256 + 145] = 13; + table[15 * 256 + 146] = 13; + table[15 * 256 + 147] = 13; + table[15 * 256 + 148] = 13; + table[15 * 256 + 149] = 13; + table[15 * 256 + 150] = 13; + table[15 * 256 + 151] = 13; + table[15 * 256 + 152] = 13; + table[15 * 256 + 153] = 13; + table[15 * 256 + 154] = 13; + table[15 * 256 + 155] = 13; + table[15 * 256 + 156] = 13; + table[15 * 256 + 157] = 13; + table[15 * 256 + 158] = 13; + table[15 * 256 + 159] = 13; + table[15 * 256 + 160] = 13; + table[15 * 256 + 161] = 13; + table[15 * 256 + 162] = 13; + table[15 * 256 + 163] = 13; + table[15 * 256 + 164] = 13; + table[15 * 256 + 165] = 13; + table[15 * 256 + 166] = 13; + table[15 * 256 + 167] = 13; + table[15 * 256 + 168] = 13; + table[15 * 256 + 169] = 13; + table[15 * 256 + 170] = 13; + table[15 * 256 + 171] = 13; + table[15 * 256 + 172] = 13; + table[15 * 256 + 173] = 13; + table[15 * 256 + 174] = 13; + table[15 * 256 + 175] = 13; + table[15 * 256 + 176] = 13; + table[15 * 256 + 177] = 13; + table[15 * 256 + 178] = 13; + table[15 * 256 + 179] = 13; + table[15 * 256 + 180] = 13; + table[15 * 256 + 181] = 13; + table[15 * 256 + 182] = 13; + table[15 * 256 + 183] = 13; + table[15 * 256 + 184] = 13; + table[15 * 256 + 185] = 13; + table[15 * 256 + 186] = 13; + table[15 * 256 + 187] = 13; + table[15 * 256 + 188] = 13; + table[15 * 256 + 189] = 13; + table[15 * 256 + 190] = 13; + table[15 * 256 + 191] = 13; + table[16 * 256 + 128] = 13; + table[16 * 256 + 129] = 13; + table[16 * 256 + 130] = 13; + table[16 * 256 + 131] = 13; + table[16 * 256 + 132] = 13; + table[16 * 256 + 133] = 13; + table[16 * 256 + 134] = 13; + table[16 * 256 + 135] = 13; + table[16 * 256 + 136] = 13; + table[16 * 256 + 137] = 13; + table[16 * 256 + 138] = 13; + table[16 * 256 + 139] = 13; + table[16 * 256 + 140] = 13; + table[16 * 256 + 141] = 13; + table[16 * 256 + 142] = 13; + table[16 * 256 + 143] = 13; + table[16 * 256 + 144] = 13; + table[16 * 256 + 145] = 13; + table[16 * 256 + 146] = 13; + table[16 * 256 + 147] = 13; + table[16 * 256 + 148] = 13; + table[16 * 256 + 149] = 13; + table[16 * 256 + 150] = 13; + table[16 * 256 + 151] = 13; + table[16 * 256 + 152] = 13; + table[16 * 256 + 153] = 13; + table[16 * 256 + 154] = 13; + table[16 * 256 + 155] = 13; + table[16 * 256 + 156] = 13; + table[16 * 256 + 157] = 13; + table[16 * 256 + 158] = 13; + table[16 * 256 + 159] = 13; + table[16 * 256 + 160] = 13; + table[16 * 256 + 161] = 13; + table[16 * 256 + 162] = 13; + table[16 * 256 + 163] = 13; + table[16 * 256 + 164] = 13; + table[16 * 256 + 165] = 13; + table[16 * 256 + 166] = 13; + table[16 * 256 + 167] = 13; + table[16 * 256 + 168] = 13; + table[16 * 256 + 169] = 13; + table[16 * 256 + 170] = 13; + table[16 * 256 + 171] = 13; + table[16 * 256 + 172] = 13; + table[16 * 256 + 173] = 13; + table[16 * 256 + 174] = 13; + table[16 * 256 + 175] = 13; + table[16 * 256 + 176] = 13; + table[16 * 256 + 177] = 13; + table[16 * 256 + 178] = 13; + table[16 * 256 + 179] = 13; + table[16 * 256 + 180] = 13; + table[16 * 256 + 181] = 13; + table[16 * 256 + 182] = 13; + table[16 * 256 + 183] = 13; + table[16 * 256 + 184] = 13; + table[16 * 256 + 185] = 13; + table[16 * 256 + 186] = 13; + table[16 * 256 + 187] = 13; + table[16 * 256 + 188] = 13; + table[16 * 256 + 189] = 13; + table[16 * 256 + 190] = 13; + table[16 * 256 + 191] = 13; + table[17 * 256 + 128] = 13; + table[17 * 256 + 129] = 13; + table[17 * 256 + 130] = 13; + table[17 * 256 + 131] = 13; + table[17 * 256 + 132] = 13; + table[17 * 256 + 133] = 13; + table[17 * 256 + 134] = 13; + table[17 * 256 + 135] = 13; + table[17 * 256 + 136] = 13; + table[17 * 256 + 137] = 13; + table[17 * 256 + 138] = 13; + table[17 * 256 + 139] = 13; + table[17 * 256 + 140] = 13; + table[17 * 256 + 141] = 13; + table[17 * 256 + 142] = 13; + table[17 * 256 + 143] = 13; + + table +} + + +pub fn regex_match(input: [u8; N]) -> (BoundedVec, bool) { + let substrings = unsafe { __regex_match(input) }; + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + let mut start_range = 0; + let mut end_range = 0; + + // check the match + for i in 0..N { + // state transition + let temp = input[i] as Field; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + s = 0; + s_next = potential_s_next; + } + std::as_witness(s_next); + + // range conditions for substring matches + if ((start_range == 0) & (end_range == 0)) { + start_range = i as Field; + } + if (((s == 10) & (s_next == 18)) & (end_range == 0)) { + end_range = i as Field + 1; + } + + + let range_0 = substrings.get_unchecked(0).in_range(i); + let case_0 = [ + (s == 1) & ((s_next == 2) | (s_next == 3) | (s_next == 4) | (s_next == 5) | (s_next == 6) | (s_next == 7) | (s_next == 8) | (s_next == 9)), + (s == 2) & ((s_next == 2) | (s_next == 3) | (s_next == 4) | (s_next == 5) | (s_next == 6) | (s_next == 7) | (s_next == 8) | (s_next == 9)), + (s_next == 2) & ((s == 3)), + (s_next == 3) & ((s == 4) | (s == 5) | (s == 6)), + (s_next == 5) & ((s == 7) | (s == 8) | (s == 9)) + ].any(|case| case == true) | !range_0; + + + + let substring_range_check = [case_0] + .all(|case| case == true); + + assert(substring_range_check, "substr array ranges wrong"); + + + s = s_next; + } + // check final state + + let matched: bool = (s == 10) | (s == 18); + + // constrain extracted substrings to be in match range + //let full_match = Sequence::new(start_range as u32, end_range as u32 - start_range as u32); + //let full_match_end = full_match.end(); + // for i in 0..1 { + // let substring = substrings.get_unchecked(i); + // let is_not_valid = i >= substrings.len(); + // let index_check = substring.index >= full_match.index; + // let length_check = substring.end() <= full_match_end; + // let check = (index_check) | is_not_valid; + // assert(check, f"Substring {i} range is out of bounds of the full match found"); + // } + (substrings, matched) +} + + +pub unconstrained fn __regex_match(input: [u8; N]) -> BoundedVec { + // regex: >[^<>]+<.* + let mut substrings: BoundedVec = BoundedVec::new(); + let mut current_substring = Sequence::default(); + let mut full_match = Sequence::default(); + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + + let mut consecutive_substr = 0; + let mut complete = false; + + for i in 0..input.len() { + let temp = input[i] as Field; + let mut reset = false; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + reset = true; + s = 0; + s_next = potential_s_next; + } + // If a substring was in the making, but the state was reset + // we disregard previous progress because apparently it is invalid + if (reset & (consecutive_substr == 1)) { + current_substring = Sequence::default(); + consecutive_substr = 0; + } + // Fill up substrings + + + if ((s == 1) & (s_next == 2) | (s == 1) & (s_next == 3) | (s == 1) & (s_next == 4) | (s == 1) & (s_next == 5) | (s == 1) & (s_next == 6) | (s == 1) & (s_next == 7) | (s == 1) & (s_next == 8) | (s == 1) & (s_next == 9) | (s == 2) & (s_next == 2) | (s == 2) & (s_next == 3) | (s == 2) & (s_next == 4) | (s == 2) & (s_next == 5) | (s == 2) & (s_next == 6) | (s == 2) & (s_next == 7) | (s == 2) & (s_next == 8) | (s == 2) & (s_next == 9) | (s == 3) & (s_next == 2) | (s == 4) & (s_next == 3) | (s == 5) & (s_next == 3) | (s == 6) & (s_next == 3) | (s == 7) & (s_next == 5) | (s == 8) & (s_next == 5) | (s == 9) & (s_next == 5)) { + + if (consecutive_substr == 0) { + current_substring.index = i; + }; + current_substring.length += 1; + consecutive_substr = 1; + } else if ((consecutive_substr == 1) & (s_next == 0)) { + current_substring = Sequence::default(); + full_match = Sequence::default(); + substrings = BoundedVec::new(); + consecutive_substr = 0; + } else if (s == 10) & (s_next == 18) { + full_match.length = i - full_match.index + 1; + complete = true; + } else if (consecutive_substr == 1) { + // The substring is done so "save" it + substrings.push(current_substring); + // reset the substring holder for next use + current_substring = Sequence::default(); + consecutive_substr = 0; + } + s = s_next; + if complete == true { + break; + } + } + assert((s == 10) | (s == 18), f"no match: {s}"); + // Add pending substring that hasn't been added + if consecutive_substr == 1 { + substrings.push(current_substring); + full_match.length = input.len() - full_match.index; + } + + + + substrings +} + + + + \ No newline at end of file diff --git a/packages/noir/src/capture/raw/subject_all.nr b/packages/noir/src/capture/raw/subject_all.nr new file mode 100644 index 00000000..fb8bc4ff --- /dev/null +++ b/packages/noir/src/capture/raw/subject_all.nr @@ -0,0 +1,1356 @@ + +use crate::common::Sequence; + + +global table: [Field; 5632] = comptime { make_lookup_table() }; + +comptime fn make_lookup_table() -> [Field; 5632] { + let mut table = [0; 5632]; + table[20 * 256 + 0] = 21; + table[21 * 256 + 0] = 21; + table[20 * 256 + 1] = 21; + table[21 * 256 + 1] = 21; + table[20 * 256 + 2] = 21; + table[21 * 256 + 2] = 21; + table[20 * 256 + 3] = 21; + table[21 * 256 + 3] = 21; + table[20 * 256 + 4] = 21; + table[21 * 256 + 4] = 21; + table[20 * 256 + 5] = 21; + table[21 * 256 + 5] = 21; + table[20 * 256 + 6] = 21; + table[21 * 256 + 6] = 21; + table[20 * 256 + 7] = 21; + table[21 * 256 + 7] = 21; + table[20 * 256 + 8] = 21; + table[21 * 256 + 8] = 21; + table[20 * 256 + 9] = 21; + table[21 * 256 + 9] = 21; + table[20 * 256 + 10] = 21; + table[21 * 256 + 10] = 21; + table[20 * 256 + 11] = 21; + table[21 * 256 + 11] = 21; + table[20 * 256 + 12] = 21; + table[21 * 256 + 12] = 21; + table[20 * 256 + 13] = 21; + table[21 * 256 + 13] = 21; + table[20 * 256 + 14] = 21; + table[21 * 256 + 14] = 21; + table[20 * 256 + 15] = 21; + table[21 * 256 + 15] = 21; + table[20 * 256 + 16] = 21; + table[21 * 256 + 16] = 21; + table[20 * 256 + 17] = 21; + table[21 * 256 + 17] = 21; + table[20 * 256 + 18] = 21; + table[21 * 256 + 18] = 21; + table[20 * 256 + 19] = 21; + table[21 * 256 + 19] = 21; + table[20 * 256 + 20] = 21; + table[21 * 256 + 20] = 21; + table[20 * 256 + 21] = 21; + table[21 * 256 + 21] = 21; + table[20 * 256 + 22] = 21; + table[21 * 256 + 22] = 21; + table[20 * 256 + 23] = 21; + table[21 * 256 + 23] = 21; + table[20 * 256 + 24] = 21; + table[21 * 256 + 24] = 21; + table[20 * 256 + 25] = 21; + table[21 * 256 + 25] = 21; + table[20 * 256 + 26] = 21; + table[21 * 256 + 26] = 21; + table[20 * 256 + 27] = 21; + table[21 * 256 + 27] = 21; + table[20 * 256 + 28] = 21; + table[21 * 256 + 28] = 21; + table[20 * 256 + 29] = 21; + table[21 * 256 + 29] = 21; + table[20 * 256 + 30] = 21; + table[21 * 256 + 30] = 21; + table[20 * 256 + 31] = 21; + table[21 * 256 + 31] = 21; + table[20 * 256 + 32] = 21; + table[21 * 256 + 32] = 21; + table[20 * 256 + 33] = 21; + table[21 * 256 + 33] = 21; + table[20 * 256 + 34] = 21; + table[21 * 256 + 34] = 21; + table[20 * 256 + 35] = 21; + table[21 * 256 + 35] = 21; + table[20 * 256 + 36] = 21; + table[21 * 256 + 36] = 21; + table[20 * 256 + 37] = 21; + table[21 * 256 + 37] = 21; + table[20 * 256 + 38] = 21; + table[21 * 256 + 38] = 21; + table[20 * 256 + 39] = 21; + table[21 * 256 + 39] = 21; + table[20 * 256 + 40] = 21; + table[21 * 256 + 40] = 21; + table[20 * 256 + 41] = 21; + table[21 * 256 + 41] = 21; + table[20 * 256 + 42] = 21; + table[21 * 256 + 42] = 21; + table[20 * 256 + 43] = 21; + table[21 * 256 + 43] = 21; + table[20 * 256 + 44] = 21; + table[21 * 256 + 44] = 21; + table[20 * 256 + 45] = 21; + table[21 * 256 + 45] = 21; + table[20 * 256 + 46] = 21; + table[21 * 256 + 46] = 21; + table[20 * 256 + 47] = 21; + table[21 * 256 + 47] = 21; + table[20 * 256 + 48] = 21; + table[21 * 256 + 48] = 21; + table[20 * 256 + 49] = 21; + table[21 * 256 + 49] = 21; + table[20 * 256 + 50] = 21; + table[21 * 256 + 50] = 21; + table[20 * 256 + 51] = 21; + table[21 * 256 + 51] = 21; + table[20 * 256 + 52] = 21; + table[21 * 256 + 52] = 21; + table[20 * 256 + 53] = 21; + table[21 * 256 + 53] = 21; + table[20 * 256 + 54] = 21; + table[21 * 256 + 54] = 21; + table[20 * 256 + 55] = 21; + table[21 * 256 + 55] = 21; + table[20 * 256 + 56] = 21; + table[21 * 256 + 56] = 21; + table[20 * 256 + 57] = 21; + table[21 * 256 + 57] = 21; + table[20 * 256 + 58] = 21; + table[21 * 256 + 58] = 21; + table[20 * 256 + 59] = 21; + table[21 * 256 + 59] = 21; + table[20 * 256 + 60] = 21; + table[21 * 256 + 60] = 21; + table[20 * 256 + 61] = 21; + table[21 * 256 + 61] = 21; + table[20 * 256 + 62] = 21; + table[21 * 256 + 62] = 21; + table[20 * 256 + 63] = 21; + table[21 * 256 + 63] = 21; + table[20 * 256 + 64] = 21; + table[21 * 256 + 64] = 21; + table[20 * 256 + 65] = 21; + table[21 * 256 + 65] = 21; + table[20 * 256 + 66] = 21; + table[21 * 256 + 66] = 21; + table[20 * 256 + 67] = 21; + table[21 * 256 + 67] = 21; + table[20 * 256 + 68] = 21; + table[21 * 256 + 68] = 21; + table[20 * 256 + 69] = 21; + table[21 * 256 + 69] = 21; + table[20 * 256 + 70] = 21; + table[21 * 256 + 70] = 21; + table[20 * 256 + 71] = 21; + table[21 * 256 + 71] = 21; + table[20 * 256 + 72] = 21; + table[21 * 256 + 72] = 21; + table[20 * 256 + 73] = 21; + table[21 * 256 + 73] = 21; + table[20 * 256 + 74] = 21; + table[21 * 256 + 74] = 21; + table[20 * 256 + 75] = 21; + table[21 * 256 + 75] = 21; + table[20 * 256 + 76] = 21; + table[21 * 256 + 76] = 21; + table[20 * 256 + 77] = 21; + table[21 * 256 + 77] = 21; + table[20 * 256 + 78] = 21; + table[21 * 256 + 78] = 21; + table[20 * 256 + 79] = 21; + table[21 * 256 + 79] = 21; + table[20 * 256 + 80] = 21; + table[21 * 256 + 80] = 21; + table[20 * 256 + 81] = 21; + table[21 * 256 + 81] = 21; + table[20 * 256 + 82] = 21; + table[21 * 256 + 82] = 21; + table[20 * 256 + 83] = 21; + table[21 * 256 + 83] = 21; + table[20 * 256 + 84] = 21; + table[21 * 256 + 84] = 21; + table[20 * 256 + 85] = 21; + table[21 * 256 + 85] = 21; + table[20 * 256 + 86] = 21; + table[21 * 256 + 86] = 21; + table[20 * 256 + 87] = 21; + table[21 * 256 + 87] = 21; + table[20 * 256 + 88] = 21; + table[21 * 256 + 88] = 21; + table[20 * 256 + 89] = 21; + table[21 * 256 + 89] = 21; + table[20 * 256 + 90] = 21; + table[21 * 256 + 90] = 21; + table[20 * 256 + 91] = 21; + table[21 * 256 + 91] = 21; + table[20 * 256 + 92] = 21; + table[21 * 256 + 92] = 21; + table[20 * 256 + 93] = 21; + table[21 * 256 + 93] = 21; + table[20 * 256 + 94] = 21; + table[21 * 256 + 94] = 21; + table[20 * 256 + 95] = 21; + table[21 * 256 + 95] = 21; + table[20 * 256 + 96] = 21; + table[21 * 256 + 96] = 21; + table[20 * 256 + 97] = 21; + table[21 * 256 + 97] = 21; + table[20 * 256 + 98] = 21; + table[21 * 256 + 98] = 21; + table[20 * 256 + 99] = 21; + table[21 * 256 + 99] = 21; + table[20 * 256 + 100] = 21; + table[21 * 256 + 100] = 21; + table[20 * 256 + 101] = 21; + table[21 * 256 + 101] = 21; + table[20 * 256 + 102] = 21; + table[21 * 256 + 102] = 21; + table[20 * 256 + 103] = 21; + table[21 * 256 + 103] = 21; + table[20 * 256 + 104] = 21; + table[21 * 256 + 104] = 21; + table[20 * 256 + 105] = 21; + table[21 * 256 + 105] = 21; + table[20 * 256 + 106] = 21; + table[21 * 256 + 106] = 21; + table[20 * 256 + 107] = 21; + table[21 * 256 + 107] = 21; + table[20 * 256 + 108] = 21; + table[21 * 256 + 108] = 21; + table[20 * 256 + 109] = 21; + table[21 * 256 + 109] = 21; + table[20 * 256 + 110] = 21; + table[21 * 256 + 110] = 21; + table[20 * 256 + 111] = 21; + table[21 * 256 + 111] = 21; + table[20 * 256 + 112] = 21; + table[21 * 256 + 112] = 21; + table[20 * 256 + 113] = 21; + table[21 * 256 + 113] = 21; + table[20 * 256 + 114] = 21; + table[21 * 256 + 114] = 21; + table[20 * 256 + 115] = 21; + table[21 * 256 + 115] = 21; + table[20 * 256 + 116] = 21; + table[21 * 256 + 116] = 21; + table[20 * 256 + 117] = 21; + table[21 * 256 + 117] = 21; + table[20 * 256 + 118] = 21; + table[21 * 256 + 118] = 21; + table[20 * 256 + 119] = 21; + table[21 * 256 + 119] = 21; + table[20 * 256 + 120] = 21; + table[21 * 256 + 120] = 21; + table[20 * 256 + 121] = 21; + table[21 * 256 + 121] = 21; + table[20 * 256 + 122] = 21; + table[21 * 256 + 122] = 21; + table[20 * 256 + 123] = 21; + table[21 * 256 + 123] = 21; + table[20 * 256 + 124] = 21; + table[21 * 256 + 124] = 21; + table[20 * 256 + 125] = 21; + table[21 * 256 + 125] = 21; + table[20 * 256 + 126] = 21; + table[21 * 256 + 126] = 21; + table[20 * 256 + 127] = 21; + table[21 * 256 + 127] = 21; + table[20 * 256 + 128] = 21; + table[21 * 256 + 128] = 21; + table[20 * 256 + 129] = 21; + table[21 * 256 + 129] = 21; + table[20 * 256 + 130] = 21; + table[21 * 256 + 130] = 21; + table[20 * 256 + 131] = 21; + table[21 * 256 + 131] = 21; + table[20 * 256 + 132] = 21; + table[21 * 256 + 132] = 21; + table[20 * 256 + 133] = 21; + table[21 * 256 + 133] = 21; + table[20 * 256 + 134] = 21; + table[21 * 256 + 134] = 21; + table[20 * 256 + 135] = 21; + table[21 * 256 + 135] = 21; + table[20 * 256 + 136] = 21; + table[21 * 256 + 136] = 21; + table[20 * 256 + 137] = 21; + table[21 * 256 + 137] = 21; + table[20 * 256 + 138] = 21; + table[21 * 256 + 138] = 21; + table[20 * 256 + 139] = 21; + table[21 * 256 + 139] = 21; + table[20 * 256 + 140] = 21; + table[21 * 256 + 140] = 21; + table[20 * 256 + 141] = 21; + table[21 * 256 + 141] = 21; + table[20 * 256 + 142] = 21; + table[21 * 256 + 142] = 21; + table[20 * 256 + 143] = 21; + table[21 * 256 + 143] = 21; + table[20 * 256 + 144] = 21; + table[21 * 256 + 144] = 21; + table[20 * 256 + 145] = 21; + table[21 * 256 + 145] = 21; + table[20 * 256 + 146] = 21; + table[21 * 256 + 146] = 21; + table[20 * 256 + 147] = 21; + table[21 * 256 + 147] = 21; + table[20 * 256 + 148] = 21; + table[21 * 256 + 148] = 21; + table[20 * 256 + 149] = 21; + table[21 * 256 + 149] = 21; + table[20 * 256 + 150] = 21; + table[21 * 256 + 150] = 21; + table[20 * 256 + 151] = 21; + table[21 * 256 + 151] = 21; + table[20 * 256 + 152] = 21; + table[21 * 256 + 152] = 21; + table[20 * 256 + 153] = 21; + table[21 * 256 + 153] = 21; + table[20 * 256 + 154] = 21; + table[21 * 256 + 154] = 21; + table[20 * 256 + 155] = 21; + table[21 * 256 + 155] = 21; + table[20 * 256 + 156] = 21; + table[21 * 256 + 156] = 21; + table[20 * 256 + 157] = 21; + table[21 * 256 + 157] = 21; + table[20 * 256 + 158] = 21; + table[21 * 256 + 158] = 21; + table[20 * 256 + 159] = 21; + table[21 * 256 + 159] = 21; + table[20 * 256 + 160] = 21; + table[21 * 256 + 160] = 21; + table[20 * 256 + 161] = 21; + table[21 * 256 + 161] = 21; + table[20 * 256 + 162] = 21; + table[21 * 256 + 162] = 21; + table[20 * 256 + 163] = 21; + table[21 * 256 + 163] = 21; + table[20 * 256 + 164] = 21; + table[21 * 256 + 164] = 21; + table[20 * 256 + 165] = 21; + table[21 * 256 + 165] = 21; + table[20 * 256 + 166] = 21; + table[21 * 256 + 166] = 21; + table[20 * 256 + 167] = 21; + table[21 * 256 + 167] = 21; + table[20 * 256 + 168] = 21; + table[21 * 256 + 168] = 21; + table[20 * 256 + 169] = 21; + table[21 * 256 + 169] = 21; + table[20 * 256 + 170] = 21; + table[21 * 256 + 170] = 21; + table[20 * 256 + 171] = 21; + table[21 * 256 + 171] = 21; + table[20 * 256 + 172] = 21; + table[21 * 256 + 172] = 21; + table[20 * 256 + 173] = 21; + table[21 * 256 + 173] = 21; + table[20 * 256 + 174] = 21; + table[21 * 256 + 174] = 21; + table[20 * 256 + 175] = 21; + table[21 * 256 + 175] = 21; + table[20 * 256 + 176] = 21; + table[21 * 256 + 176] = 21; + table[20 * 256 + 177] = 21; + table[21 * 256 + 177] = 21; + table[20 * 256 + 178] = 21; + table[21 * 256 + 178] = 21; + table[20 * 256 + 179] = 21; + table[21 * 256 + 179] = 21; + table[20 * 256 + 180] = 21; + table[21 * 256 + 180] = 21; + table[20 * 256 + 181] = 21; + table[21 * 256 + 181] = 21; + table[20 * 256 + 182] = 21; + table[21 * 256 + 182] = 21; + table[20 * 256 + 183] = 21; + table[21 * 256 + 183] = 21; + table[20 * 256 + 184] = 21; + table[21 * 256 + 184] = 21; + table[20 * 256 + 185] = 21; + table[21 * 256 + 185] = 21; + table[20 * 256 + 186] = 21; + table[21 * 256 + 186] = 21; + table[20 * 256 + 187] = 21; + table[21 * 256 + 187] = 21; + table[20 * 256 + 188] = 21; + table[21 * 256 + 188] = 21; + table[20 * 256 + 189] = 21; + table[21 * 256 + 189] = 21; + table[20 * 256 + 190] = 21; + table[21 * 256 + 190] = 21; + table[20 * 256 + 191] = 21; + table[21 * 256 + 191] = 21; + table[20 * 256 + 192] = 21; + table[21 * 256 + 192] = 21; + table[20 * 256 + 193] = 21; + table[21 * 256 + 193] = 21; + table[20 * 256 + 194] = 21; + table[21 * 256 + 194] = 21; + table[20 * 256 + 195] = 21; + table[21 * 256 + 195] = 21; + table[20 * 256 + 196] = 21; + table[21 * 256 + 196] = 21; + table[20 * 256 + 197] = 21; + table[21 * 256 + 197] = 21; + table[20 * 256 + 198] = 21; + table[21 * 256 + 198] = 21; + table[20 * 256 + 199] = 21; + table[21 * 256 + 199] = 21; + table[20 * 256 + 200] = 21; + table[21 * 256 + 200] = 21; + table[20 * 256 + 201] = 21; + table[21 * 256 + 201] = 21; + table[20 * 256 + 202] = 21; + table[21 * 256 + 202] = 21; + table[20 * 256 + 203] = 21; + table[21 * 256 + 203] = 21; + table[20 * 256 + 204] = 21; + table[21 * 256 + 204] = 21; + table[20 * 256 + 205] = 21; + table[21 * 256 + 205] = 21; + table[20 * 256 + 206] = 21; + table[21 * 256 + 206] = 21; + table[20 * 256 + 207] = 21; + table[21 * 256 + 207] = 21; + table[20 * 256 + 208] = 21; + table[21 * 256 + 208] = 21; + table[20 * 256 + 209] = 21; + table[21 * 256 + 209] = 21; + table[20 * 256 + 210] = 21; + table[21 * 256 + 210] = 21; + table[20 * 256 + 211] = 21; + table[21 * 256 + 211] = 21; + table[20 * 256 + 212] = 21; + table[21 * 256 + 212] = 21; + table[20 * 256 + 213] = 21; + table[21 * 256 + 213] = 21; + table[20 * 256 + 214] = 21; + table[21 * 256 + 214] = 21; + table[20 * 256 + 215] = 21; + table[21 * 256 + 215] = 21; + table[20 * 256 + 216] = 21; + table[21 * 256 + 216] = 21; + table[20 * 256 + 217] = 21; + table[21 * 256 + 217] = 21; + table[20 * 256 + 218] = 21; + table[21 * 256 + 218] = 21; + table[20 * 256 + 219] = 21; + table[21 * 256 + 219] = 21; + table[20 * 256 + 220] = 21; + table[21 * 256 + 220] = 21; + table[20 * 256 + 221] = 21; + table[21 * 256 + 221] = 21; + table[20 * 256 + 222] = 21; + table[21 * 256 + 222] = 21; + table[20 * 256 + 223] = 21; + table[21 * 256 + 223] = 21; + table[20 * 256 + 224] = 21; + table[21 * 256 + 224] = 21; + table[20 * 256 + 225] = 21; + table[21 * 256 + 225] = 21; + table[20 * 256 + 226] = 21; + table[21 * 256 + 226] = 21; + table[20 * 256 + 227] = 21; + table[21 * 256 + 227] = 21; + table[20 * 256 + 228] = 21; + table[21 * 256 + 228] = 21; + table[20 * 256 + 229] = 21; + table[21 * 256 + 229] = 21; + table[20 * 256 + 230] = 21; + table[21 * 256 + 230] = 21; + table[20 * 256 + 231] = 21; + table[21 * 256 + 231] = 21; + table[20 * 256 + 232] = 21; + table[21 * 256 + 232] = 21; + table[20 * 256 + 233] = 21; + table[21 * 256 + 233] = 21; + table[20 * 256 + 234] = 21; + table[21 * 256 + 234] = 21; + table[20 * 256 + 235] = 21; + table[21 * 256 + 235] = 21; + table[20 * 256 + 236] = 21; + table[21 * 256 + 236] = 21; + table[20 * 256 + 237] = 21; + table[21 * 256 + 237] = 21; + table[20 * 256 + 238] = 21; + table[21 * 256 + 238] = 21; + table[20 * 256 + 239] = 21; + table[21 * 256 + 239] = 21; + table[20 * 256 + 240] = 21; + table[21 * 256 + 240] = 21; + table[20 * 256 + 241] = 21; + table[21 * 256 + 241] = 21; + table[20 * 256 + 242] = 21; + table[21 * 256 + 242] = 21; + table[20 * 256 + 243] = 21; + table[21 * 256 + 243] = 21; + table[20 * 256 + 244] = 21; + table[21 * 256 + 244] = 21; + table[20 * 256 + 245] = 21; + table[21 * 256 + 245] = 21; + table[20 * 256 + 246] = 21; + table[21 * 256 + 246] = 21; + table[20 * 256 + 247] = 21; + table[21 * 256 + 247] = 21; + table[20 * 256 + 248] = 21; + table[21 * 256 + 248] = 21; + table[20 * 256 + 249] = 21; + table[21 * 256 + 249] = 21; + table[20 * 256 + 250] = 21; + table[21 * 256 + 250] = 21; + table[20 * 256 + 251] = 21; + table[21 * 256 + 251] = 21; + table[20 * 256 + 252] = 21; + table[21 * 256 + 252] = 21; + table[20 * 256 + 253] = 21; + table[21 * 256 + 253] = 21; + table[20 * 256 + 254] = 21; + table[21 * 256 + 254] = 21; + table[0 * 256 + 13] = 1; + table[0 * 256 + 255] = 2; + table[1 * 256 + 10] = 2; + table[2 * 256 + 115] = 3; + table[3 * 256 + 117] = 4; + table[4 * 256 + 98] = 5; + table[5 * 256 + 106] = 6; + table[6 * 256 + 101] = 7; + table[7 * 256 + 99] = 8; + table[8 * 256 + 116] = 9; + table[9 * 256 + 58] = 10; + table[10 * 256 + 0] = 11; + table[10 * 256 + 1] = 11; + table[10 * 256 + 2] = 11; + table[10 * 256 + 3] = 11; + table[10 * 256 + 4] = 11; + table[10 * 256 + 5] = 11; + table[10 * 256 + 6] = 11; + table[10 * 256 + 7] = 11; + table[10 * 256 + 8] = 11; + table[10 * 256 + 9] = 11; + table[10 * 256 + 11] = 11; + table[10 * 256 + 12] = 11; + table[10 * 256 + 14] = 11; + table[10 * 256 + 15] = 11; + table[10 * 256 + 16] = 11; + table[10 * 256 + 17] = 11; + table[10 * 256 + 18] = 11; + table[10 * 256 + 19] = 11; + table[10 * 256 + 20] = 11; + table[10 * 256 + 21] = 11; + table[10 * 256 + 22] = 11; + table[10 * 256 + 23] = 11; + table[10 * 256 + 24] = 11; + table[10 * 256 + 25] = 11; + table[10 * 256 + 26] = 11; + table[10 * 256 + 27] = 11; + table[10 * 256 + 28] = 11; + table[10 * 256 + 29] = 11; + table[10 * 256 + 30] = 11; + table[10 * 256 + 31] = 11; + table[10 * 256 + 32] = 11; + table[10 * 256 + 33] = 11; + table[10 * 256 + 34] = 11; + table[10 * 256 + 35] = 11; + table[10 * 256 + 36] = 11; + table[10 * 256 + 37] = 11; + table[10 * 256 + 38] = 11; + table[10 * 256 + 39] = 11; + table[10 * 256 + 40] = 11; + table[10 * 256 + 41] = 11; + table[10 * 256 + 42] = 11; + table[10 * 256 + 43] = 11; + table[10 * 256 + 44] = 11; + table[10 * 256 + 45] = 11; + table[10 * 256 + 46] = 11; + table[10 * 256 + 47] = 11; + table[10 * 256 + 48] = 11; + table[10 * 256 + 49] = 11; + table[10 * 256 + 50] = 11; + table[10 * 256 + 51] = 11; + table[10 * 256 + 52] = 11; + table[10 * 256 + 53] = 11; + table[10 * 256 + 54] = 11; + table[10 * 256 + 55] = 11; + table[10 * 256 + 56] = 11; + table[10 * 256 + 57] = 11; + table[10 * 256 + 58] = 11; + table[10 * 256 + 59] = 11; + table[10 * 256 + 60] = 11; + table[10 * 256 + 61] = 11; + table[10 * 256 + 62] = 11; + table[10 * 256 + 63] = 11; + table[10 * 256 + 64] = 11; + table[10 * 256 + 65] = 11; + table[10 * 256 + 66] = 11; + table[10 * 256 + 67] = 11; + table[10 * 256 + 68] = 11; + table[10 * 256 + 69] = 11; + table[10 * 256 + 70] = 11; + table[10 * 256 + 71] = 11; + table[10 * 256 + 72] = 11; + table[10 * 256 + 73] = 11; + table[10 * 256 + 74] = 11; + table[10 * 256 + 75] = 11; + table[10 * 256 + 76] = 11; + table[10 * 256 + 77] = 11; + table[10 * 256 + 78] = 11; + table[10 * 256 + 79] = 11; + table[10 * 256 + 80] = 11; + table[10 * 256 + 81] = 11; + table[10 * 256 + 82] = 11; + table[10 * 256 + 83] = 11; + table[10 * 256 + 84] = 11; + table[10 * 256 + 85] = 11; + table[10 * 256 + 86] = 11; + table[10 * 256 + 87] = 11; + table[10 * 256 + 88] = 11; + table[10 * 256 + 89] = 11; + table[10 * 256 + 90] = 11; + table[10 * 256 + 91] = 11; + table[10 * 256 + 92] = 11; + table[10 * 256 + 93] = 11; + table[10 * 256 + 94] = 11; + table[10 * 256 + 95] = 11; + table[10 * 256 + 96] = 11; + table[10 * 256 + 97] = 11; + table[10 * 256 + 98] = 11; + table[10 * 256 + 99] = 11; + table[10 * 256 + 100] = 11; + table[10 * 256 + 101] = 11; + table[10 * 256 + 102] = 11; + table[10 * 256 + 103] = 11; + table[10 * 256 + 104] = 11; + table[10 * 256 + 105] = 11; + table[10 * 256 + 106] = 11; + table[10 * 256 + 107] = 11; + table[10 * 256 + 108] = 11; + table[10 * 256 + 109] = 11; + table[10 * 256 + 110] = 11; + table[10 * 256 + 111] = 11; + table[10 * 256 + 112] = 11; + table[10 * 256 + 113] = 11; + table[10 * 256 + 114] = 11; + table[10 * 256 + 115] = 11; + table[10 * 256 + 116] = 11; + table[10 * 256 + 117] = 11; + table[10 * 256 + 118] = 11; + table[10 * 256 + 119] = 11; + table[10 * 256 + 120] = 11; + table[10 * 256 + 121] = 11; + table[10 * 256 + 122] = 11; + table[10 * 256 + 123] = 11; + table[10 * 256 + 124] = 11; + table[10 * 256 + 125] = 11; + table[10 * 256 + 126] = 11; + table[10 * 256 + 127] = 11; + table[10 * 256 + 194] = 12; + table[10 * 256 + 195] = 12; + table[10 * 256 + 196] = 12; + table[10 * 256 + 197] = 12; + table[10 * 256 + 198] = 12; + table[10 * 256 + 199] = 12; + table[10 * 256 + 200] = 12; + table[10 * 256 + 201] = 12; + table[10 * 256 + 202] = 12; + table[10 * 256 + 203] = 12; + table[10 * 256 + 204] = 12; + table[10 * 256 + 205] = 12; + table[10 * 256 + 206] = 12; + table[10 * 256 + 207] = 12; + table[10 * 256 + 208] = 12; + table[10 * 256 + 209] = 12; + table[10 * 256 + 210] = 12; + table[10 * 256 + 211] = 12; + table[10 * 256 + 212] = 12; + table[10 * 256 + 213] = 12; + table[10 * 256 + 214] = 12; + table[10 * 256 + 215] = 12; + table[10 * 256 + 216] = 12; + table[10 * 256 + 217] = 12; + table[10 * 256 + 218] = 12; + table[10 * 256 + 219] = 12; + table[10 * 256 + 220] = 12; + table[10 * 256 + 221] = 12; + table[10 * 256 + 222] = 12; + table[10 * 256 + 223] = 12; + table[10 * 256 + 224] = 13; + table[10 * 256 + 225] = 14; + table[10 * 256 + 226] = 14; + table[10 * 256 + 227] = 14; + table[10 * 256 + 228] = 14; + table[10 * 256 + 229] = 14; + table[10 * 256 + 230] = 14; + table[10 * 256 + 231] = 14; + table[10 * 256 + 232] = 14; + table[10 * 256 + 233] = 14; + table[10 * 256 + 234] = 14; + table[10 * 256 + 235] = 14; + table[10 * 256 + 236] = 14; + table[10 * 256 + 238] = 14; + table[10 * 256 + 239] = 14; + table[10 * 256 + 237] = 15; + table[10 * 256 + 240] = 16; + table[10 * 256 + 241] = 17; + table[10 * 256 + 242] = 17; + table[10 * 256 + 243] = 17; + table[10 * 256 + 244] = 18; + table[11 * 256 + 0] = 11; + table[11 * 256 + 1] = 11; + table[11 * 256 + 2] = 11; + table[11 * 256 + 3] = 11; + table[11 * 256 + 4] = 11; + table[11 * 256 + 5] = 11; + table[11 * 256 + 6] = 11; + table[11 * 256 + 7] = 11; + table[11 * 256 + 8] = 11; + table[11 * 256 + 9] = 11; + table[11 * 256 + 11] = 11; + table[11 * 256 + 12] = 11; + table[11 * 256 + 14] = 11; + table[11 * 256 + 15] = 11; + table[11 * 256 + 16] = 11; + table[11 * 256 + 17] = 11; + table[11 * 256 + 18] = 11; + table[11 * 256 + 19] = 11; + table[11 * 256 + 20] = 11; + table[11 * 256 + 21] = 11; + table[11 * 256 + 22] = 11; + table[11 * 256 + 23] = 11; + table[11 * 256 + 24] = 11; + table[11 * 256 + 25] = 11; + table[11 * 256 + 26] = 11; + table[11 * 256 + 27] = 11; + table[11 * 256 + 28] = 11; + table[11 * 256 + 29] = 11; + table[11 * 256 + 30] = 11; + table[11 * 256 + 31] = 11; + table[11 * 256 + 32] = 11; + table[11 * 256 + 33] = 11; + table[11 * 256 + 34] = 11; + table[11 * 256 + 35] = 11; + table[11 * 256 + 36] = 11; + table[11 * 256 + 37] = 11; + table[11 * 256 + 38] = 11; + table[11 * 256 + 39] = 11; + table[11 * 256 + 40] = 11; + table[11 * 256 + 41] = 11; + table[11 * 256 + 42] = 11; + table[11 * 256 + 43] = 11; + table[11 * 256 + 44] = 11; + table[11 * 256 + 45] = 11; + table[11 * 256 + 46] = 11; + table[11 * 256 + 47] = 11; + table[11 * 256 + 48] = 11; + table[11 * 256 + 49] = 11; + table[11 * 256 + 50] = 11; + table[11 * 256 + 51] = 11; + table[11 * 256 + 52] = 11; + table[11 * 256 + 53] = 11; + table[11 * 256 + 54] = 11; + table[11 * 256 + 55] = 11; + table[11 * 256 + 56] = 11; + table[11 * 256 + 57] = 11; + table[11 * 256 + 58] = 11; + table[11 * 256 + 59] = 11; + table[11 * 256 + 60] = 11; + table[11 * 256 + 61] = 11; + table[11 * 256 + 62] = 11; + table[11 * 256 + 63] = 11; + table[11 * 256 + 64] = 11; + table[11 * 256 + 65] = 11; + table[11 * 256 + 66] = 11; + table[11 * 256 + 67] = 11; + table[11 * 256 + 68] = 11; + table[11 * 256 + 69] = 11; + table[11 * 256 + 70] = 11; + table[11 * 256 + 71] = 11; + table[11 * 256 + 72] = 11; + table[11 * 256 + 73] = 11; + table[11 * 256 + 74] = 11; + table[11 * 256 + 75] = 11; + table[11 * 256 + 76] = 11; + table[11 * 256 + 77] = 11; + table[11 * 256 + 78] = 11; + table[11 * 256 + 79] = 11; + table[11 * 256 + 80] = 11; + table[11 * 256 + 81] = 11; + table[11 * 256 + 82] = 11; + table[11 * 256 + 83] = 11; + table[11 * 256 + 84] = 11; + table[11 * 256 + 85] = 11; + table[11 * 256 + 86] = 11; + table[11 * 256 + 87] = 11; + table[11 * 256 + 88] = 11; + table[11 * 256 + 89] = 11; + table[11 * 256 + 90] = 11; + table[11 * 256 + 91] = 11; + table[11 * 256 + 92] = 11; + table[11 * 256 + 93] = 11; + table[11 * 256 + 94] = 11; + table[11 * 256 + 95] = 11; + table[11 * 256 + 96] = 11; + table[11 * 256 + 97] = 11; + table[11 * 256 + 98] = 11; + table[11 * 256 + 99] = 11; + table[11 * 256 + 100] = 11; + table[11 * 256 + 101] = 11; + table[11 * 256 + 102] = 11; + table[11 * 256 + 103] = 11; + table[11 * 256 + 104] = 11; + table[11 * 256 + 105] = 11; + table[11 * 256 + 106] = 11; + table[11 * 256 + 107] = 11; + table[11 * 256 + 108] = 11; + table[11 * 256 + 109] = 11; + table[11 * 256 + 110] = 11; + table[11 * 256 + 111] = 11; + table[11 * 256 + 112] = 11; + table[11 * 256 + 113] = 11; + table[11 * 256 + 114] = 11; + table[11 * 256 + 115] = 11; + table[11 * 256 + 116] = 11; + table[11 * 256 + 117] = 11; + table[11 * 256 + 118] = 11; + table[11 * 256 + 119] = 11; + table[11 * 256 + 120] = 11; + table[11 * 256 + 121] = 11; + table[11 * 256 + 122] = 11; + table[11 * 256 + 123] = 11; + table[11 * 256 + 124] = 11; + table[11 * 256 + 125] = 11; + table[11 * 256 + 126] = 11; + table[11 * 256 + 127] = 11; + table[11 * 256 + 194] = 12; + table[11 * 256 + 195] = 12; + table[11 * 256 + 196] = 12; + table[11 * 256 + 197] = 12; + table[11 * 256 + 198] = 12; + table[11 * 256 + 199] = 12; + table[11 * 256 + 200] = 12; + table[11 * 256 + 201] = 12; + table[11 * 256 + 202] = 12; + table[11 * 256 + 203] = 12; + table[11 * 256 + 204] = 12; + table[11 * 256 + 205] = 12; + table[11 * 256 + 206] = 12; + table[11 * 256 + 207] = 12; + table[11 * 256 + 208] = 12; + table[11 * 256 + 209] = 12; + table[11 * 256 + 210] = 12; + table[11 * 256 + 211] = 12; + table[11 * 256 + 212] = 12; + table[11 * 256 + 213] = 12; + table[11 * 256 + 214] = 12; + table[11 * 256 + 215] = 12; + table[11 * 256 + 216] = 12; + table[11 * 256 + 217] = 12; + table[11 * 256 + 218] = 12; + table[11 * 256 + 219] = 12; + table[11 * 256 + 220] = 12; + table[11 * 256 + 221] = 12; + table[11 * 256 + 222] = 12; + table[11 * 256 + 223] = 12; + table[11 * 256 + 224] = 13; + table[11 * 256 + 225] = 14; + table[11 * 256 + 226] = 14; + table[11 * 256 + 227] = 14; + table[11 * 256 + 228] = 14; + table[11 * 256 + 229] = 14; + table[11 * 256 + 230] = 14; + table[11 * 256 + 231] = 14; + table[11 * 256 + 232] = 14; + table[11 * 256 + 233] = 14; + table[11 * 256 + 234] = 14; + table[11 * 256 + 235] = 14; + table[11 * 256 + 236] = 14; + table[11 * 256 + 238] = 14; + table[11 * 256 + 239] = 14; + table[11 * 256 + 237] = 15; + table[11 * 256 + 240] = 16; + table[11 * 256 + 241] = 17; + table[11 * 256 + 242] = 17; + table[11 * 256 + 243] = 17; + table[11 * 256 + 244] = 18; + table[11 * 256 + 13] = 19; + table[12 * 256 + 128] = 11; + table[12 * 256 + 129] = 11; + table[12 * 256 + 130] = 11; + table[12 * 256 + 131] = 11; + table[12 * 256 + 132] = 11; + table[12 * 256 + 133] = 11; + table[12 * 256 + 134] = 11; + table[12 * 256 + 135] = 11; + table[12 * 256 + 136] = 11; + table[12 * 256 + 137] = 11; + table[12 * 256 + 138] = 11; + table[12 * 256 + 139] = 11; + table[12 * 256 + 140] = 11; + table[12 * 256 + 141] = 11; + table[12 * 256 + 142] = 11; + table[12 * 256 + 143] = 11; + table[12 * 256 + 144] = 11; + table[12 * 256 + 145] = 11; + table[12 * 256 + 146] = 11; + table[12 * 256 + 147] = 11; + table[12 * 256 + 148] = 11; + table[12 * 256 + 149] = 11; + table[12 * 256 + 150] = 11; + table[12 * 256 + 151] = 11; + table[12 * 256 + 152] = 11; + table[12 * 256 + 153] = 11; + table[12 * 256 + 154] = 11; + table[12 * 256 + 155] = 11; + table[12 * 256 + 156] = 11; + table[12 * 256 + 157] = 11; + table[12 * 256 + 158] = 11; + table[12 * 256 + 159] = 11; + table[12 * 256 + 160] = 11; + table[12 * 256 + 161] = 11; + table[12 * 256 + 162] = 11; + table[12 * 256 + 163] = 11; + table[12 * 256 + 164] = 11; + table[12 * 256 + 165] = 11; + table[12 * 256 + 166] = 11; + table[12 * 256 + 167] = 11; + table[12 * 256 + 168] = 11; + table[12 * 256 + 169] = 11; + table[12 * 256 + 170] = 11; + table[12 * 256 + 171] = 11; + table[12 * 256 + 172] = 11; + table[12 * 256 + 173] = 11; + table[12 * 256 + 174] = 11; + table[12 * 256 + 175] = 11; + table[12 * 256 + 176] = 11; + table[12 * 256 + 177] = 11; + table[12 * 256 + 178] = 11; + table[12 * 256 + 179] = 11; + table[12 * 256 + 180] = 11; + table[12 * 256 + 181] = 11; + table[12 * 256 + 182] = 11; + table[12 * 256 + 183] = 11; + table[12 * 256 + 184] = 11; + table[12 * 256 + 185] = 11; + table[12 * 256 + 186] = 11; + table[12 * 256 + 187] = 11; + table[12 * 256 + 188] = 11; + table[12 * 256 + 189] = 11; + table[12 * 256 + 190] = 11; + table[12 * 256 + 191] = 11; + table[13 * 256 + 160] = 12; + table[13 * 256 + 161] = 12; + table[13 * 256 + 162] = 12; + table[13 * 256 + 163] = 12; + table[13 * 256 + 164] = 12; + table[13 * 256 + 165] = 12; + table[13 * 256 + 166] = 12; + table[13 * 256 + 167] = 12; + table[13 * 256 + 168] = 12; + table[13 * 256 + 169] = 12; + table[13 * 256 + 170] = 12; + table[13 * 256 + 171] = 12; + table[13 * 256 + 172] = 12; + table[13 * 256 + 173] = 12; + table[13 * 256 + 174] = 12; + table[13 * 256 + 175] = 12; + table[13 * 256 + 176] = 12; + table[13 * 256 + 177] = 12; + table[13 * 256 + 178] = 12; + table[13 * 256 + 179] = 12; + table[13 * 256 + 180] = 12; + table[13 * 256 + 181] = 12; + table[13 * 256 + 182] = 12; + table[13 * 256 + 183] = 12; + table[13 * 256 + 184] = 12; + table[13 * 256 + 185] = 12; + table[13 * 256 + 186] = 12; + table[13 * 256 + 187] = 12; + table[13 * 256 + 188] = 12; + table[13 * 256 + 189] = 12; + table[13 * 256 + 190] = 12; + table[13 * 256 + 191] = 12; + table[14 * 256 + 128] = 12; + table[14 * 256 + 129] = 12; + table[14 * 256 + 130] = 12; + table[14 * 256 + 131] = 12; + table[14 * 256 + 132] = 12; + table[14 * 256 + 133] = 12; + table[14 * 256 + 134] = 12; + table[14 * 256 + 135] = 12; + table[14 * 256 + 136] = 12; + table[14 * 256 + 137] = 12; + table[14 * 256 + 138] = 12; + table[14 * 256 + 139] = 12; + table[14 * 256 + 140] = 12; + table[14 * 256 + 141] = 12; + table[14 * 256 + 142] = 12; + table[14 * 256 + 143] = 12; + table[14 * 256 + 144] = 12; + table[14 * 256 + 145] = 12; + table[14 * 256 + 146] = 12; + table[14 * 256 + 147] = 12; + table[14 * 256 + 148] = 12; + table[14 * 256 + 149] = 12; + table[14 * 256 + 150] = 12; + table[14 * 256 + 151] = 12; + table[14 * 256 + 152] = 12; + table[14 * 256 + 153] = 12; + table[14 * 256 + 154] = 12; + table[14 * 256 + 155] = 12; + table[14 * 256 + 156] = 12; + table[14 * 256 + 157] = 12; + table[14 * 256 + 158] = 12; + table[14 * 256 + 159] = 12; + table[14 * 256 + 160] = 12; + table[14 * 256 + 161] = 12; + table[14 * 256 + 162] = 12; + table[14 * 256 + 163] = 12; + table[14 * 256 + 164] = 12; + table[14 * 256 + 165] = 12; + table[14 * 256 + 166] = 12; + table[14 * 256 + 167] = 12; + table[14 * 256 + 168] = 12; + table[14 * 256 + 169] = 12; + table[14 * 256 + 170] = 12; + table[14 * 256 + 171] = 12; + table[14 * 256 + 172] = 12; + table[14 * 256 + 173] = 12; + table[14 * 256 + 174] = 12; + table[14 * 256 + 175] = 12; + table[14 * 256 + 176] = 12; + table[14 * 256 + 177] = 12; + table[14 * 256 + 178] = 12; + table[14 * 256 + 179] = 12; + table[14 * 256 + 180] = 12; + table[14 * 256 + 181] = 12; + table[14 * 256 + 182] = 12; + table[14 * 256 + 183] = 12; + table[14 * 256 + 184] = 12; + table[14 * 256 + 185] = 12; + table[14 * 256 + 186] = 12; + table[14 * 256 + 187] = 12; + table[14 * 256 + 188] = 12; + table[14 * 256 + 189] = 12; + table[14 * 256 + 190] = 12; + table[14 * 256 + 191] = 12; + table[15 * 256 + 128] = 12; + table[15 * 256 + 129] = 12; + table[15 * 256 + 130] = 12; + table[15 * 256 + 131] = 12; + table[15 * 256 + 132] = 12; + table[15 * 256 + 133] = 12; + table[15 * 256 + 134] = 12; + table[15 * 256 + 135] = 12; + table[15 * 256 + 136] = 12; + table[15 * 256 + 137] = 12; + table[15 * 256 + 138] = 12; + table[15 * 256 + 139] = 12; + table[15 * 256 + 140] = 12; + table[15 * 256 + 141] = 12; + table[15 * 256 + 142] = 12; + table[15 * 256 + 143] = 12; + table[15 * 256 + 144] = 12; + table[15 * 256 + 145] = 12; + table[15 * 256 + 146] = 12; + table[15 * 256 + 147] = 12; + table[15 * 256 + 148] = 12; + table[15 * 256 + 149] = 12; + table[15 * 256 + 150] = 12; + table[15 * 256 + 151] = 12; + table[15 * 256 + 152] = 12; + table[15 * 256 + 153] = 12; + table[15 * 256 + 154] = 12; + table[15 * 256 + 155] = 12; + table[15 * 256 + 156] = 12; + table[15 * 256 + 157] = 12; + table[15 * 256 + 158] = 12; + table[15 * 256 + 159] = 12; + table[16 * 256 + 144] = 14; + table[16 * 256 + 145] = 14; + table[16 * 256 + 146] = 14; + table[16 * 256 + 147] = 14; + table[16 * 256 + 148] = 14; + table[16 * 256 + 149] = 14; + table[16 * 256 + 150] = 14; + table[16 * 256 + 151] = 14; + table[16 * 256 + 152] = 14; + table[16 * 256 + 153] = 14; + table[16 * 256 + 154] = 14; + table[16 * 256 + 155] = 14; + table[16 * 256 + 156] = 14; + table[16 * 256 + 157] = 14; + table[16 * 256 + 158] = 14; + table[16 * 256 + 159] = 14; + table[16 * 256 + 160] = 14; + table[16 * 256 + 161] = 14; + table[16 * 256 + 162] = 14; + table[16 * 256 + 163] = 14; + table[16 * 256 + 164] = 14; + table[16 * 256 + 165] = 14; + table[16 * 256 + 166] = 14; + table[16 * 256 + 167] = 14; + table[16 * 256 + 168] = 14; + table[16 * 256 + 169] = 14; + table[16 * 256 + 170] = 14; + table[16 * 256 + 171] = 14; + table[16 * 256 + 172] = 14; + table[16 * 256 + 173] = 14; + table[16 * 256 + 174] = 14; + table[16 * 256 + 175] = 14; + table[16 * 256 + 176] = 14; + table[16 * 256 + 177] = 14; + table[16 * 256 + 178] = 14; + table[16 * 256 + 179] = 14; + table[16 * 256 + 180] = 14; + table[16 * 256 + 181] = 14; + table[16 * 256 + 182] = 14; + table[16 * 256 + 183] = 14; + table[16 * 256 + 184] = 14; + table[16 * 256 + 185] = 14; + table[16 * 256 + 186] = 14; + table[16 * 256 + 187] = 14; + table[16 * 256 + 188] = 14; + table[16 * 256 + 189] = 14; + table[16 * 256 + 190] = 14; + table[16 * 256 + 191] = 14; + table[17 * 256 + 128] = 14; + table[17 * 256 + 129] = 14; + table[17 * 256 + 130] = 14; + table[17 * 256 + 131] = 14; + table[17 * 256 + 132] = 14; + table[17 * 256 + 133] = 14; + table[17 * 256 + 134] = 14; + table[17 * 256 + 135] = 14; + table[17 * 256 + 136] = 14; + table[17 * 256 + 137] = 14; + table[17 * 256 + 138] = 14; + table[17 * 256 + 139] = 14; + table[17 * 256 + 140] = 14; + table[17 * 256 + 141] = 14; + table[17 * 256 + 142] = 14; + table[17 * 256 + 143] = 14; + table[17 * 256 + 144] = 14; + table[17 * 256 + 145] = 14; + table[17 * 256 + 146] = 14; + table[17 * 256 + 147] = 14; + table[17 * 256 + 148] = 14; + table[17 * 256 + 149] = 14; + table[17 * 256 + 150] = 14; + table[17 * 256 + 151] = 14; + table[17 * 256 + 152] = 14; + table[17 * 256 + 153] = 14; + table[17 * 256 + 154] = 14; + table[17 * 256 + 155] = 14; + table[17 * 256 + 156] = 14; + table[17 * 256 + 157] = 14; + table[17 * 256 + 158] = 14; + table[17 * 256 + 159] = 14; + table[17 * 256 + 160] = 14; + table[17 * 256 + 161] = 14; + table[17 * 256 + 162] = 14; + table[17 * 256 + 163] = 14; + table[17 * 256 + 164] = 14; + table[17 * 256 + 165] = 14; + table[17 * 256 + 166] = 14; + table[17 * 256 + 167] = 14; + table[17 * 256 + 168] = 14; + table[17 * 256 + 169] = 14; + table[17 * 256 + 170] = 14; + table[17 * 256 + 171] = 14; + table[17 * 256 + 172] = 14; + table[17 * 256 + 173] = 14; + table[17 * 256 + 174] = 14; + table[17 * 256 + 175] = 14; + table[17 * 256 + 176] = 14; + table[17 * 256 + 177] = 14; + table[17 * 256 + 178] = 14; + table[17 * 256 + 179] = 14; + table[17 * 256 + 180] = 14; + table[17 * 256 + 181] = 14; + table[17 * 256 + 182] = 14; + table[17 * 256 + 183] = 14; + table[17 * 256 + 184] = 14; + table[17 * 256 + 185] = 14; + table[17 * 256 + 186] = 14; + table[17 * 256 + 187] = 14; + table[17 * 256 + 188] = 14; + table[17 * 256 + 189] = 14; + table[17 * 256 + 190] = 14; + table[17 * 256 + 191] = 14; + table[18 * 256 + 128] = 14; + table[18 * 256 + 129] = 14; + table[18 * 256 + 130] = 14; + table[18 * 256 + 131] = 14; + table[18 * 256 + 132] = 14; + table[18 * 256 + 133] = 14; + table[18 * 256 + 134] = 14; + table[18 * 256 + 135] = 14; + table[18 * 256 + 136] = 14; + table[18 * 256 + 137] = 14; + table[18 * 256 + 138] = 14; + table[18 * 256 + 139] = 14; + table[18 * 256 + 140] = 14; + table[18 * 256 + 141] = 14; + table[18 * 256 + 142] = 14; + table[18 * 256 + 143] = 14; + table[19 * 256 + 10] = 20; + + table +} + + +pub fn regex_match(input: [u8; N]) -> (BoundedVec, bool) { + let substrings = unsafe { __regex_match(input) }; + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + let mut start_range = 0; + let mut end_range = 0; + + // check the match + for i in 0..N { + // state transition + let temp = input[i] as Field; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + s = 0; + s_next = potential_s_next; + } + std::as_witness(s_next); + + // range conditions for substring matches + if ((start_range == 0) & (end_range == 0)) { + start_range = i as Field; + } + if (((s == 20) & (s_next == 21)) & (end_range == 0)) { + end_range = i as Field + 1; + } + + + let range_0 = substrings.get_unchecked(0).in_range(i); + let case_0 = [ + (s == 10) & ((s_next == 11) | (s_next == 12) | (s_next == 13) | (s_next == 14) | (s_next == 15) | (s_next == 16) | (s_next == 17) | (s_next == 18)), + (s == 11) & ((s_next == 11) | (s_next == 12) | (s_next == 13) | (s_next == 14) | (s_next == 15) | (s_next == 16) | (s_next == 17) | (s_next == 18)), + (s_next == 11) & ((s == 12)), + (s_next == 12) & ((s == 13) | (s == 14) | (s == 15)), + (s_next == 14) & ((s == 16) | (s == 17) | (s == 18)) + ].any(|case| case == true) | !range_0; + + + + let substring_range_check = [case_0] + .all(|case| case == true); + + assert(substring_range_check, "substr array ranges wrong"); + + + s = s_next; + } + // check final state + + let matched: bool = (s == 20) | (s == 21); + + // constrain extracted substrings to be in match range + //let full_match = Sequence::new(start_range as u32, end_range as u32 - start_range as u32); + //let full_match_end = full_match.end(); + // for i in 0..1 { + // let substring = substrings.get_unchecked(i); + // let is_not_valid = i >= substrings.len(); + // let index_check = substring.index >= full_match.index; + // let length_check = substring.end() <= full_match_end; + // let check = (index_check) | is_not_valid; + // assert(check, f"Substring {i} range is out of bounds of the full match found"); + // } + (substrings, matched) +} + + +pub unconstrained fn __regex_match(input: [u8; N]) -> BoundedVec { + // regex: (\r\n|^)subject:[^\r\n]+\r\n + let mut substrings: BoundedVec = BoundedVec::new(); + let mut current_substring = Sequence::default(); + let mut full_match = Sequence::default(); + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + + let mut consecutive_substr = 0; + let mut complete = false; + + for i in 0..input.len() { + let temp = input[i] as Field; + let mut reset = false; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + reset = true; + s = 0; + s_next = potential_s_next; + } + // If a substring was in the making, but the state was reset + // we disregard previous progress because apparently it is invalid + if (reset & (consecutive_substr == 1)) { + current_substring = Sequence::default(); + consecutive_substr = 0; + } + // Fill up substrings + + + if ((s == 10) & (s_next == 11) | (s == 10) & (s_next == 12) | (s == 10) & (s_next == 13) | (s == 10) & (s_next == 14) | (s == 10) & (s_next == 15) | (s == 10) & (s_next == 16) | (s == 10) & (s_next == 17) | (s == 10) & (s_next == 18) | (s == 11) & (s_next == 11) | (s == 11) & (s_next == 12) | (s == 11) & (s_next == 13) | (s == 11) & (s_next == 14) | (s == 11) & (s_next == 15) | (s == 11) & (s_next == 16) | (s == 11) & (s_next == 17) | (s == 11) & (s_next == 18) | (s == 12) & (s_next == 11) | (s == 13) & (s_next == 12) | (s == 14) & (s_next == 12) | (s == 15) & (s_next == 12) | (s == 16) & (s_next == 14) | (s == 17) & (s_next == 14) | (s == 18) & (s_next == 14)) { + + if (consecutive_substr == 0) { + current_substring.index = i; + }; + current_substring.length += 1; + consecutive_substr = 1; + } else if ((consecutive_substr == 1) & (s_next == 0)) { + current_substring = Sequence::default(); + full_match = Sequence::default(); + substrings = BoundedVec::new(); + consecutive_substr = 0; + } else if (s == 20) & (s_next == 21) { + full_match.length = i - full_match.index + 1; + complete = true; + } else if (consecutive_substr == 1) { + // The substring is done so "save" it + substrings.push(current_substring); + // reset the substring holder for next use + current_substring = Sequence::default(); + consecutive_substr = 0; + } + s = s_next; + if complete == true { + break; + } + } + assert((s == 20) | (s == 21), f"no match: {s}"); + // Add pending substring that hasn't been added + if consecutive_substr == 1 { + substrings.push(current_substring); + full_match.length = input.len() - full_match.index; + } + + + + substrings +} + + + + \ No newline at end of file diff --git a/packages/noir/src/capture/raw/timestamp.nr b/packages/noir/src/capture/raw/timestamp.nr new file mode 100644 index 00000000..93a2b116 --- /dev/null +++ b/packages/noir/src/capture/raw/timestamp.nr @@ -0,0 +1,1656 @@ + +use crate::common::Sequence; + + +global table: [Field; 8960] = comptime { make_lookup_table() }; + +comptime fn make_lookup_table() -> [Field; 8960] { + let mut table = [0; 8960]; + table[33 * 256 + 0] = 34; + table[34 * 256 + 0] = 34; + table[33 * 256 + 1] = 34; + table[34 * 256 + 1] = 34; + table[33 * 256 + 2] = 34; + table[34 * 256 + 2] = 34; + table[33 * 256 + 3] = 34; + table[34 * 256 + 3] = 34; + table[33 * 256 + 4] = 34; + table[34 * 256 + 4] = 34; + table[33 * 256 + 5] = 34; + table[34 * 256 + 5] = 34; + table[33 * 256 + 6] = 34; + table[34 * 256 + 6] = 34; + table[33 * 256 + 7] = 34; + table[34 * 256 + 7] = 34; + table[33 * 256 + 8] = 34; + table[34 * 256 + 8] = 34; + table[33 * 256 + 9] = 34; + table[34 * 256 + 9] = 34; + table[33 * 256 + 10] = 34; + table[34 * 256 + 10] = 34; + table[33 * 256 + 11] = 34; + table[34 * 256 + 11] = 34; + table[33 * 256 + 12] = 34; + table[34 * 256 + 12] = 34; + table[33 * 256 + 13] = 34; + table[34 * 256 + 13] = 34; + table[33 * 256 + 14] = 34; + table[34 * 256 + 14] = 34; + table[33 * 256 + 15] = 34; + table[34 * 256 + 15] = 34; + table[33 * 256 + 16] = 34; + table[34 * 256 + 16] = 34; + table[33 * 256 + 17] = 34; + table[34 * 256 + 17] = 34; + table[33 * 256 + 18] = 34; + table[34 * 256 + 18] = 34; + table[33 * 256 + 19] = 34; + table[34 * 256 + 19] = 34; + table[33 * 256 + 20] = 34; + table[34 * 256 + 20] = 34; + table[33 * 256 + 21] = 34; + table[34 * 256 + 21] = 34; + table[33 * 256 + 22] = 34; + table[34 * 256 + 22] = 34; + table[33 * 256 + 23] = 34; + table[34 * 256 + 23] = 34; + table[33 * 256 + 24] = 34; + table[34 * 256 + 24] = 34; + table[33 * 256 + 25] = 34; + table[34 * 256 + 25] = 34; + table[33 * 256 + 26] = 34; + table[34 * 256 + 26] = 34; + table[33 * 256 + 27] = 34; + table[34 * 256 + 27] = 34; + table[33 * 256 + 28] = 34; + table[34 * 256 + 28] = 34; + table[33 * 256 + 29] = 34; + table[34 * 256 + 29] = 34; + table[33 * 256 + 30] = 34; + table[34 * 256 + 30] = 34; + table[33 * 256 + 31] = 34; + table[34 * 256 + 31] = 34; + table[33 * 256 + 32] = 34; + table[34 * 256 + 32] = 34; + table[33 * 256 + 33] = 34; + table[34 * 256 + 33] = 34; + table[33 * 256 + 34] = 34; + table[34 * 256 + 34] = 34; + table[33 * 256 + 35] = 34; + table[34 * 256 + 35] = 34; + table[33 * 256 + 36] = 34; + table[34 * 256 + 36] = 34; + table[33 * 256 + 37] = 34; + table[34 * 256 + 37] = 34; + table[33 * 256 + 38] = 34; + table[34 * 256 + 38] = 34; + table[33 * 256 + 39] = 34; + table[34 * 256 + 39] = 34; + table[33 * 256 + 40] = 34; + table[34 * 256 + 40] = 34; + table[33 * 256 + 41] = 34; + table[34 * 256 + 41] = 34; + table[33 * 256 + 42] = 34; + table[34 * 256 + 42] = 34; + table[33 * 256 + 43] = 34; + table[34 * 256 + 43] = 34; + table[33 * 256 + 44] = 34; + table[34 * 256 + 44] = 34; + table[33 * 256 + 45] = 34; + table[34 * 256 + 45] = 34; + table[33 * 256 + 46] = 34; + table[34 * 256 + 46] = 34; + table[33 * 256 + 47] = 34; + table[34 * 256 + 47] = 34; + table[33 * 256 + 48] = 34; + table[34 * 256 + 48] = 34; + table[33 * 256 + 49] = 34; + table[34 * 256 + 49] = 34; + table[33 * 256 + 50] = 34; + table[34 * 256 + 50] = 34; + table[33 * 256 + 51] = 34; + table[34 * 256 + 51] = 34; + table[33 * 256 + 52] = 34; + table[34 * 256 + 52] = 34; + table[33 * 256 + 53] = 34; + table[34 * 256 + 53] = 34; + table[33 * 256 + 54] = 34; + table[34 * 256 + 54] = 34; + table[33 * 256 + 55] = 34; + table[34 * 256 + 55] = 34; + table[33 * 256 + 56] = 34; + table[34 * 256 + 56] = 34; + table[33 * 256 + 57] = 34; + table[34 * 256 + 57] = 34; + table[33 * 256 + 58] = 34; + table[34 * 256 + 58] = 34; + table[33 * 256 + 59] = 34; + table[34 * 256 + 59] = 34; + table[33 * 256 + 60] = 34; + table[34 * 256 + 60] = 34; + table[33 * 256 + 61] = 34; + table[34 * 256 + 61] = 34; + table[33 * 256 + 62] = 34; + table[34 * 256 + 62] = 34; + table[33 * 256 + 63] = 34; + table[34 * 256 + 63] = 34; + table[33 * 256 + 64] = 34; + table[34 * 256 + 64] = 34; + table[33 * 256 + 65] = 34; + table[34 * 256 + 65] = 34; + table[33 * 256 + 66] = 34; + table[34 * 256 + 66] = 34; + table[33 * 256 + 67] = 34; + table[34 * 256 + 67] = 34; + table[33 * 256 + 68] = 34; + table[34 * 256 + 68] = 34; + table[33 * 256 + 69] = 34; + table[34 * 256 + 69] = 34; + table[33 * 256 + 70] = 34; + table[34 * 256 + 70] = 34; + table[33 * 256 + 71] = 34; + table[34 * 256 + 71] = 34; + table[33 * 256 + 72] = 34; + table[34 * 256 + 72] = 34; + table[33 * 256 + 73] = 34; + table[34 * 256 + 73] = 34; + table[33 * 256 + 74] = 34; + table[34 * 256 + 74] = 34; + table[33 * 256 + 75] = 34; + table[34 * 256 + 75] = 34; + table[33 * 256 + 76] = 34; + table[34 * 256 + 76] = 34; + table[33 * 256 + 77] = 34; + table[34 * 256 + 77] = 34; + table[33 * 256 + 78] = 34; + table[34 * 256 + 78] = 34; + table[33 * 256 + 79] = 34; + table[34 * 256 + 79] = 34; + table[33 * 256 + 80] = 34; + table[34 * 256 + 80] = 34; + table[33 * 256 + 81] = 34; + table[34 * 256 + 81] = 34; + table[33 * 256 + 82] = 34; + table[34 * 256 + 82] = 34; + table[33 * 256 + 83] = 34; + table[34 * 256 + 83] = 34; + table[33 * 256 + 84] = 34; + table[34 * 256 + 84] = 34; + table[33 * 256 + 85] = 34; + table[34 * 256 + 85] = 34; + table[33 * 256 + 86] = 34; + table[34 * 256 + 86] = 34; + table[33 * 256 + 87] = 34; + table[34 * 256 + 87] = 34; + table[33 * 256 + 88] = 34; + table[34 * 256 + 88] = 34; + table[33 * 256 + 89] = 34; + table[34 * 256 + 89] = 34; + table[33 * 256 + 90] = 34; + table[34 * 256 + 90] = 34; + table[33 * 256 + 91] = 34; + table[34 * 256 + 91] = 34; + table[33 * 256 + 92] = 34; + table[34 * 256 + 92] = 34; + table[33 * 256 + 93] = 34; + table[34 * 256 + 93] = 34; + table[33 * 256 + 94] = 34; + table[34 * 256 + 94] = 34; + table[33 * 256 + 95] = 34; + table[34 * 256 + 95] = 34; + table[33 * 256 + 96] = 34; + table[34 * 256 + 96] = 34; + table[33 * 256 + 97] = 34; + table[34 * 256 + 97] = 34; + table[33 * 256 + 98] = 34; + table[34 * 256 + 98] = 34; + table[33 * 256 + 99] = 34; + table[34 * 256 + 99] = 34; + table[33 * 256 + 100] = 34; + table[34 * 256 + 100] = 34; + table[33 * 256 + 101] = 34; + table[34 * 256 + 101] = 34; + table[33 * 256 + 102] = 34; + table[34 * 256 + 102] = 34; + table[33 * 256 + 103] = 34; + table[34 * 256 + 103] = 34; + table[33 * 256 + 104] = 34; + table[34 * 256 + 104] = 34; + table[33 * 256 + 105] = 34; + table[34 * 256 + 105] = 34; + table[33 * 256 + 106] = 34; + table[34 * 256 + 106] = 34; + table[33 * 256 + 107] = 34; + table[34 * 256 + 107] = 34; + table[33 * 256 + 108] = 34; + table[34 * 256 + 108] = 34; + table[33 * 256 + 109] = 34; + table[34 * 256 + 109] = 34; + table[33 * 256 + 110] = 34; + table[34 * 256 + 110] = 34; + table[33 * 256 + 111] = 34; + table[34 * 256 + 111] = 34; + table[33 * 256 + 112] = 34; + table[34 * 256 + 112] = 34; + table[33 * 256 + 113] = 34; + table[34 * 256 + 113] = 34; + table[33 * 256 + 114] = 34; + table[34 * 256 + 114] = 34; + table[33 * 256 + 115] = 34; + table[34 * 256 + 115] = 34; + table[33 * 256 + 116] = 34; + table[34 * 256 + 116] = 34; + table[33 * 256 + 117] = 34; + table[34 * 256 + 117] = 34; + table[33 * 256 + 118] = 34; + table[34 * 256 + 118] = 34; + table[33 * 256 + 119] = 34; + table[34 * 256 + 119] = 34; + table[33 * 256 + 120] = 34; + table[34 * 256 + 120] = 34; + table[33 * 256 + 121] = 34; + table[34 * 256 + 121] = 34; + table[33 * 256 + 122] = 34; + table[34 * 256 + 122] = 34; + table[33 * 256 + 123] = 34; + table[34 * 256 + 123] = 34; + table[33 * 256 + 124] = 34; + table[34 * 256 + 124] = 34; + table[33 * 256 + 125] = 34; + table[34 * 256 + 125] = 34; + table[33 * 256 + 126] = 34; + table[34 * 256 + 126] = 34; + table[33 * 256 + 127] = 34; + table[34 * 256 + 127] = 34; + table[33 * 256 + 128] = 34; + table[34 * 256 + 128] = 34; + table[33 * 256 + 129] = 34; + table[34 * 256 + 129] = 34; + table[33 * 256 + 130] = 34; + table[34 * 256 + 130] = 34; + table[33 * 256 + 131] = 34; + table[34 * 256 + 131] = 34; + table[33 * 256 + 132] = 34; + table[34 * 256 + 132] = 34; + table[33 * 256 + 133] = 34; + table[34 * 256 + 133] = 34; + table[33 * 256 + 134] = 34; + table[34 * 256 + 134] = 34; + table[33 * 256 + 135] = 34; + table[34 * 256 + 135] = 34; + table[33 * 256 + 136] = 34; + table[34 * 256 + 136] = 34; + table[33 * 256 + 137] = 34; + table[34 * 256 + 137] = 34; + table[33 * 256 + 138] = 34; + table[34 * 256 + 138] = 34; + table[33 * 256 + 139] = 34; + table[34 * 256 + 139] = 34; + table[33 * 256 + 140] = 34; + table[34 * 256 + 140] = 34; + table[33 * 256 + 141] = 34; + table[34 * 256 + 141] = 34; + table[33 * 256 + 142] = 34; + table[34 * 256 + 142] = 34; + table[33 * 256 + 143] = 34; + table[34 * 256 + 143] = 34; + table[33 * 256 + 144] = 34; + table[34 * 256 + 144] = 34; + table[33 * 256 + 145] = 34; + table[34 * 256 + 145] = 34; + table[33 * 256 + 146] = 34; + table[34 * 256 + 146] = 34; + table[33 * 256 + 147] = 34; + table[34 * 256 + 147] = 34; + table[33 * 256 + 148] = 34; + table[34 * 256 + 148] = 34; + table[33 * 256 + 149] = 34; + table[34 * 256 + 149] = 34; + table[33 * 256 + 150] = 34; + table[34 * 256 + 150] = 34; + table[33 * 256 + 151] = 34; + table[34 * 256 + 151] = 34; + table[33 * 256 + 152] = 34; + table[34 * 256 + 152] = 34; + table[33 * 256 + 153] = 34; + table[34 * 256 + 153] = 34; + table[33 * 256 + 154] = 34; + table[34 * 256 + 154] = 34; + table[33 * 256 + 155] = 34; + table[34 * 256 + 155] = 34; + table[33 * 256 + 156] = 34; + table[34 * 256 + 156] = 34; + table[33 * 256 + 157] = 34; + table[34 * 256 + 157] = 34; + table[33 * 256 + 158] = 34; + table[34 * 256 + 158] = 34; + table[33 * 256 + 159] = 34; + table[34 * 256 + 159] = 34; + table[33 * 256 + 160] = 34; + table[34 * 256 + 160] = 34; + table[33 * 256 + 161] = 34; + table[34 * 256 + 161] = 34; + table[33 * 256 + 162] = 34; + table[34 * 256 + 162] = 34; + table[33 * 256 + 163] = 34; + table[34 * 256 + 163] = 34; + table[33 * 256 + 164] = 34; + table[34 * 256 + 164] = 34; + table[33 * 256 + 165] = 34; + table[34 * 256 + 165] = 34; + table[33 * 256 + 166] = 34; + table[34 * 256 + 166] = 34; + table[33 * 256 + 167] = 34; + table[34 * 256 + 167] = 34; + table[33 * 256 + 168] = 34; + table[34 * 256 + 168] = 34; + table[33 * 256 + 169] = 34; + table[34 * 256 + 169] = 34; + table[33 * 256 + 170] = 34; + table[34 * 256 + 170] = 34; + table[33 * 256 + 171] = 34; + table[34 * 256 + 171] = 34; + table[33 * 256 + 172] = 34; + table[34 * 256 + 172] = 34; + table[33 * 256 + 173] = 34; + table[34 * 256 + 173] = 34; + table[33 * 256 + 174] = 34; + table[34 * 256 + 174] = 34; + table[33 * 256 + 175] = 34; + table[34 * 256 + 175] = 34; + table[33 * 256 + 176] = 34; + table[34 * 256 + 176] = 34; + table[33 * 256 + 177] = 34; + table[34 * 256 + 177] = 34; + table[33 * 256 + 178] = 34; + table[34 * 256 + 178] = 34; + table[33 * 256 + 179] = 34; + table[34 * 256 + 179] = 34; + table[33 * 256 + 180] = 34; + table[34 * 256 + 180] = 34; + table[33 * 256 + 181] = 34; + table[34 * 256 + 181] = 34; + table[33 * 256 + 182] = 34; + table[34 * 256 + 182] = 34; + table[33 * 256 + 183] = 34; + table[34 * 256 + 183] = 34; + table[33 * 256 + 184] = 34; + table[34 * 256 + 184] = 34; + table[33 * 256 + 185] = 34; + table[34 * 256 + 185] = 34; + table[33 * 256 + 186] = 34; + table[34 * 256 + 186] = 34; + table[33 * 256 + 187] = 34; + table[34 * 256 + 187] = 34; + table[33 * 256 + 188] = 34; + table[34 * 256 + 188] = 34; + table[33 * 256 + 189] = 34; + table[34 * 256 + 189] = 34; + table[33 * 256 + 190] = 34; + table[34 * 256 + 190] = 34; + table[33 * 256 + 191] = 34; + table[34 * 256 + 191] = 34; + table[33 * 256 + 192] = 34; + table[34 * 256 + 192] = 34; + table[33 * 256 + 193] = 34; + table[34 * 256 + 193] = 34; + table[33 * 256 + 194] = 34; + table[34 * 256 + 194] = 34; + table[33 * 256 + 195] = 34; + table[34 * 256 + 195] = 34; + table[33 * 256 + 196] = 34; + table[34 * 256 + 196] = 34; + table[33 * 256 + 197] = 34; + table[34 * 256 + 197] = 34; + table[33 * 256 + 198] = 34; + table[34 * 256 + 198] = 34; + table[33 * 256 + 199] = 34; + table[34 * 256 + 199] = 34; + table[33 * 256 + 200] = 34; + table[34 * 256 + 200] = 34; + table[33 * 256 + 201] = 34; + table[34 * 256 + 201] = 34; + table[33 * 256 + 202] = 34; + table[34 * 256 + 202] = 34; + table[33 * 256 + 203] = 34; + table[34 * 256 + 203] = 34; + table[33 * 256 + 204] = 34; + table[34 * 256 + 204] = 34; + table[33 * 256 + 205] = 34; + table[34 * 256 + 205] = 34; + table[33 * 256 + 206] = 34; + table[34 * 256 + 206] = 34; + table[33 * 256 + 207] = 34; + table[34 * 256 + 207] = 34; + table[33 * 256 + 208] = 34; + table[34 * 256 + 208] = 34; + table[33 * 256 + 209] = 34; + table[34 * 256 + 209] = 34; + table[33 * 256 + 210] = 34; + table[34 * 256 + 210] = 34; + table[33 * 256 + 211] = 34; + table[34 * 256 + 211] = 34; + table[33 * 256 + 212] = 34; + table[34 * 256 + 212] = 34; + table[33 * 256 + 213] = 34; + table[34 * 256 + 213] = 34; + table[33 * 256 + 214] = 34; + table[34 * 256 + 214] = 34; + table[33 * 256 + 215] = 34; + table[34 * 256 + 215] = 34; + table[33 * 256 + 216] = 34; + table[34 * 256 + 216] = 34; + table[33 * 256 + 217] = 34; + table[34 * 256 + 217] = 34; + table[33 * 256 + 218] = 34; + table[34 * 256 + 218] = 34; + table[33 * 256 + 219] = 34; + table[34 * 256 + 219] = 34; + table[33 * 256 + 220] = 34; + table[34 * 256 + 220] = 34; + table[33 * 256 + 221] = 34; + table[34 * 256 + 221] = 34; + table[33 * 256 + 222] = 34; + table[34 * 256 + 222] = 34; + table[33 * 256 + 223] = 34; + table[34 * 256 + 223] = 34; + table[33 * 256 + 224] = 34; + table[34 * 256 + 224] = 34; + table[33 * 256 + 225] = 34; + table[34 * 256 + 225] = 34; + table[33 * 256 + 226] = 34; + table[34 * 256 + 226] = 34; + table[33 * 256 + 227] = 34; + table[34 * 256 + 227] = 34; + table[33 * 256 + 228] = 34; + table[34 * 256 + 228] = 34; + table[33 * 256 + 229] = 34; + table[34 * 256 + 229] = 34; + table[33 * 256 + 230] = 34; + table[34 * 256 + 230] = 34; + table[33 * 256 + 231] = 34; + table[34 * 256 + 231] = 34; + table[33 * 256 + 232] = 34; + table[34 * 256 + 232] = 34; + table[33 * 256 + 233] = 34; + table[34 * 256 + 233] = 34; + table[33 * 256 + 234] = 34; + table[34 * 256 + 234] = 34; + table[33 * 256 + 235] = 34; + table[34 * 256 + 235] = 34; + table[33 * 256 + 236] = 34; + table[34 * 256 + 236] = 34; + table[33 * 256 + 237] = 34; + table[34 * 256 + 237] = 34; + table[33 * 256 + 238] = 34; + table[34 * 256 + 238] = 34; + table[33 * 256 + 239] = 34; + table[34 * 256 + 239] = 34; + table[33 * 256 + 240] = 34; + table[34 * 256 + 240] = 34; + table[33 * 256 + 241] = 34; + table[34 * 256 + 241] = 34; + table[33 * 256 + 242] = 34; + table[34 * 256 + 242] = 34; + table[33 * 256 + 243] = 34; + table[34 * 256 + 243] = 34; + table[33 * 256 + 244] = 34; + table[34 * 256 + 244] = 34; + table[33 * 256 + 245] = 34; + table[34 * 256 + 245] = 34; + table[33 * 256 + 246] = 34; + table[34 * 256 + 246] = 34; + table[33 * 256 + 247] = 34; + table[34 * 256 + 247] = 34; + table[33 * 256 + 248] = 34; + table[34 * 256 + 248] = 34; + table[33 * 256 + 249] = 34; + table[34 * 256 + 249] = 34; + table[33 * 256 + 250] = 34; + table[34 * 256 + 250] = 34; + table[33 * 256 + 251] = 34; + table[34 * 256 + 251] = 34; + table[33 * 256 + 252] = 34; + table[34 * 256 + 252] = 34; + table[33 * 256 + 253] = 34; + table[34 * 256 + 253] = 34; + table[33 * 256 + 254] = 34; + table[34 * 256 + 254] = 34; + table[0 * 256 + 13] = 1; + table[0 * 256 + 255] = 2; + table[1 * 256 + 10] = 2; + table[2 * 256 + 100] = 3; + table[3 * 256 + 107] = 4; + table[4 * 256 + 105] = 5; + table[5 * 256 + 109] = 6; + table[6 * 256 + 45] = 7; + table[7 * 256 + 115] = 8; + table[8 * 256 + 105] = 9; + table[9 * 256 + 103] = 10; + table[10 * 256 + 110] = 11; + table[11 * 256 + 97] = 12; + table[12 * 256 + 116] = 13; + table[13 * 256 + 117] = 14; + table[14 * 256 + 114] = 15; + table[15 * 256 + 101] = 16; + table[16 * 256 + 58] = 17; + table[17 * 256 + 97] = 18; + table[17 * 256 + 98] = 18; + table[17 * 256 + 99] = 18; + table[17 * 256 + 100] = 18; + table[17 * 256 + 101] = 18; + table[17 * 256 + 102] = 18; + table[17 * 256 + 103] = 18; + table[17 * 256 + 104] = 18; + table[17 * 256 + 105] = 18; + table[17 * 256 + 106] = 18; + table[17 * 256 + 107] = 18; + table[17 * 256 + 108] = 18; + table[17 * 256 + 109] = 18; + table[17 * 256 + 110] = 18; + table[17 * 256 + 111] = 18; + table[17 * 256 + 112] = 18; + table[17 * 256 + 113] = 18; + table[17 * 256 + 114] = 18; + table[17 * 256 + 115] = 18; + table[17 * 256 + 116] = 18; + table[17 * 256 + 117] = 18; + table[17 * 256 + 118] = 18; + table[17 * 256 + 119] = 18; + table[17 * 256 + 120] = 18; + table[17 * 256 + 121] = 18; + table[17 * 256 + 122] = 18; + table[18 * 256 + 97] = 18; + table[18 * 256 + 98] = 18; + table[18 * 256 + 99] = 18; + table[18 * 256 + 100] = 18; + table[18 * 256 + 101] = 18; + table[18 * 256 + 102] = 18; + table[18 * 256 + 103] = 18; + table[18 * 256 + 104] = 18; + table[18 * 256 + 105] = 18; + table[18 * 256 + 106] = 18; + table[18 * 256 + 107] = 18; + table[18 * 256 + 108] = 18; + table[18 * 256 + 109] = 18; + table[18 * 256 + 110] = 18; + table[18 * 256 + 111] = 18; + table[18 * 256 + 112] = 18; + table[18 * 256 + 113] = 18; + table[18 * 256 + 114] = 18; + table[18 * 256 + 115] = 18; + table[18 * 256 + 116] = 18; + table[18 * 256 + 117] = 18; + table[18 * 256 + 118] = 18; + table[18 * 256 + 119] = 18; + table[18 * 256 + 120] = 18; + table[18 * 256 + 121] = 18; + table[18 * 256 + 122] = 18; + table[18 * 256 + 61] = 19; + table[19 * 256 + 0] = 20; + table[19 * 256 + 1] = 20; + table[19 * 256 + 2] = 20; + table[19 * 256 + 3] = 20; + table[19 * 256 + 4] = 20; + table[19 * 256 + 5] = 20; + table[19 * 256 + 6] = 20; + table[19 * 256 + 7] = 20; + table[19 * 256 + 8] = 20; + table[19 * 256 + 9] = 20; + table[19 * 256 + 10] = 20; + table[19 * 256 + 11] = 20; + table[19 * 256 + 12] = 20; + table[19 * 256 + 13] = 20; + table[19 * 256 + 14] = 20; + table[19 * 256 + 15] = 20; + table[19 * 256 + 16] = 20; + table[19 * 256 + 17] = 20; + table[19 * 256 + 18] = 20; + table[19 * 256 + 19] = 20; + table[19 * 256 + 20] = 20; + table[19 * 256 + 21] = 20; + table[19 * 256 + 22] = 20; + table[19 * 256 + 23] = 20; + table[19 * 256 + 24] = 20; + table[19 * 256 + 25] = 20; + table[19 * 256 + 26] = 20; + table[19 * 256 + 27] = 20; + table[19 * 256 + 28] = 20; + table[19 * 256 + 29] = 20; + table[19 * 256 + 30] = 20; + table[19 * 256 + 31] = 20; + table[19 * 256 + 32] = 20; + table[19 * 256 + 33] = 20; + table[19 * 256 + 34] = 20; + table[19 * 256 + 35] = 20; + table[19 * 256 + 36] = 20; + table[19 * 256 + 37] = 20; + table[19 * 256 + 38] = 20; + table[19 * 256 + 39] = 20; + table[19 * 256 + 40] = 20; + table[19 * 256 + 41] = 20; + table[19 * 256 + 42] = 20; + table[19 * 256 + 43] = 20; + table[19 * 256 + 44] = 20; + table[19 * 256 + 45] = 20; + table[19 * 256 + 46] = 20; + table[19 * 256 + 47] = 20; + table[19 * 256 + 48] = 20; + table[19 * 256 + 49] = 20; + table[19 * 256 + 50] = 20; + table[19 * 256 + 51] = 20; + table[19 * 256 + 52] = 20; + table[19 * 256 + 53] = 20; + table[19 * 256 + 54] = 20; + table[19 * 256 + 55] = 20; + table[19 * 256 + 56] = 20; + table[19 * 256 + 57] = 20; + table[19 * 256 + 58] = 20; + table[19 * 256 + 60] = 20; + table[19 * 256 + 61] = 20; + table[19 * 256 + 62] = 20; + table[19 * 256 + 63] = 20; + table[19 * 256 + 64] = 20; + table[19 * 256 + 65] = 20; + table[19 * 256 + 66] = 20; + table[19 * 256 + 67] = 20; + table[19 * 256 + 68] = 20; + table[19 * 256 + 69] = 20; + table[19 * 256 + 70] = 20; + table[19 * 256 + 71] = 20; + table[19 * 256 + 72] = 20; + table[19 * 256 + 73] = 20; + table[19 * 256 + 74] = 20; + table[19 * 256 + 75] = 20; + table[19 * 256 + 76] = 20; + table[19 * 256 + 77] = 20; + table[19 * 256 + 78] = 20; + table[19 * 256 + 79] = 20; + table[19 * 256 + 80] = 20; + table[19 * 256 + 81] = 20; + table[19 * 256 + 82] = 20; + table[19 * 256 + 83] = 20; + table[19 * 256 + 84] = 20; + table[19 * 256 + 85] = 20; + table[19 * 256 + 86] = 20; + table[19 * 256 + 87] = 20; + table[19 * 256 + 88] = 20; + table[19 * 256 + 89] = 20; + table[19 * 256 + 90] = 20; + table[19 * 256 + 91] = 20; + table[19 * 256 + 92] = 20; + table[19 * 256 + 93] = 20; + table[19 * 256 + 94] = 20; + table[19 * 256 + 95] = 20; + table[19 * 256 + 96] = 20; + table[19 * 256 + 97] = 20; + table[19 * 256 + 98] = 20; + table[19 * 256 + 99] = 20; + table[19 * 256 + 100] = 20; + table[19 * 256 + 101] = 20; + table[19 * 256 + 102] = 20; + table[19 * 256 + 103] = 20; + table[19 * 256 + 104] = 20; + table[19 * 256 + 105] = 20; + table[19 * 256 + 106] = 20; + table[19 * 256 + 107] = 20; + table[19 * 256 + 108] = 20; + table[19 * 256 + 109] = 20; + table[19 * 256 + 110] = 20; + table[19 * 256 + 111] = 20; + table[19 * 256 + 112] = 20; + table[19 * 256 + 113] = 20; + table[19 * 256 + 114] = 20; + table[19 * 256 + 115] = 20; + table[19 * 256 + 116] = 20; + table[19 * 256 + 117] = 20; + table[19 * 256 + 118] = 20; + table[19 * 256 + 119] = 20; + table[19 * 256 + 120] = 20; + table[19 * 256 + 121] = 20; + table[19 * 256 + 122] = 20; + table[19 * 256 + 123] = 20; + table[19 * 256 + 124] = 20; + table[19 * 256 + 125] = 20; + table[19 * 256 + 126] = 20; + table[19 * 256 + 127] = 20; + table[19 * 256 + 194] = 21; + table[19 * 256 + 195] = 21; + table[19 * 256 + 196] = 21; + table[19 * 256 + 197] = 21; + table[19 * 256 + 198] = 21; + table[19 * 256 + 199] = 21; + table[19 * 256 + 200] = 21; + table[19 * 256 + 201] = 21; + table[19 * 256 + 202] = 21; + table[19 * 256 + 203] = 21; + table[19 * 256 + 204] = 21; + table[19 * 256 + 205] = 21; + table[19 * 256 + 206] = 21; + table[19 * 256 + 207] = 21; + table[19 * 256 + 208] = 21; + table[19 * 256 + 209] = 21; + table[19 * 256 + 210] = 21; + table[19 * 256 + 211] = 21; + table[19 * 256 + 212] = 21; + table[19 * 256 + 213] = 21; + table[19 * 256 + 214] = 21; + table[19 * 256 + 215] = 21; + table[19 * 256 + 216] = 21; + table[19 * 256 + 217] = 21; + table[19 * 256 + 218] = 21; + table[19 * 256 + 219] = 21; + table[19 * 256 + 220] = 21; + table[19 * 256 + 221] = 21; + table[19 * 256 + 222] = 21; + table[19 * 256 + 223] = 21; + table[19 * 256 + 224] = 22; + table[19 * 256 + 225] = 23; + table[19 * 256 + 226] = 23; + table[19 * 256 + 227] = 23; + table[19 * 256 + 228] = 23; + table[19 * 256 + 229] = 23; + table[19 * 256 + 230] = 23; + table[19 * 256 + 231] = 23; + table[19 * 256 + 232] = 23; + table[19 * 256 + 233] = 23; + table[19 * 256 + 234] = 23; + table[19 * 256 + 235] = 23; + table[19 * 256 + 236] = 23; + table[19 * 256 + 238] = 23; + table[19 * 256 + 239] = 23; + table[19 * 256 + 237] = 24; + table[19 * 256 + 240] = 25; + table[19 * 256 + 241] = 26; + table[19 * 256 + 242] = 26; + table[19 * 256 + 243] = 26; + table[19 * 256 + 244] = 27; + table[20 * 256 + 0] = 20; + table[20 * 256 + 1] = 20; + table[20 * 256 + 2] = 20; + table[20 * 256 + 3] = 20; + table[20 * 256 + 4] = 20; + table[20 * 256 + 5] = 20; + table[20 * 256 + 6] = 20; + table[20 * 256 + 7] = 20; + table[20 * 256 + 8] = 20; + table[20 * 256 + 9] = 20; + table[20 * 256 + 10] = 20; + table[20 * 256 + 11] = 20; + table[20 * 256 + 12] = 20; + table[20 * 256 + 13] = 20; + table[20 * 256 + 14] = 20; + table[20 * 256 + 15] = 20; + table[20 * 256 + 16] = 20; + table[20 * 256 + 17] = 20; + table[20 * 256 + 18] = 20; + table[20 * 256 + 19] = 20; + table[20 * 256 + 20] = 20; + table[20 * 256 + 21] = 20; + table[20 * 256 + 22] = 20; + table[20 * 256 + 23] = 20; + table[20 * 256 + 24] = 20; + table[20 * 256 + 25] = 20; + table[20 * 256 + 26] = 20; + table[20 * 256 + 27] = 20; + table[20 * 256 + 28] = 20; + table[20 * 256 + 29] = 20; + table[20 * 256 + 30] = 20; + table[20 * 256 + 31] = 20; + table[20 * 256 + 32] = 20; + table[20 * 256 + 33] = 20; + table[20 * 256 + 34] = 20; + table[20 * 256 + 35] = 20; + table[20 * 256 + 36] = 20; + table[20 * 256 + 37] = 20; + table[20 * 256 + 38] = 20; + table[20 * 256 + 39] = 20; + table[20 * 256 + 40] = 20; + table[20 * 256 + 41] = 20; + table[20 * 256 + 42] = 20; + table[20 * 256 + 43] = 20; + table[20 * 256 + 44] = 20; + table[20 * 256 + 45] = 20; + table[20 * 256 + 46] = 20; + table[20 * 256 + 47] = 20; + table[20 * 256 + 48] = 20; + table[20 * 256 + 49] = 20; + table[20 * 256 + 50] = 20; + table[20 * 256 + 51] = 20; + table[20 * 256 + 52] = 20; + table[20 * 256 + 53] = 20; + table[20 * 256 + 54] = 20; + table[20 * 256 + 55] = 20; + table[20 * 256 + 56] = 20; + table[20 * 256 + 57] = 20; + table[20 * 256 + 58] = 20; + table[20 * 256 + 60] = 20; + table[20 * 256 + 61] = 20; + table[20 * 256 + 62] = 20; + table[20 * 256 + 63] = 20; + table[20 * 256 + 64] = 20; + table[20 * 256 + 65] = 20; + table[20 * 256 + 66] = 20; + table[20 * 256 + 67] = 20; + table[20 * 256 + 68] = 20; + table[20 * 256 + 69] = 20; + table[20 * 256 + 70] = 20; + table[20 * 256 + 71] = 20; + table[20 * 256 + 72] = 20; + table[20 * 256 + 73] = 20; + table[20 * 256 + 74] = 20; + table[20 * 256 + 75] = 20; + table[20 * 256 + 76] = 20; + table[20 * 256 + 77] = 20; + table[20 * 256 + 78] = 20; + table[20 * 256 + 79] = 20; + table[20 * 256 + 80] = 20; + table[20 * 256 + 81] = 20; + table[20 * 256 + 82] = 20; + table[20 * 256 + 83] = 20; + table[20 * 256 + 84] = 20; + table[20 * 256 + 85] = 20; + table[20 * 256 + 86] = 20; + table[20 * 256 + 87] = 20; + table[20 * 256 + 88] = 20; + table[20 * 256 + 89] = 20; + table[20 * 256 + 90] = 20; + table[20 * 256 + 91] = 20; + table[20 * 256 + 92] = 20; + table[20 * 256 + 93] = 20; + table[20 * 256 + 94] = 20; + table[20 * 256 + 95] = 20; + table[20 * 256 + 96] = 20; + table[20 * 256 + 97] = 20; + table[20 * 256 + 98] = 20; + table[20 * 256 + 99] = 20; + table[20 * 256 + 100] = 20; + table[20 * 256 + 101] = 20; + table[20 * 256 + 102] = 20; + table[20 * 256 + 103] = 20; + table[20 * 256 + 104] = 20; + table[20 * 256 + 105] = 20; + table[20 * 256 + 106] = 20; + table[20 * 256 + 107] = 20; + table[20 * 256 + 108] = 20; + table[20 * 256 + 109] = 20; + table[20 * 256 + 110] = 20; + table[20 * 256 + 111] = 20; + table[20 * 256 + 112] = 20; + table[20 * 256 + 113] = 20; + table[20 * 256 + 114] = 20; + table[20 * 256 + 115] = 20; + table[20 * 256 + 116] = 20; + table[20 * 256 + 117] = 20; + table[20 * 256 + 118] = 20; + table[20 * 256 + 119] = 20; + table[20 * 256 + 120] = 20; + table[20 * 256 + 121] = 20; + table[20 * 256 + 122] = 20; + table[20 * 256 + 123] = 20; + table[20 * 256 + 124] = 20; + table[20 * 256 + 125] = 20; + table[20 * 256 + 126] = 20; + table[20 * 256 + 127] = 20; + table[20 * 256 + 194] = 21; + table[20 * 256 + 195] = 21; + table[20 * 256 + 196] = 21; + table[20 * 256 + 197] = 21; + table[20 * 256 + 198] = 21; + table[20 * 256 + 199] = 21; + table[20 * 256 + 200] = 21; + table[20 * 256 + 201] = 21; + table[20 * 256 + 202] = 21; + table[20 * 256 + 203] = 21; + table[20 * 256 + 204] = 21; + table[20 * 256 + 205] = 21; + table[20 * 256 + 206] = 21; + table[20 * 256 + 207] = 21; + table[20 * 256 + 208] = 21; + table[20 * 256 + 209] = 21; + table[20 * 256 + 210] = 21; + table[20 * 256 + 211] = 21; + table[20 * 256 + 212] = 21; + table[20 * 256 + 213] = 21; + table[20 * 256 + 214] = 21; + table[20 * 256 + 215] = 21; + table[20 * 256 + 216] = 21; + table[20 * 256 + 217] = 21; + table[20 * 256 + 218] = 21; + table[20 * 256 + 219] = 21; + table[20 * 256 + 220] = 21; + table[20 * 256 + 221] = 21; + table[20 * 256 + 222] = 21; + table[20 * 256 + 223] = 21; + table[20 * 256 + 224] = 22; + table[20 * 256 + 225] = 23; + table[20 * 256 + 226] = 23; + table[20 * 256 + 227] = 23; + table[20 * 256 + 228] = 23; + table[20 * 256 + 229] = 23; + table[20 * 256 + 230] = 23; + table[20 * 256 + 231] = 23; + table[20 * 256 + 232] = 23; + table[20 * 256 + 233] = 23; + table[20 * 256 + 234] = 23; + table[20 * 256 + 235] = 23; + table[20 * 256 + 236] = 23; + table[20 * 256 + 238] = 23; + table[20 * 256 + 239] = 23; + table[20 * 256 + 237] = 24; + table[20 * 256 + 240] = 25; + table[20 * 256 + 241] = 26; + table[20 * 256 + 242] = 26; + table[20 * 256 + 243] = 26; + table[20 * 256 + 244] = 27; + table[20 * 256 + 59] = 28; + table[21 * 256 + 128] = 20; + table[21 * 256 + 129] = 20; + table[21 * 256 + 130] = 20; + table[21 * 256 + 131] = 20; + table[21 * 256 + 132] = 20; + table[21 * 256 + 133] = 20; + table[21 * 256 + 134] = 20; + table[21 * 256 + 135] = 20; + table[21 * 256 + 136] = 20; + table[21 * 256 + 137] = 20; + table[21 * 256 + 138] = 20; + table[21 * 256 + 139] = 20; + table[21 * 256 + 140] = 20; + table[21 * 256 + 141] = 20; + table[21 * 256 + 142] = 20; + table[21 * 256 + 143] = 20; + table[21 * 256 + 144] = 20; + table[21 * 256 + 145] = 20; + table[21 * 256 + 146] = 20; + table[21 * 256 + 147] = 20; + table[21 * 256 + 148] = 20; + table[21 * 256 + 149] = 20; + table[21 * 256 + 150] = 20; + table[21 * 256 + 151] = 20; + table[21 * 256 + 152] = 20; + table[21 * 256 + 153] = 20; + table[21 * 256 + 154] = 20; + table[21 * 256 + 155] = 20; + table[21 * 256 + 156] = 20; + table[21 * 256 + 157] = 20; + table[21 * 256 + 158] = 20; + table[21 * 256 + 159] = 20; + table[21 * 256 + 160] = 20; + table[21 * 256 + 161] = 20; + table[21 * 256 + 162] = 20; + table[21 * 256 + 163] = 20; + table[21 * 256 + 164] = 20; + table[21 * 256 + 165] = 20; + table[21 * 256 + 166] = 20; + table[21 * 256 + 167] = 20; + table[21 * 256 + 168] = 20; + table[21 * 256 + 169] = 20; + table[21 * 256 + 170] = 20; + table[21 * 256 + 171] = 20; + table[21 * 256 + 172] = 20; + table[21 * 256 + 173] = 20; + table[21 * 256 + 174] = 20; + table[21 * 256 + 175] = 20; + table[21 * 256 + 176] = 20; + table[21 * 256 + 177] = 20; + table[21 * 256 + 178] = 20; + table[21 * 256 + 179] = 20; + table[21 * 256 + 180] = 20; + table[21 * 256 + 181] = 20; + table[21 * 256 + 182] = 20; + table[21 * 256 + 183] = 20; + table[21 * 256 + 184] = 20; + table[21 * 256 + 185] = 20; + table[21 * 256 + 186] = 20; + table[21 * 256 + 187] = 20; + table[21 * 256 + 188] = 20; + table[21 * 256 + 189] = 20; + table[21 * 256 + 190] = 20; + table[21 * 256 + 191] = 20; + table[22 * 256 + 160] = 21; + table[22 * 256 + 161] = 21; + table[22 * 256 + 162] = 21; + table[22 * 256 + 163] = 21; + table[22 * 256 + 164] = 21; + table[22 * 256 + 165] = 21; + table[22 * 256 + 166] = 21; + table[22 * 256 + 167] = 21; + table[22 * 256 + 168] = 21; + table[22 * 256 + 169] = 21; + table[22 * 256 + 170] = 21; + table[22 * 256 + 171] = 21; + table[22 * 256 + 172] = 21; + table[22 * 256 + 173] = 21; + table[22 * 256 + 174] = 21; + table[22 * 256 + 175] = 21; + table[22 * 256 + 176] = 21; + table[22 * 256 + 177] = 21; + table[22 * 256 + 178] = 21; + table[22 * 256 + 179] = 21; + table[22 * 256 + 180] = 21; + table[22 * 256 + 181] = 21; + table[22 * 256 + 182] = 21; + table[22 * 256 + 183] = 21; + table[22 * 256 + 184] = 21; + table[22 * 256 + 185] = 21; + table[22 * 256 + 186] = 21; + table[22 * 256 + 187] = 21; + table[22 * 256 + 188] = 21; + table[22 * 256 + 189] = 21; + table[22 * 256 + 190] = 21; + table[22 * 256 + 191] = 21; + table[23 * 256 + 128] = 21; + table[23 * 256 + 129] = 21; + table[23 * 256 + 130] = 21; + table[23 * 256 + 131] = 21; + table[23 * 256 + 132] = 21; + table[23 * 256 + 133] = 21; + table[23 * 256 + 134] = 21; + table[23 * 256 + 135] = 21; + table[23 * 256 + 136] = 21; + table[23 * 256 + 137] = 21; + table[23 * 256 + 138] = 21; + table[23 * 256 + 139] = 21; + table[23 * 256 + 140] = 21; + table[23 * 256 + 141] = 21; + table[23 * 256 + 142] = 21; + table[23 * 256 + 143] = 21; + table[23 * 256 + 144] = 21; + table[23 * 256 + 145] = 21; + table[23 * 256 + 146] = 21; + table[23 * 256 + 147] = 21; + table[23 * 256 + 148] = 21; + table[23 * 256 + 149] = 21; + table[23 * 256 + 150] = 21; + table[23 * 256 + 151] = 21; + table[23 * 256 + 152] = 21; + table[23 * 256 + 153] = 21; + table[23 * 256 + 154] = 21; + table[23 * 256 + 155] = 21; + table[23 * 256 + 156] = 21; + table[23 * 256 + 157] = 21; + table[23 * 256 + 158] = 21; + table[23 * 256 + 159] = 21; + table[23 * 256 + 160] = 21; + table[23 * 256 + 161] = 21; + table[23 * 256 + 162] = 21; + table[23 * 256 + 163] = 21; + table[23 * 256 + 164] = 21; + table[23 * 256 + 165] = 21; + table[23 * 256 + 166] = 21; + table[23 * 256 + 167] = 21; + table[23 * 256 + 168] = 21; + table[23 * 256 + 169] = 21; + table[23 * 256 + 170] = 21; + table[23 * 256 + 171] = 21; + table[23 * 256 + 172] = 21; + table[23 * 256 + 173] = 21; + table[23 * 256 + 174] = 21; + table[23 * 256 + 175] = 21; + table[23 * 256 + 176] = 21; + table[23 * 256 + 177] = 21; + table[23 * 256 + 178] = 21; + table[23 * 256 + 179] = 21; + table[23 * 256 + 180] = 21; + table[23 * 256 + 181] = 21; + table[23 * 256 + 182] = 21; + table[23 * 256 + 183] = 21; + table[23 * 256 + 184] = 21; + table[23 * 256 + 185] = 21; + table[23 * 256 + 186] = 21; + table[23 * 256 + 187] = 21; + table[23 * 256 + 188] = 21; + table[23 * 256 + 189] = 21; + table[23 * 256 + 190] = 21; + table[23 * 256 + 191] = 21; + table[24 * 256 + 128] = 21; + table[24 * 256 + 129] = 21; + table[24 * 256 + 130] = 21; + table[24 * 256 + 131] = 21; + table[24 * 256 + 132] = 21; + table[24 * 256 + 133] = 21; + table[24 * 256 + 134] = 21; + table[24 * 256 + 135] = 21; + table[24 * 256 + 136] = 21; + table[24 * 256 + 137] = 21; + table[24 * 256 + 138] = 21; + table[24 * 256 + 139] = 21; + table[24 * 256 + 140] = 21; + table[24 * 256 + 141] = 21; + table[24 * 256 + 142] = 21; + table[24 * 256 + 143] = 21; + table[24 * 256 + 144] = 21; + table[24 * 256 + 145] = 21; + table[24 * 256 + 146] = 21; + table[24 * 256 + 147] = 21; + table[24 * 256 + 148] = 21; + table[24 * 256 + 149] = 21; + table[24 * 256 + 150] = 21; + table[24 * 256 + 151] = 21; + table[24 * 256 + 152] = 21; + table[24 * 256 + 153] = 21; + table[24 * 256 + 154] = 21; + table[24 * 256 + 155] = 21; + table[24 * 256 + 156] = 21; + table[24 * 256 + 157] = 21; + table[24 * 256 + 158] = 21; + table[24 * 256 + 159] = 21; + table[25 * 256 + 144] = 23; + table[25 * 256 + 145] = 23; + table[25 * 256 + 146] = 23; + table[25 * 256 + 147] = 23; + table[25 * 256 + 148] = 23; + table[25 * 256 + 149] = 23; + table[25 * 256 + 150] = 23; + table[25 * 256 + 151] = 23; + table[25 * 256 + 152] = 23; + table[25 * 256 + 153] = 23; + table[25 * 256 + 154] = 23; + table[25 * 256 + 155] = 23; + table[25 * 256 + 156] = 23; + table[25 * 256 + 157] = 23; + table[25 * 256 + 158] = 23; + table[25 * 256 + 159] = 23; + table[25 * 256 + 160] = 23; + table[25 * 256 + 161] = 23; + table[25 * 256 + 162] = 23; + table[25 * 256 + 163] = 23; + table[25 * 256 + 164] = 23; + table[25 * 256 + 165] = 23; + table[25 * 256 + 166] = 23; + table[25 * 256 + 167] = 23; + table[25 * 256 + 168] = 23; + table[25 * 256 + 169] = 23; + table[25 * 256 + 170] = 23; + table[25 * 256 + 171] = 23; + table[25 * 256 + 172] = 23; + table[25 * 256 + 173] = 23; + table[25 * 256 + 174] = 23; + table[25 * 256 + 175] = 23; + table[25 * 256 + 176] = 23; + table[25 * 256 + 177] = 23; + table[25 * 256 + 178] = 23; + table[25 * 256 + 179] = 23; + table[25 * 256 + 180] = 23; + table[25 * 256 + 181] = 23; + table[25 * 256 + 182] = 23; + table[25 * 256 + 183] = 23; + table[25 * 256 + 184] = 23; + table[25 * 256 + 185] = 23; + table[25 * 256 + 186] = 23; + table[25 * 256 + 187] = 23; + table[25 * 256 + 188] = 23; + table[25 * 256 + 189] = 23; + table[25 * 256 + 190] = 23; + table[25 * 256 + 191] = 23; + table[26 * 256 + 128] = 23; + table[26 * 256 + 129] = 23; + table[26 * 256 + 130] = 23; + table[26 * 256 + 131] = 23; + table[26 * 256 + 132] = 23; + table[26 * 256 + 133] = 23; + table[26 * 256 + 134] = 23; + table[26 * 256 + 135] = 23; + table[26 * 256 + 136] = 23; + table[26 * 256 + 137] = 23; + table[26 * 256 + 138] = 23; + table[26 * 256 + 139] = 23; + table[26 * 256 + 140] = 23; + table[26 * 256 + 141] = 23; + table[26 * 256 + 142] = 23; + table[26 * 256 + 143] = 23; + table[26 * 256 + 144] = 23; + table[26 * 256 + 145] = 23; + table[26 * 256 + 146] = 23; + table[26 * 256 + 147] = 23; + table[26 * 256 + 148] = 23; + table[26 * 256 + 149] = 23; + table[26 * 256 + 150] = 23; + table[26 * 256 + 151] = 23; + table[26 * 256 + 152] = 23; + table[26 * 256 + 153] = 23; + table[26 * 256 + 154] = 23; + table[26 * 256 + 155] = 23; + table[26 * 256 + 156] = 23; + table[26 * 256 + 157] = 23; + table[26 * 256 + 158] = 23; + table[26 * 256 + 159] = 23; + table[26 * 256 + 160] = 23; + table[26 * 256 + 161] = 23; + table[26 * 256 + 162] = 23; + table[26 * 256 + 163] = 23; + table[26 * 256 + 164] = 23; + table[26 * 256 + 165] = 23; + table[26 * 256 + 166] = 23; + table[26 * 256 + 167] = 23; + table[26 * 256 + 168] = 23; + table[26 * 256 + 169] = 23; + table[26 * 256 + 170] = 23; + table[26 * 256 + 171] = 23; + table[26 * 256 + 172] = 23; + table[26 * 256 + 173] = 23; + table[26 * 256 + 174] = 23; + table[26 * 256 + 175] = 23; + table[26 * 256 + 176] = 23; + table[26 * 256 + 177] = 23; + table[26 * 256 + 178] = 23; + table[26 * 256 + 179] = 23; + table[26 * 256 + 180] = 23; + table[26 * 256 + 181] = 23; + table[26 * 256 + 182] = 23; + table[26 * 256 + 183] = 23; + table[26 * 256 + 184] = 23; + table[26 * 256 + 185] = 23; + table[26 * 256 + 186] = 23; + table[26 * 256 + 187] = 23; + table[26 * 256 + 188] = 23; + table[26 * 256 + 189] = 23; + table[26 * 256 + 190] = 23; + table[26 * 256 + 191] = 23; + table[27 * 256 + 128] = 23; + table[27 * 256 + 129] = 23; + table[27 * 256 + 130] = 23; + table[27 * 256 + 131] = 23; + table[27 * 256 + 132] = 23; + table[27 * 256 + 133] = 23; + table[27 * 256 + 134] = 23; + table[27 * 256 + 135] = 23; + table[27 * 256 + 136] = 23; + table[27 * 256 + 137] = 23; + table[27 * 256 + 138] = 23; + table[27 * 256 + 139] = 23; + table[27 * 256 + 140] = 23; + table[27 * 256 + 141] = 23; + table[27 * 256 + 142] = 23; + table[27 * 256 + 143] = 23; + table[28 * 256 + 32] = 29; + table[29 * 256 + 97] = 18; + table[29 * 256 + 98] = 18; + table[29 * 256 + 99] = 18; + table[29 * 256 + 100] = 18; + table[29 * 256 + 101] = 18; + table[29 * 256 + 102] = 18; + table[29 * 256 + 103] = 18; + table[29 * 256 + 104] = 18; + table[29 * 256 + 105] = 18; + table[29 * 256 + 106] = 18; + table[29 * 256 + 107] = 18; + table[29 * 256 + 108] = 18; + table[29 * 256 + 109] = 18; + table[29 * 256 + 110] = 18; + table[29 * 256 + 111] = 18; + table[29 * 256 + 112] = 18; + table[29 * 256 + 113] = 18; + table[29 * 256 + 114] = 18; + table[29 * 256 + 115] = 18; + table[29 * 256 + 117] = 18; + table[29 * 256 + 118] = 18; + table[29 * 256 + 119] = 18; + table[29 * 256 + 120] = 18; + table[29 * 256 + 121] = 18; + table[29 * 256 + 122] = 18; + table[29 * 256 + 116] = 30; + table[30 * 256 + 97] = 18; + table[30 * 256 + 98] = 18; + table[30 * 256 + 99] = 18; + table[30 * 256 + 100] = 18; + table[30 * 256 + 101] = 18; + table[30 * 256 + 102] = 18; + table[30 * 256 + 103] = 18; + table[30 * 256 + 104] = 18; + table[30 * 256 + 105] = 18; + table[30 * 256 + 106] = 18; + table[30 * 256 + 107] = 18; + table[30 * 256 + 108] = 18; + table[30 * 256 + 109] = 18; + table[30 * 256 + 110] = 18; + table[30 * 256 + 111] = 18; + table[30 * 256 + 112] = 18; + table[30 * 256 + 113] = 18; + table[30 * 256 + 114] = 18; + table[30 * 256 + 115] = 18; + table[30 * 256 + 116] = 18; + table[30 * 256 + 117] = 18; + table[30 * 256 + 118] = 18; + table[30 * 256 + 119] = 18; + table[30 * 256 + 120] = 18; + table[30 * 256 + 121] = 18; + table[30 * 256 + 122] = 18; + table[30 * 256 + 61] = 31; + table[31 * 256 + 0] = 20; + table[31 * 256 + 1] = 20; + table[31 * 256 + 2] = 20; + table[31 * 256 + 3] = 20; + table[31 * 256 + 4] = 20; + table[31 * 256 + 5] = 20; + table[31 * 256 + 6] = 20; + table[31 * 256 + 7] = 20; + table[31 * 256 + 8] = 20; + table[31 * 256 + 9] = 20; + table[31 * 256 + 10] = 20; + table[31 * 256 + 11] = 20; + table[31 * 256 + 12] = 20; + table[31 * 256 + 13] = 20; + table[31 * 256 + 14] = 20; + table[31 * 256 + 15] = 20; + table[31 * 256 + 16] = 20; + table[31 * 256 + 17] = 20; + table[31 * 256 + 18] = 20; + table[31 * 256 + 19] = 20; + table[31 * 256 + 20] = 20; + table[31 * 256 + 21] = 20; + table[31 * 256 + 22] = 20; + table[31 * 256 + 23] = 20; + table[31 * 256 + 24] = 20; + table[31 * 256 + 25] = 20; + table[31 * 256 + 26] = 20; + table[31 * 256 + 27] = 20; + table[31 * 256 + 28] = 20; + table[31 * 256 + 29] = 20; + table[31 * 256 + 30] = 20; + table[31 * 256 + 31] = 20; + table[31 * 256 + 32] = 20; + table[31 * 256 + 33] = 20; + table[31 * 256 + 34] = 20; + table[31 * 256 + 35] = 20; + table[31 * 256 + 36] = 20; + table[31 * 256 + 37] = 20; + table[31 * 256 + 38] = 20; + table[31 * 256 + 39] = 20; + table[31 * 256 + 40] = 20; + table[31 * 256 + 41] = 20; + table[31 * 256 + 42] = 20; + table[31 * 256 + 43] = 20; + table[31 * 256 + 44] = 20; + table[31 * 256 + 45] = 20; + table[31 * 256 + 46] = 20; + table[31 * 256 + 47] = 20; + table[31 * 256 + 58] = 20; + table[31 * 256 + 60] = 20; + table[31 * 256 + 61] = 20; + table[31 * 256 + 62] = 20; + table[31 * 256 + 63] = 20; + table[31 * 256 + 64] = 20; + table[31 * 256 + 65] = 20; + table[31 * 256 + 66] = 20; + table[31 * 256 + 67] = 20; + table[31 * 256 + 68] = 20; + table[31 * 256 + 69] = 20; + table[31 * 256 + 70] = 20; + table[31 * 256 + 71] = 20; + table[31 * 256 + 72] = 20; + table[31 * 256 + 73] = 20; + table[31 * 256 + 74] = 20; + table[31 * 256 + 75] = 20; + table[31 * 256 + 76] = 20; + table[31 * 256 + 77] = 20; + table[31 * 256 + 78] = 20; + table[31 * 256 + 79] = 20; + table[31 * 256 + 80] = 20; + table[31 * 256 + 81] = 20; + table[31 * 256 + 82] = 20; + table[31 * 256 + 83] = 20; + table[31 * 256 + 84] = 20; + table[31 * 256 + 85] = 20; + table[31 * 256 + 86] = 20; + table[31 * 256 + 87] = 20; + table[31 * 256 + 88] = 20; + table[31 * 256 + 89] = 20; + table[31 * 256 + 90] = 20; + table[31 * 256 + 91] = 20; + table[31 * 256 + 92] = 20; + table[31 * 256 + 93] = 20; + table[31 * 256 + 94] = 20; + table[31 * 256 + 95] = 20; + table[31 * 256 + 96] = 20; + table[31 * 256 + 97] = 20; + table[31 * 256 + 98] = 20; + table[31 * 256 + 99] = 20; + table[31 * 256 + 100] = 20; + table[31 * 256 + 101] = 20; + table[31 * 256 + 102] = 20; + table[31 * 256 + 103] = 20; + table[31 * 256 + 104] = 20; + table[31 * 256 + 105] = 20; + table[31 * 256 + 106] = 20; + table[31 * 256 + 107] = 20; + table[31 * 256 + 108] = 20; + table[31 * 256 + 109] = 20; + table[31 * 256 + 110] = 20; + table[31 * 256 + 111] = 20; + table[31 * 256 + 112] = 20; + table[31 * 256 + 113] = 20; + table[31 * 256 + 114] = 20; + table[31 * 256 + 115] = 20; + table[31 * 256 + 116] = 20; + table[31 * 256 + 117] = 20; + table[31 * 256 + 118] = 20; + table[31 * 256 + 119] = 20; + table[31 * 256 + 120] = 20; + table[31 * 256 + 121] = 20; + table[31 * 256 + 122] = 20; + table[31 * 256 + 123] = 20; + table[31 * 256 + 124] = 20; + table[31 * 256 + 125] = 20; + table[31 * 256 + 126] = 20; + table[31 * 256 + 127] = 20; + table[31 * 256 + 194] = 21; + table[31 * 256 + 195] = 21; + table[31 * 256 + 196] = 21; + table[31 * 256 + 197] = 21; + table[31 * 256 + 198] = 21; + table[31 * 256 + 199] = 21; + table[31 * 256 + 200] = 21; + table[31 * 256 + 201] = 21; + table[31 * 256 + 202] = 21; + table[31 * 256 + 203] = 21; + table[31 * 256 + 204] = 21; + table[31 * 256 + 205] = 21; + table[31 * 256 + 206] = 21; + table[31 * 256 + 207] = 21; + table[31 * 256 + 208] = 21; + table[31 * 256 + 209] = 21; + table[31 * 256 + 210] = 21; + table[31 * 256 + 211] = 21; + table[31 * 256 + 212] = 21; + table[31 * 256 + 213] = 21; + table[31 * 256 + 214] = 21; + table[31 * 256 + 215] = 21; + table[31 * 256 + 216] = 21; + table[31 * 256 + 217] = 21; + table[31 * 256 + 218] = 21; + table[31 * 256 + 219] = 21; + table[31 * 256 + 220] = 21; + table[31 * 256 + 221] = 21; + table[31 * 256 + 222] = 21; + table[31 * 256 + 223] = 21; + table[31 * 256 + 224] = 22; + table[31 * 256 + 225] = 23; + table[31 * 256 + 226] = 23; + table[31 * 256 + 227] = 23; + table[31 * 256 + 228] = 23; + table[31 * 256 + 229] = 23; + table[31 * 256 + 230] = 23; + table[31 * 256 + 231] = 23; + table[31 * 256 + 232] = 23; + table[31 * 256 + 233] = 23; + table[31 * 256 + 234] = 23; + table[31 * 256 + 235] = 23; + table[31 * 256 + 236] = 23; + table[31 * 256 + 238] = 23; + table[31 * 256 + 239] = 23; + table[31 * 256 + 237] = 24; + table[31 * 256 + 240] = 25; + table[31 * 256 + 241] = 26; + table[31 * 256 + 242] = 26; + table[31 * 256 + 243] = 26; + table[31 * 256 + 244] = 27; + table[31 * 256 + 48] = 32; + table[31 * 256 + 49] = 32; + table[31 * 256 + 50] = 32; + table[31 * 256 + 51] = 32; + table[31 * 256 + 52] = 32; + table[31 * 256 + 53] = 32; + table[31 * 256 + 54] = 32; + table[31 * 256 + 55] = 32; + table[31 * 256 + 56] = 32; + table[31 * 256 + 57] = 32; + table[32 * 256 + 48] = 32; + table[32 * 256 + 49] = 32; + table[32 * 256 + 50] = 32; + table[32 * 256 + 51] = 32; + table[32 * 256 + 52] = 32; + table[32 * 256 + 53] = 32; + table[32 * 256 + 54] = 32; + table[32 * 256 + 55] = 32; + table[32 * 256 + 56] = 32; + table[32 * 256 + 57] = 32; + table[32 * 256 + 59] = 33; + + table +} + + +pub fn regex_match(input: [u8; N]) -> (BoundedVec, bool) { + let substrings = unsafe { __regex_match(input) }; + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + let mut start_range = 0; + let mut end_range = 0; + + // check the match + for i in 0..N { + // state transition + let temp = input[i] as Field; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + s = 0; + s_next = potential_s_next; + } + std::as_witness(s_next); + + // range conditions for substring matches + if ((start_range == 0) & (end_range == 0)) { + start_range = i as Field; + } + if (((s == 33) & (s_next == 34)) & (end_range == 0)) { + end_range = i as Field + 1; + } + + + let range_0 = substrings.get_unchecked(0).in_range(i); + let case_0 = [ + (s_next == 32) & ((s == 31) | (s == 32)) + ].any(|case| case == true) | !range_0; + + + + let substring_range_check = [case_0] + .all(|case| case == true); + + assert(substring_range_check, "substr array ranges wrong"); + + + s = s_next; + } + // check final state + + let matched: bool = (s == 33) | (s == 34); + + // constrain extracted substrings to be in match range + //let full_match = Sequence::new(start_range as u32, end_range as u32 - start_range as u32); + //let full_match_end = full_match.end(); + // for i in 0..1 { + // let substring = substrings.get_unchecked(i); + // let is_not_valid = i >= substrings.len(); + // let index_check = substring.index >= full_match.index; + // let length_check = substring.end() <= full_match_end; + // let check = (index_check) | is_not_valid; + // assert(check, f"Substring {i} range is out of bounds of the full match found"); + // } + (substrings, matched) +} + + +pub unconstrained fn __regex_match(input: [u8; N]) -> BoundedVec { + // regex: (\r\n|^)dkim-signature:([a-z]+=[^;]+; )+t=[0-9]+; + let mut substrings: BoundedVec = BoundedVec::new(); + let mut current_substring = Sequence::default(); + let mut full_match = Sequence::default(); + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + + let mut consecutive_substr = 0; + let mut complete = false; + + for i in 0..input.len() { + let temp = input[i] as Field; + let mut reset = false; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + reset = true; + s = 0; + s_next = potential_s_next; + } + // If a substring was in the making, but the state was reset + // we disregard previous progress because apparently it is invalid + if (reset & (consecutive_substr == 1)) { + current_substring = Sequence::default(); + consecutive_substr = 0; + } + // Fill up substrings + + + if ((s == 31) & (s_next == 32) | (s == 32) & (s_next == 32)) { + + if (consecutive_substr == 0) { + current_substring.index = i; + }; + current_substring.length += 1; + consecutive_substr = 1; + } else if ((consecutive_substr == 1) & (s_next == 0)) { + current_substring = Sequence::default(); + full_match = Sequence::default(); + substrings = BoundedVec::new(); + consecutive_substr = 0; + } else if (s == 33) & (s_next == 34) { + full_match.length = i - full_match.index + 1; + complete = true; + } else if (consecutive_substr == 1) { + // The substring is done so "save" it + substrings.push(current_substring); + // reset the substring holder for next use + current_substring = Sequence::default(); + consecutive_substr = 0; + } + s = s_next; + if complete == true { + break; + } + } + assert((s == 33) | (s == 34), f"no match: {s}"); + // Add pending substring that hasn't been added + if consecutive_substr == 1 { + substrings.push(current_substring); + full_match.length = input.len() - full_match.index; + } + + + + substrings +} + + + + \ No newline at end of file diff --git a/packages/noir/src/capture/raw/to_all.nr b/packages/noir/src/capture/raw/to_all.nr new file mode 100644 index 00000000..ae4ee09e --- /dev/null +++ b/packages/noir/src/capture/raw/to_all.nr @@ -0,0 +1,1351 @@ + +use crate::common::Sequence; + + +global table: [Field; 4352] = comptime { make_lookup_table() }; + +comptime fn make_lookup_table() -> [Field; 4352] { + let mut table = [0; 4352]; + table[15 * 256 + 0] = 16; + table[16 * 256 + 0] = 16; + table[15 * 256 + 1] = 16; + table[16 * 256 + 1] = 16; + table[15 * 256 + 2] = 16; + table[16 * 256 + 2] = 16; + table[15 * 256 + 3] = 16; + table[16 * 256 + 3] = 16; + table[15 * 256 + 4] = 16; + table[16 * 256 + 4] = 16; + table[15 * 256 + 5] = 16; + table[16 * 256 + 5] = 16; + table[15 * 256 + 6] = 16; + table[16 * 256 + 6] = 16; + table[15 * 256 + 7] = 16; + table[16 * 256 + 7] = 16; + table[15 * 256 + 8] = 16; + table[16 * 256 + 8] = 16; + table[15 * 256 + 9] = 16; + table[16 * 256 + 9] = 16; + table[15 * 256 + 10] = 16; + table[16 * 256 + 10] = 16; + table[15 * 256 + 11] = 16; + table[16 * 256 + 11] = 16; + table[15 * 256 + 12] = 16; + table[16 * 256 + 12] = 16; + table[15 * 256 + 13] = 16; + table[16 * 256 + 13] = 16; + table[15 * 256 + 14] = 16; + table[16 * 256 + 14] = 16; + table[15 * 256 + 15] = 16; + table[16 * 256 + 15] = 16; + table[15 * 256 + 16] = 16; + table[16 * 256 + 16] = 16; + table[15 * 256 + 17] = 16; + table[16 * 256 + 17] = 16; + table[15 * 256 + 18] = 16; + table[16 * 256 + 18] = 16; + table[15 * 256 + 19] = 16; + table[16 * 256 + 19] = 16; + table[15 * 256 + 20] = 16; + table[16 * 256 + 20] = 16; + table[15 * 256 + 21] = 16; + table[16 * 256 + 21] = 16; + table[15 * 256 + 22] = 16; + table[16 * 256 + 22] = 16; + table[15 * 256 + 23] = 16; + table[16 * 256 + 23] = 16; + table[15 * 256 + 24] = 16; + table[16 * 256 + 24] = 16; + table[15 * 256 + 25] = 16; + table[16 * 256 + 25] = 16; + table[15 * 256 + 26] = 16; + table[16 * 256 + 26] = 16; + table[15 * 256 + 27] = 16; + table[16 * 256 + 27] = 16; + table[15 * 256 + 28] = 16; + table[16 * 256 + 28] = 16; + table[15 * 256 + 29] = 16; + table[16 * 256 + 29] = 16; + table[15 * 256 + 30] = 16; + table[16 * 256 + 30] = 16; + table[15 * 256 + 31] = 16; + table[16 * 256 + 31] = 16; + table[15 * 256 + 32] = 16; + table[16 * 256 + 32] = 16; + table[15 * 256 + 33] = 16; + table[16 * 256 + 33] = 16; + table[15 * 256 + 34] = 16; + table[16 * 256 + 34] = 16; + table[15 * 256 + 35] = 16; + table[16 * 256 + 35] = 16; + table[15 * 256 + 36] = 16; + table[16 * 256 + 36] = 16; + table[15 * 256 + 37] = 16; + table[16 * 256 + 37] = 16; + table[15 * 256 + 38] = 16; + table[16 * 256 + 38] = 16; + table[15 * 256 + 39] = 16; + table[16 * 256 + 39] = 16; + table[15 * 256 + 40] = 16; + table[16 * 256 + 40] = 16; + table[15 * 256 + 41] = 16; + table[16 * 256 + 41] = 16; + table[15 * 256 + 42] = 16; + table[16 * 256 + 42] = 16; + table[15 * 256 + 43] = 16; + table[16 * 256 + 43] = 16; + table[15 * 256 + 44] = 16; + table[16 * 256 + 44] = 16; + table[15 * 256 + 45] = 16; + table[16 * 256 + 45] = 16; + table[15 * 256 + 46] = 16; + table[16 * 256 + 46] = 16; + table[15 * 256 + 47] = 16; + table[16 * 256 + 47] = 16; + table[15 * 256 + 48] = 16; + table[16 * 256 + 48] = 16; + table[15 * 256 + 49] = 16; + table[16 * 256 + 49] = 16; + table[15 * 256 + 50] = 16; + table[16 * 256 + 50] = 16; + table[15 * 256 + 51] = 16; + table[16 * 256 + 51] = 16; + table[15 * 256 + 52] = 16; + table[16 * 256 + 52] = 16; + table[15 * 256 + 53] = 16; + table[16 * 256 + 53] = 16; + table[15 * 256 + 54] = 16; + table[16 * 256 + 54] = 16; + table[15 * 256 + 55] = 16; + table[16 * 256 + 55] = 16; + table[15 * 256 + 56] = 16; + table[16 * 256 + 56] = 16; + table[15 * 256 + 57] = 16; + table[16 * 256 + 57] = 16; + table[15 * 256 + 58] = 16; + table[16 * 256 + 58] = 16; + table[15 * 256 + 59] = 16; + table[16 * 256 + 59] = 16; + table[15 * 256 + 60] = 16; + table[16 * 256 + 60] = 16; + table[15 * 256 + 61] = 16; + table[16 * 256 + 61] = 16; + table[15 * 256 + 62] = 16; + table[16 * 256 + 62] = 16; + table[15 * 256 + 63] = 16; + table[16 * 256 + 63] = 16; + table[15 * 256 + 64] = 16; + table[16 * 256 + 64] = 16; + table[15 * 256 + 65] = 16; + table[16 * 256 + 65] = 16; + table[15 * 256 + 66] = 16; + table[16 * 256 + 66] = 16; + table[15 * 256 + 67] = 16; + table[16 * 256 + 67] = 16; + table[15 * 256 + 68] = 16; + table[16 * 256 + 68] = 16; + table[15 * 256 + 69] = 16; + table[16 * 256 + 69] = 16; + table[15 * 256 + 70] = 16; + table[16 * 256 + 70] = 16; + table[15 * 256 + 71] = 16; + table[16 * 256 + 71] = 16; + table[15 * 256 + 72] = 16; + table[16 * 256 + 72] = 16; + table[15 * 256 + 73] = 16; + table[16 * 256 + 73] = 16; + table[15 * 256 + 74] = 16; + table[16 * 256 + 74] = 16; + table[15 * 256 + 75] = 16; + table[16 * 256 + 75] = 16; + table[15 * 256 + 76] = 16; + table[16 * 256 + 76] = 16; + table[15 * 256 + 77] = 16; + table[16 * 256 + 77] = 16; + table[15 * 256 + 78] = 16; + table[16 * 256 + 78] = 16; + table[15 * 256 + 79] = 16; + table[16 * 256 + 79] = 16; + table[15 * 256 + 80] = 16; + table[16 * 256 + 80] = 16; + table[15 * 256 + 81] = 16; + table[16 * 256 + 81] = 16; + table[15 * 256 + 82] = 16; + table[16 * 256 + 82] = 16; + table[15 * 256 + 83] = 16; + table[16 * 256 + 83] = 16; + table[15 * 256 + 84] = 16; + table[16 * 256 + 84] = 16; + table[15 * 256 + 85] = 16; + table[16 * 256 + 85] = 16; + table[15 * 256 + 86] = 16; + table[16 * 256 + 86] = 16; + table[15 * 256 + 87] = 16; + table[16 * 256 + 87] = 16; + table[15 * 256 + 88] = 16; + table[16 * 256 + 88] = 16; + table[15 * 256 + 89] = 16; + table[16 * 256 + 89] = 16; + table[15 * 256 + 90] = 16; + table[16 * 256 + 90] = 16; + table[15 * 256 + 91] = 16; + table[16 * 256 + 91] = 16; + table[15 * 256 + 92] = 16; + table[16 * 256 + 92] = 16; + table[15 * 256 + 93] = 16; + table[16 * 256 + 93] = 16; + table[15 * 256 + 94] = 16; + table[16 * 256 + 94] = 16; + table[15 * 256 + 95] = 16; + table[16 * 256 + 95] = 16; + table[15 * 256 + 96] = 16; + table[16 * 256 + 96] = 16; + table[15 * 256 + 97] = 16; + table[16 * 256 + 97] = 16; + table[15 * 256 + 98] = 16; + table[16 * 256 + 98] = 16; + table[15 * 256 + 99] = 16; + table[16 * 256 + 99] = 16; + table[15 * 256 + 100] = 16; + table[16 * 256 + 100] = 16; + table[15 * 256 + 101] = 16; + table[16 * 256 + 101] = 16; + table[15 * 256 + 102] = 16; + table[16 * 256 + 102] = 16; + table[15 * 256 + 103] = 16; + table[16 * 256 + 103] = 16; + table[15 * 256 + 104] = 16; + table[16 * 256 + 104] = 16; + table[15 * 256 + 105] = 16; + table[16 * 256 + 105] = 16; + table[15 * 256 + 106] = 16; + table[16 * 256 + 106] = 16; + table[15 * 256 + 107] = 16; + table[16 * 256 + 107] = 16; + table[15 * 256 + 108] = 16; + table[16 * 256 + 108] = 16; + table[15 * 256 + 109] = 16; + table[16 * 256 + 109] = 16; + table[15 * 256 + 110] = 16; + table[16 * 256 + 110] = 16; + table[15 * 256 + 111] = 16; + table[16 * 256 + 111] = 16; + table[15 * 256 + 112] = 16; + table[16 * 256 + 112] = 16; + table[15 * 256 + 113] = 16; + table[16 * 256 + 113] = 16; + table[15 * 256 + 114] = 16; + table[16 * 256 + 114] = 16; + table[15 * 256 + 115] = 16; + table[16 * 256 + 115] = 16; + table[15 * 256 + 116] = 16; + table[16 * 256 + 116] = 16; + table[15 * 256 + 117] = 16; + table[16 * 256 + 117] = 16; + table[15 * 256 + 118] = 16; + table[16 * 256 + 118] = 16; + table[15 * 256 + 119] = 16; + table[16 * 256 + 119] = 16; + table[15 * 256 + 120] = 16; + table[16 * 256 + 120] = 16; + table[15 * 256 + 121] = 16; + table[16 * 256 + 121] = 16; + table[15 * 256 + 122] = 16; + table[16 * 256 + 122] = 16; + table[15 * 256 + 123] = 16; + table[16 * 256 + 123] = 16; + table[15 * 256 + 124] = 16; + table[16 * 256 + 124] = 16; + table[15 * 256 + 125] = 16; + table[16 * 256 + 125] = 16; + table[15 * 256 + 126] = 16; + table[16 * 256 + 126] = 16; + table[15 * 256 + 127] = 16; + table[16 * 256 + 127] = 16; + table[15 * 256 + 128] = 16; + table[16 * 256 + 128] = 16; + table[15 * 256 + 129] = 16; + table[16 * 256 + 129] = 16; + table[15 * 256 + 130] = 16; + table[16 * 256 + 130] = 16; + table[15 * 256 + 131] = 16; + table[16 * 256 + 131] = 16; + table[15 * 256 + 132] = 16; + table[16 * 256 + 132] = 16; + table[15 * 256 + 133] = 16; + table[16 * 256 + 133] = 16; + table[15 * 256 + 134] = 16; + table[16 * 256 + 134] = 16; + table[15 * 256 + 135] = 16; + table[16 * 256 + 135] = 16; + table[15 * 256 + 136] = 16; + table[16 * 256 + 136] = 16; + table[15 * 256 + 137] = 16; + table[16 * 256 + 137] = 16; + table[15 * 256 + 138] = 16; + table[16 * 256 + 138] = 16; + table[15 * 256 + 139] = 16; + table[16 * 256 + 139] = 16; + table[15 * 256 + 140] = 16; + table[16 * 256 + 140] = 16; + table[15 * 256 + 141] = 16; + table[16 * 256 + 141] = 16; + table[15 * 256 + 142] = 16; + table[16 * 256 + 142] = 16; + table[15 * 256 + 143] = 16; + table[16 * 256 + 143] = 16; + table[15 * 256 + 144] = 16; + table[16 * 256 + 144] = 16; + table[15 * 256 + 145] = 16; + table[16 * 256 + 145] = 16; + table[15 * 256 + 146] = 16; + table[16 * 256 + 146] = 16; + table[15 * 256 + 147] = 16; + table[16 * 256 + 147] = 16; + table[15 * 256 + 148] = 16; + table[16 * 256 + 148] = 16; + table[15 * 256 + 149] = 16; + table[16 * 256 + 149] = 16; + table[15 * 256 + 150] = 16; + table[16 * 256 + 150] = 16; + table[15 * 256 + 151] = 16; + table[16 * 256 + 151] = 16; + table[15 * 256 + 152] = 16; + table[16 * 256 + 152] = 16; + table[15 * 256 + 153] = 16; + table[16 * 256 + 153] = 16; + table[15 * 256 + 154] = 16; + table[16 * 256 + 154] = 16; + table[15 * 256 + 155] = 16; + table[16 * 256 + 155] = 16; + table[15 * 256 + 156] = 16; + table[16 * 256 + 156] = 16; + table[15 * 256 + 157] = 16; + table[16 * 256 + 157] = 16; + table[15 * 256 + 158] = 16; + table[16 * 256 + 158] = 16; + table[15 * 256 + 159] = 16; + table[16 * 256 + 159] = 16; + table[15 * 256 + 160] = 16; + table[16 * 256 + 160] = 16; + table[15 * 256 + 161] = 16; + table[16 * 256 + 161] = 16; + table[15 * 256 + 162] = 16; + table[16 * 256 + 162] = 16; + table[15 * 256 + 163] = 16; + table[16 * 256 + 163] = 16; + table[15 * 256 + 164] = 16; + table[16 * 256 + 164] = 16; + table[15 * 256 + 165] = 16; + table[16 * 256 + 165] = 16; + table[15 * 256 + 166] = 16; + table[16 * 256 + 166] = 16; + table[15 * 256 + 167] = 16; + table[16 * 256 + 167] = 16; + table[15 * 256 + 168] = 16; + table[16 * 256 + 168] = 16; + table[15 * 256 + 169] = 16; + table[16 * 256 + 169] = 16; + table[15 * 256 + 170] = 16; + table[16 * 256 + 170] = 16; + table[15 * 256 + 171] = 16; + table[16 * 256 + 171] = 16; + table[15 * 256 + 172] = 16; + table[16 * 256 + 172] = 16; + table[15 * 256 + 173] = 16; + table[16 * 256 + 173] = 16; + table[15 * 256 + 174] = 16; + table[16 * 256 + 174] = 16; + table[15 * 256 + 175] = 16; + table[16 * 256 + 175] = 16; + table[15 * 256 + 176] = 16; + table[16 * 256 + 176] = 16; + table[15 * 256 + 177] = 16; + table[16 * 256 + 177] = 16; + table[15 * 256 + 178] = 16; + table[16 * 256 + 178] = 16; + table[15 * 256 + 179] = 16; + table[16 * 256 + 179] = 16; + table[15 * 256 + 180] = 16; + table[16 * 256 + 180] = 16; + table[15 * 256 + 181] = 16; + table[16 * 256 + 181] = 16; + table[15 * 256 + 182] = 16; + table[16 * 256 + 182] = 16; + table[15 * 256 + 183] = 16; + table[16 * 256 + 183] = 16; + table[15 * 256 + 184] = 16; + table[16 * 256 + 184] = 16; + table[15 * 256 + 185] = 16; + table[16 * 256 + 185] = 16; + table[15 * 256 + 186] = 16; + table[16 * 256 + 186] = 16; + table[15 * 256 + 187] = 16; + table[16 * 256 + 187] = 16; + table[15 * 256 + 188] = 16; + table[16 * 256 + 188] = 16; + table[15 * 256 + 189] = 16; + table[16 * 256 + 189] = 16; + table[15 * 256 + 190] = 16; + table[16 * 256 + 190] = 16; + table[15 * 256 + 191] = 16; + table[16 * 256 + 191] = 16; + table[15 * 256 + 192] = 16; + table[16 * 256 + 192] = 16; + table[15 * 256 + 193] = 16; + table[16 * 256 + 193] = 16; + table[15 * 256 + 194] = 16; + table[16 * 256 + 194] = 16; + table[15 * 256 + 195] = 16; + table[16 * 256 + 195] = 16; + table[15 * 256 + 196] = 16; + table[16 * 256 + 196] = 16; + table[15 * 256 + 197] = 16; + table[16 * 256 + 197] = 16; + table[15 * 256 + 198] = 16; + table[16 * 256 + 198] = 16; + table[15 * 256 + 199] = 16; + table[16 * 256 + 199] = 16; + table[15 * 256 + 200] = 16; + table[16 * 256 + 200] = 16; + table[15 * 256 + 201] = 16; + table[16 * 256 + 201] = 16; + table[15 * 256 + 202] = 16; + table[16 * 256 + 202] = 16; + table[15 * 256 + 203] = 16; + table[16 * 256 + 203] = 16; + table[15 * 256 + 204] = 16; + table[16 * 256 + 204] = 16; + table[15 * 256 + 205] = 16; + table[16 * 256 + 205] = 16; + table[15 * 256 + 206] = 16; + table[16 * 256 + 206] = 16; + table[15 * 256 + 207] = 16; + table[16 * 256 + 207] = 16; + table[15 * 256 + 208] = 16; + table[16 * 256 + 208] = 16; + table[15 * 256 + 209] = 16; + table[16 * 256 + 209] = 16; + table[15 * 256 + 210] = 16; + table[16 * 256 + 210] = 16; + table[15 * 256 + 211] = 16; + table[16 * 256 + 211] = 16; + table[15 * 256 + 212] = 16; + table[16 * 256 + 212] = 16; + table[15 * 256 + 213] = 16; + table[16 * 256 + 213] = 16; + table[15 * 256 + 214] = 16; + table[16 * 256 + 214] = 16; + table[15 * 256 + 215] = 16; + table[16 * 256 + 215] = 16; + table[15 * 256 + 216] = 16; + table[16 * 256 + 216] = 16; + table[15 * 256 + 217] = 16; + table[16 * 256 + 217] = 16; + table[15 * 256 + 218] = 16; + table[16 * 256 + 218] = 16; + table[15 * 256 + 219] = 16; + table[16 * 256 + 219] = 16; + table[15 * 256 + 220] = 16; + table[16 * 256 + 220] = 16; + table[15 * 256 + 221] = 16; + table[16 * 256 + 221] = 16; + table[15 * 256 + 222] = 16; + table[16 * 256 + 222] = 16; + table[15 * 256 + 223] = 16; + table[16 * 256 + 223] = 16; + table[15 * 256 + 224] = 16; + table[16 * 256 + 224] = 16; + table[15 * 256 + 225] = 16; + table[16 * 256 + 225] = 16; + table[15 * 256 + 226] = 16; + table[16 * 256 + 226] = 16; + table[15 * 256 + 227] = 16; + table[16 * 256 + 227] = 16; + table[15 * 256 + 228] = 16; + table[16 * 256 + 228] = 16; + table[15 * 256 + 229] = 16; + table[16 * 256 + 229] = 16; + table[15 * 256 + 230] = 16; + table[16 * 256 + 230] = 16; + table[15 * 256 + 231] = 16; + table[16 * 256 + 231] = 16; + table[15 * 256 + 232] = 16; + table[16 * 256 + 232] = 16; + table[15 * 256 + 233] = 16; + table[16 * 256 + 233] = 16; + table[15 * 256 + 234] = 16; + table[16 * 256 + 234] = 16; + table[15 * 256 + 235] = 16; + table[16 * 256 + 235] = 16; + table[15 * 256 + 236] = 16; + table[16 * 256 + 236] = 16; + table[15 * 256 + 237] = 16; + table[16 * 256 + 237] = 16; + table[15 * 256 + 238] = 16; + table[16 * 256 + 238] = 16; + table[15 * 256 + 239] = 16; + table[16 * 256 + 239] = 16; + table[15 * 256 + 240] = 16; + table[16 * 256 + 240] = 16; + table[15 * 256 + 241] = 16; + table[16 * 256 + 241] = 16; + table[15 * 256 + 242] = 16; + table[16 * 256 + 242] = 16; + table[15 * 256 + 243] = 16; + table[16 * 256 + 243] = 16; + table[15 * 256 + 244] = 16; + table[16 * 256 + 244] = 16; + table[15 * 256 + 245] = 16; + table[16 * 256 + 245] = 16; + table[15 * 256 + 246] = 16; + table[16 * 256 + 246] = 16; + table[15 * 256 + 247] = 16; + table[16 * 256 + 247] = 16; + table[15 * 256 + 248] = 16; + table[16 * 256 + 248] = 16; + table[15 * 256 + 249] = 16; + table[16 * 256 + 249] = 16; + table[15 * 256 + 250] = 16; + table[16 * 256 + 250] = 16; + table[15 * 256 + 251] = 16; + table[16 * 256 + 251] = 16; + table[15 * 256 + 252] = 16; + table[16 * 256 + 252] = 16; + table[15 * 256 + 253] = 16; + table[16 * 256 + 253] = 16; + table[15 * 256 + 254] = 16; + table[16 * 256 + 254] = 16; + table[0 * 256 + 13] = 1; + table[0 * 256 + 255] = 2; + table[1 * 256 + 10] = 2; + table[2 * 256 + 116] = 3; + table[3 * 256 + 111] = 4; + table[4 * 256 + 58] = 5; + table[5 * 256 + 0] = 6; + table[5 * 256 + 1] = 6; + table[5 * 256 + 2] = 6; + table[5 * 256 + 3] = 6; + table[5 * 256 + 4] = 6; + table[5 * 256 + 5] = 6; + table[5 * 256 + 6] = 6; + table[5 * 256 + 7] = 6; + table[5 * 256 + 8] = 6; + table[5 * 256 + 9] = 6; + table[5 * 256 + 11] = 6; + table[5 * 256 + 12] = 6; + table[5 * 256 + 14] = 6; + table[5 * 256 + 15] = 6; + table[5 * 256 + 16] = 6; + table[5 * 256 + 17] = 6; + table[5 * 256 + 18] = 6; + table[5 * 256 + 19] = 6; + table[5 * 256 + 20] = 6; + table[5 * 256 + 21] = 6; + table[5 * 256 + 22] = 6; + table[5 * 256 + 23] = 6; + table[5 * 256 + 24] = 6; + table[5 * 256 + 25] = 6; + table[5 * 256 + 26] = 6; + table[5 * 256 + 27] = 6; + table[5 * 256 + 28] = 6; + table[5 * 256 + 29] = 6; + table[5 * 256 + 30] = 6; + table[5 * 256 + 31] = 6; + table[5 * 256 + 32] = 6; + table[5 * 256 + 33] = 6; + table[5 * 256 + 34] = 6; + table[5 * 256 + 35] = 6; + table[5 * 256 + 36] = 6; + table[5 * 256 + 37] = 6; + table[5 * 256 + 38] = 6; + table[5 * 256 + 39] = 6; + table[5 * 256 + 40] = 6; + table[5 * 256 + 41] = 6; + table[5 * 256 + 42] = 6; + table[5 * 256 + 43] = 6; + table[5 * 256 + 44] = 6; + table[5 * 256 + 45] = 6; + table[5 * 256 + 46] = 6; + table[5 * 256 + 47] = 6; + table[5 * 256 + 48] = 6; + table[5 * 256 + 49] = 6; + table[5 * 256 + 50] = 6; + table[5 * 256 + 51] = 6; + table[5 * 256 + 52] = 6; + table[5 * 256 + 53] = 6; + table[5 * 256 + 54] = 6; + table[5 * 256 + 55] = 6; + table[5 * 256 + 56] = 6; + table[5 * 256 + 57] = 6; + table[5 * 256 + 58] = 6; + table[5 * 256 + 59] = 6; + table[5 * 256 + 60] = 6; + table[5 * 256 + 61] = 6; + table[5 * 256 + 62] = 6; + table[5 * 256 + 63] = 6; + table[5 * 256 + 64] = 6; + table[5 * 256 + 65] = 6; + table[5 * 256 + 66] = 6; + table[5 * 256 + 67] = 6; + table[5 * 256 + 68] = 6; + table[5 * 256 + 69] = 6; + table[5 * 256 + 70] = 6; + table[5 * 256 + 71] = 6; + table[5 * 256 + 72] = 6; + table[5 * 256 + 73] = 6; + table[5 * 256 + 74] = 6; + table[5 * 256 + 75] = 6; + table[5 * 256 + 76] = 6; + table[5 * 256 + 77] = 6; + table[5 * 256 + 78] = 6; + table[5 * 256 + 79] = 6; + table[5 * 256 + 80] = 6; + table[5 * 256 + 81] = 6; + table[5 * 256 + 82] = 6; + table[5 * 256 + 83] = 6; + table[5 * 256 + 84] = 6; + table[5 * 256 + 85] = 6; + table[5 * 256 + 86] = 6; + table[5 * 256 + 87] = 6; + table[5 * 256 + 88] = 6; + table[5 * 256 + 89] = 6; + table[5 * 256 + 90] = 6; + table[5 * 256 + 91] = 6; + table[5 * 256 + 92] = 6; + table[5 * 256 + 93] = 6; + table[5 * 256 + 94] = 6; + table[5 * 256 + 95] = 6; + table[5 * 256 + 96] = 6; + table[5 * 256 + 97] = 6; + table[5 * 256 + 98] = 6; + table[5 * 256 + 99] = 6; + table[5 * 256 + 100] = 6; + table[5 * 256 + 101] = 6; + table[5 * 256 + 102] = 6; + table[5 * 256 + 103] = 6; + table[5 * 256 + 104] = 6; + table[5 * 256 + 105] = 6; + table[5 * 256 + 106] = 6; + table[5 * 256 + 107] = 6; + table[5 * 256 + 108] = 6; + table[5 * 256 + 109] = 6; + table[5 * 256 + 110] = 6; + table[5 * 256 + 111] = 6; + table[5 * 256 + 112] = 6; + table[5 * 256 + 113] = 6; + table[5 * 256 + 114] = 6; + table[5 * 256 + 115] = 6; + table[5 * 256 + 116] = 6; + table[5 * 256 + 117] = 6; + table[5 * 256 + 118] = 6; + table[5 * 256 + 119] = 6; + table[5 * 256 + 120] = 6; + table[5 * 256 + 121] = 6; + table[5 * 256 + 122] = 6; + table[5 * 256 + 123] = 6; + table[5 * 256 + 124] = 6; + table[5 * 256 + 125] = 6; + table[5 * 256 + 126] = 6; + table[5 * 256 + 127] = 6; + table[5 * 256 + 194] = 7; + table[5 * 256 + 195] = 7; + table[5 * 256 + 196] = 7; + table[5 * 256 + 197] = 7; + table[5 * 256 + 198] = 7; + table[5 * 256 + 199] = 7; + table[5 * 256 + 200] = 7; + table[5 * 256 + 201] = 7; + table[5 * 256 + 202] = 7; + table[5 * 256 + 203] = 7; + table[5 * 256 + 204] = 7; + table[5 * 256 + 205] = 7; + table[5 * 256 + 206] = 7; + table[5 * 256 + 207] = 7; + table[5 * 256 + 208] = 7; + table[5 * 256 + 209] = 7; + table[5 * 256 + 210] = 7; + table[5 * 256 + 211] = 7; + table[5 * 256 + 212] = 7; + table[5 * 256 + 213] = 7; + table[5 * 256 + 214] = 7; + table[5 * 256 + 215] = 7; + table[5 * 256 + 216] = 7; + table[5 * 256 + 217] = 7; + table[5 * 256 + 218] = 7; + table[5 * 256 + 219] = 7; + table[5 * 256 + 220] = 7; + table[5 * 256 + 221] = 7; + table[5 * 256 + 222] = 7; + table[5 * 256 + 223] = 7; + table[5 * 256 + 224] = 8; + table[5 * 256 + 225] = 9; + table[5 * 256 + 226] = 9; + table[5 * 256 + 227] = 9; + table[5 * 256 + 228] = 9; + table[5 * 256 + 229] = 9; + table[5 * 256 + 230] = 9; + table[5 * 256 + 231] = 9; + table[5 * 256 + 232] = 9; + table[5 * 256 + 233] = 9; + table[5 * 256 + 234] = 9; + table[5 * 256 + 235] = 9; + table[5 * 256 + 236] = 9; + table[5 * 256 + 238] = 9; + table[5 * 256 + 239] = 9; + table[5 * 256 + 237] = 10; + table[5 * 256 + 240] = 11; + table[5 * 256 + 241] = 12; + table[5 * 256 + 242] = 12; + table[5 * 256 + 243] = 12; + table[5 * 256 + 244] = 13; + table[6 * 256 + 0] = 6; + table[6 * 256 + 1] = 6; + table[6 * 256 + 2] = 6; + table[6 * 256 + 3] = 6; + table[6 * 256 + 4] = 6; + table[6 * 256 + 5] = 6; + table[6 * 256 + 6] = 6; + table[6 * 256 + 7] = 6; + table[6 * 256 + 8] = 6; + table[6 * 256 + 9] = 6; + table[6 * 256 + 11] = 6; + table[6 * 256 + 12] = 6; + table[6 * 256 + 14] = 6; + table[6 * 256 + 15] = 6; + table[6 * 256 + 16] = 6; + table[6 * 256 + 17] = 6; + table[6 * 256 + 18] = 6; + table[6 * 256 + 19] = 6; + table[6 * 256 + 20] = 6; + table[6 * 256 + 21] = 6; + table[6 * 256 + 22] = 6; + table[6 * 256 + 23] = 6; + table[6 * 256 + 24] = 6; + table[6 * 256 + 25] = 6; + table[6 * 256 + 26] = 6; + table[6 * 256 + 27] = 6; + table[6 * 256 + 28] = 6; + table[6 * 256 + 29] = 6; + table[6 * 256 + 30] = 6; + table[6 * 256 + 31] = 6; + table[6 * 256 + 32] = 6; + table[6 * 256 + 33] = 6; + table[6 * 256 + 34] = 6; + table[6 * 256 + 35] = 6; + table[6 * 256 + 36] = 6; + table[6 * 256 + 37] = 6; + table[6 * 256 + 38] = 6; + table[6 * 256 + 39] = 6; + table[6 * 256 + 40] = 6; + table[6 * 256 + 41] = 6; + table[6 * 256 + 42] = 6; + table[6 * 256 + 43] = 6; + table[6 * 256 + 44] = 6; + table[6 * 256 + 45] = 6; + table[6 * 256 + 46] = 6; + table[6 * 256 + 47] = 6; + table[6 * 256 + 48] = 6; + table[6 * 256 + 49] = 6; + table[6 * 256 + 50] = 6; + table[6 * 256 + 51] = 6; + table[6 * 256 + 52] = 6; + table[6 * 256 + 53] = 6; + table[6 * 256 + 54] = 6; + table[6 * 256 + 55] = 6; + table[6 * 256 + 56] = 6; + table[6 * 256 + 57] = 6; + table[6 * 256 + 58] = 6; + table[6 * 256 + 59] = 6; + table[6 * 256 + 60] = 6; + table[6 * 256 + 61] = 6; + table[6 * 256 + 62] = 6; + table[6 * 256 + 63] = 6; + table[6 * 256 + 64] = 6; + table[6 * 256 + 65] = 6; + table[6 * 256 + 66] = 6; + table[6 * 256 + 67] = 6; + table[6 * 256 + 68] = 6; + table[6 * 256 + 69] = 6; + table[6 * 256 + 70] = 6; + table[6 * 256 + 71] = 6; + table[6 * 256 + 72] = 6; + table[6 * 256 + 73] = 6; + table[6 * 256 + 74] = 6; + table[6 * 256 + 75] = 6; + table[6 * 256 + 76] = 6; + table[6 * 256 + 77] = 6; + table[6 * 256 + 78] = 6; + table[6 * 256 + 79] = 6; + table[6 * 256 + 80] = 6; + table[6 * 256 + 81] = 6; + table[6 * 256 + 82] = 6; + table[6 * 256 + 83] = 6; + table[6 * 256 + 84] = 6; + table[6 * 256 + 85] = 6; + table[6 * 256 + 86] = 6; + table[6 * 256 + 87] = 6; + table[6 * 256 + 88] = 6; + table[6 * 256 + 89] = 6; + table[6 * 256 + 90] = 6; + table[6 * 256 + 91] = 6; + table[6 * 256 + 92] = 6; + table[6 * 256 + 93] = 6; + table[6 * 256 + 94] = 6; + table[6 * 256 + 95] = 6; + table[6 * 256 + 96] = 6; + table[6 * 256 + 97] = 6; + table[6 * 256 + 98] = 6; + table[6 * 256 + 99] = 6; + table[6 * 256 + 100] = 6; + table[6 * 256 + 101] = 6; + table[6 * 256 + 102] = 6; + table[6 * 256 + 103] = 6; + table[6 * 256 + 104] = 6; + table[6 * 256 + 105] = 6; + table[6 * 256 + 106] = 6; + table[6 * 256 + 107] = 6; + table[6 * 256 + 108] = 6; + table[6 * 256 + 109] = 6; + table[6 * 256 + 110] = 6; + table[6 * 256 + 111] = 6; + table[6 * 256 + 112] = 6; + table[6 * 256 + 113] = 6; + table[6 * 256 + 114] = 6; + table[6 * 256 + 115] = 6; + table[6 * 256 + 116] = 6; + table[6 * 256 + 117] = 6; + table[6 * 256 + 118] = 6; + table[6 * 256 + 119] = 6; + table[6 * 256 + 120] = 6; + table[6 * 256 + 121] = 6; + table[6 * 256 + 122] = 6; + table[6 * 256 + 123] = 6; + table[6 * 256 + 124] = 6; + table[6 * 256 + 125] = 6; + table[6 * 256 + 126] = 6; + table[6 * 256 + 127] = 6; + table[6 * 256 + 194] = 7; + table[6 * 256 + 195] = 7; + table[6 * 256 + 196] = 7; + table[6 * 256 + 197] = 7; + table[6 * 256 + 198] = 7; + table[6 * 256 + 199] = 7; + table[6 * 256 + 200] = 7; + table[6 * 256 + 201] = 7; + table[6 * 256 + 202] = 7; + table[6 * 256 + 203] = 7; + table[6 * 256 + 204] = 7; + table[6 * 256 + 205] = 7; + table[6 * 256 + 206] = 7; + table[6 * 256 + 207] = 7; + table[6 * 256 + 208] = 7; + table[6 * 256 + 209] = 7; + table[6 * 256 + 210] = 7; + table[6 * 256 + 211] = 7; + table[6 * 256 + 212] = 7; + table[6 * 256 + 213] = 7; + table[6 * 256 + 214] = 7; + table[6 * 256 + 215] = 7; + table[6 * 256 + 216] = 7; + table[6 * 256 + 217] = 7; + table[6 * 256 + 218] = 7; + table[6 * 256 + 219] = 7; + table[6 * 256 + 220] = 7; + table[6 * 256 + 221] = 7; + table[6 * 256 + 222] = 7; + table[6 * 256 + 223] = 7; + table[6 * 256 + 224] = 8; + table[6 * 256 + 225] = 9; + table[6 * 256 + 226] = 9; + table[6 * 256 + 227] = 9; + table[6 * 256 + 228] = 9; + table[6 * 256 + 229] = 9; + table[6 * 256 + 230] = 9; + table[6 * 256 + 231] = 9; + table[6 * 256 + 232] = 9; + table[6 * 256 + 233] = 9; + table[6 * 256 + 234] = 9; + table[6 * 256 + 235] = 9; + table[6 * 256 + 236] = 9; + table[6 * 256 + 238] = 9; + table[6 * 256 + 239] = 9; + table[6 * 256 + 237] = 10; + table[6 * 256 + 240] = 11; + table[6 * 256 + 241] = 12; + table[6 * 256 + 242] = 12; + table[6 * 256 + 243] = 12; + table[6 * 256 + 244] = 13; + table[6 * 256 + 13] = 14; + table[7 * 256 + 128] = 6; + table[7 * 256 + 129] = 6; + table[7 * 256 + 130] = 6; + table[7 * 256 + 131] = 6; + table[7 * 256 + 132] = 6; + table[7 * 256 + 133] = 6; + table[7 * 256 + 134] = 6; + table[7 * 256 + 135] = 6; + table[7 * 256 + 136] = 6; + table[7 * 256 + 137] = 6; + table[7 * 256 + 138] = 6; + table[7 * 256 + 139] = 6; + table[7 * 256 + 140] = 6; + table[7 * 256 + 141] = 6; + table[7 * 256 + 142] = 6; + table[7 * 256 + 143] = 6; + table[7 * 256 + 144] = 6; + table[7 * 256 + 145] = 6; + table[7 * 256 + 146] = 6; + table[7 * 256 + 147] = 6; + table[7 * 256 + 148] = 6; + table[7 * 256 + 149] = 6; + table[7 * 256 + 150] = 6; + table[7 * 256 + 151] = 6; + table[7 * 256 + 152] = 6; + table[7 * 256 + 153] = 6; + table[7 * 256 + 154] = 6; + table[7 * 256 + 155] = 6; + table[7 * 256 + 156] = 6; + table[7 * 256 + 157] = 6; + table[7 * 256 + 158] = 6; + table[7 * 256 + 159] = 6; + table[7 * 256 + 160] = 6; + table[7 * 256 + 161] = 6; + table[7 * 256 + 162] = 6; + table[7 * 256 + 163] = 6; + table[7 * 256 + 164] = 6; + table[7 * 256 + 165] = 6; + table[7 * 256 + 166] = 6; + table[7 * 256 + 167] = 6; + table[7 * 256 + 168] = 6; + table[7 * 256 + 169] = 6; + table[7 * 256 + 170] = 6; + table[7 * 256 + 171] = 6; + table[7 * 256 + 172] = 6; + table[7 * 256 + 173] = 6; + table[7 * 256 + 174] = 6; + table[7 * 256 + 175] = 6; + table[7 * 256 + 176] = 6; + table[7 * 256 + 177] = 6; + table[7 * 256 + 178] = 6; + table[7 * 256 + 179] = 6; + table[7 * 256 + 180] = 6; + table[7 * 256 + 181] = 6; + table[7 * 256 + 182] = 6; + table[7 * 256 + 183] = 6; + table[7 * 256 + 184] = 6; + table[7 * 256 + 185] = 6; + table[7 * 256 + 186] = 6; + table[7 * 256 + 187] = 6; + table[7 * 256 + 188] = 6; + table[7 * 256 + 189] = 6; + table[7 * 256 + 190] = 6; + table[7 * 256 + 191] = 6; + table[8 * 256 + 160] = 7; + table[8 * 256 + 161] = 7; + table[8 * 256 + 162] = 7; + table[8 * 256 + 163] = 7; + table[8 * 256 + 164] = 7; + table[8 * 256 + 165] = 7; + table[8 * 256 + 166] = 7; + table[8 * 256 + 167] = 7; + table[8 * 256 + 168] = 7; + table[8 * 256 + 169] = 7; + table[8 * 256 + 170] = 7; + table[8 * 256 + 171] = 7; + table[8 * 256 + 172] = 7; + table[8 * 256 + 173] = 7; + table[8 * 256 + 174] = 7; + table[8 * 256 + 175] = 7; + table[8 * 256 + 176] = 7; + table[8 * 256 + 177] = 7; + table[8 * 256 + 178] = 7; + table[8 * 256 + 179] = 7; + table[8 * 256 + 180] = 7; + table[8 * 256 + 181] = 7; + table[8 * 256 + 182] = 7; + table[8 * 256 + 183] = 7; + table[8 * 256 + 184] = 7; + table[8 * 256 + 185] = 7; + table[8 * 256 + 186] = 7; + table[8 * 256 + 187] = 7; + table[8 * 256 + 188] = 7; + table[8 * 256 + 189] = 7; + table[8 * 256 + 190] = 7; + table[8 * 256 + 191] = 7; + table[9 * 256 + 128] = 7; + table[9 * 256 + 129] = 7; + table[9 * 256 + 130] = 7; + table[9 * 256 + 131] = 7; + table[9 * 256 + 132] = 7; + table[9 * 256 + 133] = 7; + table[9 * 256 + 134] = 7; + table[9 * 256 + 135] = 7; + table[9 * 256 + 136] = 7; + table[9 * 256 + 137] = 7; + table[9 * 256 + 138] = 7; + table[9 * 256 + 139] = 7; + table[9 * 256 + 140] = 7; + table[9 * 256 + 141] = 7; + table[9 * 256 + 142] = 7; + table[9 * 256 + 143] = 7; + table[9 * 256 + 144] = 7; + table[9 * 256 + 145] = 7; + table[9 * 256 + 146] = 7; + table[9 * 256 + 147] = 7; + table[9 * 256 + 148] = 7; + table[9 * 256 + 149] = 7; + table[9 * 256 + 150] = 7; + table[9 * 256 + 151] = 7; + table[9 * 256 + 152] = 7; + table[9 * 256 + 153] = 7; + table[9 * 256 + 154] = 7; + table[9 * 256 + 155] = 7; + table[9 * 256 + 156] = 7; + table[9 * 256 + 157] = 7; + table[9 * 256 + 158] = 7; + table[9 * 256 + 159] = 7; + table[9 * 256 + 160] = 7; + table[9 * 256 + 161] = 7; + table[9 * 256 + 162] = 7; + table[9 * 256 + 163] = 7; + table[9 * 256 + 164] = 7; + table[9 * 256 + 165] = 7; + table[9 * 256 + 166] = 7; + table[9 * 256 + 167] = 7; + table[9 * 256 + 168] = 7; + table[9 * 256 + 169] = 7; + table[9 * 256 + 170] = 7; + table[9 * 256 + 171] = 7; + table[9 * 256 + 172] = 7; + table[9 * 256 + 173] = 7; + table[9 * 256 + 174] = 7; + table[9 * 256 + 175] = 7; + table[9 * 256 + 176] = 7; + table[9 * 256 + 177] = 7; + table[9 * 256 + 178] = 7; + table[9 * 256 + 179] = 7; + table[9 * 256 + 180] = 7; + table[9 * 256 + 181] = 7; + table[9 * 256 + 182] = 7; + table[9 * 256 + 183] = 7; + table[9 * 256 + 184] = 7; + table[9 * 256 + 185] = 7; + table[9 * 256 + 186] = 7; + table[9 * 256 + 187] = 7; + table[9 * 256 + 188] = 7; + table[9 * 256 + 189] = 7; + table[9 * 256 + 190] = 7; + table[9 * 256 + 191] = 7; + table[10 * 256 + 128] = 7; + table[10 * 256 + 129] = 7; + table[10 * 256 + 130] = 7; + table[10 * 256 + 131] = 7; + table[10 * 256 + 132] = 7; + table[10 * 256 + 133] = 7; + table[10 * 256 + 134] = 7; + table[10 * 256 + 135] = 7; + table[10 * 256 + 136] = 7; + table[10 * 256 + 137] = 7; + table[10 * 256 + 138] = 7; + table[10 * 256 + 139] = 7; + table[10 * 256 + 140] = 7; + table[10 * 256 + 141] = 7; + table[10 * 256 + 142] = 7; + table[10 * 256 + 143] = 7; + table[10 * 256 + 144] = 7; + table[10 * 256 + 145] = 7; + table[10 * 256 + 146] = 7; + table[10 * 256 + 147] = 7; + table[10 * 256 + 148] = 7; + table[10 * 256 + 149] = 7; + table[10 * 256 + 150] = 7; + table[10 * 256 + 151] = 7; + table[10 * 256 + 152] = 7; + table[10 * 256 + 153] = 7; + table[10 * 256 + 154] = 7; + table[10 * 256 + 155] = 7; + table[10 * 256 + 156] = 7; + table[10 * 256 + 157] = 7; + table[10 * 256 + 158] = 7; + table[10 * 256 + 159] = 7; + table[11 * 256 + 144] = 9; + table[11 * 256 + 145] = 9; + table[11 * 256 + 146] = 9; + table[11 * 256 + 147] = 9; + table[11 * 256 + 148] = 9; + table[11 * 256 + 149] = 9; + table[11 * 256 + 150] = 9; + table[11 * 256 + 151] = 9; + table[11 * 256 + 152] = 9; + table[11 * 256 + 153] = 9; + table[11 * 256 + 154] = 9; + table[11 * 256 + 155] = 9; + table[11 * 256 + 156] = 9; + table[11 * 256 + 157] = 9; + table[11 * 256 + 158] = 9; + table[11 * 256 + 159] = 9; + table[11 * 256 + 160] = 9; + table[11 * 256 + 161] = 9; + table[11 * 256 + 162] = 9; + table[11 * 256 + 163] = 9; + table[11 * 256 + 164] = 9; + table[11 * 256 + 165] = 9; + table[11 * 256 + 166] = 9; + table[11 * 256 + 167] = 9; + table[11 * 256 + 168] = 9; + table[11 * 256 + 169] = 9; + table[11 * 256 + 170] = 9; + table[11 * 256 + 171] = 9; + table[11 * 256 + 172] = 9; + table[11 * 256 + 173] = 9; + table[11 * 256 + 174] = 9; + table[11 * 256 + 175] = 9; + table[11 * 256 + 176] = 9; + table[11 * 256 + 177] = 9; + table[11 * 256 + 178] = 9; + table[11 * 256 + 179] = 9; + table[11 * 256 + 180] = 9; + table[11 * 256 + 181] = 9; + table[11 * 256 + 182] = 9; + table[11 * 256 + 183] = 9; + table[11 * 256 + 184] = 9; + table[11 * 256 + 185] = 9; + table[11 * 256 + 186] = 9; + table[11 * 256 + 187] = 9; + table[11 * 256 + 188] = 9; + table[11 * 256 + 189] = 9; + table[11 * 256 + 190] = 9; + table[11 * 256 + 191] = 9; + table[12 * 256 + 128] = 9; + table[12 * 256 + 129] = 9; + table[12 * 256 + 130] = 9; + table[12 * 256 + 131] = 9; + table[12 * 256 + 132] = 9; + table[12 * 256 + 133] = 9; + table[12 * 256 + 134] = 9; + table[12 * 256 + 135] = 9; + table[12 * 256 + 136] = 9; + table[12 * 256 + 137] = 9; + table[12 * 256 + 138] = 9; + table[12 * 256 + 139] = 9; + table[12 * 256 + 140] = 9; + table[12 * 256 + 141] = 9; + table[12 * 256 + 142] = 9; + table[12 * 256 + 143] = 9; + table[12 * 256 + 144] = 9; + table[12 * 256 + 145] = 9; + table[12 * 256 + 146] = 9; + table[12 * 256 + 147] = 9; + table[12 * 256 + 148] = 9; + table[12 * 256 + 149] = 9; + table[12 * 256 + 150] = 9; + table[12 * 256 + 151] = 9; + table[12 * 256 + 152] = 9; + table[12 * 256 + 153] = 9; + table[12 * 256 + 154] = 9; + table[12 * 256 + 155] = 9; + table[12 * 256 + 156] = 9; + table[12 * 256 + 157] = 9; + table[12 * 256 + 158] = 9; + table[12 * 256 + 159] = 9; + table[12 * 256 + 160] = 9; + table[12 * 256 + 161] = 9; + table[12 * 256 + 162] = 9; + table[12 * 256 + 163] = 9; + table[12 * 256 + 164] = 9; + table[12 * 256 + 165] = 9; + table[12 * 256 + 166] = 9; + table[12 * 256 + 167] = 9; + table[12 * 256 + 168] = 9; + table[12 * 256 + 169] = 9; + table[12 * 256 + 170] = 9; + table[12 * 256 + 171] = 9; + table[12 * 256 + 172] = 9; + table[12 * 256 + 173] = 9; + table[12 * 256 + 174] = 9; + table[12 * 256 + 175] = 9; + table[12 * 256 + 176] = 9; + table[12 * 256 + 177] = 9; + table[12 * 256 + 178] = 9; + table[12 * 256 + 179] = 9; + table[12 * 256 + 180] = 9; + table[12 * 256 + 181] = 9; + table[12 * 256 + 182] = 9; + table[12 * 256 + 183] = 9; + table[12 * 256 + 184] = 9; + table[12 * 256 + 185] = 9; + table[12 * 256 + 186] = 9; + table[12 * 256 + 187] = 9; + table[12 * 256 + 188] = 9; + table[12 * 256 + 189] = 9; + table[12 * 256 + 190] = 9; + table[12 * 256 + 191] = 9; + table[13 * 256 + 128] = 9; + table[13 * 256 + 129] = 9; + table[13 * 256 + 130] = 9; + table[13 * 256 + 131] = 9; + table[13 * 256 + 132] = 9; + table[13 * 256 + 133] = 9; + table[13 * 256 + 134] = 9; + table[13 * 256 + 135] = 9; + table[13 * 256 + 136] = 9; + table[13 * 256 + 137] = 9; + table[13 * 256 + 138] = 9; + table[13 * 256 + 139] = 9; + table[13 * 256 + 140] = 9; + table[13 * 256 + 141] = 9; + table[13 * 256 + 142] = 9; + table[13 * 256 + 143] = 9; + table[14 * 256 + 10] = 15; + + table +} + + +pub fn regex_match(input: [u8; N]) -> (BoundedVec, bool) { + let substrings = unsafe { __regex_match(input) }; + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + let mut start_range = 0; + let mut end_range = 0; + + // check the match + for i in 0..N { + // state transition + let temp = input[i] as Field; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + s = 0; + s_next = potential_s_next; + } + std::as_witness(s_next); + + // range conditions for substring matches + if ((start_range == 0) & (end_range == 0)) { + start_range = i as Field; + } + if (((s == 15) & (s_next == 16)) & (end_range == 0)) { + end_range = i as Field + 1; + } + + + let range_0 = substrings.get_unchecked(0).in_range(i); + let case_0 = [ + (s == 5) & ((s_next == 6) | (s_next == 7) | (s_next == 8) | (s_next == 9) | (s_next == 10) | (s_next == 11) | (s_next == 12) | (s_next == 13)), + (s == 6) & ((s_next == 6) | (s_next == 7) | (s_next == 8) | (s_next == 9) | (s_next == 10) | (s_next == 11) | (s_next == 12) | (s_next == 13)), + (s_next == 6) & ((s == 7)), + (s_next == 7) & ((s == 8) | (s == 9) | (s == 10)), + (s_next == 9) & ((s == 11) | (s == 12) | (s == 13)) + ].any(|case| case == true) | !range_0; + + + + let substring_range_check = [case_0] + .all(|case| case == true); + + assert(substring_range_check, "substr array ranges wrong"); + + + s = s_next; + } + // check final state + + let matched: bool = (s == 15) | (s == 16); + + // constrain extracted substrings to be in match range + //let full_match = Sequence::new(start_range as u32, end_range as u32 - start_range as u32); + //let full_match_end = full_match.end(); + // for i in 0..1 { + // let substring = substrings.get_unchecked(i); + // let is_not_valid = i >= substrings.len(); + // let index_check = substring.index >= full_match.index; + // let length_check = substring.end() <= full_match_end; + // let check = (index_check) | is_not_valid; + // assert(check, f"Substring {i} range is out of bounds of the full match found"); + // } + (substrings, matched) +} + + +pub unconstrained fn __regex_match(input: [u8; N]) -> BoundedVec { + // regex: (\r\n|^)to:[^\r\n]+\r\n + let mut substrings: BoundedVec = BoundedVec::new(); + let mut current_substring = Sequence::default(); + let mut full_match = Sequence::default(); + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + + let mut consecutive_substr = 0; + let mut complete = false; + + for i in 0..input.len() { + let temp = input[i] as Field; + let mut reset = false; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + reset = true; + s = 0; + s_next = potential_s_next; + } + // If a substring was in the making, but the state was reset + // we disregard previous progress because apparently it is invalid + if (reset & (consecutive_substr == 1)) { + current_substring = Sequence::default(); + consecutive_substr = 0; + } + // Fill up substrings + + + if ((s == 5) & (s_next == 6) | (s == 5) & (s_next == 7) | (s == 5) & (s_next == 8) | (s == 5) & (s_next == 9) | (s == 5) & (s_next == 10) | (s == 5) & (s_next == 11) | (s == 5) & (s_next == 12) | (s == 5) & (s_next == 13) | (s == 6) & (s_next == 6) | (s == 6) & (s_next == 7) | (s == 6) & (s_next == 8) | (s == 6) & (s_next == 9) | (s == 6) & (s_next == 10) | (s == 6) & (s_next == 11) | (s == 6) & (s_next == 12) | (s == 6) & (s_next == 13) | (s == 7) & (s_next == 6) | (s == 8) & (s_next == 7) | (s == 9) & (s_next == 7) | (s == 10) & (s_next == 7) | (s == 11) & (s_next == 9) | (s == 12) & (s_next == 9) | (s == 13) & (s_next == 9)) { + + if (consecutive_substr == 0) { + current_substring.index = i; + }; + current_substring.length += 1; + consecutive_substr = 1; + } else if ((consecutive_substr == 1) & (s_next == 0)) { + current_substring = Sequence::default(); + full_match = Sequence::default(); + substrings = BoundedVec::new(); + consecutive_substr = 0; + } else if (s == 15) & (s_next == 16) { + full_match.length = i - full_match.index + 1; + complete = true; + } else if (consecutive_substr == 1) { + // The substring is done so "save" it + substrings.push(current_substring); + // reset the substring holder for next use + current_substring = Sequence::default(); + consecutive_substr = 0; + } + s = s_next; + if complete == true { + break; + } + } + assert((s == 15) | (s == 16), f"no match: {s}"); + // Add pending substring that hasn't been added + if consecutive_substr == 1 { + substrings.push(current_substring); + full_match.length = input.len() - full_match.index; + } + + + + substrings +} + + + + \ No newline at end of file diff --git a/packages/noir/src/common.nr b/packages/noir/src/common.nr new file mode 100644 index 00000000..38d2bf60 --- /dev/null +++ b/packages/noir/src/common.nr @@ -0,0 +1,195 @@ +/// BYTE SEQUENCE POINTER /// + +pub struct Sequence { + index: u32, + length: u32, + end: u32 +} + +impl Sequence { + pub fn new(index: u32, length: u32) -> Self { + Self { index, length, end: index + length } + } + + pub fn default() -> Self { + Self { index: 0, length: 0, end: 0 } + } + + pub fn initialized(self) -> bool { + self.length > 0 + } + + pub fn index(self) -> u32 { + self.index + } + + pub fn length(self) -> u32 { + self.length + } + + pub fn end(self) -> u32 { + self.end + } + + pub fn in_range(self, index: u32) -> bool { + // if indexend == 0, index < self.end implicitly returns false if uninitialized + index >= self.index & index < self.end + } +} + +/// SUBSTRING CAPTURE EXTRACTION /// + +/** + * Extracts all substrings from a pattern match + * @dev not super optimal - all substrings will be assumed to be of the length of longest substring. + * often this will be the size of the input. Use at discretion. + * + * @param input - the input array to extract from + * @param sequences - the sequences to extract from the input + * @returns the extracted substrings + */ +pub fn extract_all_substrings< + let INPUT_LENGTH: u32, + let NUM_SUBSTRINGS: u32, + let MAX_SUBSTRING_LENGTH: u32 +>( + input: [u8; INPUT_LENGTH], + sequences: BoundedVec, +) -> BoundedVec, NUM_SUBSTRINGS> {{ + let mut substrings: BoundedVec, NUM_SUBSTRINGS> = BoundedVec::new(); + for i in 0..NUM_SUBSTRINGS {{ + let substring = sequences.get_unchecked(i); + let mut extracted_substring = extract_substring(substring, input); + let mut len = substrings.len() + 1; + if i >= sequences.len() {{ + extracted_substring = BoundedVec::new(); + len = substrings.len(); + }} + substrings.len = len; + substrings.storage[i] = extracted_substring; + }} + substrings +}} + +/** + * Optimized algorithm for extracting a subsequence from an input array + * + * @param substring_sequence - the sequence to extract from the input + * @param input - the input array to extract from + * @returns the extracted subsequence + */ +pub fn extract_substring( + substring_sequence: Sequence, + input: [u8; INPUT_LENGTH], +) -> BoundedVec { + let mut substring: BoundedVec = unsafe { __extract_substring(substring_sequence, input) }; + assert(substring_sequence.length == substring.len(), "length mismatch"); + for i in 0..MAX_SUBSTRING_LENGTH { + // hack for index to never exceed array bounds + // must be constrained to be true when matching is required to prevent 0's passing when shouldn't + // @dev while this adds constraints in worse case it can be more efficient if MAX_SUBSTRING_LENGTH < INPUT_LENGTH + let input_range_check = substring_sequence.index + i < INPUT_LENGTH; + let index = (substring_sequence.index + i) as Field * input_range_check as Field; + + // range where input should match substring + let sequence_range_check = i >= substring_sequence.length; + + // constrain array construction if in range + let expected_byte = input[index]; + let byte = substring.get_unchecked(i); + let matched = (expected_byte as Field == byte as Field); + assert(matched | sequence_range_check, "incorrect substring construction"); + } + substring +} + +/** + * Unconstrained helper to build the extracted substring + * @dev must be checked by extract_substring to constrain construction of substring + * + * @param substring_sequence - the sequence to extract from the input + * @param input - the input array to extract from + * @returns the extracted subsequence + */ +unconstrained fn __extract_substring( + substring_sequence: Sequence, + input: [u8; INPUT_LENGTH], +) -> BoundedVec { + let mut substring: BoundedVec = BoundedVec::new(); + for i in 0..substring_sequence.length { + let byte = input[substring_sequence.index + i]; + substring.push(byte); + } + substring +} + +/// SUBSTRING CAPTURE INPUT MASKING /// + +/** + * Masks input to only reveal public captures defined in the regex + * + * @param substring_sequences - the sequences to mask from the input + * @param input - the input array to mask + * @returns the input masked to only reveal public captures defined in the regex + */ +pub fn mask_input( + substring_sequences: BoundedVec, + input: [u8; INPUT_LENGTH], +) -> [u8; INPUT_LENGTH] { + + let masked: [u8; INPUT_LENGTH] = unsafe { __mask_input(substring_sequences, input) }; + for i in 0..INPUT_LENGTH { + let any_in_range = substring_sequences + .storage() + .any(| sequence: Sequence | sequence.in_range(i)); + let expected_byte = input[i] as Field * any_in_range as Field; + assert(masked[i] as Field == expected_byte, "Incorrect masking"); + } + masked +} + +/** + * Unconstrained helper to mask input + * @dev SHOULD NOT BE CALLED BY ANYTHING EXCEPT `mask_input` + * + * @param substring_sequences - the sequences to mask from the input + * @param input - the input array to mask + * @returns the input masked to only reveal public captures defined in the regex + */ +unconstrained fn __mask_input( + substring_sequences: BoundedVec, + input: [u8; INPUT_LENGTH], +) -> [u8; INPUT_LENGTH] { + let mut masked_input: [u8; INPUT_LENGTH] = [0; INPUT_LENGTH]; + for i in 0..substring_sequences.len() { + let sequence = substring_sequences.get_unchecked(i); + for j in sequence.index..sequence.end() { + masked_input[j] = input[j]; + } + } + masked_input +} + +/// VECTOR REVERSAL /// + +pub fn reverse_vec(input: BoundedVec) -> BoundedVec { + let mut reversed = unsafe { __reverse_vec(input) }; + for i in 0..N { + let in_range = (i < reversed.len()) as Field; + // if in range choose opposite index, otherwise choose same index to check 0's + // yeah I know this is ugly show me a more efficient version and I'll use it + let index = (((input.len() as Field) - (i as Field * in_range) - 1) * in_range as Field + (i as Field * (1 - in_range))) as Field; + let expected_byte = input.get_unchecked(index as u32) as Field * in_range as Field; + let byte = reversed.get_unchecked(i) as Field; + assert(byte == expected_byte, "Incorrect reverse"); + } + reversed +} + +unconstrained fn __reverse_vec(input: BoundedVec) -> BoundedVec { + let mut reversed: BoundedVec = BoundedVec::new(); + for i in 0..input.len() { + reversed.push(input.get(input.len() - i - 1)); + } + reversed +} \ No newline at end of file diff --git a/packages/noir/src/constants.nr b/packages/noir/src/constants.nr new file mode 100644 index 00000000..1be1bc3a --- /dev/null +++ b/packages/noir/src/constants.nr @@ -0,0 +1,22 @@ +/// EMAIL ADDR REGEX /// +// https://www.rfc-editor.org/errata/eid1690#:~:text=Section%203%20says%3A,total%20length%20of%20320%20characters. +pub global ADDR_REGEX_MAX_CAPTURE_LEN: u32 = 320; +global CRLF_POSTFIX: u32 = 2; + +/// TO_ALL REGEX /// +// (\r\n|^)to: +global TO_ALL_MAX_PREFIX: u32 = 5; +// \r\n +pub global TO_ALL_MAX_LEN: u32 = TO_ALL_MAX_PREFIX + ADDR_REGEX_MAX_CAPTURE_LEN + CRLF_POSTFIX; + +/// FROM ALL REGEX /// +// (\r\n|^)from: +global FROM_ALL_MAX_PREFIX: u32 = 7; +pub global FROM_ALL_MAX_LEN: u32 = FROM_ALL_MAX_PREFIX + ADDR_REGEX_MAX_CAPTURE_LEN + CRLF_POSTFIX; + +/// BODY HASH REGEX /// +pub global BODY_HASH_BASE64_LEN: u32 = 44; +pub global BODY_HASH_LEN: u32 = 32; + +/// TIMESTAMP REGEX /// +pub global TIMESTAMP_LEN: u32 = 10; \ No newline at end of file diff --git a/packages/noir/src/lib.nr b/packages/noir/src/lib.nr new file mode 100644 index 00000000..24f74e8f --- /dev/null +++ b/packages/noir/src/lib.nr @@ -0,0 +1,4 @@ +pub mod basic; +pub mod capture; +pub mod common; +pub mod constants; \ No newline at end of file diff --git a/packages/noir/templates/basic.json b/packages/noir/templates/basic.json new file mode 100644 index 00000000..afe2475f --- /dev/null +++ b/packages/noir/templates/basic.json @@ -0,0 +1,16 @@ +{ + "parts": [ + { + "is_public": true, + "regex_def": "a" + }, + { + "is_public": true, + "regex_def": "b" + }, + { + "is_public": true, + "regex_def": "c" + } + ] +} diff --git a/packages/noir/templates/body_hash.json b/packages/noir/templates/body_hash.json new file mode 100644 index 00000000..62ffdbf8 --- /dev/null +++ b/packages/noir/templates/body_hash.json @@ -0,0 +1,20 @@ +{ + "parts": [ + { + "is_public": false, + "regex_def": "(\r\n|^)dkim-signature:" + }, + { + "is_public": false, + "regex_def": "([a-z]+=[^;]+; )+bh=" + }, + { + "is_public": true, + "regex_def": "[a-zA-Z0-9+/=]+" + }, + { + "is_public": false, + "regex_def": ";" + } + ] + } \ No newline at end of file diff --git a/packages/noir/templates/email_addr.json b/packages/noir/templates/email_addr.json new file mode 100644 index 00000000..7060e9a1 --- /dev/null +++ b/packages/noir/templates/email_addr.json @@ -0,0 +1,8 @@ +{ + "parts": [ + { + "is_public": true, + "regex_def": "[A-Za-z0-9!#$%&'*+=?\\-\\^_`{|}~./@]+@[A-Za-z0-9.\\-]+" + } + ] + } \ No newline at end of file diff --git a/packages/noir/templates/email_domain.json b/packages/noir/templates/email_domain.json new file mode 100644 index 00000000..436fd391 --- /dev/null +++ b/packages/noir/templates/email_domain.json @@ -0,0 +1,12 @@ +{ + "parts": [ + { + "is_public": false, + "regex_def": "[A-Za-z0-9!#$%&'*+=?\\-\\^_`{|}~./]+@" + }, + { + "is_public": true, + "regex_def": "[A-Za-z0-9.\\-@]+" + } + ] + } \ No newline at end of file diff --git a/packages/noir/templates/from_all.json b/packages/noir/templates/from_all.json new file mode 100644 index 00000000..28d2415b --- /dev/null +++ b/packages/noir/templates/from_all.json @@ -0,0 +1,16 @@ +{ + "parts": [ + { + "is_public": false, + "regex_def": "(\r\n|^)from:" + }, + { + "is_public": true, + "regex_def": "[^\r\n]+" + }, + { + "is_public": false, + "regex_def": "\r\n" + } + ] +} diff --git a/packages/noir/templates/message_id.json b/packages/noir/templates/message_id.json new file mode 100644 index 00000000..b9d12277 --- /dev/null +++ b/packages/noir/templates/message_id.json @@ -0,0 +1,16 @@ +{ + "parts": [ + { + "is_public": false, + "regex_def": "(\r\n|^)message-id:" + }, + { + "is_public": true, + "regex_def": "<[A-Za-z0-9=@\\.\\+_-]+>" + }, + { + "is_public": false, + "regex_def": "\r\n" + } + ] +} diff --git a/packages/noir/templates/reversed_bracket.json b/packages/noir/templates/reversed_bracket.json new file mode 100644 index 00000000..55ffaaba --- /dev/null +++ b/packages/noir/templates/reversed_bracket.json @@ -0,0 +1,16 @@ +{ + "parts": [ + { + "is_public": false, + "regex_def": ">" + }, + { + "is_public": true, + "regex_def": "[^<>]+" + }, + { + "is_public": false, + "regex_def": "<.*" + } + ] +} \ No newline at end of file diff --git a/packages/noir/templates/subject_all.json b/packages/noir/templates/subject_all.json new file mode 100644 index 00000000..882e4b76 --- /dev/null +++ b/packages/noir/templates/subject_all.json @@ -0,0 +1,16 @@ +{ + "parts": [ + { + "is_public": false, + "regex_def": "(\r\n|^)subject:" + }, + { + "is_public": true, + "regex_def": "[^\r\n]+" + }, + { + "is_public": false, + "regex_def": "\r\n" + } + ] + } \ No newline at end of file diff --git a/packages/noir/templates/timestamp.json b/packages/noir/templates/timestamp.json new file mode 100644 index 00000000..48fc76c4 --- /dev/null +++ b/packages/noir/templates/timestamp.json @@ -0,0 +1,20 @@ +{ + "parts": [ + { + "is_public": false, + "regex_def": "(\r\n|^)dkim-signature:" + }, + { + "is_public": false, + "regex_def": "([a-z]+=[^;]+; )+t=" + }, + { + "is_public": true, + "regex_def": "[0-9]+" + }, + { + "is_public": false, + "regex_def": ";" + } + ] + } \ No newline at end of file diff --git a/packages/noir/templates/to_all.json b/packages/noir/templates/to_all.json new file mode 100644 index 00000000..76be9fdb --- /dev/null +++ b/packages/noir/templates/to_all.json @@ -0,0 +1,16 @@ +{ + "parts": [ + { + "is_public": false, + "regex_def": "(\r\n|^)to:" + }, + { + "is_public": true, + "regex_def": "[^\r\n]+" + }, + { + "is_public": false, + "regex_def": "\r\n" + } + ] +} \ No newline at end of file diff --git a/packages/noir/x/Nargo.toml b/packages/noir/x/Nargo.toml new file mode 100644 index 00000000..ea01f545 --- /dev/null +++ b/packages/noir/x/Nargo.toml @@ -0,0 +1,10 @@ +[package] +name = "x" +type = "bin" +authors = [""] + +[dependencies] +regex = { path = "../" } +zkemail = { tag = "v0.4.2", git = "https://github.com/zkemail/zkemail.nr", directory = "lib" } +base64 = { tag = "v0.3.1", git = "https://github.com/noir-lang/noir_base64" } +sha256 = { tag = "v0.1.2", git = "https://github.com/noir-lang/sha256" } diff --git a/packages/noir/x/src/main.nr b/packages/noir/x/src/main.nr new file mode 100644 index 00000000..a2e86eb5 --- /dev/null +++ b/packages/noir/x/src/main.nr @@ -0,0 +1,202 @@ +use regex::capture::composite::{decoded_body_hash, timestamp as timestamp_regex}; +use std::hash::pedersen_hash; +use sha256::sha256_var; +use zkemail::{dkim::RSAPubkey, KEY_LIMBS_2048}; + +global MAX_EMAIL_HEADER_LENGTH: u32 = 512; +global MAX_EMAIL_BODY_LENGTH: u32 = 1024; + +pub struct Output { + pubkey_hash: Field, // the hash of the pubkey + email_nullifier: Field, // the unique nullifier of the email + timestamp: Field // timestamp from dkim signature over email +} + +/** + * Demonstrates ZKEmail where the body hash is regexed from the header + */ +fn main( + header: BoundedVec, + pubkey: RSAPubkey, + signature: [Field; KEY_LIMBS_2048], + body: BoundedVec, +) -> pub Output { + // 1. verify header + pubkey.verify_dkim_signature(header, signature); + // 2. extract the body hash from the header + let signed_body_hash = decoded_body_hash::regex_match(header); + // 3. hash the asserted body + let computed_body_hash: [u8; 32] = sha256_var(body.storage(), body.len() as u64); + // 4. compare found body hash + assert( + signed_body_hash == computed_body_hash, + "SHA256 hash computed over body does not match body hash found in DKIM-signed header", + ); + // 5. get the timestamp (cuz why not) + let timestamp = timestamp_regex::regex_match(header); + // 6. publicly output the pubkey hash, email nullifier, and timestamp + Output { + pubkey_hash: pubkey.hash(), + email_nullifier: pedersen_hash(signature), + timestamp: timestamp_regex::parse_timestamp(timestamp) + } +} + +#[test] +fn test_zkemail_with_regex() { + // inputs // + let header: BoundedVec = BoundedVec { + storage: [ + 102, 114, 111, 109, 58, 114, 117, 110, 110, 105, 101, 114, 46, 108, 101, 97, 103, 117, + 101, 115, 46, 48, 106, 64, 105, 99, 108, 111, 117, 100, 46, 99, 111, 109, 13, 10, 99, + 111, 110, 116, 101, 110, 116, 45, 116, 121, 112, 101, 58, 116, 101, 120, 116, 47, 112, + 108, 97, 105, 110, 59, 32, 99, 104, 97, 114, 115, 101, 116, 61, 117, 116, 102, 45, 56, + 13, 10, 109, 105, 109, 101, 45, 118, 101, 114, 115, 105, 111, 110, 58, 49, 46, 48, 32, + 40, 77, 97, 99, 32, 79, 83, 32, 88, 32, 77, 97, 105, 108, 32, 49, 54, 46, 48, 32, 92, + 40, 51, 55, 51, 49, 46, 53, 48, 48, 46, 50, 51, 49, 92, 41, 41, 13, 10, 115, 117, 98, + 106, 101, 99, 116, 58, 66, 105, 116, 99, 111, 105, 110, 13, 10, 109, 101, 115, 115, 97, + 103, 101, 45, 105, 100, 58, 60, 49, 50, 56, 48, 48, 65, 57, 48, 45, 52, 69, 67, 67, 45, + 52, 53, 49, 51, 45, 57, 50, 57, 56, 45, 65, 51, 51, 53, 52, 54, 49, 50, 50, 57, 50, 48, + 64, 109, 101, 46, 99, 111, 109, 62, 13, 10, 100, 97, 116, 101, 58, 87, 101, 100, 44, 32, + 51, 32, 65, 112, 114, 32, 50, 48, 50, 52, 32, 49, 54, 58, 50, 51, 58, 52, 56, 32, 43, + 48, 53, 51, 48, 13, 10, 116, 111, 58, 122, 107, 101, 119, 116, 101, 115, 116, 64, 103, + 109, 97, 105, 108, 46, 99, 111, 109, 13, 10, 100, 107, 105, 109, 45, 115, 105, 103, 110, + 97, 116, 117, 114, 101, 58, 118, 61, 49, 59, 32, 97, 61, 114, 115, 97, 45, 115, 104, 97, + 50, 53, 54, 59, 32, 99, 61, 114, 101, 108, 97, 120, 101, 100, 47, 114, 101, 108, 97, + 120, 101, 100, 59, 32, 100, 61, 105, 99, 108, 111, 117, 100, 46, 99, 111, 109, 59, 32, + 115, 61, 49, 97, 49, 104, 97, 105, 59, 32, 116, 61, 49, 55, 49, 50, 49, 52, 49, 54, 52, + 52, 59, 32, 98, 104, 61, 50, 74, 115, 100, 75, 52, 66, 77, 122, 122, 116, 57, 119, 52, + 90, 108, 122, 50, 84, 100, 121, 86, 67, 70, 99, 43, 108, 55, 118, 78, 121, 84, 53, 97, + 65, 103, 71, 68, 89, 102, 55, 102, 77, 61, 59, 32, 104, 61, 102, 114, 111, 109, 58, 67, + 111, 110, 116, 101, 110, 116, 45, 84, 121, 112, 101, 58, 77, 105, 109, 101, 45, 86, 101, + 114, 115, 105, 111, 110, 58, 83, 117, 98, 106, 101, 99, 116, 58, 77, 101, 115, 115, 97, + 103, 101, 45, 73, 100, 58, 68, 97, 116, 101, 58, 116, 111, 59, 32, 98, 61, 128, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, + ], + len: 470, + }; + + let body: BoundedVec = BoundedVec { + storage: [ + 84, 104, 101, 32, 84, 105, 109, 101, 115, 32, 48, 51, 47, 74, 97, 110, 47, 50, 48, 48, + 57, 32, 67, 104, 97, 110, 99, 101, 108, 108, 111, 114, 32, 111, 110, 32, 98, 114, 105, + 110, 107, 32, 111, 102, 32, 115, 101, 99, 111, 110, 100, 32, 98, 97, 105, 108, 111, 117, + 116, 32, 102, 111, 114, 32, 98, 97, 110, 107, 115, 13, 10, 13, 10, 49, 53, 32, 121, 101, + 97, 114, 115, 32, 97, 103, 111, 44, 32, 83, 97, 116, 111, 115, 104, 105, 32, 109, 105, + 110, 101, 100, 32, 116, 104, 101, 32, 102, 105, 114, 115, 116, 32, 98, 108, 111, 99, + 107, 32, 111, 102, 32, 116, 104, 101, 32, 66, 105, 116, 99, 111, 105, 110, 32, 98, 108, + 111, 99, 107, 99, 104, 97, 105, 110, 32, 61, 13, 10, 65, 102, 116, 101, 114, 32, 116, + 104, 101, 32, 66, 105, 116, 99, 111, 105, 110, 32, 119, 104, 105, 116, 101, 32, 112, 97, + 112, 101, 114, 32, 97, 112, 112, 101, 97, 114, 101, 100, 32, 111, 110, 32, 79, 99, 116, + 111, 98, 101, 114, 32, 51, 49, 44, 32, 50, 48, 48, 56, 44, 32, 111, 110, 32, 97, 32, 61, + 13, 10, 99, 114, 121, 112, 116, 111, 103, 114, 97, 112, 104, 121, 32, 109, 97, 105, 108, + 105, 110, 103, 32, 108, 105, 115, 116, 44, 32, 116, 104, 101, 32, 71, 101, 110, 101, + 115, 105, 115, 32, 66, 108, 111, 99, 107, 32, 61, 69, 50, 61, 56, 48, 61, 57, 52, 32, + 116, 104, 101, 32, 102, 105, 114, 115, 116, 32, 98, 105, 116, 99, 111, 105, 110, 32, 61, + 13, 10, 98, 108, 111, 99, 107, 32, 97, 110, 100, 32, 116, 104, 101, 32, 98, 97, 115, + 105, 115, 32, 111, 102, 32, 116, 104, 101, 32, 101, 110, 116, 105, 114, 101, 32, 66, + 105, 116, 99, 111, 105, 110, 32, 116, 114, 97, 100, 105, 110, 103, 32, 115, 121, 115, + 116, 101, 109, 32, 105, 110, 32, 112, 108, 97, 99, 101, 32, 116, 111, 32, 61, 13, 10, + 116, 104, 105, 115, 32, 100, 97, 121, 32, 61, 69, 50, 61, 56, 48, 61, 57, 52, 32, 119, + 97, 115, 32, 109, 105, 110, 101, 100, 32, 111, 110, 32, 74, 97, 110, 117, 97, 114, 121, + 32, 51, 44, 32, 50, 48, 48, 57, 46, 61, 50, 48, 13, 10, 13, 10, 84, 104, 101, 32, 71, + 101, 110, 101, 115, 105, 115, 32, 66, 108, 111, 99, 107, 32, 105, 115, 32, 97, 108, 115, + 111, 32, 107, 110, 111, 119, 110, 32, 97, 115, 32, 66, 108, 111, 99, 107, 32, 48, 32, + 111, 114, 32, 66, 108, 111, 99, 107, 32, 49, 44, 32, 97, 110, 100, 32, 105, 115, 32, + 115, 116, 105, 108, 108, 32, 105, 110, 32, 61, 13, 10, 116, 104, 101, 32, 66, 105, 116, + 99, 111, 105, 110, 32, 110, 101, 116, 119, 111, 114, 107, 44, 32, 119, 104, 101, 114, + 101, 32, 105, 116, 32, 119, 105, 108, 108, 32, 114, 101, 109, 97, 105, 110, 32, 97, 115, + 32, 108, 111, 110, 103, 32, 97, 115, 32, 116, 104, 101, 114, 101, 32, 105, 115, 32, 97, + 32, 99, 111, 109, 112, 117, 116, 101, 114, 32, 61, 13, 10, 114, 117, 110, 110, 105, 110, + 103, 32, 116, 104, 101, 32, 66, 105, 116, 99, 111, 105, 110, 32, 115, 111, 102, 116, + 119, 97, 114, 101, 46, 61, 50, 48, 13, 10, 13, 10, 65, 108, 108, 32, 110, 111, 100, 101, + 115, 32, 105, 110, 32, 116, 104, 101, 32, 66, 105, 116, 99, 111, 105, 110, 32, 110, 101, + 116, 119, 111, 114, 107, 32, 99, 97, 110, 32, 99, 111, 110, 115, 117, 108, 116, 32, 105, + 116, 44, 32, 101, 118, 101, 110, 32, 105, 102, 32, 105, 116, 32, 105, 115, 32, 97, 116, + 32, 116, 104, 101, 32, 61, 13, 10, 111, 116, 104, 101, 114, 32, 101, 110, 100, 32, 111, + 102, 32, 116, 104, 101, 32, 110, 101, 116, 119, 111, 114, 107, 32, 119, 105, 116, 104, + 32, 104, 117, 110, 100, 114, 101, 100, 115, 32, 111, 102, 32, 116, 104, 111, 117, 115, + 97, 110, 100, 115, 32, 111, 102, 32, 98, 108, 111, 99, 107, 115, 46, 13, 10, 128, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 23, 32, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + ], + len: 740, + }; + + let pubkey: RSAPubkey = RSAPubkey { + modulus: [ + 0xe5cf995b5ef59ce9943d1f4209b6ab, + 0xe0caf03235e91a2db27e9ed214bcc6, + 0xafe1309f87414bd36ed296dacfade2, + 0xbeff3f19046a43adce46c932514988, + 0x324041af8736e87de4358860fff057, + 0xadcc6669dfa346f322717851a8c22a, + 0x8b2a193089e6bf951c553b5a6f71aa, + 0x0a570fe582918c4f731a0002068df2, + 0x39419a433d6bfdd1978356cbca4b60, + 0x550d695a514d38b45c862320a00ea5, + 0x1c56ac1dfbf1beea31e8a613c2a51f, + 0x6a30c9f22d2e5cb6934263d0838809, + 0x0a281f268a44b21a4f77a91a52f960, + 0x5134dc3966c8e91402669a47cc8597, + 0x71590781df114ec072e641cdc5d224, + 0xa1bc0f0937489c806c1944fd029dc9, + 0x911f6e47f84db3b64c3648ebb5a127, + 0xd5, + ], + redc: [ + 0x48a824e4ebc7e0f1059f3ecfa57c46, + 0x5c1db23f3c7d47ad7e7d7cfda5189a, + 0x9bb6bbbd8facf011f022fa9051aec0, + 0x4faa4cef474bed639362ea71f7a217, + 0x503aa50b77e24b030841a7d0615812, + 0xbbf4e62805e1860a904c0f66a5fad1, + 0xcbd24b72442d2ce647dd7d0a443685, + 0x74a8839a4460c169dce7138efdaef5, + 0xf06e09e3191b995b08e5b45182f650, + 0x1fad4a89f8369fe10e5d4b6e149a10, + 0xc778b15982d11ebf7fe23b4e15f105, + 0x09ff3a4567077510c474e4ac0a21ad, + 0x37e69e5dbb77167b73065e4c5ad6aa, + 0xcf4774e22e7fe3a38642186f7ae74b, + 0x6e72b5eb4c813a3b37998083aab81e, + 0x48e7050aa8abedce5a45c169853761, + 0xd3285e53b322b221f7bcf4f8f8ad8a, + 0x132d, + ], + }; + + let signature = [ + 0xf193c3300b7c9902e32861c38d0d2d, + 0x9f6927fdb3df0b84092d8459654327, + 0x8a0bea5e2fa82821e49c27b68d5a7b, + 0xaa8c0acc1190f9fd845ef64f8e7ae9, + 0xa7aeebb37f4395965543e6df69a5a7, + 0x087ecef9921569cfba83331ca11c6b, + 0x4589ed316ed20757e65ad221736011, + 0x0835d8748f11dcc985700c3fea27b1, + 0xe870d2493fb83b4a1d72350e5de926, + 0x268b28eda0aac07625cfab32b60af1, + 0xb41a164eae7ba1602eaec5b5a39fe6, + 0x693cc5ec578422bee48eabe390fc37, + 0xa29504dd504f14423f2ce65b2ac388, + 0x6c3ac6310c084a0b126fcd5225c208, + 0xab0903e48563e5f4a5365ac5cbd888, + 0xf05bf2e5b6266c0ac88dfc733c414f, + 0xf58f9e9669e0f4f3086cce1187fd44, + 0xb9, + ]; + + // test // + let output = main(header, pubkey, signature, body); + assert(output.timestamp == 1712141644); +} diff --git a/x/gen.sh b/x/gen.sh new file mode 100755 index 00000000..be5be898 --- /dev/null +++ b/x/gen.sh @@ -0,0 +1,17 @@ +#!/bin/bash + +GEN_SUBSTRINGS=true + +# generate using sparse array +zk-regex decomposed -d x.json \ + --noir-file-path ./sparse/src/regex.nr \ + -g $GEN_SUBSTRINGS \ + --sparse-array true \ + --use-common crate::regex_common + +# generate using simple array +zk-regex decomposed -d x.json \ + --noir-file-path ./simple/src/regex.nr \ + -g $GEN_SUBSTRINGS \ + --sparse-array false \ + --use-common crate::regex_common \ No newline at end of file diff --git a/x/gen_simple.sh b/x/gen_simple.sh new file mode 100755 index 00000000..50d36c49 --- /dev/null +++ b/x/gen_simple.sh @@ -0,0 +1,19 @@ +#!/bin/bash + +GEN_SUBSTRINGS=true + +# generate using sparse array +zk-regex raw \ + -r "1=(a|b) (2=(b|c)+ )+d" \ + -s ./transitions.json \ + --noir-file-path ./sparse/src/regex.nr \ + -g $GEN_SUBSTRINGS \ + --sparse-array true + +# generate using simple array +zk-regex raw \ + -r "1=(a|b) (2=(b|c)+ )+d" \ + -s ./transitions.json \ + --noir-file-path ./simple/src/regex.nr \ + -g $GEN_SUBSTRINGS \ + --sparse-array false \ No newline at end of file diff --git a/x/info.sh b/x/info.sh new file mode 100755 index 00000000..aec83921 --- /dev/null +++ b/x/info.sh @@ -0,0 +1,15 @@ +#!/bin/bash + +# echo "============[Sparse Array Regex]============" +# cd sparse +# nargo compile --force --silence-warnings +# nargo info +# bb gates -b target/sparse_regex.json | grep "circuit" +# cd .. + +echo "============[Simple Array Regex]============" +cd simple +nargo compile --force --silence-warnings +nargo info +bb gates -b target/simple_regex.json | grep "circuit" +cd .. \ No newline at end of file diff --git a/x/profile.sh b/x/profile.sh new file mode 100755 index 00000000..508178e4 --- /dev/null +++ b/x/profile.sh @@ -0,0 +1,11 @@ +#!/bin/bash +SCRIPT_DIR="$(dirname "$(realpath "$0")")" +BACKEND_BINARY_PATH=$(which bb) + +cd $SCRIPT_DIR + +noir-profiler gates \ + --artifact-path ./simple/target/simple_regex.json \ + --backend-path $BACKEND_BINARY_PATH \ + --output ./simple +mv ./simple/main::gates.svg ./simple/simple_flamegraph.svg diff --git a/x/prove.sh b/x/prove.sh new file mode 100755 index 00000000..ddf9d7ec --- /dev/null +++ b/x/prove.sh @@ -0,0 +1,28 @@ +#!/bin/bash + +if command -v gdate &> /dev/null +then + # Set variable for gdate + date_cmd='gdate' +else + # Set variable for date (Linux typically) + date_cmd='date' +fi + +cd sparse + +nargo execute witness +witness_end=$($date_cmd +%s%N) +duration_witness=$((witness_end - start_time)) +witness_seconds=$(echo "$duration_witness / 1000000000" | bc -l) +echo "Witness generated in: $witness_seconds seconds" +echo "Proving with UltraHonk..." + +bb prove_ultra_honk -b ./target/sparse_regex.json -w ./target/witness.gz -o ./target/honk.proof +end_time=$($date_cmd +%s%N) +duration_prover=$((end_time - witness_end)) +duration_total=$((end_time - start_time)) +prover_seconds=$(echo "$duration_prover / 1000000000" | bc -l) +total_seconds=$(echo "$duration_total / 1000000000" | bc -l) +echo "Proof generated in: $prover_seconds seconds" +echo "Total time for client: $total_seconds seconds" diff --git a/x/r.json b/x/r.json new file mode 100644 index 00000000..329a3b9b --- /dev/null +++ b/x/r.json @@ -0,0 +1,16 @@ +{ + "parts": [ + { + "is_public": true, + "regex_def": "x[0-9]{2}" + }, + { + "is_public": false, + "regex_def": "-y{2,3}" + }, + { + "is_public": true, + "regex_def": "_z" + } + ] +} diff --git a/x/simple/Nargo.toml b/x/simple/Nargo.toml new file mode 100644 index 00000000..bc4707ba --- /dev/null +++ b/x/simple/Nargo.toml @@ -0,0 +1,7 @@ +[package] +name = "simple_regex" +type = "bin" +authors = [""] +compiler_version = ">=1.0.0" + +[dependencies] \ No newline at end of file diff --git a/x/simple/Prover.toml b/x/simple/Prover.toml new file mode 100644 index 00000000..abd5f0da --- /dev/null +++ b/x/simple/Prover.toml @@ -0,0 +1 @@ +input = [97, 98, 99, 100, 101, 102, 103, 104, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0] \ No newline at end of file diff --git a/x/simple/simple_flamegraph.svg b/x/simple/simple_flamegraph.svg new file mode 100644 index 00000000..bbc00dc8 --- /dev/null +++ b/x/simple/simple_flamegraph.svg @@ -0,0 +1,493 @@ +./simple/target/simple_regex.json-main Reset ZoomSearch acir::blackbox::range (5,419 gates, 4.03%)acir..acir::memory::init (3 gates, 0.00%)main.nr:10:16::r != 0 (3,072 gates, 2.29%)m..acir::arithmetic (3,072 gates, 2.29%)a..acir::blackbox::range (4,027 gates, 3.00%)aci..regex.nr:1512:34::__regex_match(input) (4,029 gates, 3.00%)reg..acir::memory::init (2 gates, 0.00%)acir::arithmetic (1,060 gates, 0.79%)acir::memory::init (15 gates, 0.01%)regex.nr:1525:18::table[s * 256 + temp] (16,435 gates, 12.24%)regex.nr:1525:18::..acir::memory::op (15,360 gates, 11.43%)acir::memory::opregex.nr:1526:32::table[temp] (15,360 gates, 11.43%)regex.nr:1526:32:..acir::memory::op (15,360 gates, 11.43%)acir::memory::opregex.nr:1527:12::s_next == 0 (2,048 gates, 1.52%)acir::arithmetic (2,048 gates, 1.52%)regex.nr:1529:27::0 (1,021 gates, 0.76%)acir::arithmetic (1,021 gates, 0.76%)regex.nr:1532:14::start_range == 0 (3,066 gates, 2.28%)r..acir::arithmetic (3,066 gates, 2.28%)a..regex.nr:1532:35::end_range == 0 (5,108 gates, 3.80%)rege..acir::arithmetic (5,108 gates, 3.80%)acir..regex.nr:1533:27::i as Field (2,044 gates, 1.52%)acir::arithmetic (2,044 gates, 1.52%)regex.nr:1535:13::((s == 33) | (s == 34)) & (end_range == 0) (1,022 gates, 0.76%)acir::arithmetic (1,022 gates, 0.76%)regex.nr:1535:15::s == 33 (3,069 gates, 2.28%)r..acir::arithmetic (3,069 gates, 2.28%)a..regex.nr:1535:27::s == 34 (3,069 gates, 2.28%)r..acir::arithmetic (3,069 gates, 2.28%)a..regex.nr:1536:25::i as Field (2,044 gates, 1.52%)acir::arithmetic (2,044 gates, 1.52%)acir::arithmetic (1,024 gates, 0.76%)regex.nr:1691:31::index < self.end() (3,584 gates, 2.67%)re..acir::blackbox::range (2,560 gates, 1.91%)a..acir::arithmetic (1 gates, 0.00%)regex.nr:1691:39::self.end (3 gates, 0.00%)regex.nr:1687:9::self.index + self.length (3 gates, 0.00%)acir::blackbox::range (2 gates, 0.00%)acir::arithmetic (1,024 gates, 0.76%)regex.nr:1541:23::pattern_match.substrings.get_unchecked(0).in_range (7,683 gates, 5.72%)regex.n..regex.nr:1691:9::index >= self.index (4,096 gates, 3.05%)reg..acir::blackbox::range (3,072 gates, 2.29%)a..regex.nr:1542:22::[ + (s_next == 32) & ((s == 31) | (s == 32)) + ].any(|case| case == true) | !range_0 (2,048 gates, 1.52%)acir::arithmetic (2,048 gates, 1.52%)regex.nr:1543:13::(s_next == 32) & ((s == 31) | (s == 32)) (1,024 gates, 0.76%)acir::arithmetic (1,024 gates, 0.76%)regex.nr:1543:14::s_next == 32 (3,072 gates, 2.29%)r..acir::arithmetic (3,072 gates, 2.29%)a..regex.nr:1543:32::s == 31 (3,072 gates, 2.29%)r..acir::arithmetic (3,072 gates, 2.29%)a..regex.nr:1543:44::s == 32 (3,072 gates, 2.29%)r..acir::arithmetic (3,072 gates, 2.29%)a..regex.nr:1551:16::substring_range_check (1,024 gates, 0.76%)acir::arithmetic (1,024 gates, 0.76%)acir::arithmetic (4 gates, 0.00%)regex.nr:1556:36::start_range as u32 (710 gates, 0.53%)acir::blackbox::range (706 gates, 0.53%)acir::arithmetic (1 gates, 0.00%)regex.nr:1556:56::end_range as u32 - start_range as u32 (2 gates, 0.00%)acir::blackbox::range (1 gates, 0.00%)acir::arithmetic (4 gates, 0.00%)regex.nr:1556:56::end_range as u32 (18 gates, 0.01%)acir::blackbox::range (14 gates, 0.01%)acir::arithmetic (1 gates, 0.00%)regex.nr:1557:26::full_match.end (4 gates, 0.00%)regex.nr:1687:9::self.index + self.length (4 gates, 0.00%)acir::blackbox::range (3 gates, 0.00%)acir::arithmetic (2,013 gates, 1.50%)regex.nr:1559:25::pattern_match.substrings.get_unchecked (6,105 gates, 4.54%)regex..bounded_vec.nr:112:9::self.storage[index] (6,105 gates, 4.54%)bound..acir::memory::op (4,092 gates, 3.05%)aci..acir::arithmetic (1,024 gates, 0.76%)regex.nr:1560:28::i >= pattern_match.substrings.len() (5,118 gates, 3.81%)rege..acir::blackbox::range (4,094 gates, 3.05%)aci..acir::arithmetic (1,024 gates, 0.76%)regex.nr:1561:27::substring.index >= full_match.index (3,073 gates, 2.29%)r..acir::blackbox::range (2,049 gates, 1.53%)acir::arithmetic (1,024 gates, 0.76%)regex.nr:1562:28::substring.end() <= full_match_end (3,072 gates, 2.29%)r..acir::blackbox::range (2,048 gates, 1.52%)acir::arithmetic (1,023 gates, 0.76%)regex.nr:1562:28::substring.end (3,069 gates, 2.28%)r..regex.nr:1687:9::self.index + self.length (3,069 gates, 2.28%)r..acir::blackbox::range (2,046 gates, 1.52%)regex.nr:1563:21::(index_check & length_check) | is_not_valid (1,024 gates, 0.76%)acir::arithmetic (1,024 gates, 0.76%)regex.nr:1564:16::check (1,024 gates, 0.76%)acir::arithmetic (1,024 gates, 0.76%)regex.nr:1568:12::(s == 33) | (s == 34) (1 gates, 0.00%)acir::arithmetic (1 gates, 0.00%)regex.nr:1568:13::s == 33 (3 gates, 0.00%)acir::arithmetic (3 gates, 0.00%)regex.nr:1568:25::s == 34 (3 gates, 0.00%)acir::arithmetic (3 gates, 0.00%)regex.nr:1705:72::__extract_substring(substring_sequence, input) (1,283 gates, 0.96%)acir::blackbox::range (1,283 gates, 0.96%)acir::arithmetic (1,024 gates, 0.76%)regex.nr:1711:33::substring_sequence.index + i < INPUT_LENGTH (3,840 gates, 2.86%)re..acir::blackbox::range (2,816 gates, 2.10%)a..acir::arithmetic (1,023 gates, 0.76%)regex.nr:1711:33::substring_sequence.index + i (2,812 gates, 2.09%)r..acir::blackbox::range (1,789 gates, 1.33%)acir::arithmetic (1,024 gates, 0.76%)regex.nr:1715:36::i >= substring_sequence.length (3,840 gates, 2.86%)re..acir::blackbox::range (2,816 gates, 2.10%)a..acir::arithmetic (1,024 gates, 0.76%)regex.nr:1718:29::input[index] (4,096 gates, 3.05%)reg..acir::memory::op (3,072 gates, 2.29%)a..regex.nr:1720:24::expected_byte as Field == byte as Field (3,072 gates, 2.29%)r..acir::arithmetic (3,072 gates, 2.29%)a..regex.nr:1574:39::extract_substring(substring, input) (19,967 gates, 14.86%)regex.nr:1574:39::extra..regex.nr:1721:16::matched | sequence_range_check (1,024 gates, 0.76%)acir::arithmetic (1,024 gates, 0.76%)acir::arithmetic (2,048 gates, 1.52%)all (134,325 gates, 100%)main.nr:6:13::regex::regex_match(input) (125,831 gates, 93.68%)main.nr:6:13::regex::regex_match(input)regex.nr:1577:35::BoundedVec::new() (3,328 gates, 2.48%)re..acir::blackbox::range (1,280 gates, 0.95%) \ No newline at end of file diff --git a/x/simple/src/main.nr b/x/simple/src/main.nr new file mode 100644 index 00000000..99eb9a33 --- /dev/null +++ b/x/simple/src/main.nr @@ -0,0 +1,203 @@ +mod regex; +mod regex_common; + +global MAX_INPUT_SIZE: u32 = 1024; + +fn main(input: [u8; MAX_INPUT_SIZE]) { + let matches = regex::regex_match(input); + let substring = + regex_common::extract_substring::(matches.get(0), input); + // let q = substrings.get_unchecked(0); + for i in 0..MAX_INPUT_SIZE { + let r = substring.get_unchecked(i); + assert(r != 0); + } +} + +#[test] +fn test_out() { + let input = "xaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaab" + .as_bytes(); + let matches = regex::regex_match(input); + let substring = regex_common::extract_substring::<846, 846>(matches.get(0), input); + println(f"substring: {substring}"); +} + +// #[test] +// fn test_pass_1() { +// // let input: [u8; 8] = "x12-yy_z".as_bytes(); +// let input = "x12-yy_ x12-yy_z ".as_bytes(); + +// let out = regex::regex_match(input); +// println(f"out: {out}"); +// // for i in 0..2 { +// // if i < out.len() { +// // println(out.get(i)); +// // } +// // } +// // println(out); +// } + +// #[test] +fn test_2() { + let input2 = "\r\nsubject:this is a test.\r\n ".as_bytes(); + let input = "subject:これはテストです。\r\n".as_bytes(); + // let mut x = [0; 38]; + // for i in 0..37 { + // x[i + 1] = input[i]; + // } + // // x[0] = 0xFF; + // println(x); + // // let (out, _, _) = regex::__regex_match(input); + // let out = regex::regex_match(input2); + // for i in 0..10 { + // if i < out.len() { + // println(out.get(i)); + // } + // } +} + +// #[test] +// fn test_3() { +// let input = "dkim-signature:v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20230601; t=1694989812; x=1695594612; dara=google.com; h=to:subject:message-id:date:from:mime-version:from:to:cc:subject :date:message-id:reply-to; bh=BWETwQ9JDReS4GyR2v2TTR8Bpzj9ayumsWQJ3q7vehs=; b=".as_bytes(); +// let out = regex::regex_match(input); +// for i in 0..1 { +// if i < out.len() { +// println(out.get(i)); +// } +// } + +// } + +// #[test] +// fn test_4() { +// let input = "aa".as_bytes(); +// let out = regex::regex_match(input); +// println(out.get(0)); +// } + +#[test] +fn test_5() { + let input2 = "Latin-Extension=Ʃƣƙ Greek=ϕω Cyrillic=иЩ Arabic=أبت Devanagari=आदित्य Hiragana&Katakana=なツ" + .as_bytes(); + let input = [76, 97, 116, 105, 110, 45, 69, 120, 116, 101, 110, 115, 105, 111, 110, 61, 195, 154, 197, 178, 196, 165, 196, 168, 198, 164, 195, 174, 196, 185, 197, 187, 32, 71, 114, 101, 101, 107, 61, 207, 186, 207, 167, 32, 67, 121, 114, 105, 108, 108, 105, 99, 61, 209, 138, 211, 171, 209, 132, 209, 178, 209, 151, 211, 160, 209, 167, 208, 175]; + let out = regex::regex_match(input); + for i in 0..3 { + if i < out.len() { + let substring = regex_common::extract_substring::<_, 4000>(out.get(i), input); + println(f"substring: {substring}"); + } else { + println(f"No element at {i}"); + } + } +} + +#[test] +fn test_pass_3() { + let input = "ab".as_bytes(); + let matches = regex::regex_match(input); + let substring = regex_common::extract_substring::<_, 2>(matches.get(0), input); + println(f"substring: {substring}"); +} + +// #[test] +// fn test_pass_4() { +// let input: [u8; 9] = "x45-yyy_z".as_bytes(); +// regex::regex_match(input); +// } + +// #[test] +// fn test_pass_5() { +// let input: [u8; 8] = "x01-yy_z".as_bytes(); +// regex::regex_match(input); +// } + +// #[test] +// fn test_pass_6() { +// let input: [u8; 9] = "x78-yyy_z".as_bytes(); +// regex::regex_match(input); +// } + +// #[test] +// fn test_pass_7() { +// let input: [u8; 8] = "x34-yy_z".as_bytes(); +// regex::regex_match(input); +// } + +// #[test] +// fn test_pass_8() { +// let input: [u8; 9] = "x89-yyy_z".as_bytes(); +// regex::regex_match(input); +// } + +// #[test] +// fn test_pass_9() { +// let input: [u8; 8] = "x23-yy_z".as_bytes(); +// regex::regex_match(input); +// } + +// #[test] +// fn test_pass_10() { +// let input: [u8; 9] = "x67-yyy_z".as_bytes(); +// regex::regex_match(input); +// } + +// #[test(should_fail)] +// fn test_fail_1() { +// let input: [u8; 10] = "x123-yyy_z".as_bytes(); +// regex::regex_match(input); +// } + +// #[test(should_fail)] +// fn test_fail_2() { +// let input: [u8; 7] = "x12-y_z".as_bytes(); +// regex::regex_match(input); +// } + +// #[test(should_fail)] +// fn test_fail_3() { +// let input: [u8; 7] = "x12-yyy".as_bytes(); +// regex::regex_match(input); +// } + +// #[test(should_fail)] +// fn test_fail_4() { +// let input: [u8; 8] = "x1-yyy_z".as_bytes(); +// regex::regex_match(input); +// } + +// #[test(should_fail)] +// fn test_fail_5() { +// let input: [u8; 9] = "x12-yy_zz".as_bytes(); +// regex::regex_match(input); +// } + +// #[test(should_fail)] +// fn test_fail_6() { +// let input: [u8; 9] = "x12-yyy_x".as_bytes(); +// regex::regex_match(input); +// } + +// #[test(should_fail)] +// fn test_fail_7() { +// let input: [u8; 7] = "x12yy_z".as_bytes(); +// regex::regex_match(input); +// } + +// #[test(should_fail)] +// fn test_fail_8() { +// let input: [u8; 7] = "12-yy_z".as_bytes(); +// regex::regex_match(input); +// } + +// #[test(should_fail)] +// fn test_fail_9() { +// let input: [u8; 9] = "x12-y_zzz".as_bytes(); +// regex::regex_match(input); +// } + +// #[test(should_fail)] +// fn test_fail_10() { +// let input: [u8; 9] = "x12--yy_z".as_bytes(); +// regex::regex_match(input); +// } diff --git a/x/simple/src/regex.nr b/x/simple/src/regex.nr new file mode 100644 index 00000000..33d09b0f --- /dev/null +++ b/x/simple/src/regex.nr @@ -0,0 +1,994 @@ + +use crate::regex_common::Sequence; + + +global table: [Field; 11008] = comptime { make_lookup_table() }; + +comptime fn make_lookup_table() -> [Field; 11008] { + let mut table = [0; 11008]; + table[41 * 256 + 0] = 42; + table[42 * 256 + 0] = 42; + table[41 * 256 + 1] = 42; + table[42 * 256 + 1] = 42; + table[41 * 256 + 2] = 42; + table[42 * 256 + 2] = 42; + table[41 * 256 + 3] = 42; + table[42 * 256 + 3] = 42; + table[41 * 256 + 4] = 42; + table[42 * 256 + 4] = 42; + table[41 * 256 + 5] = 42; + table[42 * 256 + 5] = 42; + table[41 * 256 + 6] = 42; + table[42 * 256 + 6] = 42; + table[41 * 256 + 7] = 42; + table[42 * 256 + 7] = 42; + table[41 * 256 + 8] = 42; + table[42 * 256 + 8] = 42; + table[41 * 256 + 9] = 42; + table[42 * 256 + 9] = 42; + table[41 * 256 + 10] = 42; + table[42 * 256 + 10] = 42; + table[41 * 256 + 11] = 42; + table[42 * 256 + 11] = 42; + table[41 * 256 + 12] = 42; + table[42 * 256 + 12] = 42; + table[41 * 256 + 13] = 42; + table[42 * 256 + 13] = 42; + table[41 * 256 + 14] = 42; + table[42 * 256 + 14] = 42; + table[41 * 256 + 15] = 42; + table[42 * 256 + 15] = 42; + table[41 * 256 + 16] = 42; + table[42 * 256 + 16] = 42; + table[41 * 256 + 17] = 42; + table[42 * 256 + 17] = 42; + table[41 * 256 + 18] = 42; + table[42 * 256 + 18] = 42; + table[41 * 256 + 19] = 42; + table[42 * 256 + 19] = 42; + table[41 * 256 + 20] = 42; + table[42 * 256 + 20] = 42; + table[41 * 256 + 21] = 42; + table[42 * 256 + 21] = 42; + table[41 * 256 + 22] = 42; + table[42 * 256 + 22] = 42; + table[41 * 256 + 23] = 42; + table[42 * 256 + 23] = 42; + table[41 * 256 + 24] = 42; + table[42 * 256 + 24] = 42; + table[41 * 256 + 25] = 42; + table[42 * 256 + 25] = 42; + table[41 * 256 + 26] = 42; + table[42 * 256 + 26] = 42; + table[41 * 256 + 27] = 42; + table[42 * 256 + 27] = 42; + table[41 * 256 + 28] = 42; + table[42 * 256 + 28] = 42; + table[41 * 256 + 29] = 42; + table[42 * 256 + 29] = 42; + table[41 * 256 + 30] = 42; + table[42 * 256 + 30] = 42; + table[41 * 256 + 31] = 42; + table[42 * 256 + 31] = 42; + table[41 * 256 + 32] = 42; + table[42 * 256 + 32] = 42; + table[41 * 256 + 33] = 42; + table[42 * 256 + 33] = 42; + table[41 * 256 + 34] = 42; + table[42 * 256 + 34] = 42; + table[41 * 256 + 35] = 42; + table[42 * 256 + 35] = 42; + table[41 * 256 + 36] = 42; + table[42 * 256 + 36] = 42; + table[41 * 256 + 37] = 42; + table[42 * 256 + 37] = 42; + table[41 * 256 + 38] = 42; + table[42 * 256 + 38] = 42; + table[41 * 256 + 39] = 42; + table[42 * 256 + 39] = 42; + table[41 * 256 + 40] = 42; + table[42 * 256 + 40] = 42; + table[41 * 256 + 41] = 42; + table[42 * 256 + 41] = 42; + table[41 * 256 + 42] = 42; + table[42 * 256 + 42] = 42; + table[41 * 256 + 43] = 42; + table[42 * 256 + 43] = 42; + table[41 * 256 + 44] = 42; + table[42 * 256 + 44] = 42; + table[41 * 256 + 45] = 42; + table[42 * 256 + 45] = 42; + table[41 * 256 + 46] = 42; + table[42 * 256 + 46] = 42; + table[41 * 256 + 47] = 42; + table[42 * 256 + 47] = 42; + table[41 * 256 + 48] = 42; + table[42 * 256 + 48] = 42; + table[41 * 256 + 49] = 42; + table[42 * 256 + 49] = 42; + table[41 * 256 + 50] = 42; + table[42 * 256 + 50] = 42; + table[41 * 256 + 51] = 42; + table[42 * 256 + 51] = 42; + table[41 * 256 + 52] = 42; + table[42 * 256 + 52] = 42; + table[41 * 256 + 53] = 42; + table[42 * 256 + 53] = 42; + table[41 * 256 + 54] = 42; + table[42 * 256 + 54] = 42; + table[41 * 256 + 55] = 42; + table[42 * 256 + 55] = 42; + table[41 * 256 + 56] = 42; + table[42 * 256 + 56] = 42; + table[41 * 256 + 57] = 42; + table[42 * 256 + 57] = 42; + table[41 * 256 + 58] = 42; + table[42 * 256 + 58] = 42; + table[41 * 256 + 59] = 42; + table[42 * 256 + 59] = 42; + table[41 * 256 + 60] = 42; + table[42 * 256 + 60] = 42; + table[41 * 256 + 61] = 42; + table[42 * 256 + 61] = 42; + table[41 * 256 + 62] = 42; + table[42 * 256 + 62] = 42; + table[41 * 256 + 63] = 42; + table[42 * 256 + 63] = 42; + table[41 * 256 + 64] = 42; + table[42 * 256 + 64] = 42; + table[41 * 256 + 65] = 42; + table[42 * 256 + 65] = 42; + table[41 * 256 + 66] = 42; + table[42 * 256 + 66] = 42; + table[41 * 256 + 67] = 42; + table[42 * 256 + 67] = 42; + table[41 * 256 + 68] = 42; + table[42 * 256 + 68] = 42; + table[41 * 256 + 69] = 42; + table[42 * 256 + 69] = 42; + table[41 * 256 + 70] = 42; + table[42 * 256 + 70] = 42; + table[41 * 256 + 71] = 42; + table[42 * 256 + 71] = 42; + table[41 * 256 + 72] = 42; + table[42 * 256 + 72] = 42; + table[41 * 256 + 73] = 42; + table[42 * 256 + 73] = 42; + table[41 * 256 + 74] = 42; + table[42 * 256 + 74] = 42; + table[41 * 256 + 75] = 42; + table[42 * 256 + 75] = 42; + table[41 * 256 + 76] = 42; + table[42 * 256 + 76] = 42; + table[41 * 256 + 77] = 42; + table[42 * 256 + 77] = 42; + table[41 * 256 + 78] = 42; + table[42 * 256 + 78] = 42; + table[41 * 256 + 79] = 42; + table[42 * 256 + 79] = 42; + table[41 * 256 + 80] = 42; + table[42 * 256 + 80] = 42; + table[41 * 256 + 81] = 42; + table[42 * 256 + 81] = 42; + table[41 * 256 + 82] = 42; + table[42 * 256 + 82] = 42; + table[41 * 256 + 83] = 42; + table[42 * 256 + 83] = 42; + table[41 * 256 + 84] = 42; + table[42 * 256 + 84] = 42; + table[41 * 256 + 85] = 42; + table[42 * 256 + 85] = 42; + table[41 * 256 + 86] = 42; + table[42 * 256 + 86] = 42; + table[41 * 256 + 87] = 42; + table[42 * 256 + 87] = 42; + table[41 * 256 + 88] = 42; + table[42 * 256 + 88] = 42; + table[41 * 256 + 89] = 42; + table[42 * 256 + 89] = 42; + table[41 * 256 + 90] = 42; + table[42 * 256 + 90] = 42; + table[41 * 256 + 91] = 42; + table[42 * 256 + 91] = 42; + table[41 * 256 + 92] = 42; + table[42 * 256 + 92] = 42; + table[41 * 256 + 93] = 42; + table[42 * 256 + 93] = 42; + table[41 * 256 + 94] = 42; + table[42 * 256 + 94] = 42; + table[41 * 256 + 95] = 42; + table[42 * 256 + 95] = 42; + table[41 * 256 + 96] = 42; + table[42 * 256 + 96] = 42; + table[41 * 256 + 97] = 42; + table[42 * 256 + 97] = 42; + table[41 * 256 + 98] = 42; + table[42 * 256 + 98] = 42; + table[41 * 256 + 99] = 42; + table[42 * 256 + 99] = 42; + table[41 * 256 + 100] = 42; + table[42 * 256 + 100] = 42; + table[41 * 256 + 101] = 42; + table[42 * 256 + 101] = 42; + table[41 * 256 + 102] = 42; + table[42 * 256 + 102] = 42; + table[41 * 256 + 103] = 42; + table[42 * 256 + 103] = 42; + table[41 * 256 + 104] = 42; + table[42 * 256 + 104] = 42; + table[41 * 256 + 105] = 42; + table[42 * 256 + 105] = 42; + table[41 * 256 + 106] = 42; + table[42 * 256 + 106] = 42; + table[41 * 256 + 107] = 42; + table[42 * 256 + 107] = 42; + table[41 * 256 + 108] = 42; + table[42 * 256 + 108] = 42; + table[41 * 256 + 109] = 42; + table[42 * 256 + 109] = 42; + table[41 * 256 + 110] = 42; + table[42 * 256 + 110] = 42; + table[41 * 256 + 111] = 42; + table[42 * 256 + 111] = 42; + table[41 * 256 + 112] = 42; + table[42 * 256 + 112] = 42; + table[41 * 256 + 113] = 42; + table[42 * 256 + 113] = 42; + table[41 * 256 + 114] = 42; + table[42 * 256 + 114] = 42; + table[41 * 256 + 115] = 42; + table[42 * 256 + 115] = 42; + table[41 * 256 + 116] = 42; + table[42 * 256 + 116] = 42; + table[41 * 256 + 117] = 42; + table[42 * 256 + 117] = 42; + table[41 * 256 + 118] = 42; + table[42 * 256 + 118] = 42; + table[41 * 256 + 119] = 42; + table[42 * 256 + 119] = 42; + table[41 * 256 + 120] = 42; + table[42 * 256 + 120] = 42; + table[41 * 256 + 121] = 42; + table[42 * 256 + 121] = 42; + table[41 * 256 + 122] = 42; + table[42 * 256 + 122] = 42; + table[41 * 256 + 123] = 42; + table[42 * 256 + 123] = 42; + table[41 * 256 + 124] = 42; + table[42 * 256 + 124] = 42; + table[41 * 256 + 125] = 42; + table[42 * 256 + 125] = 42; + table[41 * 256 + 126] = 42; + table[42 * 256 + 126] = 42; + table[41 * 256 + 127] = 42; + table[42 * 256 + 127] = 42; + table[41 * 256 + 128] = 42; + table[42 * 256 + 128] = 42; + table[41 * 256 + 129] = 42; + table[42 * 256 + 129] = 42; + table[41 * 256 + 130] = 42; + table[42 * 256 + 130] = 42; + table[41 * 256 + 131] = 42; + table[42 * 256 + 131] = 42; + table[41 * 256 + 132] = 42; + table[42 * 256 + 132] = 42; + table[41 * 256 + 133] = 42; + table[42 * 256 + 133] = 42; + table[41 * 256 + 134] = 42; + table[42 * 256 + 134] = 42; + table[41 * 256 + 135] = 42; + table[42 * 256 + 135] = 42; + table[41 * 256 + 136] = 42; + table[42 * 256 + 136] = 42; + table[41 * 256 + 137] = 42; + table[42 * 256 + 137] = 42; + table[41 * 256 + 138] = 42; + table[42 * 256 + 138] = 42; + table[41 * 256 + 139] = 42; + table[42 * 256 + 139] = 42; + table[41 * 256 + 140] = 42; + table[42 * 256 + 140] = 42; + table[41 * 256 + 141] = 42; + table[42 * 256 + 141] = 42; + table[41 * 256 + 142] = 42; + table[42 * 256 + 142] = 42; + table[41 * 256 + 143] = 42; + table[42 * 256 + 143] = 42; + table[41 * 256 + 144] = 42; + table[42 * 256 + 144] = 42; + table[41 * 256 + 145] = 42; + table[42 * 256 + 145] = 42; + table[41 * 256 + 146] = 42; + table[42 * 256 + 146] = 42; + table[41 * 256 + 147] = 42; + table[42 * 256 + 147] = 42; + table[41 * 256 + 148] = 42; + table[42 * 256 + 148] = 42; + table[41 * 256 + 149] = 42; + table[42 * 256 + 149] = 42; + table[41 * 256 + 150] = 42; + table[42 * 256 + 150] = 42; + table[41 * 256 + 151] = 42; + table[42 * 256 + 151] = 42; + table[41 * 256 + 152] = 42; + table[42 * 256 + 152] = 42; + table[41 * 256 + 153] = 42; + table[42 * 256 + 153] = 42; + table[41 * 256 + 154] = 42; + table[42 * 256 + 154] = 42; + table[41 * 256 + 155] = 42; + table[42 * 256 + 155] = 42; + table[41 * 256 + 156] = 42; + table[42 * 256 + 156] = 42; + table[41 * 256 + 157] = 42; + table[42 * 256 + 157] = 42; + table[41 * 256 + 158] = 42; + table[42 * 256 + 158] = 42; + table[41 * 256 + 159] = 42; + table[42 * 256 + 159] = 42; + table[41 * 256 + 160] = 42; + table[42 * 256 + 160] = 42; + table[41 * 256 + 161] = 42; + table[42 * 256 + 161] = 42; + table[41 * 256 + 162] = 42; + table[42 * 256 + 162] = 42; + table[41 * 256 + 163] = 42; + table[42 * 256 + 163] = 42; + table[41 * 256 + 164] = 42; + table[42 * 256 + 164] = 42; + table[41 * 256 + 165] = 42; + table[42 * 256 + 165] = 42; + table[41 * 256 + 166] = 42; + table[42 * 256 + 166] = 42; + table[41 * 256 + 167] = 42; + table[42 * 256 + 167] = 42; + table[41 * 256 + 168] = 42; + table[42 * 256 + 168] = 42; + table[41 * 256 + 169] = 42; + table[42 * 256 + 169] = 42; + table[41 * 256 + 170] = 42; + table[42 * 256 + 170] = 42; + table[41 * 256 + 171] = 42; + table[42 * 256 + 171] = 42; + table[41 * 256 + 172] = 42; + table[42 * 256 + 172] = 42; + table[41 * 256 + 173] = 42; + table[42 * 256 + 173] = 42; + table[41 * 256 + 174] = 42; + table[42 * 256 + 174] = 42; + table[41 * 256 + 175] = 42; + table[42 * 256 + 175] = 42; + table[41 * 256 + 176] = 42; + table[42 * 256 + 176] = 42; + table[41 * 256 + 177] = 42; + table[42 * 256 + 177] = 42; + table[41 * 256 + 178] = 42; + table[42 * 256 + 178] = 42; + table[41 * 256 + 179] = 42; + table[42 * 256 + 179] = 42; + table[41 * 256 + 180] = 42; + table[42 * 256 + 180] = 42; + table[41 * 256 + 181] = 42; + table[42 * 256 + 181] = 42; + table[41 * 256 + 182] = 42; + table[42 * 256 + 182] = 42; + table[41 * 256 + 183] = 42; + table[42 * 256 + 183] = 42; + table[41 * 256 + 184] = 42; + table[42 * 256 + 184] = 42; + table[41 * 256 + 185] = 42; + table[42 * 256 + 185] = 42; + table[41 * 256 + 186] = 42; + table[42 * 256 + 186] = 42; + table[41 * 256 + 187] = 42; + table[42 * 256 + 187] = 42; + table[41 * 256 + 188] = 42; + table[42 * 256 + 188] = 42; + table[41 * 256 + 189] = 42; + table[42 * 256 + 189] = 42; + table[41 * 256 + 190] = 42; + table[42 * 256 + 190] = 42; + table[41 * 256 + 191] = 42; + table[42 * 256 + 191] = 42; + table[41 * 256 + 192] = 42; + table[42 * 256 + 192] = 42; + table[41 * 256 + 193] = 42; + table[42 * 256 + 193] = 42; + table[41 * 256 + 194] = 42; + table[42 * 256 + 194] = 42; + table[41 * 256 + 195] = 42; + table[42 * 256 + 195] = 42; + table[41 * 256 + 196] = 42; + table[42 * 256 + 196] = 42; + table[41 * 256 + 197] = 42; + table[42 * 256 + 197] = 42; + table[41 * 256 + 198] = 42; + table[42 * 256 + 198] = 42; + table[41 * 256 + 199] = 42; + table[42 * 256 + 199] = 42; + table[41 * 256 + 200] = 42; + table[42 * 256 + 200] = 42; + table[41 * 256 + 201] = 42; + table[42 * 256 + 201] = 42; + table[41 * 256 + 202] = 42; + table[42 * 256 + 202] = 42; + table[41 * 256 + 203] = 42; + table[42 * 256 + 203] = 42; + table[41 * 256 + 204] = 42; + table[42 * 256 + 204] = 42; + table[41 * 256 + 205] = 42; + table[42 * 256 + 205] = 42; + table[41 * 256 + 206] = 42; + table[42 * 256 + 206] = 42; + table[41 * 256 + 207] = 42; + table[42 * 256 + 207] = 42; + table[41 * 256 + 208] = 42; + table[42 * 256 + 208] = 42; + table[41 * 256 + 209] = 42; + table[42 * 256 + 209] = 42; + table[41 * 256 + 210] = 42; + table[42 * 256 + 210] = 42; + table[41 * 256 + 211] = 42; + table[42 * 256 + 211] = 42; + table[41 * 256 + 212] = 42; + table[42 * 256 + 212] = 42; + table[41 * 256 + 213] = 42; + table[42 * 256 + 213] = 42; + table[41 * 256 + 214] = 42; + table[42 * 256 + 214] = 42; + table[41 * 256 + 215] = 42; + table[42 * 256 + 215] = 42; + table[41 * 256 + 216] = 42; + table[42 * 256 + 216] = 42; + table[41 * 256 + 217] = 42; + table[42 * 256 + 217] = 42; + table[41 * 256 + 218] = 42; + table[42 * 256 + 218] = 42; + table[41 * 256 + 219] = 42; + table[42 * 256 + 219] = 42; + table[41 * 256 + 220] = 42; + table[42 * 256 + 220] = 42; + table[41 * 256 + 221] = 42; + table[42 * 256 + 221] = 42; + table[41 * 256 + 222] = 42; + table[42 * 256 + 222] = 42; + table[41 * 256 + 223] = 42; + table[42 * 256 + 223] = 42; + table[41 * 256 + 224] = 42; + table[42 * 256 + 224] = 42; + table[41 * 256 + 225] = 42; + table[42 * 256 + 225] = 42; + table[41 * 256 + 226] = 42; + table[42 * 256 + 226] = 42; + table[41 * 256 + 227] = 42; + table[42 * 256 + 227] = 42; + table[41 * 256 + 228] = 42; + table[42 * 256 + 228] = 42; + table[41 * 256 + 229] = 42; + table[42 * 256 + 229] = 42; + table[41 * 256 + 230] = 42; + table[42 * 256 + 230] = 42; + table[41 * 256 + 231] = 42; + table[42 * 256 + 231] = 42; + table[41 * 256 + 232] = 42; + table[42 * 256 + 232] = 42; + table[41 * 256 + 233] = 42; + table[42 * 256 + 233] = 42; + table[41 * 256 + 234] = 42; + table[42 * 256 + 234] = 42; + table[41 * 256 + 235] = 42; + table[42 * 256 + 235] = 42; + table[41 * 256 + 236] = 42; + table[42 * 256 + 236] = 42; + table[41 * 256 + 237] = 42; + table[42 * 256 + 237] = 42; + table[41 * 256 + 238] = 42; + table[42 * 256 + 238] = 42; + table[41 * 256 + 239] = 42; + table[42 * 256 + 239] = 42; + table[41 * 256 + 240] = 42; + table[42 * 256 + 240] = 42; + table[41 * 256 + 241] = 42; + table[42 * 256 + 241] = 42; + table[41 * 256 + 242] = 42; + table[42 * 256 + 242] = 42; + table[41 * 256 + 243] = 42; + table[42 * 256 + 243] = 42; + table[41 * 256 + 244] = 42; + table[42 * 256 + 244] = 42; + table[41 * 256 + 245] = 42; + table[42 * 256 + 245] = 42; + table[41 * 256 + 246] = 42; + table[42 * 256 + 246] = 42; + table[41 * 256 + 247] = 42; + table[42 * 256 + 247] = 42; + table[41 * 256 + 248] = 42; + table[42 * 256 + 248] = 42; + table[41 * 256 + 249] = 42; + table[42 * 256 + 249] = 42; + table[41 * 256 + 250] = 42; + table[42 * 256 + 250] = 42; + table[41 * 256 + 251] = 42; + table[42 * 256 + 251] = 42; + table[41 * 256 + 252] = 42; + table[42 * 256 + 252] = 42; + table[41 * 256 + 253] = 42; + table[42 * 256 + 253] = 42; + table[41 * 256 + 254] = 42; + table[42 * 256 + 254] = 42; + table[0 * 256 + 76] = 1; + table[1 * 256 + 97] = 2; + table[2 * 256 + 116] = 3; + table[3 * 256 + 105] = 4; + table[4 * 256 + 110] = 5; + table[5 * 256 + 45] = 6; + table[6 * 256 + 69] = 7; + table[7 * 256 + 120] = 8; + table[8 * 256 + 116] = 9; + table[9 * 256 + 101] = 10; + table[10 * 256 + 110] = 11; + table[11 * 256 + 115] = 12; + table[12 * 256 + 105] = 13; + table[13 * 256 + 111] = 14; + table[14 * 256 + 110] = 15; + table[15 * 256 + 61] = 16; + table[16 * 256 + 194] = 17; + table[16 * 256 + 195] = 18; + table[16 * 256 + 196] = 18; + table[16 * 256 + 197] = 18; + table[16 * 256 + 198] = 18; + table[17 * 256 + 161] = 19; + table[17 * 256 + 162] = 19; + table[17 * 256 + 163] = 19; + table[17 * 256 + 164] = 19; + table[17 * 256 + 165] = 19; + table[17 * 256 + 166] = 19; + table[17 * 256 + 167] = 19; + table[17 * 256 + 168] = 19; + table[17 * 256 + 169] = 19; + table[17 * 256 + 170] = 19; + table[17 * 256 + 171] = 19; + table[17 * 256 + 172] = 19; + table[17 * 256 + 173] = 19; + table[17 * 256 + 174] = 19; + table[17 * 256 + 175] = 19; + table[17 * 256 + 176] = 19; + table[17 * 256 + 177] = 19; + table[17 * 256 + 178] = 19; + table[17 * 256 + 179] = 19; + table[17 * 256 + 180] = 19; + table[17 * 256 + 181] = 19; + table[17 * 256 + 182] = 19; + table[17 * 256 + 183] = 19; + table[17 * 256 + 184] = 19; + table[17 * 256 + 185] = 19; + table[17 * 256 + 186] = 19; + table[17 * 256 + 187] = 19; + table[17 * 256 + 188] = 19; + table[17 * 256 + 189] = 19; + table[17 * 256 + 190] = 19; + table[17 * 256 + 191] = 19; + table[18 * 256 + 128] = 19; + table[18 * 256 + 129] = 19; + table[18 * 256 + 130] = 19; + table[18 * 256 + 131] = 19; + table[18 * 256 + 132] = 19; + table[18 * 256 + 133] = 19; + table[18 * 256 + 134] = 19; + table[18 * 256 + 135] = 19; + table[18 * 256 + 136] = 19; + table[18 * 256 + 137] = 19; + table[18 * 256 + 138] = 19; + table[18 * 256 + 139] = 19; + table[18 * 256 + 140] = 19; + table[18 * 256 + 141] = 19; + table[18 * 256 + 142] = 19; + table[18 * 256 + 143] = 19; + table[18 * 256 + 144] = 19; + table[18 * 256 + 145] = 19; + table[18 * 256 + 146] = 19; + table[18 * 256 + 147] = 19; + table[18 * 256 + 148] = 19; + table[18 * 256 + 149] = 19; + table[18 * 256 + 150] = 19; + table[18 * 256 + 151] = 19; + table[18 * 256 + 152] = 19; + table[18 * 256 + 153] = 19; + table[18 * 256 + 154] = 19; + table[18 * 256 + 155] = 19; + table[18 * 256 + 156] = 19; + table[18 * 256 + 157] = 19; + table[18 * 256 + 158] = 19; + table[18 * 256 + 159] = 19; + table[18 * 256 + 160] = 19; + table[18 * 256 + 161] = 19; + table[18 * 256 + 162] = 19; + table[18 * 256 + 163] = 19; + table[18 * 256 + 164] = 19; + table[18 * 256 + 165] = 19; + table[18 * 256 + 166] = 19; + table[18 * 256 + 167] = 19; + table[18 * 256 + 168] = 19; + table[18 * 256 + 169] = 19; + table[18 * 256 + 170] = 19; + table[18 * 256 + 171] = 19; + table[18 * 256 + 172] = 19; + table[18 * 256 + 173] = 19; + table[18 * 256 + 174] = 19; + table[18 * 256 + 175] = 19; + table[18 * 256 + 176] = 19; + table[18 * 256 + 177] = 19; + table[18 * 256 + 178] = 19; + table[18 * 256 + 179] = 19; + table[18 * 256 + 180] = 19; + table[18 * 256 + 181] = 19; + table[18 * 256 + 182] = 19; + table[18 * 256 + 183] = 19; + table[18 * 256 + 184] = 19; + table[18 * 256 + 185] = 19; + table[18 * 256 + 186] = 19; + table[18 * 256 + 187] = 19; + table[18 * 256 + 188] = 19; + table[18 * 256 + 189] = 19; + table[18 * 256 + 190] = 19; + table[18 * 256 + 191] = 19; + table[19 * 256 + 194] = 17; + table[19 * 256 + 195] = 18; + table[19 * 256 + 196] = 18; + table[19 * 256 + 197] = 18; + table[19 * 256 + 198] = 18; + table[19 * 256 + 32] = 20; + table[20 * 256 + 71] = 21; + table[21 * 256 + 114] = 22; + table[22 * 256 + 101] = 23; + table[23 * 256 + 101] = 24; + table[24 * 256 + 107] = 25; + table[25 * 256 + 61] = 26; + table[26 * 256 + 205] = 27; + table[26 * 256 + 206] = 28; + table[26 * 256 + 207] = 28; + table[27 * 256 + 176] = 29; + table[27 * 256 + 177] = 29; + table[27 * 256 + 178] = 29; + table[27 * 256 + 179] = 29; + table[27 * 256 + 180] = 29; + table[27 * 256 + 181] = 29; + table[27 * 256 + 182] = 29; + table[27 * 256 + 183] = 29; + table[27 * 256 + 184] = 29; + table[27 * 256 + 185] = 29; + table[27 * 256 + 186] = 29; + table[27 * 256 + 187] = 29; + table[27 * 256 + 188] = 29; + table[27 * 256 + 189] = 29; + table[27 * 256 + 190] = 29; + table[27 * 256 + 191] = 29; + table[28 * 256 + 128] = 29; + table[28 * 256 + 129] = 29; + table[28 * 256 + 130] = 29; + table[28 * 256 + 131] = 29; + table[28 * 256 + 132] = 29; + table[28 * 256 + 133] = 29; + table[28 * 256 + 134] = 29; + table[28 * 256 + 135] = 29; + table[28 * 256 + 136] = 29; + table[28 * 256 + 137] = 29; + table[28 * 256 + 138] = 29; + table[28 * 256 + 139] = 29; + table[28 * 256 + 140] = 29; + table[28 * 256 + 141] = 29; + table[28 * 256 + 142] = 29; + table[28 * 256 + 143] = 29; + table[28 * 256 + 144] = 29; + table[28 * 256 + 145] = 29; + table[28 * 256 + 146] = 29; + table[28 * 256 + 147] = 29; + table[28 * 256 + 148] = 29; + table[28 * 256 + 149] = 29; + table[28 * 256 + 150] = 29; + table[28 * 256 + 151] = 29; + table[28 * 256 + 152] = 29; + table[28 * 256 + 153] = 29; + table[28 * 256 + 154] = 29; + table[28 * 256 + 155] = 29; + table[28 * 256 + 156] = 29; + table[28 * 256 + 157] = 29; + table[28 * 256 + 158] = 29; + table[28 * 256 + 159] = 29; + table[28 * 256 + 160] = 29; + table[28 * 256 + 161] = 29; + table[28 * 256 + 162] = 29; + table[28 * 256 + 163] = 29; + table[28 * 256 + 164] = 29; + table[28 * 256 + 165] = 29; + table[28 * 256 + 166] = 29; + table[28 * 256 + 167] = 29; + table[28 * 256 + 168] = 29; + table[28 * 256 + 169] = 29; + table[28 * 256 + 170] = 29; + table[28 * 256 + 171] = 29; + table[28 * 256 + 172] = 29; + table[28 * 256 + 173] = 29; + table[28 * 256 + 174] = 29; + table[28 * 256 + 175] = 29; + table[28 * 256 + 176] = 29; + table[28 * 256 + 177] = 29; + table[28 * 256 + 178] = 29; + table[28 * 256 + 179] = 29; + table[28 * 256 + 180] = 29; + table[28 * 256 + 181] = 29; + table[28 * 256 + 182] = 29; + table[28 * 256 + 183] = 29; + table[28 * 256 + 184] = 29; + table[28 * 256 + 185] = 29; + table[28 * 256 + 186] = 29; + table[28 * 256 + 187] = 29; + table[28 * 256 + 188] = 29; + table[28 * 256 + 189] = 29; + table[28 * 256 + 190] = 29; + table[28 * 256 + 191] = 29; + table[29 * 256 + 205] = 27; + table[29 * 256 + 206] = 28; + table[29 * 256 + 207] = 28; + table[29 * 256 + 32] = 30; + table[30 * 256 + 67] = 31; + table[31 * 256 + 121] = 32; + table[32 * 256 + 114] = 33; + table[33 * 256 + 105] = 34; + table[34 * 256 + 108] = 35; + table[35 * 256 + 108] = 36; + table[36 * 256 + 105] = 37; + table[37 * 256 + 99] = 38; + table[38 * 256 + 61] = 39; + table[39 * 256 + 208] = 40; + table[39 * 256 + 209] = 40; + table[39 * 256 + 210] = 40; + table[39 * 256 + 211] = 40; + table[40 * 256 + 128] = 41; + table[40 * 256 + 129] = 41; + table[40 * 256 + 130] = 41; + table[40 * 256 + 131] = 41; + table[40 * 256 + 132] = 41; + table[40 * 256 + 133] = 41; + table[40 * 256 + 134] = 41; + table[40 * 256 + 135] = 41; + table[40 * 256 + 136] = 41; + table[40 * 256 + 137] = 41; + table[40 * 256 + 138] = 41; + table[40 * 256 + 139] = 41; + table[40 * 256 + 140] = 41; + table[40 * 256 + 141] = 41; + table[40 * 256 + 142] = 41; + table[40 * 256 + 143] = 41; + table[40 * 256 + 144] = 41; + table[40 * 256 + 145] = 41; + table[40 * 256 + 146] = 41; + table[40 * 256 + 147] = 41; + table[40 * 256 + 148] = 41; + table[40 * 256 + 149] = 41; + table[40 * 256 + 150] = 41; + table[40 * 256 + 151] = 41; + table[40 * 256 + 152] = 41; + table[40 * 256 + 153] = 41; + table[40 * 256 + 154] = 41; + table[40 * 256 + 155] = 41; + table[40 * 256 + 156] = 41; + table[40 * 256 + 157] = 41; + table[40 * 256 + 158] = 41; + table[40 * 256 + 159] = 41; + table[40 * 256 + 160] = 41; + table[40 * 256 + 161] = 41; + table[40 * 256 + 162] = 41; + table[40 * 256 + 163] = 41; + table[40 * 256 + 164] = 41; + table[40 * 256 + 165] = 41; + table[40 * 256 + 166] = 41; + table[40 * 256 + 167] = 41; + table[40 * 256 + 168] = 41; + table[40 * 256 + 169] = 41; + table[40 * 256 + 170] = 41; + table[40 * 256 + 171] = 41; + table[40 * 256 + 172] = 41; + table[40 * 256 + 173] = 41; + table[40 * 256 + 174] = 41; + table[40 * 256 + 175] = 41; + table[40 * 256 + 176] = 41; + table[40 * 256 + 177] = 41; + table[40 * 256 + 178] = 41; + table[40 * 256 + 179] = 41; + table[40 * 256 + 180] = 41; + table[40 * 256 + 181] = 41; + table[40 * 256 + 182] = 41; + table[40 * 256 + 183] = 41; + table[40 * 256 + 184] = 41; + table[40 * 256 + 185] = 41; + table[40 * 256 + 186] = 41; + table[40 * 256 + 187] = 41; + table[40 * 256 + 188] = 41; + table[40 * 256 + 189] = 41; + table[40 * 256 + 190] = 41; + table[40 * 256 + 191] = 41; + table[41 * 256 + 208] = 40; + table[41 * 256 + 209] = 40; + table[41 * 256 + 210] = 40; + table[41 * 256 + 211] = 40; + + table +} + + +pub fn regex_match(input: [u8; N]) -> BoundedVec { + let substrings = unsafe { __regex_match(input) }; + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + let mut start_range = 0; + let mut end_range = 0; + + // check the match + for i in 0..N { + // state transition + let temp = input[i] as Field; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + s = 0; + s_next = potential_s_next; + } + std::as_witness(s_next); + + // range conditions for substring matches + if ((start_range == 0) & (end_range == 0)) { + start_range = i as Field; + } + if (((s == 41) & (s_next == 42)) & (end_range == 0)) { + end_range = i as Field + 1; + } + + + let range_0 = substrings.get_unchecked(0).in_range(i); + let case_0 = [ + (s == 16) & ((s_next == 17) | (s_next == 18)), + (s == 19) & ((s_next == 17) | (s_next == 18)), + (s_next == 19) & ((s == 17) | (s == 18)) + ].any(|case| case == true) | !range_0; + + let range_1 = substrings.get_unchecked(1).in_range(i); + let case_1 = [ + (s == 26) & ((s_next == 27) | (s_next == 28)), + (s == 29) & ((s_next == 27) | (s_next == 28)), + (s_next == 29) & ((s == 27) | (s == 28)) + ].any(|case| case == true) | !range_1; + + let range_2 = substrings.get_unchecked(2).in_range(i); + let case_2 = [ + (s_next == 40) & ((s == 39) | (s == 41)), + (s_next == 41) & ((s == 40)) + ].any(|case| case == true) | !range_2; + + + + let substring_range_check = [case_0, case_1, case_2] + .all(|case| case == true); + + assert(substring_range_check, "substr array ranges wrong"); + + + s = s_next; + } + // check final state + + assert((s == 41) | (s == 42), "Match not found"); + + // constrain extracted substrings to be in match range + //let full_match = Sequence::new(start_range as u32, end_range as u32 - start_range as u32); + //let full_match_end = full_match.end(); + // for i in 0..3 { + // let substring = substrings.get_unchecked(i); + // let is_not_valid = i >= substrings.len(); + // let index_check = substring.index >= full_match.index; + // let length_check = substring.end() <= full_match_end; + // let check = (index_check) | is_not_valid; + // assert(check, f"Substring {i} range is out of bounds of the full match found"); + // } + substrings +} + + +pub unconstrained fn __regex_match(input: [u8; N]) -> BoundedVec { + // regex: Latin-Extension=[\u{00a1}-\u{01bf}]+ Greek=[\u{0370}-\u{03ff}]+ Cyrillic=[\u{0400}-\u{04ff}]+ + let mut substrings: BoundedVec = BoundedVec::new(); + let mut current_substring = Sequence::default(); + let mut full_match = Sequence::default(); + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + + let mut consecutive_substr = 0; + let mut complete = false; + + for i in 0..input.len() { + let temp = input[i] as Field; + let mut reset = false; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + reset = true; + s = 0; + s_next = potential_s_next; + } + // If a substring was in the making, but the state was reset + // we disregard previous progress because apparently it is invalid + if (reset & (consecutive_substr == 1)) { + current_substring = Sequence::default(); + consecutive_substr = 0; + } + // Fill up substrings + + + if ((s == 16) & (s_next == 17) | (s == 16) & (s_next == 18) | (s == 17) & (s_next == 19) | (s == 18) & (s_next == 19) | (s == 19) & (s_next == 17) | (s == 19) & (s_next == 18)) { + + if (consecutive_substr == 0) { + current_substring.index = i; + }; + current_substring.length += 1; + consecutive_substr = 1; + } + + else if ((s == 26) & (s_next == 27) | (s == 26) & (s_next == 28) | (s == 27) & (s_next == 29) | (s == 28) & (s_next == 29) | (s == 29) & (s_next == 27) | (s == 29) & (s_next == 28)) { + + if (consecutive_substr == 0) { + current_substring.index = i; + }; + current_substring.length += 1; + consecutive_substr = 1; + } + + else if ((s == 39) & (s_next == 40) | (s == 40) & (s_next == 41) | (s == 41) & (s_next == 40)) { + + if (consecutive_substr == 0) { + current_substring.index = i; + }; + current_substring.length += 1; + consecutive_substr = 1; + } else if ((consecutive_substr == 1) & (s_next == 0)) { + current_substring = Sequence::default(); + full_match = Sequence::default(); + substrings = BoundedVec::new(); + consecutive_substr = 0; + } else if (s == 41) & (s_next == 42) { + full_match.length = i - full_match.index + 1; + complete = true; + } else if (consecutive_substr == 1) { + // The substring is done so "save" it + substrings.push(current_substring); + // reset the substring holder for next use + current_substring = Sequence::default(); + consecutive_substr = 0; + } + s = s_next; + if complete == true { + break; + } + } + assert((s == 41) | (s == 42), f"no match: {s}"); + // Add pending substring that hasn't been added + if consecutive_substr == 1 { + substrings.push(current_substring); + full_match.length = input.len() - full_match.index; + } + + + + substrings +} + + + + \ No newline at end of file diff --git a/x/simple/src/regex_bak.nr b/x/simple/src/regex_bak.nr new file mode 100644 index 00000000..5033380f --- /dev/null +++ b/x/simple/src/regex_bak.nr @@ -0,0 +1,692 @@ +global table: [Field; 1024] = comptime { make_lookup_table() }; + +comptime fn make_lookup_table() -> [Field; 1024] { + let mut table = [0; 1024]; + table[2 * 256 + 0] = 3; + table[3 * 256 + 0] = 3; + table[2 * 256 + 1] = 3; + table[3 * 256 + 1] = 3; + table[2 * 256 + 2] = 3; + table[3 * 256 + 2] = 3; + table[2 * 256 + 3] = 3; + table[3 * 256 + 3] = 3; + table[2 * 256 + 4] = 3; + table[3 * 256 + 4] = 3; + table[2 * 256 + 5] = 3; + table[3 * 256 + 5] = 3; + table[2 * 256 + 6] = 3; + table[3 * 256 + 6] = 3; + table[2 * 256 + 7] = 3; + table[3 * 256 + 7] = 3; + table[2 * 256 + 8] = 3; + table[3 * 256 + 8] = 3; + table[2 * 256 + 9] = 3; + table[3 * 256 + 9] = 3; + table[2 * 256 + 10] = 3; + table[3 * 256 + 10] = 3; + table[2 * 256 + 11] = 3; + table[3 * 256 + 11] = 3; + table[2 * 256 + 12] = 3; + table[3 * 256 + 12] = 3; + table[2 * 256 + 13] = 3; + table[3 * 256 + 13] = 3; + table[2 * 256 + 14] = 3; + table[3 * 256 + 14] = 3; + table[2 * 256 + 15] = 3; + table[3 * 256 + 15] = 3; + table[2 * 256 + 16] = 3; + table[3 * 256 + 16] = 3; + table[2 * 256 + 17] = 3; + table[3 * 256 + 17] = 3; + table[2 * 256 + 18] = 3; + table[3 * 256 + 18] = 3; + table[2 * 256 + 19] = 3; + table[3 * 256 + 19] = 3; + table[2 * 256 + 20] = 3; + table[3 * 256 + 20] = 3; + table[2 * 256 + 21] = 3; + table[3 * 256 + 21] = 3; + table[2 * 256 + 22] = 3; + table[3 * 256 + 22] = 3; + table[2 * 256 + 23] = 3; + table[3 * 256 + 23] = 3; + table[2 * 256 + 24] = 3; + table[3 * 256 + 24] = 3; + table[2 * 256 + 25] = 3; + table[3 * 256 + 25] = 3; + table[2 * 256 + 26] = 3; + table[3 * 256 + 26] = 3; + table[2 * 256 + 27] = 3; + table[3 * 256 + 27] = 3; + table[2 * 256 + 28] = 3; + table[3 * 256 + 28] = 3; + table[2 * 256 + 29] = 3; + table[3 * 256 + 29] = 3; + table[2 * 256 + 30] = 3; + table[3 * 256 + 30] = 3; + table[2 * 256 + 31] = 3; + table[3 * 256 + 31] = 3; + table[2 * 256 + 32] = 3; + table[3 * 256 + 32] = 3; + table[2 * 256 + 33] = 3; + table[3 * 256 + 33] = 3; + table[2 * 256 + 34] = 3; + table[3 * 256 + 34] = 3; + table[2 * 256 + 35] = 3; + table[3 * 256 + 35] = 3; + table[2 * 256 + 36] = 3; + table[3 * 256 + 36] = 3; + table[2 * 256 + 37] = 3; + table[3 * 256 + 37] = 3; + table[2 * 256 + 38] = 3; + table[3 * 256 + 38] = 3; + table[2 * 256 + 39] = 3; + table[3 * 256 + 39] = 3; + table[2 * 256 + 40] = 3; + table[3 * 256 + 40] = 3; + table[2 * 256 + 41] = 3; + table[3 * 256 + 41] = 3; + table[2 * 256 + 42] = 3; + table[3 * 256 + 42] = 3; + table[2 * 256 + 43] = 3; + table[3 * 256 + 43] = 3; + table[2 * 256 + 44] = 3; + table[3 * 256 + 44] = 3; + table[2 * 256 + 45] = 3; + table[3 * 256 + 45] = 3; + table[2 * 256 + 46] = 3; + table[3 * 256 + 46] = 3; + table[2 * 256 + 47] = 3; + table[3 * 256 + 47] = 3; + table[2 * 256 + 48] = 3; + table[3 * 256 + 48] = 3; + table[2 * 256 + 49] = 3; + table[3 * 256 + 49] = 3; + table[2 * 256 + 50] = 3; + table[3 * 256 + 50] = 3; + table[2 * 256 + 51] = 3; + table[3 * 256 + 51] = 3; + table[2 * 256 + 52] = 3; + table[3 * 256 + 52] = 3; + table[2 * 256 + 53] = 3; + table[3 * 256 + 53] = 3; + table[2 * 256 + 54] = 3; + table[3 * 256 + 54] = 3; + table[2 * 256 + 55] = 3; + table[3 * 256 + 55] = 3; + table[2 * 256 + 56] = 3; + table[3 * 256 + 56] = 3; + table[2 * 256 + 57] = 3; + table[3 * 256 + 57] = 3; + table[2 * 256 + 58] = 3; + table[3 * 256 + 58] = 3; + table[2 * 256 + 59] = 3; + table[3 * 256 + 59] = 3; + table[2 * 256 + 60] = 3; + table[3 * 256 + 60] = 3; + table[2 * 256 + 61] = 3; + table[3 * 256 + 61] = 3; + table[2 * 256 + 62] = 3; + table[3 * 256 + 62] = 3; + table[2 * 256 + 63] = 3; + table[3 * 256 + 63] = 3; + table[2 * 256 + 64] = 3; + table[3 * 256 + 64] = 3; + table[2 * 256 + 65] = 3; + table[3 * 256 + 65] = 3; + table[2 * 256 + 66] = 3; + table[3 * 256 + 66] = 3; + table[2 * 256 + 67] = 3; + table[3 * 256 + 67] = 3; + table[2 * 256 + 68] = 3; + table[3 * 256 + 68] = 3; + table[2 * 256 + 69] = 3; + table[3 * 256 + 69] = 3; + table[2 * 256 + 70] = 3; + table[3 * 256 + 70] = 3; + table[2 * 256 + 71] = 3; + table[3 * 256 + 71] = 3; + table[2 * 256 + 72] = 3; + table[3 * 256 + 72] = 3; + table[2 * 256 + 73] = 3; + table[3 * 256 + 73] = 3; + table[2 * 256 + 74] = 3; + table[3 * 256 + 74] = 3; + table[2 * 256 + 75] = 3; + table[3 * 256 + 75] = 3; + table[2 * 256 + 76] = 3; + table[3 * 256 + 76] = 3; + table[2 * 256 + 77] = 3; + table[3 * 256 + 77] = 3; + table[2 * 256 + 78] = 3; + table[3 * 256 + 78] = 3; + table[2 * 256 + 79] = 3; + table[3 * 256 + 79] = 3; + table[2 * 256 + 80] = 3; + table[3 * 256 + 80] = 3; + table[2 * 256 + 81] = 3; + table[3 * 256 + 81] = 3; + table[2 * 256 + 82] = 3; + table[3 * 256 + 82] = 3; + table[2 * 256 + 83] = 3; + table[3 * 256 + 83] = 3; + table[2 * 256 + 84] = 3; + table[3 * 256 + 84] = 3; + table[2 * 256 + 85] = 3; + table[3 * 256 + 85] = 3; + table[2 * 256 + 86] = 3; + table[3 * 256 + 86] = 3; + table[2 * 256 + 87] = 3; + table[3 * 256 + 87] = 3; + table[2 * 256 + 88] = 3; + table[3 * 256 + 88] = 3; + table[2 * 256 + 89] = 3; + table[3 * 256 + 89] = 3; + table[2 * 256 + 90] = 3; + table[3 * 256 + 90] = 3; + table[2 * 256 + 91] = 3; + table[3 * 256 + 91] = 3; + table[2 * 256 + 92] = 3; + table[3 * 256 + 92] = 3; + table[2 * 256 + 93] = 3; + table[3 * 256 + 93] = 3; + table[2 * 256 + 94] = 3; + table[3 * 256 + 94] = 3; + table[2 * 256 + 95] = 3; + table[3 * 256 + 95] = 3; + table[2 * 256 + 96] = 3; + table[3 * 256 + 96] = 3; + table[2 * 256 + 97] = 3; + table[3 * 256 + 97] = 3; + table[2 * 256 + 98] = 3; + table[3 * 256 + 98] = 3; + table[2 * 256 + 99] = 3; + table[3 * 256 + 99] = 3; + table[2 * 256 + 100] = 3; + table[3 * 256 + 100] = 3; + table[2 * 256 + 101] = 3; + table[3 * 256 + 101] = 3; + table[2 * 256 + 102] = 3; + table[3 * 256 + 102] = 3; + table[2 * 256 + 103] = 3; + table[3 * 256 + 103] = 3; + table[2 * 256 + 104] = 3; + table[3 * 256 + 104] = 3; + table[2 * 256 + 105] = 3; + table[3 * 256 + 105] = 3; + table[2 * 256 + 106] = 3; + table[3 * 256 + 106] = 3; + table[2 * 256 + 107] = 3; + table[3 * 256 + 107] = 3; + table[2 * 256 + 108] = 3; + table[3 * 256 + 108] = 3; + table[2 * 256 + 109] = 3; + table[3 * 256 + 109] = 3; + table[2 * 256 + 110] = 3; + table[3 * 256 + 110] = 3; + table[2 * 256 + 111] = 3; + table[3 * 256 + 111] = 3; + table[2 * 256 + 112] = 3; + table[3 * 256 + 112] = 3; + table[2 * 256 + 113] = 3; + table[3 * 256 + 113] = 3; + table[2 * 256 + 114] = 3; + table[3 * 256 + 114] = 3; + table[2 * 256 + 115] = 3; + table[3 * 256 + 115] = 3; + table[2 * 256 + 116] = 3; + table[3 * 256 + 116] = 3; + table[2 * 256 + 117] = 3; + table[3 * 256 + 117] = 3; + table[2 * 256 + 118] = 3; + table[3 * 256 + 118] = 3; + table[2 * 256 + 119] = 3; + table[3 * 256 + 119] = 3; + table[2 * 256 + 120] = 3; + table[3 * 256 + 120] = 3; + table[2 * 256 + 121] = 3; + table[3 * 256 + 121] = 3; + table[2 * 256 + 122] = 3; + table[3 * 256 + 122] = 3; + table[2 * 256 + 123] = 3; + table[3 * 256 + 123] = 3; + table[2 * 256 + 124] = 3; + table[3 * 256 + 124] = 3; + table[2 * 256 + 125] = 3; + table[3 * 256 + 125] = 3; + table[2 * 256 + 126] = 3; + table[3 * 256 + 126] = 3; + table[2 * 256 + 127] = 3; + table[3 * 256 + 127] = 3; + table[2 * 256 + 128] = 3; + table[3 * 256 + 128] = 3; + table[2 * 256 + 129] = 3; + table[3 * 256 + 129] = 3; + table[2 * 256 + 130] = 3; + table[3 * 256 + 130] = 3; + table[2 * 256 + 131] = 3; + table[3 * 256 + 131] = 3; + table[2 * 256 + 132] = 3; + table[3 * 256 + 132] = 3; + table[2 * 256 + 133] = 3; + table[3 * 256 + 133] = 3; + table[2 * 256 + 134] = 3; + table[3 * 256 + 134] = 3; + table[2 * 256 + 135] = 3; + table[3 * 256 + 135] = 3; + table[2 * 256 + 136] = 3; + table[3 * 256 + 136] = 3; + table[2 * 256 + 137] = 3; + table[3 * 256 + 137] = 3; + table[2 * 256 + 138] = 3; + table[3 * 256 + 138] = 3; + table[2 * 256 + 139] = 3; + table[3 * 256 + 139] = 3; + table[2 * 256 + 140] = 3; + table[3 * 256 + 140] = 3; + table[2 * 256 + 141] = 3; + table[3 * 256 + 141] = 3; + table[2 * 256 + 142] = 3; + table[3 * 256 + 142] = 3; + table[2 * 256 + 143] = 3; + table[3 * 256 + 143] = 3; + table[2 * 256 + 144] = 3; + table[3 * 256 + 144] = 3; + table[2 * 256 + 145] = 3; + table[3 * 256 + 145] = 3; + table[2 * 256 + 146] = 3; + table[3 * 256 + 146] = 3; + table[2 * 256 + 147] = 3; + table[3 * 256 + 147] = 3; + table[2 * 256 + 148] = 3; + table[3 * 256 + 148] = 3; + table[2 * 256 + 149] = 3; + table[3 * 256 + 149] = 3; + table[2 * 256 + 150] = 3; + table[3 * 256 + 150] = 3; + table[2 * 256 + 151] = 3; + table[3 * 256 + 151] = 3; + table[2 * 256 + 152] = 3; + table[3 * 256 + 152] = 3; + table[2 * 256 + 153] = 3; + table[3 * 256 + 153] = 3; + table[2 * 256 + 154] = 3; + table[3 * 256 + 154] = 3; + table[2 * 256 + 155] = 3; + table[3 * 256 + 155] = 3; + table[2 * 256 + 156] = 3; + table[3 * 256 + 156] = 3; + table[2 * 256 + 157] = 3; + table[3 * 256 + 157] = 3; + table[2 * 256 + 158] = 3; + table[3 * 256 + 158] = 3; + table[2 * 256 + 159] = 3; + table[3 * 256 + 159] = 3; + table[2 * 256 + 160] = 3; + table[3 * 256 + 160] = 3; + table[2 * 256 + 161] = 3; + table[3 * 256 + 161] = 3; + table[2 * 256 + 162] = 3; + table[3 * 256 + 162] = 3; + table[2 * 256 + 163] = 3; + table[3 * 256 + 163] = 3; + table[2 * 256 + 164] = 3; + table[3 * 256 + 164] = 3; + table[2 * 256 + 165] = 3; + table[3 * 256 + 165] = 3; + table[2 * 256 + 166] = 3; + table[3 * 256 + 166] = 3; + table[2 * 256 + 167] = 3; + table[3 * 256 + 167] = 3; + table[2 * 256 + 168] = 3; + table[3 * 256 + 168] = 3; + table[2 * 256 + 169] = 3; + table[3 * 256 + 169] = 3; + table[2 * 256 + 170] = 3; + table[3 * 256 + 170] = 3; + table[2 * 256 + 171] = 3; + table[3 * 256 + 171] = 3; + table[2 * 256 + 172] = 3; + table[3 * 256 + 172] = 3; + table[2 * 256 + 173] = 3; + table[3 * 256 + 173] = 3; + table[2 * 256 + 174] = 3; + table[3 * 256 + 174] = 3; + table[2 * 256 + 175] = 3; + table[3 * 256 + 175] = 3; + table[2 * 256 + 176] = 3; + table[3 * 256 + 176] = 3; + table[2 * 256 + 177] = 3; + table[3 * 256 + 177] = 3; + table[2 * 256 + 178] = 3; + table[3 * 256 + 178] = 3; + table[2 * 256 + 179] = 3; + table[3 * 256 + 179] = 3; + table[2 * 256 + 180] = 3; + table[3 * 256 + 180] = 3; + table[2 * 256 + 181] = 3; + table[3 * 256 + 181] = 3; + table[2 * 256 + 182] = 3; + table[3 * 256 + 182] = 3; + table[2 * 256 + 183] = 3; + table[3 * 256 + 183] = 3; + table[2 * 256 + 184] = 3; + table[3 * 256 + 184] = 3; + table[2 * 256 + 185] = 3; + table[3 * 256 + 185] = 3; + table[2 * 256 + 186] = 3; + table[3 * 256 + 186] = 3; + table[2 * 256 + 187] = 3; + table[3 * 256 + 187] = 3; + table[2 * 256 + 188] = 3; + table[3 * 256 + 188] = 3; + table[2 * 256 + 189] = 3; + table[3 * 256 + 189] = 3; + table[2 * 256 + 190] = 3; + table[3 * 256 + 190] = 3; + table[2 * 256 + 191] = 3; + table[3 * 256 + 191] = 3; + table[2 * 256 + 192] = 3; + table[3 * 256 + 192] = 3; + table[2 * 256 + 193] = 3; + table[3 * 256 + 193] = 3; + table[2 * 256 + 194] = 3; + table[3 * 256 + 194] = 3; + table[2 * 256 + 195] = 3; + table[3 * 256 + 195] = 3; + table[2 * 256 + 196] = 3; + table[3 * 256 + 196] = 3; + table[2 * 256 + 197] = 3; + table[3 * 256 + 197] = 3; + table[2 * 256 + 198] = 3; + table[3 * 256 + 198] = 3; + table[2 * 256 + 199] = 3; + table[3 * 256 + 199] = 3; + table[2 * 256 + 200] = 3; + table[3 * 256 + 200] = 3; + table[2 * 256 + 201] = 3; + table[3 * 256 + 201] = 3; + table[2 * 256 + 202] = 3; + table[3 * 256 + 202] = 3; + table[2 * 256 + 203] = 3; + table[3 * 256 + 203] = 3; + table[2 * 256 + 204] = 3; + table[3 * 256 + 204] = 3; + table[2 * 256 + 205] = 3; + table[3 * 256 + 205] = 3; + table[2 * 256 + 206] = 3; + table[3 * 256 + 206] = 3; + table[2 * 256 + 207] = 3; + table[3 * 256 + 207] = 3; + table[2 * 256 + 208] = 3; + table[3 * 256 + 208] = 3; + table[2 * 256 + 209] = 3; + table[3 * 256 + 209] = 3; + table[2 * 256 + 210] = 3; + table[3 * 256 + 210] = 3; + table[2 * 256 + 211] = 3; + table[3 * 256 + 211] = 3; + table[2 * 256 + 212] = 3; + table[3 * 256 + 212] = 3; + table[2 * 256 + 213] = 3; + table[3 * 256 + 213] = 3; + table[2 * 256 + 214] = 3; + table[3 * 256 + 214] = 3; + table[2 * 256 + 215] = 3; + table[3 * 256 + 215] = 3; + table[2 * 256 + 216] = 3; + table[3 * 256 + 216] = 3; + table[2 * 256 + 217] = 3; + table[3 * 256 + 217] = 3; + table[2 * 256 + 218] = 3; + table[3 * 256 + 218] = 3; + table[2 * 256 + 219] = 3; + table[3 * 256 + 219] = 3; + table[2 * 256 + 220] = 3; + table[3 * 256 + 220] = 3; + table[2 * 256 + 221] = 3; + table[3 * 256 + 221] = 3; + table[2 * 256 + 222] = 3; + table[3 * 256 + 222] = 3; + table[2 * 256 + 223] = 3; + table[3 * 256 + 223] = 3; + table[2 * 256 + 224] = 3; + table[3 * 256 + 224] = 3; + table[2 * 256 + 225] = 3; + table[3 * 256 + 225] = 3; + table[2 * 256 + 226] = 3; + table[3 * 256 + 226] = 3; + table[2 * 256 + 227] = 3; + table[3 * 256 + 227] = 3; + table[2 * 256 + 228] = 3; + table[3 * 256 + 228] = 3; + table[2 * 256 + 229] = 3; + table[3 * 256 + 229] = 3; + table[2 * 256 + 230] = 3; + table[3 * 256 + 230] = 3; + table[2 * 256 + 231] = 3; + table[3 * 256 + 231] = 3; + table[2 * 256 + 232] = 3; + table[3 * 256 + 232] = 3; + table[2 * 256 + 233] = 3; + table[3 * 256 + 233] = 3; + table[2 * 256 + 234] = 3; + table[3 * 256 + 234] = 3; + table[2 * 256 + 235] = 3; + table[3 * 256 + 235] = 3; + table[2 * 256 + 236] = 3; + table[3 * 256 + 236] = 3; + table[2 * 256 + 237] = 3; + table[3 * 256 + 237] = 3; + table[2 * 256 + 238] = 3; + table[3 * 256 + 238] = 3; + table[2 * 256 + 239] = 3; + table[3 * 256 + 239] = 3; + table[2 * 256 + 240] = 3; + table[3 * 256 + 240] = 3; + table[2 * 256 + 241] = 3; + table[3 * 256 + 241] = 3; + table[2 * 256 + 242] = 3; + table[3 * 256 + 242] = 3; + table[2 * 256 + 243] = 3; + table[3 * 256 + 243] = 3; + table[2 * 256 + 244] = 3; + table[3 * 256 + 244] = 3; + table[2 * 256 + 245] = 3; + table[3 * 256 + 245] = 3; + table[2 * 256 + 246] = 3; + table[3 * 256 + 246] = 3; + table[2 * 256 + 247] = 3; + table[3 * 256 + 247] = 3; + table[2 * 256 + 248] = 3; + table[3 * 256 + 248] = 3; + table[2 * 256 + 249] = 3; + table[3 * 256 + 249] = 3; + table[2 * 256 + 250] = 3; + table[3 * 256 + 250] = 3; + table[2 * 256 + 251] = 3; + table[3 * 256 + 251] = 3; + table[2 * 256 + 252] = 3; + table[3 * 256 + 252] = 3; + table[2 * 256 + 253] = 3; + table[3 * 256 + 253] = 3; + table[2 * 256 + 254] = 3; + table[3 * 256 + 254] = 3; + table[0 * 256 + 255] = 1; + table[1 * 256 + 97] = 2; + + table +} + +pub struct Sequence { + index: u32, + length: u32, +} + +impl Sequence { + pub fn new(index: u32, length: u32) -> Self { + Self { index, length } + } + + pub fn default() -> Self { + Self { index: 0, length: 0 } + } +} + +pub struct RegexMatch { + masked: [u8; INPUT_LENGTH], + full_match: Sequence, + substrings: [Sequence; NUM_SUBSTRINGS], +} + +pub fn regex_match(input: [u8; N]) -> BoundedVec, 1> { + let pattern_match = unsafe { __regex_match(input) }; + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + + // check the match + for i in 0..N { + let temp = input[i] as Field; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + s = 0; + s_next = potential_s_next; + } + std::as_witness(s_next); + + // let range = i >= start & i <= end; + // let cases = [(s == 1) & (s_next == 2), (s == 2) & (s_next == 3), (s == 3) & (s_next == 3)]; + // // idk why have to say == true + // let found = cases.any(|case| case == true | range == false); + s = s_next; + // assert(found, "no match"); + } + // check final state + assert((s == 2) | (s == 3), f"no match: {s}"); + + // extract substrings + let mut substrings: BoundedVec, 1> = BoundedVec::new(); + for i in 0..1 { + let substring = pattern_match.substrings[i]; + let extracted_substring = extract_substring(substring, input); + substrings.push(extracted_substring); + } + + substrings +} + +pub unconstrained fn __regex_match(input: [u8; N]) -> RegexMatch { + // regex: ^a + // let mut substrings: BoundedVec, 1> = BoundedVec::new(); + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + + let mut consecutive_substr = 0; + let mut current_substring = Sequence::default(); + let mut full_match = Sequence::default(); + let mut substrings: BoundedVec = BoundedVec::new(); + let mut complete = false; + + for i in 0..input.len() { + let temp = input[i] as Field; + let mut reset = false; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + reset = true; + s = 0; + s_next = potential_s_next; + } + // If a substring was in the making, but the state was reset + // we disregard previous progress because apparently it is invalid + if (reset & (consecutive_substr == 1)) { + current_substring = Sequence::default(); + consecutive_substr = 0; + } + // Fill up substrings + if ((s == 1) & (s_next == 2)) { + if (consecutive_substr == 0) { + full_match.index = i; + current_substring.index = i; + }; + + current_substring.length += 1; + consecutive_substr = 1; + } else if ((consecutive_substr == 1) & (s_next == 0)) { + current_substring = Sequence::default(); + full_match = Sequence::default(); + substrings = BoundedVec::new(); + consecutive_substr = 0; + } else if (s == 2) & (s_next == 3) { + full_match.length = i - full_match.index + 1; + complete = true; + } else if (consecutive_substr == 1) { + // The substring is done so "save" it + substrings.push(current_substring); + // reset the substring holder for next use + current_substring = Sequence::default(); + consecutive_substr = 0; + } + s = s_next; + if complete == true { + break; + } + } + assert((s == 2) | (s == 3), f"no match: {s}"); + // Add pending substring that hasn't been added + if consecutive_substr == 1 { + substrings.push(current_substring); + full_match.length = input.len() - full_match.index; + } + + // make masked array + let mut masked = [0; N]; + for i in 0..substrings.len() { + let substring = substrings.get(i); + let start_index = substring.index; + let end_index = start_index + substring.length; + for j in start_index..end_index { + masked[j] = input[j]; + } + } + + // return match + RegexMatch { masked, full_match, substrings: substrings.storage() } +} + +pub fn extract_substring( + substring_sequence: Sequence, + input: [u8; INPUT_LENGTH], +) -> BoundedVec { + let mut substring: BoundedVec = unsafe { __extract_substring(substring_sequence, input) }; + assert(substring_sequence.length == substring.len(), "length mismatch"); + for i in 0..MAX_SUBSTRING_LENGTH { + let index = substring_sequence.index + i; + let range_check = i >= substring_sequence.length; + let expected_byte = input[index]; + let byte = substring.get_unchecked(index); + let matched = expected_byte == byte; + assert(range_check | matched, "incorrect substring construction"); + } + substring +} + +unconstrained fn __extract_substring( + substring_sequence: Sequence, + input: [u8; INPUT_LENGTH], +) -> BoundedVec { + let mut substring: BoundedVec = BoundedVec::new(); + for i in 0..substring_sequence.length { + let byte = input[substring_sequence.index + i]; + substring.push(byte); + } + substring +} diff --git a/x/simple/src/regex_common.nr b/x/simple/src/regex_common.nr new file mode 100644 index 00000000..9fd637ac --- /dev/null +++ b/x/simple/src/regex_common.nr @@ -0,0 +1,161 @@ + + + + + +// points to a seque +pub struct Sequence { + index: u32, + length: u32, + end: u32 +} + +impl Sequence { + pub fn new(index: u32, length: u32) -> Self { + Self { index, length, end: index + length } + } + + pub fn default() -> Self { + Self { index: 0, length: 0, end: 0 } + } + + pub fn initialized(self) -> bool { + self.length > 0 + } + + pub fn index(self) -> u32 { + self.index + } + + pub fn length(self) -> u32 { + self.length + } + + pub fn end(self) -> u32 { + self.end + } + + pub fn in_range(self, index: u32) -> bool { + // if index + length == 0, index < self.end implicitly returns false if uninitialized + index >= self.index & index < self.end + } +} + + +/** + * Extracts all substrings from a pattern match + * @dev not super optimal - all substrings will be assumed to be of the length of longest substring. + * often this will be the size of the input. Use at discretion. + * + * @param input - the input array to extract from + * @param sequences - the sequences to extract from the input + * @returns the extracted substrings + */ +pub fn extract_all_substrings< + let INPUT_LENGTH: u32, + let NUM_SUBSTRINGS: u32, + let MAX_SUBSTRING_LENGTH: u32 +>( + input: [u8; INPUT_LENGTH], + sequences: BoundedVec, +) -> BoundedVec, NUM_SUBSTRINGS> {{ + let mut substrings: BoundedVec, NUM_SUBSTRINGS> = BoundedVec::new(); + for i in 0..NUM_SUBSTRINGS {{ + let substring = sequences.get_unchecked(i); + let mut extracted_substring = extract_substring(substring, input); + let mut len = substrings.len() + 1; + if i >= sequences.len() {{ + extracted_substring = BoundedVec::new(); + len = substrings.len(); + }} + substrings.len = len; + substrings.storage[i] = extracted_substring; + }} + substrings +}} + +/** + * Optimized algorithm for extracting a subsequence from an input array + * + * @param substring_sequence - the sequence to extract from the input + * @param input - the input array to extract from + * @returns the extracted subsequence + */ +pub fn extract_substring( + substring_sequence: Sequence, + input: [u8; INPUT_LENGTH], +) -> BoundedVec { + let mut substring: BoundedVec = unsafe { __extract_substring(substring_sequence, input) }; + assert(substring_sequence.length == substring.len(), "length mismatch"); + for i in 0..MAX_SUBSTRING_LENGTH { + // hack for index to never exceed array bounds + // must be constrained to be true when matching is required to prevent 0's passing when shouldn't + // @dev while this adds constraints in worse case it can be more efficient if MAX_SUBSTRING_LENGTH < INPUT_LENGTH + let input_range_check = substring_sequence.index + i < INPUT_LENGTH; + let index = (substring_sequence.index + i) as Field * input_range_check as Field; + + // range where input should match substring + let sequence_range_check = i >= substring_sequence.length; + + // constrain array construction if in range + let expected_byte = input[index]; + let byte = substring.get_unchecked(i); + let matched = (expected_byte as Field == byte as Field); + assert(matched | sequence_range_check, "incorrect substring construction"); + } + substring +} + +/** + * Unconstrained helper to build the extracted substring + * @dev must be checked by extract_substring to constrain construction of substring + * + * @param substring_sequence - the sequence to extract from the input + * @param input - the input array to extract from + * @returns the extracted subsequence + */ +unconstrained fn __extract_substring( + substring_sequence: Sequence, + input: [u8; INPUT_LENGTH], +) -> BoundedVec { + let mut substring: BoundedVec = BoundedVec::new(); + for i in 0..substring_sequence.length { + let byte = input[substring_sequence.index + i]; + substring.push(byte); + } + substring +} + + + +// pub fn mask_input( +// substring_sequences: BoundedVec, +// input: [u8; INPUT_LENGTH], +// ) -> [u8; INPUT_LENGTH] { +// let masked: [u8; INPUT_LENGTH] = unsafe { __mask_input(substring_sequences, input) }; +// for i in 0..INPUT_LENGTH { +// let any_in_range = substring_sequences +// .storage() +// .any(|sequence| sequence.in_range(i)); +// let expected_byte = input[i] as Field * any_in_range as Field; +// assert(masked[i] as Field == expected_byte, "Incorrect masking"); +// } +// masked +// } + +unconstrained fn __mask_input( + substring_sequences: BoundedVec, + input: [u8; INPUT_LENGTH], +) -> [u8; INPUT_LENGTH] { + let mut masked_input: [u8; INPUT_LENGTH] = [0; INPUT_LENGTH]; + for i in 0..substring_sequences.len() { + let sequence = substring_sequences.get_unchecked(i); + for j in sequence.index..sequence.end() { + masked_input[j] = input[j]; + } + } + masked_input +} + + + \ No newline at end of file diff --git a/x/simple/src/working-2.nr b/x/simple/src/working-2.nr new file mode 100644 index 00000000..4979a393 --- /dev/null +++ b/x/simple/src/working-2.nr @@ -0,0 +1,1747 @@ +global table: [Field; 8960] = comptime { make_lookup_table() }; + +comptime fn make_lookup_table() -> [Field; 8960] { + let mut table = [0; 8960]; + table[33 * 256 + 0] = 34; + table[34 * 256 + 0] = 34; + table[33 * 256 + 1] = 34; + table[34 * 256 + 1] = 34; + table[33 * 256 + 2] = 34; + table[34 * 256 + 2] = 34; + table[33 * 256 + 3] = 34; + table[34 * 256 + 3] = 34; + table[33 * 256 + 4] = 34; + table[34 * 256 + 4] = 34; + table[33 * 256 + 5] = 34; + table[34 * 256 + 5] = 34; + table[33 * 256 + 6] = 34; + table[34 * 256 + 6] = 34; + table[33 * 256 + 7] = 34; + table[34 * 256 + 7] = 34; + table[33 * 256 + 8] = 34; + table[34 * 256 + 8] = 34; + table[33 * 256 + 9] = 34; + table[34 * 256 + 9] = 34; + table[33 * 256 + 10] = 34; + table[34 * 256 + 10] = 34; + table[33 * 256 + 11] = 34; + table[34 * 256 + 11] = 34; + table[33 * 256 + 12] = 34; + table[34 * 256 + 12] = 34; + table[33 * 256 + 13] = 34; + table[34 * 256 + 13] = 34; + table[33 * 256 + 14] = 34; + table[34 * 256 + 14] = 34; + table[33 * 256 + 15] = 34; + table[34 * 256 + 15] = 34; + table[33 * 256 + 16] = 34; + table[34 * 256 + 16] = 34; + table[33 * 256 + 17] = 34; + table[34 * 256 + 17] = 34; + table[33 * 256 + 18] = 34; + table[34 * 256 + 18] = 34; + table[33 * 256 + 19] = 34; + table[34 * 256 + 19] = 34; + table[33 * 256 + 20] = 34; + table[34 * 256 + 20] = 34; + table[33 * 256 + 21] = 34; + table[34 * 256 + 21] = 34; + table[33 * 256 + 22] = 34; + table[34 * 256 + 22] = 34; + table[33 * 256 + 23] = 34; + table[34 * 256 + 23] = 34; + table[33 * 256 + 24] = 34; + table[34 * 256 + 24] = 34; + table[33 * 256 + 25] = 34; + table[34 * 256 + 25] = 34; + table[33 * 256 + 26] = 34; + table[34 * 256 + 26] = 34; + table[33 * 256 + 27] = 34; + table[34 * 256 + 27] = 34; + table[33 * 256 + 28] = 34; + table[34 * 256 + 28] = 34; + table[33 * 256 + 29] = 34; + table[34 * 256 + 29] = 34; + table[33 * 256 + 30] = 34; + table[34 * 256 + 30] = 34; + table[33 * 256 + 31] = 34; + table[34 * 256 + 31] = 34; + table[33 * 256 + 32] = 34; + table[34 * 256 + 32] = 34; + table[33 * 256 + 33] = 34; + table[34 * 256 + 33] = 34; + table[33 * 256 + 34] = 34; + table[34 * 256 + 34] = 34; + table[33 * 256 + 35] = 34; + table[34 * 256 + 35] = 34; + table[33 * 256 + 36] = 34; + table[34 * 256 + 36] = 34; + table[33 * 256 + 37] = 34; + table[34 * 256 + 37] = 34; + table[33 * 256 + 38] = 34; + table[34 * 256 + 38] = 34; + table[33 * 256 + 39] = 34; + table[34 * 256 + 39] = 34; + table[33 * 256 + 40] = 34; + table[34 * 256 + 40] = 34; + table[33 * 256 + 41] = 34; + table[34 * 256 + 41] = 34; + table[33 * 256 + 42] = 34; + table[34 * 256 + 42] = 34; + table[33 * 256 + 43] = 34; + table[34 * 256 + 43] = 34; + table[33 * 256 + 44] = 34; + table[34 * 256 + 44] = 34; + table[33 * 256 + 45] = 34; + table[34 * 256 + 45] = 34; + table[33 * 256 + 46] = 34; + table[34 * 256 + 46] = 34; + table[33 * 256 + 47] = 34; + table[34 * 256 + 47] = 34; + table[33 * 256 + 48] = 34; + table[34 * 256 + 48] = 34; + table[33 * 256 + 49] = 34; + table[34 * 256 + 49] = 34; + table[33 * 256 + 50] = 34; + table[34 * 256 + 50] = 34; + table[33 * 256 + 51] = 34; + table[34 * 256 + 51] = 34; + table[33 * 256 + 52] = 34; + table[34 * 256 + 52] = 34; + table[33 * 256 + 53] = 34; + table[34 * 256 + 53] = 34; + table[33 * 256 + 54] = 34; + table[34 * 256 + 54] = 34; + table[33 * 256 + 55] = 34; + table[34 * 256 + 55] = 34; + table[33 * 256 + 56] = 34; + table[34 * 256 + 56] = 34; + table[33 * 256 + 57] = 34; + table[34 * 256 + 57] = 34; + table[33 * 256 + 58] = 34; + table[34 * 256 + 58] = 34; + table[33 * 256 + 59] = 34; + table[34 * 256 + 59] = 34; + table[33 * 256 + 60] = 34; + table[34 * 256 + 60] = 34; + table[33 * 256 + 61] = 34; + table[34 * 256 + 61] = 34; + table[33 * 256 + 62] = 34; + table[34 * 256 + 62] = 34; + table[33 * 256 + 63] = 34; + table[34 * 256 + 63] = 34; + table[33 * 256 + 64] = 34; + table[34 * 256 + 64] = 34; + table[33 * 256 + 65] = 34; + table[34 * 256 + 65] = 34; + table[33 * 256 + 66] = 34; + table[34 * 256 + 66] = 34; + table[33 * 256 + 67] = 34; + table[34 * 256 + 67] = 34; + table[33 * 256 + 68] = 34; + table[34 * 256 + 68] = 34; + table[33 * 256 + 69] = 34; + table[34 * 256 + 69] = 34; + table[33 * 256 + 70] = 34; + table[34 * 256 + 70] = 34; + table[33 * 256 + 71] = 34; + table[34 * 256 + 71] = 34; + table[33 * 256 + 72] = 34; + table[34 * 256 + 72] = 34; + table[33 * 256 + 73] = 34; + table[34 * 256 + 73] = 34; + table[33 * 256 + 74] = 34; + table[34 * 256 + 74] = 34; + table[33 * 256 + 75] = 34; + table[34 * 256 + 75] = 34; + table[33 * 256 + 76] = 34; + table[34 * 256 + 76] = 34; + table[33 * 256 + 77] = 34; + table[34 * 256 + 77] = 34; + table[33 * 256 + 78] = 34; + table[34 * 256 + 78] = 34; + table[33 * 256 + 79] = 34; + table[34 * 256 + 79] = 34; + table[33 * 256 + 80] = 34; + table[34 * 256 + 80] = 34; + table[33 * 256 + 81] = 34; + table[34 * 256 + 81] = 34; + table[33 * 256 + 82] = 34; + table[34 * 256 + 82] = 34; + table[33 * 256 + 83] = 34; + table[34 * 256 + 83] = 34; + table[33 * 256 + 84] = 34; + table[34 * 256 + 84] = 34; + table[33 * 256 + 85] = 34; + table[34 * 256 + 85] = 34; + table[33 * 256 + 86] = 34; + table[34 * 256 + 86] = 34; + table[33 * 256 + 87] = 34; + table[34 * 256 + 87] = 34; + table[33 * 256 + 88] = 34; + table[34 * 256 + 88] = 34; + table[33 * 256 + 89] = 34; + table[34 * 256 + 89] = 34; + table[33 * 256 + 90] = 34; + table[34 * 256 + 90] = 34; + table[33 * 256 + 91] = 34; + table[34 * 256 + 91] = 34; + table[33 * 256 + 92] = 34; + table[34 * 256 + 92] = 34; + table[33 * 256 + 93] = 34; + table[34 * 256 + 93] = 34; + table[33 * 256 + 94] = 34; + table[34 * 256 + 94] = 34; + table[33 * 256 + 95] = 34; + table[34 * 256 + 95] = 34; + table[33 * 256 + 96] = 34; + table[34 * 256 + 96] = 34; + table[33 * 256 + 97] = 34; + table[34 * 256 + 97] = 34; + table[33 * 256 + 98] = 34; + table[34 * 256 + 98] = 34; + table[33 * 256 + 99] = 34; + table[34 * 256 + 99] = 34; + table[33 * 256 + 100] = 34; + table[34 * 256 + 100] = 34; + table[33 * 256 + 101] = 34; + table[34 * 256 + 101] = 34; + table[33 * 256 + 102] = 34; + table[34 * 256 + 102] = 34; + table[33 * 256 + 103] = 34; + table[34 * 256 + 103] = 34; + table[33 * 256 + 104] = 34; + table[34 * 256 + 104] = 34; + table[33 * 256 + 105] = 34; + table[34 * 256 + 105] = 34; + table[33 * 256 + 106] = 34; + table[34 * 256 + 106] = 34; + table[33 * 256 + 107] = 34; + table[34 * 256 + 107] = 34; + table[33 * 256 + 108] = 34; + table[34 * 256 + 108] = 34; + table[33 * 256 + 109] = 34; + table[34 * 256 + 109] = 34; + table[33 * 256 + 110] = 34; + table[34 * 256 + 110] = 34; + table[33 * 256 + 111] = 34; + table[34 * 256 + 111] = 34; + table[33 * 256 + 112] = 34; + table[34 * 256 + 112] = 34; + table[33 * 256 + 113] = 34; + table[34 * 256 + 113] = 34; + table[33 * 256 + 114] = 34; + table[34 * 256 + 114] = 34; + table[33 * 256 + 115] = 34; + table[34 * 256 + 115] = 34; + table[33 * 256 + 116] = 34; + table[34 * 256 + 116] = 34; + table[33 * 256 + 117] = 34; + table[34 * 256 + 117] = 34; + table[33 * 256 + 118] = 34; + table[34 * 256 + 118] = 34; + table[33 * 256 + 119] = 34; + table[34 * 256 + 119] = 34; + table[33 * 256 + 120] = 34; + table[34 * 256 + 120] = 34; + table[33 * 256 + 121] = 34; + table[34 * 256 + 121] = 34; + table[33 * 256 + 122] = 34; + table[34 * 256 + 122] = 34; + table[33 * 256 + 123] = 34; + table[34 * 256 + 123] = 34; + table[33 * 256 + 124] = 34; + table[34 * 256 + 124] = 34; + table[33 * 256 + 125] = 34; + table[34 * 256 + 125] = 34; + table[33 * 256 + 126] = 34; + table[34 * 256 + 126] = 34; + table[33 * 256 + 127] = 34; + table[34 * 256 + 127] = 34; + table[33 * 256 + 128] = 34; + table[34 * 256 + 128] = 34; + table[33 * 256 + 129] = 34; + table[34 * 256 + 129] = 34; + table[33 * 256 + 130] = 34; + table[34 * 256 + 130] = 34; + table[33 * 256 + 131] = 34; + table[34 * 256 + 131] = 34; + table[33 * 256 + 132] = 34; + table[34 * 256 + 132] = 34; + table[33 * 256 + 133] = 34; + table[34 * 256 + 133] = 34; + table[33 * 256 + 134] = 34; + table[34 * 256 + 134] = 34; + table[33 * 256 + 135] = 34; + table[34 * 256 + 135] = 34; + table[33 * 256 + 136] = 34; + table[34 * 256 + 136] = 34; + table[33 * 256 + 137] = 34; + table[34 * 256 + 137] = 34; + table[33 * 256 + 138] = 34; + table[34 * 256 + 138] = 34; + table[33 * 256 + 139] = 34; + table[34 * 256 + 139] = 34; + table[33 * 256 + 140] = 34; + table[34 * 256 + 140] = 34; + table[33 * 256 + 141] = 34; + table[34 * 256 + 141] = 34; + table[33 * 256 + 142] = 34; + table[34 * 256 + 142] = 34; + table[33 * 256 + 143] = 34; + table[34 * 256 + 143] = 34; + table[33 * 256 + 144] = 34; + table[34 * 256 + 144] = 34; + table[33 * 256 + 145] = 34; + table[34 * 256 + 145] = 34; + table[33 * 256 + 146] = 34; + table[34 * 256 + 146] = 34; + table[33 * 256 + 147] = 34; + table[34 * 256 + 147] = 34; + table[33 * 256 + 148] = 34; + table[34 * 256 + 148] = 34; + table[33 * 256 + 149] = 34; + table[34 * 256 + 149] = 34; + table[33 * 256 + 150] = 34; + table[34 * 256 + 150] = 34; + table[33 * 256 + 151] = 34; + table[34 * 256 + 151] = 34; + table[33 * 256 + 152] = 34; + table[34 * 256 + 152] = 34; + table[33 * 256 + 153] = 34; + table[34 * 256 + 153] = 34; + table[33 * 256 + 154] = 34; + table[34 * 256 + 154] = 34; + table[33 * 256 + 155] = 34; + table[34 * 256 + 155] = 34; + table[33 * 256 + 156] = 34; + table[34 * 256 + 156] = 34; + table[33 * 256 + 157] = 34; + table[34 * 256 + 157] = 34; + table[33 * 256 + 158] = 34; + table[34 * 256 + 158] = 34; + table[33 * 256 + 159] = 34; + table[34 * 256 + 159] = 34; + table[33 * 256 + 160] = 34; + table[34 * 256 + 160] = 34; + table[33 * 256 + 161] = 34; + table[34 * 256 + 161] = 34; + table[33 * 256 + 162] = 34; + table[34 * 256 + 162] = 34; + table[33 * 256 + 163] = 34; + table[34 * 256 + 163] = 34; + table[33 * 256 + 164] = 34; + table[34 * 256 + 164] = 34; + table[33 * 256 + 165] = 34; + table[34 * 256 + 165] = 34; + table[33 * 256 + 166] = 34; + table[34 * 256 + 166] = 34; + table[33 * 256 + 167] = 34; + table[34 * 256 + 167] = 34; + table[33 * 256 + 168] = 34; + table[34 * 256 + 168] = 34; + table[33 * 256 + 169] = 34; + table[34 * 256 + 169] = 34; + table[33 * 256 + 170] = 34; + table[34 * 256 + 170] = 34; + table[33 * 256 + 171] = 34; + table[34 * 256 + 171] = 34; + table[33 * 256 + 172] = 34; + table[34 * 256 + 172] = 34; + table[33 * 256 + 173] = 34; + table[34 * 256 + 173] = 34; + table[33 * 256 + 174] = 34; + table[34 * 256 + 174] = 34; + table[33 * 256 + 175] = 34; + table[34 * 256 + 175] = 34; + table[33 * 256 + 176] = 34; + table[34 * 256 + 176] = 34; + table[33 * 256 + 177] = 34; + table[34 * 256 + 177] = 34; + table[33 * 256 + 178] = 34; + table[34 * 256 + 178] = 34; + table[33 * 256 + 179] = 34; + table[34 * 256 + 179] = 34; + table[33 * 256 + 180] = 34; + table[34 * 256 + 180] = 34; + table[33 * 256 + 181] = 34; + table[34 * 256 + 181] = 34; + table[33 * 256 + 182] = 34; + table[34 * 256 + 182] = 34; + table[33 * 256 + 183] = 34; + table[34 * 256 + 183] = 34; + table[33 * 256 + 184] = 34; + table[34 * 256 + 184] = 34; + table[33 * 256 + 185] = 34; + table[34 * 256 + 185] = 34; + table[33 * 256 + 186] = 34; + table[34 * 256 + 186] = 34; + table[33 * 256 + 187] = 34; + table[34 * 256 + 187] = 34; + table[33 * 256 + 188] = 34; + table[34 * 256 + 188] = 34; + table[33 * 256 + 189] = 34; + table[34 * 256 + 189] = 34; + table[33 * 256 + 190] = 34; + table[34 * 256 + 190] = 34; + table[33 * 256 + 191] = 34; + table[34 * 256 + 191] = 34; + table[33 * 256 + 192] = 34; + table[34 * 256 + 192] = 34; + table[33 * 256 + 193] = 34; + table[34 * 256 + 193] = 34; + table[33 * 256 + 194] = 34; + table[34 * 256 + 194] = 34; + table[33 * 256 + 195] = 34; + table[34 * 256 + 195] = 34; + table[33 * 256 + 196] = 34; + table[34 * 256 + 196] = 34; + table[33 * 256 + 197] = 34; + table[34 * 256 + 197] = 34; + table[33 * 256 + 198] = 34; + table[34 * 256 + 198] = 34; + table[33 * 256 + 199] = 34; + table[34 * 256 + 199] = 34; + table[33 * 256 + 200] = 34; + table[34 * 256 + 200] = 34; + table[33 * 256 + 201] = 34; + table[34 * 256 + 201] = 34; + table[33 * 256 + 202] = 34; + table[34 * 256 + 202] = 34; + table[33 * 256 + 203] = 34; + table[34 * 256 + 203] = 34; + table[33 * 256 + 204] = 34; + table[34 * 256 + 204] = 34; + table[33 * 256 + 205] = 34; + table[34 * 256 + 205] = 34; + table[33 * 256 + 206] = 34; + table[34 * 256 + 206] = 34; + table[33 * 256 + 207] = 34; + table[34 * 256 + 207] = 34; + table[33 * 256 + 208] = 34; + table[34 * 256 + 208] = 34; + table[33 * 256 + 209] = 34; + table[34 * 256 + 209] = 34; + table[33 * 256 + 210] = 34; + table[34 * 256 + 210] = 34; + table[33 * 256 + 211] = 34; + table[34 * 256 + 211] = 34; + table[33 * 256 + 212] = 34; + table[34 * 256 + 212] = 34; + table[33 * 256 + 213] = 34; + table[34 * 256 + 213] = 34; + table[33 * 256 + 214] = 34; + table[34 * 256 + 214] = 34; + table[33 * 256 + 215] = 34; + table[34 * 256 + 215] = 34; + table[33 * 256 + 216] = 34; + table[34 * 256 + 216] = 34; + table[33 * 256 + 217] = 34; + table[34 * 256 + 217] = 34; + table[33 * 256 + 218] = 34; + table[34 * 256 + 218] = 34; + table[33 * 256 + 219] = 34; + table[34 * 256 + 219] = 34; + table[33 * 256 + 220] = 34; + table[34 * 256 + 220] = 34; + table[33 * 256 + 221] = 34; + table[34 * 256 + 221] = 34; + table[33 * 256 + 222] = 34; + table[34 * 256 + 222] = 34; + table[33 * 256 + 223] = 34; + table[34 * 256 + 223] = 34; + table[33 * 256 + 224] = 34; + table[34 * 256 + 224] = 34; + table[33 * 256 + 225] = 34; + table[34 * 256 + 225] = 34; + table[33 * 256 + 226] = 34; + table[34 * 256 + 226] = 34; + table[33 * 256 + 227] = 34; + table[34 * 256 + 227] = 34; + table[33 * 256 + 228] = 34; + table[34 * 256 + 228] = 34; + table[33 * 256 + 229] = 34; + table[34 * 256 + 229] = 34; + table[33 * 256 + 230] = 34; + table[34 * 256 + 230] = 34; + table[33 * 256 + 231] = 34; + table[34 * 256 + 231] = 34; + table[33 * 256 + 232] = 34; + table[34 * 256 + 232] = 34; + table[33 * 256 + 233] = 34; + table[34 * 256 + 233] = 34; + table[33 * 256 + 234] = 34; + table[34 * 256 + 234] = 34; + table[33 * 256 + 235] = 34; + table[34 * 256 + 235] = 34; + table[33 * 256 + 236] = 34; + table[34 * 256 + 236] = 34; + table[33 * 256 + 237] = 34; + table[34 * 256 + 237] = 34; + table[33 * 256 + 238] = 34; + table[34 * 256 + 238] = 34; + table[33 * 256 + 239] = 34; + table[34 * 256 + 239] = 34; + table[33 * 256 + 240] = 34; + table[34 * 256 + 240] = 34; + table[33 * 256 + 241] = 34; + table[34 * 256 + 241] = 34; + table[33 * 256 + 242] = 34; + table[34 * 256 + 242] = 34; + table[33 * 256 + 243] = 34; + table[34 * 256 + 243] = 34; + table[33 * 256 + 244] = 34; + table[34 * 256 + 244] = 34; + table[33 * 256 + 245] = 34; + table[34 * 256 + 245] = 34; + table[33 * 256 + 246] = 34; + table[34 * 256 + 246] = 34; + table[33 * 256 + 247] = 34; + table[34 * 256 + 247] = 34; + table[33 * 256 + 248] = 34; + table[34 * 256 + 248] = 34; + table[33 * 256 + 249] = 34; + table[34 * 256 + 249] = 34; + table[33 * 256 + 250] = 34; + table[34 * 256 + 250] = 34; + table[33 * 256 + 251] = 34; + table[34 * 256 + 251] = 34; + table[33 * 256 + 252] = 34; + table[34 * 256 + 252] = 34; + table[33 * 256 + 253] = 34; + table[34 * 256 + 253] = 34; + table[33 * 256 + 254] = 34; + table[34 * 256 + 254] = 34; + table[0 * 256 + 13] = 1; + table[0 * 256 + 255] = 2; + table[1 * 256 + 10] = 2; + table[2 * 256 + 100] = 3; + table[3 * 256 + 107] = 4; + table[4 * 256 + 105] = 5; + table[5 * 256 + 109] = 6; + table[6 * 256 + 45] = 7; + table[7 * 256 + 115] = 8; + table[8 * 256 + 105] = 9; + table[9 * 256 + 103] = 10; + table[10 * 256 + 110] = 11; + table[11 * 256 + 97] = 12; + table[12 * 256 + 116] = 13; + table[13 * 256 + 117] = 14; + table[14 * 256 + 114] = 15; + table[15 * 256 + 101] = 16; + table[16 * 256 + 58] = 17; + table[17 * 256 + 97] = 18; + table[17 * 256 + 98] = 18; + table[17 * 256 + 99] = 18; + table[17 * 256 + 100] = 18; + table[17 * 256 + 101] = 18; + table[17 * 256 + 102] = 18; + table[17 * 256 + 103] = 18; + table[17 * 256 + 104] = 18; + table[17 * 256 + 105] = 18; + table[17 * 256 + 106] = 18; + table[17 * 256 + 107] = 18; + table[17 * 256 + 108] = 18; + table[17 * 256 + 109] = 18; + table[17 * 256 + 110] = 18; + table[17 * 256 + 111] = 18; + table[17 * 256 + 112] = 18; + table[17 * 256 + 113] = 18; + table[17 * 256 + 114] = 18; + table[17 * 256 + 115] = 18; + table[17 * 256 + 116] = 18; + table[17 * 256 + 117] = 18; + table[17 * 256 + 118] = 18; + table[17 * 256 + 119] = 18; + table[17 * 256 + 120] = 18; + table[17 * 256 + 121] = 18; + table[17 * 256 + 122] = 18; + table[18 * 256 + 97] = 18; + table[18 * 256 + 98] = 18; + table[18 * 256 + 99] = 18; + table[18 * 256 + 100] = 18; + table[18 * 256 + 101] = 18; + table[18 * 256 + 102] = 18; + table[18 * 256 + 103] = 18; + table[18 * 256 + 104] = 18; + table[18 * 256 + 105] = 18; + table[18 * 256 + 106] = 18; + table[18 * 256 + 107] = 18; + table[18 * 256 + 108] = 18; + table[18 * 256 + 109] = 18; + table[18 * 256 + 110] = 18; + table[18 * 256 + 111] = 18; + table[18 * 256 + 112] = 18; + table[18 * 256 + 113] = 18; + table[18 * 256 + 114] = 18; + table[18 * 256 + 115] = 18; + table[18 * 256 + 116] = 18; + table[18 * 256 + 117] = 18; + table[18 * 256 + 118] = 18; + table[18 * 256 + 119] = 18; + table[18 * 256 + 120] = 18; + table[18 * 256 + 121] = 18; + table[18 * 256 + 122] = 18; + table[18 * 256 + 61] = 19; + table[19 * 256 + 0] = 20; + table[19 * 256 + 1] = 20; + table[19 * 256 + 2] = 20; + table[19 * 256 + 3] = 20; + table[19 * 256 + 4] = 20; + table[19 * 256 + 5] = 20; + table[19 * 256 + 6] = 20; + table[19 * 256 + 7] = 20; + table[19 * 256 + 8] = 20; + table[19 * 256 + 9] = 20; + table[19 * 256 + 10] = 20; + table[19 * 256 + 11] = 20; + table[19 * 256 + 12] = 20; + table[19 * 256 + 13] = 20; + table[19 * 256 + 14] = 20; + table[19 * 256 + 15] = 20; + table[19 * 256 + 16] = 20; + table[19 * 256 + 17] = 20; + table[19 * 256 + 18] = 20; + table[19 * 256 + 19] = 20; + table[19 * 256 + 20] = 20; + table[19 * 256 + 21] = 20; + table[19 * 256 + 22] = 20; + table[19 * 256 + 23] = 20; + table[19 * 256 + 24] = 20; + table[19 * 256 + 25] = 20; + table[19 * 256 + 26] = 20; + table[19 * 256 + 27] = 20; + table[19 * 256 + 28] = 20; + table[19 * 256 + 29] = 20; + table[19 * 256 + 30] = 20; + table[19 * 256 + 31] = 20; + table[19 * 256 + 32] = 20; + table[19 * 256 + 33] = 20; + table[19 * 256 + 34] = 20; + table[19 * 256 + 35] = 20; + table[19 * 256 + 36] = 20; + table[19 * 256 + 37] = 20; + table[19 * 256 + 38] = 20; + table[19 * 256 + 39] = 20; + table[19 * 256 + 40] = 20; + table[19 * 256 + 41] = 20; + table[19 * 256 + 42] = 20; + table[19 * 256 + 43] = 20; + table[19 * 256 + 44] = 20; + table[19 * 256 + 45] = 20; + table[19 * 256 + 46] = 20; + table[19 * 256 + 47] = 20; + table[19 * 256 + 48] = 20; + table[19 * 256 + 49] = 20; + table[19 * 256 + 50] = 20; + table[19 * 256 + 51] = 20; + table[19 * 256 + 52] = 20; + table[19 * 256 + 53] = 20; + table[19 * 256 + 54] = 20; + table[19 * 256 + 55] = 20; + table[19 * 256 + 56] = 20; + table[19 * 256 + 57] = 20; + table[19 * 256 + 58] = 20; + table[19 * 256 + 60] = 20; + table[19 * 256 + 61] = 20; + table[19 * 256 + 62] = 20; + table[19 * 256 + 63] = 20; + table[19 * 256 + 64] = 20; + table[19 * 256 + 65] = 20; + table[19 * 256 + 66] = 20; + table[19 * 256 + 67] = 20; + table[19 * 256 + 68] = 20; + table[19 * 256 + 69] = 20; + table[19 * 256 + 70] = 20; + table[19 * 256 + 71] = 20; + table[19 * 256 + 72] = 20; + table[19 * 256 + 73] = 20; + table[19 * 256 + 74] = 20; + table[19 * 256 + 75] = 20; + table[19 * 256 + 76] = 20; + table[19 * 256 + 77] = 20; + table[19 * 256 + 78] = 20; + table[19 * 256 + 79] = 20; + table[19 * 256 + 80] = 20; + table[19 * 256 + 81] = 20; + table[19 * 256 + 82] = 20; + table[19 * 256 + 83] = 20; + table[19 * 256 + 84] = 20; + table[19 * 256 + 85] = 20; + table[19 * 256 + 86] = 20; + table[19 * 256 + 87] = 20; + table[19 * 256 + 88] = 20; + table[19 * 256 + 89] = 20; + table[19 * 256 + 90] = 20; + table[19 * 256 + 91] = 20; + table[19 * 256 + 92] = 20; + table[19 * 256 + 93] = 20; + table[19 * 256 + 94] = 20; + table[19 * 256 + 95] = 20; + table[19 * 256 + 96] = 20; + table[19 * 256 + 97] = 20; + table[19 * 256 + 98] = 20; + table[19 * 256 + 99] = 20; + table[19 * 256 + 100] = 20; + table[19 * 256 + 101] = 20; + table[19 * 256 + 102] = 20; + table[19 * 256 + 103] = 20; + table[19 * 256 + 104] = 20; + table[19 * 256 + 105] = 20; + table[19 * 256 + 106] = 20; + table[19 * 256 + 107] = 20; + table[19 * 256 + 108] = 20; + table[19 * 256 + 109] = 20; + table[19 * 256 + 110] = 20; + table[19 * 256 + 111] = 20; + table[19 * 256 + 112] = 20; + table[19 * 256 + 113] = 20; + table[19 * 256 + 114] = 20; + table[19 * 256 + 115] = 20; + table[19 * 256 + 116] = 20; + table[19 * 256 + 117] = 20; + table[19 * 256 + 118] = 20; + table[19 * 256 + 119] = 20; + table[19 * 256 + 120] = 20; + table[19 * 256 + 121] = 20; + table[19 * 256 + 122] = 20; + table[19 * 256 + 123] = 20; + table[19 * 256 + 124] = 20; + table[19 * 256 + 125] = 20; + table[19 * 256 + 126] = 20; + table[19 * 256 + 127] = 20; + table[19 * 256 + 194] = 21; + table[19 * 256 + 195] = 21; + table[19 * 256 + 196] = 21; + table[19 * 256 + 197] = 21; + table[19 * 256 + 198] = 21; + table[19 * 256 + 199] = 21; + table[19 * 256 + 200] = 21; + table[19 * 256 + 201] = 21; + table[19 * 256 + 202] = 21; + table[19 * 256 + 203] = 21; + table[19 * 256 + 204] = 21; + table[19 * 256 + 205] = 21; + table[19 * 256 + 206] = 21; + table[19 * 256 + 207] = 21; + table[19 * 256 + 208] = 21; + table[19 * 256 + 209] = 21; + table[19 * 256 + 210] = 21; + table[19 * 256 + 211] = 21; + table[19 * 256 + 212] = 21; + table[19 * 256 + 213] = 21; + table[19 * 256 + 214] = 21; + table[19 * 256 + 215] = 21; + table[19 * 256 + 216] = 21; + table[19 * 256 + 217] = 21; + table[19 * 256 + 218] = 21; + table[19 * 256 + 219] = 21; + table[19 * 256 + 220] = 21; + table[19 * 256 + 221] = 21; + table[19 * 256 + 222] = 21; + table[19 * 256 + 223] = 21; + table[19 * 256 + 224] = 22; + table[19 * 256 + 225] = 23; + table[19 * 256 + 226] = 23; + table[19 * 256 + 227] = 23; + table[19 * 256 + 228] = 23; + table[19 * 256 + 229] = 23; + table[19 * 256 + 230] = 23; + table[19 * 256 + 231] = 23; + table[19 * 256 + 232] = 23; + table[19 * 256 + 233] = 23; + table[19 * 256 + 234] = 23; + table[19 * 256 + 235] = 23; + table[19 * 256 + 236] = 23; + table[19 * 256 + 238] = 23; + table[19 * 256 + 239] = 23; + table[19 * 256 + 237] = 24; + table[19 * 256 + 240] = 25; + table[19 * 256 + 241] = 26; + table[19 * 256 + 242] = 26; + table[19 * 256 + 243] = 26; + table[19 * 256 + 244] = 27; + table[20 * 256 + 0] = 20; + table[20 * 256 + 1] = 20; + table[20 * 256 + 2] = 20; + table[20 * 256 + 3] = 20; + table[20 * 256 + 4] = 20; + table[20 * 256 + 5] = 20; + table[20 * 256 + 6] = 20; + table[20 * 256 + 7] = 20; + table[20 * 256 + 8] = 20; + table[20 * 256 + 9] = 20; + table[20 * 256 + 10] = 20; + table[20 * 256 + 11] = 20; + table[20 * 256 + 12] = 20; + table[20 * 256 + 13] = 20; + table[20 * 256 + 14] = 20; + table[20 * 256 + 15] = 20; + table[20 * 256 + 16] = 20; + table[20 * 256 + 17] = 20; + table[20 * 256 + 18] = 20; + table[20 * 256 + 19] = 20; + table[20 * 256 + 20] = 20; + table[20 * 256 + 21] = 20; + table[20 * 256 + 22] = 20; + table[20 * 256 + 23] = 20; + table[20 * 256 + 24] = 20; + table[20 * 256 + 25] = 20; + table[20 * 256 + 26] = 20; + table[20 * 256 + 27] = 20; + table[20 * 256 + 28] = 20; + table[20 * 256 + 29] = 20; + table[20 * 256 + 30] = 20; + table[20 * 256 + 31] = 20; + table[20 * 256 + 32] = 20; + table[20 * 256 + 33] = 20; + table[20 * 256 + 34] = 20; + table[20 * 256 + 35] = 20; + table[20 * 256 + 36] = 20; + table[20 * 256 + 37] = 20; + table[20 * 256 + 38] = 20; + table[20 * 256 + 39] = 20; + table[20 * 256 + 40] = 20; + table[20 * 256 + 41] = 20; + table[20 * 256 + 42] = 20; + table[20 * 256 + 43] = 20; + table[20 * 256 + 44] = 20; + table[20 * 256 + 45] = 20; + table[20 * 256 + 46] = 20; + table[20 * 256 + 47] = 20; + table[20 * 256 + 48] = 20; + table[20 * 256 + 49] = 20; + table[20 * 256 + 50] = 20; + table[20 * 256 + 51] = 20; + table[20 * 256 + 52] = 20; + table[20 * 256 + 53] = 20; + table[20 * 256 + 54] = 20; + table[20 * 256 + 55] = 20; + table[20 * 256 + 56] = 20; + table[20 * 256 + 57] = 20; + table[20 * 256 + 58] = 20; + table[20 * 256 + 60] = 20; + table[20 * 256 + 61] = 20; + table[20 * 256 + 62] = 20; + table[20 * 256 + 63] = 20; + table[20 * 256 + 64] = 20; + table[20 * 256 + 65] = 20; + table[20 * 256 + 66] = 20; + table[20 * 256 + 67] = 20; + table[20 * 256 + 68] = 20; + table[20 * 256 + 69] = 20; + table[20 * 256 + 70] = 20; + table[20 * 256 + 71] = 20; + table[20 * 256 + 72] = 20; + table[20 * 256 + 73] = 20; + table[20 * 256 + 74] = 20; + table[20 * 256 + 75] = 20; + table[20 * 256 + 76] = 20; + table[20 * 256 + 77] = 20; + table[20 * 256 + 78] = 20; + table[20 * 256 + 79] = 20; + table[20 * 256 + 80] = 20; + table[20 * 256 + 81] = 20; + table[20 * 256 + 82] = 20; + table[20 * 256 + 83] = 20; + table[20 * 256 + 84] = 20; + table[20 * 256 + 85] = 20; + table[20 * 256 + 86] = 20; + table[20 * 256 + 87] = 20; + table[20 * 256 + 88] = 20; + table[20 * 256 + 89] = 20; + table[20 * 256 + 90] = 20; + table[20 * 256 + 91] = 20; + table[20 * 256 + 92] = 20; + table[20 * 256 + 93] = 20; + table[20 * 256 + 94] = 20; + table[20 * 256 + 95] = 20; + table[20 * 256 + 96] = 20; + table[20 * 256 + 97] = 20; + table[20 * 256 + 98] = 20; + table[20 * 256 + 99] = 20; + table[20 * 256 + 100] = 20; + table[20 * 256 + 101] = 20; + table[20 * 256 + 102] = 20; + table[20 * 256 + 103] = 20; + table[20 * 256 + 104] = 20; + table[20 * 256 + 105] = 20; + table[20 * 256 + 106] = 20; + table[20 * 256 + 107] = 20; + table[20 * 256 + 108] = 20; + table[20 * 256 + 109] = 20; + table[20 * 256 + 110] = 20; + table[20 * 256 + 111] = 20; + table[20 * 256 + 112] = 20; + table[20 * 256 + 113] = 20; + table[20 * 256 + 114] = 20; + table[20 * 256 + 115] = 20; + table[20 * 256 + 116] = 20; + table[20 * 256 + 117] = 20; + table[20 * 256 + 118] = 20; + table[20 * 256 + 119] = 20; + table[20 * 256 + 120] = 20; + table[20 * 256 + 121] = 20; + table[20 * 256 + 122] = 20; + table[20 * 256 + 123] = 20; + table[20 * 256 + 124] = 20; + table[20 * 256 + 125] = 20; + table[20 * 256 + 126] = 20; + table[20 * 256 + 127] = 20; + table[20 * 256 + 194] = 21; + table[20 * 256 + 195] = 21; + table[20 * 256 + 196] = 21; + table[20 * 256 + 197] = 21; + table[20 * 256 + 198] = 21; + table[20 * 256 + 199] = 21; + table[20 * 256 + 200] = 21; + table[20 * 256 + 201] = 21; + table[20 * 256 + 202] = 21; + table[20 * 256 + 203] = 21; + table[20 * 256 + 204] = 21; + table[20 * 256 + 205] = 21; + table[20 * 256 + 206] = 21; + table[20 * 256 + 207] = 21; + table[20 * 256 + 208] = 21; + table[20 * 256 + 209] = 21; + table[20 * 256 + 210] = 21; + table[20 * 256 + 211] = 21; + table[20 * 256 + 212] = 21; + table[20 * 256 + 213] = 21; + table[20 * 256 + 214] = 21; + table[20 * 256 + 215] = 21; + table[20 * 256 + 216] = 21; + table[20 * 256 + 217] = 21; + table[20 * 256 + 218] = 21; + table[20 * 256 + 219] = 21; + table[20 * 256 + 220] = 21; + table[20 * 256 + 221] = 21; + table[20 * 256 + 222] = 21; + table[20 * 256 + 223] = 21; + table[20 * 256 + 224] = 22; + table[20 * 256 + 225] = 23; + table[20 * 256 + 226] = 23; + table[20 * 256 + 227] = 23; + table[20 * 256 + 228] = 23; + table[20 * 256 + 229] = 23; + table[20 * 256 + 230] = 23; + table[20 * 256 + 231] = 23; + table[20 * 256 + 232] = 23; + table[20 * 256 + 233] = 23; + table[20 * 256 + 234] = 23; + table[20 * 256 + 235] = 23; + table[20 * 256 + 236] = 23; + table[20 * 256 + 238] = 23; + table[20 * 256 + 239] = 23; + table[20 * 256 + 237] = 24; + table[20 * 256 + 240] = 25; + table[20 * 256 + 241] = 26; + table[20 * 256 + 242] = 26; + table[20 * 256 + 243] = 26; + table[20 * 256 + 244] = 27; + table[20 * 256 + 59] = 28; + table[21 * 256 + 128] = 20; + table[21 * 256 + 129] = 20; + table[21 * 256 + 130] = 20; + table[21 * 256 + 131] = 20; + table[21 * 256 + 132] = 20; + table[21 * 256 + 133] = 20; + table[21 * 256 + 134] = 20; + table[21 * 256 + 135] = 20; + table[21 * 256 + 136] = 20; + table[21 * 256 + 137] = 20; + table[21 * 256 + 138] = 20; + table[21 * 256 + 139] = 20; + table[21 * 256 + 140] = 20; + table[21 * 256 + 141] = 20; + table[21 * 256 + 142] = 20; + table[21 * 256 + 143] = 20; + table[21 * 256 + 144] = 20; + table[21 * 256 + 145] = 20; + table[21 * 256 + 146] = 20; + table[21 * 256 + 147] = 20; + table[21 * 256 + 148] = 20; + table[21 * 256 + 149] = 20; + table[21 * 256 + 150] = 20; + table[21 * 256 + 151] = 20; + table[21 * 256 + 152] = 20; + table[21 * 256 + 153] = 20; + table[21 * 256 + 154] = 20; + table[21 * 256 + 155] = 20; + table[21 * 256 + 156] = 20; + table[21 * 256 + 157] = 20; + table[21 * 256 + 158] = 20; + table[21 * 256 + 159] = 20; + table[21 * 256 + 160] = 20; + table[21 * 256 + 161] = 20; + table[21 * 256 + 162] = 20; + table[21 * 256 + 163] = 20; + table[21 * 256 + 164] = 20; + table[21 * 256 + 165] = 20; + table[21 * 256 + 166] = 20; + table[21 * 256 + 167] = 20; + table[21 * 256 + 168] = 20; + table[21 * 256 + 169] = 20; + table[21 * 256 + 170] = 20; + table[21 * 256 + 171] = 20; + table[21 * 256 + 172] = 20; + table[21 * 256 + 173] = 20; + table[21 * 256 + 174] = 20; + table[21 * 256 + 175] = 20; + table[21 * 256 + 176] = 20; + table[21 * 256 + 177] = 20; + table[21 * 256 + 178] = 20; + table[21 * 256 + 179] = 20; + table[21 * 256 + 180] = 20; + table[21 * 256 + 181] = 20; + table[21 * 256 + 182] = 20; + table[21 * 256 + 183] = 20; + table[21 * 256 + 184] = 20; + table[21 * 256 + 185] = 20; + table[21 * 256 + 186] = 20; + table[21 * 256 + 187] = 20; + table[21 * 256 + 188] = 20; + table[21 * 256 + 189] = 20; + table[21 * 256 + 190] = 20; + table[21 * 256 + 191] = 20; + table[22 * 256 + 160] = 21; + table[22 * 256 + 161] = 21; + table[22 * 256 + 162] = 21; + table[22 * 256 + 163] = 21; + table[22 * 256 + 164] = 21; + table[22 * 256 + 165] = 21; + table[22 * 256 + 166] = 21; + table[22 * 256 + 167] = 21; + table[22 * 256 + 168] = 21; + table[22 * 256 + 169] = 21; + table[22 * 256 + 170] = 21; + table[22 * 256 + 171] = 21; + table[22 * 256 + 172] = 21; + table[22 * 256 + 173] = 21; + table[22 * 256 + 174] = 21; + table[22 * 256 + 175] = 21; + table[22 * 256 + 176] = 21; + table[22 * 256 + 177] = 21; + table[22 * 256 + 178] = 21; + table[22 * 256 + 179] = 21; + table[22 * 256 + 180] = 21; + table[22 * 256 + 181] = 21; + table[22 * 256 + 182] = 21; + table[22 * 256 + 183] = 21; + table[22 * 256 + 184] = 21; + table[22 * 256 + 185] = 21; + table[22 * 256 + 186] = 21; + table[22 * 256 + 187] = 21; + table[22 * 256 + 188] = 21; + table[22 * 256 + 189] = 21; + table[22 * 256 + 190] = 21; + table[22 * 256 + 191] = 21; + table[23 * 256 + 128] = 21; + table[23 * 256 + 129] = 21; + table[23 * 256 + 130] = 21; + table[23 * 256 + 131] = 21; + table[23 * 256 + 132] = 21; + table[23 * 256 + 133] = 21; + table[23 * 256 + 134] = 21; + table[23 * 256 + 135] = 21; + table[23 * 256 + 136] = 21; + table[23 * 256 + 137] = 21; + table[23 * 256 + 138] = 21; + table[23 * 256 + 139] = 21; + table[23 * 256 + 140] = 21; + table[23 * 256 + 141] = 21; + table[23 * 256 + 142] = 21; + table[23 * 256 + 143] = 21; + table[23 * 256 + 144] = 21; + table[23 * 256 + 145] = 21; + table[23 * 256 + 146] = 21; + table[23 * 256 + 147] = 21; + table[23 * 256 + 148] = 21; + table[23 * 256 + 149] = 21; + table[23 * 256 + 150] = 21; + table[23 * 256 + 151] = 21; + table[23 * 256 + 152] = 21; + table[23 * 256 + 153] = 21; + table[23 * 256 + 154] = 21; + table[23 * 256 + 155] = 21; + table[23 * 256 + 156] = 21; + table[23 * 256 + 157] = 21; + table[23 * 256 + 158] = 21; + table[23 * 256 + 159] = 21; + table[23 * 256 + 160] = 21; + table[23 * 256 + 161] = 21; + table[23 * 256 + 162] = 21; + table[23 * 256 + 163] = 21; + table[23 * 256 + 164] = 21; + table[23 * 256 + 165] = 21; + table[23 * 256 + 166] = 21; + table[23 * 256 + 167] = 21; + table[23 * 256 + 168] = 21; + table[23 * 256 + 169] = 21; + table[23 * 256 + 170] = 21; + table[23 * 256 + 171] = 21; + table[23 * 256 + 172] = 21; + table[23 * 256 + 173] = 21; + table[23 * 256 + 174] = 21; + table[23 * 256 + 175] = 21; + table[23 * 256 + 176] = 21; + table[23 * 256 + 177] = 21; + table[23 * 256 + 178] = 21; + table[23 * 256 + 179] = 21; + table[23 * 256 + 180] = 21; + table[23 * 256 + 181] = 21; + table[23 * 256 + 182] = 21; + table[23 * 256 + 183] = 21; + table[23 * 256 + 184] = 21; + table[23 * 256 + 185] = 21; + table[23 * 256 + 186] = 21; + table[23 * 256 + 187] = 21; + table[23 * 256 + 188] = 21; + table[23 * 256 + 189] = 21; + table[23 * 256 + 190] = 21; + table[23 * 256 + 191] = 21; + table[24 * 256 + 128] = 21; + table[24 * 256 + 129] = 21; + table[24 * 256 + 130] = 21; + table[24 * 256 + 131] = 21; + table[24 * 256 + 132] = 21; + table[24 * 256 + 133] = 21; + table[24 * 256 + 134] = 21; + table[24 * 256 + 135] = 21; + table[24 * 256 + 136] = 21; + table[24 * 256 + 137] = 21; + table[24 * 256 + 138] = 21; + table[24 * 256 + 139] = 21; + table[24 * 256 + 140] = 21; + table[24 * 256 + 141] = 21; + table[24 * 256 + 142] = 21; + table[24 * 256 + 143] = 21; + table[24 * 256 + 144] = 21; + table[24 * 256 + 145] = 21; + table[24 * 256 + 146] = 21; + table[24 * 256 + 147] = 21; + table[24 * 256 + 148] = 21; + table[24 * 256 + 149] = 21; + table[24 * 256 + 150] = 21; + table[24 * 256 + 151] = 21; + table[24 * 256 + 152] = 21; + table[24 * 256 + 153] = 21; + table[24 * 256 + 154] = 21; + table[24 * 256 + 155] = 21; + table[24 * 256 + 156] = 21; + table[24 * 256 + 157] = 21; + table[24 * 256 + 158] = 21; + table[24 * 256 + 159] = 21; + table[25 * 256 + 144] = 23; + table[25 * 256 + 145] = 23; + table[25 * 256 + 146] = 23; + table[25 * 256 + 147] = 23; + table[25 * 256 + 148] = 23; + table[25 * 256 + 149] = 23; + table[25 * 256 + 150] = 23; + table[25 * 256 + 151] = 23; + table[25 * 256 + 152] = 23; + table[25 * 256 + 153] = 23; + table[25 * 256 + 154] = 23; + table[25 * 256 + 155] = 23; + table[25 * 256 + 156] = 23; + table[25 * 256 + 157] = 23; + table[25 * 256 + 158] = 23; + table[25 * 256 + 159] = 23; + table[25 * 256 + 160] = 23; + table[25 * 256 + 161] = 23; + table[25 * 256 + 162] = 23; + table[25 * 256 + 163] = 23; + table[25 * 256 + 164] = 23; + table[25 * 256 + 165] = 23; + table[25 * 256 + 166] = 23; + table[25 * 256 + 167] = 23; + table[25 * 256 + 168] = 23; + table[25 * 256 + 169] = 23; + table[25 * 256 + 170] = 23; + table[25 * 256 + 171] = 23; + table[25 * 256 + 172] = 23; + table[25 * 256 + 173] = 23; + table[25 * 256 + 174] = 23; + table[25 * 256 + 175] = 23; + table[25 * 256 + 176] = 23; + table[25 * 256 + 177] = 23; + table[25 * 256 + 178] = 23; + table[25 * 256 + 179] = 23; + table[25 * 256 + 180] = 23; + table[25 * 256 + 181] = 23; + table[25 * 256 + 182] = 23; + table[25 * 256 + 183] = 23; + table[25 * 256 + 184] = 23; + table[25 * 256 + 185] = 23; + table[25 * 256 + 186] = 23; + table[25 * 256 + 187] = 23; + table[25 * 256 + 188] = 23; + table[25 * 256 + 189] = 23; + table[25 * 256 + 190] = 23; + table[25 * 256 + 191] = 23; + table[26 * 256 + 128] = 23; + table[26 * 256 + 129] = 23; + table[26 * 256 + 130] = 23; + table[26 * 256 + 131] = 23; + table[26 * 256 + 132] = 23; + table[26 * 256 + 133] = 23; + table[26 * 256 + 134] = 23; + table[26 * 256 + 135] = 23; + table[26 * 256 + 136] = 23; + table[26 * 256 + 137] = 23; + table[26 * 256 + 138] = 23; + table[26 * 256 + 139] = 23; + table[26 * 256 + 140] = 23; + table[26 * 256 + 141] = 23; + table[26 * 256 + 142] = 23; + table[26 * 256 + 143] = 23; + table[26 * 256 + 144] = 23; + table[26 * 256 + 145] = 23; + table[26 * 256 + 146] = 23; + table[26 * 256 + 147] = 23; + table[26 * 256 + 148] = 23; + table[26 * 256 + 149] = 23; + table[26 * 256 + 150] = 23; + table[26 * 256 + 151] = 23; + table[26 * 256 + 152] = 23; + table[26 * 256 + 153] = 23; + table[26 * 256 + 154] = 23; + table[26 * 256 + 155] = 23; + table[26 * 256 + 156] = 23; + table[26 * 256 + 157] = 23; + table[26 * 256 + 158] = 23; + table[26 * 256 + 159] = 23; + table[26 * 256 + 160] = 23; + table[26 * 256 + 161] = 23; + table[26 * 256 + 162] = 23; + table[26 * 256 + 163] = 23; + table[26 * 256 + 164] = 23; + table[26 * 256 + 165] = 23; + table[26 * 256 + 166] = 23; + table[26 * 256 + 167] = 23; + table[26 * 256 + 168] = 23; + table[26 * 256 + 169] = 23; + table[26 * 256 + 170] = 23; + table[26 * 256 + 171] = 23; + table[26 * 256 + 172] = 23; + table[26 * 256 + 173] = 23; + table[26 * 256 + 174] = 23; + table[26 * 256 + 175] = 23; + table[26 * 256 + 176] = 23; + table[26 * 256 + 177] = 23; + table[26 * 256 + 178] = 23; + table[26 * 256 + 179] = 23; + table[26 * 256 + 180] = 23; + table[26 * 256 + 181] = 23; + table[26 * 256 + 182] = 23; + table[26 * 256 + 183] = 23; + table[26 * 256 + 184] = 23; + table[26 * 256 + 185] = 23; + table[26 * 256 + 186] = 23; + table[26 * 256 + 187] = 23; + table[26 * 256 + 188] = 23; + table[26 * 256 + 189] = 23; + table[26 * 256 + 190] = 23; + table[26 * 256 + 191] = 23; + table[27 * 256 + 128] = 23; + table[27 * 256 + 129] = 23; + table[27 * 256 + 130] = 23; + table[27 * 256 + 131] = 23; + table[27 * 256 + 132] = 23; + table[27 * 256 + 133] = 23; + table[27 * 256 + 134] = 23; + table[27 * 256 + 135] = 23; + table[27 * 256 + 136] = 23; + table[27 * 256 + 137] = 23; + table[27 * 256 + 138] = 23; + table[27 * 256 + 139] = 23; + table[27 * 256 + 140] = 23; + table[27 * 256 + 141] = 23; + table[27 * 256 + 142] = 23; + table[27 * 256 + 143] = 23; + table[28 * 256 + 32] = 29; + table[29 * 256 + 97] = 18; + table[29 * 256 + 98] = 18; + table[29 * 256 + 99] = 18; + table[29 * 256 + 100] = 18; + table[29 * 256 + 101] = 18; + table[29 * 256 + 102] = 18; + table[29 * 256 + 103] = 18; + table[29 * 256 + 104] = 18; + table[29 * 256 + 105] = 18; + table[29 * 256 + 106] = 18; + table[29 * 256 + 107] = 18; + table[29 * 256 + 108] = 18; + table[29 * 256 + 109] = 18; + table[29 * 256 + 110] = 18; + table[29 * 256 + 111] = 18; + table[29 * 256 + 112] = 18; + table[29 * 256 + 113] = 18; + table[29 * 256 + 114] = 18; + table[29 * 256 + 115] = 18; + table[29 * 256 + 117] = 18; + table[29 * 256 + 118] = 18; + table[29 * 256 + 119] = 18; + table[29 * 256 + 120] = 18; + table[29 * 256 + 121] = 18; + table[29 * 256 + 122] = 18; + table[29 * 256 + 116] = 30; + table[30 * 256 + 97] = 18; + table[30 * 256 + 98] = 18; + table[30 * 256 + 99] = 18; + table[30 * 256 + 100] = 18; + table[30 * 256 + 101] = 18; + table[30 * 256 + 102] = 18; + table[30 * 256 + 103] = 18; + table[30 * 256 + 104] = 18; + table[30 * 256 + 105] = 18; + table[30 * 256 + 106] = 18; + table[30 * 256 + 107] = 18; + table[30 * 256 + 108] = 18; + table[30 * 256 + 109] = 18; + table[30 * 256 + 110] = 18; + table[30 * 256 + 111] = 18; + table[30 * 256 + 112] = 18; + table[30 * 256 + 113] = 18; + table[30 * 256 + 114] = 18; + table[30 * 256 + 115] = 18; + table[30 * 256 + 116] = 18; + table[30 * 256 + 117] = 18; + table[30 * 256 + 118] = 18; + table[30 * 256 + 119] = 18; + table[30 * 256 + 120] = 18; + table[30 * 256 + 121] = 18; + table[30 * 256 + 122] = 18; + table[30 * 256 + 61] = 31; + table[31 * 256 + 0] = 20; + table[31 * 256 + 1] = 20; + table[31 * 256 + 2] = 20; + table[31 * 256 + 3] = 20; + table[31 * 256 + 4] = 20; + table[31 * 256 + 5] = 20; + table[31 * 256 + 6] = 20; + table[31 * 256 + 7] = 20; + table[31 * 256 + 8] = 20; + table[31 * 256 + 9] = 20; + table[31 * 256 + 10] = 20; + table[31 * 256 + 11] = 20; + table[31 * 256 + 12] = 20; + table[31 * 256 + 13] = 20; + table[31 * 256 + 14] = 20; + table[31 * 256 + 15] = 20; + table[31 * 256 + 16] = 20; + table[31 * 256 + 17] = 20; + table[31 * 256 + 18] = 20; + table[31 * 256 + 19] = 20; + table[31 * 256 + 20] = 20; + table[31 * 256 + 21] = 20; + table[31 * 256 + 22] = 20; + table[31 * 256 + 23] = 20; + table[31 * 256 + 24] = 20; + table[31 * 256 + 25] = 20; + table[31 * 256 + 26] = 20; + table[31 * 256 + 27] = 20; + table[31 * 256 + 28] = 20; + table[31 * 256 + 29] = 20; + table[31 * 256 + 30] = 20; + table[31 * 256 + 31] = 20; + table[31 * 256 + 32] = 20; + table[31 * 256 + 33] = 20; + table[31 * 256 + 34] = 20; + table[31 * 256 + 35] = 20; + table[31 * 256 + 36] = 20; + table[31 * 256 + 37] = 20; + table[31 * 256 + 38] = 20; + table[31 * 256 + 39] = 20; + table[31 * 256 + 40] = 20; + table[31 * 256 + 41] = 20; + table[31 * 256 + 42] = 20; + table[31 * 256 + 43] = 20; + table[31 * 256 + 44] = 20; + table[31 * 256 + 45] = 20; + table[31 * 256 + 46] = 20; + table[31 * 256 + 47] = 20; + table[31 * 256 + 58] = 20; + table[31 * 256 + 60] = 20; + table[31 * 256 + 61] = 20; + table[31 * 256 + 62] = 20; + table[31 * 256 + 63] = 20; + table[31 * 256 + 64] = 20; + table[31 * 256 + 65] = 20; + table[31 * 256 + 66] = 20; + table[31 * 256 + 67] = 20; + table[31 * 256 + 68] = 20; + table[31 * 256 + 69] = 20; + table[31 * 256 + 70] = 20; + table[31 * 256 + 71] = 20; + table[31 * 256 + 72] = 20; + table[31 * 256 + 73] = 20; + table[31 * 256 + 74] = 20; + table[31 * 256 + 75] = 20; + table[31 * 256 + 76] = 20; + table[31 * 256 + 77] = 20; + table[31 * 256 + 78] = 20; + table[31 * 256 + 79] = 20; + table[31 * 256 + 80] = 20; + table[31 * 256 + 81] = 20; + table[31 * 256 + 82] = 20; + table[31 * 256 + 83] = 20; + table[31 * 256 + 84] = 20; + table[31 * 256 + 85] = 20; + table[31 * 256 + 86] = 20; + table[31 * 256 + 87] = 20; + table[31 * 256 + 88] = 20; + table[31 * 256 + 89] = 20; + table[31 * 256 + 90] = 20; + table[31 * 256 + 91] = 20; + table[31 * 256 + 92] = 20; + table[31 * 256 + 93] = 20; + table[31 * 256 + 94] = 20; + table[31 * 256 + 95] = 20; + table[31 * 256 + 96] = 20; + table[31 * 256 + 97] = 20; + table[31 * 256 + 98] = 20; + table[31 * 256 + 99] = 20; + table[31 * 256 + 100] = 20; + table[31 * 256 + 101] = 20; + table[31 * 256 + 102] = 20; + table[31 * 256 + 103] = 20; + table[31 * 256 + 104] = 20; + table[31 * 256 + 105] = 20; + table[31 * 256 + 106] = 20; + table[31 * 256 + 107] = 20; + table[31 * 256 + 108] = 20; + table[31 * 256 + 109] = 20; + table[31 * 256 + 110] = 20; + table[31 * 256 + 111] = 20; + table[31 * 256 + 112] = 20; + table[31 * 256 + 113] = 20; + table[31 * 256 + 114] = 20; + table[31 * 256 + 115] = 20; + table[31 * 256 + 116] = 20; + table[31 * 256 + 117] = 20; + table[31 * 256 + 118] = 20; + table[31 * 256 + 119] = 20; + table[31 * 256 + 120] = 20; + table[31 * 256 + 121] = 20; + table[31 * 256 + 122] = 20; + table[31 * 256 + 123] = 20; + table[31 * 256 + 124] = 20; + table[31 * 256 + 125] = 20; + table[31 * 256 + 126] = 20; + table[31 * 256 + 127] = 20; + table[31 * 256 + 194] = 21; + table[31 * 256 + 195] = 21; + table[31 * 256 + 196] = 21; + table[31 * 256 + 197] = 21; + table[31 * 256 + 198] = 21; + table[31 * 256 + 199] = 21; + table[31 * 256 + 200] = 21; + table[31 * 256 + 201] = 21; + table[31 * 256 + 202] = 21; + table[31 * 256 + 203] = 21; + table[31 * 256 + 204] = 21; + table[31 * 256 + 205] = 21; + table[31 * 256 + 206] = 21; + table[31 * 256 + 207] = 21; + table[31 * 256 + 208] = 21; + table[31 * 256 + 209] = 21; + table[31 * 256 + 210] = 21; + table[31 * 256 + 211] = 21; + table[31 * 256 + 212] = 21; + table[31 * 256 + 213] = 21; + table[31 * 256 + 214] = 21; + table[31 * 256 + 215] = 21; + table[31 * 256 + 216] = 21; + table[31 * 256 + 217] = 21; + table[31 * 256 + 218] = 21; + table[31 * 256 + 219] = 21; + table[31 * 256 + 220] = 21; + table[31 * 256 + 221] = 21; + table[31 * 256 + 222] = 21; + table[31 * 256 + 223] = 21; + table[31 * 256 + 224] = 22; + table[31 * 256 + 225] = 23; + table[31 * 256 + 226] = 23; + table[31 * 256 + 227] = 23; + table[31 * 256 + 228] = 23; + table[31 * 256 + 229] = 23; + table[31 * 256 + 230] = 23; + table[31 * 256 + 231] = 23; + table[31 * 256 + 232] = 23; + table[31 * 256 + 233] = 23; + table[31 * 256 + 234] = 23; + table[31 * 256 + 235] = 23; + table[31 * 256 + 236] = 23; + table[31 * 256 + 238] = 23; + table[31 * 256 + 239] = 23; + table[31 * 256 + 237] = 24; + table[31 * 256 + 240] = 25; + table[31 * 256 + 241] = 26; + table[31 * 256 + 242] = 26; + table[31 * 256 + 243] = 26; + table[31 * 256 + 244] = 27; + table[31 * 256 + 48] = 32; + table[31 * 256 + 49] = 32; + table[31 * 256 + 50] = 32; + table[31 * 256 + 51] = 32; + table[31 * 256 + 52] = 32; + table[31 * 256 + 53] = 32; + table[31 * 256 + 54] = 32; + table[31 * 256 + 55] = 32; + table[31 * 256 + 56] = 32; + table[31 * 256 + 57] = 32; + table[32 * 256 + 48] = 32; + table[32 * 256 + 49] = 32; + table[32 * 256 + 50] = 32; + table[32 * 256 + 51] = 32; + table[32 * 256 + 52] = 32; + table[32 * 256 + 53] = 32; + table[32 * 256 + 54] = 32; + table[32 * 256 + 55] = 32; + table[32 * 256 + 56] = 32; + table[32 * 256 + 57] = 32; + table[32 * 256 + 59] = 33; + + table +} + + +pub fn regex_match(input: [u8; N]) -> BoundedVec, 1> { + let pattern_match = unsafe { __regex_match(input) }; + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + let mut start_range = 0; + let mut end_range = 0; + + // check the match + for i in 0..N { + let temp = input[i] as Field; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + s = 0; + start_range = 0; + s_next = potential_s_next; + } + std::as_witness(s_next); + + + let switch = (start_range + end_range != 0) as Field; + let case_1 = start_range - (start_range * switch); + let case_2 = (1 - switch) * i as Field; + start_range = case_1 + case_2; + // if (start_range + end_range == 0) { + // start_range = i as Field; + // } + if (((s == 33) | (s == 34)) & (end_range == 0)) { + end_range = i as Field; + } + + + let range_0 = pattern_match.substrings.get_unchecked(0).in_range(i); + let case_0 = [ + (s_next == 32) & ((s == 31) | (s == 32)) + ].any(|case| case == true) | !range_0; + + + + let substring_range_check = [case_0] + .all(|case| case == true); + + assert(substring_range_check, "substr array ranges wrong"); + + + s = s_next; + } + println(f"start_range: {start_range}, end_range: {end_range}"); + let full_match = Sequence::new(start_range as u32, end_range as u32 - start_range as u32); + let full_match_end = full_match.end(); + println(f"full_match: {full_match}"); + let x = pattern_match.substrings; + for i in 0..1 { + let substring = pattern_match.substrings.get_unchecked(i); + let is_not_valid = i >= pattern_match.substrings.len(); + let index_check = substring.index >= full_match.index; + let length_check = substring.end() <= full_match_end; + let check = (index_check & length_check) | is_not_valid; + assert(check, f"Substring {i} range is out of bounds of the full match found"); + } + + // check final state + assert((s == 33) | (s == 34), f"no match: {s}"); + + // extract substrings + let mut substrings: BoundedVec, 1> = BoundedVec::new(); + for i in 0..1 { + let substring = pattern_match.substrings.get_unchecked(i); + let mut extracted_substring = extract_substring(substring, input); + let mut len = substrings.len() + 1; + if i >= pattern_match.substrings.len() { + extracted_substring = BoundedVec::new(); + len = substrings.len(); + } + substrings.len = len; + substrings.storage[i] = extracted_substring; + } + + substrings +} + +pub unconstrained fn __regex_match(input: [u8; N]) -> RegexMatch { + // regex: (\r\n|^)dkim-signature:([a-z]+=[^;]+; )+t=[0-9]+; + let mut substrings: BoundedVec = BoundedVec::new(); + let mut current_substring = Sequence::default(); + let mut full_match = Sequence::default(); + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + + let mut consecutive_substr = 0; + let mut complete = false; + + for i in 0..input.len() { + let temp = input[i] as Field; + let mut reset = false; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + full_match.index = 0; + reset = true;s + s = 0; + s_next = potential_s_next; + } + if (full_match.index == 0) { + full_match.index = i; + } + // If a substring was in the making, but the state was reset + // we disregard previous progress because apparently it is invalid + if (reset & (consecutive_substr == 1)) { + current_substring = Sequence::default(); + consecutive_substr = 0; + } + // Fill up substrings + if ((s == 31) & (s_next == 32) | (s == 32) & (s_next == 32)) { + if (consecutive_substr == 0) { + current_substring.index = i; + }; + + current_substring.length += 1; + consecutive_substr = 1; + } else if ((consecutive_substr == 1) & (s_next == 0)) { + current_substring = Sequence::default(); + full_match = Sequence::default(); + substrings = BoundedVec::new(); + consecutive_substr = 0; + } else if (s == 33) & (s_next == 34) { + full_match.length = i - full_match.index; + complete = true; + } else if (consecutive_substr == 1) { + // The substring is done so "save" it + substrings.push(current_substring); + // reset the substring holder for next use + current_substring = Sequence::default(); + consecutive_substr = 0; + } + s = s_next; + if complete == true { + println("breaking"); + break; + } + } + assert((s == 33) | (s == 34), f"no match: {s}"); + // Add pending substring that hasn't been added + if consecutive_substr == 1 { + substrings.push(current_substring); + full_match.length = input.len() - full_match.index; + } + + + // make masked array + let mut masked = [0; N]; + for i in 0..substrings.len() { + let substring = substrings.get(i); + let start_index = substring.index; + let end_index = start_index + substring.length; + for j in start_index..end_index { + masked[j] = input[j]; + } + } + + RegexMatch { masked, full_match, substrings } +} + + +pub struct Sequence { + index: u32, + length: u32, +} + +impl Sequence { + pub fn new(index: u32, length: u32) -> Self { + Self { index, length } + } + + pub fn default() -> Self { + Self { index: 0, length: 0 } + } + + pub fn end(self) -> u32 { + self.index + self.length + } + + pub fn in_range(self, index: u32) -> bool { + index >= self.index & index < self.end() + } +} + +pub struct RegexMatch { + masked: [u8; INPUT_LENGTH], + full_match: Sequence, + substrings: BoundedVec, +} + +pub fn extract_substring( + substring_sequence: Sequence, + input: [u8; INPUT_LENGTH], +) -> BoundedVec { + let mut substring: BoundedVec = unsafe { __extract_substring(substring_sequence, input) }; + assert(substring_sequence.length == substring.len(), "length mismatch"); + for i in 0..MAX_SUBSTRING_LENGTH { + // hack for index to never exceed array bounds + // must be constrained to be true when matching is required to prevent 0's passing when shouldn't + // @dev while this adds constraints in worse case it can be more efficient if MAX_SUBSTRING_LENGTH < INPUT_LENGTH + let input_range_check = substring_sequence.index + i < INPUT_LENGTH; + let index = (substring_sequence.index + i) as Field * input_range_check as Field; + + // range where input should match substring + let sequence_range_check = i >= substring_sequence.length; + + // constrain array construction if in range + let expected_byte = input[index]; + let byte = substring.get_unchecked(i); + let matched = (expected_byte as Field == byte as Field); + assert(matched | sequence_range_check, "incorrect substring construction"); + } + substring +} + +unconstrained fn __extract_substring( + substring_sequence: Sequence, + input: [u8; INPUT_LENGTH], +) -> BoundedVec { + let mut substring: BoundedVec = BoundedVec::new(); + for i in 0..substring_sequence.length { + let byte = input[substring_sequence.index + i]; + substring.push(byte); + } + substring +} \ No newline at end of file diff --git a/x/simple/src/working.nr b/x/simple/src/working.nr new file mode 100644 index 00000000..90189ad7 --- /dev/null +++ b/x/simple/src/working.nr @@ -0,0 +1,1064 @@ +global table: [Field; 11008] = comptime { make_lookup_table() }; + +comptime fn make_lookup_table() -> [Field; 11008] { + let mut table = [0; 11008]; + table[41 * 256 + 0] = 42; + table[42 * 256 + 0] = 42; + table[41 * 256 + 1] = 42; + table[42 * 256 + 1] = 42; + table[41 * 256 + 2] = 42; + table[42 * 256 + 2] = 42; + table[41 * 256 + 3] = 42; + table[42 * 256 + 3] = 42; + table[41 * 256 + 4] = 42; + table[42 * 256 + 4] = 42; + table[41 * 256 + 5] = 42; + table[42 * 256 + 5] = 42; + table[41 * 256 + 6] = 42; + table[42 * 256 + 6] = 42; + table[41 * 256 + 7] = 42; + table[42 * 256 + 7] = 42; + table[41 * 256 + 8] = 42; + table[42 * 256 + 8] = 42; + table[41 * 256 + 9] = 42; + table[42 * 256 + 9] = 42; + table[41 * 256 + 10] = 42; + table[42 * 256 + 10] = 42; + table[41 * 256 + 11] = 42; + table[42 * 256 + 11] = 42; + table[41 * 256 + 12] = 42; + table[42 * 256 + 12] = 42; + table[41 * 256 + 13] = 42; + table[42 * 256 + 13] = 42; + table[41 * 256 + 14] = 42; + table[42 * 256 + 14] = 42; + table[41 * 256 + 15] = 42; + table[42 * 256 + 15] = 42; + table[41 * 256 + 16] = 42; + table[42 * 256 + 16] = 42; + table[41 * 256 + 17] = 42; + table[42 * 256 + 17] = 42; + table[41 * 256 + 18] = 42; + table[42 * 256 + 18] = 42; + table[41 * 256 + 19] = 42; + table[42 * 256 + 19] = 42; + table[41 * 256 + 20] = 42; + table[42 * 256 + 20] = 42; + table[41 * 256 + 21] = 42; + table[42 * 256 + 21] = 42; + table[41 * 256 + 22] = 42; + table[42 * 256 + 22] = 42; + table[41 * 256 + 23] = 42; + table[42 * 256 + 23] = 42; + table[41 * 256 + 24] = 42; + table[42 * 256 + 24] = 42; + table[41 * 256 + 25] = 42; + table[42 * 256 + 25] = 42; + table[41 * 256 + 26] = 42; + table[42 * 256 + 26] = 42; + table[41 * 256 + 27] = 42; + table[42 * 256 + 27] = 42; + table[41 * 256 + 28] = 42; + table[42 * 256 + 28] = 42; + table[41 * 256 + 29] = 42; + table[42 * 256 + 29] = 42; + table[41 * 256 + 30] = 42; + table[42 * 256 + 30] = 42; + table[41 * 256 + 31] = 42; + table[42 * 256 + 31] = 42; + table[41 * 256 + 32] = 42; + table[42 * 256 + 32] = 42; + table[41 * 256 + 33] = 42; + table[42 * 256 + 33] = 42; + table[41 * 256 + 34] = 42; + table[42 * 256 + 34] = 42; + table[41 * 256 + 35] = 42; + table[42 * 256 + 35] = 42; + table[41 * 256 + 36] = 42; + table[42 * 256 + 36] = 42; + table[41 * 256 + 37] = 42; + table[42 * 256 + 37] = 42; + table[41 * 256 + 38] = 42; + table[42 * 256 + 38] = 42; + table[41 * 256 + 39] = 42; + table[42 * 256 + 39] = 42; + table[41 * 256 + 40] = 42; + table[42 * 256 + 40] = 42; + table[41 * 256 + 41] = 42; + table[42 * 256 + 41] = 42; + table[41 * 256 + 42] = 42; + table[42 * 256 + 42] = 42; + table[41 * 256 + 43] = 42; + table[42 * 256 + 43] = 42; + table[41 * 256 + 44] = 42; + table[42 * 256 + 44] = 42; + table[41 * 256 + 45] = 42; + table[42 * 256 + 45] = 42; + table[41 * 256 + 46] = 42; + table[42 * 256 + 46] = 42; + table[41 * 256 + 47] = 42; + table[42 * 256 + 47] = 42; + table[41 * 256 + 48] = 42; + table[42 * 256 + 48] = 42; + table[41 * 256 + 49] = 42; + table[42 * 256 + 49] = 42; + table[41 * 256 + 50] = 42; + table[42 * 256 + 50] = 42; + table[41 * 256 + 51] = 42; + table[42 * 256 + 51] = 42; + table[41 * 256 + 52] = 42; + table[42 * 256 + 52] = 42; + table[41 * 256 + 53] = 42; + table[42 * 256 + 53] = 42; + table[41 * 256 + 54] = 42; + table[42 * 256 + 54] = 42; + table[41 * 256 + 55] = 42; + table[42 * 256 + 55] = 42; + table[41 * 256 + 56] = 42; + table[42 * 256 + 56] = 42; + table[41 * 256 + 57] = 42; + table[42 * 256 + 57] = 42; + table[41 * 256 + 58] = 42; + table[42 * 256 + 58] = 42; + table[41 * 256 + 59] = 42; + table[42 * 256 + 59] = 42; + table[41 * 256 + 60] = 42; + table[42 * 256 + 60] = 42; + table[41 * 256 + 61] = 42; + table[42 * 256 + 61] = 42; + table[41 * 256 + 62] = 42; + table[42 * 256 + 62] = 42; + table[41 * 256 + 63] = 42; + table[42 * 256 + 63] = 42; + table[41 * 256 + 64] = 42; + table[42 * 256 + 64] = 42; + table[41 * 256 + 65] = 42; + table[42 * 256 + 65] = 42; + table[41 * 256 + 66] = 42; + table[42 * 256 + 66] = 42; + table[41 * 256 + 67] = 42; + table[42 * 256 + 67] = 42; + table[41 * 256 + 68] = 42; + table[42 * 256 + 68] = 42; + table[41 * 256 + 69] = 42; + table[42 * 256 + 69] = 42; + table[41 * 256 + 70] = 42; + table[42 * 256 + 70] = 42; + table[41 * 256 + 71] = 42; + table[42 * 256 + 71] = 42; + table[41 * 256 + 72] = 42; + table[42 * 256 + 72] = 42; + table[41 * 256 + 73] = 42; + table[42 * 256 + 73] = 42; + table[41 * 256 + 74] = 42; + table[42 * 256 + 74] = 42; + table[41 * 256 + 75] = 42; + table[42 * 256 + 75] = 42; + table[41 * 256 + 76] = 42; + table[42 * 256 + 76] = 42; + table[41 * 256 + 77] = 42; + table[42 * 256 + 77] = 42; + table[41 * 256 + 78] = 42; + table[42 * 256 + 78] = 42; + table[41 * 256 + 79] = 42; + table[42 * 256 + 79] = 42; + table[41 * 256 + 80] = 42; + table[42 * 256 + 80] = 42; + table[41 * 256 + 81] = 42; + table[42 * 256 + 81] = 42; + table[41 * 256 + 82] = 42; + table[42 * 256 + 82] = 42; + table[41 * 256 + 83] = 42; + table[42 * 256 + 83] = 42; + table[41 * 256 + 84] = 42; + table[42 * 256 + 84] = 42; + table[41 * 256 + 85] = 42; + table[42 * 256 + 85] = 42; + table[41 * 256 + 86] = 42; + table[42 * 256 + 86] = 42; + table[41 * 256 + 87] = 42; + table[42 * 256 + 87] = 42; + table[41 * 256 + 88] = 42; + table[42 * 256 + 88] = 42; + table[41 * 256 + 89] = 42; + table[42 * 256 + 89] = 42; + table[41 * 256 + 90] = 42; + table[42 * 256 + 90] = 42; + table[41 * 256 + 91] = 42; + table[42 * 256 + 91] = 42; + table[41 * 256 + 92] = 42; + table[42 * 256 + 92] = 42; + table[41 * 256 + 93] = 42; + table[42 * 256 + 93] = 42; + table[41 * 256 + 94] = 42; + table[42 * 256 + 94] = 42; + table[41 * 256 + 95] = 42; + table[42 * 256 + 95] = 42; + table[41 * 256 + 96] = 42; + table[42 * 256 + 96] = 42; + table[41 * 256 + 97] = 42; + table[42 * 256 + 97] = 42; + table[41 * 256 + 98] = 42; + table[42 * 256 + 98] = 42; + table[41 * 256 + 99] = 42; + table[42 * 256 + 99] = 42; + table[41 * 256 + 100] = 42; + table[42 * 256 + 100] = 42; + table[41 * 256 + 101] = 42; + table[42 * 256 + 101] = 42; + table[41 * 256 + 102] = 42; + table[42 * 256 + 102] = 42; + table[41 * 256 + 103] = 42; + table[42 * 256 + 103] = 42; + table[41 * 256 + 104] = 42; + table[42 * 256 + 104] = 42; + table[41 * 256 + 105] = 42; + table[42 * 256 + 105] = 42; + table[41 * 256 + 106] = 42; + table[42 * 256 + 106] = 42; + table[41 * 256 + 107] = 42; + table[42 * 256 + 107] = 42; + table[41 * 256 + 108] = 42; + table[42 * 256 + 108] = 42; + table[41 * 256 + 109] = 42; + table[42 * 256 + 109] = 42; + table[41 * 256 + 110] = 42; + table[42 * 256 + 110] = 42; + table[41 * 256 + 111] = 42; + table[42 * 256 + 111] = 42; + table[41 * 256 + 112] = 42; + table[42 * 256 + 112] = 42; + table[41 * 256 + 113] = 42; + table[42 * 256 + 113] = 42; + table[41 * 256 + 114] = 42; + table[42 * 256 + 114] = 42; + table[41 * 256 + 115] = 42; + table[42 * 256 + 115] = 42; + table[41 * 256 + 116] = 42; + table[42 * 256 + 116] = 42; + table[41 * 256 + 117] = 42; + table[42 * 256 + 117] = 42; + table[41 * 256 + 118] = 42; + table[42 * 256 + 118] = 42; + table[41 * 256 + 119] = 42; + table[42 * 256 + 119] = 42; + table[41 * 256 + 120] = 42; + table[42 * 256 + 120] = 42; + table[41 * 256 + 121] = 42; + table[42 * 256 + 121] = 42; + table[41 * 256 + 122] = 42; + table[42 * 256 + 122] = 42; + table[41 * 256 + 123] = 42; + table[42 * 256 + 123] = 42; + table[41 * 256 + 124] = 42; + table[42 * 256 + 124] = 42; + table[41 * 256 + 125] = 42; + table[42 * 256 + 125] = 42; + table[41 * 256 + 126] = 42; + table[42 * 256 + 126] = 42; + table[41 * 256 + 127] = 42; + table[42 * 256 + 127] = 42; + table[41 * 256 + 128] = 42; + table[42 * 256 + 128] = 42; + table[41 * 256 + 129] = 42; + table[42 * 256 + 129] = 42; + table[41 * 256 + 130] = 42; + table[42 * 256 + 130] = 42; + table[41 * 256 + 131] = 42; + table[42 * 256 + 131] = 42; + table[41 * 256 + 132] = 42; + table[42 * 256 + 132] = 42; + table[41 * 256 + 133] = 42; + table[42 * 256 + 133] = 42; + table[41 * 256 + 134] = 42; + table[42 * 256 + 134] = 42; + table[41 * 256 + 135] = 42; + table[42 * 256 + 135] = 42; + table[41 * 256 + 136] = 42; + table[42 * 256 + 136] = 42; + table[41 * 256 + 137] = 42; + table[42 * 256 + 137] = 42; + table[41 * 256 + 138] = 42; + table[42 * 256 + 138] = 42; + table[41 * 256 + 139] = 42; + table[42 * 256 + 139] = 42; + table[41 * 256 + 140] = 42; + table[42 * 256 + 140] = 42; + table[41 * 256 + 141] = 42; + table[42 * 256 + 141] = 42; + table[41 * 256 + 142] = 42; + table[42 * 256 + 142] = 42; + table[41 * 256 + 143] = 42; + table[42 * 256 + 143] = 42; + table[41 * 256 + 144] = 42; + table[42 * 256 + 144] = 42; + table[41 * 256 + 145] = 42; + table[42 * 256 + 145] = 42; + table[41 * 256 + 146] = 42; + table[42 * 256 + 146] = 42; + table[41 * 256 + 147] = 42; + table[42 * 256 + 147] = 42; + table[41 * 256 + 148] = 42; + table[42 * 256 + 148] = 42; + table[41 * 256 + 149] = 42; + table[42 * 256 + 149] = 42; + table[41 * 256 + 150] = 42; + table[42 * 256 + 150] = 42; + table[41 * 256 + 151] = 42; + table[42 * 256 + 151] = 42; + table[41 * 256 + 152] = 42; + table[42 * 256 + 152] = 42; + table[41 * 256 + 153] = 42; + table[42 * 256 + 153] = 42; + table[41 * 256 + 154] = 42; + table[42 * 256 + 154] = 42; + table[41 * 256 + 155] = 42; + table[42 * 256 + 155] = 42; + table[41 * 256 + 156] = 42; + table[42 * 256 + 156] = 42; + table[41 * 256 + 157] = 42; + table[42 * 256 + 157] = 42; + table[41 * 256 + 158] = 42; + table[42 * 256 + 158] = 42; + table[41 * 256 + 159] = 42; + table[42 * 256 + 159] = 42; + table[41 * 256 + 160] = 42; + table[42 * 256 + 160] = 42; + table[41 * 256 + 161] = 42; + table[42 * 256 + 161] = 42; + table[41 * 256 + 162] = 42; + table[42 * 256 + 162] = 42; + table[41 * 256 + 163] = 42; + table[42 * 256 + 163] = 42; + table[41 * 256 + 164] = 42; + table[42 * 256 + 164] = 42; + table[41 * 256 + 165] = 42; + table[42 * 256 + 165] = 42; + table[41 * 256 + 166] = 42; + table[42 * 256 + 166] = 42; + table[41 * 256 + 167] = 42; + table[42 * 256 + 167] = 42; + table[41 * 256 + 168] = 42; + table[42 * 256 + 168] = 42; + table[41 * 256 + 169] = 42; + table[42 * 256 + 169] = 42; + table[41 * 256 + 170] = 42; + table[42 * 256 + 170] = 42; + table[41 * 256 + 171] = 42; + table[42 * 256 + 171] = 42; + table[41 * 256 + 172] = 42; + table[42 * 256 + 172] = 42; + table[41 * 256 + 173] = 42; + table[42 * 256 + 173] = 42; + table[41 * 256 + 174] = 42; + table[42 * 256 + 174] = 42; + table[41 * 256 + 175] = 42; + table[42 * 256 + 175] = 42; + table[41 * 256 + 176] = 42; + table[42 * 256 + 176] = 42; + table[41 * 256 + 177] = 42; + table[42 * 256 + 177] = 42; + table[41 * 256 + 178] = 42; + table[42 * 256 + 178] = 42; + table[41 * 256 + 179] = 42; + table[42 * 256 + 179] = 42; + table[41 * 256 + 180] = 42; + table[42 * 256 + 180] = 42; + table[41 * 256 + 181] = 42; + table[42 * 256 + 181] = 42; + table[41 * 256 + 182] = 42; + table[42 * 256 + 182] = 42; + table[41 * 256 + 183] = 42; + table[42 * 256 + 183] = 42; + table[41 * 256 + 184] = 42; + table[42 * 256 + 184] = 42; + table[41 * 256 + 185] = 42; + table[42 * 256 + 185] = 42; + table[41 * 256 + 186] = 42; + table[42 * 256 + 186] = 42; + table[41 * 256 + 187] = 42; + table[42 * 256 + 187] = 42; + table[41 * 256 + 188] = 42; + table[42 * 256 + 188] = 42; + table[41 * 256 + 189] = 42; + table[42 * 256 + 189] = 42; + table[41 * 256 + 190] = 42; + table[42 * 256 + 190] = 42; + table[41 * 256 + 191] = 42; + table[42 * 256 + 191] = 42; + table[41 * 256 + 192] = 42; + table[42 * 256 + 192] = 42; + table[41 * 256 + 193] = 42; + table[42 * 256 + 193] = 42; + table[41 * 256 + 194] = 42; + table[42 * 256 + 194] = 42; + table[41 * 256 + 195] = 42; + table[42 * 256 + 195] = 42; + table[41 * 256 + 196] = 42; + table[42 * 256 + 196] = 42; + table[41 * 256 + 197] = 42; + table[42 * 256 + 197] = 42; + table[41 * 256 + 198] = 42; + table[42 * 256 + 198] = 42; + table[41 * 256 + 199] = 42; + table[42 * 256 + 199] = 42; + table[41 * 256 + 200] = 42; + table[42 * 256 + 200] = 42; + table[41 * 256 + 201] = 42; + table[42 * 256 + 201] = 42; + table[41 * 256 + 202] = 42; + table[42 * 256 + 202] = 42; + table[41 * 256 + 203] = 42; + table[42 * 256 + 203] = 42; + table[41 * 256 + 204] = 42; + table[42 * 256 + 204] = 42; + table[41 * 256 + 205] = 42; + table[42 * 256 + 205] = 42; + table[41 * 256 + 206] = 42; + table[42 * 256 + 206] = 42; + table[41 * 256 + 207] = 42; + table[42 * 256 + 207] = 42; + table[41 * 256 + 208] = 42; + table[42 * 256 + 208] = 42; + table[41 * 256 + 209] = 42; + table[42 * 256 + 209] = 42; + table[41 * 256 + 210] = 42; + table[42 * 256 + 210] = 42; + table[41 * 256 + 211] = 42; + table[42 * 256 + 211] = 42; + table[41 * 256 + 212] = 42; + table[42 * 256 + 212] = 42; + table[41 * 256 + 213] = 42; + table[42 * 256 + 213] = 42; + table[41 * 256 + 214] = 42; + table[42 * 256 + 214] = 42; + table[41 * 256 + 215] = 42; + table[42 * 256 + 215] = 42; + table[41 * 256 + 216] = 42; + table[42 * 256 + 216] = 42; + table[41 * 256 + 217] = 42; + table[42 * 256 + 217] = 42; + table[41 * 256 + 218] = 42; + table[42 * 256 + 218] = 42; + table[41 * 256 + 219] = 42; + table[42 * 256 + 219] = 42; + table[41 * 256 + 220] = 42; + table[42 * 256 + 220] = 42; + table[41 * 256 + 221] = 42; + table[42 * 256 + 221] = 42; + table[41 * 256 + 222] = 42; + table[42 * 256 + 222] = 42; + table[41 * 256 + 223] = 42; + table[42 * 256 + 223] = 42; + table[41 * 256 + 224] = 42; + table[42 * 256 + 224] = 42; + table[41 * 256 + 225] = 42; + table[42 * 256 + 225] = 42; + table[41 * 256 + 226] = 42; + table[42 * 256 + 226] = 42; + table[41 * 256 + 227] = 42; + table[42 * 256 + 227] = 42; + table[41 * 256 + 228] = 42; + table[42 * 256 + 228] = 42; + table[41 * 256 + 229] = 42; + table[42 * 256 + 229] = 42; + table[41 * 256 + 230] = 42; + table[42 * 256 + 230] = 42; + table[41 * 256 + 231] = 42; + table[42 * 256 + 231] = 42; + table[41 * 256 + 232] = 42; + table[42 * 256 + 232] = 42; + table[41 * 256 + 233] = 42; + table[42 * 256 + 233] = 42; + table[41 * 256 + 234] = 42; + table[42 * 256 + 234] = 42; + table[41 * 256 + 235] = 42; + table[42 * 256 + 235] = 42; + table[41 * 256 + 236] = 42; + table[42 * 256 + 236] = 42; + table[41 * 256 + 237] = 42; + table[42 * 256 + 237] = 42; + table[41 * 256 + 238] = 42; + table[42 * 256 + 238] = 42; + table[41 * 256 + 239] = 42; + table[42 * 256 + 239] = 42; + table[41 * 256 + 240] = 42; + table[42 * 256 + 240] = 42; + table[41 * 256 + 241] = 42; + table[42 * 256 + 241] = 42; + table[41 * 256 + 242] = 42; + table[42 * 256 + 242] = 42; + table[41 * 256 + 243] = 42; + table[42 * 256 + 243] = 42; + table[41 * 256 + 244] = 42; + table[42 * 256 + 244] = 42; + table[41 * 256 + 245] = 42; + table[42 * 256 + 245] = 42; + table[41 * 256 + 246] = 42; + table[42 * 256 + 246] = 42; + table[41 * 256 + 247] = 42; + table[42 * 256 + 247] = 42; + table[41 * 256 + 248] = 42; + table[42 * 256 + 248] = 42; + table[41 * 256 + 249] = 42; + table[42 * 256 + 249] = 42; + table[41 * 256 + 250] = 42; + table[42 * 256 + 250] = 42; + table[41 * 256 + 251] = 42; + table[42 * 256 + 251] = 42; + table[41 * 256 + 252] = 42; + table[42 * 256 + 252] = 42; + table[41 * 256 + 253] = 42; + table[42 * 256 + 253] = 42; + table[41 * 256 + 254] = 42; + table[42 * 256 + 254] = 42; + table[0 * 256 + 76] = 1; + table[1 * 256 + 97] = 2; + table[2 * 256 + 116] = 3; + table[3 * 256 + 105] = 4; + table[4 * 256 + 110] = 5; + table[5 * 256 + 45] = 6; + table[6 * 256 + 69] = 7; + table[7 * 256 + 120] = 8; + table[8 * 256 + 116] = 9; + table[9 * 256 + 101] = 10; + table[10 * 256 + 110] = 11; + table[11 * 256 + 115] = 12; + table[12 * 256 + 105] = 13; + table[13 * 256 + 111] = 14; + table[14 * 256 + 110] = 15; + table[15 * 256 + 61] = 16; + table[16 * 256 + 194] = 17; + table[16 * 256 + 195] = 18; + table[16 * 256 + 196] = 18; + table[16 * 256 + 197] = 18; + table[16 * 256 + 198] = 18; + table[17 * 256 + 161] = 19; + table[17 * 256 + 162] = 19; + table[17 * 256 + 163] = 19; + table[17 * 256 + 164] = 19; + table[17 * 256 + 165] = 19; + table[17 * 256 + 166] = 19; + table[17 * 256 + 167] = 19; + table[17 * 256 + 168] = 19; + table[17 * 256 + 169] = 19; + table[17 * 256 + 170] = 19; + table[17 * 256 + 171] = 19; + table[17 * 256 + 172] = 19; + table[17 * 256 + 173] = 19; + table[17 * 256 + 174] = 19; + table[17 * 256 + 175] = 19; + table[17 * 256 + 176] = 19; + table[17 * 256 + 177] = 19; + table[17 * 256 + 178] = 19; + table[17 * 256 + 179] = 19; + table[17 * 256 + 180] = 19; + table[17 * 256 + 181] = 19; + table[17 * 256 + 182] = 19; + table[17 * 256 + 183] = 19; + table[17 * 256 + 184] = 19; + table[17 * 256 + 185] = 19; + table[17 * 256 + 186] = 19; + table[17 * 256 + 187] = 19; + table[17 * 256 + 188] = 19; + table[17 * 256 + 189] = 19; + table[17 * 256 + 190] = 19; + table[17 * 256 + 191] = 19; + table[18 * 256 + 128] = 19; + table[18 * 256 + 129] = 19; + table[18 * 256 + 130] = 19; + table[18 * 256 + 131] = 19; + table[18 * 256 + 132] = 19; + table[18 * 256 + 133] = 19; + table[18 * 256 + 134] = 19; + table[18 * 256 + 135] = 19; + table[18 * 256 + 136] = 19; + table[18 * 256 + 137] = 19; + table[18 * 256 + 138] = 19; + table[18 * 256 + 139] = 19; + table[18 * 256 + 140] = 19; + table[18 * 256 + 141] = 19; + table[18 * 256 + 142] = 19; + table[18 * 256 + 143] = 19; + table[18 * 256 + 144] = 19; + table[18 * 256 + 145] = 19; + table[18 * 256 + 146] = 19; + table[18 * 256 + 147] = 19; + table[18 * 256 + 148] = 19; + table[18 * 256 + 149] = 19; + table[18 * 256 + 150] = 19; + table[18 * 256 + 151] = 19; + table[18 * 256 + 152] = 19; + table[18 * 256 + 153] = 19; + table[18 * 256 + 154] = 19; + table[18 * 256 + 155] = 19; + table[18 * 256 + 156] = 19; + table[18 * 256 + 157] = 19; + table[18 * 256 + 158] = 19; + table[18 * 256 + 159] = 19; + table[18 * 256 + 160] = 19; + table[18 * 256 + 161] = 19; + table[18 * 256 + 162] = 19; + table[18 * 256 + 163] = 19; + table[18 * 256 + 164] = 19; + table[18 * 256 + 165] = 19; + table[18 * 256 + 166] = 19; + table[18 * 256 + 167] = 19; + table[18 * 256 + 168] = 19; + table[18 * 256 + 169] = 19; + table[18 * 256 + 170] = 19; + table[18 * 256 + 171] = 19; + table[18 * 256 + 172] = 19; + table[18 * 256 + 173] = 19; + table[18 * 256 + 174] = 19; + table[18 * 256 + 175] = 19; + table[18 * 256 + 176] = 19; + table[18 * 256 + 177] = 19; + table[18 * 256 + 178] = 19; + table[18 * 256 + 179] = 19; + table[18 * 256 + 180] = 19; + table[18 * 256 + 181] = 19; + table[18 * 256 + 182] = 19; + table[18 * 256 + 183] = 19; + table[18 * 256 + 184] = 19; + table[18 * 256 + 185] = 19; + table[18 * 256 + 186] = 19; + table[18 * 256 + 187] = 19; + table[18 * 256 + 188] = 19; + table[18 * 256 + 189] = 19; + table[18 * 256 + 190] = 19; + table[18 * 256 + 191] = 19; + table[19 * 256 + 194] = 17; + table[19 * 256 + 195] = 18; + table[19 * 256 + 196] = 18; + table[19 * 256 + 197] = 18; + table[19 * 256 + 198] = 18; + table[19 * 256 + 32] = 20; + table[20 * 256 + 71] = 21; + table[21 * 256 + 114] = 22; + table[22 * 256 + 101] = 23; + table[23 * 256 + 101] = 24; + table[24 * 256 + 107] = 25; + table[25 * 256 + 61] = 26; + table[26 * 256 + 205] = 27; + table[26 * 256 + 206] = 28; + table[26 * 256 + 207] = 28; + table[27 * 256 + 176] = 29; + table[27 * 256 + 177] = 29; + table[27 * 256 + 178] = 29; + table[27 * 256 + 179] = 29; + table[27 * 256 + 180] = 29; + table[27 * 256 + 181] = 29; + table[27 * 256 + 182] = 29; + table[27 * 256 + 183] = 29; + table[27 * 256 + 184] = 29; + table[27 * 256 + 185] = 29; + table[27 * 256 + 186] = 29; + table[27 * 256 + 187] = 29; + table[27 * 256 + 188] = 29; + table[27 * 256 + 189] = 29; + table[27 * 256 + 190] = 29; + table[27 * 256 + 191] = 29; + table[28 * 256 + 128] = 29; + table[28 * 256 + 129] = 29; + table[28 * 256 + 130] = 29; + table[28 * 256 + 131] = 29; + table[28 * 256 + 132] = 29; + table[28 * 256 + 133] = 29; + table[28 * 256 + 134] = 29; + table[28 * 256 + 135] = 29; + table[28 * 256 + 136] = 29; + table[28 * 256 + 137] = 29; + table[28 * 256 + 138] = 29; + table[28 * 256 + 139] = 29; + table[28 * 256 + 140] = 29; + table[28 * 256 + 141] = 29; + table[28 * 256 + 142] = 29; + table[28 * 256 + 143] = 29; + table[28 * 256 + 144] = 29; + table[28 * 256 + 145] = 29; + table[28 * 256 + 146] = 29; + table[28 * 256 + 147] = 29; + table[28 * 256 + 148] = 29; + table[28 * 256 + 149] = 29; + table[28 * 256 + 150] = 29; + table[28 * 256 + 151] = 29; + table[28 * 256 + 152] = 29; + table[28 * 256 + 153] = 29; + table[28 * 256 + 154] = 29; + table[28 * 256 + 155] = 29; + table[28 * 256 + 156] = 29; + table[28 * 256 + 157] = 29; + table[28 * 256 + 158] = 29; + table[28 * 256 + 159] = 29; + table[28 * 256 + 160] = 29; + table[28 * 256 + 161] = 29; + table[28 * 256 + 162] = 29; + table[28 * 256 + 163] = 29; + table[28 * 256 + 164] = 29; + table[28 * 256 + 165] = 29; + table[28 * 256 + 166] = 29; + table[28 * 256 + 167] = 29; + table[28 * 256 + 168] = 29; + table[28 * 256 + 169] = 29; + table[28 * 256 + 170] = 29; + table[28 * 256 + 171] = 29; + table[28 * 256 + 172] = 29; + table[28 * 256 + 173] = 29; + table[28 * 256 + 174] = 29; + table[28 * 256 + 175] = 29; + table[28 * 256 + 176] = 29; + table[28 * 256 + 177] = 29; + table[28 * 256 + 178] = 29; + table[28 * 256 + 179] = 29; + table[28 * 256 + 180] = 29; + table[28 * 256 + 181] = 29; + table[28 * 256 + 182] = 29; + table[28 * 256 + 183] = 29; + table[28 * 256 + 184] = 29; + table[28 * 256 + 185] = 29; + table[28 * 256 + 186] = 29; + table[28 * 256 + 187] = 29; + table[28 * 256 + 188] = 29; + table[28 * 256 + 189] = 29; + table[28 * 256 + 190] = 29; + table[28 * 256 + 191] = 29; + table[29 * 256 + 205] = 27; + table[29 * 256 + 206] = 28; + table[29 * 256 + 207] = 28; + table[29 * 256 + 32] = 30; + table[30 * 256 + 67] = 31; + table[31 * 256 + 121] = 32; + table[32 * 256 + 114] = 33; + table[33 * 256 + 105] = 34; + table[34 * 256 + 108] = 35; + table[35 * 256 + 108] = 36; + table[36 * 256 + 105] = 37; + table[37 * 256 + 99] = 38; + table[38 * 256 + 61] = 39; + table[39 * 256 + 208] = 40; + table[39 * 256 + 209] = 40; + table[39 * 256 + 210] = 40; + table[39 * 256 + 211] = 40; + table[40 * 256 + 128] = 41; + table[40 * 256 + 129] = 41; + table[40 * 256 + 130] = 41; + table[40 * 256 + 131] = 41; + table[40 * 256 + 132] = 41; + table[40 * 256 + 133] = 41; + table[40 * 256 + 134] = 41; + table[40 * 256 + 135] = 41; + table[40 * 256 + 136] = 41; + table[40 * 256 + 137] = 41; + table[40 * 256 + 138] = 41; + table[40 * 256 + 139] = 41; + table[40 * 256 + 140] = 41; + table[40 * 256 + 141] = 41; + table[40 * 256 + 142] = 41; + table[40 * 256 + 143] = 41; + table[40 * 256 + 144] = 41; + table[40 * 256 + 145] = 41; + table[40 * 256 + 146] = 41; + table[40 * 256 + 147] = 41; + table[40 * 256 + 148] = 41; + table[40 * 256 + 149] = 41; + table[40 * 256 + 150] = 41; + table[40 * 256 + 151] = 41; + table[40 * 256 + 152] = 41; + table[40 * 256 + 153] = 41; + table[40 * 256 + 154] = 41; + table[40 * 256 + 155] = 41; + table[40 * 256 + 156] = 41; + table[40 * 256 + 157] = 41; + table[40 * 256 + 158] = 41; + table[40 * 256 + 159] = 41; + table[40 * 256 + 160] = 41; + table[40 * 256 + 161] = 41; + table[40 * 256 + 162] = 41; + table[40 * 256 + 163] = 41; + table[40 * 256 + 164] = 41; + table[40 * 256 + 165] = 41; + table[40 * 256 + 166] = 41; + table[40 * 256 + 167] = 41; + table[40 * 256 + 168] = 41; + table[40 * 256 + 169] = 41; + table[40 * 256 + 170] = 41; + table[40 * 256 + 171] = 41; + table[40 * 256 + 172] = 41; + table[40 * 256 + 173] = 41; + table[40 * 256 + 174] = 41; + table[40 * 256 + 175] = 41; + table[40 * 256 + 176] = 41; + table[40 * 256 + 177] = 41; + table[40 * 256 + 178] = 41; + table[40 * 256 + 179] = 41; + table[40 * 256 + 180] = 41; + table[40 * 256 + 181] = 41; + table[40 * 256 + 182] = 41; + table[40 * 256 + 183] = 41; + table[40 * 256 + 184] = 41; + table[40 * 256 + 185] = 41; + table[40 * 256 + 186] = 41; + table[40 * 256 + 187] = 41; + table[40 * 256 + 188] = 41; + table[40 * 256 + 189] = 41; + table[40 * 256 + 190] = 41; + table[40 * 256 + 191] = 41; + table[41 * 256 + 208] = 40; + table[41 * 256 + 209] = 40; + table[41 * 256 + 210] = 40; + table[41 * 256 + 211] = 40; + + table +} + +pub fn regex_match(input: [u8; N]) -> BoundedVec, 3> { + let pattern_match = unsafe { __regex_match(input) }; + let substring_ranges = pattern_match.substrings; + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + + // check the match + for i in 0..N { + let temp = input[i] as Field; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + s = 0; + s_next = potential_s_next; + } + std::as_witness(s_next); + + // check case 1 + let range_1 = substring_ranges.get_unchecked(0).in_range(i); + let case_1 = [ + (s == 16) & ((s_next == 17) | (s_next == 18)), + (s_next == 19) & ((s == 17) | (s == 18)), + (s == 19) & ((s_next == 17) | (s_next == 18)), + ] + .any(|case| case == true | range_1 == false); + + let range_2 = substring_ranges.get_unchecked(1).in_range(i); + // ((s == 26) & (s_next == 27)), + // ((s == 26) & (s_next == 28)), + // ((s == 27) & (s_next == 29)), + // ((s == 28) & (s_next == 29)), + // ((s == 29) & (s_next == 27)), + // ((s == 29) & (s_next == 28)), + let case_2 = [ + (s_next == 27) & ((s == 26) | (s == 29)), + (s_next == 28) & ((s == 26) | (s == 29)), + (s_next == 29) & ((s == 27) | (s == 28)), + ] + .any(|case| case == true | range_2 == false); + + // let check_2 = case_2.any(|case| case == true | range_2 == false); + let range_3 = substring_ranges.get_unchecked(2).in_range(i); + let case_3 = [ + (s_next == 40) & ((s == 41) | (s == 39)), + (s == 40) & (s_next == 41), + ].any(|case| case == true | range_3 == false); + + // let check_3 = case_3.any(|case| case == true | range_3 == false); + + let substring_range_check = [case_1, case_2, case_3] + .all(|check| check == true); + + // let check = check_1 & check_2 & check_3; + assert(substring_range_check, "substr array ranges wrong"); + + s = s_next; + } + // check final state + assert((s == 41) | (s == 42), f"no match: {s}"); + + // extract substrings + let mut substrings: BoundedVec, 3> = BoundedVec::new(); + for i in 0..2 { + let substring = pattern_match.substrings.get_unchecked(i); + let mut extracted_substring = extract_substring(substring, pattern_match.masked); + let mut len = substrings.len() + 1; + if i < pattern_match.substrings.len() { + extracted_substring = BoundedVec::new(); + len = substrings.len(); + } + substrings.len = len; + substrings.storage[i] = extracted_substring; + } + + substrings +} + +pub unconstrained fn __regex_match(input: [u8; N]) -> RegexMatch { + // regex: Latin-Extension=[\u{00a1}-\u{01bf}]+ Greek=[\u{0370}-\u{03ff}]+ Cyrillic=[\u{0400}-\u{04ff}]+ + let mut substrings: BoundedVec = BoundedVec::new(); + let mut current_substring = Sequence::default(); + let mut full_match = Sequence::default(); + + // "Previous" state + let mut s: Field = 0; + s = table[255]; + // "Next"/upcoming state + let mut s_next: Field = 0; + + let mut consecutive_substr = 0; + let mut complete = false; + + for i in 0..input.len() { + let temp = input[i] as Field; + let mut reset = false; + s_next = table[s * 256 + temp]; + let potential_s_next = table[temp]; + if s_next == 0 { + reset = true; + s = 0; + s_next = potential_s_next; + } + // If a substring was in the making, but the state was reset + // we disregard previous progress because apparently it is invalid + if (reset & (consecutive_substr == 1)) { + current_substring = Sequence::default(); + consecutive_substr = 0; + } + // Fill up substrings + if ( + (s == 16) & (s_next == 17) + | (s == 16) & (s_next == 18) + | (s == 17) & (s_next == 19) + | (s == 18) & (s_next == 19) + | (s == 19) & (s_next == 17) + | (s == 19) & (s_next == 18) + ) { + if (consecutive_substr == 0) { + full_match.index = i; + current_substring.index = i; + }; + + current_substring.length += 1; + consecutive_substr = 1; + } else if ( + (s == 26) & (s_next == 27) + | (s == 26) & (s_next == 28) + | (s == 27) & (s_next == 29) + | (s == 28) & (s_next == 29) + | (s == 29) & (s_next == 27) + | (s == 29) & (s_next == 28) + ) { + current_substring.length += 1; + consecutive_substr = 1; + } else if ( + (s == 39) & (s_next == 40) | (s == 40) & (s_next == 41) | (s == 41) & (s_next == 40) + ) { + current_substring.length += 1; + consecutive_substr = 1; + } else if ((consecutive_substr == 1) & (s_next == 0)) { + current_substring = Sequence::default(); + full_match = Sequence::default(); + substrings = BoundedVec::new(); + consecutive_substr = 0; + } else if (s == 41) & (s_next == 42) { + full_match.length = i - full_match.index + 1; + complete = true; + } else if (consecutive_substr == 1) { + // The substring is done so "save" it + substrings.push(current_substring); + // reset the substring holder for next use + current_substring = Sequence::default(); + consecutive_substr = 0; + } + s = s_next; + if complete == true { + break; + } + } + assert((s == 41) | (s == 42), f"no match: {s}"); + // Add pending substring that hasn't been added + if consecutive_substr == 1 { + substrings.push(current_substring); + full_match.length = input.len() - full_match.index; + } + + // make masked array + let mut masked = [0; N]; + for i in 0..substrings.len() { + let substring = substrings.get(i); + let start_index = substring.index; + let end_index = start_index + substring.length; + for j in start_index..end_index { + masked[j] = input[j]; + } + } + + RegexMatch { masked, full_match, substrings } +} + +pub struct Sequence { + index: u32, + length: u32, +} + +impl Sequence { + pub fn new(index: u32, length: u32) -> Self { + Self { index, length } + } + + pub fn default() -> Self { + Self { index: 0, length: 0 } + } + + pub fn end(self) -> u32 { + self.index + self.length + } + + pub fn in_range(self, index: u32) -> bool { + index >= self.index & index < self.end() + } +} + +pub struct RegexMatch { + masked: [u8; INPUT_LENGTH], + full_match: Sequence, + substrings: BoundedVec, +} + +pub fn extract_substring( + substring_sequence: Sequence, + input: [u8; INPUT_LENGTH], +) -> BoundedVec { + let mut substring: BoundedVec = + unsafe { __extract_substring(substring_sequence, input) }; + assert(substring_sequence.length == substring.len(), "length mismatch"); + // let first_index = input[substring_sequence.index]; + for i in 0..MAX_SUBSTRING_LENGTH { + // hack for index to never exceed array bounds + // must be constrained to be true when matching is required to prevent 0's passing when shouldn't + // @dev while this adds constraints in worse case it can be more efficient if MAX_SUBSTRING_LENGTH < INPUT_LENGTH + let input_range_check = substring_sequence.index + i < INPUT_LENGTH; + let index = (substring_sequence.index + i) as Field * input_range_check as Field; + + // range where input should match substring + let sequence_range_check = i >= substring_sequence.length; + + // constrain array construction if in range + let expected_byte = input[index]; + let byte = substring.get_unchecked(i); + let matched = (expected_byte as Field == byte as Field); + assert(matched | sequence_range_check, "incorrect substring construction"); + } + substring +} + +unconstrained fn __extract_substring( + substring_sequence: Sequence, + input: [u8; INPUT_LENGTH], +) -> BoundedVec { + let mut substring: BoundedVec = BoundedVec::new(); + for i in 0..substring_sequence.length { + let byte = input[substring_sequence.index + i]; + substring.push(byte); + } + substring +} diff --git a/x/sparse/Nargo.toml b/x/sparse/Nargo.toml new file mode 100644 index 00000000..5a04eb8a --- /dev/null +++ b/x/sparse/Nargo.toml @@ -0,0 +1,8 @@ +[package] +name = "sparse_regex" +type = "bin" +authors = [""] +compiler_version = ">=1.0.0" + +[dependencies] +sparse_array = { git = "https://github.com/jp4g/sparse_array/", tag = "feat/comptime-codegen"} \ No newline at end of file diff --git a/x/sparse/Prover.toml b/x/sparse/Prover.toml new file mode 100644 index 00000000..fcb4b2ae --- /dev/null +++ b/x/sparse/Prover.toml @@ -0,0 +1 @@ +input = [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 120, 49, 50, 45, 121, 121, 95, 122] \ No newline at end of file diff --git a/x/sparse/src/main.nr b/x/sparse/src/main.nr new file mode 100644 index 00000000..920e43d2 --- /dev/null +++ b/x/sparse/src/main.nr @@ -0,0 +1,138 @@ +mod regex; + +global MAX_INPUT_SIZE: u32 = 256; + +fn main(input: [u8; MAX_INPUT_SIZE]) { + let x = regex::regex_match(input); +} + +#[test] +fn test_out() { + let input: [u8; 8] = "x12-yy_z".as_bytes(); + let mut full_input = [0; MAX_INPUT_SIZE]; + for i in 0..8 { + full_input[MAX_INPUT_SIZE-8+i] = input[i]; + } + println(full_input); + // main(input); +} + +#[test] +fn test_pass_1() { + let input: [u8; 8] = "x12-yy_z".as_bytes(); + regex::regex_match(input); +} + +#[test] +fn test_pass_2() { + let input: [u8; 9] = "x99-yyy_z".as_bytes(); + regex::regex_match(input); +} + +#[test] +fn test_pass_3() { + let input: [u8; 8] = "x00-yy_z".as_bytes(); + regex::regex_match(input); +} + +#[test] +fn test_pass_4() { + let input: [u8; 9] = "x45-yyy_z".as_bytes(); + regex::regex_match(input); +} + +#[test] +fn test_pass_5() { + let input: [u8; 8] = "x01-yy_z".as_bytes(); + regex::regex_match(input); +} + +#[test] +fn test_pass_6() { + let input: [u8; 9] = "x78-yyy_z".as_bytes(); + regex::regex_match(input); +} + +#[test] +fn test_pass_7() { + let input: [u8; 8] = "x34-yy_z".as_bytes(); + regex::regex_match(input); +} + +#[test] +fn test_pass_8() { + let input: [u8; 9] = "x89-yyy_z".as_bytes(); + regex::regex_match(input); +} + +#[test] +fn test_pass_9() { + let input: [u8; 8] = "x23-yy_z".as_bytes(); + regex::regex_match(input); +} + +#[test] +fn test_pass_10() { + let input: [u8; 9] = "x67-yyy_z".as_bytes(); + regex::regex_match(input); +} + +#[test(should_fail)] +fn test_fail_1() { + let input: [u8; 10] = "x123-yyy_z".as_bytes(); + regex::regex_match(input); +} + +#[test(should_fail)] +fn test_fail_2() { + let input: [u8; 7] = "x12-y_z".as_bytes(); + regex::regex_match(input); +} + +#[test(should_fail)] +fn test_fail_3() { + let input: [u8; 7] = "x12-yyy".as_bytes(); + regex::regex_match(input); +} + +#[test(should_fail)] +fn test_fail_4() { + let input: [u8; 8] = "x1-yyy_z".as_bytes(); + regex::regex_match(input); +} + +#[test(should_fail)] +fn test_fail_5() { + let input: [u8; 9] = "x12-yy_zz".as_bytes(); + regex::regex_match(input); +} + +#[test(should_fail)] +fn test_fail_6() { + let input: [u8; 9] = "x12-yyy_x".as_bytes(); + regex::regex_match(input); +} + +#[test(should_fail)] +fn test_fail_7() { + let input: [u8; 7] = "x12yy_z".as_bytes(); + regex::regex_match(input); +} + +#[test(should_fail)] +fn test_fail_8() { + let input: [u8; 7] = "12-yy_z".as_bytes(); + regex::regex_match(input); +} + +#[test(should_fail)] +fn test_fail_9() { + let input: [u8; 9] = "x12-y_zzz".as_bytes(); + regex::regex_match(input); +} + +#[test(should_fail)] +fn test_fail_10() { + let input: [u8; 9] = "x12--yy_z".as_bytes(); + regex::regex_match(input); +} \ No newline at end of file diff --git a/x/sparse/src/regex.nr b/x/sparse/src/regex.nr new file mode 100644 index 00000000..603eaad1 --- /dev/null +++ b/x/sparse/src/regex.nr @@ -0,0 +1,187 @@ + +use crate::regex_common::Sequence; + + +global table: sparse_array::SparseArray<806, Field> = sparse_array::SparseArray { + keys: [0x00000000, 0x0000004c, 0x00000161, 0x00000274, 0x00000369, 0x0000046e, 0x0000052d, 0x00000645, 0x00000778, 0x00000874, 0x00000965, 0x00000a6e, 0x00000b73, 0x00000c69, 0x00000d6f, 0x00000e6e, 0x00000f3d, 0x000010c2, 0x000010c3, 0x000010c4, 0x000010c5, 0x000010c6, 0x000011a1, 0x000011a2, 0x000011a3, 0x000011a4, 0x000011a5, 0x000011a6, 0x000011a7, 0x000011a8, 0x000011a9, 0x000011aa, 0x000011ab, 0x000011ac, 0x000011ad, 0x000011ae, 0x000011af, 0x000011b0, 0x000011b1, 0x000011b2, 0x000011b3, 0x000011b4, 0x000011b5, 0x000011b6, 0x000011b7, 0x000011b8, 0x000011b9, 0x000011ba, 0x000011bb, 0x000011bc, 0x000011bd, 0x000011be, 0x000011bf, 0x00001280, 0x00001281, 0x00001282, 0x00001283, 0x00001284, 0x00001285, 0x00001286, 0x00001287, 0x00001288, 0x00001289, 0x0000128a, 0x0000128b, 0x0000128c, 0x0000128d, 0x0000128e, 0x0000128f, 0x00001290, 0x00001291, 0x00001292, 0x00001293, 0x00001294, 0x00001295, 0x00001296, 0x00001297, 0x00001298, 0x00001299, 0x0000129a, 0x0000129b, 0x0000129c, 0x0000129d, 0x0000129e, 0x0000129f, 0x000012a0, 0x000012a1, 0x000012a2, 0x000012a3, 0x000012a4, 0x000012a5, 0x000012a6, 0x000012a7, 0x000012a8, 0x000012a9, 0x000012aa, 0x000012ab, 0x000012ac, 0x000012ad, 0x000012ae, 0x000012af, 0x000012b0, 0x000012b1, 0x000012b2, 0x000012b3, 0x000012b4, 0x000012b5, 0x000012b6, 0x000012b7, 0x000012b8, 0x000012b9, 0x000012ba, 0x000012bb, 0x000012bc, 0x000012bd, 0x000012be, 0x000012bf, 0x00001320, 0x000013c2, 0x000013c3, 0x000013c4, 0x000013c5, 0x000013c6, 0x00001447, 0x00001572, 0x00001665, 0x00001765, 0x0000186b, 0x0000193d, 0x00001acd, 0x00001ace, 0x00001acf, 0x00001bb0, 0x00001bb1, 0x00001bb2, 0x00001bb3, 0x00001bb4, 0x00001bb5, 0x00001bb6, 0x00001bb7, 0x00001bb8, 0x00001bb9, 0x00001bba, 0x00001bbb, 0x00001bbc, 0x00001bbd, 0x00001bbe, 0x00001bbf, 0x00001c80, 0x00001c81, 0x00001c82, 0x00001c83, 0x00001c84, 0x00001c85, 0x00001c86, 0x00001c87, 0x00001c88, 0x00001c89, 0x00001c8a, 0x00001c8b, 0x00001c8c, 0x00001c8d, 0x00001c8e, 0x00001c8f, 0x00001c90, 0x00001c91, 0x00001c92, 0x00001c93, 0x00001c94, 0x00001c95, 0x00001c96, 0x00001c97, 0x00001c98, 0x00001c99, 0x00001c9a, 0x00001c9b, 0x00001c9c, 0x00001c9d, 0x00001c9e, 0x00001c9f, 0x00001ca0, 0x00001ca1, 0x00001ca2, 0x00001ca3, 0x00001ca4, 0x00001ca5, 0x00001ca6, 0x00001ca7, 0x00001ca8, 0x00001ca9, 0x00001caa, 0x00001cab, 0x00001cac, 0x00001cad, 0x00001cae, 0x00001caf, 0x00001cb0, 0x00001cb1, 0x00001cb2, 0x00001cb3, 0x00001cb4, 0x00001cb5, 0x00001cb6, 0x00001cb7, 0x00001cb8, 0x00001cb9, 0x00001cba, 0x00001cbb, 0x00001cbc, 0x00001cbd, 0x00001cbe, 0x00001cbf, 0x00001d20, 0x00001dcd, 0x00001dce, 0x00001dcf, 0x00001e43, 0x00001f79, 0x00002072, 0x00002169, 0x0000226c, 0x0000236c, 0x00002469, 0x00002563, 0x0000263d, 0x000027d0, 0x000027d1, 0x000027d2, 0x000027d3, 0x00002880, 0x00002881, 0x00002882, 0x00002883, 0x00002884, 0x00002885, 0x00002886, 0x00002887, 0x00002888, 0x00002889, 0x0000288a, 0x0000288b, 0x0000288c, 0x0000288d, 0x0000288e, 0x0000288f, 0x00002890, 0x00002891, 0x00002892, 0x00002893, 0x00002894, 0x00002895, 0x00002896, 0x00002897, 0x00002898, 0x00002899, 0x0000289a, 0x0000289b, 0x0000289c, 0x0000289d, 0x0000289e, 0x0000289f, 0x000028a0, 0x000028a1, 0x000028a2, 0x000028a3, 0x000028a4, 0x000028a5, 0x000028a6, 0x000028a7, 0x000028a8, 0x000028a9, 0x000028aa, 0x000028ab, 0x000028ac, 0x000028ad, 0x000028ae, 0x000028af, 0x000028b0, 0x000028b1, 0x000028b2, 0x000028b3, 0x000028b4, 0x000028b5, 0x000028b6, 0x000028b7, 0x000028b8, 0x000028b9, 0x000028ba, 0x000028bb, 0x000028bc, 0x000028bd, 0x000028be, 0x000028bf, 0x00002900, 0x00002901, 0x00002902, 0x00002903, 0x00002904, 0x00002905, 0x00002906, 0x00002907, 0x00002908, 0x00002909, 0x0000290a, 0x0000290b, 0x0000290c, 0x0000290d, 0x0000290e, 0x0000290f, 0x00002910, 0x00002911, 0x00002912, 0x00002913, 0x00002914, 0x00002915, 0x00002916, 0x00002917, 0x00002918, 0x00002919, 0x0000291a, 0x0000291b, 0x0000291c, 0x0000291d, 0x0000291e, 0x0000291f, 0x00002920, 0x00002921, 0x00002922, 0x00002923, 0x00002924, 0x00002925, 0x00002926, 0x00002927, 0x00002928, 0x00002929, 0x0000292a, 0x0000292b, 0x0000292c, 0x0000292d, 0x0000292e, 0x0000292f, 0x00002930, 0x00002931, 0x00002932, 0x00002933, 0x00002934, 0x00002935, 0x00002936, 0x00002937, 0x00002938, 0x00002939, 0x0000293a, 0x0000293b, 0x0000293c, 0x0000293d, 0x0000293e, 0x0000293f, 0x00002940, 0x00002941, 0x00002942, 0x00002943, 0x00002944, 0x00002945, 0x00002946, 0x00002947, 0x00002948, 0x00002949, 0x0000294a, 0x0000294b, 0x0000294c, 0x0000294d, 0x0000294e, 0x0000294f, 0x00002950, 0x00002951, 0x00002952, 0x00002953, 0x00002954, 0x00002955, 0x00002956, 0x00002957, 0x00002958, 0x00002959, 0x0000295a, 0x0000295b, 0x0000295c, 0x0000295d, 0x0000295e, 0x0000295f, 0x00002960, 0x00002961, 0x00002962, 0x00002963, 0x00002964, 0x00002965, 0x00002966, 0x00002967, 0x00002968, 0x00002969, 0x0000296a, 0x0000296b, 0x0000296c, 0x0000296d, 0x0000296e, 0x0000296f, 0x00002970, 0x00002971, 0x00002972, 0x00002973, 0x00002974, 0x00002975, 0x00002976, 0x00002977, 0x00002978, 0x00002979, 0x0000297a, 0x0000297b, 0x0000297c, 0x0000297d, 0x0000297e, 0x0000297f, 0x00002980, 0x00002981, 0x00002982, 0x00002983, 0x00002984, 0x00002985, 0x00002986, 0x00002987, 0x00002988, 0x00002989, 0x0000298a, 0x0000298b, 0x0000298c, 0x0000298d, 0x0000298e, 0x0000298f, 0x00002990, 0x00002991, 0x00002992, 0x00002993, 0x00002994, 0x00002995, 0x00002996, 0x00002997, 0x00002998, 0x00002999, 0x0000299a, 0x0000299b, 0x0000299c, 0x0000299d, 0x0000299e, 0x0000299f, 0x000029a0, 0x000029a1, 0x000029a2, 0x000029a3, 0x000029a4, 0x000029a5, 0x000029a6, 0x000029a7, 0x000029a8, 0x000029a9, 0x000029aa, 0x000029ab, 0x000029ac, 0x000029ad, 0x000029ae, 0x000029af, 0x000029b0, 0x000029b1, 0x000029b2, 0x000029b3, 0x000029b4, 0x000029b5, 0x000029b6, 0x000029b7, 0x000029b8, 0x000029b9, 0x000029ba, 0x000029bb, 0x000029bc, 0x000029bd, 0x000029be, 0x000029bf, 0x000029c0, 0x000029c1, 0x000029c2, 0x000029c3, 0x000029c4, 0x000029c5, 0x000029c6, 0x000029c7, 0x000029c8, 0x000029c9, 0x000029ca, 0x000029cb, 0x000029cc, 0x000029cd, 0x000029ce, 0x000029cf, 0x000029d0, 0x000029d0, 0x000029d1, 0x000029d1, 0x000029d2, 0x000029d2, 0x000029d3, 0x000029d3, 0x000029d4, 0x000029d5, 0x000029d6, 0x000029d7, 0x000029d8, 0x000029d9, 0x000029da, 0x000029db, 0x000029dc, 0x000029dd, 0x000029de, 0x000029df, 0x000029e0, 0x000029e1, 0x000029e2, 0x000029e3, 0x000029e4, 0x000029e5, 0x000029e6, 0x000029e7, 0x000029e8, 0x000029e9, 0x000029ea, 0x000029eb, 0x000029ec, 0x000029ed, 0x000029ee, 0x000029ef, 0x000029f0, 0x000029f1, 0x000029f2, 0x000029f3, 0x000029f4, 0x000029f5, 0x000029f6, 0x000029f7, 0x000029f8, 0x000029f9, 0x000029fa, 0x000029fb, 0x000029fc, 0x000029fd, 0x000029fe, 0x00002a00, 0x00002a01, 0x00002a02, 0x00002a03, 0x00002a04, 0x00002a05, 0x00002a06, 0x00002a07, 0x00002a08, 0x00002a09, 0x00002a0a, 0x00002a0b, 0x00002a0c, 0x00002a0d, 0x00002a0e, 0x00002a0f, 0x00002a10, 0x00002a11, 0x00002a12, 0x00002a13, 0x00002a14, 0x00002a15, 0x00002a16, 0x00002a17, 0x00002a18, 0x00002a19, 0x00002a1a, 0x00002a1b, 0x00002a1c, 0x00002a1d, 0x00002a1e, 0x00002a1f, 0x00002a20, 0x00002a21, 0x00002a22, 0x00002a23, 0x00002a24, 0x00002a25, 0x00002a26, 0x00002a27, 0x00002a28, 0x00002a29, 0x00002a2a, 0x00002a2b, 0x00002a2c, 0x00002a2d, 0x00002a2e, 0x00002a2f, 0x00002a30, 0x00002a31, 0x00002a32, 0x00002a33, 0x00002a34, 0x00002a35, 0x00002a36, 0x00002a37, 0x00002a38, 0x00002a39, 0x00002a3a, 0x00002a3b, 0x00002a3c, 0x00002a3d, 0x00002a3e, 0x00002a3f, 0x00002a40, 0x00002a41, 0x00002a42, 0x00002a43, 0x00002a44, 0x00002a45, 0x00002a46, 0x00002a47, 0x00002a48, 0x00002a49, 0x00002a4a, 0x00002a4b, 0x00002a4c, 0x00002a4d, 0x00002a4e, 0x00002a4f, 0x00002a50, 0x00002a51, 0x00002a52, 0x00002a53, 0x00002a54, 0x00002a55, 0x00002a56, 0x00002a57, 0x00002a58, 0x00002a59, 0x00002a5a, 0x00002a5b, 0x00002a5c, 0x00002a5d, 0x00002a5e, 0x00002a5f, 0x00002a60, 0x00002a61, 0x00002a62, 0x00002a63, 0x00002a64, 0x00002a65, 0x00002a66, 0x00002a67, 0x00002a68, 0x00002a69, 0x00002a6a, 0x00002a6b, 0x00002a6c, 0x00002a6d, 0x00002a6e, 0x00002a6f, 0x00002a70, 0x00002a71, 0x00002a72, 0x00002a73, 0x00002a74, 0x00002a75, 0x00002a76, 0x00002a77, 0x00002a78, 0x00002a79, 0x00002a7a, 0x00002a7b, 0x00002a7c, 0x00002a7d, 0x00002a7e, 0x00002a7f, 0x00002a80, 0x00002a81, 0x00002a82, 0x00002a83, 0x00002a84, 0x00002a85, 0x00002a86, 0x00002a87, 0x00002a88, 0x00002a89, 0x00002a8a, 0x00002a8b, 0x00002a8c, 0x00002a8d, 0x00002a8e, 0x00002a8f, 0x00002a90, 0x00002a91, 0x00002a92, 0x00002a93, 0x00002a94, 0x00002a95, 0x00002a96, 0x00002a97, 0x00002a98, 0x00002a99, 0x00002a9a, 0x00002a9b, 0x00002a9c, 0x00002a9d, 0x00002a9e, 0x00002a9f, 0x00002aa0, 0x00002aa1, 0x00002aa2, 0x00002aa3, 0x00002aa4, 0x00002aa5, 0x00002aa6, 0x00002aa7, 0x00002aa8, 0x00002aa9, 0x00002aaa, 0x00002aab, 0x00002aac, 0x00002aad, 0x00002aae, 0x00002aaf, 0x00002ab0, 0x00002ab1, 0x00002ab2, 0x00002ab3, 0x00002ab4, 0x00002ab5, 0x00002ab6, 0x00002ab7, 0x00002ab8, 0x00002ab9, 0x00002aba, 0x00002abb, 0x00002abc, 0x00002abd, 0x00002abe, 0x00002abf, 0x00002ac0, 0x00002ac1, 0x00002ac2, 0x00002ac3, 0x00002ac4, 0x00002ac5, 0x00002ac6, 0x00002ac7, 0x00002ac8, 0x00002ac9, 0x00002aca, 0x00002acb, 0x00002acc, 0x00002acd, 0x00002ace, 0x00002acf, 0x00002ad0, 0x00002ad1, 0x00002ad2, 0x00002ad3, 0x00002ad4, 0x00002ad5, 0x00002ad6, 0x00002ad7, 0x00002ad8, 0x00002ad9, 0x00002ada, 0x00002adb, 0x00002adc, 0x00002add, 0x00002ade, 0x00002adf, 0x00002ae0, 0x00002ae1, 0x00002ae2, 0x00002ae3, 0x00002ae4, 0x00002ae5, 0x00002ae6, 0x00002ae7, 0x00002ae8, 0x00002ae9, 0x00002aea, 0x00002aeb, 0x00002aec, 0x00002aed, 0x00002aee, 0x00002aef, 0x00002af0, 0x00002af1, 0x00002af2, 0x00002af3, 0x00002af4, 0x00002af5, 0x00002af6, 0x00002af7, 0x00002af8, 0x00002af9, 0x00002afa, 0x00002afb, 0x00002afc, 0x00002afd, 0x00002afe, 0x00002aff], + values: [0x00000000, 0x00000000, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000013, 0x0000002a, 0x00000011, 0x0000002a, 0x00000012, 0x0000002a, 0x00000012, 0x0000002a, 0x00000012, 0x0000002a, 0x00000012, 0x0000002a, 0x00000014, 0x0000002a, 0x00000015, 0x0000002a, 0x00000016, 0x0000002a, 0x00000017, 0x0000002a, 0x00000018, 0x0000002a, 0x00000019, 0x0000002a, 0x0000001a, 0x0000002a, 0x0000001b, 0x0000002a, 0x0000001c, 0x0000002a, 0x0000001c, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001d, 0x0000002a, 0x0000001b, 0x0000002a, 0x0000001c, 0x0000002a, 0x0000001c, 0x0000002a, 0x0000001e, 0x0000002a, 0x0000001f, 0x0000002a, 0x00000020, 0x0000002a, 0x00000021, 0x0000002a, 0x00000022, 0x0000002a, 0x00000023, 0x0000002a, 0x00000024, 0x0000002a, 0x00000025, 0x0000002a, 0x00000026, 0x0000002a, 0x00000027, 0x0000002a, 0x00000028, 0x0000002a, 0x00000028, 0x0000002a, 0x00000028, 0x0000002a, 0x00000028, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x0000002a, 0x00000029, 0x00000001, 0x00000029, 0x00000002, 0x00000029, 0x00000003, 0x00000029, 0x00000004, 0x00000029, 0x00000005, 0x00000029, 0x00000006, 0x00000029, 0x00000007, 0x00000029, 0x00000008, 0x00000029, 0x00000009, 0x00000029, 0x0000000a, 0x00000029, 0x0000000b, 0x00000029, 0x0000000c, 0x00000029, 0x0000000d, 0x00000029, 0x0000000e, 0x00000029, 0x0000000f, 0x00000029, 0x00000010, 0x00000029, 0x00000011, 0x00000029, 0x00000012, 0x00000029, 0x00000012, 0x00000029, 0x00000012, 0x00000029, 0x00000012, 0x00000029, 0x00000013, 0x00000029, 0x00000013, 0x00000029, 0x00000013, 0x00000029, 0x00000013, 0x00000029, 0x00000013, 0x00000029, 0x00000013, 0x00000029, 0x00000013, 0x00000029, 0x00000013, 0x00000029, 0x00000013, 0x00000029, 0x00000013, 0x00000029, 0x00000013, 0x00000029, 0x00000013, 0x00000029, 0x00000013, 0x00000029, 0x00000013, 0x00000029, 0x00000013, 0x00000029, 0x00000013, 0x00000029, 0x00000013, 0x00000028, 0x00000013, 0x00000028, 0x00000013, 0x00000028, 0x00000013, 0x00000028, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x0000002a, 0x00000000], + maximum: 0x00002aff +}; + + + +pub fn regex_match(input: [u8; N]) -> BoundedVec { + let substrings = unsafe { __regex_match(input) }; + + // "Previous" state + let mut s: Field = 0; + s = table.get(255); + // "Next"/upcoming state + let mut s_next: Field = 0; + let mut start_range = 0; + let mut end_range = 0; + + // check the match + for i in 0..N { + // state transition + let temp = input[i] as Field; + s_next = table.get(s * 256 + temp); + let potential_s_next = table.get(temp); + if s_next == 0 { + s = 0; + s_next = potential_s_next; + } + std::as_witness(s_next); + + // range conditions for substring matches + if ((start_range == 0) & (end_range == 0)) { + start_range = i as Field; + } + if (((s == 41) & (s_next == 42)) & (end_range == 0)) { + end_range = i as Field + 1; + } + + + let range_0 = substrings.get_unchecked(0).in_range(i); + let case_0 = [ + (s == 16) & ((s_next == 17) | (s_next == 18)), + (s == 19) & ((s_next == 17) | (s_next == 18)), + (s_next == 19) & ((s == 17) | (s == 18)) + ].any(|case| case == true) | !range_0; + + let range_1 = substrings.get_unchecked(1).in_range(i); + let case_1 = [ + (s == 26) & ((s_next == 27) | (s_next == 28)), + (s == 29) & ((s_next == 27) | (s_next == 28)), + (s_next == 29) & ((s == 27) | (s == 28)) + ].any(|case| case == true) | !range_1; + + let range_2 = substrings.get_unchecked(2).in_range(i); + let case_2 = [ + (s_next == 40) & ((s == 39) | (s == 41)), + (s_next == 41) & ((s == 40)) + ].any(|case| case == true) | !range_2; + + + + let substring_range_check = [case_0, case_1, case_2] + .all(|case| case == true); + + assert(substring_range_check, "substr array ranges wrong"); + + + s = s_next; + } + // check final state + + assert((s == 41) | (s == 42), "Match not found"); + + // constrain extracted substrings to be in match range + //let full_match = Sequence::new(start_range as u32, end_range as u32 - start_range as u32); + //let full_match_end = full_match.end(); + // for i in 0..3 { + // let substring = substrings.get_unchecked(i); + // let is_not_valid = i >= substrings.len(); + // let index_check = substring.index >= full_match.index; + // let length_check = substring.end() <= full_match_end; + // let check = (index_check) | is_not_valid; + // assert(check, f"Substring {i} range is out of bounds of the full match found"); + // } + substrings +} + + +pub unconstrained fn __regex_match(input: [u8; N]) -> BoundedVec { + // regex: Latin-Extension=[\u{00a1}-\u{01bf}]+ Greek=[\u{0370}-\u{03ff}]+ Cyrillic=[\u{0400}-\u{04ff}]+ + let mut substrings: BoundedVec = BoundedVec::new(); + let mut current_substring = Sequence::default(); + let mut full_match = Sequence::default(); + + // "Previous" state + let mut s: Field = 0; + s = table.get(255); + // "Next"/upcoming state + let mut s_next: Field = 0; + + let mut consecutive_substr = 0; + let mut complete = false; + + for i in 0..input.len() { + let temp = input[i] as Field; + let mut reset = false; + s_next = table.get(s * 256 + temp); + let potential_s_next = table.get(temp); + if s_next == 0 { + reset = true; + s = 0; + s_next = potential_s_next; + } + // If a substring was in the making, but the state was reset + // we disregard previous progress because apparently it is invalid + if (reset & (consecutive_substr == 1)) { + current_substring = Sequence::default(); + consecutive_substr = 0; + } + // Fill up substrings + + + if ((s == 16) & (s_next == 17) | (s == 16) & (s_next == 18) | (s == 17) & (s_next == 19) | (s == 18) & (s_next == 19) | (s == 19) & (s_next == 17) | (s == 19) & (s_next == 18)) { + + if (consecutive_substr == 0) { + current_substring.index = i; + }; + current_substring.length += 1; + consecutive_substr = 1; + } + + else if ((s == 26) & (s_next == 27) | (s == 26) & (s_next == 28) | (s == 27) & (s_next == 29) | (s == 28) & (s_next == 29) | (s == 29) & (s_next == 27) | (s == 29) & (s_next == 28)) { + + if (consecutive_substr == 0) { + current_substring.index = i; + }; + current_substring.length += 1; + consecutive_substr = 1; + } + + else if ((s == 39) & (s_next == 40) | (s == 40) & (s_next == 41) | (s == 41) & (s_next == 40)) { + + if (consecutive_substr == 0) { + current_substring.index = i; + }; + current_substring.length += 1; + consecutive_substr = 1; + } else if ((consecutive_substr == 1) & (s_next == 0)) { + current_substring = Sequence::default(); + full_match = Sequence::default(); + substrings = BoundedVec::new(); + consecutive_substr = 0; + } else if (s == 41) & (s_next == 42) { + full_match.length = i - full_match.index + 1; + complete = true; + } else if (consecutive_substr == 1) { + // The substring is done so "save" it + substrings.push(current_substring); + // reset the substring holder for next use + current_substring = Sequence::default(); + consecutive_substr = 0; + } + s = s_next; + if complete == true { + break; + } + } + assert((s == 41) | (s == 42), f"no match: {s}"); + // Add pending substring that hasn't been added + if consecutive_substr == 1 { + substrings.push(current_substring); + full_match.length = input.len() - full_match.index; + } + + + + substrings +} + + + + \ No newline at end of file diff --git a/x/transitions.json b/x/transitions.json new file mode 100644 index 00000000..980669b9 --- /dev/null +++ b/x/transitions.json @@ -0,0 +1,10 @@ +{ + "transitions": [ + [[2, 3]], + [ + [6, 7], + [7, 7] + ], + [[8, 9]] + ] +} diff --git a/x/x.json b/x/x.json new file mode 100644 index 00000000..8ca75c31 --- /dev/null +++ b/x/x.json @@ -0,0 +1,29 @@ +{ + "parts": [ + { + "is_public": false, + "regex_def": "Latin-Extension=" + }, + { + "is_public": true, + "regex_def": "[¡-ƿ]+" + }, + { + "is_public": false, + "regex_def": " Greek=" + }, + { + "is_public": true, + "regex_def": "[Ͱ-Ͽ]+" + }, + { + "is_public": false, + "regex_def": " Cyrillic=" + }, + { + "is_public": true, + "regex_def": "[Ѐ-ӿ]+" + } + ] + } + \ No newline at end of file diff --git a/x/z.json b/x/z.json new file mode 100644 index 00000000..11955e95 --- /dev/null +++ b/x/z.json @@ -0,0 +1,8 @@ +{ + "parts": [ + { + "is_public": true, + "regex_def": "a[bc]$" + } + ] +}