diff --git a/.github/actions/restore-python/action.yml b/.github/actions/restore-python/action.yml index 4ad9e2eaed..d3fe2a89dc 100644 --- a/.github/actions/restore-python/action.yml +++ b/.github/actions/restore-python/action.yml @@ -17,7 +17,7 @@ runs: steps: - name: Set up Python ${{ inputs.python-version }} id: python - uses: actions/setup-python@v5.1.0 + uses: actions/setup-python@v5.1.1 with: python-version: ${{ inputs.python-version }} - name: Restore Python virtual environment diff --git a/esphome/components/aht10/aht10.cpp b/esphome/components/aht10/aht10.cpp index 332218b9e9..441c1ac9df 100644 --- a/esphome/components/aht10/aht10.cpp +++ b/esphome/components/aht10/aht10.cpp @@ -93,8 +93,9 @@ void AHT10Component::restart_read_() { void AHT10Component::read_data_() { uint8_t data[6]; - if (this->read_count_ > 1) + if (this->read_count_ > 1) { ESP_LOGD(TAG, "Read attempt %d at %ums", this->read_count_, (unsigned) (millis() - this->start_time_)); + } if (this->read(data, 6) != i2c::ERROR_OK) { this->status_set_warning("AHT10 read failed, retrying soon"); this->restart_read_(); @@ -119,8 +120,9 @@ void AHT10Component::read_data_() { return; } } - if (this->read_count_ > 1) + if (this->read_count_ > 1) { ESP_LOGD(TAG, "Success at %ums", (unsigned) (millis() - this->start_time_)); + } uint32_t raw_temperature = ((data[3] & 0x0F) << 16) | (data[4] << 8) | data[5]; uint32_t raw_humidity = ((data[1] << 16) | (data[2] << 8) | data[3]) >> 4; diff --git a/esphome/components/climate/climate.cpp b/esphome/components/climate/climate.cpp index 1822707152..bc8d932089 100644 --- a/esphome/components/climate/climate.cpp +++ b/esphome/components/climate/climate.cpp @@ -574,21 +574,25 @@ void Climate::dump_traits_(const char *tag) { ESP_LOGCONFIG(tag, " - Max temperature: %.1f", traits.get_visual_max_temperature()); ESP_LOGCONFIG(tag, " - Temperature step:"); ESP_LOGCONFIG(tag, " Target: %.1f", traits.get_visual_target_temperature_step()); - ESP_LOGCONFIG(tag, " Current: %.1f", traits.get_visual_current_temperature_step()); - ESP_LOGCONFIG(tag, " - Min humidity: %.0f", traits.get_visual_min_humidity()); - ESP_LOGCONFIG(tag, " - Max humidity: %.0f", traits.get_visual_max_humidity()); if (traits.get_supports_current_temperature()) { - ESP_LOGCONFIG(tag, " [x] Supports current temperature"); + ESP_LOGCONFIG(tag, " Current: %.1f", traits.get_visual_current_temperature_step()); } - if (traits.get_supports_current_humidity()) { - ESP_LOGCONFIG(tag, " [x] Supports current humidity"); + if (traits.get_supports_target_humidity() || traits.get_supports_current_humidity()) { + ESP_LOGCONFIG(tag, " - Min humidity: %.0f", traits.get_visual_min_humidity()); + ESP_LOGCONFIG(tag, " - Max humidity: %.0f", traits.get_visual_max_humidity()); } if (traits.get_supports_two_point_target_temperature()) { ESP_LOGCONFIG(tag, " [x] Supports two-point target temperature"); } + if (traits.get_supports_current_temperature()) { + ESP_LOGCONFIG(tag, " [x] Supports current temperature"); + } if (traits.get_supports_target_humidity()) { ESP_LOGCONFIG(tag, " [x] Supports target humidity"); } + if (traits.get_supports_current_humidity()) { + ESP_LOGCONFIG(tag, " [x] Supports current humidity"); + } if (traits.get_supports_action()) { ESP_LOGCONFIG(tag, " [x] Supports action"); } diff --git a/esphome/components/climate/climate_traits.h b/esphome/components/climate/climate_traits.h index fd5b025a03..58d7b586d7 100644 --- a/esphome/components/climate/climate_traits.h +++ b/esphome/components/climate/climate_traits.h @@ -73,7 +73,7 @@ class ClimateTraits { ESPDEPRECATED("This method is deprecated, use set_supported_modes() instead", "v1.20") void set_supports_dry_mode(bool supports_dry_mode) { set_mode_support_(CLIMATE_MODE_DRY, supports_dry_mode); } bool supports_mode(ClimateMode mode) const { return supported_modes_.count(mode); } - std::set get_supported_modes() const { return supported_modes_; } + const std::set &get_supported_modes() const { return supported_modes_; } void set_supports_action(bool supports_action) { supports_action_ = supports_action; } bool get_supports_action() const { return supports_action_; } @@ -101,7 +101,7 @@ class ClimateTraits { void set_supports_fan_mode_diffuse(bool supported) { set_fan_mode_support_(CLIMATE_FAN_DIFFUSE, supported); } bool supports_fan_mode(ClimateFanMode fan_mode) const { return supported_fan_modes_.count(fan_mode); } bool get_supports_fan_modes() const { return !supported_fan_modes_.empty() || !supported_custom_fan_modes_.empty(); } - std::set get_supported_fan_modes() const { return supported_fan_modes_; } + const std::set &get_supported_fan_modes() const { return supported_fan_modes_; } void set_supported_custom_fan_modes(std::set supported_custom_fan_modes) { supported_custom_fan_modes_ = std::move(supported_custom_fan_modes); @@ -140,7 +140,7 @@ class ClimateTraits { } bool supports_swing_mode(ClimateSwingMode swing_mode) const { return supported_swing_modes_.count(swing_mode); } bool get_supports_swing_modes() const { return !supported_swing_modes_.empty(); } - std::set get_supported_swing_modes() const { return supported_swing_modes_; } + const std::set &get_supported_swing_modes() const { return supported_swing_modes_; } float get_visual_min_temperature() const { return visual_min_temperature_; } void set_visual_min_temperature(float visual_min_temperature) { visual_min_temperature_ = visual_min_temperature; } diff --git a/esphome/components/ethernet/ethernet_component.cpp b/esphome/components/ethernet/ethernet_component.cpp index 6b34157b9d..962a864a29 100644 --- a/esphome/components/ethernet/ethernet_component.cpp +++ b/esphome/components/ethernet/ethernet_component.cpp @@ -394,7 +394,7 @@ void EthernetComponent::got_ip_event_handler(void *arg, esp_event_base_t event_b const esp_netif_ip_info_t *ip_info = &event->ip_info; ESP_LOGV(TAG, "[Ethernet event] ETH Got IP " IPSTR, IP2STR(&ip_info->ip)); global_eth_component->got_ipv4_address_ = true; -#if USE_NETWORK_IPV6 +#if USE_NETWORK_IPV6 && (USE_NETWORK_MIN_IPV6_ADDR_COUNT > 0) global_eth_component->connected_ = global_eth_component->ipv6_count_ >= USE_NETWORK_MIN_IPV6_ADDR_COUNT; #else global_eth_component->connected_ = true; @@ -407,8 +407,12 @@ void EthernetComponent::got_ip6_event_handler(void *arg, esp_event_base_t event_ ip_event_got_ip6_t *event = (ip_event_got_ip6_t *) event_data; ESP_LOGV(TAG, "[Ethernet event] ETH Got IPv6: " IPV6STR, IPV62STR(event->ip6_info.ip)); global_eth_component->ipv6_count_ += 1; +#if (USE_NETWORK_MIN_IPV6_ADDR_COUNT > 0) global_eth_component->connected_ = global_eth_component->got_ipv4_address_ && (global_eth_component->ipv6_count_ >= USE_NETWORK_MIN_IPV6_ADDR_COUNT); +#else + global_eth_component->connected_ = global_eth_component->got_ipv4_address_; +#endif } #endif /* USE_NETWORK_IPV6 */ diff --git a/esphome/components/http_request/http_request_arduino.cpp b/esphome/components/http_request/http_request_arduino.cpp index 248a85a439..95b1cdc38e 100644 --- a/esphome/components/http_request/http_request_arduino.cpp +++ b/esphome/components/http_request/http_request_arduino.cpp @@ -32,6 +32,13 @@ std::shared_ptr HttpRequestArduino::start(std::string url, std::s watchdog::WatchdogManager wdm(this->get_watchdog_timeout()); + if (this->follow_redirects_) { + container->client_.setFollowRedirects(HTTPC_FORCE_FOLLOW_REDIRECTS); + container->client_.setRedirectLimit(this->redirect_limit_); + } else { + container->client_.setFollowRedirects(HTTPC_DISABLE_FOLLOW_REDIRECTS); + } + #if defined(USE_ESP8266) std::unique_ptr stream_ptr; #ifdef USE_HTTP_REQUEST_ESP8266_HTTPS @@ -59,8 +66,6 @@ std::shared_ptr HttpRequestArduino::start(std::string url, std::s "in your YAML, or use HTTPS"); } #endif // USE_ARDUINO_VERSION_CODE - - container->client_.setFollowRedirects(HTTPC_STRICT_FOLLOW_REDIRECTS); bool status = container->client_.begin(*stream_ptr, url.c_str()); #elif defined(USE_RP2040) diff --git a/esphome/components/micro_wake_word/__init__.py b/esphome/components/micro_wake_word/__init__.py index 35ee3cfedc..3d3459ccab 100644 --- a/esphome/components/micro_wake_word/__init__.py +++ b/esphome/components/micro_wake_word/__init__.py @@ -9,7 +9,7 @@ import requests import esphome.config_validation as cv import esphome.codegen as cg -from esphome.core import CORE, HexInt, EsphomeError +from esphome.core import CORE, HexInt from esphome.components import esp32, microphone from esphome import automation, git, external_files @@ -41,9 +41,15 @@ CODEOWNERS = ["@kahrendt", "@jesserockz"] DEPENDENCIES = ["microphone"] DOMAIN = "micro_wake_word" + +CONF_FEATURE_STEP_SIZE = "feature_step_size" +CONF_MODELS = "models" +CONF_ON_WAKE_WORD_DETECTED = "on_wake_word_detected" CONF_PROBABILITY_CUTOFF = "probability_cutoff" CONF_SLIDING_WINDOW_AVERAGE_SIZE = "sliding_window_average_size" -CONF_ON_WAKE_WORD_DETECTED = "on_wake_word_detected" +CONF_SLIDING_WINDOW_SIZE = "sliding_window_size" +CONF_TENSOR_ARENA_SIZE = "tensor_arena_size" +CONF_VAD = "vad" TYPE_HTTP = "http" @@ -98,12 +104,14 @@ GIT_SCHEMA = cv.All( _process_git_source, ) -KEY_WAKE_WORD = "wake_word" + KEY_AUTHOR = "author" -KEY_WEBSITE = "website" -KEY_VERSION = "version" KEY_MICRO = "micro" KEY_MINIMUM_ESPHOME_VERSION = "minimum_esphome_version" +KEY_TRAINED_LANGUAGES = "trained_languages" +KEY_VERSION = "version" +KEY_WAKE_WORD = "wake_word" +KEY_WEBSITE = "website" MANIFEST_SCHEMA_V1 = cv.Schema( { @@ -125,6 +133,29 @@ MANIFEST_SCHEMA_V1 = cv.Schema( } ) +MANIFEST_SCHEMA_V2 = cv.Schema( + { + cv.Required(CONF_TYPE): "micro", + cv.Required(CONF_MODEL): cv.string, + cv.Required(KEY_AUTHOR): cv.string, + cv.Required(KEY_VERSION): cv.All(cv.int_, 2), + cv.Required(KEY_WAKE_WORD): cv.string, + cv.Required(KEY_TRAINED_LANGUAGES): cv.ensure_list(cv.string), + cv.Optional(KEY_WEBSITE): cv.url, + cv.Required(KEY_MICRO): cv.Schema( + { + cv.Required(CONF_FEATURE_STEP_SIZE): cv.int_range(min=0, max=30), + cv.Required(CONF_TENSOR_ARENA_SIZE): cv.int_, + cv.Required(CONF_PROBABILITY_CUTOFF): cv.float_, + cv.Required(CONF_SLIDING_WINDOW_SIZE): cv.positive_int, + cv.Required(KEY_MINIMUM_ESPHOME_VERSION): cv.All( + cv.version_number, cv.validate_esphome_version + ), + } + ), + } +) + def _compute_local_file_path(config: dict) -> Path: url = config[CONF_URL] @@ -135,6 +166,24 @@ def _compute_local_file_path(config: dict) -> Path: return base_dir / key +def _convert_manifest_v1_to_v2(v1_manifest): + v2_manifest = v1_manifest.copy() + + v2_manifest[KEY_VERSION] = 2 + v2_manifest[KEY_MICRO][CONF_SLIDING_WINDOW_SIZE] = v1_manifest[KEY_MICRO][ + CONF_SLIDING_WINDOW_AVERAGE_SIZE + ] + del v2_manifest[KEY_MICRO][CONF_SLIDING_WINDOW_AVERAGE_SIZE] + v2_manifest[KEY_MICRO][ + CONF_TENSOR_ARENA_SIZE + ] = 45672 # Original Inception-based V1 manifest models require a minimum of 45672 bytes + v2_manifest[KEY_MICRO][ + CONF_FEATURE_STEP_SIZE + ] = 20 # Original Inception-based V1 manifest models use a 20 ms feature step size + + return v2_manifest + + def _download_file(url: str, path: Path) -> bytes: if not external_files.has_remote_file_changed(url, path): _LOGGER.debug("Remote file has not changed, skipping download") @@ -155,6 +204,24 @@ def _download_file(url: str, path: Path) -> bytes: return req.content +def _validate_manifest_version(manifest_data): + if manifest_version := manifest_data.get(KEY_VERSION): + if manifest_version == 1: + try: + MANIFEST_SCHEMA_V1(manifest_data) + except cv.Invalid as e: + raise cv.Invalid(f"Invalid manifest file: {e}") from e + elif manifest_version == 2: + try: + MANIFEST_SCHEMA_V2(manifest_data) + except cv.Invalid as e: + raise cv.Invalid(f"Invalid manifest file: {e}") from e + else: + raise cv.Invalid("Invalid manifest version") + else: + raise cv.Invalid("Invalid manifest file, missing 'version' key.") + + def _process_http_source(config): url = config[CONF_URL] path = _compute_local_file_path(config) @@ -167,11 +234,6 @@ def _process_http_source(config): if not isinstance(manifest_data, dict): raise cv.Invalid("Manifest file must contain a JSON object") - try: - MANIFEST_SCHEMA_V1(manifest_data) - except cv.Invalid as e: - raise cv.Invalid(f"Invalid manifest file: {e}") from e - model = manifest_data[CONF_MODEL] model_url = urljoin(url, model) @@ -206,7 +268,7 @@ def _validate_source_model_name(value): return MODEL_SOURCE_SCHEMA( { CONF_TYPE: TYPE_HTTP, - CONF_URL: f"https://github.com/esphome/micro-wake-word-models/raw/main/models/{value}.json", + CONF_URL: f"https://github.com/esphome/micro-wake-word-models/raw/main/models/v2/{value}.json", } ) @@ -260,18 +322,55 @@ MODEL_SOURCE_SCHEMA = cv.Any( msg="Not a valid model name, local path, http(s) url, or github shorthand", ) +MODEL_SCHEMA = cv.Schema( + { + cv.Optional(CONF_MODEL): MODEL_SOURCE_SCHEMA, + cv.Optional(CONF_PROBABILITY_CUTOFF): cv.percentage, + cv.Optional(CONF_SLIDING_WINDOW_SIZE): cv.positive_int, + cv.GenerateID(CONF_RAW_DATA_ID): cv.declare_id(cg.uint8), + } +) + +# Provide a default VAD model that could be overridden +VAD_MODEL_SCHEMA = MODEL_SCHEMA.extend( + cv.Schema( + { + cv.Optional( + CONF_MODEL, + default="vad", + ): MODEL_SOURCE_SCHEMA, + } + ) +) + + +def _maybe_empty_vad_schema(value): + # Idea borrowed from uart/__init__.py's ``maybe_empty_debug`` function. Accessed 2 July 2024. + # Loads a default VAD model without any parameters overridden. + if value is None: + value = {} + return VAD_MODEL_SCHEMA(value) + + CONFIG_SCHEMA = cv.All( cv.Schema( { cv.GenerateID(): cv.declare_id(MicroWakeWord), cv.GenerateID(CONF_MICROPHONE): cv.use_id(microphone.Microphone), - cv.Optional(CONF_PROBABILITY_CUTOFF): cv.percentage, - cv.Optional(CONF_SLIDING_WINDOW_AVERAGE_SIZE): cv.positive_int, + cv.Required(CONF_MODELS): cv.ensure_list(MODEL_SCHEMA), cv.Optional(CONF_ON_WAKE_WORD_DETECTED): automation.validate_automation( single=True ), - cv.Required(CONF_MODEL): MODEL_SOURCE_SCHEMA, - cv.GenerateID(CONF_RAW_DATA_ID): cv.declare_id(cg.uint8), + cv.Optional(CONF_VAD): _maybe_empty_vad_schema, + cv.Optional(CONF_MODEL): cv.invalid( + f"The {CONF_MODEL} parameter has moved to be a list element under the {CONF_MODELS} parameter." + ), + cv.Optional(CONF_PROBABILITY_CUTOFF): cv.invalid( + f"The {CONF_PROBABILITY_CUTOFF} parameter has moved to be a list element under the {CONF_MODELS} parameter." + ), + cv.Optional(CONF_SLIDING_WINDOW_AVERAGE_SIZE): cv.invalid( + f"The {CONF_SLIDING_WINDOW_AVERAGE_SIZE} parameter has been renamed to {CONF_SLIDING_WINDOW_SIZE} and moved to be a list element under the {CONF_MODELS} parameter." + ), } ).extend(cv.COMPONENT_SCHEMA), cv.only_with_esp_idf, @@ -282,45 +381,20 @@ def _load_model_data(manifest_path: Path): with open(manifest_path, encoding="utf-8") as f: manifest = json.load(f) - try: - MANIFEST_SCHEMA_V1(manifest) - except cv.Invalid as e: - raise EsphomeError(f"Invalid manifest file: {e}") from e + _validate_manifest_version(manifest) model_path = manifest_path.parent / manifest[CONF_MODEL] with open(model_path, "rb") as f: model = f.read() + if manifest.get(KEY_VERSION) == 1: + manifest = _convert_manifest_v1_to_v2(manifest) + return manifest, model -async def to_code(config): - var = cg.new_Pvariable(config[CONF_ID]) - await cg.register_component(var, config) - - mic = await cg.get_variable(config[CONF_MICROPHONE]) - cg.add(var.set_microphone(mic)) - - if on_wake_word_detection_config := config.get(CONF_ON_WAKE_WORD_DETECTED): - await automation.build_automation( - var.get_wake_word_detected_trigger(), - [(cg.std_string, "wake_word")], - on_wake_word_detection_config, - ) - - esp32.add_idf_component( - name="esp-tflite-micro", - repo="https://github.com/espressif/esp-tflite-micro", - ref="v1.3.1", - ) - - cg.add_build_flag("-DTF_LITE_STATIC_MEMORY") - cg.add_build_flag("-DTF_LITE_DISABLE_X86_NEON") - cg.add_build_flag("-DESP_NN") - - model_config = config.get(CONF_MODEL) - data = [] +def _model_config_to_manifest_data(model_config): if model_config[CONF_TYPE] == TYPE_GIT: # compute path to model file key = f"{model_config[CONF_URL]}@{model_config.get(CONF_REF)}" @@ -338,23 +412,95 @@ async def to_code(config): else: raise ValueError("Unsupported config type: {model_config[CONF_TYPE]}") - manifest, data = _load_model_data(file) + return _load_model_data(file) - rhs = [HexInt(x) for x in data] - prog_arr = cg.progmem_array(config[CONF_RAW_DATA_ID], rhs) - cg.add(var.set_model_start(prog_arr)) - probability_cutoff = config.get( - CONF_PROBABILITY_CUTOFF, manifest[KEY_MICRO][CONF_PROBABILITY_CUTOFF] +def _feature_step_size_validate(config): + features_step_size = None + + for model_parameters in config[CONF_MODELS]: + model_config = model_parameters.get(CONF_MODEL) + manifest, _ = _model_config_to_manifest_data(model_config) + + model_step_size = manifest[KEY_MICRO][CONF_FEATURE_STEP_SIZE] + + if features_step_size is None: + features_step_size = model_step_size + elif features_step_size != model_step_size: + raise cv.Invalid("Cannot load models with different features step sizes.") + + +FINAL_VALIDATE_SCHEMA = _feature_step_size_validate + + +async def to_code(config): + var = cg.new_Pvariable(config[CONF_ID]) + await cg.register_component(var, config) + + mic = await cg.get_variable(config[CONF_MICROPHONE]) + cg.add(var.set_microphone(mic)) + + esp32.add_idf_component( + name="esp-tflite-micro", + repo="https://github.com/espressif/esp-tflite-micro", + ref="v1.3.1", ) - cg.add(var.set_probability_cutoff(probability_cutoff)) - sliding_window_average_size = config.get( - CONF_SLIDING_WINDOW_AVERAGE_SIZE, - manifest[KEY_MICRO][CONF_SLIDING_WINDOW_AVERAGE_SIZE], - ) - cg.add(var.set_sliding_window_average_size(sliding_window_average_size)) - cg.add(var.set_wake_word(manifest[KEY_WAKE_WORD])) + cg.add_build_flag("-DTF_LITE_STATIC_MEMORY") + cg.add_build_flag("-DTF_LITE_DISABLE_X86_NEON") + cg.add_build_flag("-DESP_NN") + + if on_wake_word_detection_config := config.get(CONF_ON_WAKE_WORD_DETECTED): + await automation.build_automation( + var.get_wake_word_detected_trigger(), + [(cg.std_string, "wake_word")], + on_wake_word_detection_config, + ) + + if vad_model := config.get(CONF_VAD): + cg.add_define("USE_MICRO_WAKE_WORD_VAD") + + # Use the general model loading code for the VAD codegen + config[CONF_MODELS].append(vad_model) + + for model_parameters in config[CONF_MODELS]: + model_config = model_parameters.get(CONF_MODEL) + data = [] + manifest, data = _model_config_to_manifest_data(model_config) + + rhs = [HexInt(x) for x in data] + prog_arr = cg.progmem_array(model_parameters[CONF_RAW_DATA_ID], rhs) + + probability_cutoff = model_parameters.get( + CONF_PROBABILITY_CUTOFF, manifest[KEY_MICRO][CONF_PROBABILITY_CUTOFF] + ) + sliding_window_size = model_parameters.get( + CONF_SLIDING_WINDOW_SIZE, + manifest[KEY_MICRO][CONF_SLIDING_WINDOW_SIZE], + ) + + if manifest[KEY_WAKE_WORD] == "vad": + cg.add( + var.add_vad_model( + prog_arr, + probability_cutoff, + sliding_window_size, + manifest[KEY_MICRO][CONF_TENSOR_ARENA_SIZE], + ) + ) + else: + cg.add( + var.add_wake_word_model( + prog_arr, + probability_cutoff, + sliding_window_size, + manifest[KEY_WAKE_WORD], + manifest[KEY_MICRO][CONF_TENSOR_ARENA_SIZE], + ) + ) + + cg.add(var.set_features_step_size(manifest[KEY_MICRO][CONF_FEATURE_STEP_SIZE])) + cg.add_library("kahrendt/ESPMicroSpeechFeatures", "1.0.0") MICRO_WAKE_WORD_ACTION_SCHEMA = cv.Schema({cv.GenerateID(): cv.use_id(MicroWakeWord)}) diff --git a/esphome/components/micro_wake_word/audio_preprocessor_int8_model_data.h b/esphome/components/micro_wake_word/audio_preprocessor_int8_model_data.h deleted file mode 100644 index 918e76045f..0000000000 --- a/esphome/components/micro_wake_word/audio_preprocessor_int8_model_data.h +++ /dev/null @@ -1,493 +0,0 @@ -#pragma once - -#ifdef USE_ESP_IDF - -// Converted audio_preprocessor_int8.tflite -// From https://github.com/tensorflow/tflite-micro/tree/main/tensorflow/lite/micro/examples/micro_speech/models accessed -// January 2024 -// -// Copyright 2023 The TensorFlow Authors. All Rights Reserved. -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. - -namespace esphome { -namespace micro_wake_word { - -const unsigned char G_AUDIO_PREPROCESSOR_INT8_TFLITE[] = { - 0x1c, 0x00, 0x00, 0x00, 0x54, 0x46, 0x4c, 0x33, 0x14, 0x00, 0x20, 0x00, 0x1c, 0x00, 0x18, 0x00, 0x14, 0x00, 0x10, - 0x00, 0x0c, 0x00, 0x00, 0x00, 0x08, 0x00, 0x04, 0x00, 0x14, 0x00, 0x00, 0x00, 0x1c, 0x00, 0x00, 0x00, 0x88, 0x00, - 0x00, 0x00, 0xe0, 0x00, 0x00, 0x00, 0x80, 0x0e, 0x00, 0x00, 0x90, 0x0e, 0x00, 0x00, 0xcc, 0x1f, 0x00, 0x00, 0x03, - 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0xe2, 0xeb, 0xff, 0xff, 0x0c, 0x00, 0x00, 0x00, - 0x1c, 0x00, 0x00, 0x00, 0x3c, 0x00, 0x00, 0x00, 0x0f, 0x00, 0x00, 0x00, 0x73, 0x65, 0x72, 0x76, 0x69, 0x6e, 0x67, - 0x5f, 0x64, 0x65, 0x66, 0x61, 0x75, 0x6c, 0x74, 0x00, 0x01, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x94, 0xff, - 0xff, 0xff, 0x2a, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x6f, 0x75, 0x74, 0x70, 0x75, - 0x74, 0x5f, 0x30, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0xc2, 0xf5, 0xff, 0xff, - 0x04, 0x00, 0x00, 0x00, 0x0b, 0x00, 0x00, 0x00, 0x61, 0x75, 0x64, 0x69, 0x6f, 0x5f, 0x66, 0x72, 0x61, 0x6d, 0x65, - 0x00, 0x02, 0x00, 0x00, 0x00, 0x34, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0xdc, 0xff, 0xff, 0xff, 0x2d, 0x00, - 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x13, 0x00, 0x00, 0x00, 0x43, 0x4f, 0x4e, 0x56, 0x45, 0x52, 0x53, 0x49, 0x4f, - 0x4e, 0x5f, 0x4d, 0x45, 0x54, 0x41, 0x44, 0x41, 0x54, 0x41, 0x00, 0x08, 0x00, 0x0c, 0x00, 0x08, 0x00, 0x04, 0x00, - 0x08, 0x00, 0x00, 0x00, 0x2c, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x13, 0x00, 0x00, 0x00, 0x6d, 0x69, 0x6e, - 0x5f, 0x72, 0x75, 0x6e, 0x74, 0x69, 0x6d, 0x65, 0x5f, 0x76, 0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x00, 0x2e, 0x00, - 0x00, 0x00, 0x9c, 0x0d, 0x00, 0x00, 0x94, 0x0d, 0x00, 0x00, 0xc4, 0x09, 0x00, 0x00, 0x6c, 0x09, 0x00, 0x00, 0x48, - 0x09, 0x00, 0x00, 0x34, 0x09, 0x00, 0x00, 0x20, 0x09, 0x00, 0x00, 0x0c, 0x09, 0x00, 0x00, 0xf8, 0x08, 0x00, 0x00, - 0xec, 0x07, 0x00, 0x00, 0x88, 0x07, 0x00, 0x00, 0x24, 0x07, 0x00, 0x00, 0xc0, 0x06, 0x00, 0x00, 0x38, 0x04, 0x00, - 0x00, 0xb0, 0x01, 0x00, 0x00, 0x9c, 0x01, 0x00, 0x00, 0x88, 0x01, 0x00, 0x00, 0x74, 0x01, 0x00, 0x00, 0x60, 0x01, - 0x00, 0x00, 0x4c, 0x01, 0x00, 0x00, 0x44, 0x01, 0x00, 0x00, 0x3c, 0x01, 0x00, 0x00, 0x34, 0x01, 0x00, 0x00, 0x2c, - 0x01, 0x00, 0x00, 0x24, 0x01, 0x00, 0x00, 0x1c, 0x01, 0x00, 0x00, 0x14, 0x01, 0x00, 0x00, 0x0c, 0x01, 0x00, 0x00, - 0x04, 0x01, 0x00, 0x00, 0xfc, 0x00, 0x00, 0x00, 0xf4, 0x00, 0x00, 0x00, 0xec, 0x00, 0x00, 0x00, 0xe4, 0x00, 0x00, - 0x00, 0xdc, 0x00, 0x00, 0x00, 0xd4, 0x00, 0x00, 0x00, 0xcc, 0x00, 0x00, 0x00, 0xc4, 0x00, 0x00, 0x00, 0xbc, 0x00, - 0x00, 0x00, 0xb4, 0x00, 0x00, 0x00, 0xac, 0x00, 0x00, 0x00, 0xa4, 0x00, 0x00, 0x00, 0x9c, 0x00, 0x00, 0x00, 0x94, - 0x00, 0x00, 0x00, 0x8c, 0x00, 0x00, 0x00, 0x6c, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0xf2, 0xf6, 0xff, 0xff, - 0x04, 0x00, 0x00, 0x00, 0x58, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x08, 0x00, 0x0c, 0x00, 0x08, 0x00, 0x04, - 0x00, 0x08, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00, 0x08, 0x00, 0x0c, 0x00, 0x08, 0x00, - 0x07, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x0a, 0x00, 0x10, 0x00, 0x0c, 0x00, 0x08, 0x00, 0x04, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, - 0x02, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x32, 0x2e, 0x31, 0x32, 0x2e, 0x30, 0x00, - 0x00, 0x56, 0xf7, 0xff, 0xff, 0x04, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x32, 0x2e, 0x38, 0x2e, 0x30, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xd4, 0xe1, 0xff, 0xff, 0xd8, 0xe1, 0xff, 0xff, 0xdc, - 0xe1, 0xff, 0xff, 0xe0, 0xe1, 0xff, 0xff, 0xe4, 0xe1, 0xff, 0xff, 0xe8, 0xe1, 0xff, 0xff, 0xec, 0xe1, 0xff, 0xff, - 0xf0, 0xe1, 0xff, 0xff, 0xf4, 0xe1, 0xff, 0xff, 0xf8, 0xe1, 0xff, 0xff, 0xfc, 0xe1, 0xff, 0xff, 0x00, 0xe2, 0xff, - 0xff, 0x04, 0xe2, 0xff, 0xff, 0x08, 0xe2, 0xff, 0xff, 0x0c, 0xe2, 0xff, 0xff, 0x10, 0xe2, 0xff, 0xff, 0x14, 0xe2, - 0xff, 0xff, 0x18, 0xe2, 0xff, 0xff, 0x1c, 0xe2, 0xff, 0xff, 0x20, 0xe2, 0xff, 0xff, 0x24, 0xe2, 0xff, 0xff, 0x28, - 0xe2, 0xff, 0xff, 0x2c, 0xe2, 0xff, 0xff, 0x30, 0xe2, 0xff, 0xff, 0xd2, 0xf7, 0xff, 0xff, 0x04, 0x00, 0x00, 0x00, - 0x04, 0x00, 0x00, 0x00, 0x9a, 0x02, 0x00, 0x00, 0xe2, 0xf7, 0xff, 0xff, 0x04, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, - 0x00, 0x00, 0x01, 0x00, 0x00, 0xf2, 0xf7, 0xff, 0xff, 0x04, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x80, 0xff, - 0xff, 0xff, 0x02, 0xf8, 0xff, 0xff, 0x04, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x12, - 0xf8, 0xff, 0xff, 0x04, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x7f, 0x00, 0x00, 0x00, 0x22, 0xf8, 0xff, 0xff, - 0x04, 0x00, 0x00, 0x00, 0x78, 0x02, 0x00, 0x00, 0x00, 0x00, 0x61, 0x05, 0x00, 0x00, 0x00, 0x00, 0x23, 0x0b, 0x41, - 0x01, 0x00, 0x00, 0x00, 0x00, 0xb3, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x74, 0x0e, 0x80, 0x05, - 0x00, 0x00, 0x00, 0x00, 0xd1, 0x0c, 0x63, 0x04, 0x00, 0x00, 0x00, 0x00, 0x34, 0x0c, 0x3f, 0x04, 0x00, 0x00, 0x00, - 0x00, 0x81, 0x0c, 0xf7, 0x04, 0x00, 0x00, 0x00, 0x00, 0x9f, 0x0d, 0x77, 0x06, 0x00, 0x00, 0x00, 0x00, 0x7b, 0x0f, - 0xa9, 0x08, 0x01, 0x02, 0x7f, 0x0b, 0x22, 0x05, 0x00, 0x00, 0x00, 0x00, 0xe9, 0x0e, 0xd1, 0x08, 0xdb, 0x02, 0x00, - 0x00, 0x00, 0x00, 0x03, 0x0d, 0x4a, 0x07, 0xad, 0x01, 0x2c, 0x0c, 0xc6, 0x06, 0x79, 0x01, 0x00, 0x00, 0x00, 0x00, - 0x45, 0x0c, 0x29, 0x07, 0x23, 0x02, 0x34, 0x0d, 0x5b, 0x08, 0x96, 0x03, 0x00, 0x00, 0x00, 0x00, 0xe5, 0x0e, 0x48, - 0x0a, 0xbd, 0x05, 0x45, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xde, 0x0c, 0x88, 0x08, 0x43, 0x04, - 0x0e, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xe9, 0x0b, 0xd3, 0x07, 0xcb, 0x03, 0xd2, 0x0f, 0xe7, - 0x0b, 0x09, 0x08, 0x39, 0x04, 0x76, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xbf, 0x0c, 0x14, 0x09, - 0x75, 0x05, 0xe2, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x5a, 0x0e, 0xdd, 0x0a, 0x6b, 0x07, 0x03, - 0x04, 0xa6, 0x00, 0x00, 0x00, 0x00, 0x00, 0x53, 0x0d, 0x09, 0x0a, 0xc9, 0x06, 0x93, 0x03, 0x65, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x41, 0x0d, 0x25, 0x0a, 0x12, 0x07, 0x07, 0x04, 0x05, 0x01, 0x00, 0x00, 0x00, - 0x00, 0x0a, 0x0e, 0x17, 0x0b, 0x2c, 0x08, 0x49, 0x05, 0x6d, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x98, 0x0f, 0xcb, 0x0c, 0x04, 0x0a, 0x44, 0x07, 0x8b, 0x04, 0xd8, 0x01, 0x00, 0x00, 0x00, 0x00, 0x2c, 0x0f, 0x87, - 0x0c, 0xe7, 0x09, 0x4e, 0x07, 0xba, 0x04, 0x2d, 0x02, 0x00, 0x00, 0x00, 0x00, 0xa5, 0x0f, 0x23, 0x0d, 0xa7, 0x0a, - 0x30, 0x08, 0xbe, 0x05, 0x52, 0x03, 0xeb, 0x00, 0x89, 0x0e, 0x2c, 0x0c, 0xd4, 0x09, 0x81, 0x07, 0x33, 0x05, 0xe9, - 0x02, 0xa5, 0x00, 0x00, 0x00, 0x00, 0x00, 0x64, 0x0e, 0x29, 0x0c, 0xf1, 0x09, 0xbe, 0x07, 0x90, 0x05, 0x65, 0x03, - 0x3f, 0x01, 0x1d, 0x0f, 0xff, 0x0c, 0xe5, 0x0a, 0xcf, 0x08, 0xbc, 0x06, 0xae, 0x04, 0xa3, 0x02, 0x9c, 0x00, 0x99, - 0x0e, 0x99, 0x0c, 0x9d, 0x0a, 0xa4, 0x08, 0xaf, 0x06, 0xbd, 0x04, 0xcf, 0x02, 0xe4, 0x00, 0xfc, 0x0e, 0x17, 0x0d, - 0x36, 0x0b, 0x57, 0x09, 0x7c, 0x07, 0xa4, 0x05, 0xcf, 0x03, 0xfd, 0x01, 0x2e, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x62, 0x0e, 0x98, 0x0c, 0xd2, 0x0a, 0x0e, 0x09, 0x4d, 0x07, 0x8f, 0x05, 0xd4, 0x03, 0x1b, 0x02, - 0x65, 0x00, 0x00, 0x00, 0x00, 0x00, 0xb1, 0x0e, 0x00, 0x0d, 0x52, 0x0b, 0xa6, 0x09, 0xfd, 0x07, 0x56, 0x06, 0xb1, - 0x04, 0x0f, 0x03, 0x6f, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xd2, 0x0f, 0x37, 0x0e, 0x9e, 0x0c, - 0x08, 0x0b, 0x73, 0x09, 0xe1, 0x07, 0x52, 0x06, 0xc4, 0x04, 0x38, 0x03, 0xaf, 0x01, 0x28, 0x00, 0xa3, 0x0e, 0x1f, - 0x0d, 0x9e, 0x0b, 0x1f, 0x0a, 0xa2, 0x08, 0x27, 0x07, 0xae, 0x05, 0x37, 0x04, 0xc2, 0x02, 0x4e, 0x01, 0x00, 0x00, - 0x00, 0x00, 0xdd, 0x0f, 0x6d, 0x0e, 0xff, 0x0c, 0x93, 0x0b, 0x29, 0x0a, 0xc1, 0x08, 0x5a, 0x07, 0xf5, 0x05, 0x92, - 0x04, 0x30, 0x03, 0xd1, 0x01, 0x73, 0x00, 0x16, 0x0f, 0xbc, 0x0d, 0x62, 0x0c, 0x0b, 0x0b, 0xb5, 0x09, 0x61, 0x08, - 0x0e, 0x07, 0xbd, 0x05, 0x6d, 0x04, 0x1f, 0x03, 0xd3, 0x01, 0x88, 0x00, 0x3e, 0x0f, 0xf6, 0x0d, 0xaf, 0x0c, 0x6a, - 0x0b, 0x27, 0x0a, 0xe4, 0x08, 0xa3, 0x07, 0x64, 0x06, 0x26, 0x05, 0xe9, 0x03, 0xae, 0x02, 0x74, 0x01, 0x3b, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x0f, 0xce, 0x0d, 0x99, 0x0c, 0x66, 0x0b, 0x34, 0x0a, 0x03, - 0x09, 0xd3, 0x07, 0xa5, 0x06, 0x78, 0x05, 0x4c, 0x04, 0x22, 0x03, 0xf8, 0x01, 0xd0, 0x00, 0x00, 0x00, 0x00, 0x00, - 0xa9, 0x0f, 0x83, 0x0e, 0x5f, 0x0d, 0x3b, 0x0c, 0x19, 0x0b, 0xf8, 0x09, 0xd8, 0x08, 0xb9, 0x07, 0x9b, 0x06, 0x7e, - 0x05, 0x63, 0x04, 0x48, 0x03, 0x2f, 0x02, 0x17, 0x01, 0x00, 0x00, 0x00, 0x00, 0xa6, 0xfa, 0xff, 0xff, 0x04, 0x00, - 0x00, 0x00, 0x78, 0x02, 0x00, 0x00, 0x00, 0x00, 0x9e, 0x0a, 0x00, 0x00, 0x00, 0x00, 0xdc, 0x04, 0xbe, 0x0e, 0x00, - 0x00, 0x00, 0x00, 0x4c, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x8b, 0x01, 0x7f, 0x0a, 0x00, 0x00, - 0x00, 0x00, 0x2e, 0x03, 0x9c, 0x0b, 0x00, 0x00, 0x00, 0x00, 0xcb, 0x03, 0xc0, 0x0b, 0x00, 0x00, 0x00, 0x00, 0x7e, - 0x03, 0x08, 0x0b, 0x00, 0x00, 0x00, 0x00, 0x60, 0x02, 0x88, 0x09, 0x00, 0x00, 0x00, 0x00, 0x84, 0x00, 0x56, 0x07, - 0xfe, 0x0d, 0x80, 0x04, 0xdd, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x16, 0x01, 0x2e, 0x07, 0x24, 0x0d, 0x00, 0x00, 0x00, - 0x00, 0xfc, 0x02, 0xb5, 0x08, 0x52, 0x0e, 0xd3, 0x03, 0x39, 0x09, 0x86, 0x0e, 0x00, 0x00, 0x00, 0x00, 0xba, 0x03, - 0xd6, 0x08, 0xdc, 0x0d, 0xcb, 0x02, 0xa4, 0x07, 0x69, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x1a, 0x01, 0xb7, 0x05, 0x42, - 0x0a, 0xba, 0x0e, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x21, 0x03, 0x77, 0x07, 0xbc, 0x0b, 0xf1, 0x0f, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x16, 0x04, 0x2c, 0x08, 0x34, 0x0c, 0x2d, 0x00, 0x18, 0x04, 0xf6, - 0x07, 0xc6, 0x0b, 0x89, 0x0f, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x03, 0xeb, 0x06, 0x8a, 0x0a, - 0x1d, 0x0e, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xa5, 0x01, 0x22, 0x05, 0x94, 0x08, 0xfc, 0x0b, 0x59, - 0x0f, 0x00, 0x00, 0x00, 0x00, 0xac, 0x02, 0xf6, 0x05, 0x36, 0x09, 0x6c, 0x0c, 0x9a, 0x0f, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0xbe, 0x02, 0xda, 0x05, 0xed, 0x08, 0xf8, 0x0b, 0xfa, 0x0e, 0x00, 0x00, 0x00, 0x00, 0xf5, - 0x01, 0xe8, 0x04, 0xd3, 0x07, 0xb6, 0x0a, 0x92, 0x0d, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x67, 0x00, - 0x34, 0x03, 0xfb, 0x05, 0xbb, 0x08, 0x74, 0x0b, 0x27, 0x0e, 0x00, 0x00, 0x00, 0x00, 0xd3, 0x00, 0x78, 0x03, 0x18, - 0x06, 0xb1, 0x08, 0x45, 0x0b, 0xd2, 0x0d, 0x00, 0x00, 0x00, 0x00, 0x5a, 0x00, 0xdc, 0x02, 0x58, 0x05, 0xcf, 0x07, - 0x41, 0x0a, 0xad, 0x0c, 0x14, 0x0f, 0x76, 0x01, 0xd3, 0x03, 0x2b, 0x06, 0x7e, 0x08, 0xcc, 0x0a, 0x16, 0x0d, 0x5a, - 0x0f, 0x00, 0x00, 0x00, 0x00, 0x9b, 0x01, 0xd6, 0x03, 0x0e, 0x06, 0x41, 0x08, 0x6f, 0x0a, 0x9a, 0x0c, 0xc0, 0x0e, - 0xe2, 0x00, 0x00, 0x03, 0x1a, 0x05, 0x30, 0x07, 0x43, 0x09, 0x51, 0x0b, 0x5c, 0x0d, 0x63, 0x0f, 0x66, 0x01, 0x66, - 0x03, 0x62, 0x05, 0x5b, 0x07, 0x50, 0x09, 0x42, 0x0b, 0x30, 0x0d, 0x1b, 0x0f, 0x03, 0x01, 0xe8, 0x02, 0xc9, 0x04, - 0xa8, 0x06, 0x83, 0x08, 0x5b, 0x0a, 0x30, 0x0c, 0x02, 0x0e, 0xd1, 0x0f, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x9d, 0x01, 0x67, 0x03, 0x2d, 0x05, 0xf1, 0x06, 0xb2, 0x08, 0x70, 0x0a, 0x2b, 0x0c, 0xe4, 0x0d, 0x9a, 0x0f, - 0x00, 0x00, 0x00, 0x00, 0x4e, 0x01, 0xff, 0x02, 0xad, 0x04, 0x59, 0x06, 0x02, 0x08, 0xa9, 0x09, 0x4e, 0x0b, 0xf0, - 0x0c, 0x90, 0x0e, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x2d, 0x00, 0xc8, 0x01, 0x61, 0x03, 0xf7, 0x04, - 0x8c, 0x06, 0x1e, 0x08, 0xad, 0x09, 0x3b, 0x0b, 0xc7, 0x0c, 0x50, 0x0e, 0xd7, 0x0f, 0x5c, 0x01, 0xe0, 0x02, 0x61, - 0x04, 0xe0, 0x05, 0x5d, 0x07, 0xd8, 0x08, 0x51, 0x0a, 0xc8, 0x0b, 0x3d, 0x0d, 0xb1, 0x0e, 0x00, 0x00, 0x00, 0x00, - 0x22, 0x00, 0x92, 0x01, 0x00, 0x03, 0x6c, 0x04, 0xd6, 0x05, 0x3e, 0x07, 0xa5, 0x08, 0x0a, 0x0a, 0x6d, 0x0b, 0xcf, - 0x0c, 0x2e, 0x0e, 0x8c, 0x0f, 0xe9, 0x00, 0x43, 0x02, 0x9d, 0x03, 0xf4, 0x04, 0x4a, 0x06, 0x9e, 0x07, 0xf1, 0x08, - 0x42, 0x0a, 0x92, 0x0b, 0xe0, 0x0c, 0x2c, 0x0e, 0x77, 0x0f, 0xc1, 0x00, 0x09, 0x02, 0x50, 0x03, 0x95, 0x04, 0xd8, - 0x05, 0x1b, 0x07, 0x5c, 0x08, 0x9b, 0x09, 0xd9, 0x0a, 0x16, 0x0c, 0x51, 0x0d, 0x8b, 0x0e, 0xc4, 0x0f, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xfb, 0x00, 0x31, 0x02, 0x66, 0x03, 0x99, 0x04, 0xcb, 0x05, 0xfc, 0x06, 0x2c, - 0x08, 0x5a, 0x09, 0x87, 0x0a, 0xb3, 0x0b, 0xdd, 0x0c, 0x07, 0x0e, 0x2f, 0x0f, 0x00, 0x00, 0x00, 0x00, 0x56, 0x00, - 0x7c, 0x01, 0xa0, 0x02, 0xc4, 0x03, 0xe6, 0x04, 0x07, 0x06, 0x27, 0x07, 0x46, 0x08, 0x64, 0x09, 0x81, 0x0a, 0x9c, - 0x0b, 0xb7, 0x0c, 0xd0, 0x0d, 0xe8, 0x0e, 0x00, 0x10, 0x00, 0x00, 0x2a, 0xfd, 0xff, 0xff, 0x04, 0x00, 0x00, 0x00, - 0x52, 0x00, 0x00, 0x00, 0x04, 0x00, 0x06, 0x00, 0x08, 0x00, 0x08, 0x00, 0x0a, 0x00, 0x0c, 0x00, 0x0e, 0x00, 0x10, - 0x00, 0x12, 0x00, 0x16, 0x00, 0x18, 0x00, 0x1a, 0x00, 0x1e, 0x00, 0x20, 0x00, 0x24, 0x00, 0x26, 0x00, 0x2a, 0x00, - 0x2e, 0x00, 0x32, 0x00, 0x36, 0x00, 0x3a, 0x00, 0x40, 0x00, 0x44, 0x00, 0x4a, 0x00, 0x4e, 0x00, 0x54, 0x00, 0x5a, - 0x00, 0x62, 0x00, 0x68, 0x00, 0x70, 0x00, 0x78, 0x00, 0x80, 0x00, 0x88, 0x00, 0x92, 0x00, 0x9a, 0x00, 0xa6, 0x00, - 0xb0, 0x00, 0xbc, 0x00, 0xc8, 0x00, 0xd4, 0x00, 0xe2, 0x00, 0x00, 0x00, 0x8a, 0xfd, 0xff, 0xff, 0x04, 0x00, 0x00, - 0x00, 0x52, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x08, 0x00, 0x0c, 0x00, 0x10, 0x00, 0x14, 0x00, 0x18, 0x00, - 0x1c, 0x00, 0x20, 0x00, 0x24, 0x00, 0x28, 0x00, 0x2c, 0x00, 0x30, 0x00, 0x34, 0x00, 0x38, 0x00, 0x3c, 0x00, 0x44, - 0x00, 0x4c, 0x00, 0x50, 0x00, 0x58, 0x00, 0x60, 0x00, 0x68, 0x00, 0x70, 0x00, 0x78, 0x00, 0x80, 0x00, 0x88, 0x00, - 0x90, 0x00, 0x98, 0x00, 0xa0, 0x00, 0xa8, 0x00, 0xb0, 0x00, 0xb8, 0x00, 0xc4, 0x00, 0xd0, 0x00, 0xdc, 0x00, 0xe8, - 0x00, 0xf4, 0x00, 0x00, 0x01, 0x0c, 0x01, 0x1c, 0x01, 0x2c, 0x01, 0x00, 0x00, 0xea, 0xfd, 0xff, 0xff, 0x04, 0x00, - 0x00, 0x00, 0x52, 0x00, 0x00, 0x00, 0x04, 0x00, 0x04, 0x00, 0x04, 0x00, 0x04, 0x00, 0x04, 0x00, 0x04, 0x00, 0x04, - 0x00, 0x04, 0x00, 0x04, 0x00, 0x04, 0x00, 0x04, 0x00, 0x04, 0x00, 0x04, 0x00, 0x04, 0x00, 0x04, 0x00, 0x08, 0x00, - 0x08, 0x00, 0x04, 0x00, 0x08, 0x00, 0x08, 0x00, 0x08, 0x00, 0x08, 0x00, 0x08, 0x00, 0x08, 0x00, 0x08, 0x00, 0x08, - 0x00, 0x08, 0x00, 0x08, 0x00, 0x08, 0x00, 0x08, 0x00, 0x08, 0x00, 0x0c, 0x00, 0x0c, 0x00, 0x0c, 0x00, 0x0c, 0x00, - 0x0c, 0x00, 0x0c, 0x00, 0x0c, 0x00, 0x10, 0x00, 0x10, 0x00, 0x10, 0x00, 0x00, 0x00, 0x4a, 0xfe, 0xff, 0xff, 0x04, - 0x00, 0x00, 0x00, 0xfa, 0x00, 0x00, 0x00, 0x7c, 0x7f, 0x79, 0x7f, 0x76, 0x7f, 0xfa, 0xff, 0x00, 0x00, 0x00, 0x00, - 0x70, 0x7f, 0xf4, 0xff, 0x00, 0x00, 0x00, 0x00, 0x64, 0x7f, 0xe9, 0xff, 0xfe, 0xff, 0x00, 0x00, 0x4b, 0x7f, 0xd0, - 0xff, 0x00, 0x00, 0x00, 0x00, 0x1b, 0x7f, 0xa0, 0xff, 0x00, 0x00, 0x00, 0x00, 0xbb, 0x7e, 0x42, 0xff, 0x00, 0x00, - 0x00, 0x00, 0xfd, 0x7d, 0x86, 0xfe, 0x04, 0x00, 0x00, 0x00, 0x87, 0x7c, 0x1d, 0xfd, 0x12, 0x00, 0x00, 0x00, 0xb6, - 0x79, 0x7f, 0xfa, 0x3e, 0x00, 0x00, 0x00, 0x73, 0x74, 0xf9, 0xf5, 0xca, 0x00, 0x00, 0x00, 0x36, 0x6b, 0x33, 0xef, - 0x32, 0x02, 0x00, 0x00, 0x9b, 0x5c, 0x87, 0xe7, 0xce, 0x04, 0x00, 0x00, 0xf0, 0x48, 0xde, 0xe2, 0xa0, 0x07, 0x00, - 0x00, 0x6e, 0x33, 0x8a, 0xe4, 0xa4, 0x08, 0x00, 0x00, 0x9c, 0x20, 0x22, 0xeb, 0x4c, 0x07, 0x00, 0x00, 0x0a, 0x13, - 0x7d, 0xf2, 0x02, 0x05, 0x00, 0x00, 0x89, 0x0a, 0x17, 0xf8, 0x06, 0x03, 0x00, 0x00, 0xa6, 0x05, 0xa0, 0xfb, 0xb4, - 0x01, 0x00, 0x00, 0xfa, 0x02, 0xac, 0xfd, 0xe8, 0x00, 0x00, 0x00, 0x8e, 0x01, 0xc7, 0xfe, 0x7a, 0x00, 0x00, 0x00, - 0xcf, 0x00, 0x5c, 0xff, 0x40, 0x00, 0x00, 0x00, 0x6b, 0x00, 0xab, 0xff, 0x22, 0x00, 0x00, 0x00, 0x38, 0x00, 0xd3, - 0xff, 0x12, 0x00, 0x00, 0x00, 0x1d, 0x00, 0xea, 0xff, 0x08, 0x00, 0x00, 0x00, 0x0f, 0x00, 0xf3, 0xff, 0x06, 0x00, - 0x00, 0x00, 0x08, 0x00, 0xf8, 0xff, 0x04, 0x00, 0x00, 0x00, 0x04, 0x00, 0xfe, 0xff, 0x00, 0x00, 0x00, 0x00, 0x02, - 0x00, 0xfd, 0xff, 0x02, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0xfd, 0xff, - 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x52, 0xff, 0xff, 0xff, 0x04, 0x00, 0x00, - 0x00, 0x04, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x62, 0xff, 0xff, 0xff, 0x04, 0x00, 0x00, 0x00, 0x04, 0x00, - 0x00, 0x00, 0xf1, 0x00, 0x00, 0x00, 0x72, 0xff, 0xff, 0xff, 0x04, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x01, - 0x00, 0x00, 0x00, 0x82, 0xff, 0xff, 0xff, 0x04, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x4d, 0x01, 0x00, 0x00, - 0x92, 0xff, 0xff, 0xff, 0x04, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xb2, 0xff, 0xff, 0xff, 0x04, 0x00, - 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x08, 0x00, - 0x04, 0x00, 0x06, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0xc0, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, - 0x00, 0x02, 0x00, 0x04, 0x00, 0x05, 0x00, 0x07, 0x00, 0x0a, 0x00, 0x0d, 0x00, 0x10, 0x00, 0x13, 0x00, 0x17, 0x00, - 0x1b, 0x00, 0x20, 0x00, 0x25, 0x00, 0x2a, 0x00, 0x30, 0x00, 0x35, 0x00, 0x3c, 0x00, 0x42, 0x00, 0x49, 0x00, 0x51, - 0x00, 0x58, 0x00, 0x60, 0x00, 0x68, 0x00, 0x71, 0x00, 0x7a, 0x00, 0x83, 0x00, 0x8d, 0x00, 0x97, 0x00, 0xa1, 0x00, - 0xac, 0x00, 0xb7, 0x00, 0xc2, 0x00, 0xcd, 0x00, 0xd9, 0x00, 0xe5, 0x00, 0xf2, 0x00, 0xff, 0x00, 0x0c, 0x01, 0x19, - 0x01, 0x27, 0x01, 0x35, 0x01, 0x43, 0x01, 0x52, 0x01, 0x61, 0x01, 0x70, 0x01, 0x7f, 0x01, 0x8f, 0x01, 0x9f, 0x01, - 0xaf, 0x01, 0xc0, 0x01, 0xd1, 0x01, 0xe2, 0x01, 0xf3, 0x01, 0x05, 0x02, 0x17, 0x02, 0x29, 0x02, 0x3c, 0x02, 0x4e, - 0x02, 0x61, 0x02, 0x75, 0x02, 0x88, 0x02, 0x9c, 0x02, 0xb0, 0x02, 0xc4, 0x02, 0xd8, 0x02, 0xed, 0x02, 0x02, 0x03, - 0x17, 0x03, 0x2c, 0x03, 0x41, 0x03, 0x57, 0x03, 0x6d, 0x03, 0x83, 0x03, 0x99, 0x03, 0xb0, 0x03, 0xc7, 0x03, 0xdd, - 0x03, 0xf4, 0x03, 0x0c, 0x04, 0x23, 0x04, 0x3b, 0x04, 0x52, 0x04, 0x6a, 0x04, 0x82, 0x04, 0x9a, 0x04, 0xb3, 0x04, - 0xcb, 0x04, 0xe4, 0x04, 0xfd, 0x04, 0x16, 0x05, 0x2f, 0x05, 0x48, 0x05, 0x61, 0x05, 0x7a, 0x05, 0x94, 0x05, 0xad, - 0x05, 0xc7, 0x05, 0xe1, 0x05, 0xfb, 0x05, 0x15, 0x06, 0x2f, 0x06, 0x49, 0x06, 0x63, 0x06, 0x7e, 0x06, 0x98, 0x06, - 0xb2, 0x06, 0xcd, 0x06, 0xe7, 0x06, 0x02, 0x07, 0x1d, 0x07, 0x37, 0x07, 0x52, 0x07, 0x6d, 0x07, 0x87, 0x07, 0xa2, - 0x07, 0xbd, 0x07, 0xd8, 0x07, 0xf3, 0x07, 0x0d, 0x08, 0x28, 0x08, 0x43, 0x08, 0x5e, 0x08, 0x79, 0x08, 0x93, 0x08, - 0xae, 0x08, 0xc9, 0x08, 0xe3, 0x08, 0xfe, 0x08, 0x19, 0x09, 0x33, 0x09, 0x4e, 0x09, 0x68, 0x09, 0x82, 0x09, 0x9d, - 0x09, 0xb7, 0x09, 0xd1, 0x09, 0xeb, 0x09, 0x05, 0x0a, 0x1f, 0x0a, 0x39, 0x0a, 0x53, 0x0a, 0x6c, 0x0a, 0x86, 0x0a, - 0x9f, 0x0a, 0xb8, 0x0a, 0xd1, 0x0a, 0xea, 0x0a, 0x03, 0x0b, 0x1c, 0x0b, 0x35, 0x0b, 0x4d, 0x0b, 0x66, 0x0b, 0x7e, - 0x0b, 0x96, 0x0b, 0xae, 0x0b, 0xc5, 0x0b, 0xdd, 0x0b, 0xf4, 0x0b, 0x0c, 0x0c, 0x23, 0x0c, 0x39, 0x0c, 0x50, 0x0c, - 0x67, 0x0c, 0x7d, 0x0c, 0x93, 0x0c, 0xa9, 0x0c, 0xbf, 0x0c, 0xd4, 0x0c, 0xe9, 0x0c, 0xfe, 0x0c, 0x13, 0x0d, 0x28, - 0x0d, 0x3c, 0x0d, 0x50, 0x0d, 0x64, 0x0d, 0x78, 0x0d, 0x8b, 0x0d, 0x9f, 0x0d, 0xb2, 0x0d, 0xc4, 0x0d, 0xd7, 0x0d, - 0xe9, 0x0d, 0xfb, 0x0d, 0x0d, 0x0e, 0x1e, 0x0e, 0x2f, 0x0e, 0x40, 0x0e, 0x51, 0x0e, 0x61, 0x0e, 0x71, 0x0e, 0x81, - 0x0e, 0x90, 0x0e, 0x9f, 0x0e, 0xae, 0x0e, 0xbd, 0x0e, 0xcb, 0x0e, 0xd9, 0x0e, 0xe7, 0x0e, 0xf4, 0x0e, 0x01, 0x0f, - 0x0e, 0x0f, 0x1b, 0x0f, 0x27, 0x0f, 0x33, 0x0f, 0x3e, 0x0f, 0x49, 0x0f, 0x54, 0x0f, 0x5f, 0x0f, 0x69, 0x0f, 0x73, - 0x0f, 0x7d, 0x0f, 0x86, 0x0f, 0x8f, 0x0f, 0x98, 0x0f, 0xa0, 0x0f, 0xa8, 0x0f, 0xaf, 0x0f, 0xb7, 0x0f, 0xbe, 0x0f, - 0xc4, 0x0f, 0xcb, 0x0f, 0xd0, 0x0f, 0xd6, 0x0f, 0xdb, 0x0f, 0xe0, 0x0f, 0xe5, 0x0f, 0xe9, 0x0f, 0xed, 0x0f, 0xf0, - 0x0f, 0xf3, 0x0f, 0xf6, 0x0f, 0xf9, 0x0f, 0xfb, 0x0f, 0xfc, 0x0f, 0xfe, 0x0f, 0xff, 0x0f, 0x00, 0x10, 0x00, 0x10, - 0x00, 0x10, 0x00, 0x10, 0xff, 0x0f, 0xfe, 0x0f, 0xfc, 0x0f, 0xfb, 0x0f, 0xf9, 0x0f, 0xf6, 0x0f, 0xf3, 0x0f, 0xf0, - 0x0f, 0xed, 0x0f, 0xe9, 0x0f, 0xe5, 0x0f, 0xe0, 0x0f, 0xdb, 0x0f, 0xd6, 0x0f, 0xd0, 0x0f, 0xcb, 0x0f, 0xc4, 0x0f, - 0xbe, 0x0f, 0xb7, 0x0f, 0xaf, 0x0f, 0xa8, 0x0f, 0xa0, 0x0f, 0x98, 0x0f, 0x8f, 0x0f, 0x86, 0x0f, 0x7d, 0x0f, 0x73, - 0x0f, 0x69, 0x0f, 0x5f, 0x0f, 0x54, 0x0f, 0x49, 0x0f, 0x3e, 0x0f, 0x33, 0x0f, 0x27, 0x0f, 0x1b, 0x0f, 0x0e, 0x0f, - 0x01, 0x0f, 0xf4, 0x0e, 0xe7, 0x0e, 0xd9, 0x0e, 0xcb, 0x0e, 0xbd, 0x0e, 0xae, 0x0e, 0x9f, 0x0e, 0x90, 0x0e, 0x81, - 0x0e, 0x71, 0x0e, 0x61, 0x0e, 0x51, 0x0e, 0x40, 0x0e, 0x2f, 0x0e, 0x1e, 0x0e, 0x0d, 0x0e, 0xfb, 0x0d, 0xe9, 0x0d, - 0xd7, 0x0d, 0xc4, 0x0d, 0xb2, 0x0d, 0x9f, 0x0d, 0x8b, 0x0d, 0x78, 0x0d, 0x64, 0x0d, 0x50, 0x0d, 0x3c, 0x0d, 0x28, - 0x0d, 0x13, 0x0d, 0xfe, 0x0c, 0xe9, 0x0c, 0xd4, 0x0c, 0xbf, 0x0c, 0xa9, 0x0c, 0x93, 0x0c, 0x7d, 0x0c, 0x67, 0x0c, - 0x50, 0x0c, 0x39, 0x0c, 0x23, 0x0c, 0x0c, 0x0c, 0xf4, 0x0b, 0xdd, 0x0b, 0xc5, 0x0b, 0xae, 0x0b, 0x96, 0x0b, 0x7e, - 0x0b, 0x66, 0x0b, 0x4d, 0x0b, 0x35, 0x0b, 0x1c, 0x0b, 0x03, 0x0b, 0xea, 0x0a, 0xd1, 0x0a, 0xb8, 0x0a, 0x9f, 0x0a, - 0x86, 0x0a, 0x6c, 0x0a, 0x53, 0x0a, 0x39, 0x0a, 0x1f, 0x0a, 0x05, 0x0a, 0xeb, 0x09, 0xd1, 0x09, 0xb7, 0x09, 0x9d, - 0x09, 0x82, 0x09, 0x68, 0x09, 0x4e, 0x09, 0x33, 0x09, 0x19, 0x09, 0xfe, 0x08, 0xe3, 0x08, 0xc9, 0x08, 0xae, 0x08, - 0x93, 0x08, 0x79, 0x08, 0x5e, 0x08, 0x43, 0x08, 0x28, 0x08, 0x0d, 0x08, 0xf3, 0x07, 0xd8, 0x07, 0xbd, 0x07, 0xa2, - 0x07, 0x87, 0x07, 0x6d, 0x07, 0x52, 0x07, 0x37, 0x07, 0x1d, 0x07, 0x02, 0x07, 0xe7, 0x06, 0xcd, 0x06, 0xb2, 0x06, - 0x98, 0x06, 0x7e, 0x06, 0x63, 0x06, 0x49, 0x06, 0x2f, 0x06, 0x15, 0x06, 0xfb, 0x05, 0xe1, 0x05, 0xc7, 0x05, 0xad, - 0x05, 0x94, 0x05, 0x7a, 0x05, 0x61, 0x05, 0x48, 0x05, 0x2f, 0x05, 0x16, 0x05, 0xfd, 0x04, 0xe4, 0x04, 0xcb, 0x04, - 0xb3, 0x04, 0x9a, 0x04, 0x82, 0x04, 0x6a, 0x04, 0x52, 0x04, 0x3b, 0x04, 0x23, 0x04, 0x0c, 0x04, 0xf4, 0x03, 0xdd, - 0x03, 0xc7, 0x03, 0xb0, 0x03, 0x99, 0x03, 0x83, 0x03, 0x6d, 0x03, 0x57, 0x03, 0x41, 0x03, 0x2c, 0x03, 0x17, 0x03, - 0x02, 0x03, 0xed, 0x02, 0xd8, 0x02, 0xc4, 0x02, 0xb0, 0x02, 0x9c, 0x02, 0x88, 0x02, 0x75, 0x02, 0x61, 0x02, 0x4e, - 0x02, 0x3c, 0x02, 0x29, 0x02, 0x17, 0x02, 0x05, 0x02, 0xf3, 0x01, 0xe2, 0x01, 0xd1, 0x01, 0xc0, 0x01, 0xaf, 0x01, - 0x9f, 0x01, 0x8f, 0x01, 0x7f, 0x01, 0x70, 0x01, 0x61, 0x01, 0x52, 0x01, 0x43, 0x01, 0x35, 0x01, 0x27, 0x01, 0x19, - 0x01, 0x0c, 0x01, 0xff, 0x00, 0xf2, 0x00, 0xe5, 0x00, 0xd9, 0x00, 0xcd, 0x00, 0xc2, 0x00, 0xb7, 0x00, 0xac, 0x00, - 0xa1, 0x00, 0x97, 0x00, 0x8d, 0x00, 0x83, 0x00, 0x7a, 0x00, 0x71, 0x00, 0x68, 0x00, 0x60, 0x00, 0x58, 0x00, 0x51, - 0x00, 0x49, 0x00, 0x42, 0x00, 0x3c, 0x00, 0x35, 0x00, 0x30, 0x00, 0x2a, 0x00, 0x25, 0x00, 0x20, 0x00, 0x1b, 0x00, - 0x17, 0x00, 0x13, 0x00, 0x10, 0x00, 0x0d, 0x00, 0x0a, 0x00, 0x07, 0x00, 0x05, 0x00, 0x04, 0x00, 0x02, 0x00, 0x01, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x34, 0xee, 0xff, 0xff, 0x38, 0xee, 0xff, 0xff, 0x0f, 0x00, 0x00, 0x00, 0x4d, 0x4c, - 0x49, 0x52, 0x20, 0x43, 0x6f, 0x6e, 0x76, 0x65, 0x72, 0x74, 0x65, 0x64, 0x2e, 0x00, 0x01, 0x00, 0x00, 0x00, 0x14, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x0e, 0x00, 0x18, 0x00, 0x14, 0x00, 0x10, 0x00, 0x0c, 0x00, 0x08, 0x00, 0x04, 0x00, - 0x0e, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x1c, 0x00, 0x00, 0x00, 0xf4, 0x05, 0x00, 0x00, 0xf8, 0x05, 0x00, - 0x00, 0xfc, 0x05, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x6d, 0x61, 0x69, 0x6e, 0x00, 0x00, 0x00, 0x00, 0x16, 0x00, - 0x00, 0x00, 0xa0, 0x05, 0x00, 0x00, 0x68, 0x05, 0x00, 0x00, 0x24, 0x05, 0x00, 0x00, 0xc8, 0x04, 0x00, 0x00, 0x70, - 0x04, 0x00, 0x00, 0x4c, 0x04, 0x00, 0x00, 0x10, 0x04, 0x00, 0x00, 0xc8, 0x03, 0x00, 0x00, 0xa4, 0x03, 0x00, 0x00, - 0x4c, 0x03, 0x00, 0x00, 0x14, 0x03, 0x00, 0x00, 0x10, 0x02, 0x00, 0x00, 0xc8, 0x01, 0x00, 0x00, 0x6c, 0x01, 0x00, - 0x00, 0x48, 0x01, 0x00, 0x00, 0x14, 0x01, 0x00, 0x00, 0xe0, 0x00, 0x00, 0x00, 0xac, 0x00, 0x00, 0x00, 0x78, 0x00, - 0x00, 0x00, 0x50, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0xf6, 0xfa, 0xff, 0xff, 0x0c, - 0x00, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x2a, 0x00, 0x00, 0x00, - 0x01, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x00, 0x16, 0xfb, 0xff, 0xff, 0x0c, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00, - 0x00, 0x11, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x28, 0x00, - 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x3a, 0xfb, 0xff, 0xff, 0x0c, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x10, - 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x27, 0x00, 0x00, 0x00, - 0x0e, 0x00, 0x00, 0x00, 0xa6, 0xfc, 0xff, 0xff, 0x14, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0b, 0x10, 0x00, 0x00, - 0x00, 0x14, 0x00, 0x00, 0x00, 0x0e, 0x00, 0x00, 0x00, 0x68, 0xef, 0xff, 0xff, 0x01, 0x00, 0x00, 0x00, 0x27, 0x00, - 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x26, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0xd6, 0xfc, 0xff, 0xff, 0x14, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1d, 0x10, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x0f, 0x00, 0x00, 0x00, - 0x98, 0xef, 0xff, 0xff, 0x01, 0x00, 0x00, 0x00, 0x26, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x25, 0x00, 0x00, - 0x00, 0x12, 0x00, 0x00, 0x00, 0x06, 0xfd, 0xff, 0xff, 0x14, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0b, 0x10, 0x00, - 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x0e, 0x00, 0x00, 0x00, 0xc8, 0xef, 0xff, 0xff, 0x01, 0x00, 0x00, 0x00, 0x25, - 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x24, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x36, 0xfd, 0xff, 0xff, - 0x14, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x15, 0x10, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x0d, 0x00, 0x00, - 0x00, 0xf8, 0xef, 0xff, 0xff, 0x01, 0x00, 0x00, 0x00, 0x24, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x23, 0x00, - 0x00, 0x00, 0x11, 0x00, 0x00, 0x00, 0x1e, 0xfc, 0xff, 0xff, 0x0c, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x05, - 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x23, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x22, 0x00, 0x00, 0x00, - 0x84, 0xfc, 0xff, 0xff, 0x10, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x44, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, - 0x00, 0x30, 0x00, 0x00, 0x00, 0x69, 0x6e, 0x70, 0x75, 0x74, 0x5f, 0x63, 0x6f, 0x72, 0x72, 0x65, 0x63, 0x74, 0x69, - 0x6f, 0x6e, 0x5f, 0x62, 0x69, 0x74, 0x73, 0x00, 0x6f, 0x75, 0x74, 0x70, 0x75, 0x74, 0x5f, 0x73, 0x63, 0x61, 0x6c, - 0x65, 0x00, 0x02, 0x24, 0x0f, 0x02, 0x01, 0x02, 0x03, 0x40, 0x04, 0x04, 0x04, 0x24, 0x01, 0x01, 0x00, 0x00, 0x00, - 0x22, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x21, 0x00, 0x00, 0x00, 0xdc, 0xfc, 0xff, 0xff, 0x10, 0x00, 0x00, - 0x00, 0x24, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00, 0x0b, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x73, 0x6e, - 0x72, 0x5f, 0x73, 0x68, 0x69, 0x66, 0x74, 0x00, 0x01, 0x0b, 0x01, 0x01, 0x01, 0x06, 0x04, 0x02, 0x24, 0x01, 0x01, - 0x00, 0x00, 0x00, 0x21, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x1f, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, - 0x08, 0x00, 0x00, 0x00, 0x20, 0xfd, 0xff, 0xff, 0x10, 0x00, 0x00, 0x00, 0xe4, 0x00, 0x00, 0x00, 0xec, 0x00, 0x00, - 0x00, 0x0a, 0x00, 0x00, 0x00, 0xd2, 0x00, 0x00, 0x00, 0x61, 0x6c, 0x74, 0x65, 0x72, 0x6e, 0x61, 0x74, 0x65, 0x5f, - 0x6f, 0x6e, 0x65, 0x5f, 0x6d, 0x69, 0x6e, 0x75, 0x73, 0x5f, 0x73, 0x6d, 0x6f, 0x6f, 0x74, 0x68, 0x69, 0x6e, 0x67, - 0x00, 0x61, 0x6c, 0x74, 0x65, 0x72, 0x6e, 0x61, 0x74, 0x65, 0x5f, 0x73, 0x6d, 0x6f, 0x6f, 0x74, 0x68, 0x69, 0x6e, - 0x67, 0x00, 0x63, 0x6c, 0x61, 0x6d, 0x70, 0x69, 0x6e, 0x67, 0x00, 0x6d, 0x69, 0x6e, 0x5f, 0x73, 0x69, 0x67, 0x6e, - 0x61, 0x6c, 0x5f, 0x72, 0x65, 0x6d, 0x61, 0x69, 0x6e, 0x69, 0x6e, 0x67, 0x00, 0x6e, 0x75, 0x6d, 0x5f, 0x63, 0x68, - 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x73, 0x00, 0x6f, 0x6e, 0x65, 0x5f, 0x6d, 0x69, 0x6e, 0x75, 0x73, 0x5f, 0x73, 0x6d, - 0x6f, 0x6f, 0x74, 0x68, 0x69, 0x6e, 0x67, 0x00, 0x73, 0x6d, 0x6f, 0x6f, 0x74, 0x68, 0x69, 0x6e, 0x67, 0x00, 0x73, - 0x6d, 0x6f, 0x6f, 0x74, 0x68, 0x69, 0x6e, 0x67, 0x5f, 0x62, 0x69, 0x74, 0x73, 0x00, 0x73, 0x70, 0x65, 0x63, 0x74, - 0x72, 0x61, 0x6c, 0x5f, 0x73, 0x75, 0x62, 0x74, 0x72, 0x61, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x5f, 0x62, 0x69, 0x74, - 0x73, 0x00, 0x09, 0xa5, 0x88, 0x75, 0x6d, 0x59, 0x4d, 0x3a, 0x31, 0x23, 0x09, 0x00, 0x01, 0x00, 0x09, 0x00, 0x29, - 0x3c, 0xd7, 0x03, 0x00, 0x00, 0x33, 0x03, 0x28, 0x00, 0x67, 0x3e, 0x99, 0x01, 0x0a, 0x00, 0x0e, 0x00, 0x05, 0x05, - 0x69, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x1b, 0x25, 0x01, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x1f, 0x00, 0x00, - 0x00, 0x20, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x1e, 0x00, 0x00, 0x00, 0x20, 0xfe, 0xff, 0xff, 0x10, 0x00, - 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x1c, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x01, 0x00, 0x00, 0x24, 0x01, 0x00, 0x01, 0x00, 0x00, 0x00, 0x1e, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, - 0x1d, 0x00, 0x00, 0x00, 0x16, 0x00, 0x00, 0x00, 0x54, 0xfe, 0xff, 0xff, 0x10, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, - 0x00, 0x2c, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x6e, 0x75, 0x6d, 0x5f, 0x63, 0x68, - 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x73, 0x00, 0x01, 0x0e, 0x01, 0x01, 0x01, 0x28, 0x04, 0x02, 0x24, 0x01, 0x00, 0x01, - 0x00, 0x00, 0x00, 0x1d, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x1c, 0x00, 0x00, 0x00, 0x0d, 0x00, 0x00, 0x00, - 0x0c, 0x00, 0x00, 0x00, 0x0b, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x62, 0xfe, 0xff, - 0xff, 0x0c, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x1c, 0x00, - 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x1b, 0x00, 0x00, 0x00, 0xca, 0xff, 0xff, 0xff, 0x14, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x0a, 0x10, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x8c, 0xf2, 0xff, 0xff, - 0x01, 0x00, 0x00, 0x00, 0x1b, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x1a, 0x00, 0x00, - 0x00, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0e, 0x00, 0x18, 0x00, 0x14, 0x00, 0x10, 0x00, 0x0c, 0x00, 0x0b, 0x00, - 0x04, 0x00, 0x0e, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x10, 0x00, 0x00, 0x00, 0x14, - 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0xd0, 0xf2, 0xff, 0xff, 0x01, 0x00, 0x00, 0x00, 0x1a, 0x00, 0x00, 0x00, - 0x04, 0x00, 0x00, 0x00, 0x19, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00, - 0x00, 0xfe, 0xfe, 0xff, 0xff, 0x0c, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x01, 0x00, - 0x00, 0x00, 0x19, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x64, 0xff, 0xff, 0xff, 0x10, - 0x00, 0x00, 0x00, 0x3c, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x00, - 0x65, 0x6e, 0x64, 0x5f, 0x69, 0x6e, 0x64, 0x65, 0x78, 0x00, 0x73, 0x74, 0x61, 0x72, 0x74, 0x5f, 0x69, 0x6e, 0x64, - 0x65, 0x78, 0x00, 0x02, 0x17, 0x0e, 0x00, 0x03, 0x00, 0x01, 0x00, 0x02, 0x00, 0xf1, 0x00, 0x05, 0x00, 0x05, 0x05, - 0x06, 0x25, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x17, - 0x00, 0x00, 0x00, 0xb8, 0xff, 0xff, 0xff, 0x10, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x34, 0x00, 0x00, 0x00, - 0x03, 0x00, 0x00, 0x00, 0x1f, 0x00, 0x00, 0x00, 0x54, 0x00, 0x66, 0x66, 0x74, 0x5f, 0x6c, 0x65, 0x6e, 0x67, 0x74, - 0x68, 0x00, 0x02, 0x0e, 0x0d, 0x02, 0x00, 0x01, 0x00, 0x02, 0x00, 0x07, 0x00, 0x00, 0x02, 0x05, 0x05, 0x06, 0x25, - 0x01, 0x00, 0x01, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x15, 0x00, 0x00, 0x00, 0x10, - 0x00, 0x14, 0x00, 0x10, 0x00, 0x0c, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x10, 0x00, 0x00, 0x00, - 0x10, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x24, 0x01, 0x00, 0x02, 0x00, 0x00, 0x00, 0x15, 0x00, 0x00, 0x00, 0x16, 0x00, - 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x10, 0x00, 0x0c, 0x00, 0x08, - 0x00, 0x04, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, - 0x01, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x13, 0x00, 0x00, 0x00, 0x0f, 0x00, 0x00, - 0x00, 0x10, 0x00, 0x10, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x10, 0x00, - 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x1c, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x73, - 0x68, 0x69, 0x66, 0x74, 0x00, 0x01, 0x07, 0x01, 0x01, 0x01, 0x0c, 0x04, 0x02, 0x24, 0x01, 0x01, 0x00, 0x00, 0x00, - 0x13, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, - 0x00, 0x2a, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x2b, 0x00, 0x00, 0x00, 0xc4, 0x0a, - 0x00, 0x00, 0x74, 0x0a, 0x00, 0x00, 0x3c, 0x0a, 0x00, 0x00, 0x04, 0x0a, 0x00, 0x00, 0xd0, 0x09, 0x00, 0x00, 0x88, - 0x09, 0x00, 0x00, 0x40, 0x09, 0x00, 0x00, 0xfc, 0x08, 0x00, 0x00, 0xb8, 0x08, 0x00, 0x00, 0x6c, 0x08, 0x00, 0x00, - 0x20, 0x08, 0x00, 0x00, 0xd4, 0x07, 0x00, 0x00, 0x88, 0x07, 0x00, 0x00, 0x3c, 0x07, 0x00, 0x00, 0xf8, 0x06, 0x00, - 0x00, 0xb8, 0x06, 0x00, 0x00, 0x84, 0x06, 0x00, 0x00, 0x50, 0x06, 0x00, 0x00, 0x1c, 0x06, 0x00, 0x00, 0xd8, 0x05, - 0x00, 0x00, 0xa0, 0x05, 0x00, 0x00, 0x58, 0x05, 0x00, 0x00, 0x14, 0x05, 0x00, 0x00, 0xd8, 0x04, 0x00, 0x00, 0x98, - 0x04, 0x00, 0x00, 0x60, 0x04, 0x00, 0x00, 0x20, 0x04, 0x00, 0x00, 0xe8, 0x03, 0x00, 0x00, 0xb0, 0x03, 0x00, 0x00, - 0x6c, 0x03, 0x00, 0x00, 0x1c, 0x03, 0x00, 0x00, 0xc4, 0x02, 0x00, 0x00, 0x68, 0x02, 0x00, 0x00, 0x2c, 0x02, 0x00, - 0x00, 0xe4, 0x01, 0x00, 0x00, 0xac, 0x01, 0x00, 0x00, 0x78, 0x01, 0x00, 0x00, 0x44, 0x01, 0x00, 0x00, 0x08, 0x01, - 0x00, 0x00, 0xd0, 0x00, 0x00, 0x00, 0x88, 0x00, 0x00, 0x00, 0x48, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0xfe, - 0xf5, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x2b, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x09, 0x20, 0x00, 0x00, 0x00, 0x44, 0xf5, 0xff, 0xff, 0x11, 0x00, 0x00, 0x00, 0x50, 0x61, 0x72, - 0x74, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x65, 0x64, 0x43, 0x61, 0x6c, 0x6c, 0x3a, 0x30, 0x00, 0x00, 0x00, 0x01, 0x00, - 0x00, 0x00, 0x28, 0x00, 0x00, 0x00, 0x3e, 0xf6, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, - 0x00, 0x00, 0x00, 0x2a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x1c, 0x00, 0x00, 0x00, 0x84, 0xf5, 0xff, 0xff, - 0x0d, 0x00, 0x00, 0x00, 0x63, 0x6c, 0x69, 0x70, 0x5f, 0x62, 0x79, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x00, 0x00, - 0x00, 0x01, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00, 0x7a, 0xf6, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, - 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x24, 0x00, 0x00, 0x00, 0xc0, - 0xf5, 0xff, 0xff, 0x15, 0x00, 0x00, 0x00, 0x63, 0x6c, 0x69, 0x70, 0x5f, 0x62, 0x79, 0x5f, 0x76, 0x61, 0x6c, 0x75, - 0x65, 0x2f, 0x4d, 0x69, 0x6e, 0x69, 0x6d, 0x75, 0x6d, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, - 0x00, 0xbe, 0xf6, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x28, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x14, 0x00, 0x00, 0x00, 0x04, 0xf6, 0xff, 0xff, 0x05, 0x00, 0x00, 0x00, 0x61, - 0x64, 0x64, 0x5f, 0x31, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00, 0xf2, 0xf6, 0xff, 0xff, - 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x27, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x02, 0x18, 0x00, 0x00, 0x00, 0x38, 0xf6, 0xff, 0xff, 0x0b, 0x00, 0x00, 0x00, 0x54, 0x72, 0x75, 0x6e, 0x63, 0x61, - 0x74, 0x65, 0x44, 0x69, 0x76, 0x00, 0x01, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00, 0x2a, 0xf7, 0xff, 0xff, 0x00, - 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x26, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, - 0x10, 0x00, 0x00, 0x00, 0x70, 0xf6, 0xff, 0xff, 0x03, 0x00, 0x00, 0x00, 0x61, 0x64, 0x64, 0x00, 0x01, 0x00, 0x00, - 0x00, 0x28, 0x00, 0x00, 0x00, 0x5a, 0xf7, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, - 0x00, 0x00, 0x25, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x10, 0x00, 0x00, 0x00, 0xa0, 0xf6, 0xff, 0xff, 0x03, - 0x00, 0x00, 0x00, 0x6d, 0x75, 0x6c, 0x00, 0x01, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00, 0x8a, 0xf7, 0xff, 0xff, - 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x24, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x02, 0x14, 0x00, 0x00, 0x00, 0xd0, 0xf6, 0xff, 0xff, 0x06, 0x00, 0x00, 0x00, 0x43, 0x61, 0x73, 0x74, 0x5f, 0x32, - 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00, 0xbe, 0xf7, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, - 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x23, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0x24, 0x00, 0x00, 0x00, - 0x04, 0xf7, 0xff, 0xff, 0x16, 0x00, 0x00, 0x00, 0x73, 0x69, 0x67, 0x6e, 0x61, 0x6c, 0x5f, 0x66, 0x69, 0x6c, 0x74, - 0x65, 0x72, 0x5f, 0x62, 0x61, 0x6e, 0x6b, 0x5f, 0x6c, 0x6f, 0x67, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x28, 0x00, - 0x00, 0x00, 0x02, 0xf8, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x22, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0f, 0x18, 0x00, 0x00, 0x00, 0x48, 0xf7, 0xff, 0xff, 0x0b, 0x00, 0x00, 0x00, - 0x73, 0x69, 0x67, 0x6e, 0x61, 0x6c, 0x5f, 0x70, 0x63, 0x61, 0x6e, 0x00, 0x01, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, - 0x00, 0x3a, 0xf8, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x21, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x0f, 0x38, 0x00, 0x00, 0x00, 0x80, 0xf7, 0xff, 0xff, 0x28, 0x00, 0x00, 0x00, 0x73, - 0x69, 0x67, 0x6e, 0x61, 0x6c, 0x5f, 0x66, 0x69, 0x6c, 0x74, 0x65, 0x72, 0x5f, 0x62, 0x61, 0x6e, 0x6b, 0x5f, 0x73, - 0x70, 0x65, 0x63, 0x74, 0x72, 0x61, 0x6c, 0x5f, 0x73, 0x75, 0x62, 0x74, 0x72, 0x61, 0x63, 0x74, 0x69, 0x6f, 0x6e, - 0x31, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00, 0x92, 0xf8, 0xff, 0xff, 0x00, 0x00, - 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0f, 0x34, - 0x00, 0x00, 0x00, 0xd8, 0xf7, 0xff, 0xff, 0x27, 0x00, 0x00, 0x00, 0x73, 0x69, 0x67, 0x6e, 0x61, 0x6c, 0x5f, 0x66, - 0x69, 0x6c, 0x74, 0x65, 0x72, 0x5f, 0x62, 0x61, 0x6e, 0x6b, 0x5f, 0x73, 0x70, 0x65, 0x63, 0x74, 0x72, 0x61, 0x6c, - 0x5f, 0x73, 0x75, 0x62, 0x74, 0x72, 0x61, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x00, 0x01, 0x00, 0x00, 0x00, 0x28, 0x00, - 0x00, 0x00, 0xe6, 0xf8, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x1f, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0f, 0x2c, 0x00, 0x00, 0x00, 0x2c, 0xf8, 0xff, 0xff, 0x1e, 0x00, 0x00, 0x00, - 0x73, 0x69, 0x67, 0x6e, 0x61, 0x6c, 0x5f, 0x66, 0x69, 0x6c, 0x74, 0x65, 0x72, 0x5f, 0x62, 0x61, 0x6e, 0x6b, 0x5f, - 0x73, 0x71, 0x75, 0x61, 0x72, 0x65, 0x5f, 0x72, 0x6f, 0x6f, 0x74, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x28, 0x00, - 0x00, 0x00, 0x32, 0xf9, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x1e, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x20, 0x00, 0x00, 0x00, 0x78, 0xf8, 0xff, 0xff, 0x12, 0x00, 0x00, 0x00, - 0x73, 0x69, 0x67, 0x6e, 0x61, 0x6c, 0x5f, 0x66, 0x69, 0x6c, 0x74, 0x65, 0x72, 0x5f, 0x62, 0x61, 0x6e, 0x6b, 0x00, - 0x00, 0x01, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00, 0x72, 0xf9, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, - 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x1d, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0f, 0x14, 0x00, 0x00, 0x00, 0xb8, - 0xf8, 0xff, 0xff, 0x06, 0x00, 0x00, 0x00, 0x43, 0x61, 0x73, 0x74, 0x5f, 0x31, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, - 0x01, 0x01, 0x00, 0x00, 0xa6, 0xf9, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, - 0x00, 0x1c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x14, 0x00, 0x00, 0x00, 0xec, 0xf8, 0xff, 0xff, 0x06, 0x00, - 0x00, 0x00, 0x63, 0x6f, 0x6e, 0x63, 0x61, 0x74, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x01, 0x00, 0x00, 0xda, - 0xf9, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x1b, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x02, 0x1c, 0x00, 0x00, 0x00, 0x20, 0xf9, 0xff, 0xff, 0x0d, 0x00, 0x00, 0x00, 0x73, 0x74, 0x72, - 0x69, 0x64, 0x65, 0x64, 0x5f, 0x73, 0x6c, 0x69, 0x63, 0x65, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0xec, 0x00, - 0x00, 0x00, 0x16, 0xfa, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x1a, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x14, 0x00, 0x00, 0x00, 0x5c, 0xf9, 0xff, 0xff, 0x04, 0x00, 0x00, 0x00, - 0x43, 0x61, 0x73, 0x74, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x01, 0x00, 0x00, 0x4a, 0xfa, 0xff, - 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x19, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x0f, 0x1c, 0x00, 0x00, 0x00, 0x90, 0xf9, 0xff, 0xff, 0x0d, 0x00, 0x00, 0x00, 0x73, 0x69, 0x67, 0x6e, 0x61, - 0x6c, 0x5f, 0x65, 0x6e, 0x65, 0x72, 0x67, 0x79, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x01, 0x00, 0x00, - 0x86, 0xfa, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x07, 0x18, 0x00, 0x00, 0x00, 0xcc, 0xf9, 0xff, 0xff, 0x0b, 0x00, 0x00, 0x00, 0x73, 0x69, - 0x67, 0x6e, 0x61, 0x6c, 0x5f, 0x72, 0x66, 0x66, 0x74, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02, 0x02, 0x00, 0x00, 0xbe, - 0xfa, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x02, 0x24, 0x00, 0x00, 0x00, 0x04, 0xfa, 0xff, 0xff, 0x16, 0x00, 0x00, 0x00, 0x73, 0x69, 0x67, - 0x6e, 0x61, 0x6c, 0x5f, 0x66, 0x66, 0x74, 0x5f, 0x61, 0x75, 0x74, 0x6f, 0x5f, 0x73, 0x63, 0x61, 0x6c, 0x65, 0x31, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xfe, 0xfa, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, - 0x00, 0x00, 0x00, 0x16, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0x24, 0x00, 0x00, 0x00, 0x44, 0xfa, 0xff, 0xff, - 0x15, 0x00, 0x00, 0x00, 0x73, 0x69, 0x67, 0x6e, 0x61, 0x6c, 0x5f, 0x66, 0x66, 0x74, 0x5f, 0x61, 0x75, 0x74, 0x6f, - 0x5f, 0x73, 0x63, 0x61, 0x6c, 0x65, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0xe0, 0x01, 0x00, 0x00, 0x42, 0xfb, - 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x15, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x07, 0x14, 0x00, 0x00, 0x00, 0x88, 0xfa, 0xff, 0xff, 0x07, 0x00, 0x00, 0x00, 0x52, 0x65, 0x73, 0x68, - 0x61, 0x70, 0x65, 0x00, 0x01, 0x00, 0x00, 0x00, 0xe0, 0x01, 0x00, 0x00, 0x76, 0xfb, 0xff, 0xff, 0x00, 0x00, 0x00, - 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0x1c, 0x00, - 0x00, 0x00, 0xbc, 0xfa, 0xff, 0xff, 0x0d, 0x00, 0x00, 0x00, 0x73, 0x69, 0x67, 0x6e, 0x61, 0x6c, 0x5f, 0x77, 0x69, - 0x6e, 0x64, 0x6f, 0x77, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0xe0, 0x01, 0x00, 0x00, - 0xb6, 0xfb, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x13, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x02, 0x14, 0x00, 0x00, 0x00, 0xfc, 0xfa, 0xff, 0xff, 0x07, 0x00, 0x00, 0x00, 0x43, 0x6f, - 0x6e, 0x73, 0x74, 0x5f, 0x31, 0x00, 0x00, 0x00, 0x00, 0x00, 0xe6, 0xfb, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, - 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x12, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x14, 0x00, 0x00, 0x00, - 0x2c, 0xfb, 0xff, 0xff, 0x06, 0x00, 0x00, 0x00, 0x43, 0x6f, 0x6e, 0x73, 0x74, 0x31, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x16, 0xfc, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x11, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x14, 0x00, 0x00, 0x00, 0x5c, 0xfb, 0xff, 0xff, 0x07, 0x00, 0x00, 0x00, 0x43, - 0x6f, 0x6e, 0x73, 0x74, 0x5f, 0x32, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46, 0xfc, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, - 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x1c, 0x00, 0x00, - 0x00, 0x8c, 0xfb, 0xff, 0xff, 0x0d, 0x00, 0x00, 0x00, 0x52, 0x65, 0x73, 0x68, 0x61, 0x70, 0x65, 0x2f, 0x73, 0x68, - 0x61, 0x70, 0x65, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x82, 0xfc, 0xff, 0xff, 0x00, - 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x0f, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, - 0x24, 0x00, 0x00, 0x00, 0xc8, 0xfb, 0xff, 0xff, 0x17, 0x00, 0x00, 0x00, 0x63, 0x6c, 0x69, 0x70, 0x5f, 0x62, 0x79, - 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x2f, 0x4d, 0x69, 0x6e, 0x69, 0x6d, 0x75, 0x6d, 0x2f, 0x79, 0x00, 0x00, 0x00, - 0x00, 0x00, 0xc2, 0xfc, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x0e, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0x28, 0x00, 0x00, 0x00, 0x08, 0xfc, 0xff, 0xff, 0x18, 0x00, 0x00, 0x00, - 0x73, 0x69, 0x67, 0x6e, 0x61, 0x6c, 0x5f, 0x66, 0x69, 0x6c, 0x74, 0x65, 0x72, 0x5f, 0x62, 0x61, 0x6e, 0x6b, 0x2f, - 0x43, 0x6f, 0x6e, 0x73, 0x74, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x3c, 0x01, 0x00, 0x00, 0x0a, 0xfd, - 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x0d, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x07, 0x28, 0x00, 0x00, 0x00, 0x50, 0xfc, 0xff, 0xff, 0x1a, 0x00, 0x00, 0x00, 0x73, 0x69, 0x67, 0x6e, - 0x61, 0x6c, 0x5f, 0x66, 0x69, 0x6c, 0x74, 0x65, 0x72, 0x5f, 0x62, 0x61, 0x6e, 0x6b, 0x2f, 0x43, 0x6f, 0x6e, 0x73, - 0x74, 0x5f, 0x31, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x3c, 0x01, 0x00, 0x00, 0x52, 0xfd, 0xff, 0xff, 0x00, 0x00, - 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0x28, - 0x00, 0x00, 0x00, 0x98, 0xfc, 0xff, 0xff, 0x1a, 0x00, 0x00, 0x00, 0x73, 0x69, 0x67, 0x6e, 0x61, 0x6c, 0x5f, 0x66, - 0x69, 0x6c, 0x74, 0x65, 0x72, 0x5f, 0x62, 0x61, 0x6e, 0x6b, 0x2f, 0x43, 0x6f, 0x6e, 0x73, 0x74, 0x5f, 0x32, 0x00, - 0x00, 0x01, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x00, 0x9a, 0xfd, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, - 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x0b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0x28, 0x00, 0x00, 0x00, 0xe0, - 0xfc, 0xff, 0xff, 0x1a, 0x00, 0x00, 0x00, 0x73, 0x69, 0x67, 0x6e, 0x61, 0x6c, 0x5f, 0x66, 0x69, 0x6c, 0x74, 0x65, - 0x72, 0x5f, 0x62, 0x61, 0x6e, 0x6b, 0x2f, 0x43, 0x6f, 0x6e, 0x73, 0x74, 0x5f, 0x33, 0x00, 0x00, 0x01, 0x00, 0x00, - 0x00, 0x29, 0x00, 0x00, 0x00, 0xe2, 0xfd, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, - 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0x28, 0x00, 0x00, 0x00, 0x28, 0xfd, 0xff, 0xff, 0x1a, - 0x00, 0x00, 0x00, 0x73, 0x69, 0x67, 0x6e, 0x61, 0x6c, 0x5f, 0x66, 0x69, 0x6c, 0x74, 0x65, 0x72, 0x5f, 0x62, 0x61, - 0x6e, 0x6b, 0x2f, 0x43, 0x6f, 0x6e, 0x73, 0x74, 0x5f, 0x34, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, - 0x00, 0x2a, 0xfe, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x09, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0x20, 0x00, 0x00, 0x00, 0x70, 0xfd, 0xff, 0xff, 0x11, 0x00, 0x00, 0x00, 0x73, - 0x69, 0x67, 0x6e, 0x61, 0x6c, 0x5f, 0x70, 0x63, 0x61, 0x6e, 0x2f, 0x43, 0x6f, 0x6e, 0x73, 0x74, 0x00, 0x00, 0x00, - 0x01, 0x00, 0x00, 0x00, 0x7d, 0x00, 0x00, 0x00, 0x6a, 0xfe, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, - 0x00, 0x14, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x20, 0x00, 0x00, 0x00, 0xb0, 0xfd, - 0xff, 0xff, 0x13, 0x00, 0x00, 0x00, 0x73, 0x74, 0x72, 0x69, 0x64, 0x65, 0x64, 0x5f, 0x73, 0x6c, 0x69, 0x63, 0x65, - 0x2f, 0x73, 0x74, 0x61, 0x63, 0x6b, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0xaa, 0xfe, 0xff, 0xff, - 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x02, 0x24, 0x00, 0x00, 0x00, 0xf0, 0xfd, 0xff, 0xff, 0x15, 0x00, 0x00, 0x00, 0x73, 0x74, 0x72, 0x69, 0x64, 0x65, - 0x64, 0x5f, 0x73, 0x6c, 0x69, 0x63, 0x65, 0x2f, 0x73, 0x74, 0x61, 0x63, 0x6b, 0x5f, 0x31, 0x00, 0x00, 0x00, 0x01, - 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0xee, 0xfe, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, - 0x14, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x24, 0x00, 0x00, 0x00, 0x34, 0xfe, 0xff, - 0xff, 0x15, 0x00, 0x00, 0x00, 0x73, 0x74, 0x72, 0x69, 0x64, 0x65, 0x64, 0x5f, 0x73, 0x6c, 0x69, 0x63, 0x65, 0x2f, - 0x73, 0x74, 0x61, 0x63, 0x6b, 0x5f, 0x32, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x32, - 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x02, 0x14, 0x00, 0x00, 0x00, 0x78, 0xfe, 0xff, 0xff, 0x06, 0x00, 0x00, 0x00, 0x43, 0x61, 0x73, - 0x74, 0x5f, 0x33, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x62, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, - 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x14, 0x00, 0x00, 0x00, 0xa8, - 0xfe, 0xff, 0xff, 0x05, 0x00, 0x00, 0x00, 0x7a, 0x65, 0x72, 0x6f, 0x73, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, - 0x05, 0x00, 0x00, 0x00, 0x96, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, - 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x14, 0x00, 0x00, 0x00, 0xdc, 0xfe, 0xff, 0xff, 0x07, 0x00, - 0x00, 0x00, 0x7a, 0x65, 0x72, 0x6f, 0x73, 0x5f, 0x31, 0x00, 0x01, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0xca, - 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x07, 0x14, 0x00, 0x00, 0x00, 0x10, 0xff, 0xff, 0xff, 0x05, 0x00, 0x00, 0x00, 0x43, 0x6f, 0x6e, - 0x73, 0x74, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0xe0, 0x01, 0x00, 0x00, 0x00, 0x00, 0x16, 0x00, 0x1c, 0x00, - 0x18, 0x00, 0x17, 0x00, 0x10, 0x00, 0x0c, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0x00, 0x16, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x14, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x07, 0x2c, 0x00, 0x00, 0x00, 0x5c, 0xff, 0xff, 0xff, 0x1d, 0x00, 0x00, 0x00, 0x73, 0x65, 0x72, - 0x76, 0x69, 0x6e, 0x67, 0x5f, 0x64, 0x65, 0x66, 0x61, 0x75, 0x6c, 0x74, 0x5f, 0x61, 0x75, 0x64, 0x69, 0x6f, 0x5f, - 0x66, 0x72, 0x61, 0x6d, 0x65, 0x3a, 0x30, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0xe0, - 0x01, 0x00, 0x00, 0x12, 0x00, 0x00, 0x00, 0x1c, 0x02, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0xc8, 0x01, 0x00, 0x00, - 0xa4, 0x01, 0x00, 0x00, 0x7c, 0x01, 0x00, 0x00, 0x68, 0x01, 0x00, 0x00, 0x4c, 0x01, 0x00, 0x00, 0x3c, 0x01, 0x00, - 0x00, 0x10, 0x01, 0x00, 0x00, 0xdc, 0x00, 0x00, 0x00, 0xa0, 0x00, 0x00, 0x00, 0x7c, 0x00, 0x00, 0x00, 0x50, 0x00, - 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x38, 0x00, 0x00, 0x00, 0x24, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x04, - 0x00, 0x00, 0x00, 0x50, 0xfe, 0xff, 0xff, 0x37, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x37, 0x5c, 0xfe, 0xff, 0xff, - 0x39, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x39, 0x68, 0xfe, 0xff, 0xff, 0x2a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x2a, 0x04, 0x00, 0x04, 0x00, 0x04, 0x00, 0x00, 0x00, 0x7c, 0xfe, 0xff, 0xff, 0x12, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x12, 0x70, 0xfe, 0xff, 0xff, 0x20, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x13, - 0x00, 0x00, 0x00, 0x53, 0x69, 0x67, 0x6e, 0x61, 0x6c, 0x46, 0x69, 0x6c, 0x74, 0x65, 0x72, 0x42, 0x61, 0x6e, 0x6b, - 0x4c, 0x6f, 0x67, 0x00, 0x98, 0xfe, 0xff, 0xff, 0x20, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x20, 0x0a, 0x00, 0x00, 0x00, 0x53, 0x69, 0x67, 0x6e, 0x61, 0x6c, 0x50, 0x43, 0x41, 0x4e, 0x00, 0x00, 0xb8, 0xfe, - 0xff, 0xff, 0x20, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x23, 0x00, 0x00, 0x00, 0x53, - 0x69, 0x67, 0x6e, 0x61, 0x6c, 0x46, 0x69, 0x6c, 0x74, 0x65, 0x72, 0x42, 0x61, 0x6e, 0x6b, 0x53, 0x70, 0x65, 0x63, - 0x74, 0x72, 0x61, 0x6c, 0x53, 0x75, 0x62, 0x74, 0x72, 0x61, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x00, 0xf0, 0xfe, 0xff, - 0xff, 0x20, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x1a, 0x00, 0x00, 0x00, 0x53, 0x69, - 0x67, 0x6e, 0x61, 0x6c, 0x46, 0x69, 0x6c, 0x74, 0x65, 0x72, 0x42, 0x61, 0x6e, 0x6b, 0x53, 0x71, 0x75, 0x61, 0x72, - 0x65, 0x52, 0x6f, 0x6f, 0x74, 0x00, 0x00, 0x20, 0xff, 0xff, 0xff, 0x20, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x20, 0x10, 0x00, 0x00, 0x00, 0x53, 0x69, 0x67, 0x6e, 0x61, 0x6c, 0x46, 0x69, 0x6c, 0x74, 0x65, - 0x72, 0x42, 0x61, 0x6e, 0x6b, 0x00, 0x00, 0x00, 0x00, 0x60, 0xff, 0xff, 0xff, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x02, 0x6c, 0xff, 0xff, 0xff, 0x2d, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x2d, 0x0c, 0x00, 0x10, 0x00, 0x0f, - 0x00, 0x00, 0x00, 0x08, 0x00, 0x04, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x35, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x35, 0x7c, 0xff, 0xff, 0xff, 0x20, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x20, 0x0c, 0x00, 0x00, 0x00, 0x53, 0x69, 0x67, 0x6e, 0x61, 0x6c, 0x45, 0x6e, 0x65, 0x72, 0x67, 0x79, 0x00, 0x00, - 0x00, 0x00, 0xa0, 0xff, 0xff, 0xff, 0x20, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x0a, - 0x00, 0x00, 0x00, 0x53, 0x69, 0x67, 0x6e, 0x61, 0x6c, 0x52, 0x66, 0x66, 0x74, 0x00, 0x00, 0xc0, 0xff, 0xff, 0xff, - 0x20, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x12, 0x00, 0x00, 0x00, 0x53, 0x69, 0x67, - 0x6e, 0x61, 0x6c, 0x46, 0x66, 0x74, 0x41, 0x75, 0x74, 0x6f, 0x53, 0x63, 0x61, 0x6c, 0x65, 0x00, 0x00, 0x0c, 0x00, - 0x0c, 0x00, 0x0b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x16, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x16, 0x0c, 0x00, 0x10, 0x00, 0x0f, 0x00, 0x08, 0x00, 0x00, 0x00, 0x04, 0x00, 0x0c, 0x00, 0x00, 0x00, - 0x20, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x0c, 0x00, 0x00, 0x00, 0x53, 0x69, 0x67, - 0x6e, 0x61, 0x6c, 0x57, 0x69, 0x6e, 0x64, 0x6f, 0x77, 0x00, 0x00, 0x00, 0x00}; - -} // namespace micro_wake_word -} // namespace esphome - -#endif // USE_ESP_IDF diff --git a/esphome/components/micro_wake_word/micro_wake_word.cpp b/esphome/components/micro_wake_word/micro_wake_word.cpp index 5a89708127..b58c7ec434 100644 --- a/esphome/components/micro_wake_word/micro_wake_word.cpp +++ b/esphome/components/micro_wake_word/micro_wake_word.cpp @@ -1,12 +1,5 @@ #include "micro_wake_word.h" - -/** - * This is a workaround until we can figure out a way to get - * the tflite-micro idf component code available in CI - * - * */ -// -#ifndef CLANG_TIDY +#include "streaming_model.h" #ifdef USE_ESP_IDF @@ -14,13 +7,13 @@ #include "esphome/core/helpers.h" #include "esphome/core/log.h" -#include "audio_preprocessor_int8_model_data.h" +#include +#include #include #include #include -#include #include namespace esphome { @@ -29,9 +22,9 @@ namespace micro_wake_word { static const char *const TAG = "micro_wake_word"; static const size_t SAMPLE_RATE_HZ = 16000; // 16 kHz -static const size_t BUFFER_LENGTH = 500; // 0.5 seconds +static const size_t BUFFER_LENGTH = 64; // 0.064 seconds static const size_t BUFFER_SIZE = SAMPLE_RATE_HZ / 1000 * BUFFER_LENGTH; -static const size_t INPUT_BUFFER_SIZE = 32 * SAMPLE_RATE_HZ / 1000; // 32ms * 16kHz / 1000ms +static const size_t INPUT_BUFFER_SIZE = 16 * SAMPLE_RATE_HZ / 1000; // 16ms * 16kHz / 1000ms float MicroWakeWord::get_setup_priority() const { return setup_priority::AFTER_CONNECTION; } @@ -56,58 +49,56 @@ static const LogString *micro_wake_word_state_to_string(State state) { void MicroWakeWord::dump_config() { ESP_LOGCONFIG(TAG, "microWakeWord:"); - ESP_LOGCONFIG(TAG, " Wake Word: %s", this->get_wake_word().c_str()); - ESP_LOGCONFIG(TAG, " Probability cutoff: %.3f", this->probability_cutoff_); - ESP_LOGCONFIG(TAG, " Sliding window size: %d", this->sliding_window_average_size_); + ESP_LOGCONFIG(TAG, " models:"); + for (auto &model : this->wake_word_models_) { + model.log_model_config(); + } +#ifdef USE_MICRO_WAKE_WORD_VAD + this->vad_model_->log_model_config(); +#endif } void MicroWakeWord::setup() { ESP_LOGCONFIG(TAG, "Setting up microWakeWord..."); - if (!this->initialize_models()) { - ESP_LOGE(TAG, "Failed to initialize models"); - this->mark_failed(); - return; - } - - ExternalRAMAllocator allocator(ExternalRAMAllocator::ALLOW_FAILURE); - this->input_buffer_ = allocator.allocate(INPUT_BUFFER_SIZE * sizeof(int16_t)); - if (this->input_buffer_ == nullptr) { - ESP_LOGW(TAG, "Could not allocate input buffer"); - this->mark_failed(); - return; - } - - this->ring_buffer_ = RingBuffer::create(BUFFER_SIZE * sizeof(int16_t)); - if (this->ring_buffer_ == nullptr) { - ESP_LOGW(TAG, "Could not allocate ring buffer"); + if (!this->register_streaming_ops_(this->streaming_op_resolver_)) { this->mark_failed(); return; } ESP_LOGCONFIG(TAG, "Micro Wake Word initialized"); + + this->frontend_config_.window.size_ms = FEATURE_DURATION_MS; + this->frontend_config_.window.step_size_ms = this->features_step_size_; + this->frontend_config_.filterbank.num_channels = PREPROCESSOR_FEATURE_SIZE; + this->frontend_config_.filterbank.lower_band_limit = 125.0; + this->frontend_config_.filterbank.upper_band_limit = 7500.0; + this->frontend_config_.noise_reduction.smoothing_bits = 10; + this->frontend_config_.noise_reduction.even_smoothing = 0.025; + this->frontend_config_.noise_reduction.odd_smoothing = 0.06; + this->frontend_config_.noise_reduction.min_signal_remaining = 0.05; + this->frontend_config_.pcan_gain_control.enable_pcan = 1; + this->frontend_config_.pcan_gain_control.strength = 0.95; + this->frontend_config_.pcan_gain_control.offset = 80.0; + this->frontend_config_.pcan_gain_control.gain_bits = 21; + this->frontend_config_.log_scale.enable_log = 1; + this->frontend_config_.log_scale.scale_shift = 6; } -int MicroWakeWord::read_microphone_() { - size_t bytes_read = this->microphone_->read(this->input_buffer_, INPUT_BUFFER_SIZE * sizeof(int16_t)); - if (bytes_read == 0) { - return 0; - } - - size_t bytes_free = this->ring_buffer_->free(); - - if (bytes_free < bytes_read) { - ESP_LOGW(TAG, - "Not enough free bytes in ring buffer to store incoming audio data (free bytes=%d, incoming bytes=%d). " - "Resetting the ring buffer. Wake word detection accuracy will be reduced.", - bytes_free, bytes_read); - - this->ring_buffer_->reset(); - } - - return this->ring_buffer_->write((void *) this->input_buffer_, bytes_read); +void MicroWakeWord::add_wake_word_model(const uint8_t *model_start, float probability_cutoff, + size_t sliding_window_average_size, const std::string &wake_word, + size_t tensor_arena_size) { + this->wake_word_models_.emplace_back(model_start, probability_cutoff, sliding_window_average_size, wake_word, + tensor_arena_size); } +#ifdef USE_MICRO_WAKE_WORD_VAD +void MicroWakeWord::add_vad_model(const uint8_t *model_start, float probability_cutoff, size_t sliding_window_size, + size_t tensor_arena_size) { + this->vad_model_ = make_unique(model_start, probability_cutoff, sliding_window_size, tensor_arena_size); +} +#endif + void MicroWakeWord::loop() { switch (this->state_) { case State::IDLE: @@ -124,9 +115,12 @@ void MicroWakeWord::loop() { } break; case State::DETECTING_WAKE_WORD: - this->read_microphone_(); - if (this->detect_wake_word_()) { - ESP_LOGD(TAG, "Wake Word Detected"); + while (!this->has_enough_samples_()) { + this->read_microphone_(); + } + this->update_model_probabilities_(); + if (this->detect_wake_words_()) { + ESP_LOGD(TAG, "Wake Word '%s' Detected", (this->detected_wake_word_).c_str()); this->detected_ = true; this->set_state_(State::STOP_MICROPHONE); } @@ -136,13 +130,16 @@ void MicroWakeWord::loop() { this->microphone_->stop(); this->set_state_(State::STOPPING_MICROPHONE); this->high_freq_.stop(); + this->unload_models_(); + this->deallocate_buffers_(); break; case State::STOPPING_MICROPHONE: if (this->microphone_->is_stopped()) { this->set_state_(State::IDLE); if (this->detected_) { + this->wake_word_detected_trigger_->trigger(this->detected_wake_word_); this->detected_ = false; - this->wake_word_detected_trigger_->trigger(this->wake_word_); + this->detected_wake_word_ = ""; } } break; @@ -150,14 +147,34 @@ void MicroWakeWord::loop() { } void MicroWakeWord::start() { + if (!this->is_ready()) { + ESP_LOGW(TAG, "Wake word detection can't start as the component hasn't been setup yet"); + return; + } + if (this->is_failed()) { ESP_LOGW(TAG, "Wake word component is marked as failed. Please check setup logs"); return; } + + if (!this->load_models_() || !this->allocate_buffers_()) { + ESP_LOGE(TAG, "Failed to load the wake word model(s) or allocate buffers"); + this->status_set_error(); + } else { + this->status_clear_error(); + } + + if (this->status_has_error()) { + ESP_LOGW(TAG, "Wake word component has an error. Please check logs"); + return; + } + if (this->state_ != State::IDLE) { ESP_LOGW(TAG, "Wake word is already running"); return; } + + this->reset_states_(); this->set_state_(State::START_MICROPHONE); } @@ -179,289 +196,218 @@ void MicroWakeWord::set_state_(State state) { this->state_ = state; } -bool MicroWakeWord::initialize_models() { - ExternalRAMAllocator arena_allocator(ExternalRAMAllocator::ALLOW_FAILURE); - ExternalRAMAllocator features_allocator(ExternalRAMAllocator::ALLOW_FAILURE); +size_t MicroWakeWord::read_microphone_() { + size_t bytes_read = this->microphone_->read(this->input_buffer_, INPUT_BUFFER_SIZE * sizeof(int16_t)); + if (bytes_read == 0) { + return 0; + } + + size_t bytes_free = this->ring_buffer_->free(); + + if (bytes_free < bytes_read) { + ESP_LOGW(TAG, + "Not enough free bytes in ring buffer to store incoming audio data (free bytes=%d, incoming bytes=%d). " + "Resetting the ring buffer. Wake word detection accuracy will be reduced.", + bytes_free, bytes_read); + + this->ring_buffer_->reset(); + } + + return this->ring_buffer_->write((void *) this->input_buffer_, bytes_read); +} + +bool MicroWakeWord::allocate_buffers_() { ExternalRAMAllocator audio_samples_allocator(ExternalRAMAllocator::ALLOW_FAILURE); - this->streaming_tensor_arena_ = arena_allocator.allocate(STREAMING_MODEL_ARENA_SIZE); - if (this->streaming_tensor_arena_ == nullptr) { - ESP_LOGE(TAG, "Could not allocate the streaming model's tensor arena."); - return false; + if (this->input_buffer_ == nullptr) { + this->input_buffer_ = audio_samples_allocator.allocate(INPUT_BUFFER_SIZE * sizeof(int16_t)); + if (this->input_buffer_ == nullptr) { + ESP_LOGE(TAG, "Could not allocate input buffer"); + return false; + } } - this->streaming_var_arena_ = arena_allocator.allocate(STREAMING_MODEL_VARIABLE_ARENA_SIZE); - if (this->streaming_var_arena_ == nullptr) { - ESP_LOGE(TAG, "Could not allocate the streaming model variable's tensor arena."); - return false; - } - - this->preprocessor_tensor_arena_ = arena_allocator.allocate(PREPROCESSOR_ARENA_SIZE); - if (this->preprocessor_tensor_arena_ == nullptr) { - ESP_LOGE(TAG, "Could not allocate the audio preprocessor model's tensor arena."); - return false; - } - - this->new_features_data_ = features_allocator.allocate(PREPROCESSOR_FEATURE_SIZE); - if (this->new_features_data_ == nullptr) { - ESP_LOGE(TAG, "Could not allocate the audio features buffer."); - return false; - } - - this->preprocessor_audio_buffer_ = audio_samples_allocator.allocate(SAMPLE_DURATION_COUNT); if (this->preprocessor_audio_buffer_ == nullptr) { - ESP_LOGE(TAG, "Could not allocate the audio preprocessor's buffer."); - return false; + this->preprocessor_audio_buffer_ = audio_samples_allocator.allocate(this->new_samples_to_get_()); + if (this->preprocessor_audio_buffer_ == nullptr) { + ESP_LOGE(TAG, "Could not allocate the audio preprocessor's buffer."); + return false; + } } - this->preprocessor_model_ = tflite::GetModel(G_AUDIO_PREPROCESSOR_INT8_TFLITE); - if (this->preprocessor_model_->version() != TFLITE_SCHEMA_VERSION) { - ESP_LOGE(TAG, "Wake word's audio preprocessor model's schema is not supported"); - return false; - } - - this->streaming_model_ = tflite::GetModel(this->model_start_); - if (this->streaming_model_->version() != TFLITE_SCHEMA_VERSION) { - ESP_LOGE(TAG, "Wake word's streaming model's schema is not supported"); - return false; - } - - static tflite::MicroMutableOpResolver<18> preprocessor_op_resolver; - static tflite::MicroMutableOpResolver<17> streaming_op_resolver; - - if (!this->register_preprocessor_ops_(preprocessor_op_resolver)) - return false; - if (!this->register_streaming_ops_(streaming_op_resolver)) - return false; - - tflite::MicroAllocator *ma = - tflite::MicroAllocator::Create(this->streaming_var_arena_, STREAMING_MODEL_VARIABLE_ARENA_SIZE); - this->mrv_ = tflite::MicroResourceVariables::Create(ma, 15); - - static tflite::MicroInterpreter static_preprocessor_interpreter( - this->preprocessor_model_, preprocessor_op_resolver, this->preprocessor_tensor_arena_, PREPROCESSOR_ARENA_SIZE); - - static tflite::MicroInterpreter static_streaming_interpreter(this->streaming_model_, streaming_op_resolver, - this->streaming_tensor_arena_, - STREAMING_MODEL_ARENA_SIZE, this->mrv_); - - this->preprocessor_interperter_ = &static_preprocessor_interpreter; - this->streaming_interpreter_ = &static_streaming_interpreter; - - // Allocate tensors for each models. - if (this->preprocessor_interperter_->AllocateTensors() != kTfLiteOk) { - ESP_LOGE(TAG, "Failed to allocate tensors for the audio preprocessor"); - return false; - } - if (this->streaming_interpreter_->AllocateTensors() != kTfLiteOk) { - ESP_LOGE(TAG, "Failed to allocate tensors for the streaming model"); - return false; - } - - // Verify input tensor matches expected values - TfLiteTensor *input = this->streaming_interpreter_->input(0); - if ((input->dims->size != 3) || (input->dims->data[0] != 1) || (input->dims->data[0] != 1) || - (input->dims->data[1] != 1) || (input->dims->data[2] != PREPROCESSOR_FEATURE_SIZE)) { - ESP_LOGE(TAG, "Wake word detection model tensor input dimensions is not 1x1x%u", input->dims->data[2]); - return false; - } - - if (input->type != kTfLiteInt8) { - ESP_LOGE(TAG, "Wake word detection model tensor input is not int8."); - return false; - } - - // Verify output tensor matches expected values - TfLiteTensor *output = this->streaming_interpreter_->output(0); - if ((output->dims->size != 2) || (output->dims->data[0] != 1) || (output->dims->data[1] != 1)) { - ESP_LOGE(TAG, "Wake word detection model tensor output dimensions is not 1x1."); - } - - if (output->type != kTfLiteUInt8) { - ESP_LOGE(TAG, "Wake word detection model tensor input is not uint8."); - return false; - } - - this->recent_streaming_probabilities_.resize(this->sliding_window_average_size_, 0.0); - - return true; -} - -bool MicroWakeWord::update_features_() { - // Retrieve strided audio samples - int16_t *audio_samples = nullptr; - if (!this->stride_audio_samples_(&audio_samples)) { - return false; - } - - // Compute the features for the newest audio samples - if (!this->generate_single_feature_(audio_samples, SAMPLE_DURATION_COUNT, this->new_features_data_)) { - return false; + if (this->ring_buffer_ == nullptr) { + this->ring_buffer_ = RingBuffer::create(BUFFER_SIZE * sizeof(int16_t)); + if (this->ring_buffer_ == nullptr) { + ESP_LOGE(TAG, "Could not allocate ring buffer"); + return false; + } } return true; } -float MicroWakeWord::perform_streaming_inference_() { - TfLiteTensor *input = this->streaming_interpreter_->input(0); - - size_t bytes_to_copy = input->bytes; - - memcpy((void *) (tflite::GetTensorData(input)), (const void *) (this->new_features_data_), bytes_to_copy); - - uint32_t prior_invoke = millis(); - - TfLiteStatus invoke_status = this->streaming_interpreter_->Invoke(); - if (invoke_status != kTfLiteOk) { - ESP_LOGW(TAG, "Streaming Interpreter Invoke failed"); - return false; - } - - ESP_LOGV(TAG, "Streaming Inference Latency=%" PRIu32 " ms", (millis() - prior_invoke)); - - TfLiteTensor *output = this->streaming_interpreter_->output(0); - - return static_cast(output->data.uint8[0]) / 255.0; +void MicroWakeWord::deallocate_buffers_() { + ExternalRAMAllocator audio_samples_allocator(ExternalRAMAllocator::ALLOW_FAILURE); + audio_samples_allocator.deallocate(this->input_buffer_, INPUT_BUFFER_SIZE * sizeof(int16_t)); + this->input_buffer_ = nullptr; + audio_samples_allocator.deallocate(this->preprocessor_audio_buffer_, this->new_samples_to_get_()); + this->preprocessor_audio_buffer_ = nullptr; } -bool MicroWakeWord::detect_wake_word_() { - // Preprocess the newest audio samples into features - if (!this->update_features_()) { +bool MicroWakeWord::load_models_() { + // Setup preprocesor feature generator + if (!FrontendPopulateState(&this->frontend_config_, &this->frontend_state_, AUDIO_SAMPLE_FREQUENCY)) { + ESP_LOGD(TAG, "Failed to populate frontend state"); + FrontendFreeStateContents(&this->frontend_state_); return false; } - // Perform inference - float streaming_prob = this->perform_streaming_inference_(); + // Setup streaming models + for (auto &model : this->wake_word_models_) { + if (!model.load_model(this->streaming_op_resolver_)) { + ESP_LOGE(TAG, "Failed to initialize a wake word model."); + return false; + } + } +#ifdef USE_MICRO_WAKE_WORD_VAD + if (!this->vad_model_->load_model(this->streaming_op_resolver_)) { + ESP_LOGE(TAG, "Failed to initialize VAD model."); + return false; + } +#endif - // Add the most recent probability to the sliding window - this->recent_streaming_probabilities_[this->last_n_index_] = streaming_prob; - ++this->last_n_index_; - if (this->last_n_index_ == this->sliding_window_average_size_) - this->last_n_index_ = 0; + return true; +} - float sum = 0.0; - for (auto &prob : this->recent_streaming_probabilities_) { - sum += prob; +void MicroWakeWord::unload_models_() { + FrontendFreeStateContents(&this->frontend_state_); + + for (auto &model : this->wake_word_models_) { + model.unload_model(); + } +#ifdef USE_MICRO_WAKE_WORD_VAD + this->vad_model_->unload_model(); +#endif +} + +void MicroWakeWord::update_model_probabilities_() { + int8_t audio_features[PREPROCESSOR_FEATURE_SIZE]; + + if (!this->generate_features_for_window_(audio_features)) { + return; } - float sliding_window_average = sum / static_cast(this->sliding_window_average_size_); - - // Ensure we have enough samples since the last positive detection + // Increase the counter since the last positive detection this->ignore_windows_ = std::min(this->ignore_windows_ + 1, 0); + + for (auto &model : this->wake_word_models_) { + // Perform inference + model.perform_streaming_inference(audio_features); + } +#ifdef USE_MICRO_WAKE_WORD_VAD + this->vad_model_->perform_streaming_inference(audio_features); +#endif +} + +bool MicroWakeWord::detect_wake_words_() { + // Verify we have processed samples since the last positive detection if (this->ignore_windows_ < 0) { return false; } - // Detect the wake word if the sliding window average is above the cutoff - if (sliding_window_average > this->probability_cutoff_) { - this->ignore_windows_ = -MIN_SLICES_BEFORE_DETECTION; - for (auto &prob : this->recent_streaming_probabilities_) { - prob = 0; - } +#ifdef USE_MICRO_WAKE_WORD_VAD + bool vad_state = this->vad_model_->determine_detected(); +#endif - ESP_LOGD(TAG, "Wake word sliding average probability is %.3f and most recent probability is %.3f", - sliding_window_average, streaming_prob); - return true; + for (auto &model : this->wake_word_models_) { + if (model.determine_detected()) { +#ifdef USE_MICRO_WAKE_WORD_VAD + if (vad_state) { +#endif + this->detected_wake_word_ = model.get_wake_word(); + return true; +#ifdef USE_MICRO_WAKE_WORD_VAD + } else { + ESP_LOGD(TAG, "Wake word model predicts %s, but VAD model doesn't.", model.get_wake_word().c_str()); + } +#endif + } } return false; } -void MicroWakeWord::set_sliding_window_average_size(size_t size) { - this->sliding_window_average_size_ = size; - this->recent_streaming_probabilities_.resize(this->sliding_window_average_size_, 0.0); +bool MicroWakeWord::has_enough_samples_() { + return this->ring_buffer_->available() >= + (this->features_step_size_ * (AUDIO_SAMPLE_FREQUENCY / 1000)) * sizeof(int16_t); } -bool MicroWakeWord::slice_available_() { - size_t available = this->ring_buffer_->available(); - - return available > (NEW_SAMPLES_TO_GET * sizeof(int16_t)); -} - -bool MicroWakeWord::stride_audio_samples_(int16_t **audio_samples) { - if (!this->slice_available_()) { +bool MicroWakeWord::generate_features_for_window_(int8_t features[PREPROCESSOR_FEATURE_SIZE]) { + // Ensure we have enough new audio samples in the ring buffer for a full window + if (!this->has_enough_samples_()) { return false; } - // Copy the last 320 bytes (160 samples over 10 ms) from the audio buffer to the start of the audio buffer - memcpy((void *) (this->preprocessor_audio_buffer_), (void *) (this->preprocessor_audio_buffer_ + NEW_SAMPLES_TO_GET), - HISTORY_SAMPLES_TO_KEEP * sizeof(int16_t)); - - // Copy 640 bytes (320 samples over 20 ms) from the ring buffer into the audio buffer offset 320 bytes (160 samples - // over 10 ms) - size_t bytes_read = this->ring_buffer_->read((void *) (this->preprocessor_audio_buffer_ + HISTORY_SAMPLES_TO_KEEP), - NEW_SAMPLES_TO_GET * sizeof(int16_t), pdMS_TO_TICKS(200)); + size_t bytes_read = this->ring_buffer_->read((void *) (this->preprocessor_audio_buffer_), + this->new_samples_to_get_() * sizeof(int16_t), pdMS_TO_TICKS(200)); if (bytes_read == 0) { ESP_LOGE(TAG, "Could not read data from Ring Buffer"); - } else if (bytes_read < NEW_SAMPLES_TO_GET * sizeof(int16_t)) { + } else if (bytes_read < this->new_samples_to_get_() * sizeof(int16_t)) { ESP_LOGD(TAG, "Partial Read of Data by Model"); ESP_LOGD(TAG, "Could only read %d bytes when required %d bytes ", bytes_read, - (int) (NEW_SAMPLES_TO_GET * sizeof(int16_t))); + (int) (this->new_samples_to_get_() * sizeof(int16_t))); return false; } - *audio_samples = this->preprocessor_audio_buffer_; - return true; -} + size_t num_samples_read; + struct FrontendOutput frontend_output = FrontendProcessSamples( + &this->frontend_state_, this->preprocessor_audio_buffer_, this->new_samples_to_get_(), &num_samples_read); -bool MicroWakeWord::generate_single_feature_(const int16_t *audio_data, const int audio_data_size, - int8_t feature_output[PREPROCESSOR_FEATURE_SIZE]) { - TfLiteTensor *input = this->preprocessor_interperter_->input(0); - TfLiteTensor *output = this->preprocessor_interperter_->output(0); - std::copy_n(audio_data, audio_data_size, tflite::GetTensorData(input)); - - if (this->preprocessor_interperter_->Invoke() != kTfLiteOk) { - ESP_LOGE(TAG, "Failed to preprocess audio for local wake word."); - return false; + for (size_t i = 0; i < frontend_output.size; ++i) { + // These scaling values are set to match the TFLite audio frontend int8 output. + // The feature pipeline outputs 16-bit signed integers in roughly a 0 to 670 + // range. In training, these are then arbitrarily divided by 25.6 to get + // float values in the rough range of 0.0 to 26.0. This scaling is performed + // for historical reasons, to match up with the output of other feature + // generators. + // The process is then further complicated when we quantize the model. This + // means we have to scale the 0.0 to 26.0 real values to the -128 to 127 + // signed integer numbers. + // All this means that to get matching values from our integer feature + // output into the tensor input, we have to perform: + // input = (((feature / 25.6) / 26.0) * 256) - 128 + // To simplify this and perform it in 32-bit integer math, we rearrange to: + // input = (feature * 256) / (25.6 * 26.0) - 128 + constexpr int32_t value_scale = 256; + constexpr int32_t value_div = 666; // 666 = 25.6 * 26.0 after rounding + int32_t value = ((frontend_output.values[i] * value_scale) + (value_div / 2)) / value_div; + value -= 128; + if (value < -128) { + value = -128; + } + if (value > 127) { + value = 127; + } + features[i] = value; } - std::memcpy(feature_output, tflite::GetTensorData(output), PREPROCESSOR_FEATURE_SIZE * sizeof(int8_t)); return true; } -bool MicroWakeWord::register_preprocessor_ops_(tflite::MicroMutableOpResolver<18> &op_resolver) { - if (op_resolver.AddReshape() != kTfLiteOk) - return false; - if (op_resolver.AddCast() != kTfLiteOk) - return false; - if (op_resolver.AddStridedSlice() != kTfLiteOk) - return false; - if (op_resolver.AddConcatenation() != kTfLiteOk) - return false; - if (op_resolver.AddMul() != kTfLiteOk) - return false; - if (op_resolver.AddAdd() != kTfLiteOk) - return false; - if (op_resolver.AddDiv() != kTfLiteOk) - return false; - if (op_resolver.AddMinimum() != kTfLiteOk) - return false; - if (op_resolver.AddMaximum() != kTfLiteOk) - return false; - if (op_resolver.AddWindow() != kTfLiteOk) - return false; - if (op_resolver.AddFftAutoScale() != kTfLiteOk) - return false; - if (op_resolver.AddRfft() != kTfLiteOk) - return false; - if (op_resolver.AddEnergy() != kTfLiteOk) - return false; - if (op_resolver.AddFilterBank() != kTfLiteOk) - return false; - if (op_resolver.AddFilterBankSquareRoot() != kTfLiteOk) - return false; - if (op_resolver.AddFilterBankSpectralSubtraction() != kTfLiteOk) - return false; - if (op_resolver.AddPCAN() != kTfLiteOk) - return false; - if (op_resolver.AddFilterBankLog() != kTfLiteOk) - return false; - - return true; +void MicroWakeWord::reset_states_() { + ESP_LOGD(TAG, "Resetting buffers and probabilities"); + this->ring_buffer_->reset(); + this->ignore_windows_ = -MIN_SLICES_BEFORE_DETECTION; + for (auto &model : this->wake_word_models_) { + model.reset_probabilities(); + } +#ifdef USE_MICRO_WAKE_WORD_VAD + this->vad_model_->reset_probabilities(); +#endif } -bool MicroWakeWord::register_streaming_ops_(tflite::MicroMutableOpResolver<17> &op_resolver) { +bool MicroWakeWord::register_streaming_ops_(tflite::MicroMutableOpResolver<20> &op_resolver) { if (op_resolver.AddCallOnce() != kTfLiteOk) return false; if (op_resolver.AddVarHandle() != kTfLiteOk) @@ -496,6 +442,12 @@ bool MicroWakeWord::register_streaming_ops_(tflite::MicroMutableOpResolver<17> & return false; if (op_resolver.AddMaxPool2D() != kTfLiteOk) return false; + if (op_resolver.AddPad() != kTfLiteOk) + return false; + if (op_resolver.AddPack() != kTfLiteOk) + return false; + if (op_resolver.AddSplitV() != kTfLiteOk) + return false; return true; } @@ -504,5 +456,3 @@ bool MicroWakeWord::register_streaming_ops_(tflite::MicroMutableOpResolver<17> & } // namespace esphome #endif // USE_ESP_IDF - -#endif // CLANG_TIDY diff --git a/esphome/components/micro_wake_word/micro_wake_word.h b/esphome/components/micro_wake_word/micro_wake_word.h index 1d7c18d686..0c805b75fc 100644 --- a/esphome/components/micro_wake_word/micro_wake_word.h +++ b/esphome/components/micro_wake_word/micro_wake_word.h @@ -1,21 +1,18 @@ #pragma once -/** - * This is a workaround until we can figure out a way to get - * the tflite-micro idf component code available in CI - * - * */ -// -#ifndef CLANG_TIDY - #ifdef USE_ESP_IDF +#include "preprocessor_settings.h" +#include "streaming_model.h" + #include "esphome/core/automation.h" #include "esphome/core/component.h" #include "esphome/core/ring_buffer.h" #include "esphome/components/microphone/microphone.h" +#include + #include #include #include @@ -23,35 +20,6 @@ namespace esphome { namespace micro_wake_word { -// The following are dictated by the preprocessor model -// -// The number of features the audio preprocessor generates per slice -static const uint8_t PREPROCESSOR_FEATURE_SIZE = 40; -// How frequently the preprocessor generates a new set of features -static const uint8_t FEATURE_STRIDE_MS = 20; -// Duration of each slice used as input into the preprocessor -static const uint8_t FEATURE_DURATION_MS = 30; -// Audio sample frequency in hertz -static const uint16_t AUDIO_SAMPLE_FREQUENCY = 16000; -// The number of old audio samples that are saved to be part of the next feature window -static const uint16_t HISTORY_SAMPLES_TO_KEEP = - ((FEATURE_DURATION_MS - FEATURE_STRIDE_MS) * (AUDIO_SAMPLE_FREQUENCY / 1000)); -// The number of new audio samples to receive to be included with the next feature window -static const uint16_t NEW_SAMPLES_TO_GET = (FEATURE_STRIDE_MS * (AUDIO_SAMPLE_FREQUENCY / 1000)); -// The total number of audio samples included in the feature window -static const uint16_t SAMPLE_DURATION_COUNT = FEATURE_DURATION_MS * AUDIO_SAMPLE_FREQUENCY / 1000; -// Number of bytes in memory needed for the preprocessor arena -static const uint32_t PREPROCESSOR_ARENA_SIZE = 9528; - -// The following configure the streaming wake word model -// -// The number of audio slices to process before accepting a positive detection -static const uint8_t MIN_SLICES_BEFORE_DETECTION = 74; - -// Number of bytes in memory needed for the streaming wake word model -static const uint32_t STREAMING_MODEL_ARENA_SIZE = 64000; -static const uint32_t STREAMING_MODEL_VARIABLE_ARENA_SIZE = 1024; - enum State { IDLE, START_MICROPHONE, @@ -61,6 +29,9 @@ enum State { STOPPING_MICROPHONE, }; +// The number of audio slices to process before accepting a positive detection +static const uint8_t MIN_SLICES_BEFORE_DETECTION = 74; + class MicroWakeWord : public Component { public: void setup() override; @@ -73,28 +44,21 @@ class MicroWakeWord : public Component { bool is_running() const { return this->state_ != State::IDLE; } - bool initialize_models(); - - std::string get_wake_word() { return this->wake_word_; } - - // Increasing either of these will reduce the rate of false acceptances while increasing the false rejection rate - void set_probability_cutoff(float probability_cutoff) { this->probability_cutoff_ = probability_cutoff; } - void set_sliding_window_average_size(size_t size); + void set_features_step_size(uint8_t step_size) { this->features_step_size_ = step_size; } void set_microphone(microphone::Microphone *microphone) { this->microphone_ = microphone; } Trigger *get_wake_word_detected_trigger() const { return this->wake_word_detected_trigger_; } - void set_model_start(const uint8_t *model_start) { this->model_start_ = model_start; } - void set_wake_word(const std::string &wake_word) { this->wake_word_ = wake_word; } + void add_wake_word_model(const uint8_t *model_start, float probability_cutoff, size_t sliding_window_average_size, + const std::string &wake_word, size_t tensor_arena_size); + +#ifdef USE_MICRO_WAKE_WORD_VAD + void add_vad_model(const uint8_t *model_start, float probability_cutoff, size_t sliding_window_size, + size_t tensor_arena_size); +#endif protected: - void set_state_(State state); - int read_microphone_(); - - const uint8_t *model_start_; - std::string wake_word_; - microphone::Microphone *microphone_{nullptr}; Trigger *wake_word_detected_trigger_ = new Trigger(); State state_{State::IDLE}; @@ -102,85 +66,93 @@ class MicroWakeWord : public Component { std::unique_ptr ring_buffer_; - int16_t *input_buffer_; + std::vector wake_word_models_; - const tflite::Model *preprocessor_model_{nullptr}; - const tflite::Model *streaming_model_{nullptr}; - tflite::MicroInterpreter *streaming_interpreter_{nullptr}; - tflite::MicroInterpreter *preprocessor_interperter_{nullptr}; +#ifdef USE_MICRO_WAKE_WORD_VAD + std::unique_ptr vad_model_; +#endif - std::vector recent_streaming_probabilities_; - size_t last_n_index_{0}; + tflite::MicroMutableOpResolver<20> streaming_op_resolver_; - float probability_cutoff_{0.5}; - size_t sliding_window_average_size_{10}; + // Audio frontend handles generating spectrogram features + struct FrontendConfig frontend_config_; + struct FrontendState frontend_state_; - // When the wake word detection first starts or after the word has been detected once, we ignore this many audio - // feature slices before accepting a positive detection again + // When the wake word detection first starts, we ignore this many audio + // feature slices before accepting a positive detection int16_t ignore_windows_{-MIN_SLICES_BEFORE_DETECTION}; - uint8_t *streaming_var_arena_{nullptr}; - uint8_t *streaming_tensor_arena_{nullptr}; - uint8_t *preprocessor_tensor_arena_{nullptr}; - int8_t *new_features_data_{nullptr}; + uint8_t features_step_size_; - tflite::MicroResourceVariables *mrv_{nullptr}; - - // Stores audio fed into feature generator preprocessor - int16_t *preprocessor_audio_buffer_; + // Stores audio read from the microphone before being added to the ring buffer. + int16_t *input_buffer_{nullptr}; + // Stores audio to be fed into the audio frontend for generating features. + int16_t *preprocessor_audio_buffer_{nullptr}; bool detected_{false}; + std::string detected_wake_word_{""}; - /** Detects if wake word has been said + void set_state_(State state); + + /// @brief Tests if there are enough samples in the ring buffer to generate new features. + /// @return True if enough samples, false otherwise. + bool has_enough_samples_(); + + /** Reads audio from microphone into the ring buffer + * + * Audio data (16000 kHz with int16 samples) is read into the input_buffer_. + * Verifies the ring buffer has enough space for all audio data. If not, it logs + * a warning and resets the ring buffer entirely. + * @return Number of bytes written to the ring buffer + */ + size_t read_microphone_(); + + /// @brief Allocates memory for input_buffer_, preprocessor_audio_buffer_, and ring_buffer_ + /// @return True if successful, false otherwise + bool allocate_buffers_(); + + /// @brief Frees memory allocated for input_buffer_ and preprocessor_audio_buffer_ + void deallocate_buffers_(); + + /// @brief Loads streaming models and prepares the feature generation frontend + /// @return True if successful, false otherwise + bool load_models_(); + + /// @brief Deletes each model's TFLite interpreters and frees tensor arena memory. Frees memory used by the feature + /// generation frontend. + void unload_models_(); + + /** Performs inference with each configured model * * If enough audio samples are available, it will generate one slice of new features. - * If the streaming model predicts the wake word, then the nonstreaming model confirms it. - * @param ring_Buffer Ring buffer containing raw audio samples - * @return True if the wake word is detected, false otherwise + * It then loops through and performs inference with each of the loaded models. */ - bool detect_wake_word_(); + void update_model_probabilities_(); - /// @brief Returns true if there are enough audio samples in the buffer to generate another slice of features - bool slice_available_(); - - /** Shifts previous feature slices over by one and generates a new slice of features + /** Checks every model's recent probabilities to determine if the wake word has been predicted * - * @param ring_buffer ring buffer containing raw audio samples - * @return True if a new slice of features was generated, false otherwise + * Verifies the models have processed enough new samples for accurate predictions. + * Sets detected_wake_word_ to the wake word, if one is detected. + * @return True if a wake word is predicted, false otherwise */ - bool update_features_(); + bool detect_wake_words_(); - /** Generates features from audio samples + /** Generates features for a window of audio samples * - * Adapted from TFLite micro speech example - * @param audio_data Pointer to array with the audio samples - * @param audio_data_size The number of samples to use as input to the preprocessor model - * @param feature_output Array that will store the features + * Reads samples from the ring buffer and feeds them into the preprocessor frontend. + * Adapted from TFLite microspeech frontend. + * @param features int8_t array to store the audio features * @return True if successful, false otherwise. */ - bool generate_single_feature_(const int16_t *audio_data, int audio_data_size, - int8_t feature_output[PREPROCESSOR_FEATURE_SIZE]); + bool generate_features_for_window_(int8_t features[PREPROCESSOR_FEATURE_SIZE]); - /** Performs inference over the most recent feature slice with the streaming model - * - * @return Probability of the wake word between 0.0 and 1.0 - */ - float perform_streaming_inference_(); - - /** Strides the audio samples by keeping the last 10 ms of the previous slice - * - * Adapted from the TFLite micro speech example - * @param ring_buffer Ring buffer containing raw audio samples - * @param audio_samples Pointer to an array that will store the strided audio samples - * @return True if successful, false otherwise - */ - bool stride_audio_samples_(int16_t **audio_samples); - - /// @brief Returns true if successfully registered the preprocessor's TensorFlow operations - bool register_preprocessor_ops_(tflite::MicroMutableOpResolver<18> &op_resolver); + /// @brief Resets the ring buffer, ignore_windows_, and sliding window probabilities + void reset_states_(); /// @brief Returns true if successfully registered the streaming model's TensorFlow operations - bool register_streaming_ops_(tflite::MicroMutableOpResolver<17> &op_resolver); + bool register_streaming_ops_(tflite::MicroMutableOpResolver<20> &op_resolver); + + inline uint16_t new_samples_to_get_() { return (this->features_step_size_ * (AUDIO_SAMPLE_FREQUENCY / 1000)); } }; template class StartAction : public Action, public Parented { @@ -202,5 +174,3 @@ template class IsRunningCondition : public Condition, pub } // namespace esphome #endif // USE_ESP_IDF - -#endif // CLANG_TIDY diff --git a/esphome/components/micro_wake_word/preprocessor_settings.h b/esphome/components/micro_wake_word/preprocessor_settings.h new file mode 100644 index 0000000000..03f4fb5230 --- /dev/null +++ b/esphome/components/micro_wake_word/preprocessor_settings.h @@ -0,0 +1,20 @@ +#pragma once + +#ifdef USE_ESP_IDF + +#include + +namespace esphome { +namespace micro_wake_word { + +// The number of features the audio preprocessor generates per slice +static const uint8_t PREPROCESSOR_FEATURE_SIZE = 40; +// Duration of each slice used as input into the preprocessor +static const uint8_t FEATURE_DURATION_MS = 30; +// Audio sample frequency in hertz +static const uint16_t AUDIO_SAMPLE_FREQUENCY = 16000; + +} // namespace micro_wake_word +} // namespace esphome + +#endif diff --git a/esphome/components/micro_wake_word/streaming_model.cpp b/esphome/components/micro_wake_word/streaming_model.cpp new file mode 100644 index 0000000000..013fa2ce6e --- /dev/null +++ b/esphome/components/micro_wake_word/streaming_model.cpp @@ -0,0 +1,189 @@ +#ifdef USE_ESP_IDF + +#include "streaming_model.h" + +#include "esphome/core/hal.h" +#include "esphome/core/helpers.h" +#include "esphome/core/log.h" + +static const char *const TAG = "micro_wake_word"; + +namespace esphome { +namespace micro_wake_word { + +void WakeWordModel::log_model_config() { + ESP_LOGCONFIG(TAG, " - Wake Word: %s", this->wake_word_.c_str()); + ESP_LOGCONFIG(TAG, " Probability cutoff: %.3f", this->probability_cutoff_); + ESP_LOGCONFIG(TAG, " Sliding window size: %d", this->sliding_window_size_); +} + +void VADModel::log_model_config() { + ESP_LOGCONFIG(TAG, " - VAD Model"); + ESP_LOGCONFIG(TAG, " Probability cutoff: %.3f", this->probability_cutoff_); + ESP_LOGCONFIG(TAG, " Sliding window size: %d", this->sliding_window_size_); +} + +bool StreamingModel::load_model(tflite::MicroMutableOpResolver<20> &op_resolver) { + ExternalRAMAllocator arena_allocator(ExternalRAMAllocator::ALLOW_FAILURE); + + if (this->tensor_arena_ == nullptr) { + this->tensor_arena_ = arena_allocator.allocate(this->tensor_arena_size_); + if (this->tensor_arena_ == nullptr) { + ESP_LOGE(TAG, "Could not allocate the streaming model's tensor arena."); + return false; + } + } + + if (this->var_arena_ == nullptr) { + this->var_arena_ = arena_allocator.allocate(STREAMING_MODEL_VARIABLE_ARENA_SIZE); + if (this->var_arena_ == nullptr) { + ESP_LOGE(TAG, "Could not allocate the streaming model's variable tensor arena."); + return false; + } + this->ma_ = tflite::MicroAllocator::Create(this->var_arena_, STREAMING_MODEL_VARIABLE_ARENA_SIZE); + this->mrv_ = tflite::MicroResourceVariables::Create(this->ma_, 20); + } + + const tflite::Model *model = tflite::GetModel(this->model_start_); + if (model->version() != TFLITE_SCHEMA_VERSION) { + ESP_LOGE(TAG, "Streaming model's schema is not supported"); + return false; + } + + if (this->interpreter_ == nullptr) { + this->interpreter_ = make_unique( + tflite::GetModel(this->model_start_), op_resolver, this->tensor_arena_, this->tensor_arena_size_, this->mrv_); + if (this->interpreter_->AllocateTensors() != kTfLiteOk) { + ESP_LOGE(TAG, "Failed to allocate tensors for the streaming model"); + return false; + } + + // Verify input tensor matches expected values + // Dimension 3 will represent the first layer stride, so skip it may vary + TfLiteTensor *input = this->interpreter_->input(0); + if ((input->dims->size != 3) || (input->dims->data[0] != 1) || + (input->dims->data[2] != PREPROCESSOR_FEATURE_SIZE)) { + ESP_LOGE(TAG, "Streaming model tensor input dimensions has improper dimensions."); + return false; + } + + if (input->type != kTfLiteInt8) { + ESP_LOGE(TAG, "Streaming model tensor input is not int8."); + return false; + } + + // Verify output tensor matches expected values + TfLiteTensor *output = this->interpreter_->output(0); + if ((output->dims->size != 2) || (output->dims->data[0] != 1) || (output->dims->data[1] != 1)) { + ESP_LOGE(TAG, "Streaming model tensor output dimension is not 1x1."); + } + + if (output->type != kTfLiteUInt8) { + ESP_LOGE(TAG, "Streaming model tensor output is not uint8."); + return false; + } + } + + return true; +} + +void StreamingModel::unload_model() { + this->interpreter_.reset(); + + ExternalRAMAllocator arena_allocator(ExternalRAMAllocator::ALLOW_FAILURE); + + arena_allocator.deallocate(this->tensor_arena_, this->tensor_arena_size_); + this->tensor_arena_ = nullptr; + arena_allocator.deallocate(this->var_arena_, STREAMING_MODEL_VARIABLE_ARENA_SIZE); + this->var_arena_ = nullptr; +} + +bool StreamingModel::perform_streaming_inference(const int8_t features[PREPROCESSOR_FEATURE_SIZE]) { + if (this->interpreter_ != nullptr) { + TfLiteTensor *input = this->interpreter_->input(0); + + std::memmove( + (int8_t *) (tflite::GetTensorData(input)) + PREPROCESSOR_FEATURE_SIZE * this->current_stride_step_, + features, PREPROCESSOR_FEATURE_SIZE); + ++this->current_stride_step_; + + uint8_t stride = this->interpreter_->input(0)->dims->data[1]; + + if (this->current_stride_step_ >= stride) { + this->current_stride_step_ = 0; + + TfLiteStatus invoke_status = this->interpreter_->Invoke(); + if (invoke_status != kTfLiteOk) { + ESP_LOGW(TAG, "Streaming interpreter invoke failed"); + return false; + } + + TfLiteTensor *output = this->interpreter_->output(0); + + ++this->last_n_index_; + if (this->last_n_index_ == this->sliding_window_size_) + this->last_n_index_ = 0; + this->recent_streaming_probabilities_[this->last_n_index_] = output->data.uint8[0]; // probability; + } + return true; + } + ESP_LOGE(TAG, "Streaming interpreter is not initialized."); + return false; +} + +void StreamingModel::reset_probabilities() { + for (auto &prob : this->recent_streaming_probabilities_) { + prob = 0; + } +} + +WakeWordModel::WakeWordModel(const uint8_t *model_start, float probability_cutoff, size_t sliding_window_average_size, + const std::string &wake_word, size_t tensor_arena_size) { + this->model_start_ = model_start; + this->probability_cutoff_ = probability_cutoff; + this->sliding_window_size_ = sliding_window_average_size; + this->recent_streaming_probabilities_.resize(sliding_window_average_size, 0); + this->wake_word_ = wake_word; + this->tensor_arena_size_ = tensor_arena_size; +}; + +bool WakeWordModel::determine_detected() { + int32_t sum = 0; + for (auto &prob : this->recent_streaming_probabilities_) { + sum += prob; + } + + float sliding_window_average = static_cast(sum) / static_cast(255 * this->sliding_window_size_); + + // Detect the wake word if the sliding window average is above the cutoff + if (sliding_window_average > this->probability_cutoff_) { + ESP_LOGD(TAG, "The '%s' model sliding average probability is %.3f and most recent probability is %.3f", + this->wake_word_.c_str(), sliding_window_average, + this->recent_streaming_probabilities_[this->last_n_index_] / (255.0)); + return true; + } + return false; +} + +VADModel::VADModel(const uint8_t *model_start, float probability_cutoff, size_t sliding_window_size, + size_t tensor_arena_size) { + this->model_start_ = model_start; + this->probability_cutoff_ = probability_cutoff; + this->sliding_window_size_ = sliding_window_size; + this->recent_streaming_probabilities_.resize(sliding_window_size, 0); + this->tensor_arena_size_ = tensor_arena_size; +}; + +bool VADModel::determine_detected() { + uint8_t max = 0; + for (auto &prob : this->recent_streaming_probabilities_) { + max = std::max(prob, max); + } + + return max > this->probability_cutoff_; +} + +} // namespace micro_wake_word +} // namespace esphome + +#endif diff --git a/esphome/components/micro_wake_word/streaming_model.h b/esphome/components/micro_wake_word/streaming_model.h new file mode 100644 index 0000000000..0d85579f35 --- /dev/null +++ b/esphome/components/micro_wake_word/streaming_model.h @@ -0,0 +1,84 @@ +#pragma once + +#ifdef USE_ESP_IDF + +#include "preprocessor_settings.h" + +#include +#include +#include + +namespace esphome { +namespace micro_wake_word { + +static const uint32_t STREAMING_MODEL_VARIABLE_ARENA_SIZE = 1024; + +class StreamingModel { + public: + virtual void log_model_config() = 0; + virtual bool determine_detected() = 0; + + bool perform_streaming_inference(const int8_t features[PREPROCESSOR_FEATURE_SIZE]); + + /// @brief Sets all recent_streaming_probabilities to 0 + void reset_probabilities(); + + /// @brief Allocates tensor and variable arenas and sets up the model interpreter + /// @param op_resolver MicroMutableOpResolver object that must exist until the model is unloaded + /// @return True if successful, false otherwise + bool load_model(tflite::MicroMutableOpResolver<20> &op_resolver); + + /// @brief Destroys the TFLite interpreter and frees the tensor and variable arenas' memory + void unload_model(); + + protected: + uint8_t current_stride_step_{0}; + + float probability_cutoff_; + size_t sliding_window_size_; + size_t last_n_index_{0}; + size_t tensor_arena_size_; + std::vector recent_streaming_probabilities_; + + const uint8_t *model_start_; + uint8_t *tensor_arena_{nullptr}; + uint8_t *var_arena_{nullptr}; + std::unique_ptr interpreter_; + tflite::MicroResourceVariables *mrv_{nullptr}; + tflite::MicroAllocator *ma_{nullptr}; +}; + +class WakeWordModel final : public StreamingModel { + public: + WakeWordModel(const uint8_t *model_start, float probability_cutoff, size_t sliding_window_average_size, + const std::string &wake_word, size_t tensor_arena_size); + + void log_model_config() override; + + /// @brief Checks for the wake word by comparing the mean probability in the sliding window with the probability + /// cutoff + /// @return True if wake word is detected, false otherwise + bool determine_detected() override; + + const std::string &get_wake_word() const { return this->wake_word_; } + + protected: + std::string wake_word_; +}; + +class VADModel final : public StreamingModel { + public: + VADModel(const uint8_t *model_start, float probability_cutoff, size_t sliding_window_size, size_t tensor_arena_size); + + void log_model_config() override; + + /// @brief Checks for voice activity by comparing the max probability in the sliding window with the probability + /// cutoff + /// @return True if voice activity is detected, false otherwise + bool determine_detected() override; +}; + +} // namespace micro_wake_word +} // namespace esphome + +#endif diff --git a/esphome/components/mitsubishi/mitsubishi.cpp b/esphome/components/mitsubishi/mitsubishi.cpp index fd57adc586..a02aabf14d 100644 --- a/esphome/components/mitsubishi/mitsubishi.cpp +++ b/esphome/components/mitsubishi/mitsubishi.cpp @@ -52,6 +52,7 @@ const uint8_t MITSUBISHI_BYTE16 = 0X00; climate::ClimateTraits MitsubishiClimate::traits() { auto traits = climate::ClimateTraits(); + traits.set_supports_current_temperature(this->sensor_ != nullptr); traits.set_supports_action(false); traits.set_visual_min_temperature(MITSUBISHI_TEMP_MIN); traits.set_visual_max_temperature(MITSUBISHI_TEMP_MAX); diff --git a/esphome/components/pmsa003i/pmsa003i.cpp b/esphome/components/pmsa003i/pmsa003i.cpp index ca3d28367a..a9665c6a5a 100644 --- a/esphome/components/pmsa003i/pmsa003i.cpp +++ b/esphome/components/pmsa003i/pmsa003i.cpp @@ -13,6 +13,15 @@ void PMSA003IComponent::setup() { PM25AQIData data; bool successful_read = this->read_data_(&data); + if (!successful_read) { + for (int i = 0; i < 3; i++) { + successful_read = this->read_data_(&data); + if (successful_read) { + break; + } + } + } + if (!successful_read) { this->mark_failed(); return; diff --git a/esphome/components/remote_base/rc_switch_protocol.cpp b/esphome/components/remote_base/rc_switch_protocol.cpp index 1f38fdca67..cb8a077975 100644 --- a/esphome/components/remote_base/rc_switch_protocol.cpp +++ b/esphome/components/remote_base/rc_switch_protocol.cpp @@ -54,7 +54,7 @@ void RCSwitchBase::sync(RemoteTransmitData *dst) const { } } void RCSwitchBase::transmit(RemoteTransmitData *dst, uint64_t code, uint8_t len) const { - dst->set_carrier_frequency(0); + dst->set_carrier_frequency(38000); this->sync(dst); for (int16_t i = len - 1; i >= 0; i--) { if (code & ((uint64_t) 1 << i)) { diff --git a/esphome/components/uart/__init__.py b/esphome/components/uart/__init__.py index b036288078..0738a127e1 100644 --- a/esphome/components/uart/__init__.py +++ b/esphome/components/uart/__init__.py @@ -1,5 +1,5 @@ from typing import Optional - +import re import esphome.codegen as cg import esphome.config_validation as cv import esphome.final_validate as fv @@ -11,6 +11,7 @@ from esphome.const import ( CONF_NUMBER, CONF_RX_PIN, CONF_TX_PIN, + CONF_PORT, CONF_UART_ID, CONF_DATA, CONF_RX_BUFFER_SIZE, @@ -27,6 +28,7 @@ from esphome.const import ( CONF_DUMMY_RECEIVER, CONF_DUMMY_RECEIVER_ID, CONF_LAMBDA, + PLATFORM_HOST, ) from esphome.core import CORE @@ -45,6 +47,7 @@ RP2040UartComponent = uart_ns.class_("RP2040UartComponent", UARTComponent, cg.Co LibreTinyUARTComponent = uart_ns.class_( "LibreTinyUARTComponent", UARTComponent, cg.Component ) +HostUartComponent = uart_ns.class_("HostUartComponent", UARTComponent, cg.Component) NATIVE_UART_CLASSES = ( str(IDFUARTComponent), @@ -54,6 +57,39 @@ NATIVE_UART_CLASSES = ( str(LibreTinyUARTComponent), ) +HOST_BAUD_RATES = [ + 50, + 75, + 110, + 134, + 150, + 200, + 300, + 600, + 1200, + 1800, + 2400, + 4800, + 9600, + 19200, + 38400, + 57600, + 115200, + 230400, + 460800, + 500000, + 576000, + 921600, + 1000000, + 1152000, + 1500000, + 2000000, + 2500000, + 3000000, + 3500000, + 4000000, +] + UARTDevice = uart_ns.class_("UARTDevice") UARTWriteAction = uart_ns.class_("UARTWriteAction", automation.Action) UARTDebugger = uart_ns.class_("UARTDebugger", cg.Component, automation.Action) @@ -95,6 +131,20 @@ def validate_invert_esp32(config): return config +def validate_host_config(config): + if CORE.is_host: + if CONF_TX_PIN in config or CONF_RX_PIN in config: + raise cv.Invalid( + "TX and RX pins are not supported for UART on host platform." + ) + if config[CONF_BAUD_RATE] not in HOST_BAUD_RATES: + raise cv.Invalid( + f"Host platform doesn't support baud rate {config[CONF_BAUD_RATE]}", + path=[CONF_BAUD_RATE], + ) + return config + + def _uart_declare_type(value): if CORE.is_esp8266: return cv.declare_id(ESP8266UartComponent)(value) @@ -107,6 +157,8 @@ def _uart_declare_type(value): return cv.declare_id(RP2040UartComponent)(value) if CORE.is_libretiny: return cv.declare_id(LibreTinyUARTComponent)(value) + if CORE.is_host: + return cv.declare_id(HostUartComponent)(value) raise NotImplementedError @@ -149,6 +201,12 @@ def maybe_empty_debug(value): return DEBUG_SCHEMA(value) +def validate_port(value): + if not re.match(r"^/(?:[^/]+/)[^/]+$", value): + raise cv.Invalid("Port must be a valid device path") + return value + + DEBUG_SCHEMA = cv.Schema( { cv.GenerateID(CONF_TRIGGER_ID): cv.declare_id(UARTDebugger), @@ -181,6 +239,7 @@ CONFIG_SCHEMA = cv.All( cv.Required(CONF_BAUD_RATE): cv.int_range(min=1), cv.Optional(CONF_TX_PIN): pins.internal_gpio_output_pin_schema, cv.Optional(CONF_RX_PIN): validate_rx_pin, + cv.Optional(CONF_PORT): cv.All(validate_port, cv.only_on(PLATFORM_HOST)), cv.Optional(CONF_RX_BUFFER_SIZE, default=256): cv.validate_bytes, cv.Optional(CONF_STOP_BITS, default=1): cv.one_of(1, 2, int=True), cv.Optional(CONF_DATA_BITS, default=8): cv.int_range(min=5, max=8), @@ -193,8 +252,9 @@ CONFIG_SCHEMA = cv.All( cv.Optional(CONF_DEBUG): maybe_empty_debug, } ).extend(cv.COMPONENT_SCHEMA), - cv.has_at_least_one_key(CONF_TX_PIN, CONF_RX_PIN), + cv.has_at_least_one_key(CONF_TX_PIN, CONF_RX_PIN, CONF_PORT), validate_invert_esp32, + validate_host_config, ) @@ -236,6 +296,8 @@ async def to_code(config): if CONF_RX_PIN in config: rx_pin = await cg.gpio_pin_expression(config[CONF_RX_PIN]) cg.add(var.set_rx_pin(rx_pin)) + if CONF_PORT in config: + cg.add(var.set_name(config[CONF_PORT])) cg.add(var.set_rx_buffer_size(config[CONF_RX_BUFFER_SIZE])) cg.add(var.set_stop_bits(config[CONF_STOP_BITS])) cg.add(var.set_data_bits(config[CONF_DATA_BITS])) diff --git a/esphome/components/uart/uart_component_host.cpp b/esphome/components/uart/uart_component_host.cpp new file mode 100644 index 0000000000..d8d2fd75b8 --- /dev/null +++ b/esphome/components/uart/uart_component_host.cpp @@ -0,0 +1,295 @@ +#ifdef USE_HOST +#include "uart_component_host.h" +#include "esphome/core/application.h" +#include "esphome/core/defines.h" +#include "esphome/core/helpers.h" +#include "esphome/core/log.h" + +#ifndef __linux__ +#error This HostUartComponent implementation is only for Linux +#endif + +#include +#include +#include +#include +#include +#include +#include + +#ifdef USE_LOGGER +#include "esphome/components/logger/logger.h" +#endif + +namespace { + +speed_t get_baud(int baud) { + switch (baud) { + case 50: + return B50; + case 75: + return B75; + case 110: + return B110; + case 134: + return B134; + case 150: + return B150; + case 200: + return B200; + case 300: + return B300; + case 600: + return B600; + case 1200: + return B1200; + case 1800: + return B1800; + case 2400: + return B2400; + case 4800: + return B4800; + case 9600: + return B9600; + case 19200: + return B19200; + case 38400: + return B38400; + case 57600: + return B57600; + case 115200: + return B115200; + case 230400: + return B230400; + case 460800: + return B460800; + case 500000: + return B500000; + case 576000: + return B576000; + case 921600: + return B921600; + case 1000000: + return B1000000; + case 1152000: + return B1152000; + case 1500000: + return B1500000; + case 2000000: + return B2000000; + case 2500000: + return B2500000; + case 3000000: + return B3000000; + case 3500000: + return B3500000; + case 4000000: + return B4000000; + default: + return B0; + } +} + +} // namespace + +namespace esphome { +namespace uart { + +static const char *const TAG = "uart.host"; + +HostUartComponent::~HostUartComponent() { + if (this->file_descriptor_ != -1) { + close(this->file_descriptor_); + this->file_descriptor_ = -1; + } +} + +void HostUartComponent::setup() { + ESP_LOGCONFIG(TAG, "Opening UART port..."); + speed_t baud = get_baud(this->baud_rate_); + if (baud == B0) { + ESP_LOGE(TAG, "Unsupported baud rate: %d", this->baud_rate_); + this->mark_failed(); + return; + } + this->file_descriptor_ = ::open(this->port_name_.c_str(), O_RDWR | O_NOCTTY | O_NDELAY); + if (this->file_descriptor_ == -1) { + this->update_error_(strerror(errno)); + this->mark_failed(); + return; + } + fcntl(this->file_descriptor_, F_SETFL, 0); + struct termios options; + tcgetattr(this->file_descriptor_, &options); + options.c_cflag &= ~CRTSCTS; + options.c_cflag |= CREAD | CLOCAL; + options.c_lflag &= ~ICANON; + options.c_lflag &= ~ECHO; + options.c_lflag &= ~ECHOE; + options.c_lflag &= ~ECHONL; + options.c_lflag &= ~ISIG; + options.c_iflag &= ~(IXON | IXOFF | IXANY); + options.c_iflag &= ~(IGNBRK | BRKINT | PARMRK | ISTRIP | INLCR | IGNCR | ICRNL); + options.c_oflag &= ~OPOST; + options.c_oflag &= ~ONLCR; + // Set data bits + options.c_cflag &= ~CSIZE; // Mask the character size bits + switch (this->data_bits_) { + case 5: + options.c_cflag |= CS5; + break; + case 6: + options.c_cflag |= CS6; + break; + case 7: + options.c_cflag |= CS7; + break; + case 8: + default: + options.c_cflag |= CS8; + break; + } + // Set parity + switch (this->parity_) { + case UART_CONFIG_PARITY_NONE: + options.c_cflag &= ~PARENB; + break; + case UART_CONFIG_PARITY_EVEN: + options.c_cflag |= PARENB; + options.c_cflag &= ~PARODD; + break; + case UART_CONFIG_PARITY_ODD: + options.c_cflag |= PARENB; + options.c_cflag |= PARODD; + break; + }; + // Set stop bits + if (this->stop_bits_ == 2) { + options.c_cflag |= CSTOPB; + } else { + options.c_cflag &= ~CSTOPB; + } + cfsetispeed(&options, baud); + cfsetospeed(&options, baud); + tcsetattr(this->file_descriptor_, TCSANOW, &options); +} + +void HostUartComponent::dump_config() { + ESP_LOGCONFIG(TAG, "UART:"); + ESP_LOGCONFIG(TAG, " Port: %s", this->port_name_.c_str()); + if (this->file_descriptor_ == -1) { + ESP_LOGCONFIG(TAG, " Port status: Not opened"); + if (!this->first_error_.empty()) { + ESP_LOGCONFIG(TAG, " Error: %s", this->first_error_.c_str()); + } + return; + } + ESP_LOGCONFIG(TAG, " Port status: opened"); + ESP_LOGCONFIG(TAG, " Baud Rate: %d", this->baud_rate_); + ESP_LOGCONFIG(TAG, " Data Bits: %d", this->data_bits_); + ESP_LOGCONFIG(TAG, " Parity: %s", + this->parity_ == UART_CONFIG_PARITY_NONE ? "None" + : this->parity_ == UART_CONFIG_PARITY_EVEN ? "Even" + : "Odd"); + ESP_LOGCONFIG(TAG, " Stop Bits: %d", this->stop_bits_); + this->check_logger_conflict(); +} + +void HostUartComponent::write_array(const uint8_t *data, size_t len) { + if (this->file_descriptor_ == -1) { + return; + } + size_t written = ::write(this->file_descriptor_, data, len); + if (written != len) { + this->update_error_(strerror(errno)); + return; + } +#ifdef USE_UART_DEBUGGER + for (size_t i = 0; i < len; i++) { + this->debug_callback_.call(UART_DIRECTION_TX, data[i]); + } +#endif + return; +} + +bool HostUartComponent::peek_byte(uint8_t *data) { + if (this->file_descriptor_ == -1) { + return false; + } + if (!this->has_peek_) { + if (!this->check_read_timeout_()) { + return false; + } + if (::read(this->file_descriptor_, &this->peek_byte_, 1) != 1) { + this->update_error_(strerror(errno)); + return false; + } + this->has_peek_ = true; + } + *data = this->peek_byte_; + return true; +} + +bool HostUartComponent::read_array(uint8_t *data, size_t len) { + if ((this->file_descriptor_ == -1) || (len == 0)) { + return false; + } + if (!this->check_read_timeout_(len)) + return false; + uint8_t *data_ptr = data; + size_t length_to_read = len; + if (this->has_peek_) { + length_to_read--; + *data_ptr = this->peek_byte_; + data_ptr++; + this->has_peek_ = false; + } + if (length_to_read > 0) { + int sz = ::read(this->file_descriptor_, data_ptr, length_to_read); + if (sz == -1) { + this->update_error_(strerror(errno)); + return false; + } + } +#ifdef USE_UART_DEBUGGER + for (size_t i = 0; i < len; i++) { + this->debug_callback_.call(UART_DIRECTION_RX, data[i]); + } +#endif + return true; +} + +int HostUartComponent::available() { + if (this->file_descriptor_ == -1) { + return 0; + } + int available; + int res = ioctl(this->file_descriptor_, FIONREAD, &available); + if (res == -1) { + this->update_error_(strerror(errno)); + return 0; + } + if (this->has_peek_) + available++; + return available; +}; + +void HostUartComponent::flush() { + if (this->file_descriptor_ == -1) { + return; + } + tcflush(this->file_descriptor_, TCIOFLUSH); + ESP_LOGV(TAG, " Flushing..."); +} + +void HostUartComponent::update_error_(const std::string &error) { + if (this->first_error_.empty()) { + this->first_error_ = error; + } + ESP_LOGE(TAG, "Port error: %s", error.c_str()); +} + +} // namespace uart +} // namespace esphome + +#endif // USE_HOST diff --git a/esphome/components/uart/uart_component_host.h b/esphome/components/uart/uart_component_host.h new file mode 100644 index 0000000000..c1f1dd0d2c --- /dev/null +++ b/esphome/components/uart/uart_component_host.h @@ -0,0 +1,38 @@ +#pragma once + +#ifdef USE_HOST + +#include "esphome/core/component.h" +#include "esphome/core/log.h" +#include "uart_component.h" + +namespace esphome { +namespace uart { + +class HostUartComponent : public UARTComponent, public Component { + public: + virtual ~HostUartComponent(); + void setup() override; + void dump_config() override; + float get_setup_priority() const override { return setup_priority::BUS; } + void write_array(const uint8_t *data, size_t len) override; + bool peek_byte(uint8_t *data) override; + bool read_array(uint8_t *data, size_t len) override; + int available() override; + void flush() override; + void set_name(std::string port_name) { port_name_ = port_name; }; + + protected: + void update_error_(const std::string &error); + void check_logger_conflict() override {} + std::string port_name_; + std::string first_error_{""}; + int file_descriptor_ = -1; + bool has_peek_{false}; + uint8_t peek_byte_; +}; + +} // namespace uart +} // namespace esphome + +#endif // USE_HOST diff --git a/esphome/components/web_server/server_index_v2.h b/esphome/components/web_server/server_index_v2.h index c942cda592..c9932624ba 100644 --- a/esphome/components/web_server/server_index_v2.h +++ b/esphome/components/web_server/server_index_v2.h @@ -68,7 +68,7 @@ const uint8_t INDEX_GZ[] PROGMEM = { 0xe3, 0x9b, 0x82, 0xde, 0xc5, 0x0e, 0x21, 0xa9, 0x64, 0x54, 0x44, 0x2c, 0x97, 0x29, 0x21, 0x29, 0xc2, 0x3f, 0x90, 0x45, 0x68, 0xd6, 0x13, 0xec, 0x34, 0x30, 0x9c, 0xcb, 0x40, 0x71, 0x17, 0x3c, 0xe0, 0xc9, 0x9c, 0xa6, 0x82, 0xa6, 0xc1, 0x5f, 0x71, 0x4a, 0x87, 0x31, 0x40, 0xb1, 0xd3, 0xc4, 0xe3, 0x30, 0x3b, 0x1f, 0x87, 0xc9, 0x88, 0x46, 0xc1, - 0x8d, 0xc8, 0xf1, 0xdf, 0x89, 0x3b, 0x64, 0x49, 0x18, 0xb3, 0x5f, 0x69, 0xe4, 0x6a, 0x69, 0x70, 0xeb, 0xd0, 0x5b, + 0x8d, 0xc8, 0xf1, 0xdf, 0x89, 0x3b, 0x64, 0x49, 0x18, 0xb3, 0x5f, 0x69, 0xe4, 0x6a, 0x69, 0x70, 0xe6, 0xd0, 0x5b, 0x41, 0x93, 0x28, 0x73, 0x9e, 0xbf, 0x7b, 0xf9, 0x42, 0xef, 0x63, 0x45, 0x40, 0xa0, 0x45, 0x36, 0x9b, 0xd2, 0xd4, 0x43, 0x58, 0x0b, 0x88, 0x67, 0x4c, 0x32, 0xc7, 0x97, 0xe1, 0x54, 0x95, 0xb0, 0xec, 0xfd, 0x34, 0x0a, 0x05, 0x7d, 0x43, 0x93, 0x88, 0x25, 0x23, 0xb2, 0xd3, 0x54, 0xe5, 0xe3, 0x50, 0x57, 0x44, 0x45, 0xd1, 0xe5, 0xee, 0xb3, 0x58, @@ -150,19 +150,19 @@ const uint8_t INDEX_GZ[] PROGMEM = { 0xa6, 0x57, 0xfd, 0xcf, 0xf9, 0x64, 0x0a, 0xda, 0xd8, 0x0a, 0x49, 0x8f, 0xa8, 0x9e, 0xb0, 0xac, 0xcf, 0x37, 0x94, 0x55, 0xfa, 0xc8, 0xf3, 0x58, 0xa1, 0xa6, 0xc2, 0x5e, 0xde, 0x69, 0xe4, 0xb3, 0xa2, 0xa8, 0x60, 0x1c, 0x9b, 0x9c, 0x2a, 0xe7, 0xab, 0x2e, 0x19, 0x53, 0xf1, 0xda, 0x63, 0x8a, 0x0f, 0x33, 0xe0, 0x75, 0x16, 0xfb, 0x31, 0xe4, 0x6e, - 0xef, 0x7f, 0x5e, 0x22, 0x67, 0x91, 0xaf, 0xa0, 0x6f, 0x91, 0xe7, 0xb7, 0xca, 0xc8, 0xc6, 0xb7, 0xdb, 0xad, 0xe1, - 0xb2, 0x4e, 0x1b, 0x8b, 0xbd, 0x3e, 0xbe, 0x5d, 0x57, 0x1d, 0xc9, 0x62, 0xc2, 0x23, 0x1a, 0xb8, 0x7c, 0x4a, 0x13, - 0x37, 0x07, 0xaf, 0xaa, 0xde, 0xfb, 0x81, 0xf0, 0x16, 0x6f, 0xab, 0xee, 0xd5, 0xe0, 0x36, 0x07, 0xef, 0xd7, 0xd7, + 0xef, 0x7f, 0x5e, 0x22, 0x67, 0x91, 0xaf, 0xa0, 0x6f, 0x91, 0xe7, 0x67, 0xca, 0xc8, 0xc6, 0x67, 0xdb, 0xad, 0xe1, + 0xb2, 0x4e, 0x1b, 0x8b, 0xbd, 0x3e, 0x3e, 0x5b, 0x57, 0x1d, 0xc9, 0x62, 0xc2, 0x23, 0x1a, 0xb8, 0x7c, 0x4a, 0x13, + 0x37, 0x07, 0xaf, 0xaa, 0xde, 0xfb, 0x81, 0xf0, 0x16, 0x6f, 0xab, 0xee, 0xd5, 0xe0, 0x2c, 0x07, 0xef, 0xd7, 0xd7, 0xeb, 0x8e, 0xd7, 0xef, 0x69, 0x9a, 0x49, 0x45, 0xb4, 0xd0, 0x69, 0xbf, 0x2e, 0xc5, 0xd2, 0xd7, 0xc1, 0xd6, 0xf6, 0xa5, 0x09, 0xe2, 0x36, 0xfd, 0x63, 0xff, 0xc0, 0x45, 0xd2, 0x2d, 0xfc, 0x93, 0x3e, 0xf0, 0x1f, 0x8c, 0x5b, 0xf8, 0x19, 0xf9, 0x50, 0xf5, 0x0a, 0x47, 0x82, 0x3c, 0xeb, 0x3e, 0x33, 0x16, 0x33, 0x8f, 0xd9, 0xe0, 0xce, 0x73, 0x63, 0x26, 0xea, 0x10, 0x7a, 0x73, 0xf1, 0x42, 0x55, 0x80, 0x4b, 0x51, 0xba, 0xb3, 0x73, 0x63, 0xeb, 0x61, 0x21, 0x88, 0xbb, 0x1b, 0x33, 0xb1, 0xeb, 0xe2, 0x09, 0xb9, 0x82, 0x1f, 0xbb, 0x0b, 0xef, 0x65, 0x28, 0xc6, 0x7e, 0x1a, 0x26, - 0x11, 0x9f, 0x78, 0xa8, 0xe6, 0xba, 0xc8, 0xcf, 0xa4, 0xbd, 0xf1, 0x18, 0xe5, 0xbb, 0x57, 0xf8, 0x4c, 0x10, 0xb7, - 0xeb, 0xd6, 0x26, 0xf8, 0x95, 0x20, 0x57, 0xa7, 0xbb, 0x8b, 0x33, 0x91, 0x77, 0xae, 0xf0, 0x59, 0xe1, 0xb1, 0xc7, - 0x6f, 0x88, 0x87, 0x48, 0xe7, 0x4c, 0x43, 0x73, 0xce, 0x27, 0xca, 0x73, 0xef, 0x22, 0xfc, 0x1e, 0xe2, 0x2a, 0x69, - 0xc9, 0x6d, 0x74, 0x68, 0x65, 0x87, 0xb8, 0x5c, 0xba, 0x08, 0xdc, 0xbd, 0x3d, 0xab, 0xac, 0x50, 0x15, 0xf0, 0xad, - 0x20, 0x15, 0x83, 0x1c, 0xbf, 0x95, 0x11, 0x9a, 0x5b, 0xe1, 0xa5, 0xc8, 0x0c, 0xe3, 0x19, 0x3f, 0xb4, 0x3e, 0x9a, + 0x11, 0x9f, 0x78, 0xa8, 0xe6, 0xba, 0xc8, 0xcf, 0xa4, 0xbd, 0xf1, 0x18, 0xe5, 0xbb, 0x57, 0xf8, 0x56, 0x10, 0xb7, + 0xeb, 0xd6, 0x26, 0xf8, 0x95, 0x20, 0x57, 0xa7, 0xbb, 0x8b, 0x5b, 0x91, 0x77, 0xae, 0xf0, 0x6d, 0xe1, 0xb1, 0xc7, + 0x6f, 0x88, 0x87, 0x48, 0xe7, 0x56, 0x43, 0x73, 0xce, 0x27, 0xca, 0x73, 0xef, 0x22, 0xfc, 0x1e, 0xe2, 0x2a, 0x69, + 0xc9, 0x6d, 0x74, 0x68, 0x65, 0x87, 0xb8, 0x5c, 0xba, 0x08, 0xdc, 0xbd, 0x3d, 0xab, 0xac, 0x50, 0x15, 0xf0, 0x99, + 0x20, 0x15, 0x83, 0x1c, 0xbf, 0x95, 0x11, 0x9a, 0x33, 0xe1, 0xa5, 0xc8, 0x0c, 0xe3, 0x19, 0x3f, 0xb4, 0x3e, 0x9a, 0x69, 0x4f, 0x79, 0x18, 0x7c, 0x26, 0x68, 0x1a, 0x0a, 0x9e, 0xf6, 0x91, 0xad, 0x7e, 0xe0, 0xbf, 0x91, 0xab, 0x9e, 0xf3, 0x9f, 0xbe, 0xf8, 0x79, 0xf8, 0x73, 0xda, 0xbf, 0xc2, 0xaf, 0xc9, 0xfe, 0xa9, 0xd7, 0x0d, 0xbc, 0x9d, 0x7a, 0x7d, 0xf9, 0xf3, 0x7e, 0xef, 0x1f, 0x61, 0xfd, 0xd7, 0xb3, 0xfa, 0x4f, 0x7d, 0xb4, 0xf4, 0x7e, 0xde, 0xef, 0xf6, @@ -177,7 +177,7 @@ const uint8_t INDEX_GZ[] PROGMEM = { 0xf2, 0x03, 0x64, 0x81, 0xc0, 0xf3, 0x30, 0x9e, 0xd1, 0x2c, 0xa0, 0x39, 0xc2, 0x03, 0x72, 0x21, 0xbc, 0x26, 0xc2, 0xcf, 0x05, 0xfc, 0x68, 0x21, 0x7c, 0xa1, 0x03, 0x98, 0x70, 0x90, 0x15, 0x51, 0x25, 0x5c, 0x69, 0x2c, 0x2e, 0xc2, 0xd3, 0x0d, 0x95, 0x62, 0x0c, 0xde, 0x05, 0x84, 0x87, 0x95, 0x70, 0x27, 0xbe, 0x21, 0x86, 0x24, 0xde, 0xa5, 0x94, - 0xfe, 0x10, 0xc6, 0x1f, 0x69, 0xea, 0x9d, 0xe1, 0x66, 0xeb, 0x31, 0x96, 0x2e, 0xe8, 0x9d, 0x26, 0x6a, 0x17, 0xb1, + 0xfe, 0x10, 0xc6, 0x1f, 0x69, 0xea, 0xdd, 0xe2, 0x66, 0xeb, 0x31, 0x96, 0x2e, 0xe8, 0x9d, 0x26, 0x6a, 0x17, 0xb1, 0xaa, 0x73, 0xa1, 0x62, 0x04, 0x20, 0x64, 0xab, 0xbe, 0x18, 0xd8, 0xf1, 0x9d, 0x74, 0xcd, 0x61, 0x95, 0x86, 0x37, 0x2e, 0xaa, 0xc6, 0x45, 0x59, 0x32, 0x0f, 0x63, 0x16, 0x39, 0x82, 0x4e, 0xa6, 0x71, 0x28, 0xa8, 0xa3, 0xd7, 0xeb, 0x84, 0x30, 0x90, 0x5b, 0xa8, 0x0c, 0x91, 0x65, 0x70, 0x46, 0x26, 0xe0, 0x04, 0x67, 0xc5, 0x83, 0xe8, 0x94, 0x56, @@ -220,10 +220,10 @@ const uint8_t INDEX_GZ[] PROGMEM = { 0x73, 0xd4, 0x69, 0xa0, 0x45, 0xa5, 0xad, 0xd4, 0x99, 0xaa, 0x71, 0xf4, 0x82, 0x4f, 0xcf, 0x49, 0xa3, 0x3d, 0x3f, 0x1d, 0xb5, 0xe7, 0xb5, 0x1a, 0xca, 0x0c, 0x69, 0xcd, 0x7a, 0xf3, 0x3e, 0x7e, 0x03, 0x4e, 0x3d, 0x9b, 0x96, 0x70, 0x65, 0x79, 0x2d, 0xbd, 0xbc, 0x5a, 0x2d, 0xc9, 0x51, 0xdb, 0xea, 0x3a, 0x52, 0x5d, 0xf3, 0x5c, 0xe1, 0x64, 0x95, - 0xd4, 0x4e, 0x90, 0x2c, 0x81, 0x64, 0x28, 0x42, 0xc8, 0x99, 0x40, 0x1b, 0x47, 0x85, 0x31, 0xa1, 0xbb, 0x3c, 0xb3, + 0xd4, 0x4e, 0x90, 0x2c, 0x81, 0x64, 0x28, 0x42, 0xc8, 0xad, 0x40, 0x1b, 0x47, 0x85, 0x31, 0xa1, 0xbb, 0x3c, 0xb3, 0xc0, 0x3e, 0x95, 0x94, 0xf0, 0x00, 0x0b, 0xd0, 0xb5, 0xf0, 0x04, 0x4f, 0xf0, 0xac, 0xd6, 0x94, 0x64, 0x5e, 0x6f, 0xb6, 0xab, 0x63, 0x3d, 0x2a, 0xc7, 0xc2, 0xb3, 0x1a, 0x99, 0x14, 0x58, 0xca, 0x93, 0x5a, 0x2d, 0xaf, 0x06, 0x3b, - 0xcd, 0xc9, 0xad, 0x04, 0x20, 0xce, 0x56, 0x93, 0x32, 0x8c, 0x84, 0x2d, 0x65, 0x2a, 0xf3, 0x59, 0x92, 0xd0, 0x14, + 0xcd, 0xc9, 0xad, 0x04, 0x20, 0x6e, 0x57, 0x93, 0x32, 0x8c, 0x84, 0x2d, 0x65, 0x2a, 0xf3, 0x59, 0x92, 0xd0, 0x14, 0xa4, 0x28, 0x11, 0x98, 0xe5, 0x79, 0x29, 0xd9, 0x41, 0x8c, 0x62, 0x4a, 0x52, 0xe0, 0x3c, 0xd2, 0xee, 0xc2, 0x09, 0xe6, 0x78, 0x2c, 0xf9, 0x06, 0x21, 0xe4, 0xc2, 0xa4, 0xb3, 0x08, 0xc9, 0x83, 0x62, 0xc2, 0x2c, 0x99, 0x94, 0x11, 0xea, 0x5f, 0xee, 0x9e, 0xf3, 0x7b, 0x6d, 0xb2, 0x1e, 0xeb, 0x07, 0xb2, 0x59, 0xac, 0x39, 0x57, 0x48, 0xde, 0x7b, @@ -238,14 +238,14 @@ const uint8_t INDEX_GZ[] PROGMEM = { 0x13, 0xf3, 0xec, 0xa5, 0x5f, 0xd6, 0xca, 0xc6, 0x97, 0xbb, 0x67, 0xef, 0x37, 0x35, 0x83, 0xf2, 0x7c, 0x56, 0xda, 0xf8, 0x12, 0xbe, 0x05, 0x8d, 0x83, 0x85, 0x16, 0x0e, 0x01, 0xcb, 0xb1, 0x14, 0x48, 0x41, 0x96, 0x17, 0xae, 0x91, 0xa7, 0x38, 0x21, 0x32, 0x0c, 0x54, 0xdd, 0x35, 0xad, 0xe6, 0x31, 0x9e, 0x5c, 0x0c, 0xf8, 0x94, 0x6e, 0x89, 0x0d, - 0x9d, 0x21, 0x9f, 0x4d, 0x20, 0x75, 0x46, 0x82, 0xce, 0xf0, 0x4e, 0x03, 0xb5, 0xab, 0xe2, 0x2b, 0x91, 0x44, 0xca, + 0xdd, 0x22, 0x9f, 0x4d, 0x20, 0x75, 0x46, 0x82, 0xce, 0xf0, 0x4e, 0x03, 0xb5, 0xab, 0xe2, 0x2b, 0x91, 0x44, 0xca, 0x2b, 0xb2, 0x05, 0x8f, 0x49, 0x03, 0xc7, 0xa4, 0x81, 0x43, 0x92, 0xf5, 0x1a, 0x4a, 0x40, 0xb4, 0xc3, 0x62, 0x5c, 0x25, 0x66, 0x20, 0x2b, 0x4c, 0x9f, 0x56, 0x25, 0x80, 0xa3, 0x76, 0x28, 0x7d, 0x8f, 0x52, 0xa6, 0x47, 0x92, 0x2c, 0xde, 0x7a, 0x1c, 0x73, 0x39, 0xf0, 0x05, 0xbb, 0x8e, 0x21, 0xb1, 0x04, 0x56, 0x85, 0x05, 0x0a, 0x8a, 0xa6, 0x4d, 0xdd, 0x34, 0xf4, 0xe5, 0x3e, 0x71, 0x1c, 0xfa, 0xc0, 0xb9, 0x71, 0xa8, 0xf3, 0x70, 0xb2, 0xf5, 0x2e, 0xc7, 0x7b, 0x7b, 0x9e, 0xea, 0xf4, 0x8b, 0xf0, 0xb8, 0xa9, 0x2f, 0x23, 0x77, 0xdf, 0x2b, 0x5e, 0x11, 0x21, 0x09, 0x7f, 0xad, 0x16, 0xf7, 0x73, 0x08, 0x43, 0x7b, 0x61, 0x15, 0x83, 0x06, 0x78, 0xa9, 0xeb, 0x55, 0x97, 0x5f, 0xab, 0x15, 0x51, - 0xda, 0x2a, 0xb6, 0xce, 0x70, 0x92, 0xcf, 0xbd, 0x22, 0xf5, 0xa7, 0xb1, 0x96, 0x2f, 0x65, 0x40, 0x40, 0xcc, 0xa6, + 0xda, 0x2a, 0xb6, 0x6e, 0x71, 0x92, 0xcf, 0xbd, 0x22, 0xf5, 0xa7, 0xb1, 0x96, 0x2f, 0x65, 0x40, 0x40, 0xcc, 0xa6, 0x59, 0x66, 0x16, 0x63, 0x1d, 0x09, 0x06, 0xed, 0xbe, 0xd1, 0x59, 0x0b, 0x58, 0x66, 0x57, 0xe9, 0x46, 0x86, 0x9d, 0xb5, 0x50, 0x60, 0x1a, 0x41, 0x54, 0x0a, 0x1a, 0xd5, 0x72, 0x4d, 0xde, 0x6f, 0xd7, 0x73, 0x2e, 0x71, 0x86, 0xb4, 0x93, 0x4b, 0x42, 0x21, 0x91, 0xd5, 0x2a, 0x90, 0xf2, 0x9c, 0x4c, 0xb7, 0x93, 0xfc, 0x99, 0x45, 0xf2, 0x4f, 0x08, @@ -268,7 +268,7 @@ const uint8_t INDEX_GZ[] PROGMEM = { 0x36, 0x44, 0x4d, 0xa5, 0xd4, 0x91, 0x2d, 0x50, 0xd1, 0xc1, 0x9f, 0x7b, 0x4c, 0x2b, 0x6e, 0x26, 0x6e, 0x06, 0x0c, 0xf8, 0x89, 0xf0, 0x54, 0x30, 0x0a, 0x64, 0x06, 0xf7, 0x67, 0x5e, 0x65, 0xea, 0x36, 0x97, 0xdd, 0xb0, 0x46, 0xdc, 0xd8, 0x46, 0x13, 0x97, 0x71, 0xbd, 0xf3, 0x92, 0x97, 0x0e, 0x55, 0x06, 0xb5, 0x30, 0x5c, 0xb0, 0x4c, 0x24, 0xb1, - 0x96, 0x3f, 0x54, 0x49, 0xd1, 0x45, 0x23, 0x4c, 0x25, 0x18, 0xef, 0xe4, 0x1e, 0xd0, 0x1c, 0xfe, 0x2e, 0x6e, 0x85, + 0x96, 0x3f, 0x54, 0x49, 0xd1, 0x45, 0x23, 0x4c, 0x25, 0x18, 0xef, 0xe4, 0x1e, 0xd0, 0x1c, 0xfe, 0x2e, 0xce, 0x84, 0xb5, 0xa3, 0xc6, 0x89, 0x2d, 0xe7, 0xb4, 0xa4, 0xfe, 0x5b, 0x48, 0x75, 0x59, 0x3d, 0xf3, 0xcf, 0xa5, 0x2c, 0x64, 0x38, 0xab, 0x30, 0xf6, 0x44, 0x32, 0x76, 0x04, 0x7a, 0x9a, 0x49, 0xfc, 0xee, 0xea, 0x8c, 0x17, 0xa6, 0xa5, 0x9c, 0x26, 0xb1, 0x37, 0x45, 0xb4, 0xdc, 0xfa, 0xbd, 0xb2, 0x1b, 0x01, 0x23, 0x90, 0x05, 0x84, 0x35, 0x67, 0x4f, 0x10, @@ -312,7 +312,7 @@ const uint8_t INDEX_GZ[] PROGMEM = { 0xf1, 0xb5, 0x7b, 0x78, 0x63, 0x02, 0x1e, 0xb4, 0x87, 0x4d, 0x61, 0x19, 0xdb, 0x99, 0xba, 0x07, 0x64, 0x8f, 0x4f, 0xb8, 0xd1, 0xdd, 0xaa, 0x56, 0xc6, 0x1b, 0xb0, 0xff, 0x11, 0x1e, 0x9b, 0xcb, 0x71, 0x54, 0x73, 0x60, 0x1a, 0x2c, 0xf2, 0xc2, 0x29, 0xc0, 0x95, 0xf2, 0x96, 0x22, 0xcc, 0x73, 0x19, 0xe0, 0xfe, 0x16, 0x7f, 0xa7, 0x59, 0xe2, 0xb0, - 0xe0, 0x38, 0xb7, 0x0f, 0xe5, 0x88, 0x0a, 0xfc, 0x22, 0x7e, 0x0f, 0x74, 0x2c, 0x29, 0x34, 0x37, 0x54, 0xf4, 0x94, + 0xe0, 0x38, 0x67, 0x0f, 0xe5, 0x88, 0x0a, 0xfc, 0x22, 0x7e, 0x0f, 0x74, 0x2c, 0x29, 0x34, 0x37, 0x54, 0xf4, 0x94, 0xeb, 0x85, 0x6c, 0x4d, 0x4b, 0xc5, 0xb4, 0x48, 0xa9, 0x91, 0xd3, 0x6c, 0xc8, 0xe3, 0x34, 0x56, 0xb6, 0x28, 0x4e, 0x55, 0x65, 0x5e, 0xb4, 0x05, 0x8b, 0x65, 0x68, 0x71, 0xb9, 0xf4, 0xaa, 0xa8, 0x26, 0xcc, 0x8a, 0x64, 0x20, 0xcc, 0xac, 0x8c, 0x8a, 0x8a, 0x66, 0xad, 0xfa, 0x78, 0x68, 0x35, 0xa1, 0xc8, 0xe8, 0xe6, 0x15, 0x38, 0x6c, 0x17, 0x82, @@ -612,31 +612,32 @@ const uint8_t INDEX_GZ[] PROGMEM = { 0xde, 0x0b, 0x3e, 0xda, 0x3c, 0x56, 0xcc, 0x47, 0x5d, 0x79, 0x05, 0x42, 0xdd, 0xb5, 0x35, 0xca, 0x2f, 0x8f, 0xdd, 0xce, 0xa9, 0x56, 0x06, 0x1c, 0x19, 0x0e, 0x77, 0x8f, 0x1a, 0xe6, 0x56, 0x45, 0xcc, 0x47, 0x70, 0x20, 0x55, 0x17, 0x6b, 0x92, 0x8a, 0xc7, 0x7d, 0xdc, 0xec, 0x9c, 0x86, 0x8e, 0xe4, 0x2d, 0x92, 0x79, 0x64, 0xc1, 0x3e, 0x74, 0x1e, - 0xf3, 0x09, 0xf5, 0x19, 0xdf, 0xbf, 0xa1, 0xd7, 0xf5, 0x70, 0xca, 0x4a, 0xf7, 0x36, 0x28, 0x1d, 0xc5, 0x94, 0xbc, - 0x9c, 0x09, 0x7e, 0x86, 0x2b, 0x8b, 0x94, 0x2c, 0x3c, 0xd7, 0xbe, 0x73, 0xb0, 0x55, 0x80, 0x84, 0x5c, 0x47, 0x71, - 0x78, 0xe3, 0x63, 0xd7, 0xb2, 0x37, 0x77, 0x3b, 0xff, 0xfa, 0x3f, 0xfe, 0x97, 0x76, 0x9b, 0x9f, 0xee, 0x8f, 0x9b, - 0x66, 0xac, 0x15, 0x44, 0xe7, 0xa7, 0x70, 0x11, 0xb1, 0x8c, 0xf3, 0xd2, 0xdb, 0xfa, 0x28, 0x65, 0x51, 0x7d, 0x1c, - 0xc6, 0x43, 0xb7, 0xb3, 0x1d, 0x41, 0xf6, 0x0d, 0x24, 0x0d, 0x75, 0xb5, 0x08, 0x48, 0xf0, 0x37, 0xdd, 0xa1, 0x31, - 0x57, 0x31, 0xe4, 0x69, 0xb5, 0x6f, 0xd4, 0x94, 0x07, 0xaa, 0x72, 0xab, 0x26, 0xd5, 0x5f, 0xaf, 0xd2, 0x4c, 0x2d, - 0xad, 0x5c, 0xa6, 0xc9, 0x5d, 0xa7, 0x88, 0x53, 0xfd, 0xdf, 0xff, 0xf9, 0x5f, 0xfe, 0x9b, 0x79, 0x84, 0xf0, 0xd3, - 0xbf, 0xfe, 0xf7, 0xff, 0xfc, 0x7f, 0xfe, 0xf7, 0x7f, 0x85, 0x0b, 0x18, 0x3a, 0x44, 0x25, 0xf9, 0x84, 0x53, 0xc6, - 0xa7, 0x14, 0xc3, 0x70, 0x20, 0x47, 0x71, 0xc2, 0x32, 0xc1, 0x06, 0xd5, 0xeb, 0x35, 0x17, 0x72, 0x42, 0x79, 0xd8, - 0x34, 0x74, 0xf2, 0xd0, 0xe6, 0x25, 0x8d, 0x54, 0x50, 0x2e, 0x69, 0x31, 0x3f, 0xdd, 0x07, 0x7c, 0x3f, 0xec, 0x46, - 0xa2, 0x5f, 0x6c, 0xc7, 0xc2, 0x38, 0x65, 0xa1, 0x24, 0x2f, 0xcb, 0x1d, 0x08, 0x97, 0x2c, 0xe0, 0x31, 0x68, 0x59, - 0xc5, 0x72, 0xf7, 0x2a, 0x7d, 0xda, 0x1f, 0x66, 0x99, 0x60, 0x43, 0x40, 0xb9, 0x72, 0xfd, 0xca, 0xc8, 0x74, 0x1d, - 0xd4, 0xbf, 0xf8, 0x2e, 0x97, 0xa3, 0x28, 0xdb, 0xfa, 0xf0, 0xe4, 0x4f, 0xf9, 0x5f, 0x26, 0xa0, 0x64, 0x39, 0xde, - 0x24, 0xbc, 0xd5, 0x16, 0xf7, 0x71, 0xa3, 0x31, 0xbd, 0x45, 0x8b, 0x72, 0x06, 0xbc, 0x6d, 0x32, 0xe9, 0x2e, 0xb6, - 0x07, 0x94, 0x21, 0xed, 0xc2, 0x33, 0xdd, 0x70, 0xc0, 0xbd, 0xed, 0x34, 0xf2, 0xfc, 0xcf, 0x0b, 0xe9, 0x1c, 0x65, - 0xbf, 0x42, 0xe8, 0x59, 0xfb, 0x91, 0xaf, 0xb9, 0xbd, 0xb8, 0x85, 0xd5, 0xab, 0xa5, 0x7a, 0x8d, 0x9b, 0xeb, 0x17, - 0xed, 0xec, 0xd0, 0xb9, 0x1d, 0xf4, 0x3e, 0x84, 0x30, 0xf6, 0xb8, 0x89, 0xc7, 0xad, 0x45, 0x31, 0xbc, 0x10, 0x7c, - 0x62, 0xc7, 0xca, 0x69, 0x48, 0x07, 0x74, 0x68, 0xfc, 0xef, 0xba, 0x5e, 0xc5, 0xc1, 0xf3, 0xf1, 0xc1, 0x86, 0xb9, - 0x34, 0x48, 0x32, 0x46, 0xee, 0x34, 0xf2, 0x2f, 0xe1, 0x04, 0x2e, 0x86, 0x31, 0x0f, 0x45, 0x20, 0x09, 0xb6, 0x6d, - 0x47, 0xdc, 0x43, 0x60, 0x33, 0x7c, 0x61, 0xc1, 0xd3, 0x56, 0x4d, 0xc1, 0x13, 0x5e, 0xbd, 0x0e, 0x99, 0xfb, 0xb2, - 0xbb, 0x3d, 0x94, 0x72, 0xa4, 0x7d, 0xaf, 0x03, 0xd9, 0xaf, 0x2a, 0x1e, 0x28, 0x2d, 0x63, 0x5a, 0x68, 0x73, 0xbd, - 0x12, 0xd5, 0xaa, 0xf6, 0x27, 0xe1, 0xb9, 0x12, 0x4c, 0x77, 0xb5, 0x95, 0x2c, 0x84, 0x56, 0xaf, 0xc8, 0xf7, 0x85, - 0x15, 0x14, 0x4e, 0xa7, 0xb2, 0x21, 0x6a, 0x9f, 0xee, 0x2b, 0xe5, 0x15, 0xb8, 0x87, 0xcc, 0xd2, 0x50, 0x49, 0x11, - 0xba, 0x91, 0x3e, 0x0a, 0xea, 0x97, 0x4e, 0x97, 0x80, 0xcf, 0x9a, 0x75, 0xfe, 0x1f, 0xd6, 0xb2, 0x30, 0xa4, 0x67, - 0x88, 0x00, 0x00}; + 0xf3, 0x09, 0xf5, 0x19, 0xdf, 0xbf, 0xa1, 0xd7, 0xf5, 0x70, 0xca, 0x4a, 0xf7, 0x36, 0x28, 0x1d, 0xc5, 0x94, 0xdc, + 0x78, 0xc4, 0xf5, 0x9d, 0xa3, 0x56, 0xe9, 0x6e, 0x3b, 0x04, 0x9b, 0xc7, 0xb8, 0xe6, 0xa4, 0x4f, 0xce, 0x02, 0x8b, + 0x77, 0x4e, 0xf7, 0xc3, 0x15, 0x8c, 0x48, 0x7e, 0x9f, 0x6b, 0x47, 0x3b, 0x18, 0x36, 0x40, 0x6f, 0xae, 0xa3, 0xc4, + 0x81, 0x71, 0xc8, 0x6b, 0x41, 0x9d, 0xbb, 0x9d, 0x7f, 0xfd, 0x1f, 0xff, 0x4b, 0xfb, 0xd8, 0x4f, 0xf7, 0xc7, 0x4d, + 0x33, 0xd6, 0xca, 0xae, 0xe4, 0xa7, 0x70, 0x6b, 0xb1, 0x0c, 0x0a, 0xd3, 0xdb, 0xfa, 0x28, 0x65, 0x51, 0x7d, 0x1c, + 0xc6, 0x43, 0xb7, 0xb3, 0x1d, 0x9b, 0xf6, 0x75, 0x25, 0x0d, 0x75, 0xb5, 0x08, 0xe8, 0xf5, 0x37, 0x5d, 0xb8, 0x31, + 0xf7, 0x36, 0xe4, 0xd1, 0xb6, 0xaf, 0xdf, 0x94, 0xa7, 0xaf, 0x72, 0x05, 0x27, 0xd5, 0x9f, 0xba, 0xd2, 0x1c, 0x30, + 0xad, 0xdc, 0xbc, 0xc9, 0x5d, 0xa7, 0x08, 0x6a, 0xfd, 0xdf, 0xff, 0xf9, 0x5f, 0xfe, 0x9b, 0x79, 0x84, 0x58, 0xd5, + 0xbf, 0xfe, 0xf7, 0xff, 0xfc, 0x7f, 0xfe, 0xf7, 0x7f, 0x85, 0xdb, 0x1a, 0x3a, 0x9e, 0x25, 0x99, 0x8a, 0x53, 0x06, + 0xb3, 0x14, 0x77, 0x71, 0x20, 0xa1, 0x71, 0xc2, 0x32, 0xc1, 0x06, 0xd5, 0xbb, 0x38, 0x17, 0x72, 0x42, 0x79, 0x32, + 0x35, 0x74, 0xf2, 0x84, 0xe7, 0x25, 0x41, 0x55, 0x50, 0x2e, 0x09, 0x37, 0x3f, 0xdd, 0x07, 0x7c, 0x3f, 0xec, 0xfa, + 0xa2, 0x5f, 0x6c, 0xc7, 0xc2, 0x90, 0x09, 0x94, 0xe4, 0x65, 0xb9, 0x03, 0xb1, 0x95, 0x05, 0x3c, 0x06, 0x2d, 0xab, + 0x58, 0xee, 0x5e, 0xa5, 0x4f, 0xfb, 0xc3, 0x2c, 0x13, 0x6c, 0x08, 0x28, 0x57, 0x7e, 0x62, 0x19, 0xc6, 0xae, 0x83, + 0xae, 0x18, 0xdf, 0xe5, 0x72, 0x14, 0x45, 0xa0, 0x87, 0x27, 0x7f, 0xca, 0xff, 0x32, 0x01, 0x8d, 0xcc, 0xf1, 0x26, + 0xe1, 0xad, 0x36, 0xcf, 0x8f, 0x1b, 0x8d, 0xe9, 0x2d, 0x5a, 0x94, 0x33, 0xe0, 0x6d, 0x93, 0x49, 0x3a, 0xb6, 0x07, + 0x94, 0xf1, 0xef, 0xc2, 0x8d, 0xdd, 0x70, 0xc0, 0x17, 0xee, 0x34, 0xf2, 0xfc, 0xcf, 0x0b, 0xe9, 0x49, 0x65, 0xbf, + 0x42, 0x9c, 0x5a, 0x3b, 0x9d, 0xaf, 0xb9, 0xbd, 0xb8, 0x85, 0xd5, 0xab, 0xa5, 0x7a, 0x8d, 0x9b, 0xeb, 0xb7, 0xf2, + 0xec, 0x38, 0xbb, 0x1d, 0x21, 0x3f, 0x84, 0x98, 0xf7, 0xb8, 0x89, 0xc7, 0xad, 0x45, 0x31, 0xbc, 0x10, 0x7c, 0x62, + 0x07, 0xd6, 0x69, 0x48, 0x07, 0x74, 0x68, 0x9c, 0xf5, 0xba, 0x5e, 0x05, 0xcd, 0xf3, 0xf1, 0xc1, 0x86, 0xb9, 0x34, + 0x48, 0x32, 0xa0, 0xee, 0x34, 0xf2, 0x2f, 0xe1, 0x04, 0x2e, 0x86, 0x31, 0x0f, 0x45, 0x20, 0x09, 0xb6, 0x6d, 0x87, + 0xe7, 0x43, 0xe0, 0x49, 0x7c, 0x61, 0xc1, 0xd3, 0x56, 0x4d, 0xc1, 0x6d, 0x5e, 0xbd, 0x3b, 0x99, 0xfb, 0xb2, 0xbb, + 0x3d, 0x94, 0xf2, 0xba, 0x7d, 0xaf, 0xa3, 0xde, 0xaf, 0x2a, 0xee, 0x2a, 0x2d, 0x90, 0x5a, 0x68, 0x73, 0xbd, 0x92, + 0xeb, 0xaa, 0xf6, 0x27, 0xe1, 0xb9, 0x12, 0x4c, 0x77, 0xb5, 0x95, 0x2c, 0x84, 0x56, 0xaf, 0xc8, 0xf7, 0x85, 0xc9, + 0x14, 0x4e, 0xa7, 0xb2, 0x21, 0x6a, 0x9f, 0xee, 0x2b, 0x4d, 0x17, 0xb8, 0x87, 0x4c, 0xe9, 0x50, 0x19, 0x14, 0xba, + 0x91, 0x3e, 0x0a, 0xea, 0x97, 0xce, 0xad, 0x80, 0x6f, 0xa0, 0x75, 0xfe, 0x1f, 0xa2, 0x48, 0xf6, 0xdd, 0x94, 0x88, + 0x00, 0x00}; } // namespace web_server } // namespace esphome diff --git a/esphome/components/web_server/server_index_v3.h b/esphome/components/web_server/server_index_v3.h index bde1ce1fb5..0c16ea9f37 100644 --- a/esphome/components/web_server/server_index_v3.h +++ b/esphome/components/web_server/server_index_v3.h @@ -3632,373 +3632,374 @@ const uint8_t INDEX_GZ[] PROGMEM = { 0xe7, 0xec, 0xd8, 0x98, 0x31, 0x94, 0x4f, 0x43, 0x40, 0x9e, 0xd0, 0xf7, 0x01, 0xcd, 0x25, 0x67, 0x23, 0xad, 0x2b, 0xfb, 0x10, 0x17, 0x97, 0xdc, 0x84, 0x6a, 0x31, 0x6f, 0x2b, 0x3d, 0x2a, 0xc4, 0x1b, 0x16, 0x80, 0x65, 0xe9, 0x69, 0x93, 0x82, 0x6c, 0x94, 0x54, 0x45, 0xfe, 0x13, 0xbf, 0x03, 0xae, 0xad, 0xac, 0xe4, 0x0a, 0x78, 0xf5, 0xff, 0xd3, - 0xdc, 0x93, 0x2e, 0xb7, 0x6d, 0x24, 0xfd, 0x3f, 0x4f, 0x01, 0xc3, 0x5e, 0x87, 0xb0, 0x01, 0x08, 0x00, 0x45, 0x89, - 0x26, 0x45, 0x69, 0x13, 0x1f, 0xb5, 0x4e, 0x29, 0x71, 0xca, 0x56, 0x5c, 0xbb, 0x51, 0x54, 0x22, 0x48, 0x0e, 0x49, - 0xac, 0x41, 0x80, 0x05, 0x80, 0x3a, 0x42, 0x63, 0x9f, 0x65, 0x9f, 0x65, 0x9f, 0xec, 0xab, 0xee, 0x9e, 0x19, 0x0c, - 0x0e, 0x1e, 0x8a, 0x9d, 0xdd, 0xaf, 0x12, 0xdb, 0xc4, 0xdc, 0xd3, 0x33, 0xd3, 0xd3, 0xd3, 0xa7, 0x3f, 0xe3, 0xbc, - 0x17, 0xb3, 0xc5, 0xf6, 0xeb, 0xee, 0xf3, 0x67, 0x66, 0xe3, 0x96, 0x04, 0x82, 0xcf, 0xce, 0xe2, 0xd9, 0x2c, 0x64, - 0x2d, 0x5d, 0x04, 0x0f, 0xd1, 0x4d, 0xd9, 0xcd, 0xd9, 0x23, 0x47, 0x78, 0xec, 0x34, 0xf2, 0x4d, 0x47, 0x4b, 0xcc, - 0x98, 0x49, 0x97, 0x76, 0x44, 0xb9, 0x22, 0x6f, 0xf6, 0x06, 0xc5, 0x1b, 0x7c, 0x5d, 0x8a, 0xa3, 0x6b, 0x4d, 0xe2, - 0xd5, 0x28, 0x64, 0x16, 0x6e, 0x77, 0xe8, 0x72, 0x3d, 0x5a, 0x8d, 0x46, 0x10, 0xa5, 0xe5, 0x91, 0x63, 0x82, 0xdf, - 0x99, 0x38, 0xc5, 0xf7, 0x60, 0x6e, 0xf4, 0x61, 0x52, 0x76, 0x56, 0x1d, 0x3e, 0xe8, 0x8a, 0x00, 0xab, 0x87, 0x3a, - 0xc8, 0xe0, 0xed, 0xd7, 0x70, 0x6a, 0x07, 0xfa, 0x07, 0xd8, 0x7d, 0xa9, 0xde, 0x6f, 0x3a, 0xfa, 0x83, 0x4b, 0xfd, - 0x03, 0xc2, 0x18, 0xa3, 0x17, 0xbf, 0xa4, 0xdd, 0xab, 0x9b, 0x3a, 0x09, 0xbd, 0x57, 0x18, 0xc7, 0x00, 0x98, 0xbe, - 0xaf, 0x02, 0x7f, 0x16, 0xc5, 0x69, 0x16, 0x8c, 0xf5, 0xab, 0xfe, 0xdb, 0xa0, 0x75, 0xb9, 0xc8, 0x5a, 0xc6, 0x95, - 0x39, 0xce, 0xd4, 0x10, 0x28, 0x02, 0x61, 0x62, 0x04, 0x94, 0x4d, 0x85, 0xd4, 0x13, 0xb4, 0xb5, 0xa0, 0x40, 0xcd, - 0x58, 0x68, 0x9c, 0x0d, 0xa0, 0x5c, 0x25, 0x9e, 0x0a, 0x06, 0x86, 0xd2, 0xb1, 0xa6, 0xd1, 0xa7, 0x97, 0xca, 0xcb, - 0xd5, 0x1a, 0xaf, 0xf2, 0xac, 0xb8, 0x2d, 0xd1, 0x07, 0xb0, 0x30, 0x9c, 0xa1, 0xef, 0x47, 0xaa, 0xd2, 0x67, 0xe9, - 0xde, 0x1d, 0x7e, 0x57, 0xa6, 0x0b, 0xe0, 0xfe, 0x06, 0x8d, 0x8b, 0x28, 0xce, 0x34, 0x70, 0x6c, 0x03, 0x3d, 0x0e, - 0xab, 0x4a, 0x62, 0xbc, 0xd5, 0x96, 0x91, 0x73, 0x64, 0xf0, 0x3d, 0x5e, 0x7e, 0x2d, 0xee, 0xde, 0xac, 0xe4, 0xc1, - 0x82, 0x1e, 0x0b, 0x11, 0x2c, 0x60, 0x16, 0x9f, 0xc7, 0xb7, 0x55, 0x39, 0xc8, 0xcb, 0xe1, 0xee, 0xbb, 0xb7, 0x25, - 0xc8, 0x64, 0x11, 0xd5, 0xaf, 0xc5, 0x03, 0x93, 0x0a, 0x42, 0xa7, 0x72, 0xa6, 0x50, 0xf1, 0x43, 0xd0, 0x30, 0x19, - 0xe8, 0x89, 0xe1, 0x5d, 0x00, 0x28, 0x89, 0x5f, 0xd3, 0xc3, 0xfc, 0x5a, 0x84, 0x4e, 0x16, 0x81, 0x8b, 0x95, 0xcb, - 0x19, 0xb0, 0x6b, 0xb4, 0x5c, 0x65, 0xe8, 0x6a, 0x17, 0x06, 0xc0, 0x72, 0x5d, 0x43, 0xd7, 0x9d, 0x80, 0xa5, 0x0b, - 0x32, 0x31, 0xd7, 0xb5, 0x60, 0x52, 0x4f, 0xe3, 0x44, 0x2f, 0x20, 0x2f, 0xc4, 0xef, 0xc8, 0xa8, 0x82, 0xcf, 0x84, - 0x4f, 0x63, 0x6c, 0x16, 0x7e, 0xea, 0x5b, 0x63, 0x14, 0xe8, 0x34, 0x60, 0x86, 0x31, 0xb5, 0xd3, 0x6f, 0x85, 0x8d, - 0x93, 0x05, 0xf7, 0x9b, 0xa5, 0x69, 0x0e, 0x9f, 0xac, 0xa3, 0xfc, 0xec, 0xc9, 0x3a, 0xcd, 0x07, 0x4f, 0xd6, 0xbe, - 0xd4, 0x15, 0xd0, 0x2f, 0x74, 0x52, 0x14, 0x18, 0x22, 0x18, 0x86, 0xf9, 0x75, 0x61, 0xb9, 0x53, 0xcc, 0x17, 0x76, - 0x19, 0xa5, 0x6b, 0x28, 0xba, 0x1f, 0x70, 0x01, 0xfd, 0x32, 0x09, 0x16, 0x7e, 0x72, 0x4f, 0xf2, 0x7c, 0x53, 0x15, - 0xfa, 0x1b, 0xba, 0x46, 0x88, 0x9e, 0x00, 0x40, 0x38, 0x5f, 0xd7, 0xfe, 0x2a, 0xd3, 0x18, 0x9f, 0xad, 0x14, 0x6a, - 0x42, 0x5f, 0xd7, 0xfa, 0x73, 0x66, 0x4f, 0x58, 0xe6, 0x07, 0x21, 0x55, 0xe9, 0x8b, 0x68, 0xf5, 0xb5, 0xe9, 0xa5, - 0xe5, 0xe9, 0x45, 0xe5, 0xfd, 0x83, 0x93, 0xa1, 0x2b, 0x80, 0xc6, 0x8d, 0x33, 0xc3, 0x28, 0x56, 0xcd, 0x2b, 0x4a, - 0x79, 0xff, 0xd5, 0xe5, 0x60, 0xb0, 0x1c, 0x11, 0x2c, 0x07, 0x8b, 0xc6, 0xf1, 0x84, 0xfd, 0xf2, 0xfe, 0xad, 0x0c, - 0x9b, 0x05, 0x1c, 0xa0, 0x21, 0xdf, 0x98, 0x29, 0xd2, 0x0f, 0x09, 0xd2, 0x0e, 0x14, 0xe0, 0x4a, 0x93, 0x5b, 0x28, - 0xc9, 0x75, 0xed, 0x8c, 0xc6, 0xce, 0x26, 0x34, 0xea, 0x41, 0x8c, 0xb5, 0x92, 0xfc, 0xe4, 0x80, 0x4a, 0xd3, 0x6d, - 0x47, 0x85, 0x00, 0x0c, 0x09, 0xcc, 0xb0, 0x80, 0x02, 0x44, 0xf8, 0x1c, 0xb8, 0xc5, 0x83, 0xc2, 0x5e, 0x20, 0x9f, - 0xdd, 0x3d, 0x2b, 0x93, 0x2a, 0x58, 0x4b, 0x3f, 0x3d, 0xc1, 0x98, 0x5d, 0x70, 0x5f, 0x83, 0x97, 0x8f, 0x93, 0x03, - 0xfa, 0xd4, 0x2a, 0x27, 0xa2, 0x68, 0x44, 0x3c, 0xed, 0x7a, 0xbc, 0x81, 0x07, 0x1d, 0x15, 0x08, 0x11, 0x0f, 0xa9, - 0x7e, 0xae, 0x6b, 0x0b, 0x4e, 0x1a, 0x71, 0x77, 0x42, 0xe0, 0x6b, 0xc0, 0x81, 0xb3, 0xab, 0x6b, 0x0b, 0xff, 0x0e, - 0x67, 0x2e, 0x72, 0xfc, 0xbb, 0x96, 0xcb, 0xb3, 0x8a, 0xb3, 0x96, 0x96, 0xcf, 0xda, 0x98, 0x2f, 0x2e, 0x18, 0x12, - 0xc8, 0x97, 0xf5, 0x1c, 0x05, 0xb4, 0x0d, 0x8b, 0x3b, 0x17, 0x8b, 0x3b, 0xd9, 0xb0, 0xb8, 0x93, 0x2d, 0x8b, 0x1b, - 0xf2, 0x85, 0xd4, 0x24, 0xe8, 0x12, 0x34, 0x0e, 0x93, 0xc0, 0xe3, 0x84, 0x46, 0x8f, 0x9f, 0x33, 0x84, 0x93, 0x95, - 0x86, 0xa0, 0x1c, 0xb5, 0x01, 0x56, 0x4d, 0x70, 0x51, 0x00, 0x51, 0x9f, 0xb8, 0x3c, 0x75, 0x62, 0xde, 0x10, 0x83, - 0xb3, 0x15, 0x56, 0xe7, 0x0b, 0xbb, 0x94, 0xe2, 0x8b, 0xb7, 0xe6, 0x1b, 0x66, 0x3a, 0xdf, 0x32, 0xd3, 0x71, 0xe9, - 0xe8, 0xf2, 0x69, 0xd3, 0x21, 0x54, 0x27, 0x05, 0x7b, 0x10, 0x14, 0x46, 0x71, 0xcb, 0x94, 0xf7, 0xe1, 0x66, 0x1c, - 0xab, 0xec, 0xa8, 0xa5, 0x9f, 0xa6, 0xb7, 0x71, 0x02, 0x12, 0x17, 0x68, 0xe6, 0x61, 0x5b, 0x6a, 0x11, 0x44, 0xdc, - 0x99, 0xcb, 0xc6, 0xcd, 0x54, 0xe4, 0xab, 0x5b, 0xca, 0xeb, 0x74, 0xa8, 0xc4, 0xd2, 0xcf, 0x32, 0x96, 0x20, 0xd0, - 0x7d, 0xf0, 0xfa, 0xfd, 0xff, 0x64, 0x9b, 0x35, 0xe0, 0x90, 0x50, 0xc1, 0xea, 0x88, 0xa1, 0x97, 0x40, 0x5b, 0x25, - 0xe2, 0x22, 0x56, 0x1c, 0xc3, 0x25, 0x12, 0xf0, 0x3f, 0xe1, 0x71, 0x6d, 0x25, 0x8a, 0xe9, 0x92, 0x7b, 0x64, 0xd8, - 0x4b, 0x7f, 0xf2, 0x01, 0x04, 0x7b, 0x2d, 0xcf, 0x04, 0x25, 0x5d, 0xd5, 0x0d, 0x5c, 0x42, 0xc4, 0xde, 0xb8, 0x40, - 0x92, 0x88, 0x25, 0xb9, 0x0a, 0x14, 0x58, 0x4f, 0xfa, 0xd6, 0xf4, 0x6a, 0xed, 0xe5, 0x07, 0xb3, 0xc0, 0xa8, 0x61, - 0x4d, 0x40, 0x6d, 0xe1, 0xe0, 0x54, 0xbe, 0xb9, 0x42, 0xd3, 0x3d, 0x32, 0x80, 0xf3, 0x7b, 0x09, 0xf1, 0x4c, 0x1d, - 0xf1, 0xa0, 0x1d, 0x26, 0x70, 0x6b, 0x5d, 0x3a, 0x57, 0xf9, 0xd3, 0x19, 0xfe, 0x72, 0xaf, 0xf2, 0xa7, 0x23, 0xfc, - 0xe5, 0x5d, 0x61, 0xe4, 0xba, 0x86, 0x87, 0xbc, 0x32, 0x67, 0xfd, 0xb4, 0xb4, 0x9f, 0x48, 0xff, 0xec, 0x01, 0xdb, - 0x86, 0x2f, 0xf0, 0xe3, 0x27, 0xeb, 0x14, 0x2c, 0x2e, 0xd5, 0x39, 0x44, 0x76, 0x62, 0xe4, 0x8d, 0xe9, 0xb3, 0x0d, - 0xe9, 0x23, 0xe3, 0xbf, 0x7c, 0xf1, 0xe3, 0x2e, 0x89, 0x8b, 0x3b, 0xa5, 0xcc, 0x86, 0xb8, 0x1e, 0x05, 0x91, 0x9f, - 0xdc, 0x5f, 0xd3, 0xf3, 0xa2, 0x25, 0x68, 0x77, 0xc9, 0x5e, 0x21, 0xf2, 0xb2, 0x2c, 0xee, 0xca, 0x14, 0x06, 0xef, - 0x3d, 0xbf, 0xe8, 0x07, 0x7f, 0x4f, 0x14, 0xb2, 0xad, 0xf4, 0x00, 0xe5, 0x0b, 0x52, 0xea, 0xe8, 0xfa, 0xc9, 0xba, - 0xc5, 0xea, 0xcd, 0x54, 0x66, 0x5b, 0xa1, 0x0b, 0x61, 0x79, 0xf0, 0x31, 0xbb, 0x98, 0x04, 0x3d, 0x94, 0x67, 0x8d, - 0xe2, 0x3b, 0xeb, 0xc9, 0x3a, 0x3b, 0xd3, 0x17, 0x7e, 0xf2, 0x89, 0x4d, 0xac, 0x71, 0x90, 0x8c, 0x43, 0xa6, 0xf7, - 0xf4, 0x51, 0xe8, 0x47, 0x9f, 0xf8, 0xa7, 0x15, 0xaf, 0x32, 0x94, 0x50, 0xef, 0x7c, 0xfb, 0x0a, 0x98, 0x10, 0xcb, - 0x0e, 0x89, 0xd5, 0x06, 0x28, 0x68, 0x2f, 0x25, 0xc3, 0xab, 0x20, 0x14, 0x8b, 0x52, 0x26, 0x28, 0x58, 0x82, 0xd0, - 0x1c, 0x2c, 0x56, 0x4d, 0x1d, 0xd7, 0x4b, 0x37, 0xd5, 0xa9, 0x12, 0xb3, 0x52, 0x86, 0x5c, 0xbc, 0xc6, 0x16, 0xfe, - 0x78, 0x77, 0x14, 0x0c, 0x7b, 0xff, 0xee, 0x64, 0x2b, 0x5f, 0x36, 0x43, 0x48, 0xb5, 0xc8, 0x52, 0xe2, 0x01, 0x9d, - 0x73, 0x02, 0x73, 0x73, 0xd7, 0x6a, 0x65, 0x3f, 0x4d, 0x57, 0x0b, 0x36, 0x21, 0xc9, 0xe0, 0x59, 0x31, 0xa8, 0xf2, - 0xcb, 0x42, 0x1d, 0xd8, 0x6f, 0x2b, 0xef, 0xf8, 0xf0, 0x25, 0x68, 0x2c, 0x00, 0x41, 0x19, 0x4f, 0xa7, 0x7a, 0xf1, - 0xc6, 0xdf, 0x51, 0xcd, 0x3d, 0xfc, 0x6d, 0xf5, 0xe6, 0xb5, 0xf3, 0x46, 0x56, 0x8e, 0x80, 0x30, 0x16, 0xe2, 0x57, - 0x4e, 0x17, 0x2b, 0xe3, 0x15, 0x33, 0x9a, 0xfa, 0xd1, 0xe6, 0xe9, 0x5c, 0x96, 0xb6, 0xf8, 0x92, 0xb1, 0x09, 0x10, - 0xdc, 0x66, 0x2d, 0xf5, 0x3a, 0x64, 0x37, 0x4c, 0x8a, 0x76, 0xeb, 0x9d, 0x35, 0xd4, 0x40, 0xdf, 0x73, 0x5c, 0x64, - 0xcc, 0xa9, 0x3a, 0x65, 0x4a, 0x43, 0x9c, 0x03, 0x9f, 0xb9, 0x7a, 0xc4, 0x2a, 0x47, 0x6a, 0x68, 0xea, 0xca, 0x00, - 0x36, 0x8e, 0xec, 0x6c, 0x43, 0x7a, 0x0f, 0x03, 0x4f, 0x37, 0x8f, 0xcd, 0x74, 0x8d, 0x1e, 0xf8, 0xea, 0xe6, 0x70, - 0x0a, 0xe1, 0xe4, 0xb5, 0x0a, 0x76, 0xc8, 0x26, 0x88, 0x35, 0x31, 0xc9, 0x74, 0xe2, 0xbe, 0x08, 0x6d, 0x47, 0x54, - 0xfb, 0x15, 0x7c, 0xa8, 0xc6, 0xb5, 0xd1, 0xca, 0x33, 0x1f, 0x61, 0x40, 0xd7, 0x88, 0xa5, 0xe9, 0x46, 0x80, 0xc9, - 0x45, 0x37, 0xf5, 0xa2, 0x74, 0x19, 0x1e, 0x45, 0xba, 0xe9, 0x98, 0x40, 0x12, 0xe0, 0x04, 0xab, 0x7d, 0xe1, 0xf5, - 0x72, 0xbd, 0xe0, 0xfa, 0x2a, 0xc9, 0x6c, 0xa4, 0x73, 0x5d, 0x82, 0x4d, 0xf9, 0xb7, 0x3a, 0x1f, 0x54, 0xe9, 0x9a, - 0x6e, 0x1c, 0x5a, 0xab, 0x84, 0x7a, 0x6b, 0xec, 0x22, 0x6c, 0x40, 0x8c, 0xa9, 0x82, 0x5f, 0xd9, 0x74, 0xca, 0xc6, - 0x59, 0x6a, 0x08, 0xe6, 0x91, 0xf4, 0x1e, 0x0b, 0x56, 0x43, 0x8f, 0x06, 0xfa, 0x4f, 0x60, 0x43, 0x2f, 0x9c, 0x2c, - 0xf1, 0x01, 0x89, 0x37, 0x53, 0x33, 0x98, 0xa8, 0xc5, 0x32, 0x88, 0x78, 0x2f, 0x10, 0x1c, 0xbc, 0x21, 0x1d, 0x87, - 0xc6, 0xef, 0x9f, 0x62, 0x5f, 0xc4, 0x52, 0xab, 0x65, 0x3b, 0x2a, 0xda, 0x76, 0x7c, 0xd7, 0xee, 0x9b, 0x8e, 0xeb, - 0xe4, 0xba, 0x09, 0xb6, 0x5b, 0x9f, 0xf6, 0x3d, 0xf4, 0x58, 0xab, 0x0d, 0xb5, 0x56, 0xd1, 0x43, 0xea, 0x79, 0xee, - 0x0b, 0x57, 0x37, 0x49, 0x65, 0x4e, 0xc1, 0x6d, 0xe3, 0xf8, 0x86, 0x25, 0x5f, 0x3c, 0x95, 0x72, 0xe3, 0xfb, 0x8d, - 0xe7, 0xc8, 0x75, 0x00, 0x09, 0x67, 0xf1, 0xf2, 0x01, 0x53, 0x68, 0xeb, 0xa6, 0x3e, 0x0e, 0xe3, 0x94, 0xa9, 0x73, - 0x20, 0x26, 0xc8, 0x17, 0x4e, 0xe2, 0xe7, 0xf7, 0xaf, 0x3f, 0x7c, 0xd0, 0x4d, 0x8c, 0x04, 0x9a, 0xaa, 0xad, 0xf3, - 0x0d, 0xb5, 0x03, 0xfb, 0x37, 0xee, 0x3b, 0xba, 0x61, 0xe8, 0x51, 0x5b, 0xde, 0x73, 0x94, 0x56, 0xdb, 0x72, 0xfc, - 0xe6, 0xe1, 0x3d, 0xd3, 0x4b, 0x74, 0xaf, 0x79, 0x35, 0xe0, 0x86, 0xed, 0xd7, 0x5b, 0x29, 0x65, 0x11, 0x44, 0xd7, - 0x0d, 0xa9, 0xfe, 0x5d, 0x43, 0x2a, 0x3c, 0xe5, 0x6a, 0xb8, 0x6a, 0x15, 0x2f, 0x14, 0xd2, 0x00, 0x02, 0x39, 0xef, - 0x02, 0x97, 0xf2, 0x9e, 0xfa, 0x82, 0x41, 0x73, 0x4f, 0xee, 0xd5, 0x51, 0x37, 0x24, 0xf3, 0x47, 0x90, 0x84, 0xed, - 0x38, 0x04, 0x85, 0x3f, 0xa6, 0x4a, 0xe5, 0xca, 0x64, 0xa3, 0x54, 0xd7, 0x55, 0x1a, 0x21, 0xf2, 0xf6, 0x3a, 0x63, - 0x8b, 0x25, 0x4b, 0xfc, 0x6c, 0x95, 0xb0, 0xeb, 0x30, 0xbe, 0x7d, 0x54, 0xa8, 0xd3, 0xef, 0x28, 0x3c, 0x0f, 0x66, - 0x73, 0x59, 0xfa, 0xac, 0xc5, 0x06, 0x72, 0x01, 0xb7, 0x76, 0x90, 0xff, 0xe7, 0xdf, 0xb6, 0xfd, 0x9f, 0x7f, 0xef, - 0x2c, 0x0a, 0xcd, 0xe7, 0x43, 0x33, 0x1b, 0xec, 0xb1, 0x2f, 0x9a, 0x7b, 0x2a, 0xc3, 0xbc, 0xb9, 0x4c, 0x6d, 0x11, - 0x20, 0xbf, 0xb6, 0x04, 0xb5, 0xc4, 0xf2, 0xbe, 0x79, 0xd0, 0xc0, 0x60, 0x5e, 0x3b, 0x47, 0x06, 0x85, 0xbe, 0x68, - 0x68, 0x43, 0xa3, 0xb7, 0xd7, 0x8a, 0xfc, 0x71, 0x08, 0xef, 0x9a, 0xc3, 0x17, 0x0e, 0x9f, 0xf3, 0x25, 0x5f, 0x0e, - 0x87, 0x32, 0xb6, 0x9c, 0x5a, 0x15, 0x54, 0xfc, 0xcf, 0x6a, 0x29, 0xfc, 0xf2, 0xec, 0x39, 0x06, 0xd9, 0xde, 0x0f, - 0x5e, 0x0e, 0x51, 0x19, 0xed, 0x64, 0x94, 0x14, 0xc4, 0xca, 0x46, 0xd4, 0x46, 0xca, 0xe4, 0xb5, 0x46, 0x6b, 0x78, - 0x0d, 0x52, 0x31, 0xe0, 0x58, 0x3e, 0x34, 0xcc, 0x97, 0x43, 0xce, 0x58, 0xe2, 0xfa, 0xaf, 0xbd, 0xea, 0xd6, 0xe6, - 0x6c, 0xd9, 0x12, 0xd0, 0x4d, 0x8d, 0xe4, 0x3f, 0x58, 0x98, 0x15, 0x7c, 0x3c, 0x64, 0xf0, 0x03, 0x47, 0x61, 0x98, - 0x63, 0xbc, 0x93, 0x77, 0x9b, 0x74, 0xc4, 0x7e, 0xde, 0xad, 0x23, 0x76, 0xb1, 0x97, 0x8e, 0xd8, 0xcf, 0x5f, 0x5d, - 0x47, 0xec, 0x9d, 0xaa, 0x23, 0x06, 0x8b, 0xf8, 0x9a, 0xed, 0xa5, 0xb8, 0x25, 0xb4, 0x36, 0xe2, 0xdb, 0x74, 0xe0, - 0x72, 0x92, 0x36, 0x1d, 0xcf, 0x19, 0xf0, 0x08, 0xf8, 0xaa, 0x84, 0xf1, 0x0c, 0x94, 0xb8, 0xfe, 0x7c, 0x75, 0xab, - 0x30, 0x9e, 0xa9, 0xca, 0x56, 0x11, 0xf7, 0xf8, 0x5a, 0x78, 0x71, 0x22, 0x05, 0x27, 0xc7, 0x14, 0x3e, 0x9f, 0xac, - 0x43, 0x43, 0x89, 0x6a, 0x2d, 0xb5, 0xd7, 0x3c, 0xa1, 0x02, 0xd5, 0x43, 0xed, 0x29, 0x59, 0xd1, 0x7b, 0x2e, 0x7c, - 0x5b, 0xa8, 0x2d, 0x48, 0x2d, 0x61, 0xf2, 0x13, 0xb1, 0xd6, 0x7f, 0xbb, 0x73, 0xbf, 0xbf, 0x74, 0xfb, 0x6d, 0x17, - 0x8c, 0xb3, 0xe1, 0x85, 0x89, 0x09, 0x4e, 0xbf, 0xdd, 0x86, 0x84, 0x5b, 0x25, 0xc1, 0x83, 0x84, 0x40, 0x49, 0xe8, - 0x40, 0xc2, 0x58, 0x49, 0x38, 0x82, 0x84, 0x89, 0x92, 0x70, 0x0c, 0x09, 0x37, 0x7a, 0x7e, 0x19, 0xc9, 0xe1, 0x1e, - 0x1b, 0x57, 0x26, 0x3d, 0x2a, 0x44, 0xda, 0xb1, 0xe9, 0x82, 0xd6, 0x94, 0x3f, 0xeb, 0xc5, 0x26, 0x71, 0x17, 0x7b, - 0x89, 0x79, 0x3b, 0x67, 0xe4, 0x28, 0xfa, 0x15, 0xde, 0x39, 0x76, 0x16, 0x83, 0xde, 0xb4, 0x70, 0xc0, 0x20, 0xe0, - 0xa0, 0xe9, 0x06, 0x30, 0x8c, 0xfa, 0x72, 0xe5, 0x84, 0x13, 0x0b, 0x65, 0x2d, 0x8b, 0x3c, 0xea, 0xce, 0x92, 0x5b, - 0xa0, 0xd0, 0x38, 0x69, 0xa9, 0x5c, 0xc9, 0xaf, 0xa1, 0x77, 0xf0, 0x8a, 0x8d, 0x56, 0x33, 0xed, 0x3c, 0x9e, 0xed, - 0x54, 0x21, 0x50, 0xb3, 0x60, 0x94, 0x3a, 0x89, 0x5f, 0x2c, 0xb1, 0x2d, 0x79, 0x5f, 0xf4, 0x99, 0x97, 0xcb, 0x67, - 0x30, 0x36, 0x2d, 0x23, 0x05, 0x16, 0xe8, 0x07, 0x60, 0xa4, 0xc8, 0xf0, 0xcf, 0x01, 0xce, 0xca, 0xf7, 0x85, 0xaf, - 0x8c, 0xe7, 0xf4, 0x47, 0x96, 0xa6, 0xfe, 0x4c, 0x94, 0xaf, 0x8f, 0x13, 0x94, 0x76, 0xe4, 0xfb, 0x0b, 0x01, 0x08, - 0x9c, 0xbc, 0xa0, 0xa6, 0x9b, 0x91, 0xc4, 0xb7, 0x1a, 0x68, 0xff, 0xc0, 0x86, 0x2a, 0xf4, 0x14, 0x02, 0x1b, 0x96, - 0xb0, 0xac, 0x51, 0x00, 0x87, 0xff, 0x86, 0x85, 0xd5, 0xc4, 0xcc, 0x9f, 0x55, 0x93, 0x68, 0x1f, 0xe4, 0xea, 0xd8, - 0xa4, 0x40, 0xbf, 0x94, 0xf8, 0x25, 0x12, 0xea, 0x30, 0x9e, 0xfd, 0xa9, 0xe2, 0xe9, 0x2d, 0x6a, 0x05, 0x1f, 0x22, - 0x33, 0xc8, 0x86, 0x36, 0xc2, 0x58, 0xb3, 0x01, 0x84, 0xbd, 0x28, 0x9b, 0x5b, 0x68, 0x5a, 0xd6, 0xf2, 0x22, 0xc3, - 0xb4, 0x71, 0x6d, 0xd7, 0x55, 0x83, 0xda, 0x5e, 0x32, 0x1b, 0xf9, 0x2d, 0xd7, 0x3b, 0x36, 0xc5, 0x1f, 0xdb, 0xe9, - 0x18, 0x39, 0xb6, 0xa0, 0x4d, 0x82, 0x9b, 0xf5, 0x34, 0x8e, 0x32, 0x6b, 0xea, 0x2f, 0x82, 0xf0, 0xbe, 0xb7, 0x88, - 0xa3, 0x38, 0x5d, 0xfa, 0x63, 0xd6, 0x2f, 0x1e, 0xd4, 0x7d, 0x74, 0xd5, 0xc0, 0xad, 0x05, 0x5d, 0xdb, 0x4b, 0xd8, - 0x82, 0x6a, 0x4b, 0x4f, 0x0c, 0xd3, 0x90, 0xdd, 0xe5, 0xbc, 0xfb, 0x52, 0x61, 0x2a, 0x8a, 0x5b, 0x8e, 0x6a, 0x00, - 0x45, 0xca, 0xdd, 0x3c, 0x80, 0x73, 0xa3, 0xfe, 0xd2, 0x9f, 0xa0, 0x67, 0x42, 0xdb, 0xeb, 0x24, 0x6c, 0xa1, 0xd9, - 0x9d, 0x8d, 0x8d, 0x27, 0xf1, 0xed, 0x29, 0x8c, 0x16, 0x2b, 0x5b, 0x29, 0x0b, 0xa7, 0x98, 0x63, 0xa1, 0x65, 0x89, - 0x68, 0xc7, 0xc2, 0x87, 0x38, 0xb4, 0xc6, 0x16, 0x7d, 0xc8, 0xee, 0x79, 0x9a, 0xd3, 0x5f, 0x04, 0x91, 0x45, 0xd3, - 0x39, 0x76, 0x96, 0x4a, 0x5b, 0x2a, 0xfc, 0x8c, 0x35, 0x16, 0x77, 0x35, 0xa7, 0x0f, 0x8f, 0xb5, 0x69, 0x18, 0xdf, - 0xf6, 0xe6, 0xc1, 0x64, 0xc2, 0xa2, 0x3e, 0x8e, 0x59, 0x26, 0xb2, 0x30, 0x0c, 0x96, 0x69, 0x90, 0xf6, 0x17, 0xfe, - 0x1d, 0x6f, 0xf5, 0x70, 0x53, 0xab, 0x6d, 0xde, 0x6a, 0x7b, 0xef, 0x56, 0x95, 0x66, 0xc0, 0x8a, 0x85, 0xda, 0xe1, - 0x43, 0xeb, 0x68, 0x4e, 0x65, 0x9e, 0x7b, 0xb7, 0xba, 0x4c, 0xd8, 0x7a, 0xe1, 0x27, 0xb3, 0x20, 0xea, 0x39, 0xb9, - 0x7d, 0xb3, 0xa6, 0x8d, 0xf1, 0xb8, 0xdb, 0xed, 0xe6, 0xf6, 0x44, 0x7c, 0x39, 0x93, 0x49, 0x6e, 0x8f, 0xc5, 0xd7, - 0x74, 0xea, 0x38, 0xd3, 0x69, 0x6e, 0x07, 0x22, 0xa1, 0xed, 0x8d, 0x27, 0x6d, 0x2f, 0xb7, 0x6f, 0x95, 0x12, 0xb9, - 0xcd, 0xf8, 0x57, 0xc2, 0x26, 0x7d, 0xdc, 0x48, 0xa4, 0x56, 0xda, 0x3b, 0x76, 0x9c, 0x1c, 0x31, 0xc0, 0x65, 0x09, - 0x37, 0x21, 0xaf, 0xe7, 0x6a, 0xbd, 0x77, 0x49, 0xad, 0xe8, 0x6e, 0x3c, 0x6e, 0x2c, 0x37, 0xf1, 0x93, 0x4f, 0x57, - 0x9a, 0x32, 0x0b, 0xdf, 0xa7, 0x62, 0x6b, 0x01, 0x06, 0xeb, 0xae, 0x07, 0x2e, 0xbb, 0xfa, 0xa3, 0x38, 0x81, 0x33, - 0x9b, 0xf8, 0x93, 0x60, 0x95, 0xf6, 0x5c, 0x6f, 0x79, 0x27, 0x92, 0xf8, 0x5e, 0x2f, 0x12, 0xf0, 0xec, 0xf5, 0xd2, - 0x38, 0x0c, 0x26, 0x22, 0x69, 0xd3, 0x59, 0x72, 0x3d, 0xa3, 0x8f, 0x06, 0xeb, 0x01, 0xba, 0x5d, 0xf0, 0xc3, 0x50, - 0xb3, 0xdb, 0xa9, 0xc6, 0xfc, 0x14, 0xf9, 0xcb, 0x9a, 0x93, 0x12, 0x5c, 0xd0, 0x38, 0xdd, 0x3d, 0x5c, 0xde, 0xc9, - 0x3d, 0xef, 0x1e, 0x2d, 0xef, 0xf2, 0xbf, 0x2e, 0xd8, 0x24, 0xf0, 0xb5, 0x56, 0xb1, 0x9b, 0x5c, 0x07, 0x78, 0xd0, - 0xc6, 0x7a, 0xc3, 0x36, 0x15, 0xc7, 0x02, 0x5c, 0x1b, 0x3e, 0x0a, 0x16, 0xcb, 0x38, 0xc9, 0xfc, 0x28, 0xcb, 0xf3, - 0xe1, 0x55, 0x9e, 0xf7, 0x2f, 0x82, 0xd6, 0xe5, 0x3f, 0x5a, 0x74, 0x4f, 0x93, 0xcc, 0x26, 0x37, 0xae, 0xcc, 0xd7, - 0x4c, 0xd5, 0x19, 0x81, 0x6b, 0x0c, 0xf5, 0x45, 0xd4, 0xc2, 0x74, 0x4b, 0xd6, 0x0b, 0x13, 0x90, 0x65, 0x71, 0xd2, - 0x41, 0x29, 0x17, 0xc1, 0x1b, 0x08, 0x0a, 0xbc, 0x66, 0x83, 0x0b, 0x45, 0xff, 0x04, 0x88, 0x15, 0x2c, 0x4c, 0x76, - 0x05, 0x4f, 0x36, 0xd1, 0x8c, 0xdf, 0xed, 0xa6, 0x19, 0x7f, 0xcd, 0xf6, 0xa1, 0x19, 0xbf, 0xfb, 0xea, 0x34, 0xe3, - 0x93, 0xba, 0x5d, 0xc1, 0xdb, 0x78, 0xa0, 0x4b, 0x09, 0x03, 0x5c, 0x4d, 0x09, 0x79, 0xec, 0x79, 0xfb, 0x87, 0xcd, - 0x00, 0x44, 0x6b, 0x14, 0x83, 0x8e, 0x6e, 0x6e, 0xe0, 0xc7, 0xbe, 0x8b, 0x06, 0x7f, 0x4f, 0xd4, 0xef, 0xe9, 0x74, - 0xf0, 0x2a, 0x56, 0x12, 0xe4, 0x17, 0x57, 0xbe, 0x28, 0x79, 0x57, 0xa0, 0x1c, 0xa1, 0x85, 0x89, 0xf1, 0x27, 0xc0, - 0x38, 0x9b, 0xb4, 0x8e, 0x27, 0x52, 0xfb, 0xac, 0x5f, 0x1e, 0x42, 0x4b, 0xaa, 0x7c, 0x0a, 0x13, 0x9c, 0x1a, 0x2b, - 0x71, 0xc6, 0x32, 0x6e, 0x33, 0xfb, 0xfd, 0xfd, 0xdb, 0x49, 0xeb, 0x6d, 0x6c, 0xe4, 0x41, 0xfa, 0xae, 0x6a, 0x00, - 0xc3, 0x65, 0x3f, 0x03, 0x75, 0x3a, 0x39, 0xd7, 0x20, 0x53, 0x03, 0x4c, 0x43, 0x36, 0x55, 0x3f, 0x2b, 0xcd, 0xb4, - 0xa7, 0x56, 0xe4, 0x81, 0xae, 0x6a, 0x97, 0x31, 0xb7, 0x3e, 0x58, 0x73, 0x0a, 0x10, 0x63, 0x77, 0xa1, 0xdd, 0xf0, - 0x84, 0xaa, 0x07, 0x93, 0x3c, 0x37, 0xfa, 0x02, 0x10, 0xca, 0x45, 0xcb, 0x76, 0x11, 0x71, 0xe9, 0xad, 0xd4, 0x69, - 0xe0, 0x12, 0x42, 0x12, 0xff, 0xbd, 0x05, 0x81, 0x3a, 0x17, 0x16, 0x72, 0x98, 0xe9, 0x1a, 0x81, 0x8f, 0x14, 0x2d, - 0x94, 0x09, 0x81, 0x04, 0x58, 0xc2, 0x5f, 0x64, 0x89, 0x84, 0xba, 0x0e, 0x27, 0x01, 0x07, 0x35, 0x02, 0xc0, 0xca, - 0x5f, 0xf0, 0xb5, 0x09, 0xed, 0xf0, 0x32, 0xf8, 0x91, 0xeb, 0x92, 0xf6, 0xc3, 0xed, 0x77, 0x7a, 0x72, 0x00, 0x15, - 0x4e, 0x2b, 0x8a, 0x03, 0x3b, 0x34, 0x14, 0x81, 0x94, 0x48, 0x6f, 0x4d, 0x3b, 0xbd, 0xd5, 0x9e, 0xad, 0x85, 0x87, - 0x8c, 0xcc, 0x5f, 0x5a, 0xf0, 0xc4, 0x47, 0xdc, 0xcb, 0x31, 0x9e, 0xe2, 0x8c, 0xa3, 0xbf, 0x4a, 0x01, 0x37, 0xe2, - 0x43, 0x15, 0xf1, 0x4f, 0x7f, 0xbc, 0x4a, 0xd2, 0x38, 0xe9, 0x2d, 0xe3, 0x20, 0xca, 0x58, 0x92, 0x23, 0xa8, 0x2e, - 0x11, 0x3e, 0x02, 0x3c, 0x57, 0xeb, 0x78, 0xe9, 0x8f, 0x83, 0xec, 0xbe, 0xe7, 0x70, 0x92, 0xc2, 0xe9, 0x73, 0xea, - 0xc0, 0x69, 0x2c, 0xdf, 0xe3, 0xd0, 0x7c, 0x8e, 0x84, 0x5f, 0x52, 0x27, 0x67, 0xd4, 0x6d, 0xde, 0x57, 0x72, 0xc9, - 0x47, 0x08, 0x90, 0x1f, 0x7e, 0x62, 0xcd, 0x00, 0xcb, 0xc3, 0x52, 0x3b, 0x13, 0x36, 0x33, 0x11, 0x6b, 0x03, 0x5f, - 0x5e, 0xfc, 0xb1, 0x3b, 0x86, 0xe6, 0x34, 0x27, 0x03, 0xc5, 0x63, 0xec, 0x33, 0xb2, 0x9e, 0x0f, 0x11, 0xb5, 0xcc, - 0x7d, 0x4a, 0x8e, 0xd8, 0x34, 0x4e, 0x18, 0xf9, 0x93, 0x75, 0xbb, 0xcb, 0xbb, 0xfd, 0x9b, 0xdf, 0x3e, 0xfd, 0xe6, - 0x76, 0xa2, 0x38, 0x6b, 0x89, 0xc6, 0x8c, 0x1d, 0xad, 0xd5, 0xef, 0x33, 0x20, 0x0d, 0x09, 0xf2, 0x63, 0x72, 0xdd, - 0xd5, 0xd3, 0xf5, 0x7e, 0xa3, 0xdb, 0xae, 0x65, 0xcc, 0xef, 0xbc, 0x84, 0x85, 0x7e, 0x16, 0xdc, 0x08, 0x9a, 0xb1, - 0x7d, 0xb4, 0xbc, 0x13, 0x6b, 0x8c, 0x17, 0xde, 0x03, 0x16, 0xa9, 0x32, 0x14, 0xb1, 0x48, 0xd5, 0x64, 0x5c, 0xa4, - 0x7e, 0x6d, 0x36, 0xc2, 0x93, 0x45, 0xe5, 0xa6, 0xef, 0x2c, 0xef, 0xd4, 0x2b, 0xba, 0xa8, 0x26, 0x6f, 0xea, 0xaa, - 0x0b, 0xb2, 0x45, 0x30, 0x99, 0x84, 0x2c, 0x2f, 0x2d, 0x74, 0x79, 0x2d, 0x15, 0xe0, 0x48, 0x38, 0xf8, 0xa3, 0x34, - 0x0e, 0x57, 0x19, 0x6b, 0x06, 0x17, 0x01, 0xc7, 0x73, 0x0a, 0xe0, 0xe0, 0xef, 0xf2, 0x58, 0x3b, 0x40, 0x6e, 0xc3, - 0x36, 0x71, 0xfa, 0xe0, 0x71, 0xd8, 0x6a, 0x97, 0x87, 0x0e, 0x59, 0x72, 0xd0, 0x66, 0xc3, 0x44, 0x4c, 0xb8, 0x96, - 0x08, 0x7b, 0x6b, 0xb6, 0xcb, 0xd3, 0xa4, 0xd7, 0x55, 0x99, 0x94, 0x97, 0x27, 0xf3, 0xe7, 0x9c, 0xb1, 0x17, 0xcd, - 0x67, 0xec, 0x85, 0x38, 0x63, 0xdb, 0x77, 0xe6, 0xe3, 0xa9, 0x0b, 0xff, 0xf5, 0x8b, 0x09, 0xf5, 0x1c, 0xad, 0xbd, - 0xbc, 0xd3, 0xdc, 0xe5, 0x9d, 0x66, 0x79, 0xcb, 0x3b, 0x0d, 0x9b, 0x46, 0x7d, 0x10, 0xd3, 0xf6, 0x0c, 0xd3, 0xd1, - 0x20, 0x11, 0xfe, 0x38, 0xa5, 0x2c, 0xf7, 0x10, 0xf2, 0xa0, 0x56, 0xa7, 0x9e, 0xe7, 0x6d, 0x3f, 0xea, 0x74, 0x96, - 0x04, 0xd2, 0x36, 0xec, 0xcc, 0x1f, 0x8d, 0xd8, 0xa4, 0x37, 0x8d, 0xc7, 0xab, 0xf4, 0x5f, 0x7c, 0xfc, 0x1c, 0x88, - 0x5b, 0x11, 0x41, 0xa5, 0x1d, 0x51, 0x15, 0x04, 0x25, 0x37, 0x4c, 0xb4, 0xb0, 0x96, 0xeb, 0xd4, 0x23, 0xf7, 0xc8, - 0x9e, 0x7d, 0xd8, 0xb0, 0xc9, 0x9b, 0x01, 0xfd, 0xa7, 0xad, 0xd2, 0x66, 0x14, 0xf3, 0x05, 0x60, 0xd9, 0x0a, 0x8e, - 0x87, 0x43, 0x83, 0xaf, 0xa6, 0xd3, 0x6d, 0x1e, 0xee, 0xa5, 0xe8, 0xe9, 0x4a, 0x5c, 0x2a, 0xfc, 0xde, 0xe2, 0x86, - 0x29, 0xdb, 0x5b, 0xdd, 0xb4, 0x47, 0x6a, 0xad, 0x6e, 0xb9, 0x10, 0x8a, 0xb2, 0x7b, 0x62, 0xf9, 0xc7, 0x2f, 0x0e, - 0xe1, 0x3f, 0xa2, 0xea, 0x7f, 0xcd, 0x9a, 0x08, 0xf5, 0xb7, 0x65, 0x4d, 0x70, 0x22, 0x95, 0x90, 0x10, 0xdf, 0xbf, - 0xfc, 0x74, 0xfa, 0xb0, 0x0a, 0x7b, 0x97, 0x26, 0x55, 0xaa, 0x6a, 0xe9, 0xef, 0xe3, 0x18, 0x42, 0x77, 0xd6, 0x8b, - 0x0b, 0xf0, 0x90, 0xb2, 0x7b, 0x36, 0x80, 0x4a, 0xe2, 0x1d, 0x41, 0x52, 0x7c, 0x1d, 0xeb, 0xd0, 0x53, 0xe2, 0xf5, - 0xa6, 0xa7, 0xc4, 0xab, 0xdd, 0x4f, 0x89, 0x1f, 0xf6, 0x7a, 0x4a, 0xbc, 0xfa, 0xea, 0x4f, 0x89, 0xd7, 0xf5, 0xa7, - 0xc4, 0x45, 0x2c, 0xf4, 0x67, 0xcd, 0xb7, 0x2b, 0xfe, 0xf3, 0x23, 0x09, 0xe5, 0xce, 0xe3, 0x41, 0xc7, 0x21, 0x97, - 0xc7, 0x17, 0x7f, 0xf8, 0x61, 0x81, 0x1b, 0xf1, 0x3d, 0xaa, 0x93, 0x15, 0x4f, 0x0b, 0x8e, 0xd9, 0xb1, 0x1f, 0x25, - 0x39, 0x8c, 0xa3, 0xd9, 0xcf, 0x20, 0x94, 0x05, 0x76, 0x60, 0xa2, 0x64, 0x04, 0xe9, 0xcf, 0xf1, 0x72, 0xb5, 0x7c, - 0x0b, 0x6d, 0x7d, 0x0c, 0xd2, 0x60, 0x14, 0x32, 0x69, 0x89, 0x4c, 0xea, 0x6f, 0x9c, 0x27, 0x0e, 0x1a, 0xa7, 0xe2, - 0xa7, 0x7f, 0x27, 0x7e, 0xa2, 0x4e, 0x2a, 0xff, 0x4d, 0x7a, 0x75, 0x7a, 0xf3, 0x43, 0x44, 0x08, 0x01, 0x95, 0x41, - 0x3f, 0xfc, 0x31, 0x72, 0x11, 0x1b, 0x0d, 0xb3, 0x14, 0xfa, 0x0e, 0x1b, 0xdb, 0x61, 0xb5, 0x47, 0xcd, 0xca, 0x30, - 0xa5, 0x0b, 0xae, 0x3a, 0x1b, 0x7e, 0x11, 0xaf, 0x52, 0x36, 0x89, 0x6f, 0x23, 0xdd, 0x8c, 0xa4, 0x91, 0x01, 0x48, - 0x38, 0x65, 0x1d, 0x0c, 0x1e, 0xf9, 0x01, 0x09, 0xe5, 0x38, 0x69, 0xe9, 0x10, 0xbb, 0x74, 0xb5, 0xb4, 0x48, 0xd4, - 0x6c, 0xe1, 0x14, 0x75, 0x19, 0xe5, 0xe8, 0x51, 0xab, 0x15, 0x0f, 0x1e, 0x56, 0x53, 0xa8, 0x6a, 0xc4, 0x36, 0xe7, - 0x0a, 0xa7, 0xad, 0x48, 0x30, 0x17, 0x85, 0x1f, 0x8c, 0x86, 0x85, 0xe3, 0x39, 0x64, 0xba, 0x5a, 0xe4, 0x82, 0x17, - 0x91, 0x7c, 0xc5, 0xd7, 0x83, 0x7b, 0x85, 0xa0, 0xcf, 0x97, 0x0a, 0x18, 0xdf, 0xdd, 0xb0, 0x24, 0xf4, 0xef, 0x5b, - 0x46, 0x1e, 0x47, 0x3f, 0x02, 0x00, 0x5e, 0xc5, 0xb7, 0x91, 0x5a, 0x00, 0x83, 0xb5, 0x34, 0xec, 0xa5, 0x46, 0xff, - 0x25, 0x60, 0xb8, 0xa2, 0x8c, 0x00, 0xc2, 0xe4, 0xce, 0xd8, 0xdf, 0x4d, 0xfa, 0xf7, 0x1f, 0x46, 0x6e, 0x9e, 0xc7, - 0xb2, 0xa3, 0x5f, 0x96, 0x7b, 0x74, 0xf3, 0xf4, 0xe9, 0xa3, 0xcd, 0xd3, 0x2e, 0x87, 0x67, 0x6f, 0xa8, 0x6d, 0x6c, - 0x3c, 0x05, 0x30, 0x8a, 0x8b, 0x78, 0x35, 0x9e, 0xa3, 0xa2, 0xeb, 0xd7, 0x9b, 0x6f, 0x06, 0x6d, 0x62, 0x94, 0x52, - 0x39, 0xf5, 0x4a, 0x52, 0x01, 0x05, 0xec, 0xff, 0x35, 0x38, 0xe0, 0xfc, 0x1f, 0x82, 0xa1, 0xbe, 0x6b, 0xf8, 0x2b, - 0x3e, 0x78, 0xd8, 0xe6, 0xed, 0x43, 0x30, 0x4d, 0xee, 0xda, 0x42, 0x08, 0xd7, 0x9a, 0x91, 0x4c, 0x5e, 0x05, 0x9a, - 0xea, 0x46, 0x6e, 0x93, 0x87, 0x3c, 0xd1, 0x0b, 0xb3, 0xe9, 0x99, 0xce, 0x0d, 0x0d, 0x4c, 0xc6, 0xb1, 0x55, 0x05, - 0xc9, 0x70, 0x95, 0x07, 0x86, 0xe8, 0xab, 0x9a, 0xb7, 0x08, 0x22, 0x13, 0xbd, 0xc0, 0xd7, 0x73, 0xfc, 0x3b, 0xf0, - 0x83, 0x0c, 0xc8, 0xad, 0x9a, 0x05, 0x89, 0xa6, 0x6a, 0x37, 0x07, 0xa1, 0x9e, 0xf4, 0x46, 0x48, 0x08, 0x29, 0xde, - 0xf0, 0x1b, 0x4d, 0xd3, 0x34, 0xf9, 0x8c, 0xd0, 0xe4, 0x3b, 0x02, 0xd3, 0xf1, 0x39, 0x00, 0xd2, 0x92, 0x7c, 0x79, - 0x47, 0x29, 0xf0, 0x32, 0x40, 0x99, 0xac, 0x48, 0xe0, 0xae, 0xfe, 0x3a, 0x8e, 0x48, 0x10, 0x0f, 0x7a, 0x70, 0xd3, - 0xe6, 0x27, 0xe0, 0x11, 0xb8, 0xa7, 0xe1, 0x83, 0x1d, 0x73, 0x39, 0x27, 0x58, 0x73, 0xe8, 0x73, 0xd8, 0x67, 0xcd, - 0x3e, 0xe1, 0x22, 0x05, 0x0b, 0x82, 0xd4, 0xa1, 0xe2, 0xe2, 0xd9, 0x64, 0x0d, 0xb8, 0x11, 0xdf, 0x45, 0x77, 0xd9, - 0x82, 0x45, 0x2b, 0x1d, 0x63, 0x42, 0xa1, 0x8f, 0x3e, 0x28, 0xf3, 0x8a, 0x88, 0x2d, 0xc0, 0x36, 0xcd, 0x35, 0xe7, - 0x74, 0x17, 0xa6, 0x1c, 0xa5, 0xfa, 0xe6, 0x98, 0x0b, 0x36, 0x53, 0x8e, 0xdb, 0xaa, 0x37, 0x04, 0x5f, 0xd2, 0xb8, - 0x6a, 0xc8, 0x45, 0x9a, 0xd0, 0xd0, 0x06, 0x79, 0xc7, 0xe0, 0xec, 0x22, 0x01, 0xf6, 0x96, 0x5f, 0x5d, 0x34, 0x29, - 0x91, 0xf1, 0x2b, 0x8c, 0xa2, 0xc4, 0xa8, 0x37, 0xc3, 0xc7, 0x09, 0x8e, 0x89, 0x36, 0xb6, 0x33, 0xae, 0xb5, 0xb3, - 0x61, 0xd2, 0x9f, 0xd8, 0x3d, 0x5d, 0x24, 0x04, 0xaa, 0x4f, 0xec, 0x1e, 0x74, 0xff, 0x5e, 0x03, 0x37, 0x45, 0xdf, - 0x82, 0xae, 0x4d, 0x70, 0xf5, 0x3f, 0x06, 0x67, 0x55, 0x5b, 0x0e, 0x90, 0x93, 0x6f, 0xc1, 0xe2, 0x08, 0x62, 0x88, - 0xea, 0x2c, 0x0e, 0x31, 0x57, 0xf1, 0x6f, 0x35, 0xc2, 0xd8, 0x6a, 0x38, 0x1a, 0xc6, 0x33, 0xd7, 0x71, 0x0e, 0x6a, - 0xe5, 0x81, 0x91, 0xdd, 0x54, 0xda, 0x30, 0xb3, 0x81, 0xeb, 0x58, 0xc1, 0x33, 0xdb, 0xeb, 0xd7, 0xee, 0x68, 0xc5, - 0x97, 0xe4, 0x10, 0xd9, 0x5f, 0xa7, 0x4f, 0xd6, 0xad, 0xda, 0x81, 0x34, 0xaa, 0x2a, 0xf3, 0x38, 0xb6, 0x9c, 0xf3, - 0xbf, 0x86, 0xf5, 0xab, 0x9f, 0x3c, 0x59, 0x52, 0x5c, 0x93, 0x21, 0x78, 0x43, 0x6e, 0xc1, 0x31, 0xfa, 0x8b, 0xf6, - 0x5c, 0x6b, 0xd1, 0xf1, 0x31, 0x8c, 0xa1, 0x0c, 0x97, 0x2d, 0x6c, 0xca, 0xd4, 0x06, 0x2a, 0x3d, 0xa6, 0x55, 0x0c, - 0xc7, 0xfd, 0xae, 0xb2, 0x42, 0xa2, 0xb7, 0x95, 0x5a, 0xc0, 0xf6, 0x37, 0x5c, 0x9f, 0xf6, 0x08, 0xfc, 0x12, 0x40, - 0x09, 0xf0, 0x9d, 0xbe, 0xb3, 0xc1, 0xd5, 0xb2, 0xdc, 0x5c, 0xf9, 0x92, 0xdc, 0xbf, 0x31, 0xbc, 0x74, 0x50, 0x86, - 0x26, 0xdb, 0x6b, 0xbe, 0xee, 0x1e, 0xd8, 0x24, 0x8b, 0x26, 0xe5, 0x06, 0x2b, 0xf7, 0xd7, 0xfe, 0xcd, 0x95, 0x30, - 0x0a, 0x04, 0x15, 0x88, 0x1b, 0x30, 0x4a, 0x1e, 0x47, 0xb8, 0xf9, 0xe9, 0xb8, 0x05, 0x7b, 0x51, 0x31, 0x58, 0x81, - 0x3c, 0x82, 0xc9, 0x6a, 0x0a, 0x53, 0x1c, 0x3c, 0x57, 0xa3, 0x59, 0x70, 0x4b, 0x10, 0xa2, 0x1b, 0x77, 0x62, 0x26, - 0x74, 0x0a, 0x8b, 0x3a, 0x01, 0xf7, 0x45, 0xb9, 0x2f, 0xd7, 0x3a, 0xd8, 0xcd, 0xb5, 0xce, 0x76, 0x71, 0xad, 0xc9, - 0x9c, 0xea, 0x36, 0xf1, 0x97, 0x8a, 0x45, 0x9e, 0x20, 0xce, 0x55, 0xc3, 0xbc, 0x12, 0xab, 0x1b, 0xad, 0xaf, 0x44, - 0xad, 0x5a, 0x6b, 0xa4, 0x25, 0x88, 0xec, 0x6f, 0xe5, 0x81, 0x22, 0x04, 0xea, 0x2a, 0x6f, 0xfc, 0xa2, 0xe0, 0x8d, - 0xd3, 0xab, 0xa6, 0x30, 0xa4, 0x11, 0xd4, 0xbf, 0x62, 0xa4, 0x26, 0x5f, 0x07, 0x85, 0xb1, 0x5a, 0x31, 0x52, 0xc5, - 0xfc, 0xaa, 0x78, 0x68, 0x28, 0x46, 0x7d, 0xe2, 0x95, 0x51, 0xb6, 0xed, 0x2b, 0x17, 0x2d, 0xac, 0xaf, 0x8a, 0x74, - 0xe0, 0xba, 0xe3, 0x90, 0x65, 0xb2, 0xba, 0x6d, 0xca, 0xe6, 0x37, 0x6a, 0xb6, 0xb2, 0x49, 0xa4, 0x9d, 0x0c, 0x01, - 0x58, 0xb0, 0xe9, 0x2b, 0x72, 0x6d, 0xa9, 0x03, 0x81, 0x83, 0x6c, 0x30, 0xeb, 0xdb, 0xcd, 0x9d, 0xa7, 0x78, 0x09, - 0x85, 0x14, 0x5e, 0xe5, 0x41, 0x20, 0x7c, 0xaf, 0xd6, 0x0d, 0xb7, 0x3c, 0x5e, 0xf2, 0xfc, 0x7e, 0x07, 0xf6, 0xa2, - 0xe6, 0xa8, 0x82, 0x7c, 0x3c, 0x99, 0x16, 0xa9, 0xe7, 0x62, 0xd1, 0x7a, 0xa3, 0xc4, 0xc4, 0x59, 0x73, 0xcb, 0x98, - 0x32, 0x8f, 0x9e, 0x97, 0xe8, 0x89, 0x7e, 0xf9, 0xd6, 0x49, 0x56, 0x11, 0xfa, 0xb6, 0xb7, 0xb2, 0xc4, 0x1f, 0x7f, - 0x52, 0x86, 0x2c, 0xf8, 0x9c, 0xc0, 0x03, 0x2e, 0x4b, 0x0a, 0xfa, 0x3e, 0xba, 0x82, 0x64, 0x3d, 0xdb, 0x4b, 0x15, - 0xee, 0x4b, 0xef, 0xb1, 0xd3, 0xf6, 0x5f, 0x4c, 0x0f, 0x2b, 0x4c, 0x51, 0xaf, 0x53, 0x66, 0x99, 0x6f, 0x18, 0x47, - 0x36, 0x5f, 0x2d, 0x46, 0x6b, 0x95, 0xb7, 0xaa, 0xb0, 0x5c, 0xeb, 0x6c, 0x56, 0xb5, 0xdb, 0xe9, 0x74, 0x5a, 0x66, - 0x34, 0x3a, 0xda, 0x21, 0x32, 0x0b, 0x1f, 0x3b, 0x8e, 0x53, 0x1d, 0xfb, 0x76, 0xb0, 0x5b, 0xc8, 0xb7, 0xed, 0x36, - 0x8e, 0x18, 0x61, 0xbb, 0x0b, 0x7e, 0x75, 0x70, 0xe4, 0x76, 0x71, 0xb2, 0x4b, 0x6a, 0x11, 0x7d, 0x52, 0x86, 0x08, - 0x32, 0xb6, 0x48, 0x7b, 0x63, 0x86, 0x32, 0x18, 0x5b, 0x39, 0xd0, 0xa8, 0x38, 0x60, 0xcd, 0x40, 0x55, 0xc4, 0x15, - 0xbb, 0xc2, 0xd1, 0x90, 0x1f, 0x5e, 0x63, 0xde, 0x8b, 0x4e, 0xf0, 0xa0, 0xac, 0xeb, 0x3c, 0x6d, 0x9c, 0x56, 0xc7, - 0xf9, 0x4b, 0xa9, 0x9c, 0x06, 0x17, 0xe0, 0x5a, 0x08, 0xb4, 0x89, 0x3f, 0x8b, 0x7f, 0x4b, 0xfe, 0xff, 0x8b, 0xe5, - 0x5d, 0x59, 0x7f, 0xa4, 0x0b, 0x1c, 0xed, 0xe2, 0xb4, 0xd0, 0xa8, 0x9b, 0xf6, 0x80, 0xd4, 0x32, 0x98, 0xaa, 0x02, - 0x74, 0x10, 0xd2, 0x97, 0x02, 0x80, 0x34, 0xb0, 0xdf, 0x91, 0x62, 0x86, 0x25, 0x2e, 0x58, 0x88, 0x45, 0xf8, 0x3a, - 0x98, 0x83, 0xf9, 0xbc, 0x8b, 0xf2, 0x83, 0xd2, 0x9e, 0x00, 0x69, 0x7c, 0x6d, 0x6e, 0x7b, 0xb1, 0xfb, 0xab, 0x72, - 0x2d, 0xd1, 0x30, 0x80, 0xcc, 0x85, 0x43, 0x88, 0x8a, 0x04, 0x5a, 0x65, 0x73, 0xd3, 0x28, 0x65, 0xae, 0x2a, 0x67, - 0x13, 0x03, 0xc3, 0xe6, 0x9a, 0x8b, 0x50, 0xdb, 0x42, 0x5a, 0x00, 0x93, 0xe5, 0xdb, 0x0f, 0xbf, 0x2d, 0x58, 0x62, - 0x75, 0x3f, 0xba, 0xb8, 0xe4, 0xb8, 0x7f, 0x2d, 0xbc, 0x3b, 0x53, 0x3a, 0xff, 0xc8, 0x5f, 0xfc, 0xa1, 0x91, 0xa1, - 0x77, 0x51, 0xe2, 0xd0, 0x71, 0x6d, 0x71, 0xcf, 0xd8, 0xab, 0xf4, 0x22, 0x88, 0xf6, 0x2f, 0xeb, 0xdf, 0xed, 0x5d, - 0x16, 0x2e, 0x8c, 0xbd, 0x0b, 0xc3, 0x8d, 0x43, 0x9a, 0x0b, 0xd9, 0xe0, 0x07, 0x85, 0xa1, 0xa8, 0x5a, 0x1d, 0xeb, - 0x58, 0x8b, 0xa8, 0xfc, 0x8b, 0xd5, 0x60, 0x78, 0x72, 0x76, 0xb7, 0x08, 0xb5, 0x1b, 0x96, 0x40, 0x68, 0x9f, 0x81, - 0xee, 0xda, 0x8e, 0xae, 0xa1, 0x0d, 0x6d, 0x10, 0xcd, 0x06, 0xfa, 0x2f, 0x17, 0x6f, 0xac, 0xae, 0x7e, 0x06, 0x22, - 0xda, 0x9b, 0x19, 0x5e, 0x7b, 0xe7, 0xfe, 0x3d, 0x4b, 0xae, 0x3d, 0x5d, 0xc3, 0x08, 0x3e, 0x74, 0xe1, 0x61, 0x9a, - 0xe6, 0xe9, 0x7b, 0x04, 0x8a, 0xd0, 0x44, 0xac, 0x37, 0x1d, 0x50, 0x8e, 0xeb, 0x75, 0x35, 0xd7, 0x3b, 0xb4, 0x8f, - 0xba, 0xfa, 0xe9, 0x37, 0x9a, 0x76, 0x32, 0x61, 0xd3, 0xf4, 0x14, 0x9f, 0x68, 0x27, 0x78, 0x47, 0xd0, 0x6f, 0x4d, - 0xb3, 0xc7, 0x61, 0x6a, 0xb9, 0xda, 0x9a, 0x7f, 0x6a, 0xda, 0x34, 0x08, 0xc3, 0x9e, 0xf6, 0x78, 0xea, 0x4d, 0x0f, - 0xa7, 0x2f, 0xfa, 0x3c, 0x39, 0xff, 0xa6, 0x54, 0xdc, 0xa4, 0x7f, 0x3d, 0xa5, 0x5a, 0x9a, 0x25, 0xf1, 0x27, 0xc6, - 0xd5, 0x4e, 0x34, 0xf9, 0x78, 0xac, 0x56, 0xf5, 0xea, 0x3d, 0xb9, 0xdd, 0xd1, 0x78, 0xea, 0x15, 0xc5, 0x71, 0x8c, - 0x07, 0x72, 0x90, 0x27, 0x07, 0x62, 0xe8, 0x27, 0x2a, 0x98, 0x5c, 0xab, 0x09, 0x50, 0xae, 0xce, 0xe7, 0x38, 0x13, - 0xf3, 0x3b, 0x01, 0x3f, 0x8c, 0xd2, 0x5c, 0x17, 0x46, 0xa0, 0x6b, 0x93, 0x81, 0xfe, 0xa3, 0xeb, 0x75, 0x4d, 0xd7, - 0x3d, 0xb2, 0x8f, 0xba, 0x63, 0xc7, 0x3c, 0xb4, 0x0f, 0xad, 0xb6, 0x7d, 0x64, 0x76, 0xad, 0xae, 0xd9, 0xfd, 0x5b, - 0x77, 0x6c, 0x1d, 0xda, 0x87, 0xa6, 0x63, 0x75, 0x21, 0xd1, 0xea, 0x5a, 0xdd, 0x1b, 0xeb, 0xb0, 0x3b, 0x76, 0x30, - 0xd5, 0xb3, 0x3b, 0x1d, 0xcb, 0x75, 0xec, 0x4e, 0xc7, 0xec, 0xd8, 0x47, 0x47, 0x96, 0xdb, 0xb6, 0x8f, 0x8e, 0xce, - 0x3b, 0x5d, 0xbb, 0x0d, 0x79, 0xed, 0xf6, 0xb8, 0x6d, 0xbb, 0xae, 0x05, 0x7f, 0x99, 0x5d, 0xdb, 0xa3, 0x1f, 0xae, - 0x6b, 0xb7, 0x5d, 0xd3, 0x09, 0x3b, 0x9e, 0x7d, 0xf4, 0xc2, 0xc4, 0xbf, 0xb1, 0x98, 0x89, 0x7f, 0x41, 0x33, 0xe6, - 0x0b, 0xdb, 0x3b, 0xa2, 0x5f, 0xd8, 0xe0, 0xcd, 0x61, 0xf7, 0x57, 0xfd, 0x60, 0xe3, 0x1c, 0x5c, 0x9a, 0x43, 0xb7, - 0x63, 0xb7, 0xdb, 0xe6, 0xa1, 0x6b, 0x77, 0xdb, 0x73, 0xeb, 0xd0, 0xb3, 0x8f, 0x8e, 0xc7, 0x96, 0x6b, 0x1f, 0x1f, - 0x9b, 0x8e, 0xd5, 0xb6, 0x3d, 0xd3, 0xb5, 0x0f, 0xdb, 0xf8, 0xa3, 0x6d, 0x7b, 0x37, 0xc7, 0x2f, 0xec, 0xa3, 0xce, - 0xfc, 0xc8, 0x3e, 0xfc, 0x78, 0xd8, 0xb5, 0xbd, 0xf6, 0xbc, 0x7d, 0x64, 0x7b, 0xc7, 0x37, 0x47, 0xf6, 0xe1, 0xdc, - 0xf2, 0x8e, 0xb6, 0xd6, 0x74, 0x3d, 0x1b, 0x60, 0x84, 0xd9, 0x90, 0x61, 0xf2, 0x0c, 0xf8, 0x33, 0xc7, 0xba, 0xff, - 0xc5, 0x66, 0xd2, 0x7a, 0xd5, 0x17, 0x76, 0xf7, 0x78, 0x4c, 0xc5, 0x21, 0xc1, 0x12, 0x25, 0xa0, 0xca, 0x8d, 0x45, - 0xdd, 0x62, 0x73, 0x96, 0x68, 0x48, 0xfc, 0xe1, 0x9d, 0xdd, 0x58, 0xd0, 0x31, 0xf5, 0xfb, 0x3f, 0x6d, 0x47, 0x2e, - 0x39, 0x44, 0xae, 0xfc, 0x86, 0xff, 0x43, 0x41, 0x5f, 0x86, 0xe6, 0xf9, 0x26, 0x41, 0xc5, 0xfb, 0xdd, 0x82, 0x8a, - 0x37, 0xab, 0x7d, 0x04, 0x15, 0xef, 0xbf, 0xba, 0xa0, 0xe2, 0xbc, 0xaa, 0x27, 0xff, 0xbe, 0xea, 0x9b, 0xfe, 0xd7, - 0x75, 0xf5, 0x19, 0x12, 0xf8, 0xad, 0xcb, 0x8b, 0xd5, 0x15, 0x78, 0x57, 0x7a, 0x1f, 0x0f, 0xde, 0xac, 0x4a, 0x4a, - 0x60, 0x31, 0xe0, 0xd8, 0xf7, 0x31, 0xe1, 0xd8, 0xdf, 0x57, 0x03, 0xd0, 0x3c, 0xe1, 0x74, 0x49, 0x30, 0xb1, 0xe6, - 0x7e, 0x38, 0x95, 0x34, 0x0d, 0xa4, 0xf4, 0x31, 0x19, 0xac, 0x12, 0xe0, 0xba, 0x06, 0x71, 0xd8, 0x6a, 0x11, 0xa5, - 0xbd, 0x23, 0x07, 0x2e, 0x52, 0x6f, 0x9a, 0xe4, 0x95, 0xca, 0xb6, 0xf0, 0x47, 0x75, 0xcd, 0xad, 0x26, 0x36, 0xe6, - 0xa3, 0x52, 0x60, 0x73, 0xeb, 0x6e, 0xbd, 0x5d, 0x0d, 0xb4, 0x6d, 0x84, 0xd2, 0x24, 0x90, 0x73, 0x4d, 0xf9, 0x65, - 0xd5, 0xbc, 0x8a, 0x32, 0xe6, 0xe6, 0x91, 0xc2, 0x48, 0xaa, 0xf5, 0xdd, 0xb2, 0x6a, 0xdf, 0xae, 0x69, 0x36, 0x74, - 0x5f, 0xaa, 0xbe, 0x45, 0xaf, 0x50, 0x36, 0x5c, 0x05, 0x55, 0x25, 0xb2, 0x5a, 0x23, 0x40, 0x0a, 0xea, 0xbe, 0x50, - 0x3e, 0x2c, 0x48, 0x4b, 0x47, 0x43, 0x7a, 0xc7, 0x51, 0xf2, 0x4a, 0x6d, 0xaa, 0x0a, 0x8b, 0xcf, 0xd6, 0x48, 0x71, - 0x07, 0xbf, 0x03, 0xe9, 0xc8, 0x29, 0x9e, 0x51, 0xac, 0xc2, 0x79, 0xad, 0xb4, 0x4b, 0x8f, 0x99, 0x7c, 0xee, 0xae, - 0xeb, 0xc4, 0xe3, 0x46, 0x55, 0x65, 0x97, 0x2d, 0x04, 0x15, 0x84, 0xdd, 0x93, 0x62, 0x70, 0x4e, 0xca, 0xdb, 0xa8, - 0xfb, 0xbc, 0xad, 0x31, 0x51, 0xee, 0x31, 0x6c, 0x62, 0x93, 0x7f, 0xa8, 0x7e, 0x01, 0xd6, 0x53, 0x88, 0x82, 0xdd, - 0x43, 0x32, 0x4d, 0xa1, 0x51, 0x3d, 0xd4, 0x62, 0xee, 0x6f, 0x51, 0xb0, 0x51, 0x1b, 0xe6, 0x8d, 0xa0, 0x36, 0xf4, - 0x36, 0x9d, 0x1c, 0x69, 0x3c, 0xb2, 0x2e, 0x89, 0xa8, 0xdd, 0xce, 0xb1, 0xe9, 0x1e, 0x99, 0xf6, 0x71, 0xc7, 0xc8, - 0xc5, 0x81, 0x53, 0x9b, 0x2c, 0x01, 0x04, 0x94, 0xa2, 0xe5, 0x30, 0x83, 0x28, 0xc8, 0x02, 0x3f, 0xcc, 0x81, 0x3e, - 0x2e, 0xbf, 0x2a, 0xfe, 0xb9, 0x4a, 0x33, 0x98, 0xa3, 0x20, 0x7a, 0x51, 0x21, 0xdc, 0x1a, 0xb1, 0xec, 0x96, 0xb1, - 0x68, 0x83, 0xb0, 0xbc, 0xaa, 0x5f, 0xfe, 0xe7, 0x69, 0xdb, 0xe6, 0xa4, 0xc9, 0x32, 0xca, 0x22, 0xbe, 0x3f, 0x84, - 0x32, 0x74, 0x3e, 0x34, 0x7f, 0xda, 0x84, 0x70, 0xff, 0xb9, 0x1b, 0xe1, 0x66, 0x6c, 0x1f, 0x84, 0xfb, 0xcf, 0xaf, - 0x8e, 0x70, 0x7f, 0x52, 0x11, 0x6e, 0xc9, 0x16, 0xa8, 0xe0, 0x3a, 0x7f, 0xc0, 0xef, 0x16, 0x38, 0x75, 0x7e, 0xae, - 0x1f, 0x10, 0x01, 0xaf, 0x2b, 0xc1, 0x76, 0x3f, 0x96, 0xa2, 0x07, 0x21, 0x53, 0x04, 0x9d, 0xd0, 0x52, 0xa4, 0x12, - 0x08, 0x44, 0x2b, 0x43, 0xaa, 0x43, 0x9b, 0x6f, 0xa3, 0x2c, 0xb4, 0xdf, 0xf3, 0x87, 0x1f, 0x08, 0x79, 0xde, 0xc4, - 0xc9, 0xc2, 0x47, 0x07, 0x7c, 0x3a, 0x46, 0x1d, 0x84, 0x0f, 0x07, 0xec, 0xcf, 0xc6, 0x71, 0x34, 0x91, 0x92, 0x0a, - 0x36, 0xb8, 0x24, 0x8a, 0x5b, 0xbf, 0x67, 0x7e, 0xa2, 0x9b, 0x94, 0x0d, 0x8b, 0xfb, 0xac, 0xed, 0x3c, 0xf3, 0x0e, - 0x9f, 0x1d, 0x39, 0xf0, 0xbf, 0xcb, 0xda, 0xb9, 0xc9, 0x0b, 0x2e, 0xe2, 0x08, 0x02, 0x9f, 0x88, 0x92, 0x9b, 0x8a, - 0xdd, 0x32, 0xf6, 0xa9, 0x28, 0x75, 0xdc, 0x5c, 0x68, 0xe2, 0xdf, 0x17, 0x65, 0x1a, 0x4b, 0xcc, 0xe3, 0x95, 0x32, - 0xac, 0x86, 0xd1, 0x04, 0xd1, 0x0a, 0x78, 0x6f, 0x4a, 0x09, 0x35, 0x9b, 0x4f, 0xb7, 0x98, 0x17, 0x6b, 0xe7, 0x57, - 0x45, 0x74, 0x25, 0x11, 0xe5, 0x65, 0x27, 0x04, 0xb9, 0xd8, 0xc2, 0x41, 0xdf, 0xec, 0x18, 0x5f, 0x48, 0x83, 0xd8, - 0x86, 0x62, 0x81, 0x7c, 0x5a, 0xa0, 0x2c, 0x59, 0x45, 0xe3, 0x16, 0xfe, 0xf4, 0x47, 0x69, 0x2b, 0x38, 0x00, 0xef, - 0xac, 0xd8, 0xb1, 0x81, 0xab, 0xe6, 0x9f, 0x3a, 0x45, 0x28, 0x8a, 0x54, 0xac, 0x8a, 0xff, 0x2c, 0x33, 0x13, 0x0a, - 0x60, 0x8b, 0x4b, 0x6b, 0x0d, 0xfc, 0x67, 0xb2, 0xe2, 0xb3, 0xcc, 0x84, 0x20, 0xb2, 0xb0, 0xdc, 0x4f, 0x9f, 0x52, - 0x29, 0x08, 0xeb, 0x48, 0xd3, 0x3a, 0x1b, 0x17, 0xee, 0xdd, 0x34, 0x7f, 0x16, 0x93, 0x87, 0xb7, 0xde, 0xd8, 0x8c, - 0x9f, 0x3f, 0x3f, 0x1d, 0xb8, 0x06, 0x0f, 0x4a, 0x5a, 0x8a, 0xa0, 0x75, 0xbe, 0x9f, 0xf2, 0x81, 0xd1, 0x68, 0x16, - 0xb7, 0x84, 0x37, 0x93, 0x23, 0x54, 0x94, 0x39, 0xf6, 0x82, 0x88, 0x16, 0x24, 0x64, 0xf4, 0x85, 0x12, 0x80, 0x28, - 0x23, 0x5f, 0x5d, 0x6d, 0xdb, 0xb1, 0x1d, 0x5d, 0x56, 0x9c, 0x06, 0xb3, 0xc1, 0x3a, 0xce, 0x7c, 0x88, 0x0d, 0x14, - 0xc6, 0x33, 0xb0, 0xad, 0xc9, 0x82, 0x2c, 0x84, 0x40, 0x33, 0x60, 0x64, 0xb3, 0xa0, 0x77, 0x79, 0xce, 0x35, 0x9e, - 0xfd, 0xe4, 0x13, 0x06, 0x1b, 0x14, 0x66, 0x75, 0xe8, 0x71, 0xe8, 0x47, 0xb8, 0x0c, 0x5b, 0x7a, 0x0b, 0x42, 0x5d, - 0xb2, 0x24, 0xb5, 0x54, 0x0b, 0x82, 0x9e, 0x06, 0x75, 0x20, 0x0c, 0x3d, 0x36, 0x30, 0x4d, 0xfc, 0x05, 0xf8, 0x64, - 0x5f, 0xe7, 0x26, 0xc7, 0xb4, 0x3a, 0x47, 0xb5, 0x9a, 0xfb, 0xe2, 0xc8, 0xd4, 0x3c, 0xd7, 0xd4, 0x1c, 0x40, 0xb7, - 0x7a, 0x6e, 0xae, 0xf3, 0xab, 0xfe, 0x2e, 0x21, 0x28, 0xe1, 0x97, 0xc7, 0x34, 0x0f, 0x12, 0x7f, 0x72, 0xf6, 0x72, - 0x46, 0x0e, 0x24, 0x5b, 0x8a, 0xb7, 0xf4, 0x80, 0x04, 0x21, 0x17, 0xec, 0x2e, 0x33, 0x30, 0x10, 0x0b, 0x2f, 0x12, - 0x18, 0x6b, 0x34, 0xfe, 0x0b, 0x22, 0x2d, 0xf8, 0xfc, 0xb9, 0x15, 0x80, 0x81, 0xc3, 0x40, 0x81, 0x0f, 0x7c, 0x1b, - 0x25, 0x80, 0x05, 0x85, 0xe8, 0x0e, 0x81, 0x05, 0xd6, 0x47, 0xf0, 0x6f, 0x91, 0x2c, 0x7e, 0x70, 0xd1, 0xa9, 0x1d, - 0xfa, 0xd1, 0x0c, 0x50, 0x9a, 0x1f, 0xcd, 0x6a, 0x2a, 0x1a, 0x64, 0xbf, 0x58, 0x49, 0x2d, 0x9a, 0x2a, 0xd4, 0x27, - 0xd2, 0xef, 0xef, 0x2f, 0x28, 0xd0, 0x14, 0x04, 0x35, 0xf7, 0x27, 0x68, 0x6c, 0x57, 0x48, 0x77, 0x9e, 0x0f, 0xbe, - 0x3d, 0x59, 0xb0, 0xcc, 0x27, 0xd6, 0x30, 0x3c, 0x7e, 0x81, 0x1c, 0xd0, 0xc6, 0x22, 0x48, 0x2c, 0x05, 0x93, 0x9f, - 0xb0, 0x9b, 0x60, 0xcc, 0xdf, 0xa5, 0xa6, 0xc6, 0xef, 0x29, 0x0b, 0xb5, 0xc0, 0x06, 0xae, 0x49, 0x4a, 0xc8, 0x63, - 0x1f, 0xdd, 0x4c, 0x0e, 0xa2, 0x58, 0x3f, 0xfd, 0x56, 0xda, 0x6b, 0x6d, 0x5a, 0x04, 0x88, 0xf6, 0x78, 0x99, 0xb0, - 0xf0, 0x5f, 0x83, 0x6f, 0xe1, 0xe2, 0xfe, 0xf6, 0x4a, 0x37, 0xfa, 0x99, 0x3d, 0x4f, 0xd8, 0x74, 0xf0, 0x6d, 0x43, - 0xd4, 0x43, 0x7c, 0xde, 0xd3, 0x58, 0xf4, 0xb6, 0x57, 0x38, 0x07, 0x6a, 0xef, 0xf5, 0xa8, 0x3f, 0xe5, 0xaf, 0x75, - 0x78, 0x01, 0xae, 0x4b, 0x6f, 0x6c, 0xb7, 0x8f, 0xef, 0xe7, 0x51, 0xe8, 0x8f, 0x3f, 0xf5, 0x29, 0xa7, 0xf4, 0x61, - 0xc1, 0x6d, 0x3d, 0xf6, 0x97, 0x3d, 0xbc, 0x5e, 0xd5, 0x44, 0x30, 0xd7, 0xa4, 0x54, 0x49, 0xd9, 0x35, 0xee, 0x65, - 0xdc, 0xca, 0x6b, 0xec, 0x19, 0xbb, 0xba, 0x9d, 0x07, 0x19, 0x13, 0x5d, 0xe1, 0x47, 0x9e, 0x8b, 0x87, 0x3a, 0x3d, - 0x51, 0xf1, 0x61, 0x6d, 0xb7, 0x35, 0xb7, 0xfb, 0xb7, 0xce, 0x8d, 0xeb, 0xcc, 0x3d, 0xd7, 0xee, 0x7e, 0x74, 0xbb, - 0xf3, 0xb6, 0x7d, 0x1c, 0x5a, 0x6d, 0xfb, 0x18, 0xfe, 0x7c, 0x3c, 0xb6, 0xbb, 0x73, 0xcb, 0xb3, 0x0f, 0x3f, 0xba, - 0x5e, 0x68, 0x75, 0xed, 0x63, 0xf8, 0x73, 0x4e, 0xb5, 0xe0, 0x01, 0x44, 0xef, 0x9d, 0x6f, 0x4b, 0x58, 0x40, 0xf9, - 0x2d, 0xe5, 0x34, 0x66, 0xe9, 0x7a, 0x6b, 0x90, 0xf5, 0x00, 0xca, 0xd0, 0x4d, 0xe1, 0x04, 0x32, 0xea, 0xb7, 0x20, - 0x0c, 0x3b, 0x06, 0x10, 0x10, 0x2a, 0x2f, 0xc2, 0x2e, 0x55, 0xb8, 0xd2, 0x6f, 0x3c, 0x46, 0xbc, 0x4e, 0xb3, 0xc3, - 0x75, 0x11, 0x99, 0x8a, 0x84, 0x43, 0xbf, 0x2c, 0xd1, 0x89, 0x91, 0x70, 0x11, 0xaf, 0x60, 0xa5, 0x22, 0x3a, 0x62, - 0xbe, 0x7b, 0xe0, 0x68, 0x99, 0xcb, 0x64, 0x74, 0x9e, 0xaf, 0xda, 0x36, 0x17, 0x18, 0xc9, 0xd6, 0xff, 0x68, 0x3b, - 0x18, 0x94, 0x96, 0xda, 0x11, 0xde, 0x5c, 0x27, 0x41, 0x22, 0x87, 0xa7, 0xa0, 0x68, 0xb7, 0xd9, 0x53, 0xbd, 0x01, - 0x61, 0x4c, 0xde, 0x02, 0x95, 0x7c, 0xe3, 0x87, 0x8a, 0x72, 0x8b, 0x52, 0xf3, 0x91, 0xc4, 0xfc, 0x4f, 0x9f, 0x16, - 0x83, 0xb3, 0x2a, 0xe3, 0x3e, 0x71, 0x3b, 0x70, 0xed, 0x76, 0x58, 0x7b, 0xab, 0x9e, 0xd5, 0x6e, 0x77, 0xc0, 0x85, - 0xbb, 0x50, 0xa1, 0x4b, 0x21, 0xa4, 0xb8, 0x1b, 0x95, 0xbd, 0x6a, 0x32, 0x5c, 0x70, 0xa4, 0x5c, 0x79, 0xea, 0xe8, - 0x46, 0x3f, 0x12, 0x22, 0xc9, 0x68, 0x8b, 0x0b, 0x64, 0xfe, 0x16, 0xd3, 0x01, 0x34, 0x5b, 0xe6, 0xb1, 0xc3, 0x68, - 0xf4, 0x7f, 0x3d, 0x09, 0x34, 0xe0, 0x02, 0x19, 0x6a, 0xe5, 0xb4, 0x96, 0x0c, 0x7a, 0xe4, 0xbd, 0x4a, 0x17, 0x2a, - 0x4b, 0xcf, 0x74, 0x48, 0x82, 0xf8, 0x56, 0x18, 0xd2, 0x4e, 0x2a, 0x90, 0xc9, 0xdb, 0xa2, 0x48, 0x30, 0x03, 0xf0, - 0x01, 0xde, 0x12, 0xc6, 0x64, 0xc6, 0xd3, 0xa7, 0x1b, 0x2f, 0x21, 0x12, 0xd8, 0xab, 0x91, 0x3d, 0x75, 0x15, 0xbf, - 0xe9, 0x2a, 0x8a, 0x91, 0xed, 0x22, 0xd6, 0x10, 0x7a, 0x6f, 0xb4, 0xf7, 0xf0, 0xe7, 0x88, 0xf9, 0x99, 0xcd, 0x25, - 0x4d, 0x2d, 0xe5, 0x72, 0x37, 0x5d, 0xd6, 0x06, 0x8d, 0x37, 0xee, 0xeb, 0x8c, 0xfb, 0x12, 0x7c, 0xb2, 0xfe, 0xb8, - 0xe2, 0x96, 0xde, 0xd0, 0xc6, 0x67, 0xa7, 0x70, 0x4f, 0xf3, 0x2e, 0xf3, 0xc9, 0x87, 0x89, 0x7a, 0xe5, 0xc6, 0x99, - 0x2f, 0xe2, 0xc8, 0x00, 0x5d, 0xde, 0x6f, 0x14, 0xc9, 0x2a, 0xd6, 0xe0, 0xa7, 0xef, 0x2e, 0xbe, 0xd3, 0xf8, 0xfe, - 0x27, 0x09, 0x22, 0x3e, 0x64, 0x28, 0xea, 0xc1, 0x80, 0xa2, 0x1e, 0x68, 0x3c, 0x8c, 0x08, 0xc4, 0x0e, 0xc8, 0x0f, - 0x08, 0x82, 0xc8, 0x80, 0x26, 0xb9, 0xea, 0x62, 0x15, 0x66, 0xc1, 0xd2, 0x4f, 0xb2, 0x03, 0xa8, 0x6a, 0x01, 0x92, - 0xd3, 0x37, 0xd9, 0x88, 0x93, 0x68, 0x56, 0xb8, 0xd8, 0xcb, 0x22, 0x21, 0x9b, 0x9d, 0x06, 0xa1, 0x14, 0xcd, 0x8a, - 0x0e, 0xfc, 0xf1, 0x98, 0x2d, 0xb3, 0x81, 0xee, 0x2f, 0x21, 0xfa, 0x05, 0xfa, 0xb3, 0x3e, 0x88, 0xc7, 0x19, 0xcb, - 0xac, 0x34, 0x4b, 0x98, 0xbf, 0xd0, 0xa5, 0x2b, 0xd7, 0x7a, 0x7b, 0xe9, 0x6a, 0xb4, 0x08, 0x32, 0xe9, 0x0b, 0x91, - 0x26, 0x08, 0x42, 0x52, 0x18, 0xe2, 0xe9, 0x30, 0xe7, 0x20, 0x3c, 0x8f, 0x67, 0x95, 0x1d, 0x55, 0x50, 0x2e, 0x67, - 0xe8, 0x69, 0x97, 0x47, 0x3c, 0x98, 0xa0, 0xcd, 0xd3, 0x35, 0xb7, 0x6b, 0x97, 0x2e, 0x1b, 0xf5, 0xd3, 0x13, 0xfe, - 0xbc, 0xd5, 0xd0, 0x15, 0x83, 0xde, 0x71, 0xc0, 0x97, 0xf0, 0x26, 0x8b, 0xf7, 0x03, 0x5e, 0x18, 0xae, 0x26, 0x6a, - 0x19, 0xfd, 0xbc, 0xd3, 0x58, 0x2e, 0x80, 0x10, 0x2a, 0x09, 0xd1, 0xe7, 0xee, 0xa9, 0x34, 0xb1, 0xc2, 0x51, 0x21, - 0xad, 0xf4, 0xf9, 0xf3, 0xcb, 0xe1, 0x7f, 0xfe, 0x0d, 0xce, 0xe8, 0xe7, 0xae, 0xb0, 0x33, 0xbf, 0x54, 0x4b, 0x71, - 0xea, 0xd3, 0x1c, 0xa2, 0x02, 0x05, 0x9b, 0x08, 0xc7, 0x2b, 0x62, 0x6b, 0xe5, 0xc3, 0x2b, 0xe1, 0x4c, 0x0b, 0x02, - 0x4e, 0x18, 0xc2, 0x1a, 0x7e, 0x08, 0xcb, 0x3b, 0x14, 0x4e, 0x18, 0xb4, 0xdf, 0xee, 0xbe, 0x3f, 0x06, 0x67, 0xcb, - 0xb5, 0x38, 0x10, 0xca, 0x00, 0x71, 0x0f, 0x9d, 0x9e, 0xf8, 0x1a, 0x12, 0x2d, 0x48, 0x7e, 0xa4, 0xbd, 0x03, 0x98, - 0xe6, 0x3c, 0x5e, 0x30, 0x3b, 0x88, 0x0f, 0x6e, 0xd9, 0xc8, 0xf2, 0x97, 0x01, 0xc9, 0xea, 0x91, 0xef, 0xa6, 0x11, - 0xe5, 0x27, 0x45, 0xe0, 0x44, 0x5f, 0xe7, 0x05, 0x28, 0xe3, 0x02, 0x50, 0xf0, 0xd3, 0x3f, 0x2d, 0xfb, 0x67, 0xb4, - 0x45, 0x84, 0x80, 0x32, 0x96, 0x3f, 0x23, 0x37, 0x8b, 0xc2, 0xa3, 0x62, 0xf1, 0x61, 0xc5, 0xd3, 0xa9, 0xea, 0x53, - 0xd1, 0x2e, 0xf7, 0x2f, 0xa1, 0x52, 0xec, 0xd9, 0x78, 0x49, 0x3d, 0xd5, 0xbb, 0x90, 0x3f, 0x21, 0x3a, 0x32, 0x77, - 0xbf, 0x09, 0xe7, 0xb9, 0xe6, 0x9b, 0x51, 0x82, 0xe4, 0x31, 0x15, 0xe2, 0x88, 0xa2, 0xea, 0x09, 0x7c, 0x03, 0x69, - 0xf2, 0x68, 0x30, 0x20, 0x3c, 0x56, 0x45, 0x67, 0x00, 0xa5, 0x86, 0x68, 0x09, 0x30, 0xd9, 0x0c, 0x2a, 0x5a, 0x64, - 0x23, 0x87, 0x95, 0xaa, 0xd3, 0xa9, 0x8f, 0xf1, 0xc0, 0x17, 0xfb, 0xab, 0xb4, 0x03, 0x61, 0x67, 0xf1, 0x85, 0x05, - 0x04, 0x2e, 0xda, 0xa9, 0xe0, 0x71, 0xed, 0xaf, 0x84, 0xb2, 0xad, 0xd0, 0xbf, 0x8f, 0x15, 0xdd, 0x05, 0xee, 0xc6, - 0xe0, 0x1c, 0x53, 0x2f, 0x84, 0xf9, 0x60, 0xed, 0x24, 0x49, 0x8f, 0xf3, 0xf5, 0xd3, 0xa4, 0xba, 0x88, 0xdf, 0x75, - 0x98, 0xd4, 0xb2, 0xe5, 0xc9, 0x20, 0x76, 0xcc, 0x8b, 0x83, 0x56, 0xca, 0xc4, 0x73, 0x9f, 0x9f, 0x1c, 0xc0, 0xfc, - 0xc0, 0xf5, 0x42, 0x89, 0x32, 0x0a, 0x0c, 0xf0, 0xef, 0xe0, 0xa7, 0xa4, 0x7f, 0xf1, 0x76, 0x22, 0x88, 0x3a, 0x7c, - 0x39, 0x4a, 0xe7, 0xaf, 0xa5, 0x22, 0x75, 0x62, 0xc5, 0x69, 0xa6, 0xf2, 0x76, 0x47, 0x68, 0xf8, 0x7d, 0x85, 0xe1, - 0x19, 0xf2, 0x7e, 0xc6, 0x84, 0x65, 0xf3, 0x79, 0xb6, 0xc1, 0xf8, 0x79, 0x53, 0x11, 0x22, 0x58, 0xb7, 0x14, 0x28, - 0xf6, 0xf1, 0xb6, 0x52, 0x05, 0x69, 0x24, 0x8b, 0x2d, 0xfd, 0x96, 0xfe, 0x18, 0x77, 0x7c, 0xad, 0x34, 0xa6, 0x42, - 0xb9, 0xf3, 0x6c, 0x00, 0x45, 0x05, 0xb3, 0xdd, 0x5f, 0x2e, 0xa9, 0xb0, 0xd1, 0x3f, 0x39, 0xa0, 0x77, 0xe7, 0x29, - 0xed, 0xb0, 0xd3, 0x13, 0xd0, 0xdf, 0xa4, 0x45, 0xf7, 0x97, 0x4b, 0xbe, 0xa4, 0xf4, 0x8b, 0x72, 0x0e, 0xe6, 0xd9, - 0x22, 0x3c, 0xfd, 0x3f, 0x1d, 0xdb, 0x6f, 0x83, 0x01, 0x5c, 0x03, 0x00}; + 0xdc, 0xb3, 0x37, 0xb7, 0x6d, 0x23, 0xff, 0x7f, 0x3f, 0x05, 0xc3, 0xe4, 0x52, 0x31, 0x21, 0x69, 0x92, 0xb2, 0x6c, + 0x45, 0xb2, 0xec, 0x6b, 0xf3, 0x98, 0x4b, 0xc7, 0x6d, 0x3a, 0x89, 0x9b, 0xb9, 0xab, 0xeb, 0xb1, 0x28, 0x09, 0x92, + 0x78, 0xa1, 0x48, 0x0d, 0x49, 0xf9, 0x51, 0x85, 0xf7, 0x59, 0xee, 0xb3, 0xdc, 0x27, 0xfb, 0xcd, 0xee, 0x02, 0x20, + 0xf8, 0xd0, 0xc3, 0x4d, 0x7a, 0xf7, 0x9b, 0x36, 0x89, 0x08, 0x02, 0x4b, 0x60, 0x01, 0x2c, 0x16, 0xfb, 0xf4, 0x67, + 0x5c, 0xf6, 0x62, 0xb6, 0xd8, 0x7e, 0x9f, 0xfb, 0xfc, 0x99, 0xd9, 0xb8, 0x24, 0x81, 0xe1, 0xb3, 0xb3, 0x78, 0x36, + 0x0b, 0x59, 0x4b, 0x17, 0xc9, 0x43, 0x74, 0x53, 0x7e, 0xe6, 0xec, 0x91, 0x23, 0x22, 0x76, 0x1a, 0xf9, 0xa6, 0xad, + 0x25, 0x46, 0xcc, 0x64, 0x48, 0x3b, 0xe2, 0x5c, 0x51, 0x36, 0x7b, 0x83, 0xea, 0x0d, 0x3e, 0x2f, 0xc5, 0xd6, 0xb5, + 0x26, 0xf1, 0x6a, 0x14, 0x32, 0x0b, 0x97, 0x3b, 0x7c, 0x72, 0x3d, 0x5a, 0x8d, 0x46, 0x90, 0xa5, 0xe5, 0x91, 0x63, + 0x42, 0xdc, 0x99, 0x38, 0xc5, 0xfb, 0x60, 0x6e, 0xf4, 0x61, 0x50, 0x76, 0x56, 0xed, 0x3e, 0xd8, 0x8a, 0x80, 0xa8, + 0x87, 0x3e, 0x90, 0xc1, 0xdd, 0xaf, 0x61, 0xd7, 0x0e, 0xf4, 0x0f, 0xb0, 0xfa, 0x52, 0xbd, 0xdf, 0xb4, 0xf5, 0x07, + 0x97, 0xfa, 0x07, 0xc4, 0x31, 0x66, 0x2f, 0x7e, 0x49, 0xab, 0x57, 0x37, 0x75, 0x52, 0x7a, 0xaf, 0x30, 0x8f, 0x01, + 0x08, 0x7d, 0x5f, 0x05, 0xfe, 0x2c, 0x8a, 0xd3, 0x2c, 0x18, 0xeb, 0x57, 0xfd, 0xb7, 0x41, 0xeb, 0x72, 0x91, 0xb5, + 0x8c, 0x2b, 0x73, 0x9c, 0xa9, 0x29, 0x50, 0x04, 0xc1, 0xc4, 0x0c, 0x28, 0x9b, 0x2a, 0xa9, 0x3b, 0x68, 0x6b, 0x45, + 0x41, 0x9a, 0xb1, 0xd2, 0x38, 0x1b, 0x40, 0xbd, 0x4a, 0x3e, 0x15, 0x4c, 0x0c, 0xa5, 0x63, 0x4b, 0xa3, 0x4f, 0x37, + 0x95, 0x97, 0xab, 0x35, 0x1e, 0xe5, 0x59, 0x71, 0x5a, 0x62, 0x0c, 0x60, 0xe1, 0x38, 0x43, 0xcf, 0x8f, 0x54, 0xa3, + 0xcf, 0xd2, 0xb9, 0x3b, 0xfc, 0xae, 0xcc, 0x17, 0xc0, 0xf9, 0x0d, 0x16, 0x17, 0x51, 0x9c, 0x69, 0x10, 0xd8, 0x06, + 0xbe, 0x38, 0xac, 0x1a, 0x89, 0x71, 0xa8, 0x2d, 0x23, 0xe7, 0xc4, 0xe0, 0x7b, 0x3c, 0xfc, 0x5a, 0x3c, 0xbc, 0x59, + 0x29, 0x82, 0x05, 0x5d, 0x16, 0x22, 0x98, 0xc0, 0x2c, 0x3e, 0x8f, 0x6f, 0xab, 0x7a, 0x90, 0x97, 0xc3, 0xdd, 0x67, + 0x6f, 0x4b, 0xb0, 0xc9, 0x22, 0xab, 0x5f, 0x8b, 0x27, 0x26, 0x15, 0x8c, 0x4e, 0x65, 0x4f, 0xa1, 0xe1, 0x87, 0xe0, + 0x61, 0x32, 0xb0, 0x13, 0xc3, 0xb3, 0x00, 0x48, 0x12, 0x3f, 0xa6, 0x87, 0xf9, 0xb5, 0x48, 0x9d, 0x2c, 0x12, 0x17, + 0x2b, 0x87, 0x33, 0x50, 0xd7, 0x68, 0xb9, 0xca, 0x30, 0xd4, 0x2e, 0x74, 0x80, 0xe5, 0xba, 0x86, 0xa1, 0x3b, 0x81, + 0x4a, 0x17, 0x6c, 0x62, 0xae, 0x6b, 0xc1, 0xa4, 0x5e, 0xc6, 0x99, 0x5e, 0x20, 0x5e, 0x48, 0xdf, 0x51, 0x50, 0x05, + 0x8f, 0x09, 0x1f, 0xc6, 0xd8, 0x2c, 0xe2, 0xd4, 0xb7, 0xc6, 0xa8, 0xd0, 0x69, 0xa0, 0x0c, 0x63, 0x82, 0xd3, 0x6f, + 0x85, 0x8d, 0x83, 0x85, 0xf0, 0x9b, 0xa5, 0x61, 0x0e, 0x9f, 0xac, 0xa3, 0xfc, 0xec, 0xc9, 0x3a, 0xcd, 0x07, 0x4f, + 0xd6, 0xbe, 0xb4, 0x15, 0xd0, 0x2f, 0x74, 0x32, 0x14, 0x18, 0x22, 0x1a, 0x86, 0xf9, 0x75, 0xe1, 0xb9, 0x53, 0x8c, + 0x17, 0x56, 0x19, 0x95, 0x6b, 0xa8, 0xba, 0x1f, 0x70, 0x05, 0xfd, 0x32, 0x09, 0x16, 0x7e, 0x72, 0x4f, 0xfa, 0x7c, + 0x53, 0x55, 0xfa, 0x1b, 0xba, 0x46, 0x84, 0x9e, 0x10, 0x40, 0x34, 0x5f, 0xd7, 0xfe, 0x2a, 0xcb, 0x18, 0x1f, 0xad, + 0x54, 0x6a, 0xc2, 0xb7, 0xae, 0xf5, 0xe7, 0xcc, 0x9e, 0xb0, 0xcc, 0x0f, 0x42, 0x6a, 0xd2, 0x17, 0xd9, 0xea, 0x6b, + 0xc3, 0x4b, 0xcb, 0xc3, 0x8b, 0xca, 0xeb, 0x07, 0x07, 0x43, 0x47, 0x00, 0xf5, 0x1b, 0x47, 0x86, 0x59, 0xac, 0x9a, + 0x67, 0x94, 0xde, 0xfd, 0x57, 0xa7, 0x83, 0xc1, 0x74, 0x44, 0x30, 0x1d, 0x2c, 0x1a, 0xc7, 0x13, 0xf6, 0xcb, 0xfb, + 0xb7, 0x32, 0x6d, 0x16, 0x48, 0x80, 0x86, 0x7c, 0x61, 0xa6, 0xc8, 0x3f, 0x24, 0xc8, 0x3b, 0x50, 0x82, 0x2b, 0x4d, + 0x2e, 0xa1, 0x24, 0xd7, 0xb5, 0x33, 0xea, 0x3b, 0x9b, 0x50, 0xaf, 0x07, 0x31, 0xb6, 0x4a, 0xf2, 0x93, 0x03, 0xaa, + 0x4d, 0xa7, 0x1d, 0x55, 0x02, 0x34, 0x24, 0x30, 0xc2, 0x02, 0x0b, 0x90, 0xe1, 0x73, 0xe0, 0x16, 0x17, 0x0a, 0x7b, + 0x81, 0x72, 0x76, 0xf7, 0xac, 0xcc, 0xaa, 0x60, 0x2b, 0xfd, 0xf4, 0x04, 0x73, 0x76, 0xc1, 0x79, 0x0d, 0x51, 0x3e, + 0x4e, 0x0e, 0xe8, 0x51, 0xab, 0xec, 0x88, 0x02, 0x88, 0xb8, 0xda, 0xf5, 0x38, 0x80, 0x07, 0x6d, 0x15, 0x48, 0x11, + 0x0f, 0xa5, 0x7e, 0xae, 0x6b, 0x0b, 0xce, 0x1a, 0xf1, 0x70, 0x42, 0x10, 0x6b, 0xc0, 0x81, 0xbd, 0xab, 0x6b, 0x0b, + 0xff, 0x0e, 0x47, 0x2e, 0xde, 0xf8, 0x77, 0x2d, 0x97, 0xbf, 0x2a, 0xf6, 0x5a, 0x5a, 0xde, 0x6b, 0x63, 0x3e, 0xb9, + 0xe0, 0x48, 0x20, 0x6f, 0xd6, 0x73, 0x54, 0xd0, 0x36, 0x4c, 0xee, 0x5c, 0x4c, 0xee, 0x64, 0xc3, 0xe4, 0x4e, 0xb6, + 0x4c, 0x6e, 0xc8, 0x27, 0x52, 0x93, 0xa8, 0x4b, 0xd0, 0x39, 0x4c, 0x22, 0x8f, 0x33, 0x1a, 0x3d, 0xbe, 0xcf, 0x10, + 0x4f, 0x56, 0x1a, 0x82, 0x71, 0xd4, 0x06, 0x5c, 0x35, 0xe1, 0x45, 0x41, 0x44, 0x7d, 0xe0, 0x72, 0xd7, 0x89, 0x71, + 0x43, 0x0e, 0xce, 0x56, 0x58, 0x1d, 0x2f, 0xac, 0x52, 0xca, 0x2f, 0xde, 0x9a, 0x6f, 0x18, 0xe9, 0x7c, 0xcb, 0x48, + 0xc7, 0xa5, 0xad, 0xcb, 0x87, 0x4d, 0x9b, 0x50, 0x1d, 0x14, 0xac, 0x41, 0x30, 0x18, 0xc5, 0x25, 0x53, 0x5e, 0x87, + 0x9b, 0x69, 0xac, 0xb2, 0xa2, 0x96, 0x7e, 0x9a, 0xde, 0xc6, 0x09, 0x68, 0x5c, 0x00, 0xcc, 0xc3, 0x96, 0xd4, 0x22, + 0x88, 0x78, 0x30, 0x97, 0x8d, 0x8b, 0xa9, 0x78, 0xaf, 0x2e, 0x29, 0xaf, 0xd3, 0xa1, 0x1a, 0x4b, 0x3f, 0xcb, 0x58, + 0x82, 0x48, 0xf7, 0x21, 0xea, 0xf7, 0xff, 0x93, 0x65, 0xd6, 0x40, 0x43, 0x42, 0x85, 0xaa, 0x23, 0x85, 0x5e, 0x02, + 0x6f, 0x95, 0x88, 0x83, 0x58, 0x09, 0x0c, 0x97, 0x48, 0xc4, 0xff, 0x84, 0xdb, 0xb5, 0x95, 0x28, 0xae, 0x4b, 0xee, + 0x91, 0x61, 0x2f, 0xfd, 0xc9, 0x07, 0x50, 0xec, 0xb5, 0x3c, 0x13, 0x8c, 0x74, 0xd5, 0x30, 0x70, 0x09, 0x31, 0x7b, + 0xe3, 0x82, 0x48, 0x22, 0x95, 0xe4, 0x26, 0x50, 0xe0, 0x3d, 0xe9, 0x5b, 0xd3, 0xab, 0xb5, 0x97, 0x1f, 0xcc, 0x02, + 0xa3, 0x46, 0x35, 0x81, 0xb4, 0x85, 0x83, 0x53, 0x79, 0xe7, 0x0a, 0x4d, 0xf7, 0xc8, 0x00, 0xc9, 0xef, 0x25, 0xe4, + 0x33, 0x75, 0xc4, 0x85, 0x76, 0x98, 0xc0, 0xa9, 0x75, 0xe9, 0x5c, 0xe5, 0x4f, 0x67, 0xf8, 0xcb, 0xbd, 0xca, 0x9f, + 0x8e, 0xf0, 0x97, 0x77, 0x85, 0x99, 0xeb, 0x1a, 0x2e, 0xf2, 0xca, 0x98, 0xf5, 0xd3, 0xd2, 0x7a, 0x22, 0xfb, 0xb3, + 0x07, 0x2c, 0x1b, 0x3e, 0xc1, 0x8f, 0x9f, 0xac, 0x53, 0xf0, 0xb8, 0x54, 0xc7, 0x10, 0xd9, 0x89, 0x91, 0x37, 0x96, + 0xcf, 0x36, 0x94, 0x8f, 0x8c, 0xff, 0xf2, 0xc1, 0x8f, 0xab, 0x24, 0x2e, 0xce, 0x94, 0xb2, 0x18, 0xe2, 0x7a, 0x14, + 0x44, 0x7e, 0x72, 0x7f, 0x4d, 0xd7, 0x8b, 0x96, 0xe0, 0xdd, 0xa5, 0x78, 0x85, 0xd8, 0xcb, 0xb2, 0xba, 0x2b, 0x53, + 0x04, 0xbc, 0xf7, 0xfc, 0xa0, 0x1f, 0xfc, 0x3d, 0x51, 0xd8, 0xb6, 0xd2, 0x05, 0x94, 0x4f, 0x48, 0xe9, 0x43, 0xd7, + 0x4f, 0xd6, 0x2d, 0x56, 0x07, 0x53, 0x19, 0x6d, 0x85, 0x2f, 0x84, 0xe9, 0xc1, 0xcb, 0xec, 0x62, 0x12, 0xf4, 0x50, + 0x9f, 0x35, 0x8a, 0xef, 0xac, 0x27, 0xeb, 0xec, 0x4c, 0x5f, 0xf8, 0xc9, 0x27, 0x36, 0xb1, 0xc6, 0x41, 0x32, 0x0e, + 0x99, 0xde, 0xd3, 0x47, 0xa1, 0x1f, 0x7d, 0xe2, 0x8f, 0x56, 0xbc, 0xca, 0x50, 0x43, 0xbd, 0xf3, 0xee, 0x2b, 0x70, + 0x42, 0x22, 0x3b, 0x64, 0x56, 0x1b, 0xb0, 0xa0, 0xbd, 0x94, 0x02, 0xaf, 0x82, 0x51, 0x2c, 0x6a, 0x99, 0x60, 0x60, + 0x09, 0x4a, 0x73, 0xf0, 0x58, 0x35, 0x75, 0x9c, 0x2f, 0xdd, 0x54, 0x87, 0x4a, 0xc2, 0x4a, 0x99, 0x72, 0xf1, 0x1a, + 0x21, 0xfc, 0xf1, 0xcf, 0x51, 0x32, 0xec, 0xfd, 0x3f, 0x27, 0xa1, 0x7c, 0xd9, 0x08, 0xa1, 0xd4, 0x22, 0x4f, 0x89, + 0x07, 0x7c, 0x9c, 0x33, 0x98, 0x9b, 0x3f, 0xad, 0x36, 0xf6, 0xd3, 0x74, 0xb5, 0x60, 0x13, 0xd2, 0x0c, 0x9e, 0x15, + 0x9d, 0x2a, 0xdf, 0x2c, 0xd4, 0x8e, 0xfd, 0xb6, 0xf2, 0x8e, 0x0f, 0x5f, 0x82, 0xc5, 0x02, 0x30, 0x94, 0xf1, 0x74, + 0xaa, 0x17, 0x77, 0xfc, 0x1d, 0xcd, 0xdc, 0xc3, 0xdf, 0x56, 0x6f, 0x5e, 0x3b, 0x6f, 0x64, 0xe3, 0x08, 0x18, 0x63, + 0xa1, 0x7e, 0xe5, 0x7c, 0xb1, 0xd2, 0x5f, 0x31, 0xa2, 0xa9, 0x1f, 0x6d, 0x1e, 0xce, 0x65, 0x69, 0x89, 0x2f, 0x19, + 0x9b, 0x00, 0xc3, 0x6d, 0xd6, 0x4a, 0xaf, 0x43, 0x76, 0xc3, 0xa4, 0x6a, 0xb7, 0xfe, 0xb1, 0x86, 0x16, 0x18, 0x7b, + 0x8e, 0xab, 0x8c, 0x39, 0x57, 0xa7, 0x0c, 0x69, 0x88, 0x63, 0xe0, 0x23, 0x57, 0xb7, 0x58, 0x65, 0x4b, 0x0d, 0x4d, + 0x5d, 0xe9, 0xc0, 0xc6, 0x9e, 0x9d, 0x6d, 0x28, 0xef, 0x61, 0xe2, 0xe9, 0xe6, 0xbe, 0x99, 0xae, 0xd1, 0x83, 0x58, + 0xdd, 0x1c, 0x4f, 0x21, 0xec, 0xbc, 0x56, 0x21, 0x0e, 0xd9, 0x84, 0xb1, 0x26, 0x21, 0x99, 0x4e, 0xd2, 0x17, 0x61, + 0xed, 0x88, 0x66, 0xbf, 0x42, 0x0e, 0xd5, 0x38, 0x37, 0x5a, 0x79, 0xe4, 0x23, 0x4c, 0xe8, 0x1a, 0xb1, 0x34, 0xdd, + 0x88, 0x30, 0x39, 0xe9, 0xa6, 0x5e, 0xd4, 0x2e, 0xe3, 0xa3, 0x28, 0x37, 0x1d, 0x13, 0x58, 0x02, 0x1c, 0x60, 0xf5, + 0x5b, 0x78, 0xbc, 0x5c, 0x2f, 0xb8, 0xbd, 0x4a, 0x32, 0x1b, 0xe9, 0xdc, 0x96, 0x60, 0xd3, 0xfb, 0x5b, 0x9d, 0x77, + 0xaa, 0x74, 0x4c, 0x37, 0x76, 0xad, 0x55, 0x22, 0xbd, 0x35, 0x71, 0x11, 0x02, 0x10, 0x7d, 0xaa, 0xd0, 0x57, 0x36, + 0x9d, 0xb2, 0x71, 0x96, 0x1a, 0x42, 0x78, 0x24, 0xa3, 0xc7, 0x82, 0xd7, 0xd0, 0xa3, 0x81, 0xfe, 0x13, 0xf8, 0xd0, + 0x8b, 0x20, 0x4b, 0xbc, 0x43, 0xe2, 0xce, 0xd4, 0x8c, 0x26, 0x82, 0x58, 0x46, 0x11, 0xff, 0x0a, 0x24, 0x07, 0x6f, + 0x28, 0xc7, 0xae, 0xf1, 0xf3, 0xa7, 0x58, 0x17, 0xb1, 0xb4, 0x6a, 0xd9, 0x4e, 0x8a, 0xb6, 0x6d, 0xdf, 0xb5, 0xfb, + 0xa6, 0xe3, 0x3a, 0xb9, 0x6e, 0x82, 0xef, 0xd6, 0xa7, 0x7d, 0x37, 0x3d, 0xb6, 0x6a, 0x43, 0xab, 0x55, 0xf4, 0x90, + 0x76, 0x9e, 0xfb, 0xc2, 0xd5, 0x4d, 0x32, 0x99, 0x53, 0x68, 0xdb, 0x38, 0xbe, 0x61, 0xc9, 0x17, 0x0f, 0xa5, 0x0c, + 0x7c, 0xbf, 0xfe, 0x1c, 0xb9, 0x0e, 0x10, 0xe1, 0x2c, 0x5e, 0x3e, 0x60, 0x08, 0x6d, 0xdd, 0xd4, 0xc7, 0x61, 0x9c, + 0x32, 0x75, 0x0c, 0x24, 0x04, 0xf9, 0xc2, 0x41, 0xfc, 0xfc, 0xfe, 0xf5, 0x87, 0x0f, 0xba, 0x89, 0x99, 0x40, 0x53, + 0x15, 0x3a, 0x5f, 0x50, 0x3b, 0xa8, 0x7f, 0xe3, 0xba, 0xa3, 0x13, 0x86, 0x2e, 0xb5, 0xe5, 0x35, 0x47, 0x65, 0xb5, + 0x25, 0xc7, 0x4f, 0x1e, 0xfe, 0x65, 0xba, 0x89, 0xee, 0x35, 0xae, 0x06, 0xda, 0xb0, 0xfd, 0x78, 0x2b, 0x95, 0x2c, + 0x82, 0xe8, 0xba, 0xa1, 0xd4, 0xbf, 0x6b, 0x28, 0x85, 0xab, 0x5c, 0x8d, 0x56, 0xad, 0xe2, 0x85, 0xc2, 0x1a, 0x40, + 0x22, 0xe7, 0x5d, 0xe8, 0x52, 0xee, 0x53, 0x5f, 0xd0, 0x69, 0x1e, 0xc9, 0xbd, 0xda, 0xeb, 0x86, 0x62, 0x7e, 0x09, + 0x92, 0xb8, 0x1d, 0x87, 0x60, 0xf0, 0xc7, 0x54, 0xad, 0x5c, 0x99, 0x6d, 0x94, 0xe6, 0xba, 0x0a, 0x10, 0x62, 0x6f, + 0xaf, 0x33, 0xb6, 0x58, 0xb2, 0xc4, 0xcf, 0x56, 0x09, 0xbb, 0x0e, 0xe3, 0xdb, 0x47, 0x85, 0x39, 0xfd, 0x8e, 0xca, + 0xf3, 0x60, 0x36, 0x97, 0xb5, 0xcf, 0x5a, 0x6c, 0x20, 0x27, 0x70, 0xeb, 0x07, 0xf2, 0xff, 0xfc, 0xdb, 0xb6, 0xff, + 0xf3, 0xef, 0x9d, 0x55, 0x01, 0x7c, 0x3e, 0x34, 0xb3, 0xc1, 0x1e, 0xeb, 0xa2, 0xf9, 0x4b, 0x65, 0x9c, 0x37, 0xd7, + 0xa9, 0x4d, 0x02, 0xbc, 0xaf, 0x4d, 0x41, 0xad, 0xb0, 0xbc, 0x6e, 0x1e, 0xd4, 0x31, 0x18, 0xd7, 0xce, 0x9e, 0x41, + 0xa5, 0x2f, 0xea, 0xda, 0xd0, 0xe8, 0xed, 0x35, 0x23, 0x7f, 0x1c, 0xc3, 0xbb, 0xc6, 0xf0, 0x85, 0xdd, 0xe7, 0x72, + 0xc9, 0x97, 0xc3, 0xa1, 0xcc, 0x2d, 0xa7, 0x36, 0x05, 0x13, 0xff, 0xb3, 0x5a, 0x09, 0x3f, 0x3c, 0x7b, 0x8e, 0x41, + 0xbe, 0xf7, 0x83, 0x97, 0x43, 0x34, 0x46, 0x3b, 0x19, 0x25, 0x05, 0xb3, 0xb2, 0x91, 0xb4, 0x91, 0x31, 0x79, 0x0d, + 0x68, 0x8d, 0xae, 0x41, 0x29, 0x26, 0x1c, 0xcb, 0x87, 0x86, 0xf9, 0x72, 0xc8, 0x05, 0x4b, 0xdc, 0xfe, 0xb5, 0x57, + 0x5d, 0xda, 0x5c, 0x2c, 0x5b, 0x42, 0xba, 0xa9, 0x91, 0xfe, 0x07, 0x2b, 0xb3, 0x42, 0x8e, 0x87, 0x02, 0x7e, 0x90, + 0x28, 0x0c, 0x73, 0xcc, 0x77, 0xf2, 0x6e, 0x93, 0x8d, 0xd8, 0xcf, 0xbb, 0x6d, 0xc4, 0x2e, 0xf6, 0xb2, 0x11, 0xfb, + 0xf9, 0xab, 0xdb, 0x88, 0xbd, 0x53, 0x6d, 0xc4, 0x60, 0x12, 0x5f, 0xb3, 0xbd, 0x0c, 0xb7, 0x84, 0xd5, 0x46, 0x7c, + 0x9b, 0x0e, 0x5c, 0xce, 0xd2, 0xa6, 0xe3, 0x39, 0x03, 0x19, 0x01, 0x9f, 0x95, 0x30, 0x9e, 0x81, 0x11, 0xd7, 0x9f, + 0x6f, 0x6e, 0x15, 0xc6, 0x33, 0xd5, 0xd8, 0x2a, 0xe2, 0x11, 0x5f, 0x8b, 0x28, 0x4e, 0x64, 0xe0, 0xe4, 0x98, 0x22, + 0xe6, 0x93, 0x75, 0x68, 0x28, 0x59, 0xad, 0xa5, 0xf5, 0x9a, 0x27, 0x4c, 0xa0, 0x7a, 0x68, 0x3d, 0x25, 0x1b, 0x7a, + 0xcf, 0x45, 0x6c, 0x0b, 0x15, 0x82, 0xb4, 0x12, 0xa6, 0x38, 0x11, 0x6b, 0xfd, 0xb7, 0x3b, 0xf7, 0xfb, 0x4b, 0xb7, + 0xdf, 0x76, 0xc1, 0x39, 0x1b, 0x6e, 0x98, 0x58, 0xe0, 0xf4, 0xdb, 0x6d, 0x28, 0xb8, 0x55, 0x0a, 0x3c, 0x28, 0x08, + 0x94, 0x82, 0x0e, 0x14, 0x8c, 0x95, 0x82, 0x23, 0x28, 0x98, 0x28, 0x05, 0xc7, 0x50, 0x70, 0xa3, 0xe7, 0x97, 0x91, + 0xec, 0xee, 0xb1, 0x71, 0x65, 0xd2, 0xa5, 0x42, 0x94, 0x1d, 0x9b, 0x2e, 0x58, 0x4d, 0xf9, 0xb3, 0x5e, 0x6c, 0x92, + 0x74, 0xb1, 0x97, 0x98, 0xb7, 0x73, 0x46, 0x81, 0xa2, 0x5f, 0xe1, 0x99, 0x63, 0x67, 0x31, 0xd8, 0x4d, 0x8b, 0x00, + 0x0c, 0x02, 0x0f, 0x9a, 0x6e, 0x80, 0xc0, 0xa8, 0x2f, 0x67, 0x4e, 0x04, 0xb1, 0x50, 0xe6, 0xb2, 0x78, 0x47, 0x9f, + 0xb3, 0xe4, 0x12, 0x28, 0x2c, 0x4e, 0x5a, 0xaa, 0x54, 0xf2, 0x6b, 0xd8, 0x1d, 0xbc, 0x62, 0xa3, 0xd5, 0x4c, 0x3b, + 0x8f, 0x67, 0x3b, 0x4d, 0x08, 0xd4, 0x57, 0xd0, 0x4b, 0x9d, 0xd4, 0x2f, 0x96, 0x58, 0x96, 0xfc, 0x5b, 0xf4, 0x98, + 0x97, 0xeb, 0x67, 0xd0, 0x37, 0x2d, 0x23, 0x03, 0x16, 0xf8, 0x0e, 0xe0, 0x48, 0xd1, 0xe1, 0x9f, 0x03, 0x9e, 0x95, + 0xe7, 0x0b, 0x5f, 0xe9, 0xcf, 0xe9, 0x8f, 0x2c, 0x4d, 0xfd, 0x99, 0xa8, 0x5f, 0xef, 0x27, 0x18, 0xed, 0xc8, 0xfb, + 0x17, 0x22, 0x10, 0x24, 0x79, 0x41, 0xcd, 0x36, 0x23, 0x89, 0x6f, 0x35, 0xb0, 0xfe, 0x81, 0x05, 0x55, 0xd8, 0x29, + 0x04, 0x36, 0x4c, 0x61, 0xd9, 0xa2, 0x00, 0x36, 0xff, 0x0d, 0x0b, 0xab, 0x85, 0x99, 0x3f, 0xab, 0x16, 0xd1, 0x3a, + 0xc8, 0xd5, 0xbe, 0x49, 0x85, 0x7e, 0xa9, 0xf0, 0x4b, 0x34, 0xd4, 0x61, 0x3c, 0xfb, 0x53, 0xd5, 0xd3, 0x5b, 0xcc, + 0x0a, 0x3e, 0x44, 0x66, 0x90, 0x0d, 0x6d, 0xc4, 0xb1, 0x66, 0x03, 0x0a, 0x7b, 0x51, 0x36, 0xb7, 0xd0, 0xb5, 0xac, + 0xe5, 0x45, 0x86, 0x69, 0xe3, 0xdc, 0xae, 0xab, 0x0e, 0xb5, 0xbd, 0x64, 0x36, 0xf2, 0x5b, 0xae, 0x77, 0x6c, 0x8a, + 0x3f, 0xb6, 0xd3, 0x31, 0x72, 0x84, 0xa0, 0x4d, 0x82, 0x9b, 0xf5, 0x34, 0x8e, 0x32, 0x6b, 0xea, 0x2f, 0x82, 0xf0, + 0xbe, 0xb7, 0x88, 0xa3, 0x38, 0x5d, 0xfa, 0x63, 0xd6, 0x2f, 0x2e, 0xd4, 0x7d, 0x0c, 0xd5, 0xc0, 0xbd, 0x05, 0x5d, + 0xdb, 0x4b, 0xd8, 0x82, 0x5a, 0xcb, 0x48, 0x0c, 0xd3, 0x90, 0xdd, 0xe5, 0xfc, 0xf3, 0xa5, 0xca, 0x54, 0x15, 0x97, + 0x1c, 0xb5, 0x00, 0x8e, 0x94, 0x87, 0x79, 0x80, 0xe0, 0x46, 0xfd, 0xa5, 0x3f, 0xc1, 0xc8, 0x84, 0xb6, 0xd7, 0x49, + 0xd8, 0x42, 0xb3, 0x3b, 0x1b, 0x81, 0x27, 0xf1, 0xed, 0x29, 0xf4, 0x16, 0x1b, 0x5b, 0x29, 0x0b, 0xa7, 0xf8, 0xc6, + 0x42, 0xcf, 0x12, 0x01, 0xc7, 0xc2, 0x8b, 0x38, 0x40, 0x63, 0x8b, 0x3e, 0xbc, 0xee, 0x79, 0x9a, 0xd3, 0x5f, 0x04, + 0x91, 0x45, 0xc3, 0x39, 0x76, 0x96, 0x0a, 0x2c, 0x15, 0x7f, 0xc6, 0x1a, 0xab, 0xbb, 0x9a, 0xd3, 0x87, 0xcb, 0xda, + 0x34, 0x8c, 0x6f, 0x7b, 0xf3, 0x60, 0x32, 0x61, 0x51, 0x1f, 0xfb, 0x2c, 0x0b, 0x59, 0x18, 0x06, 0xcb, 0x34, 0x48, + 0xfb, 0x0b, 0xff, 0x8e, 0x43, 0x3d, 0xdc, 0x04, 0xb5, 0xcd, 0xa1, 0xb6, 0xf7, 0x86, 0xaa, 0x80, 0x01, 0x2f, 0x16, + 0x82, 0xc3, 0xbb, 0xd6, 0xd1, 0x9c, 0xca, 0x38, 0xf7, 0x86, 0xba, 0x4c, 0xd8, 0x7a, 0xe1, 0x27, 0xb3, 0x20, 0xea, + 0x39, 0xb9, 0x7d, 0xb3, 0xa6, 0x85, 0xf1, 0xb8, 0xdb, 0xed, 0xe6, 0xf6, 0x44, 0x3c, 0x39, 0x93, 0x49, 0x6e, 0x8f, + 0xc5, 0xd3, 0x74, 0xea, 0x38, 0xd3, 0x69, 0x6e, 0x07, 0xa2, 0xa0, 0xed, 0x8d, 0x27, 0x6d, 0x2f, 0xb7, 0x6f, 0x95, + 0x1a, 0xb9, 0xcd, 0xf8, 0x53, 0xc2, 0x26, 0x7d, 0x5c, 0x48, 0x64, 0x56, 0xda, 0x3b, 0x76, 0x9c, 0x1c, 0x29, 0xc0, + 0x65, 0x89, 0x36, 0xa1, 0xac, 0xe7, 0x6a, 0xbd, 0x77, 0x4d, 0xad, 0xf8, 0xdc, 0x78, 0xdc, 0x58, 0x6f, 0xe2, 0x27, + 0x9f, 0xae, 0x34, 0x65, 0x14, 0xbe, 0x4f, 0xd5, 0xd6, 0x02, 0x0d, 0xd6, 0x5d, 0x0f, 0x42, 0x76, 0xf5, 0x47, 0x71, + 0x02, 0x7b, 0x36, 0xf1, 0x27, 0xc1, 0x2a, 0xed, 0xb9, 0xde, 0xf2, 0x4e, 0x14, 0xf1, 0xb5, 0x5e, 0x14, 0xe0, 0xde, + 0xeb, 0xa5, 0x71, 0x18, 0x4c, 0x44, 0xd1, 0xa6, 0xbd, 0xe4, 0x7a, 0x46, 0x1f, 0x1d, 0xd6, 0x03, 0x0c, 0xbb, 0xe0, + 0x87, 0xa1, 0x66, 0xb7, 0x53, 0x8d, 0xf9, 0x29, 0xca, 0x97, 0x35, 0x27, 0x25, 0xbc, 0xa0, 0x73, 0xba, 0x7b, 0xb8, + 0xbc, 0x93, 0x6b, 0xde, 0x3d, 0x5a, 0xde, 0xe5, 0x7f, 0x5d, 0xb0, 0x49, 0xe0, 0x6b, 0xad, 0x62, 0x35, 0xb9, 0x0e, + 0xc8, 0xa0, 0x8d, 0xf5, 0x86, 0x65, 0x2a, 0xb6, 0x05, 0x84, 0x36, 0x7c, 0x14, 0x2c, 0x96, 0x71, 0x92, 0xf9, 0x51, + 0x96, 0xe7, 0xc3, 0xab, 0x3c, 0xef, 0x5f, 0x04, 0xad, 0xcb, 0x7f, 0xb4, 0xe8, 0x9c, 0x26, 0x9d, 0x4d, 0x6e, 0x5c, + 0x99, 0xaf, 0x99, 0x6a, 0x33, 0x02, 0xc7, 0x18, 0xda, 0x8b, 0xa8, 0x95, 0xe9, 0x94, 0xac, 0x57, 0x26, 0x24, 0xcb, + 0xea, 0x64, 0x83, 0x52, 0xae, 0x82, 0x27, 0x10, 0x54, 0x78, 0xcd, 0x06, 0x17, 0x8a, 0xfd, 0x09, 0x30, 0x2b, 0x58, + 0x99, 0xfc, 0x0a, 0x9e, 0x6c, 0xe2, 0x19, 0xbf, 0xdb, 0xcd, 0x33, 0xfe, 0x9a, 0xed, 0xc3, 0x33, 0x7e, 0xf7, 0xd5, + 0x79, 0xc6, 0x27, 0x75, 0xbf, 0x82, 0xb7, 0xf1, 0x40, 0x97, 0x1a, 0x06, 0x38, 0x9a, 0x12, 0x8a, 0xd8, 0xf3, 0xf6, + 0x0f, 0xbb, 0x01, 0x08, 0x68, 0x94, 0x83, 0x8e, 0x4e, 0x6e, 0x90, 0xc7, 0xbe, 0x8b, 0x06, 0x7f, 0x4f, 0xd4, 0xe7, + 0xe9, 0x74, 0xf0, 0x2a, 0x56, 0x0a, 0xe4, 0x13, 0x37, 0xbe, 0x28, 0x45, 0x57, 0xa0, 0x37, 0xc2, 0x0a, 0x13, 0xf3, + 0x4f, 0x80, 0x73, 0x36, 0x59, 0x1d, 0x4f, 0xa4, 0xf5, 0x59, 0xbf, 0xdc, 0x85, 0x96, 0x34, 0xf9, 0x14, 0x2e, 0x38, + 0x35, 0x51, 0xe2, 0x8c, 0x65, 0xdc, 0x67, 0xf6, 0xfb, 0xfb, 0xb7, 0x93, 0xd6, 0xdb, 0xd8, 0xc8, 0x83, 0xf4, 0x5d, + 0xd5, 0x01, 0x86, 0xeb, 0x7e, 0x06, 0xea, 0x70, 0x72, 0x6e, 0x41, 0xa6, 0x26, 0x98, 0x86, 0xd7, 0xd4, 0xfc, 0xac, + 0x34, 0xd2, 0x9e, 0xda, 0x90, 0x27, 0xba, 0xaa, 0x1d, 0xc6, 0xdc, 0xfb, 0x60, 0xcd, 0x39, 0x40, 0xcc, 0xdd, 0x85, + 0x7e, 0xc3, 0x13, 0x6a, 0x1e, 0x4c, 0xf2, 0xdc, 0xe8, 0x0b, 0x44, 0x28, 0x07, 0x2d, 0xdb, 0xc5, 0xc4, 0xa5, 0xb7, + 0xd2, 0xa6, 0x81, 0x6b, 0x08, 0x49, 0xfd, 0xf7, 0x16, 0x14, 0xea, 0x5c, 0x59, 0xc8, 0x71, 0xa6, 0x6b, 0x84, 0x3e, + 0x32, 0xb4, 0x50, 0x06, 0x04, 0x1a, 0x60, 0x89, 0x7f, 0xf1, 0x4a, 0x14, 0xd4, 0x6d, 0x38, 0x09, 0x39, 0x68, 0x11, + 0x00, 0x5e, 0xfe, 0x42, 0xae, 0x4d, 0x64, 0x87, 0xd7, 0xc1, 0x87, 0x5c, 0x97, 0xbc, 0x1f, 0x2e, 0xbf, 0xd3, 0x93, + 0x03, 0x68, 0x70, 0x5a, 0x31, 0x1c, 0xd8, 0x61, 0xa1, 0x08, 0xac, 0x44, 0x7a, 0x6b, 0xda, 0xe9, 0xad, 0xf6, 0x6c, + 0x2d, 0x22, 0x64, 0x64, 0xfe, 0xd2, 0x82, 0x2b, 0x3e, 0xd2, 0x5e, 0x4e, 0xf1, 0x94, 0x60, 0x1c, 0xfd, 0x55, 0x0a, + 0xb4, 0x11, 0x2f, 0xaa, 0x48, 0x7f, 0xfa, 0xe3, 0x55, 0x92, 0xc6, 0x49, 0x6f, 0x19, 0x07, 0x51, 0xc6, 0x92, 0x1c, + 0x51, 0x75, 0x89, 0xf8, 0x11, 0xe8, 0xb9, 0x5a, 0xc7, 0x4b, 0x7f, 0x1c, 0x64, 0xf7, 0x3d, 0x87, 0xb3, 0x14, 0x4e, + 0x9f, 0x73, 0x07, 0x4e, 0x63, 0xfd, 0x1e, 0xc7, 0xe6, 0x73, 0x64, 0xfc, 0x92, 0x3a, 0x3b, 0xa3, 0x2e, 0xf3, 0xbe, + 0xf2, 0x96, 0x62, 0x84, 0x00, 0xfb, 0xe1, 0x27, 0xd6, 0x0c, 0xa8, 0x3c, 0x4c, 0xb5, 0x33, 0x61, 0x33, 0x13, 0xa9, + 0x36, 0xc8, 0xe5, 0xc5, 0x1f, 0xbb, 0x63, 0x68, 0x4e, 0x73, 0x31, 0x70, 0x3c, 0xc6, 0x3e, 0x3d, 0xeb, 0xf9, 0x90, + 0x51, 0xcb, 0xdc, 0xa7, 0xe6, 0x88, 0x4d, 0xe3, 0x84, 0x51, 0x3c, 0x59, 0xb7, 0xbb, 0xbc, 0xdb, 0x1f, 0xfc, 0xf6, + 0xe1, 0x37, 0xc3, 0x89, 0xe2, 0xac, 0x25, 0x80, 0x19, 0x3b, 0xa0, 0xd5, 0xcf, 0x33, 0x60, 0x0d, 0x09, 0xf3, 0x63, + 0x0a, 0xdd, 0xd5, 0xd3, 0xf5, 0x7e, 0x63, 0xd8, 0xae, 0x65, 0xcc, 0xcf, 0xbc, 0x84, 0x85, 0x7e, 0x16, 0xdc, 0x08, + 0x9e, 0xb1, 0x7d, 0xb4, 0xbc, 0x13, 0x73, 0x8c, 0x07, 0xde, 0x03, 0x26, 0xa9, 0xd2, 0x15, 0x31, 0x49, 0xd5, 0x62, + 0x9c, 0xa4, 0x7e, 0x6d, 0x34, 0x22, 0x92, 0x45, 0xe5, 0xa4, 0xef, 0x2c, 0xef, 0xd4, 0x23, 0xba, 0x68, 0x26, 0x4f, + 0xea, 0x6a, 0x08, 0xb2, 0x45, 0x30, 0x99, 0x84, 0x2c, 0x2f, 0x4d, 0x74, 0x79, 0x2e, 0x15, 0xe4, 0x48, 0x3c, 0xf8, + 0xa3, 0x34, 0x0e, 0x57, 0x19, 0x6b, 0x46, 0x17, 0x21, 0xc7, 0x73, 0x0a, 0xe4, 0xe0, 0xef, 0x72, 0x5f, 0x3b, 0xc0, + 0x6e, 0xc3, 0x32, 0x71, 0xfa, 0x10, 0x71, 0xd8, 0x6a, 0x97, 0xbb, 0x0e, 0xaf, 0x64, 0xa7, 0xcd, 0x86, 0x81, 0x98, + 0x70, 0x2c, 0x11, 0xf5, 0xd6, 0x6c, 0x97, 0x97, 0xc9, 0xa8, 0xab, 0xb2, 0x28, 0x2f, 0x0f, 0xe6, 0xcf, 0xd9, 0x63, + 0x2f, 0x9a, 0xf7, 0xd8, 0x0b, 0xb1, 0xc7, 0xb6, 0xaf, 0xcc, 0xc7, 0x53, 0x17, 0xfe, 0xeb, 0x17, 0x03, 0xea, 0x39, + 0x5a, 0x7b, 0x79, 0xa7, 0xb9, 0xcb, 0x3b, 0xcd, 0xf2, 0x96, 0x77, 0x1a, 0x82, 0x46, 0x7b, 0x10, 0xd3, 0xf6, 0x0c, + 0xd3, 0xd1, 0xa0, 0x10, 0xfe, 0x38, 0xa5, 0x57, 0xee, 0x21, 0xbc, 0x83, 0x56, 0x9d, 0xfa, 0x3b, 0x6f, 0xfb, 0x56, + 0xa7, 0xbd, 0x24, 0x88, 0xb6, 0x61, 0x67, 0xfe, 0x68, 0xc4, 0x26, 0xbd, 0x69, 0x3c, 0x5e, 0xa5, 0xff, 0xe2, 0xfd, + 0xe7, 0x48, 0xdc, 0x4a, 0x08, 0x2a, 0x70, 0x44, 0x53, 0x50, 0x94, 0xdc, 0x30, 0x01, 0x61, 0x2d, 0xe7, 0xa9, 0x47, + 0xe1, 0x91, 0x3d, 0xfb, 0xb0, 0x61, 0x91, 0x37, 0x23, 0xfa, 0x4f, 0x9b, 0xa5, 0xcd, 0x24, 0xe6, 0x0b, 0xd0, 0xb2, + 0x15, 0x1d, 0x0f, 0xc7, 0x06, 0x9f, 0x4d, 0xa7, 0xdb, 0xdc, 0xdd, 0x4b, 0xf1, 0xa5, 0x2b, 0x71, 0xa8, 0xf0, 0x73, + 0x8b, 0x3b, 0xa6, 0x6c, 0x87, 0xba, 0x69, 0x8d, 0xd4, 0xa0, 0x6e, 0x39, 0x10, 0x8a, 0xba, 0x7b, 0x52, 0xf9, 0xc7, + 0x2f, 0x0e, 0xe1, 0x3f, 0xe2, 0xea, 0x7f, 0xcd, 0x9a, 0x18, 0xf5, 0xb7, 0x65, 0x4b, 0x70, 0x62, 0x95, 0x90, 0x11, + 0xdf, 0xbf, 0xfe, 0x74, 0xfa, 0xb0, 0x06, 0x7b, 0xd7, 0x26, 0x53, 0xaa, 0x6a, 0xed, 0xef, 0xe3, 0x18, 0x52, 0x77, + 0xd6, 0xab, 0x0b, 0xf4, 0x90, 0xb1, 0x7b, 0x36, 0x80, 0x46, 0xe2, 0x1e, 0x41, 0x5a, 0x7c, 0x1d, 0xdb, 0xd0, 0x55, + 0xe2, 0xf5, 0xa6, 0xab, 0xc4, 0xab, 0xdd, 0x57, 0x89, 0x1f, 0xf6, 0xba, 0x4a, 0xbc, 0xfa, 0xea, 0x57, 0x89, 0xd7, + 0xf5, 0xab, 0xc4, 0x45, 0x2c, 0xec, 0x67, 0xcd, 0xb7, 0x2b, 0xfe, 0xf3, 0x23, 0x29, 0xe5, 0xce, 0xe3, 0x41, 0xc7, + 0xa1, 0x90, 0xc7, 0x17, 0x7f, 0xf8, 0x62, 0x81, 0x0b, 0xf1, 0x3d, 0x9a, 0x93, 0x15, 0x57, 0x0b, 0x4e, 0xd9, 0xf1, + 0x3b, 0x4a, 0x71, 0x18, 0x47, 0xb3, 0x9f, 0x41, 0x29, 0x0b, 0xe2, 0xc0, 0x44, 0x79, 0x11, 0xa4, 0x3f, 0xc7, 0xcb, + 0xd5, 0xf2, 0x2d, 0xc0, 0xfa, 0x18, 0xa4, 0xc1, 0x28, 0x64, 0xd2, 0x13, 0x99, 0xcc, 0xdf, 0xb8, 0x4c, 0x1c, 0x2c, + 0x4e, 0xc5, 0x4f, 0xff, 0x4e, 0xfc, 0x44, 0x9b, 0x54, 0xfe, 0x9b, 0xec, 0xea, 0xf4, 0xe6, 0x8b, 0x88, 0x50, 0x02, + 0x2a, 0x9d, 0x7e, 0xf8, 0x65, 0xe4, 0x22, 0x36, 0x1a, 0x46, 0x29, 0xec, 0x1d, 0x36, 0xc2, 0x61, 0xb5, 0x4b, 0xcd, + 0xca, 0x30, 0x65, 0x08, 0xae, 0xba, 0x18, 0x7e, 0x11, 0xaf, 0x52, 0x36, 0x89, 0x6f, 0x23, 0xdd, 0x8c, 0xa4, 0x93, + 0x01, 0x68, 0x38, 0x65, 0x1b, 0x4c, 0x1e, 0xf9, 0x01, 0x19, 0xe5, 0x38, 0x69, 0xe9, 0x90, 0xbb, 0x74, 0xb5, 0xb4, + 0x48, 0xd5, 0x6c, 0xe1, 0x10, 0x75, 0x99, 0xe5, 0xe8, 0x51, 0xab, 0x15, 0x0f, 0x1e, 0xd6, 0x52, 0x98, 0x6a, 0xc4, + 0x36, 0x97, 0x0a, 0xa7, 0xad, 0x48, 0x08, 0x17, 0x45, 0x1c, 0x8c, 0x86, 0x89, 0xe3, 0x6f, 0xc8, 0x75, 0xb5, 0x78, + 0x0b, 0x51, 0x44, 0xf2, 0x15, 0x9f, 0x0f, 0x1e, 0x15, 0x82, 0x1e, 0x5f, 0x2a, 0x68, 0x7c, 0x77, 0xc3, 0x92, 0xd0, + 0xbf, 0x6f, 0x19, 0x79, 0x1c, 0xfd, 0x08, 0x08, 0x78, 0x15, 0xdf, 0x46, 0x6a, 0x05, 0x4c, 0xd6, 0xd2, 0xb0, 0x96, + 0x1a, 0xe3, 0x97, 0x80, 0xe3, 0x8a, 0xd2, 0x03, 0x48, 0x93, 0x3b, 0x63, 0x7f, 0x37, 0xe9, 0xdf, 0x7f, 0x18, 0xb9, + 0x79, 0x1e, 0xcb, 0x0f, 0xfd, 0xb2, 0xdc, 0xe3, 0x33, 0x4f, 0x9f, 0x3e, 0xda, 0x3c, 0xec, 0x72, 0x7a, 0xf6, 0x86, + 0xd6, 0xc6, 0xc6, 0x5d, 0x00, 0xbd, 0xb8, 0x88, 0x57, 0xe3, 0x39, 0x1a, 0xba, 0x7e, 0xbd, 0xf1, 0x66, 0x00, 0x13, + 0xb3, 0x94, 0xca, 0xa1, 0x57, 0x8a, 0x0a, 0x2c, 0xe0, 0xf7, 0x5f, 0x43, 0x00, 0xce, 0xff, 0x21, 0x1a, 0xea, 0xab, + 0x86, 0xdf, 0xe2, 0x83, 0x87, 0x2d, 0xde, 0x3e, 0x24, 0xd3, 0xe4, 0xa1, 0x2d, 0x84, 0x72, 0xad, 0x99, 0xc8, 0xe4, + 0x55, 0xa4, 0xa9, 0x61, 0xe4, 0x36, 0x45, 0xc8, 0x13, 0x5f, 0x61, 0x36, 0x5d, 0xd3, 0xb9, 0xa3, 0x81, 0xc9, 0x38, + 0xb5, 0xaa, 0x10, 0x19, 0x6e, 0xf2, 0xc0, 0x90, 0x7c, 0x55, 0xdf, 0x2d, 0x82, 0xc8, 0xc4, 0x28, 0xf0, 0xf5, 0x37, + 0xfe, 0x1d, 0xc4, 0x41, 0x06, 0xe2, 0x56, 0x7d, 0x05, 0x85, 0xa6, 0xea, 0x37, 0x07, 0xa9, 0x9e, 0xf4, 0x46, 0x4c, + 0x08, 0x2d, 0xde, 0xf0, 0x1b, 0x4d, 0xd3, 0x34, 0x79, 0x8d, 0xd0, 0xe4, 0x3d, 0x02, 0xcb, 0xf1, 0x3a, 0x00, 0xda, + 0x92, 0x7c, 0x79, 0x47, 0x25, 0x70, 0x33, 0x40, 0x9d, 0xac, 0x28, 0xe0, 0xa1, 0xfe, 0x3a, 0x8e, 0x28, 0x10, 0x17, + 0x7a, 0x08, 0xd3, 0xe6, 0x27, 0x10, 0x11, 0xb8, 0xa7, 0xe1, 0x85, 0x1d, 0xdf, 0x72, 0x49, 0xb0, 0xe6, 0xd0, 0xe3, + 0xb0, 0xcf, 0x9a, 0x63, 0xc2, 0x45, 0x0a, 0x15, 0x04, 0xad, 0x43, 0x25, 0xc4, 0xb3, 0xc9, 0x1a, 0x68, 0x23, 0xde, + 0x8b, 0xee, 0xb2, 0x05, 0x8b, 0x56, 0x3a, 0xe6, 0x84, 0xc2, 0x18, 0x7d, 0x50, 0xe7, 0x15, 0x31, 0x5b, 0x40, 0x6d, + 0x9a, 0x5b, 0xce, 0xe9, 0x2c, 0x4c, 0x39, 0x49, 0xf5, 0xcd, 0x31, 0x57, 0x6c, 0xa6, 0x9c, 0xb6, 0x55, 0x4f, 0x08, + 0x3e, 0xa5, 0x71, 0xd5, 0x91, 0x8b, 0x2c, 0xa1, 0x01, 0x06, 0x45, 0xc7, 0xe0, 0xe2, 0x22, 0x81, 0xf6, 0x96, 0x5f, + 0x9d, 0x34, 0xa9, 0x91, 0xf1, 0x2b, 0x82, 0xa2, 0xc4, 0xa8, 0x83, 0xe1, 0xfd, 0x84, 0xc0, 0x44, 0x1b, 0xe1, 0x8c, + 0x6b, 0x70, 0x36, 0x0c, 0xfa, 0x13, 0xbb, 0xa7, 0x83, 0x84, 0x50, 0xf5, 0x89, 0xdd, 0x83, 0xed, 0xdf, 0x6b, 0x90, + 0xa6, 0xe8, 0x5b, 0xc8, 0xb5, 0x09, 0xa1, 0xfe, 0xc7, 0x10, 0xac, 0x6a, 0xcb, 0x06, 0x72, 0xf2, 0x2d, 0x54, 0x1c, + 0x51, 0x0c, 0x59, 0x9d, 0xc5, 0x26, 0xe6, 0x26, 0xfe, 0xad, 0x46, 0x1c, 0x5b, 0x0d, 0x5b, 0xc3, 0x78, 0xe6, 0x3a, + 0xce, 0x41, 0xad, 0x3e, 0x08, 0xb2, 0x9b, 0x6a, 0x1b, 0x66, 0x36, 0x70, 0x1d, 0x2b, 0x78, 0x66, 0x7b, 0xfd, 0xda, + 0x19, 0xad, 0xc4, 0x92, 0x1c, 0xa2, 0xf8, 0xeb, 0xf4, 0xc9, 0xba, 0x55, 0xdb, 0x90, 0x46, 0xd5, 0x64, 0x1e, 0xfb, + 0x96, 0x73, 0xf9, 0xd7, 0xb0, 0x7e, 0xf4, 0x53, 0x24, 0x4b, 0xca, 0x6b, 0x32, 0x84, 0x68, 0xc8, 0x2d, 0xd8, 0x46, + 0x7f, 0xd1, 0x9e, 0x6b, 0x2d, 0xda, 0x3e, 0x86, 0x31, 0x94, 0xe9, 0xb2, 0x85, 0x4f, 0x99, 0x0a, 0xa0, 0xf2, 0xc5, + 0xb4, 0x4a, 0xe1, 0x78, 0xdc, 0x55, 0x56, 0x68, 0xf4, 0xb6, 0x72, 0x0b, 0x08, 0x7f, 0xc3, 0xf1, 0x69, 0x8f, 0x20, + 0x2e, 0x01, 0xd4, 0x80, 0xd8, 0xe9, 0x3b, 0x01, 0xae, 0x96, 0x65, 0x70, 0xe5, 0x43, 0x72, 0x7f, 0x60, 0x78, 0xe8, + 0xa0, 0x0e, 0x4d, 0xc2, 0x6b, 0x3e, 0xee, 0x1e, 0x08, 0x92, 0x45, 0x93, 0x32, 0xc0, 0xca, 0xf9, 0xb5, 0x3f, 0xb8, + 0x12, 0x45, 0x81, 0xa4, 0x02, 0x71, 0x03, 0x45, 0xc9, 0xe3, 0x08, 0x17, 0x3f, 0x6d, 0xb7, 0x60, 0x2f, 0x2e, 0x06, + 0x1b, 0x50, 0x44, 0x30, 0xd9, 0x4c, 0x11, 0x8a, 0x43, 0xe4, 0x6a, 0x74, 0x0b, 0x6e, 0x09, 0x46, 0x74, 0xe3, 0x4a, + 0xcc, 0x84, 0x4d, 0x61, 0xd1, 0x26, 0xe0, 0xb1, 0x28, 0xf7, 0x95, 0x5a, 0x07, 0xbb, 0xa5, 0xd6, 0xd9, 0x2e, 0xa9, + 0x35, 0xb9, 0x53, 0xdd, 0x26, 0xfe, 0x52, 0xf1, 0xc8, 0x13, 0xcc, 0xb9, 0xea, 0x98, 0x57, 0x12, 0x75, 0xa3, 0xf7, + 0x95, 0x68, 0x55, 0x83, 0x46, 0x56, 0x82, 0x28, 0xfe, 0x56, 0x2e, 0x28, 0x42, 0xa1, 0xae, 0xca, 0xc6, 0x2f, 0x0a, + 0xd9, 0x38, 0xdd, 0x6a, 0x0a, 0x47, 0x1a, 0xc1, 0xfd, 0x2b, 0x4e, 0x6a, 0xf2, 0x76, 0x50, 0x38, 0xab, 0x15, 0x3d, + 0x55, 0xdc, 0xaf, 0x8a, 0x8b, 0x86, 0xe2, 0xd4, 0x27, 0x6e, 0x19, 0x65, 0xdf, 0xbe, 0x72, 0xd5, 0xc2, 0xfb, 0xaa, + 0x28, 0x07, 0xa9, 0x3b, 0x76, 0x59, 0x16, 0xab, 0xcb, 0xa6, 0xec, 0x7e, 0xa3, 0xbe, 0x56, 0x16, 0x89, 0xf4, 0x93, + 0x21, 0x04, 0x0b, 0x31, 0x7d, 0x45, 0xaf, 0x2d, 0x6d, 0x20, 0xb0, 0x93, 0x0d, 0x6e, 0x7d, 0xbb, 0xa5, 0xf3, 0x94, + 0x2f, 0xa1, 0xd0, 0xc2, 0xab, 0x32, 0x08, 0xc4, 0xef, 0xd5, 0xba, 0xe1, 0x94, 0xc7, 0x43, 0x9e, 0x9f, 0xef, 0x20, + 0x5e, 0xd4, 0x1c, 0x55, 0x91, 0x8f, 0x3b, 0xd3, 0x22, 0xf3, 0x5c, 0xac, 0x5a, 0x07, 0x4a, 0x42, 0x9c, 0x35, 0xf7, + 0x8c, 0x29, 0xcb, 0xe8, 0x79, 0x8d, 0x9e, 0xf8, 0x2e, 0x5f, 0x3a, 0xc9, 0x2a, 0xc2, 0xd8, 0xf6, 0x56, 0x96, 0xf8, + 0xe3, 0x4f, 0x4a, 0x97, 0x85, 0x9c, 0x13, 0x64, 0xc0, 0x65, 0x4d, 0x41, 0xdf, 0xc7, 0x50, 0x90, 0xac, 0x67, 0x7b, + 0xa9, 0x22, 0x7d, 0xe9, 0x3d, 0x76, 0xda, 0xfe, 0x8b, 0xe9, 0x61, 0x45, 0x28, 0xea, 0x75, 0xca, 0x22, 0xf3, 0x0d, + 0xfd, 0xc8, 0xe6, 0xab, 0xc5, 0x68, 0xad, 0xca, 0x56, 0x15, 0x91, 0x6b, 0x5d, 0xcc, 0xaa, 0x7e, 0x76, 0x3a, 0x9d, + 0x96, 0x05, 0x8d, 0x8e, 0x76, 0x88, 0xc2, 0xc2, 0xc7, 0x8e, 0xe3, 0x54, 0xfb, 0xbe, 0x1d, 0xed, 0x16, 0xca, 0x6d, + 0xbb, 0x8d, 0x3d, 0x46, 0xdc, 0xee, 0xc2, 0x5f, 0x1d, 0x1d, 0xb9, 0x5d, 0xec, 0xec, 0x92, 0x59, 0x44, 0x9f, 0x8c, + 0x21, 0x82, 0x8c, 0x2d, 0xd2, 0xde, 0x98, 0xa1, 0x0e, 0xc6, 0x56, 0x36, 0x34, 0x1a, 0x0e, 0x58, 0x33, 0x30, 0x15, + 0x71, 0xc5, 0xaa, 0x70, 0x34, 0x94, 0x87, 0xd7, 0x84, 0xf7, 0xe2, 0x23, 0xb8, 0x51, 0xd6, 0x75, 0x99, 0x36, 0x0e, + 0xab, 0xe3, 0xfc, 0xa5, 0x54, 0x4f, 0x83, 0x03, 0x70, 0x2d, 0x14, 0xda, 0x24, 0x9f, 0xc5, 0xbf, 0xa5, 0xfc, 0xff, + 0xc5, 0xf2, 0xae, 0x6c, 0x3f, 0xd2, 0x05, 0x89, 0x76, 0xb1, 0x5b, 0xa8, 0xd7, 0x4d, 0x6b, 0x40, 0x5a, 0x19, 0x4c, + 0x55, 0x05, 0x3a, 0x28, 0xe9, 0x4b, 0x09, 0x40, 0x1a, 0xc4, 0xef, 0xc8, 0x31, 0xc3, 0x14, 0x17, 0x22, 0xc4, 0x22, + 0x7d, 0x1d, 0x8c, 0xc1, 0x7c, 0xde, 0x45, 0xfd, 0x41, 0x69, 0x4d, 0x80, 0x36, 0xbe, 0x36, 0xb6, 0xbd, 0xc4, 0xfd, + 0x55, 0xbd, 0x96, 0x00, 0x0c, 0x28, 0x73, 0x61, 0x13, 0xa2, 0x21, 0x81, 0x56, 0x59, 0xdc, 0xd4, 0x4b, 0xf9, 0x56, + 0xd5, 0xb3, 0x89, 0x8e, 0x21, 0xb8, 0xe6, 0x2a, 0x04, 0x5b, 0x68, 0x0b, 0x60, 0xb0, 0x7c, 0xf9, 0xe1, 0xb3, 0x05, + 0x53, 0xac, 0xae, 0x47, 0x17, 0xa7, 0x1c, 0xd7, 0xaf, 0x85, 0x67, 0x67, 0x4a, 0xfb, 0x1f, 0xe5, 0x8b, 0x3f, 0x34, + 0x0a, 0xf4, 0x2e, 0x4a, 0x12, 0x3a, 0x6e, 0x2d, 0xee, 0x19, 0x7b, 0xd5, 0x5e, 0x04, 0xd1, 0xfe, 0x75, 0xfd, 0xbb, + 0xbd, 0xeb, 0xc2, 0x81, 0xb1, 0x77, 0x65, 0x38, 0x71, 0xc8, 0x72, 0x21, 0x1b, 0xfc, 0xa0, 0x08, 0x14, 0x55, 0xaf, + 0x63, 0x1d, 0x5b, 0x11, 0x97, 0x7f, 0xb1, 0x1a, 0x0c, 0x4f, 0xce, 0xee, 0x16, 0xa1, 0x76, 0xc3, 0x12, 0x48, 0xed, + 0x33, 0xd0, 0x5d, 0xdb, 0xd1, 0x35, 0xf4, 0xa1, 0x0d, 0xa2, 0xd9, 0x40, 0xff, 0xe5, 0xe2, 0x8d, 0xd5, 0xd5, 0xcf, + 0x40, 0x45, 0x7b, 0x33, 0xc3, 0x63, 0xef, 0xdc, 0xbf, 0x67, 0xc9, 0xb5, 0xa7, 0x6b, 0x98, 0xc1, 0x87, 0x0e, 0x3c, + 0x2c, 0xd3, 0x3c, 0x7d, 0x8f, 0x44, 0x11, 0x9a, 0xc8, 0xf5, 0xa6, 0x03, 0xc9, 0x71, 0xbd, 0xae, 0xe6, 0x7a, 0x87, + 0xf6, 0x51, 0x57, 0x3f, 0xfd, 0x46, 0xd3, 0x4e, 0x26, 0x6c, 0x9a, 0x9e, 0xe2, 0x15, 0xed, 0x04, 0xcf, 0x08, 0xfa, + 0xad, 0x69, 0xf6, 0x38, 0x4c, 0x2d, 0x57, 0x5b, 0xf3, 0x47, 0x4d, 0x9b, 0x06, 0x61, 0xd8, 0xd3, 0x1e, 0x4f, 0xbd, + 0xe9, 0xe1, 0xf4, 0x45, 0x9f, 0x17, 0xe7, 0xdf, 0x94, 0xaa, 0x9b, 0xf4, 0xaf, 0xa7, 0x34, 0x4b, 0xb3, 0x24, 0xfe, + 0xc4, 0xb8, 0xd9, 0x89, 0x26, 0x2f, 0x8f, 0xd5, 0xa6, 0x5e, 0xfd, 0x4b, 0x6e, 0x77, 0x34, 0x9e, 0x7a, 0x45, 0x75, + 0xec, 0xe3, 0x81, 0xec, 0xe4, 0xc9, 0x81, 0xe8, 0xfa, 0x89, 0x8a, 0x26, 0xd7, 0x6a, 0x42, 0x94, 0xab, 0xf3, 0x31, + 0xce, 0xc4, 0xf8, 0x4e, 0x20, 0x0e, 0xa3, 0x74, 0xd7, 0x85, 0x1e, 0xe8, 0xda, 0x64, 0xa0, 0xff, 0xe8, 0x7a, 0x5d, + 0xd3, 0x75, 0x8f, 0xec, 0xa3, 0xee, 0xd8, 0x31, 0x0f, 0xed, 0x43, 0xab, 0x6d, 0x1f, 0x99, 0x5d, 0xab, 0x6b, 0x76, + 0xff, 0xd6, 0x1d, 0x5b, 0x87, 0xf6, 0xa1, 0xe9, 0x58, 0x5d, 0x28, 0xb4, 0xba, 0x56, 0xf7, 0xc6, 0x3a, 0xec, 0x8e, + 0x1d, 0x2c, 0xf5, 0xec, 0x4e, 0xc7, 0x72, 0x1d, 0xbb, 0xd3, 0x31, 0x3b, 0xf6, 0xd1, 0x91, 0xe5, 0xb6, 0xed, 0xa3, + 0xa3, 0xf3, 0x4e, 0xd7, 0x6e, 0xc3, 0xbb, 0x76, 0x7b, 0xdc, 0xb6, 0x5d, 0xd7, 0x82, 0xbf, 0xcc, 0xae, 0xed, 0xd1, + 0x0f, 0xd7, 0xb5, 0xdb, 0xae, 0xe9, 0x84, 0x1d, 0xcf, 0x3e, 0x7a, 0x61, 0xe2, 0xdf, 0x58, 0xcd, 0xc4, 0xbf, 0x00, + 0x8c, 0xf9, 0xc2, 0xf6, 0x8e, 0xe8, 0x17, 0x02, 0xbc, 0x39, 0xec, 0xfe, 0xaa, 0x1f, 0x6c, 0x1c, 0x83, 0x4b, 0x63, + 0xe8, 0x76, 0xec, 0x76, 0xdb, 0x3c, 0x74, 0xed, 0x6e, 0x7b, 0x6e, 0x1d, 0x7a, 0xf6, 0xd1, 0xf1, 0xd8, 0x72, 0xed, + 0xe3, 0x63, 0xd3, 0xb1, 0xda, 0xb6, 0x67, 0xba, 0xf6, 0x61, 0x1b, 0x7f, 0xb4, 0x6d, 0xef, 0xe6, 0xf8, 0x85, 0x7d, + 0xd4, 0x99, 0x1f, 0xd9, 0x87, 0x1f, 0x0f, 0xbb, 0xb6, 0xd7, 0x9e, 0xb7, 0x8f, 0x6c, 0xef, 0xf8, 0xe6, 0xc8, 0x3e, + 0x9c, 0x5b, 0xde, 0xd1, 0xd6, 0x96, 0xae, 0x67, 0x03, 0x8e, 0xf0, 0x35, 0xbc, 0x30, 0xf9, 0x0b, 0xf8, 0x33, 0xc7, + 0xb6, 0xff, 0x45, 0x30, 0x69, 0xbd, 0xe9, 0x0b, 0xbb, 0x7b, 0x3c, 0xa6, 0xea, 0x50, 0x60, 0x89, 0x1a, 0xd0, 0xe4, + 0xc6, 0xa2, 0xcf, 0x22, 0x38, 0x4b, 0x00, 0x12, 0x7f, 0xf8, 0xc7, 0x6e, 0x2c, 0xf8, 0x30, 0x7d, 0xf7, 0x7f, 0x0a, + 0x47, 0x4e, 0x39, 0x64, 0xae, 0xfc, 0x86, 0xff, 0x43, 0x49, 0x5f, 0x86, 0xe6, 0xf9, 0x26, 0x45, 0xc5, 0xfb, 0xdd, + 0x8a, 0x8a, 0x37, 0xab, 0x7d, 0x14, 0x15, 0xef, 0xbf, 0xba, 0xa2, 0xe2, 0xbc, 0x6a, 0x27, 0xff, 0xbe, 0x1a, 0x9b, + 0xfe, 0xd7, 0x75, 0xf5, 0x1a, 0x12, 0xf8, 0xad, 0xcb, 0x8b, 0xd5, 0x15, 0x44, 0x57, 0x7a, 0x1f, 0x0f, 0xde, 0xac, + 0x4a, 0x46, 0x60, 0x31, 0xd0, 0xd8, 0xf7, 0x31, 0xd1, 0xd8, 0xdf, 0x57, 0x03, 0xb0, 0x3c, 0xe1, 0x7c, 0x49, 0x30, + 0xb1, 0xe6, 0x7e, 0x38, 0x95, 0x3c, 0x0d, 0x94, 0xf4, 0xb1, 0x18, 0xbc, 0x12, 0xe0, 0xb8, 0x06, 0x75, 0xd8, 0x6a, + 0x11, 0xa5, 0xbd, 0x23, 0x07, 0x0e, 0x52, 0x6f, 0x9a, 0xe4, 0x95, 0xc6, 0xb6, 0x88, 0x47, 0x75, 0xcd, 0xbd, 0x26, + 0x36, 0xbe, 0x47, 0xa3, 0xc0, 0x66, 0xe8, 0x6e, 0x1d, 0xae, 0x06, 0xd6, 0x36, 0xc2, 0x68, 0x12, 0xd8, 0xb9, 0xa6, + 0xf7, 0x65, 0xd3, 0xbc, 0x8a, 0x31, 0xe6, 0xe6, 0x9e, 0x42, 0x4f, 0xaa, 0xed, 0xdd, 0xb2, 0x69, 0xdf, 0xae, 0x61, + 0x36, 0x7c, 0xbe, 0xd4, 0x7c, 0x8b, 0x5d, 0xa1, 0x04, 0x5c, 0x45, 0x55, 0x25, 0xb3, 0x5a, 0x23, 0x42, 0x0a, 0xee, + 0xbe, 0x30, 0x3e, 0x2c, 0x58, 0x4b, 0x47, 0x43, 0x7e, 0xc7, 0x51, 0xde, 0x95, 0x60, 0xaa, 0x06, 0x8b, 0xcf, 0xd6, + 0xc8, 0x71, 0x07, 0xbf, 0x03, 0xeb, 0xc8, 0x39, 0x9e, 0x51, 0xac, 0xe2, 0x79, 0xad, 0xc0, 0xa5, 0xcb, 0x4c, 0x3e, + 0x77, 0xd7, 0x75, 0xe6, 0x71, 0xa3, 0xa9, 0xb2, 0xcb, 0x16, 0x82, 0x0b, 0xc2, 0xcf, 0x93, 0x61, 0x70, 0x4e, 0xc6, + 0xdb, 0x68, 0xfb, 0xbc, 0x0d, 0x98, 0xa8, 0xf7, 0x18, 0x16, 0xb1, 0xc9, 0x1f, 0xd4, 0xb8, 0x00, 0xeb, 0x29, 0x64, + 0xc1, 0xee, 0x21, 0x9b, 0xa6, 0xf0, 0xa8, 0x1e, 0x5a, 0x31, 0xf7, 0xb7, 0x18, 0xd8, 0xa8, 0x80, 0x39, 0x10, 0xb4, + 0x86, 0xde, 0x66, 0x93, 0x23, 0x9d, 0x47, 0xd6, 0x25, 0x15, 0xb5, 0xdb, 0x39, 0x36, 0xdd, 0x23, 0xd3, 0x3e, 0xee, + 0x18, 0xb9, 0xd8, 0x70, 0x2a, 0xc8, 0x12, 0x42, 0xc0, 0x28, 0x5a, 0x76, 0x33, 0x88, 0x82, 0x2c, 0xf0, 0xc3, 0x1c, + 0xf8, 0xe3, 0xf2, 0xad, 0xe2, 0x9f, 0xab, 0x34, 0x83, 0x31, 0x0a, 0xa6, 0x17, 0x0d, 0xc2, 0xad, 0x11, 0xcb, 0x6e, + 0x19, 0x8b, 0x36, 0x28, 0xcb, 0xab, 0xf6, 0xe5, 0x7f, 0x9e, 0xb5, 0x6d, 0x4e, 0x96, 0x2c, 0xa3, 0x2c, 0xe2, 0xeb, + 0x43, 0x18, 0x43, 0xe7, 0x43, 0xf3, 0xa7, 0x4d, 0x04, 0xf7, 0x9f, 0xbb, 0x09, 0x6e, 0xc6, 0xf6, 0x21, 0xb8, 0xff, + 0xfc, 0xea, 0x04, 0xf7, 0x27, 0x95, 0xe0, 0x96, 0x7c, 0x81, 0x0a, 0xa9, 0xf3, 0x07, 0x7c, 0x6e, 0x41, 0x50, 0xe7, + 0xe7, 0xfa, 0x01, 0x31, 0xf0, 0xba, 0x92, 0x6c, 0xf7, 0x63, 0x29, 0x7b, 0x10, 0x0a, 0x45, 0x30, 0x08, 0x2d, 0x65, + 0x2a, 0x81, 0x44, 0xb4, 0x32, 0xa5, 0x3a, 0xc0, 0x7c, 0x1b, 0x65, 0xa1, 0xfd, 0x9e, 0x5f, 0xfc, 0x40, 0xc9, 0xf3, + 0x26, 0x4e, 0x16, 0x3e, 0x06, 0xe0, 0xd3, 0x31, 0xeb, 0x20, 0x3c, 0x38, 0xe0, 0x7f, 0x36, 0x8e, 0xa3, 0x89, 0xd4, + 0x54, 0xb0, 0xc1, 0x25, 0x71, 0xdc, 0xfa, 0x3d, 0xf3, 0x13, 0xdd, 0xa4, 0xd7, 0x30, 0xb9, 0xcf, 0xda, 0xce, 0x33, + 0xef, 0xf0, 0xd9, 0x91, 0x03, 0xff, 0xbb, 0xac, 0x9d, 0x9b, 0xbc, 0xe2, 0x22, 0x8e, 0x20, 0xf1, 0x89, 0xa8, 0xb9, + 0xa9, 0xda, 0x2d, 0x63, 0x9f, 0x8a, 0x5a, 0xc7, 0xcd, 0x95, 0x26, 0xfe, 0x7d, 0x51, 0xa7, 0xb1, 0xc6, 0x3c, 0x5e, + 0x29, 0xdd, 0x6a, 0xe8, 0x4d, 0x10, 0xad, 0x40, 0xf6, 0xa6, 0xd4, 0x50, 0x5f, 0xf3, 0xe1, 0x16, 0xe3, 0x62, 0xed, + 0xfc, 0xaa, 0xc8, 0xae, 0x24, 0xb2, 0xbc, 0xec, 0xc4, 0x20, 0x57, 0x5b, 0x38, 0x18, 0x9b, 0x1d, 0xf3, 0x0b, 0x69, + 0x90, 0xdb, 0x50, 0x4c, 0x90, 0x4f, 0x13, 0x94, 0x25, 0xab, 0x68, 0xdc, 0xc2, 0x9f, 0xfe, 0x28, 0x6d, 0x05, 0x07, + 0x10, 0x9d, 0x15, 0x3f, 0x6c, 0xe0, 0xac, 0xf9, 0xa7, 0x4e, 0x91, 0x8a, 0x22, 0x15, 0xb3, 0xe2, 0x3f, 0xcb, 0xcc, + 0x84, 0x12, 0xd8, 0xe2, 0xd4, 0x5a, 0x03, 0xff, 0x99, 0x6c, 0xf8, 0x2c, 0x33, 0x21, 0x89, 0x2c, 0x4c, 0xf7, 0xd3, + 0xa7, 0x54, 0x0b, 0xd2, 0x3a, 0xd2, 0xb0, 0xce, 0xc6, 0x45, 0x78, 0x37, 0xcd, 0x9f, 0xc5, 0x14, 0xe1, 0xad, 0x37, + 0x36, 0xe3, 0xe7, 0xcf, 0x4f, 0x07, 0xae, 0xc1, 0x93, 0x92, 0x96, 0x32, 0x68, 0x9d, 0xef, 0x67, 0x7c, 0x60, 0x34, + 0xba, 0xc5, 0x2d, 0xe1, 0xce, 0xe4, 0x08, 0x13, 0x65, 0x4e, 0xbd, 0x20, 0xa3, 0x05, 0x29, 0x19, 0x7d, 0x61, 0x04, + 0x20, 0xea, 0xc8, 0x5b, 0x57, 0xdb, 0x76, 0x6c, 0x47, 0x97, 0x0d, 0xa7, 0xc1, 0x6c, 0xb0, 0x8e, 0x33, 0x1f, 0x72, + 0x03, 0x85, 0xf1, 0x0c, 0x7c, 0x6b, 0xb2, 0x20, 0x0b, 0x21, 0xd1, 0x0c, 0x38, 0xd9, 0x2c, 0xe8, 0x5e, 0x9e, 0x73, + 0x8b, 0x67, 0x3f, 0xf9, 0x84, 0xc9, 0x06, 0x85, 0x5b, 0x1d, 0x46, 0x1c, 0xfa, 0x11, 0x0e, 0xc3, 0x96, 0xde, 0x82, + 0x54, 0x97, 0x2c, 0x49, 0x2d, 0xd5, 0x83, 0xa0, 0xa7, 0x41, 0x1b, 0x48, 0x43, 0x8f, 0x00, 0xa6, 0x89, 0xbf, 0x80, + 0x98, 0xec, 0xeb, 0xdc, 0xe4, 0x94, 0x56, 0xe7, 0xa4, 0x56, 0x73, 0x5f, 0x1c, 0x99, 0x9a, 0xe7, 0x9a, 0x9a, 0x03, + 0xe4, 0x56, 0xcf, 0xcd, 0x75, 0x7e, 0xd5, 0xdf, 0xa5, 0x04, 0x25, 0xfa, 0xf2, 0x98, 0xc6, 0x41, 0xea, 0x4f, 0x2e, + 0x5e, 0xce, 0x28, 0x80, 0x64, 0x4b, 0x89, 0x96, 0x1e, 0x90, 0x22, 0xe4, 0x82, 0xdd, 0x65, 0x06, 0x26, 0x62, 0xe1, + 0x55, 0x02, 0x63, 0x8d, 0xce, 0x7f, 0x41, 0xa4, 0x05, 0x9f, 0x3f, 0xb7, 0x02, 0x70, 0x70, 0x18, 0x28, 0xf8, 0x81, + 0x67, 0xa3, 0x84, 0xb0, 0xa0, 0x50, 0xdd, 0x21, 0xb2, 0xc0, 0xfb, 0x08, 0xfe, 0x2d, 0x8a, 0xc5, 0x0f, 0xae, 0x3a, + 0xb5, 0x43, 0x3f, 0x9a, 0x01, 0x49, 0xf3, 0xa3, 0x59, 0xcd, 0x44, 0x83, 0xfc, 0x17, 0x2b, 0xa5, 0x05, 0xa8, 0xc2, + 0x7c, 0x22, 0xfd, 0xfe, 0xfe, 0x82, 0x12, 0x4d, 0x41, 0x52, 0x73, 0x7f, 0x82, 0xce, 0x76, 0x85, 0x76, 0xe7, 0xf9, + 0xe0, 0xdb, 0x93, 0x05, 0xcb, 0x7c, 0x12, 0x0d, 0xc3, 0xe5, 0x17, 0xd8, 0x01, 0x6d, 0x2c, 0x92, 0xc4, 0x52, 0x32, + 0xf9, 0x09, 0xbb, 0x09, 0xc6, 0xfc, 0x5e, 0x6a, 0x6a, 0xfc, 0x9c, 0xb2, 0xd0, 0x0a, 0x6c, 0xe0, 0x9a, 0x64, 0x84, + 0x3c, 0xf6, 0x31, 0xcc, 0xe4, 0x20, 0x8a, 0xf5, 0xd3, 0x6f, 0xa5, 0xbf, 0xd6, 0xa6, 0x49, 0x80, 0x6c, 0x8f, 0x97, + 0x09, 0x0b, 0xff, 0x35, 0xf8, 0x16, 0x0e, 0xee, 0x6f, 0xaf, 0x74, 0xa3, 0x9f, 0xd9, 0xf3, 0x84, 0x4d, 0x07, 0xdf, + 0x36, 0x64, 0x3d, 0xc4, 0xeb, 0x3d, 0xf5, 0x45, 0x6f, 0x7b, 0x45, 0x70, 0xa0, 0xf6, 0x5e, 0x97, 0xfa, 0x53, 0x7e, + 0x5b, 0x87, 0x1b, 0xe0, 0xba, 0x74, 0xc7, 0x76, 0xfb, 0x78, 0x7f, 0x1e, 0x85, 0xfe, 0xf8, 0x53, 0x9f, 0xde, 0x94, + 0x1e, 0x2c, 0x38, 0xad, 0xc7, 0xfe, 0xb2, 0x87, 0xc7, 0xab, 0x5a, 0x08, 0xee, 0x9a, 0x54, 0x2a, 0x39, 0xbb, 0xc6, + 0xb5, 0x8c, 0x4b, 0x79, 0x8d, 0x5f, 0xc6, 0x4f, 0xdd, 0xce, 0x83, 0x8c, 0x89, 0x4f, 0xe1, 0x43, 0x9e, 0x8b, 0x8b, + 0x3a, 0x5d, 0x51, 0xf1, 0x62, 0x6d, 0xb7, 0x35, 0xb7, 0xfb, 0xb7, 0xce, 0x8d, 0xeb, 0xcc, 0x3d, 0xd7, 0xee, 0x7e, + 0x74, 0xbb, 0xf3, 0xb6, 0x7d, 0x1c, 0x5a, 0x6d, 0xfb, 0x18, 0xfe, 0x7c, 0x3c, 0xb6, 0xbb, 0x73, 0xcb, 0xb3, 0x0f, + 0x3f, 0xba, 0x5e, 0x68, 0x75, 0xed, 0x63, 0xf8, 0x73, 0x4e, 0xad, 0xe0, 0x02, 0x44, 0xf7, 0x9d, 0x6f, 0x4b, 0x54, + 0x40, 0xf9, 0x2d, 0xf5, 0x34, 0x66, 0xe9, 0x78, 0x6b, 0xd0, 0xf5, 0x00, 0xc9, 0xd0, 0x4d, 0x11, 0x04, 0x32, 0xea, + 0xb7, 0x20, 0x0d, 0x3b, 0x26, 0x10, 0x10, 0x26, 0x2f, 0xc2, 0x2f, 0x55, 0x84, 0xd2, 0x6f, 0xdc, 0x46, 0xbc, 0x4d, + 0x73, 0xc0, 0x75, 0x91, 0x99, 0x8a, 0x94, 0x43, 0xbf, 0x2c, 0x31, 0x88, 0x91, 0x08, 0x11, 0xaf, 0x50, 0xa5, 0x22, + 0x3b, 0x62, 0xbe, 0xbb, 0xe3, 0xe8, 0x99, 0xcb, 0x64, 0x76, 0x9e, 0xaf, 0x0a, 0x9b, 0x2b, 0x8c, 0x24, 0xf4, 0x3f, + 0x0a, 0x07, 0x93, 0xd2, 0x12, 0x1c, 0x11, 0xcd, 0x75, 0x12, 0x24, 0xb2, 0x7b, 0x0a, 0x89, 0x76, 0x9b, 0x23, 0xd5, + 0x1b, 0x90, 0xc6, 0xe4, 0x2d, 0x70, 0xc9, 0x37, 0x7e, 0xa8, 0x18, 0xb7, 0x28, 0x2d, 0x1f, 0x49, 0xca, 0xff, 0xf4, + 0x69, 0xd1, 0x39, 0xab, 0xd2, 0xef, 0x13, 0xb7, 0x03, 0xc7, 0x6e, 0x87, 0xb5, 0xb7, 0xda, 0x59, 0xed, 0x0e, 0x07, + 0x5c, 0x84, 0x0b, 0x15, 0xb6, 0x14, 0x42, 0x8b, 0xbb, 0xd1, 0xd8, 0xab, 0xa6, 0xc3, 0x85, 0x40, 0xca, 0x95, 0xab, + 0x8e, 0x6e, 0xf4, 0x23, 0xa1, 0x92, 0x8c, 0xb6, 0x84, 0x40, 0xe6, 0x77, 0x31, 0x1d, 0x50, 0xb3, 0x65, 0x1c, 0x3b, + 0x9c, 0x46, 0xff, 0xd7, 0x83, 0x40, 0x07, 0x2e, 0xd0, 0xa1, 0x56, 0x76, 0x6b, 0xc9, 0xa1, 0x47, 0x9e, 0xab, 0x74, + 0xa0, 0xb2, 0xf4, 0x4c, 0x87, 0x22, 0xc8, 0x6f, 0x85, 0x29, 0xed, 0xa4, 0x01, 0x99, 0x3c, 0x2d, 0x8a, 0x02, 0x33, + 0x80, 0x18, 0xe0, 0x2d, 0xe1, 0x4c, 0x66, 0x3c, 0x7d, 0xba, 0xf1, 0x10, 0x22, 0x85, 0xbd, 0x9a, 0xd9, 0x53, 0x57, + 0xe9, 0x9b, 0xae, 0x92, 0x18, 0x09, 0x17, 0xa9, 0x86, 0xb0, 0x7b, 0xa3, 0xb5, 0x87, 0x3f, 0x47, 0xcc, 0xcf, 0x6c, + 0xae, 0x69, 0x6a, 0x29, 0x87, 0xbb, 0xe9, 0xb2, 0x36, 0x58, 0xbc, 0xf1, 0x58, 0x67, 0x3c, 0x96, 0xe0, 0x93, 0xf5, + 0xc7, 0x15, 0xf7, 0xf4, 0x06, 0x18, 0x9f, 0x9d, 0x22, 0x3c, 0xcd, 0xbb, 0xcc, 0xa7, 0x18, 0x26, 0xea, 0x91, 0x1b, + 0x67, 0xbe, 0xc8, 0x23, 0x03, 0x7c, 0x79, 0xbf, 0x51, 0x25, 0xab, 0x78, 0x83, 0x9f, 0xbe, 0xbb, 0xf8, 0x4e, 0xe3, + 0xeb, 0x9f, 0x34, 0x88, 0x78, 0x91, 0xa1, 0xac, 0x07, 0x03, 0xca, 0x7a, 0xa0, 0xf1, 0x34, 0x22, 0x90, 0x3b, 0x20, + 0x3f, 0x20, 0x0c, 0xa2, 0x00, 0x9a, 0xf4, 0xaa, 0x8b, 0x55, 0x98, 0x05, 0x4b, 0x3f, 0xc9, 0x0e, 0xa0, 0xa9, 0x05, + 0x44, 0x4e, 0xdf, 0xe4, 0x23, 0x4e, 0xaa, 0x59, 0x11, 0x62, 0x2f, 0x8b, 0x84, 0x6e, 0x76, 0x1a, 0x84, 0x52, 0x35, + 0x2b, 0x3e, 0xe0, 0x8f, 0xc7, 0x6c, 0x99, 0x0d, 0x74, 0x7f, 0x09, 0xd9, 0x2f, 0x30, 0x9e, 0xf5, 0x41, 0x3c, 0xce, + 0x58, 0x66, 0xa5, 0x59, 0xc2, 0xfc, 0x85, 0x2e, 0x43, 0xb9, 0xd6, 0xe1, 0xa5, 0xab, 0xd1, 0x22, 0xc8, 0x64, 0x2c, + 0x44, 0x1a, 0x20, 0x28, 0x49, 0xa1, 0x8b, 0xa7, 0xc3, 0x9c, 0xa3, 0xf0, 0x3c, 0x9e, 0x55, 0x56, 0x54, 0xc1, 0xb9, + 0x9c, 0x61, 0xa4, 0x5d, 0x9e, 0xf1, 0x60, 0x82, 0x3e, 0x4f, 0xd7, 0xdc, 0xaf, 0x5d, 0x86, 0x6c, 0xd4, 0x4f, 0x4f, + 0xf8, 0xf5, 0x56, 0xc3, 0x50, 0x0c, 0x7a, 0xc7, 0x81, 0x58, 0xc2, 0x9b, 0x3c, 0xde, 0x0f, 0x78, 0x65, 0x38, 0x9a, + 0x08, 0x32, 0xc6, 0x79, 0xa7, 0xbe, 0x5c, 0x00, 0x23, 0x54, 0x52, 0xa2, 0xcf, 0xdd, 0x53, 0xe9, 0x62, 0x85, 0xbd, + 0x42, 0x5e, 0xe9, 0xf3, 0xe7, 0x97, 0xc3, 0xff, 0xfc, 0x1b, 0x82, 0xd1, 0xcf, 0x5d, 0xe1, 0x67, 0x7e, 0xa9, 0xd6, + 0xe2, 0xdc, 0xa7, 0x39, 0x44, 0x03, 0x0a, 0x36, 0x11, 0x81, 0x57, 0xc4, 0xd2, 0xca, 0x87, 0x57, 0x22, 0x98, 0x16, + 0x24, 0x9c, 0x30, 0x84, 0x37, 0xfc, 0x10, 0xa6, 0x77, 0x28, 0x82, 0x30, 0x68, 0xbf, 0xdd, 0x7d, 0x7f, 0x0c, 0xc1, + 0x96, 0x6b, 0x79, 0x20, 0x94, 0x0e, 0xe2, 0x1a, 0x3a, 0x3d, 0xf1, 0x35, 0x64, 0x5a, 0x90, 0xfd, 0x48, 0x7b, 0x07, + 0x30, 0xcc, 0x79, 0xbc, 0x60, 0x76, 0x10, 0x1f, 0xdc, 0xb2, 0x91, 0xe5, 0x2f, 0x03, 0xd2, 0xd5, 0xa3, 0xdc, 0x4d, + 0x23, 0xce, 0x4f, 0xaa, 0xc0, 0x89, 0xbf, 0xce, 0x0b, 0x54, 0xc6, 0xe5, 0xe8, 0x69, 0x1d, 0xaf, 0x50, 0xdc, 0x81, + 0x4f, 0xb3, 0x82, 0xc7, 0xf8, 0xf4, 0xe4, 0xc0, 0x3f, 0x2d, 0x87, 0x6f, 0xb4, 0x45, 0x02, 0x81, 0xf2, 0x21, 0x70, + 0x46, 0x51, 0x18, 0x45, 0xc0, 0xc5, 0xe2, 0xc1, 0x8a, 0xa7, 0x53, 0x35, 0xe4, 0xa2, 0x5d, 0xee, 0x9e, 0x44, 0x5a, + 0xb1, 0xa4, 0xe3, 0x25, 0x7d, 0xa9, 0xfe, 0x09, 0xf9, 0x13, 0x92, 0x27, 0xf3, 0xe8, 0x9c, 0xb0, 0xdd, 0x6b, 0xa1, + 0x1b, 0x25, 0xc6, 0x1e, 0x53, 0x25, 0x4e, 0x47, 0xaa, 0x81, 0xc2, 0x37, 0x70, 0x2e, 0x8f, 0x06, 0x03, 0x22, 0x73, + 0x55, 0x6a, 0x07, 0x48, 0x6c, 0x48, 0xa6, 0x00, 0x83, 0xcd, 0xa0, 0xa1, 0x45, 0x2e, 0x74, 0xd8, 0xa8, 0x3a, 0x9c, + 0x7a, 0x1f, 0x0f, 0x7c, 0xb1, 0xfc, 0x4a, 0x0b, 0x14, 0x16, 0x1e, 0x9f, 0x77, 0xa0, 0xef, 0x02, 0x4e, 0x85, 0xcc, + 0x6b, 0x7f, 0x25, 0x8a, 0x6e, 0x85, 0xfe, 0x7d, 0xac, 0x98, 0x36, 0xf0, 0x28, 0x07, 0xe7, 0x58, 0x7a, 0x21, 0xbc, + 0x0b, 0x6b, 0x1b, 0x4d, 0x06, 0xa4, 0xaf, 0x6f, 0x36, 0x35, 0x82, 0xfc, 0xae, 0xbd, 0xa6, 0xd6, 0x2d, 0x0f, 0x06, + 0x89, 0x67, 0x5e, 0xec, 0xc3, 0xd2, 0x4b, 0x24, 0x0b, 0xf9, 0xc9, 0x01, 0x8c, 0x0f, 0x22, 0x33, 0x94, 0x18, 0xa7, + 0xc0, 0x80, 0xf0, 0x0f, 0x7e, 0x4a, 0xe6, 0x19, 0x6f, 0x27, 0x82, 0xe7, 0xc3, 0x8b, 0xa5, 0x8c, 0x0d, 0x5b, 0xaa, + 0x52, 0xe7, 0x65, 0x9c, 0x66, 0x26, 0x70, 0x77, 0x02, 0x87, 0xdf, 0x57, 0x98, 0xbd, 0x21, 0xef, 0x67, 0x4c, 0x38, + 0x3e, 0x9f, 0x67, 0x1b, 0x7c, 0xa3, 0x37, 0x55, 0x21, 0x7e, 0x76, 0x4b, 0x85, 0x62, 0x1d, 0x6f, 0xab, 0x55, 0x70, + 0x4e, 0xb2, 0xda, 0xd2, 0x6f, 0xe9, 0x8f, 0x71, 0xc5, 0xd7, 0x6a, 0x63, 0x29, 0xd4, 0x3b, 0xcf, 0x06, 0x50, 0x55, + 0xc8, 0xe2, 0xfd, 0xe5, 0x92, 0x2a, 0x1b, 0xfd, 0x93, 0x03, 0xba, 0x96, 0x9e, 0xd2, 0x0a, 0x3b, 0x3d, 0x01, 0xf3, + 0x4e, 0x9a, 0x74, 0x7f, 0xb9, 0xe4, 0x53, 0x4a, 0xbf, 0xe8, 0xcd, 0xc1, 0x3c, 0x5b, 0x84, 0xa7, 0xff, 0x07, 0xc0, + 0xb1, 0x34, 0x8b, 0x20, 0x5c, 0x03, 0x00}; } // namespace web_server } // namespace esphome diff --git a/esphome/components/wifi/wifi_component.h b/esphome/components/wifi/wifi_component.h index 0b077819ae..d79cde0b18 100644 --- a/esphome/components/wifi/wifi_component.h +++ b/esphome/components/wifi/wifi_component.h @@ -20,8 +20,12 @@ #endif #if defined(USE_ESP_IDF) && defined(USE_WIFI_WPA2_EAP) +#if (ESP_IDF_VERSION_MAJOR >= 5) && (ESP_IDF_VERSION_MINOR >= 1) +#include +#else #include #endif +#endif #ifdef USE_ESP8266 #include diff --git a/esphome/components/wifi/wifi_component_esp_idf.cpp b/esphome/components/wifi/wifi_component_esp_idf.cpp index 96fa837767..a8d67ed44d 100644 --- a/esphome/components/wifi/wifi_component_esp_idf.cpp +++ b/esphome/components/wifi/wifi_component_esp_idf.cpp @@ -15,8 +15,12 @@ #include #include #ifdef USE_WIFI_WPA2_EAP +#if (ESP_IDF_VERSION_MAJOR >= 5) && (ESP_IDF_VERSION_MINOR >= 1) +#include +#else #include #endif +#endif #ifdef USE_WIFI_AP #include "dhcpserver/dhcpserver.h" @@ -364,48 +368,78 @@ bool WiFiComponent::wifi_sta_connect_(const WiFiAP &ap) { if (ap.get_eap().has_value()) { // note: all certificates and keys have to be null terminated. Lengths are appended by +1 to include \0. EAPAuth eap = ap.get_eap().value(); +#if (ESP_IDF_VERSION_MAJOR >= 5) && (ESP_IDF_VERSION_MINOR >= 1) + err = esp_eap_client_set_identity((uint8_t *) eap.identity.c_str(), eap.identity.length()); +#else err = esp_wifi_sta_wpa2_ent_set_identity((uint8_t *) eap.identity.c_str(), eap.identity.length()); +#endif if (err != ESP_OK) { - ESP_LOGV(TAG, "esp_wifi_sta_wpa2_ent_set_identity failed! %d", err); + ESP_LOGV(TAG, "set_identity failed %d", err); } int ca_cert_len = strlen(eap.ca_cert); int client_cert_len = strlen(eap.client_cert); int client_key_len = strlen(eap.client_key); if (ca_cert_len) { +#if (ESP_IDF_VERSION_MAJOR >= 5) && (ESP_IDF_VERSION_MINOR >= 1) + err = esp_eap_client_set_ca_cert((uint8_t *) eap.ca_cert, ca_cert_len + 1); +#else err = esp_wifi_sta_wpa2_ent_set_ca_cert((uint8_t *) eap.ca_cert, ca_cert_len + 1); +#endif if (err != ESP_OK) { - ESP_LOGV(TAG, "esp_wifi_sta_wpa2_ent_set_ca_cert failed! %d", err); + ESP_LOGV(TAG, "set_ca_cert failed %d", err); } } // workout what type of EAP this is // validation is not required as the config tool has already validated it if (client_cert_len && client_key_len) { // if we have certs, this must be EAP-TLS +#if (ESP_IDF_VERSION_MAJOR >= 5) && (ESP_IDF_VERSION_MINOR >= 1) + err = esp_eap_client_set_certificate_and_key((uint8_t *) eap.client_cert, client_cert_len + 1, + (uint8_t *) eap.client_key, client_key_len + 1, + (uint8_t *) eap.password.c_str(), strlen(eap.password.c_str())); +#else err = esp_wifi_sta_wpa2_ent_set_cert_key((uint8_t *) eap.client_cert, client_cert_len + 1, (uint8_t *) eap.client_key, client_key_len + 1, (uint8_t *) eap.password.c_str(), strlen(eap.password.c_str())); +#endif if (err != ESP_OK) { - ESP_LOGV(TAG, "esp_wifi_sta_wpa2_ent_set_cert_key failed! %d", err); + ESP_LOGV(TAG, "set_cert_key failed %d", err); } } else { // in the absence of certs, assume this is username/password based +#if (ESP_IDF_VERSION_MAJOR >= 5) && (ESP_IDF_VERSION_MINOR >= 1) + err = esp_eap_client_set_username((uint8_t *) eap.username.c_str(), eap.username.length()); +#else err = esp_wifi_sta_wpa2_ent_set_username((uint8_t *) eap.username.c_str(), eap.username.length()); +#endif if (err != ESP_OK) { - ESP_LOGV(TAG, "esp_wifi_sta_wpa2_ent_set_username failed! %d", err); + ESP_LOGV(TAG, "set_username failed %d", err); } +#if (ESP_IDF_VERSION_MAJOR >= 5) && (ESP_IDF_VERSION_MINOR >= 1) + err = esp_eap_client_set_password((uint8_t *) eap.password.c_str(), eap.password.length()); +#else err = esp_wifi_sta_wpa2_ent_set_password((uint8_t *) eap.password.c_str(), eap.password.length()); +#endif if (err != ESP_OK) { - ESP_LOGV(TAG, "esp_wifi_sta_wpa2_ent_set_password failed! %d", err); + ESP_LOGV(TAG, "set_password failed %d", err); } // set TTLS Phase 2, defaults to MSCHAPV2 +#if (ESP_IDF_VERSION_MAJOR >= 5) && (ESP_IDF_VERSION_MINOR >= 1) + err = esp_eap_client_set_ttls_phase2_method(eap.ttls_phase_2); +#else err = esp_wifi_sta_wpa2_ent_set_ttls_phase2_method(eap.ttls_phase_2); +#endif if (err != ESP_OK) { - ESP_LOGV(TAG, "esp_wifi_sta_wpa2_ent_set_ttls_phase2_method failed! %d", err); + ESP_LOGV(TAG, "set_ttls_phase2_method failed %d", err); } } +#if (ESP_IDF_VERSION_MAJOR >= 5) && (ESP_IDF_VERSION_MINOR >= 1) + err = esp_wifi_sta_enterprise_enable(); +#else err = esp_wifi_sta_wpa2_ent_enable(); +#endif if (err != ESP_OK) { - ESP_LOGV(TAG, "esp_wifi_sta_wpa2_ent_enable failed! %d", err); + ESP_LOGV(TAG, "enterprise_enable failed %d", err); } } #endif // USE_WIFI_WPA2_EAP diff --git a/esphome/components/wifi/wifi_component_pico_w.cpp b/esphome/components/wifi/wifi_component_pico_w.cpp index 2bb1af5489..4afcf2d78b 100644 --- a/esphome/components/wifi/wifi_component_pico_w.cpp +++ b/esphome/components/wifi/wifi_component_pico_w.cpp @@ -141,13 +141,29 @@ bool WiFiComponent::wifi_scan_start_(bool passive) { #ifdef USE_WIFI_AP bool WiFiComponent::wifi_ap_ip_config_(optional manual_ip) { - // TODO: - return false; + esphome::network::IPAddress ip_address, gateway, subnet, dns; + if (manual_ip.has_value()) { + ip_address = manual_ip->static_ip; + gateway = manual_ip->gateway; + subnet = manual_ip->subnet; + dns = manual_ip->static_ip; + } else { + ip_address = network::IPAddress(192, 168, 4, 1); + gateway = network::IPAddress(192, 168, 4, 1); + subnet = network::IPAddress(255, 255, 255, 0); + dns = network::IPAddress(192, 168, 4, 1); + } + WiFi.config(ip_address, dns, gateway, subnet); + return true; } bool WiFiComponent::wifi_start_ap_(const WiFiAP &ap) { if (!this->wifi_mode_({}, true)) return false; + if (!this->wifi_ap_ip_config_(ap.get_manual_ip())) { + ESP_LOGV(TAG, "wifi_ap_ip_config_ failed!"); + return false; + } WiFi.beginAP(ap.get_ssid().c_str(), ap.get_password().c_str(), ap.get_channel().value_or(1)); diff --git a/esphome/const.py b/esphome/const.py index 1ac9c88eef..7237e697fd 100644 --- a/esphome/const.py +++ b/esphome/const.py @@ -1,6 +1,6 @@ """Constants used by esphome.""" -__version__ = "2024.7.0-dev" +__version__ = "2024.8.0-dev" ALLOWED_NAME_CHARS = "abcdefghijklmnopqrstuvwxyz0123456789-_" VALID_SUBSTITUTIONS_CHARACTERS = ( diff --git a/esphome/core/defines.h b/esphome/core/defines.h index 1e6f3517db..4831ed2c9e 100644 --- a/esphome/core/defines.h +++ b/esphome/core/defines.h @@ -86,6 +86,7 @@ #define USE_ESP32_BLE_SERVER #define USE_ESP32_CAMERA #define USE_IMPROV +#define USE_MICRO_WAKE_WORD_VAD #define USE_MICROPHONE #define USE_PSRAM #define USE_SOCKET_IMPL_BSD_SOCKETS diff --git a/esphome/core/helpers.cpp b/esphome/core/helpers.cpp index d47cbdc86f..cf1b1b9206 100644 --- a/esphome/core/helpers.cpp +++ b/esphome/core/helpers.cpp @@ -83,7 +83,7 @@ static const uint16_t CRC16_1021_BE_LUT_H[] = {0x0000, 0x1231, 0x2462, 0x3653, 0 // STL backports -#if _GLIBCXX_RELEASE < 7 +#if _GLIBCXX_RELEASE < 8 std::string to_string(int value) { return str_snprintf("%d", 32, value); } // NOLINT std::string to_string(long value) { return str_snprintf("%ld", 32, value); } // NOLINT std::string to_string(long long value) { return str_snprintf("%lld", 32, value); } // NOLINT diff --git a/platformio.ini b/platformio.ini index a72bf598c5..f07889526f 100644 --- a/platformio.ini +++ b/platformio.ini @@ -142,7 +142,8 @@ platform_packages = framework = espidf lib_deps = ${common:idf.lib_deps} - droscy/esp_wireguard@0.4.2 ; wireguard + droscy/esp_wireguard@0.4.2 ; wireguard + kahrendt/ESPMicroSpeechFeatures@1.0.0 ; micro_wake_word build_flags = ${common:idf.build_flags} -Wno-nonnull-compare diff --git a/script/test_build_components b/script/test_build_components index 7789f84581..6157db4d40 100755 --- a/script/test_build_components +++ b/script/test_build_components @@ -7,12 +7,13 @@ set -e # - `c` - Component folder name to test. Default `*`. esphome_command="compile" target_component="*" -while getopts e:c: flag +while getopts e:c:t: flag do case $flag in e) esphome_command=${OPTARG};; c) target_component=${OPTARG};; - \?) echo "Usage: $0 [-e ] [-c ]" 1>&2; exit 1;; + t) requested_target_platform=${OPTARG};; + \?) echo "Usage: $0 [-e ] [-c ] [-t ]" 1>&2; exit 1;; esac done @@ -23,6 +24,10 @@ if ! [ -d "./tests/test_build_components/build" ]; then fi start_esphome() { + if [ -n "$requested_target_platform" ] && [ "$requested_target_platform" != "$target_platform" ]; then + echo "Skiping $target_platform" + return + fi # create dynamic yaml file in `build` folder. # `./tests/test_build_components/build/[target_component].[test_name].[target_platform_with_version].yaml` component_test_file="./tests/test_build_components/build/$target_component.$test_name.$target_platform_with_version.yaml" diff --git a/tests/components/micro_wake_word/common.yaml b/tests/components/micro_wake_word/common.yaml index c0f3593cc6..8bd7345307 100644 --- a/tests/components/micro_wake_word/common.yaml +++ b/tests/components/micro_wake_word/common.yaml @@ -10,6 +10,10 @@ microphone: pdm: true micro_wake_word: - model: hey_jarvis on_wake_word_detected: - logger.log: "Wake word detected" + models: + - model: hey_jarvis + probability_cutoff: 0.7 + - model: okay_nabu + sliding_window_size: 5 diff --git a/tests/components/micro_wake_word/test.esp32-idf.yaml b/tests/components/micro_wake_word/test.esp32-idf.yaml new file mode 100644 index 0000000000..dade44d145 --- /dev/null +++ b/tests/components/micro_wake_word/test.esp32-idf.yaml @@ -0,0 +1 @@ +<<: !include common.yaml diff --git a/tests/components/uart/test.host.yaml b/tests/components/uart/test.host.yaml new file mode 100644 index 0000000000..63f0ade084 --- /dev/null +++ b/tests/components/uart/test.host.yaml @@ -0,0 +1,13 @@ +esphome: + on_boot: + then: + - uart.write: 'Hello World' + - uart.write: [0x00, 0x20, 0x42] + +uart: + - id: uart_uart + port: "/dev/ttyS0" + baud_rate: 9600 + data_bits: 8 + parity: EVEN + stop_bits: 2 diff --git a/tests/components/wifi/common-eap.yaml b/tests/components/wifi/common-eap.yaml new file mode 100644 index 0000000000..779cd6b49a --- /dev/null +++ b/tests/components/wifi/common-eap.yaml @@ -0,0 +1,7 @@ +wifi: + networks: + - ssid: MySSID + eap: + username: username + password: password + identity: identity diff --git a/tests/components/wifi/test-eap.esp32-ard.yaml b/tests/components/wifi/test-eap.esp32-ard.yaml index 779cd6b49a..9177e5de10 100644 --- a/tests/components/wifi/test-eap.esp32-ard.yaml +++ b/tests/components/wifi/test-eap.esp32-ard.yaml @@ -1,7 +1 @@ -wifi: - networks: - - ssid: MySSID - eap: - username: username - password: password - identity: identity +<<: !include common-eap.yaml diff --git a/tests/components/wifi/test-eap.esp32-idf.yaml b/tests/components/wifi/test-eap.esp32-idf.yaml new file mode 100644 index 0000000000..9177e5de10 --- /dev/null +++ b/tests/components/wifi/test-eap.esp32-idf.yaml @@ -0,0 +1 @@ +<<: !include common-eap.yaml