Merge remote-tracking branch 'origin/dev' into mdev

This commit is contained in:
Ewowi
2022-10-01 12:05:49 +02:00
19 changed files with 604 additions and 272 deletions

View File

@@ -293,6 +293,7 @@ lib_deps =
https://github.com/Makuna/NeoPixelBus.git#master @ 2.7.0
https://github.com/pbolduc/AsyncTCP.git @ 1.2.0
# ------------------------------------------------------------------------------
# WLED BUILDS
# ------------------------------------------------------------------------------

View File

@@ -114,8 +114,8 @@ class Animated_Staircase : public Usermod {
// We may need to copy mode and colors from segment 0 to make sure
// changes are propagated even when the config is changed during a wipe
// segments->mode = mainsegment.mode;
// segments->colors[0] = mainsegment.colors[0];
// seg.setMode(mainsegment.mode);
// seg.setColor(0, mainsegment.colors[0]);
} else {
seg.setOption(SEG_OPTION_ON, false);
}

View File

@@ -531,11 +531,11 @@ public:
for (byte i=0; i<strip.getSegmentsNum(); i++) {
Segment& seg = strip.getSegment(i);
if (!seg.isActive()) continue;
strip.setMode(i, effectCurrent);
seg.setMode(effectCurrent);
}
} else {
//Segment& seg = strip.getSegment(strip.getMainSegmentId());
strip.setMode(strip.getMainSegmentId(), effectCurrent);
Segment& seg = strip.getSegment(strip.getMainSegmentId());
seg.setMode(effectCurrent);
}
lampUdated();
#ifdef USERMOD_FOUR_LINE_DISPLAY
@@ -661,11 +661,11 @@ public:
for (byte i=0; i<strip.getSegmentsNum(); i++) {
Segment& seg = strip.getSegment(i);
if (!seg.isActive()) continue;
seg.palette = effectPalette;
seg.setPalette(effectPalette);
}
} else {
Segment& seg = strip.getSegment(strip.getMainSegmentId());
seg.palette = effectPalette;
seg.setPalette(effectPalette);
}
lampUdated();
#ifdef USERMOD_FOUR_LINE_DISPLAY

View File

@@ -1,11 +1,12 @@
# Word Clock Usermod V2
This usermod can be used to drive a wordclock with a 11x10 pixel matrix with WLED. There are also 4 additional dots for the minutes.
The visualisation is desribed in 4 mask with LED numbers (single dots for minutes, minutes, hours and "clock/Uhr").
There are 2 parameters to chnage the behaviour:
The visualisation is desribed in 4 mask with LED numbers (single dots for minutes, minutes, hours and "clock/Uhr"). The index of the LEDs in the masks always starts with the index 0, even if the ledOffset is not 0.
There are 3 parameters to change the behaviour:
active: enable/disable usermod
diplayItIs: enable/disable display of "Es ist" on the clock.
diplayItIs: enable/disable display of "Es ist" on the clock
ledOffset: number of LEDs before the wordclock LEDs
## Installation

View File

@@ -23,6 +23,7 @@ class WordClockUsermod : public Usermod
// set your config variables to their boot default value (this can also be done in readFromConfig() or a constructor if you prefer)
bool usermodActive = false;
bool displayItIs = false;
int ledOffset = 100;
// defines for mask sizes
#define maskSizeLeds 114
@@ -358,6 +359,7 @@ class WordClockUsermod : public Usermod
JsonObject top = root.createNestedObject("WordClockUsermod");
top["active"] = usermodActive;
top["displayItIs"] = displayItIs;
top["ledOffset"] = ledOffset;
}
/*
@@ -386,6 +388,7 @@ class WordClockUsermod : public Usermod
configComplete &= getJsonValue(top["active"], usermodActive);
configComplete &= getJsonValue(top["displayItIs"], displayItIs);
configComplete &= getJsonValue(top["ledOffset"], ledOffset);
return configComplete;
}
@@ -407,7 +410,7 @@ class WordClockUsermod : public Usermod
if (maskLedsOn[x] == 0)
{
// set pixel off
strip.setPixelColor(x, RGBW32(0,0,0,0));
strip.setPixelColor(x + ledOffset, RGBW32(0,0,0,0));
}
}
}

View File

@@ -401,6 +401,7 @@ void Segment::setOption(uint8_t n, bool val) {
}
void Segment::setMode(uint8_t fx, bool loadDefaults) {
// if we have a valid mode & is not reserved
if (fx < strip.getModeCount() && strncmp_P("RSVD", strip.getModeData(fx), 4)) {
if (fx != mode) {
startTransition(strip.getTransition()); // set effect transitions
@@ -433,9 +434,11 @@ void Segment::setMode(uint8_t fx, bool loadDefaults) {
}
void Segment::setPalette(uint8_t pal) {
if (pal != palette) {
if (strip.paletteFade && !transitional) startTransition(strip.getTransition());
palette = pal;
if (pal < strip.getPaletteCount()) {
if (pal != palette) {
if (strip.paletteFade) startTransition(strip.getTransition());
palette = pal;
}
}
}

View File

@@ -377,6 +377,7 @@ bool deserializeConfig(JsonObject doc, bool fromFS) {
CJSON(e131Universe, if_live_dmx[F("uni")]);
CJSON(e131SkipOutOfSequence, if_live_dmx[F("seqskip")]);
CJSON(DMXAddress, if_live_dmx[F("addr")]);
if (!DMXAddress || DMXAddress > 510) DMXAddress = 1;
CJSON(DMXMode, if_live_dmx["mode"]);
tdd = if_live[F("timeout")] | -1;

View File

@@ -13,7 +13,7 @@
}
function H(){window.open("https://kno.wled.ge/interfaces/udp-notifier/");}
function B(){window.open("/settings","_self");}
function adj(){if (d.Sf.DI.value == 6454) {if (d.Sf.DA.value == 1) d.Sf.DA.value = 0; if (d.Sf.EU.value == 1) d.Sf.EU.value = 0;}
function adj(){if (d.Sf.DI.value == 6454) {if (d.Sf.EU.value == 1) d.Sf.EU.value = 0;}
else if (d.Sf.DI.value == 5568) {if (d.Sf.DA.value == 0) d.Sf.DA.value = 1; if (d.Sf.EU.value == 0) d.Sf.EU.value = 1;} }
// https://www.educative.io/edpresso/how-to-dynamically-load-a-js-file-in-javascript
function loadJS(FILE_URL, async = true) {
@@ -147,7 +147,7 @@ Multicast: <input type="checkbox" name="EM"><br>
Start universe: <input name="EU" type="number" min="0" max="63999" required><br>
<i>Reboot required.</i> Check out <a href="https://github.com/LedFx/LedFx" target="_blank">LedFx</a>!<br>
Skip out-of-sequence packets: <input type="checkbox" name="ES"><br>
DMX start address: <input name="DA" type="number" min="0" max="510" required><br>
DMX start address: <input name="DA" type="number" min="1" max="510" required><br>
DMX mode:
<select name=DM>
<option value=0>Disabled</option>

View File

@@ -60,6 +60,10 @@ void handleE131Packet(e131_packet_t* p, IPAddress clientIP, byte protocol){
if (protocol == P_ARTNET)
{
if (p->art_opcode == ARTNET_OPCODE_OPPOLL) {
handleArtnetPollReply(clientIP);
return;
}
uni = p->art_universe;
dmxChannels = htons(p->art_length);
e131_data = p->art_data;
@@ -86,14 +90,14 @@ void handleE131Packet(e131_packet_t* p, IPAddress clientIP, byte protocol){
#endif
// only listen for universes we're handling & allocated memory
if (uni >= (e131Universe + E131_MAX_UNIVERSE_COUNT)) return;
if (uni < e131Universe || uni >= (e131Universe + E131_MAX_UNIVERSE_COUNT)) return;
uint8_t previousUniverses = uni - e131Universe;
if (e131SkipOutOfSequence)
if (seq < e131LastSequenceNumber[uni-e131Universe] && seq > 20 && e131LastSequenceNumber[uni-e131Universe] < 250){
if (seq < e131LastSequenceNumber[previousUniverses] && seq > 20 && e131LastSequenceNumber[previousUniverses] < 250){
DEBUG_PRINT("skipping E1.31 frame (last seq=");
DEBUG_PRINT(e131LastSequenceNumber[uni-e131Universe]);
DEBUG_PRINT(e131LastSequenceNumber[previousUniverses]);
DEBUG_PRINT(", current seq=");
DEBUG_PRINT(seq);
DEBUG_PRINT(", universe=");
@@ -101,15 +105,23 @@ void handleE131Packet(e131_packet_t* p, IPAddress clientIP, byte protocol){
DEBUG_PRINTLN(")");
return;
}
e131LastSequenceNumber[uni-e131Universe] = seq;
e131LastSequenceNumber[previousUniverses] = seq;
// update status info
realtimeIP = clientIP;
byte wChannel = 0;
uint16_t totalLen = strip.getLengthTotal();
uint16_t availDMXLen = dmxChannels - DMXAddress + 1;
uint16_t availDMXLen = 0;
uint16_t dataOffset = DMXAddress;
// For legacy DMX start address 0 the available DMX length offset is 0
const uint16_t dmxLenOffset = (DMXAddress == 0) ? 0 : 1;
// Check if DMX start address fits in available channels
if (dmxChannels >= DMXAddress) {
availDMXLen = (dmxChannels - DMXAddress) + dmxLenOffset;
}
// DMX data in Art-Net packet starts at index 0, for E1.31 at index 1
if (protocol == P_ARTNET && dataOffset > 0) {
dataOffset--;
@@ -123,8 +135,11 @@ void handleE131Packet(e131_packet_t* p, IPAddress clientIP, byte protocol){
case DMX_MODE_SINGLE_RGB: // RGB only
if (uni != e131Universe) return;
if (availDMXLen < 3) return;
realtimeLock(realtimeTimeoutMs, mde);
if (realtimeOverride && !(realtimeMode && useMainSegmentOnly)) return;
wChannel = (availDMXLen > 3) ? e131_data[dataOffset+3] : 0;
for (uint16_t i = 0; i < totalLen; i++)
setRealtimePixel(i, e131_data[dataOffset+0], e131_data[dataOffset+1], e131_data[dataOffset+2], wChannel);
@@ -133,14 +148,16 @@ void handleE131Packet(e131_packet_t* p, IPAddress clientIP, byte protocol){
case DMX_MODE_SINGLE_DRGB: // Dimmer + RGB
if (uni != e131Universe) return;
if (availDMXLen < 4) return;
realtimeLock(realtimeTimeoutMs, mde);
if (realtimeOverride && !(realtimeMode && useMainSegmentOnly)) return;
wChannel = (availDMXLen > 4) ? e131_data[dataOffset+4] : 0;
if (DMXOldDimmer != e131_data[dataOffset+0]) {
DMXOldDimmer = e131_data[dataOffset+0];
if (bri != e131_data[dataOffset+0]) {
bri = e131_data[dataOffset+0];
strip.setBrightness(bri, true);
}
for (uint16_t i = 0; i < totalLen; i++)
setRealtimePixel(i, e131_data[dataOffset+1], e131_data[dataOffset+2], e131_data[dataOffset+3], wChannel);
break;
@@ -152,12 +169,12 @@ void handleE131Packet(e131_packet_t* p, IPAddress clientIP, byte protocol){
applyPreset(e131_data[dataOffset+0], CALL_MODE_NOTIFICATION);
return;
}
if (DMXOldDimmer != e131_data[dataOffset+0]) {
DMXOldDimmer = e131_data[dataOffset+0];
if (bri != e131_data[dataOffset+0]) {
bri = e131_data[dataOffset+0];
}
if (e131_data[dataOffset+1] < strip.getModeCount())
effectCurrent = e131_data[dataOffset+ 1];
effectCurrent = e131_data[dataOffset+ 1];
effectSpeed = e131_data[dataOffset+ 2]; // flickers
effectIntensity = e131_data[dataOffset+ 3];
effectPalette = e131_data[dataOffset+ 4];
@@ -181,19 +198,19 @@ void handleE131Packet(e131_packet_t* p, IPAddress clientIP, byte protocol){
case DMX_MODE_MULTIPLE_RGB:
case DMX_MODE_MULTIPLE_RGBW:
{
realtimeLock(realtimeTimeoutMs, mde);
bool is4Chan = (DMXMode == DMX_MODE_MULTIPLE_RGBW);
const uint16_t dmxChannelsPerLed = is4Chan ? 4 : 3;
const uint16_t ledsPerUniverse = is4Chan ? MAX_4_CH_LEDS_PER_UNIVERSE : MAX_3_CH_LEDS_PER_UNIVERSE;
if (realtimeOverride && !(realtimeMode && useMainSegmentOnly)) return;
uint8_t stripBrightness = bri;
uint16_t previousLeds, dmxOffset, ledsTotal;
if (previousUniverses == 0) {
if (availDMXLen < 1) return;
dmxOffset = dataOffset;
previousLeds = 0;
// First DMX address is dimmer in DMX_MODE_MULTIPLE_DRGB mode.
if (DMXMode == DMX_MODE_MULTIPLE_DRGB) {
strip.setBrightness(e131_data[dmxOffset++], true);
stripBrightness = e131_data[dmxOffset++];
ledsTotal = (availDMXLen - 1) / dmxChannelsPerLed;
} else {
ledsTotal = availDMXLen / dmxChannelsPerLed;
@@ -201,11 +218,31 @@ void handleE131Packet(e131_packet_t* p, IPAddress clientIP, byte protocol){
} else {
// All subsequent universes start at the first channel.
dmxOffset = (protocol == P_ARTNET) ? 0 : 1;
uint16_t dimmerOffset = (DMXMode == DMX_MODE_MULTIPLE_DRGB) ? 1 : 0;
uint16_t ledsInFirstUniverse = ((MAX_CHANNELS_PER_UNIVERSE - DMXAddress + 1) - dimmerOffset) / dmxChannelsPerLed;
const uint16_t dimmerOffset = (DMXMode == DMX_MODE_MULTIPLE_DRGB) ? 1 : 0;
uint16_t ledsInFirstUniverse = (((MAX_CHANNELS_PER_UNIVERSE - DMXAddress) + dmxLenOffset) - dimmerOffset) / dmxChannelsPerLed;
previousLeds = ledsInFirstUniverse + (previousUniverses - 1) * ledsPerUniverse;
ledsTotal = previousLeds + (dmxChannels / dmxChannelsPerLed);
}
// All LEDs already have values
if (previousLeds >= totalLen) {
return;
}
realtimeLock(realtimeTimeoutMs, mde);
if (realtimeOverride && !(realtimeMode && useMainSegmentOnly)) return;
if (ledsTotal > totalLen) {
ledsTotal = totalLen;
}
if (DMXMode == DMX_MODE_MULTIPLE_DRGB && previousUniverses == 0) {
if (bri != stripBrightness) {
bri = stripBrightness;
strip.setBrightness(bri, true);
}
}
if (!is4Chan) {
for (uint16_t i = previousLeds; i < ledsTotal; i++) {
setRealtimePixel(i, e131_data[dmxOffset], e131_data[dmxOffset+1], e131_data[dmxOffset+2], 0);
@@ -227,3 +264,197 @@ void handleE131Packet(e131_packet_t* p, IPAddress clientIP, byte protocol){
e131NewData = true;
}
void handleArtnetPollReply(IPAddress ipAddress) {
ArtPollReply artnetPollReply;
prepareArtnetPollReply(&artnetPollReply);
uint16_t startUniverse = e131Universe;
uint16_t endUniverse = e131Universe;
switch (DMXMode) {
case DMX_MODE_DISABLED:
return; // nothing to do
break;
case DMX_MODE_SINGLE_RGB:
case DMX_MODE_SINGLE_DRGB:
case DMX_MODE_EFFECT:
break; // 1 universe is enough
case DMX_MODE_MULTIPLE_DRGB:
case DMX_MODE_MULTIPLE_RGB:
case DMX_MODE_MULTIPLE_RGBW:
{
bool is4Chan = (DMXMode == DMX_MODE_MULTIPLE_RGBW);
const uint16_t dmxChannelsPerLed = is4Chan ? 4 : 3;
const uint16_t dimmerOffset = (DMXMode == DMX_MODE_MULTIPLE_DRGB) ? 1 : 0;
const uint16_t dmxLenOffset = (DMXAddress == 0) ? 0 : 1; // For legacy DMX start address 0
const uint16_t ledsInFirstUniverse = (((MAX_CHANNELS_PER_UNIVERSE - DMXAddress) + dmxLenOffset) - dimmerOffset) / dmxChannelsPerLed;
const uint16_t totalLen = strip.getLengthTotal();
if (totalLen > ledsInFirstUniverse) {
const uint16_t ledsPerUniverse = is4Chan ? MAX_4_CH_LEDS_PER_UNIVERSE : MAX_3_CH_LEDS_PER_UNIVERSE;
const uint16_t remainLED = totalLen - ledsInFirstUniverse;
endUniverse += (remainLED / ledsPerUniverse);
if ((remainLED % ledsPerUniverse) > 0) {
endUniverse++;
}
if ((endUniverse - startUniverse) > E131_MAX_UNIVERSE_COUNT) {
endUniverse = startUniverse + E131_MAX_UNIVERSE_COUNT - 1;
}
}
break;
}
default:
DEBUG_PRINTLN(F("unknown E1.31 DMX mode"));
return; // nothing to do
break;
}
for (uint16_t i = startUniverse; i <= endUniverse; ++i) {
sendArtnetPollReply(&artnetPollReply, ipAddress, i);
}
}
void prepareArtnetPollReply(ArtPollReply *reply) {
// Art-Net
reply->reply_id[0] = 0x41;
reply->reply_id[1] = 0x72;
reply->reply_id[2] = 0x74;
reply->reply_id[3] = 0x2d;
reply->reply_id[4] = 0x4e;
reply->reply_id[5] = 0x65;
reply->reply_id[6] = 0x74;
reply->reply_id[7] = 0x00;
reply->reply_opcode = ARTNET_OPCODE_OPPOLLREPLY;
IPAddress localIP = Network.localIP();
for (uint8_t i = 0; i < 4; i++) {
reply->reply_ip[i] = localIP[i];
}
reply->reply_port = ARTNET_DEFAULT_PORT;
char * numberEnd = versionString;
reply->reply_version_h = (uint8_t)strtol(numberEnd, &numberEnd, 10);
numberEnd++;
reply->reply_version_l = (uint8_t)strtol(numberEnd, &numberEnd, 10);
// Switch values depend on universe, set before sending
reply->reply_net_sw = 0x00;
reply->reply_sub_sw = 0x00;
reply->reply_oem_h = 0x00; // TODO add assigned oem code
reply->reply_oem_l = 0x00;
reply->reply_ubea_ver = 0x00;
// Indicators in Normal Mode
// All or part of Port-Address programmed by network or Web browser
reply->reply_status_1 = 0xE0;
reply->reply_esta_man = 0x0000;
strlcpy((char *)(reply->reply_short_name), serverDescription, 18);
strlcpy((char *)(reply->reply_long_name), serverDescription, 64);
reply->reply_node_report[0] = '\0';
reply->reply_num_ports_h = 0x00;
reply->reply_num_ports_l = 0x01; // One output port
reply->reply_port_types[0] = 0x80; // Output DMX data
reply->reply_port_types[1] = 0x00;
reply->reply_port_types[2] = 0x00;
reply->reply_port_types[3] = 0x00;
// No inputs
reply->reply_good_input[0] = 0x00;
reply->reply_good_input[1] = 0x00;
reply->reply_good_input[2] = 0x00;
reply->reply_good_input[3] = 0x00;
// One output
reply->reply_good_output_a[0] = 0x80; // Data is being transmitted
reply->reply_good_output_a[1] = 0x00;
reply->reply_good_output_a[2] = 0x00;
reply->reply_good_output_a[3] = 0x00;
// Values depend on universe, set before sending
reply->reply_sw_in[0] = 0x00;
reply->reply_sw_in[1] = 0x00;
reply->reply_sw_in[2] = 0x00;
reply->reply_sw_in[3] = 0x00;
// Values depend on universe, set before sending
reply->reply_sw_out[0] = 0x00;
reply->reply_sw_out[1] = 0x00;
reply->reply_sw_out[2] = 0x00;
reply->reply_sw_out[3] = 0x00;
reply->reply_sw_video = 0x00;
reply->reply_sw_macro = 0x00;
reply->reply_sw_remote = 0x00;
reply->reply_spare[0] = 0x00;
reply->reply_spare[1] = 0x00;
reply->reply_spare[2] = 0x00;
// A DMX to / from Art-Net device
reply->reply_style = 0x00;
Network.localMAC(reply->reply_mac);
for (uint8_t i = 0; i < 4; i++) {
reply->reply_bind_ip[i] = localIP[i];
}
reply->reply_bind_index = 1;
// Product supports web browser configuration
// Nodes IP is DHCP or manually configured
// Node is DHCP capable
// Node supports 15 bit Port-Address (Art-Net 3 or 4)
// Node is able to switch between ArtNet and sACN
reply->reply_status_2 = (staticIP[0] == 0) ? 0x1F : 0x1D;
// RDM is disabled
// Output style is continuous
reply->reply_good_output_b[0] = 0xC0;
reply->reply_good_output_b[1] = 0xC0;
reply->reply_good_output_b[2] = 0xC0;
reply->reply_good_output_b[3] = 0xC0;
// Fail-over state: Hold last state
// Node does not support fail-over
reply->reply_status_3 = 0x00;
for (uint8_t i = 0; i < 21; i++) {
reply->reply_filler[i] = 0x00;
}
}
void sendArtnetPollReply(ArtPollReply *reply, IPAddress ipAddress, uint16_t portAddress) {
reply->reply_net_sw = (uint8_t)((portAddress >> 8) & 0x007F);
reply->reply_sub_sw = (uint8_t)((portAddress >> 4) & 0x000F);
reply->reply_sw_out[0] = (uint8_t)(portAddress & 0x000F);
sprintf((char *)reply->reply_node_report, "#0001 [%04u] OK - WLED v" TOSTRING(WLED_VERSION), pollReplyCount);
if (pollReplyCount < 9999) {
pollReplyCount++;
} else {
pollReplyCount = 0;
}
notifierUdp.beginPacket(ipAddress, ARTNET_DEFAULT_PORT);
notifierUdp.write(reply->raw, sizeof(ArtPollReply));
notifierUdp.endPacket();
reply->reply_bind_index++;
}

View File

@@ -82,6 +82,9 @@ void handleDMX();
//e131.cpp
void handleE131Packet(e131_packet_t* p, IPAddress clientIP, byte protocol);
void handleArtnetPollReply(IPAddress ipAddress);
void prepareArtnetPollReply(ArtPollReply* reply);
void sendArtnetPollReply(ArtPollReply* reply, IPAddress ipAddress, uint16_t portAddress);
//file.cpp
bool handleFileRead(AsyncWebServerRequest*, String path);

View File

@@ -1028,206 +1028,205 @@ const uint8_t PAGE_settings_ui[] PROGMEM = {
// Autogenerated from wled00/data/settings_sync.htm, do not edit!!
const uint16_t PAGE_settings_sync_length = 3153;
const uint16_t PAGE_settings_sync_length = 3146;
const uint8_t PAGE_settings_sync[] PROGMEM = {
0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x13, 0x9d, 0x5a, 0x6d, 0x77, 0xda, 0xb8,
0x12, 0xfe, 0xee, 0x5f, 0xa1, 0xf8, 0xc3, 0x2e, 0x6c, 0x08, 0x18, 0x12, 0xd2, 0x94, 0x62, 0xf7,
0x12, 0xfe, 0xee, 0x5f, 0xa1, 0xfa, 0xc3, 0x2e, 0x6c, 0x08, 0x18, 0x12, 0xd2, 0x94, 0x60, 0xf7,
0x86, 0x90, 0x26, 0xec, 0x36, 0x0d, 0x85, 0x64, 0x5f, 0xce, 0xb9, 0xe7, 0xec, 0x11, 0xb6, 0x00,
0x25, 0xb6, 0xe5, 0xb5, 0xe5, 0xbc, 0x9c, 0x6e, 0xff, 0xfb, 0x9d, 0x91, 0x6c, 0x03, 0x06, 0x02,
0xbd, 0x1f, 0x4a, 0x6c, 0x69, 0x66, 0x34, 0x9a, 0x97, 0x67, 0x46, 0x72, 0xbb, 0x07, 0xfd, 0xdb,
0x8b, 0xbb, 0xbf, 0x86, 0x97, 0x64, 0x2e, 0x03, 0xdf, 0xe9, 0xe2, 0x2f, 0xf1, 0x69, 0x38, 0xb3,
0x4d, 0x16, 0x9a, 0xf0, 0xce, 0xa8, 0xe7, 0x74, 0x03, 0x26, 0x29, 0x09, 0x69, 0xc0, 0x6c, 0xf3,
0x89, 0xb3, 0xe7, 0x48, 0xc4, 0xd2, 0x24, 0xae, 0x08, 0x25, 0x0b, 0xa5, 0x6d, 0x3e, 0x73, 0x4f,
0xce, 0xed, 0xb6, 0x65, 0x99, 0x8e, 0xa1, 0x49, 0x8d, 0xd2, 0x9c, 0xc7, 0x9e, 0xb8, 0xcb, 0x8e,
0xd4, 0x4b, 0x8d, 0x87, 0x5c, 0x72, 0xea, 0x1f, 0x25, 0x2e, 0xf5, 0x99, 0xdd, 0xac, 0x05, 0xf4,
0x85, 0x07, 0x69, 0x50, 0xbc, 0xa7, 0x09, 0x8b, 0xd5, 0x0b, 0x9d, 0xc0, 0x7b, 0x28, 0x4c, 0x62,
0x94, 0x96, 0xce, 0x14, 0x72, 0xe7, 0x34, 0x4e, 0x18, 0x2c, 0x92, 0xca, 0xe9, 0xd1, 0x19, 0x8c,
0x4a, 0x2e, 0x7d, 0xe6, 0x8c, 0x5f, 0x43, 0x97, 0x8c, 0x99, 0x94, 0x3c, 0x9c, 0x25, 0xdd, 0x86,
0x1e, 0xec, 0x26, 0x6e, 0xcc, 0x23, 0xe9, 0x18, 0x4f, 0x34, 0x26, 0xbe, 0x70, 0x79, 0x54, 0xf3,
0x6c, 0x4f, 0xb8, 0x69, 0x00, 0x6a, 0xd6, 0x60, 0xc0, 0x3e, 0x68, 0x7e, 0x98, 0xa6, 0xa1, 0x2b,
0xb9, 0x08, 0xc9, 0x6c, 0xe0, 0x55, 0x58, 0xf5, 0x5b, 0xcc, 0x64, 0x1a, 0x87, 0xc4, 0xab, 0xcf,
0x98, 0xbc, 0xf4, 0x19, 0x92, 0xf6, 0x5e, 0xd5, 0xd4, 0xf7, 0x82, 0xf4, 0xba, 0x52, 0xfd, 0xf6,
0xcc, 0x43, 0x4f, 0x3c, 0xd7, 0x45, 0xc4, 0xc2, 0x8a, 0x39, 0x97, 0x32, 0x4a, 0x3a, 0x8d, 0xc6,
0x63, 0x28, 0xea, 0xcf, 0x3e, 0x43, 0xe6, 0x06, 0x07, 0x6b, 0xc4, 0x53, 0xea, 0xb2, 0xa4, 0x91,
0x7a, 0xd1, 0x51, 0x28, 0x24, 0x9f, 0x72, 0x16, 0x37, 0xcc, 0x25, 0x41, 0xbd, 0xb2, 0xa0, 0x46,
0x92, 0xed, 0xc1, 0xac, 0x99, 0x7f, 0x27, 0xcc, 0x9f, 0x2e, 0x53, 0x53, 0xef, 0x01, 0xe8, 0x4f,
0x4f, 0xda, 0x27, 0xb6, 0xed, 0xd5, 0xc7, 0xd3, 0x7a, 0x7f, 0x50, 0x7f, 0xa2, 0x7e, 0xca, 0x3e,
0x56, 0x9a, 0xf9, 0xc8, 0xb9, 0x1e, 0xf9, 0xe9, 0xa7, 0xca, 0xca, 0xbb, 0x6d, 0x55, 0x6b, 0x39,
0xcd, 0xe5, 0xfd, 0x2a, 0x4d, 0xfe, 0x0e, 0x34, 0xd5, 0x4e, 0xbb, 0x7d, 0x7a, 0x56, 0x92, 0x0e,
0x74, 0xd6, 0x2e, 0xf1, 0xcd, 0x6a, 0xcd, 0xda, 0x25, 0xbe, 0x59, 0x5d, 0xda, 0x8b, 0x2f, 0xa8,
0xf7, 0xeb, 0xb8, 0xc2, 0x6a, 0xd2, 0x3e, 0xb0, 0xaa, 0xdf, 0x7c, 0x26, 0x89, 0x0f, 0xfc, 0x6e,
0xcc, 0xa8, 0x64, 0x99, 0xdd, 0x2b, 0xa6, 0x76, 0xa0, 0x59, 0xfd, 0xe0, 0xd7, 0xc1, 0x30, 0xe7,
0x52, 0xc6, 0x7c, 0x92, 0x4a, 0x06, 0x13, 0xb1, 0x6b, 0xd6, 0x58, 0xb5, 0x56, 0x1e, 0x97, 0xaf,
0x11, 0x03, 0xd3, 0x49, 0xf6, 0x22, 0x1b, 0x0f, 0xf4, 0x89, 0xe6, 0x02, 0xd6, 0x08, 0x69, 0x02,
0x11, 0x63, 0xd6, 0x64, 0xb5, 0xe6, 0xd5, 0x27, 0xc2, 0x7b, 0xad, 0xd3, 0x08, 0x1c, 0xe0, 0x5d,
0xcc, 0xb9, 0xef, 0x55, 0x7c, 0xa4, 0xa7, 0x9e, 0x77, 0xf9, 0x04, 0x5a, 0x7c, 0xe6, 0x09, 0x84,
0x35, 0x8b, 0x2b, 0x26, 0xea, 0x6c, 0xd6, 0x2a, 0x55, 0xdb, 0xf9, 0x76, 0xc5, 0xe4, 0xef, 0x95,
0x6a, 0x0d, 0x22, 0xee, 0x77, 0xea, 0x57, 0xaa, 0xdf, 0x37, 0x33, 0xb0, 0x38, 0x16, 0x31, 0xe8,
0x09, 0x0c, 0x90, 0x1c, 0x89, 0xf0, 0x59, 0xdd, 0x17, 0xb3, 0x8a, 0x79, 0x89, 0xe3, 0x24, 0xb3,
0x02, 0x78, 0x9b, 0x4c, 0xb9, 0xcf, 0xd4, 0x7e, 0x20, 0x1b, 0x62, 0xd8, 0xf7, 0xe7, 0x6c, 0x5c,
0x4c, 0x31, 0xe3, 0xa6, 0x7c, 0x96, 0xc6, 0x54, 0x99, 0x4d, 0xef, 0x87, 0x4c, 0x29, 0xc7, 0x28,
0xfb, 0x6f, 0x38, 0x08, 0x5d, 0x11, 0x44, 0x60, 0x3d, 0x46, 0x22, 0x3a, 0x63, 0xc4, 0xa3, 0x92,
0x1e, 0x40, 0xcc, 0x2c, 0x59, 0xfa, 0xd3, 0x05, 0x04, 0xcd, 0x54, 0xc4, 0x95, 0x07, 0xdb, 0xfa,
0xf0, 0xd0, 0x3d, 0xfb, 0xf0, 0x70, 0x78, 0x58, 0xc5, 0x60, 0x37, 0xaf, 0xcc, 0xc3, 0xca, 0xc3,
0x21, 0xb8, 0xa5, 0xee, 0xce, 0x99, 0xfb, 0xc8, 0x3c, 0x5b, 0x0f, 0x8f, 0xcd, 0xaa, 0x76, 0x99,
0xe3, 0x3c, 0xfc, 0xd4, 0xac, 0xa9, 0xc1, 0xd1, 0x16, 0xda, 0xd1, 0x0a, 0xed, 0x62, 0xd5, 0x2b,
0x5c, 0x15, 0xf3, 0x0e, 0xc2, 0x0a, 0x7c, 0x6c, 0xd5, 0x7c, 0x1b, 0x72, 0xad, 0xa4, 0x05, 0x3b,
0xb4, 0x37, 0x2b, 0xf2, 0x8b, 0x5f, 0x93, 0xd9, 0xdc, 0x68, 0xc3, 0x9c, 0xff, 0x8b, 0xdd, 0xfa,
0x50, 0xd2, 0xd5, 0x66, 0xb5, 0x92, 0x46, 0xb6, 0x5c, 0xa8, 0x33, 0x1e, 0x16, 0xea, 0xac, 0xc4,
0xb6, 0x96, 0xf2, 0x12, 0x01, 0x4f, 0x22, 0x5f, 0xc1, 0x3f, 0x1e, 0x4f, 0x22, 0x9f, 0xbe, 0xda,
0xcc, 0xb1, 0x3e, 0x9a, 0xa1, 0x08, 0x99, 0xd9, 0x31, 0x27, 0x00, 0x15, 0x8f, 0xe0, 0x1e, 0xc7,
0x2a, 0x62, 0x7a, 0x98, 0x2f, 0xba, 0x64, 0xe8, 0x3c, 0x18, 0xbe, 0x25, 0xcf, 0x5c, 0xba, 0xf3,
0x4a, 0x84, 0x48, 0x35, 0x80, 0x30, 0x5e, 0x61, 0xa9, 0x56, 0xbf, 0xb9, 0x34, 0x61, 0x04, 0x13,
0xad, 0xb3, 0xa2, 0x8b, 0x8d, 0x43, 0x1f, 0x26, 0x90, 0x01, 0x8f, 0x1f, 0x14, 0x09, 0x66, 0x7a,
0x89, 0x04, 0x87, 0x96, 0x49, 0x4e, 0xac, 0x93, 0xb2, 0x14, 0x1c, 0xfa, 0x8e, 0xfb, 0xad, 0xa1,
0xe7, 0x97, 0xd4, 0x03, 0xcd, 0x4c, 0x0c, 0xb4, 0x8e, 0x69, 0xdb, 0x19, 0xe8, 0xc0, 0xc6, 0x54,
0x5c, 0xd5, 0xa3, 0x58, 0x48, 0xe1, 0x0a, 0x1f, 0x36, 0xa8, 0x70, 0xd1, 0xaa, 0x55, 0x14, 0x60,
0xda, 0x48, 0xe1, 0x8f, 0xa5, 0x88, 0x21, 0xba, 0x10, 0x12, 0x07, 0x92, 0x05, 0x98, 0x09, 0xee,
0x00, 0x6c, 0x56, 0xfd, 0xf7, 0xdf, 0x8c, 0x0c, 0xf8, 0x83, 0x08, 0x02, 0xf7, 0x13, 0xc8, 0x27,
0x37, 0xc2, 0x63, 0x75, 0x32, 0xf4, 0x19, 0x6a, 0xc8, 0x10, 0x06, 0xc9, 0x1f, 0x9f, 0x2f, 0xfb,
0x64, 0x30, 0x3c, 0xc0, 0x4c, 0x5c, 0x96, 0x98, 0xac, 0x4a, 0xac, 0x29, 0x69, 0xd5, 0x2a, 0x52,
0x29, 0x7c, 0x40, 0xf1, 0x1f, 0x15, 0xbc, 0x02, 0xba, 0x9a, 0x87, 0x6a, 0xba, 0x63, 0x9a, 0xd5,
0xc3, 0x05, 0x52, 0x36, 0x92, 0xfa, 0x43, 0xf2, 0x31, 0xb2, 0x4f, 0xcc, 0xda, 0x41, 0xb3, 0xfa,
0xdd, 0xe8, 0x36, 0x32, 0xd8, 0xef, 0x2a, 0x8f, 0x3a, 0xff, 0xe1, 0x01, 0x16, 0x10, 0x92, 0xc6,
0x3e, 0xe0, 0x86, 0x72, 0xb2, 0x9b, 0x24, 0x80, 0x29, 0x40, 0xa8, 0x08, 0xba, 0x0d, 0x5d, 0xf0,
0x10, 0x06, 0x20, 0x29, 0x71, 0x65, 0xdb, 0x04, 0x6b, 0x41, 0x71, 0x81, 0x80, 0x0d, 0x0c, 0xc2,
0xe1, 0x1d, 0x9f, 0xfe, 0x4e, 0xcc, 0xac, 0x20, 0x8e, 0xa7, 0x26, 0x81, 0x72, 0x34, 0x17, 0x30,
0x13, 0x89, 0x04, 0x0a, 0x23, 0xa4, 0x77, 0x3a, 0x09, 0x38, 0x14, 0x26, 0x8c, 0x7c, 0x60, 0xf5,
0xf8, 0x13, 0x71, 0x7d, 0x9a, 0x24, 0xb6, 0x29, 0x05, 0x98, 0xe7, 0x39, 0x1b, 0x33, 0xb2, 0xc1,
0x39, 0xf3, 0xa3, 0x1e, 0x8c, 0x01, 0x1c, 0x49, 0xf0, 0x0e, 0x02, 0x97, 0x6d, 0xea, 0x17, 0x94,
0xe6, 0xfa, 0xdc, 0x7d, 0xb4, 0xcd, 0x6b, 0x94, 0xf5, 0xb1, 0xdb, 0xd0, 0x13, 0xa0, 0x2a, 0x88,
0x28, 0x78, 0x8c, 0x2d, 0x4c, 0x3d, 0x64, 0xea, 0x51, 0xf7, 0x71, 0xc1, 0xb7, 0xb2, 0x8a, 0xd6,
0xd4, 0x74, 0xc6, 0xf4, 0x89, 0x2d, 0x48, 0xe6, 0x31, 0x54, 0x72, 0x2d, 0x7f, 0xde, 0xd2, 0x05,
0x15, 0x4c, 0x9c, 0x46, 0x60, 0x9e, 0x16, 0x0c, 0x1d, 0x3b, 0xca, 0x87, 0xbd, 0x18, 0xcc, 0x03,
0xa1, 0x27, 0x61, 0xf8, 0xd8, 0xb9, 0xef, 0x0f, 0xc9, 0x10, 0x8c, 0xdb, 0x21, 0x5d, 0x1e, 0x46,
0xa9, 0xcc, 0xcc, 0x73, 0x3f, 0x34, 0x73, 0xe5, 0xc2, 0x34, 0x98, 0xb0, 0x18, 0xac, 0xc5, 0x43,
0xdb, 0x6c, 0xc2, 0x5f, 0xfa, 0x62, 0x9b, 0xa7, 0xed, 0xf6, 0x71, 0xdb, 0xcc, 0xcd, 0xe3, 0xc1,
0x63, 0xcc, 0xfe, 0x49, 0x79, 0xcc, 0xd0, 0x0b, 0xb1, 0xd3, 0x0a, 0xbd, 0x55, 0xa9, 0x59, 0x2f,
0x70, 0xdf, 0x32, 0xc9, 0xff, 0x2f, 0x55, 0xfd, 0x5b, 0x91, 0x07, 0xe0, 0xa1, 0x7c, 0x8b, 0x7f,
0x57, 0xe5, 0xaa, 0xc0, 0x00, 0x19, 0x1a, 0x0c, 0x3a, 0x0a, 0x07, 0x9c, 0xd5, 0x3d, 0x02, 0xce,
0x68, 0xe6, 0xd1, 0xda, 0x5e, 0x37, 0x72, 0x77, 0x25, 0xb6, 0x36, 0xf9, 0x5c, 0x40, 0xe3, 0x19,
0x0f, 0x3b, 0x16, 0xa1, 0xa9, 0x14, 0x38, 0x09, 0xba, 0x49, 0x0f, 0x7b, 0x28, 0x3f, 0x89, 0x28,
0x6c, 0xea, 0x7d, 0x21, 0x06, 0x6b, 0xd9, 0x11, 0xf5, 0xf9, 0x2c, 0xec, 0xb8, 0x2a, 0x99, 0x4c,
0xed, 0x9c, 0x59, 0x2c, 0xd2, 0x08, 0x7b, 0x1d, 0xd8, 0x5e, 0x43, 0xf1, 0x2b, 0x19, 0x8e, 0x1e,
0x81, 0x7f, 0x4d, 0xa3, 0x78, 0x6c, 0x15, 0x4f, 0xc7, 0xc5, 0xd3, 0x49, 0xf1, 0xd4, 0x2e, 0x9e,
0x4e, 0x8b, 0xa7, 0x77, 0xc5, 0xd3, 0xd9, 0x62, 0x09, 0x23, 0x5f, 0x63, 0x0c, 0xa5, 0xb2, 0x53,
0x50, 0x64, 0x76, 0xd1, 0x46, 0x50, 0x28, 0x3d, 0x11, 0x2f, 0x99, 0x75, 0x9a, 0x79, 0xca, 0xc0,
0x93, 0x53, 0xe6, 0x30, 0x36, 0xb2, 0xb4, 0x0a, 0x96, 0xd6, 0x3a, 0xcb, 0x46, 0x8e, 0xe3, 0xa2,
0x5d, 0x84, 0xc7, 0xfd, 0x58, 0x4e, 0x8a, 0x45, 0x4e, 0xf6, 0xd5, 0xab, 0x5d, 0xb0, 0xb4, 0xf7,
0x5c, 0xe4, 0x74, 0xa1, 0xd7, 0xe9, 0x9e, 0x2c, 0xef, 0x8a, 0x45, 0xde, 0xed, 0xab, 0xd7, 0x59,
0xc1, 0x72, 0x96, 0xb3, 0x2c, 0xc7, 0xc3, 0x88, 0xb9, 0x8c, 0x3f, 0xb1, 0xce, 0x5e, 0xc2, 0x46,
0x85, 0xbf, 0x46, 0xcd, 0xfd, 0x34, 0x1e, 0xb5, 0x8a, 0x4d, 0x8e, 0xf6, 0xf4, 0xd7, 0xe8, 0xb8,
0x58, 0xe4, 0x78, 0xcf, 0x4d, 0x8e, 0x0a, 0x7f, 0x8d, 0x4e, 0xf6, 0x5c, 0xa4, 0xbd, 0xd0, 0x6b,
0x4f, 0x7f, 0x8d, 0x4e, 0x8b, 0x45, 0x4e, 0xf7, 0xd5, 0xab, 0xf0, 0xd7, 0xe8, 0xdd, 0x9e, 0x8b,
0x9c, 0x2d, 0xf4, 0x5a, 0xf5, 0x57, 0x43, 0x21, 0x84, 0xc2, 0xa9, 0xc2, 0x67, 0xa1, 0x78, 0x8e,
0x69, 0xb4, 0x4d, 0x5e, 0x2e, 0x07, 0xea, 0x48, 0x2f, 0xe6, 0xb3, 0xb9, 0x0c, 0x59, 0x92, 0xd4,
0xba, 0x8d, 0x9c, 0xeb, 0x6d, 0xee, 0x8c, 0xf9, 0xc2, 0x74, 0x2e, 0x84, 0x2f, 0xe2, 0x9a, 0xb1,
0xc6, 0x48, 0x01, 0x88, 0xdf, 0x66, 0xfe, 0xd3, 0x74, 0x2e, 0xa7, 0x53, 0xe6, 0xca, 0x64, 0xc1,
0x5c, 0xe0, 0xac, 0xb1, 0x85, 0x6b, 0x7c, 0x0b, 0x60, 0x3a, 0x66, 0x33, 0xec, 0xf1, 0x89, 0x88,
0xb0, 0x01, 0x49, 0x6a, 0x6f, 0x2f, 0x34, 0xbe, 0x82, 0x73, 0x26, 0x99, 0x88, 0x34, 0xf4, 0x12,
0x5c, 0x00, 0x01, 0x88, 0xe8, 0x23, 0x95, 0xee, 0x60, 0x12, 0x6c, 0xa7, 0x3d, 0x00, 0x7b, 0x57,
0xe2, 0x19, 0x31, 0x9c, 0xb1, 0x0e, 0x79, 0xdb, 0x6a, 0xe3, 0xbe, 0xe9, 0x6c, 0x17, 0x95, 0x15,
0xcc, 0x28, 0x06, 0x8b, 0x12, 0x68, 0xd6, 0x07, 0xa3, 0x9d, 0xf2, 0x7a, 0x4b, 0xf2, 0xce, 0x7d,
0xf6, 0x42, 0x57, 0xa5, 0x76, 0x76, 0xec, 0xf0, 0x5c, 0xb3, 0x1b, 0x8a, 0x7f, 0x08, 0xe7, 0x10,
0x1e, 0x25, 0xe4, 0x3a, 0x65, 0xd9, 0x76, 0x7e, 0x4c, 0xd8, 0xf5, 0xb2, 0xb0, 0x1b, 0xea, 0xc6,
0xe2, 0xc7, 0xf8, 0x6f, 0x96, 0xf9, 0x57, 0x8d, 0x23, 0x9f, 0xe1, 0x58, 0xbf, 0x8b, 0xbf, 0x65,
0x66, 0x71, 0xe0, 0x18, 0x23, 0x36, 0x11, 0x42, 0x16, 0xb5, 0x98, 0x48, 0x41, 0xe0, 0xac, 0xe5,
0xbf, 0x66, 0xfb, 0x4a, 0xea, 0xdd, 0x06, 0x57, 0xfd, 0xc5, 0x20, 0x4c, 0x24, 0x0d, 0x5d, 0x46,
0xf0, 0x00, 0xa5, 0xda, 0x0b, 0xe3, 0x32, 0x54, 0x45, 0x93, 0xe7, 0x33, 0x3e, 0xcc, 0xec, 0x58,
0xfa, 0xcb, 0xe7, 0x4c, 0xf5, 0x1b, 0xfa, 0xc8, 0x88, 0x9c, 0xf3, 0x64, 0xc1, 0x0e, 0x15, 0xd9,
0x15, 0x4f, 0x2c, 0x46, 0xa1, 0xbb, 0xc4, 0xa0, 0x37, 0x41, 0x85, 0x11, 0xa3, 0xbe, 0xe4, 0x01,
0x33, 0x94, 0x42, 0x59, 0x5e, 0x12, 0xec, 0x7b, 0xe2, 0x6c, 0x66, 0x87, 0xa0, 0x51, 0x16, 0x66,
0xc6, 0x3d, 0x34, 0xc3, 0x01, 0xe5, 0x70, 0x86, 0xcb, 0x23, 0x3f, 0xf4, 0x5f, 0x77, 0x30, 0xdf,
0xdc, 0x9a, 0x4b, 0xbd, 0x8b, 0x63, 0x7c, 0x61, 0xf2, 0x59, 0xc4, 0x8f, 0xa4, 0x7f, 0xf3, 0x27,
0x51, 0x7c, 0xca, 0x76, 0x30, 0x79, 0x07, 0xec, 0x20, 0x2b, 0x61, 0x3e, 0x26, 0x80, 0x66, 0xee,
0x0f, 0x54, 0x4f, 0xa8, 0xac, 0x0c, 0x2e, 0xc1, 0x13, 0x81, 0xba, 0x41, 0x00, 0x91, 0x3a, 0xe9,
0x88, 0xa1, 0x4f, 0x0c, 0x26, 0x1e, 0x3c, 0x20, 0x91, 0x9b, 0xf5, 0xe3, 0x26, 0xa9, 0x24, 0xe7,
0x17, 0x5f, 0xaa, 0xdd, 0x86, 0x26, 0x29, 0x48, 0x33, 0x4a, 0x3c, 0x7f, 0x98, 0xce, 0x79, 0x2c,
0x8f, 0x40, 0x95, 0x35, 0xa2, 0x5c, 0x9e, 0x05, 0xcd, 0x8b, 0xd2, 0x04, 0x8e, 0x89, 0x66, 0xfe,
0x04, 0x30, 0x93, 0x26, 0x52, 0x04, 0x04, 0xbb, 0xf1, 0x05, 0x6b, 0x43, 0xcf, 0xeb, 0x2d, 0x62,
0x83, 0x8c, 0x20, 0x09, 0x07, 0x32, 0xc7, 0xd8, 0xd0, 0x58, 0x5e, 0x0e, 0xf7, 0xe9, 0x00, 0x97,
0x77, 0x55, 0xf4, 0xdb, 0xeb, 0xfd, 0xa0, 0xea, 0x75, 0x6f, 0x52, 0x70, 0x22, 0xf6, 0xb3, 0x3b,
0x3c, 0x71, 0x59, 0x64, 0x84, 0xa4, 0x78, 0x98, 0x08, 0x21, 0x0c, 0xe0, 0x78, 0x57, 0xd6, 0xef,
0x7e, 0xa3, 0x7e, 0x56, 0xae, 0xdf, 0xf1, 0xfb, 0xf7, 0xef, 0x4b, 0x6a, 0x18, 0xe0, 0xd7, 0x52,
0x8a, 0xa8, 0x8c, 0x20, 0x17, 0xa8, 0x01, 0x11, 0x20, 0xbb, 0x4b, 0xc9, 0x3c, 0x66, 0x53, 0xbb,
0xb8, 0x66, 0x9a, 0x71, 0x39, 0x4f, 0x27, 0x75, 0x38, 0xfa, 0x37, 0x3e, 0x33, 0xef, 0xd3, 0x8b,
0xfe, 0xc5, 0x3e, 0x14, 0xda, 0x4a, 0xbc, 0x1c, 0xfb, 0x7b, 0xe2, 0xd3, 0xf0, 0xd1, 0x74, 0xd4,
0x78, 0xb7, 0x41, 0x9d, 0x03, 0x85, 0x4c, 0x8f, 0x3c, 0x42, 0x81, 0x47, 0x62, 0x7a, 0x94, 0xc0,
0x5a, 0x0c, 0x73, 0x22, 0x82, 0x73, 0x02, 0x93, 0x0b, 0x40, 0x30, 0xb6, 0xec, 0x7f, 0xac, 0xf7,
0x8f, 0x91, 0x97, 0x28, 0x13, 0x50, 0xcf, 0x43, 0x70, 0x2c, 0x59, 0xa0, 0x7f, 0x5e, 0xb6, 0x80,
0xb1, 0x62, 0x82, 0x76, 0xd3, 0x2a, 0x19, 0x00, 0x25, 0x06, 0x70, 0x62, 0x5c, 0x0b, 0xdf, 0x1b,
0xb3, 0x1c, 0x7d, 0x78, 0xd9, 0xd8, 0xe7, 0x09, 0xa6, 0xaf, 0xb7, 0x2d, 0x42, 0xa1, 0x6d, 0x19,
0xc3, 0xb1, 0x10, 0x50, 0x63, 0x74, 0xd5, 0xdb, 0x46, 0x04, 0xf0, 0x64, 0x64, 0x54, 0xfd, 0x37,
0xc8, 0x8e, 0xf3, 0xea, 0xb6, 0x8d, 0x00, 0x72, 0x41, 0x05, 0x10, 0xae, 0x65, 0x6c, 0x23, 0x82,
0xee, 0xa3, 0xcf, 0x83, 0x00, 0x4e, 0xc1, 0x87, 0xa4, 0xa0, 0xde, 0x9a, 0x60, 0xa0, 0x59, 0x41,
0xf4, 0xc7, 0x96, 0x34, 0xa1, 0xc4, 0x58, 0x0d, 0x88, 0x2d, 0xf7, 0x8e, 0x0c, 0x33, 0xfa, 0xc8,
0x0b, 0x5e, 0x1a, 0xe0, 0x94, 0x52, 0x68, 0xe8, 0x6c, 0xe7, 0xe1, 0x54, 0x60, 0x7c, 0x18, 0x0a,
0x44, 0x00, 0xcd, 0x20, 0x3c, 0xca, 0x31, 0x7d, 0xb7, 0x23, 0xe7, 0x2c, 0x6b, 0xd9, 0xa5, 0x24,
0x50, 0x05, 0xda, 0xf8, 0x24, 0x62, 0x17, 0x01, 0xef, 0x85, 0x4c, 0x8a, 0xd6, 0x64, 0x47, 0x8e,
0x7d, 0xca, 0x2a, 0x68, 0xee, 0xe3, 0x02, 0x62, 0xc9, 0x8c, 0x06, 0x01, 0x25, 0xae, 0x88, 0xb1,
0xbe, 0x83, 0x3d, 0x76, 0x61, 0xee, 0x55, 0x26, 0x28, 0x47, 0x6f, 0x82, 0x47, 0x57, 0x31, 0x9d,
0xc2, 0x81, 0xb6, 0xb4, 0xbb, 0x3f, 0x6e, 0x37, 0xee, 0xee, 0xa8, 0xd5, 0x6e, 0x67, 0x1b, 0x54,
0x4f, 0xc6, 0x22, 0x64, 0xa1, 0x0c, 0xe8, 0xea, 0xfe, 0xbb, 0x80, 0x42, 0x48, 0xce, 0x93, 0x84,
0x63, 0x79, 0xd1, 0x15, 0xeb, 0x32, 0x48, 0x7d, 0x2a, 0x59, 0x56, 0xff, 0xf5, 0x15, 0xf8, 0xae,
0xd4, 0x3a, 0xcf, 0x2a, 0x96, 0xe6, 0xe1, 0xe1, 0x53, 0x76, 0x29, 0xa3, 0xa6, 0x4b, 0x3b, 0xc5,
0xc3, 0x60, 0xd1, 0x71, 0x9c, 0x0f, 0x94, 0x8a, 0x3e, 0x0b, 0x67, 0x72, 0x0e, 0xd1, 0xda, 0xd2,
0x25, 0xab, 0xe7, 0xbf, 0x86, 0x8f, 0x4a, 0x9b, 0xee, 0xc4, 0x31, 0xd4, 0x5b, 0x8d, 0xdc, 0x7c,
0xbd, 0xbb, 0x23, 0xd8, 0xcf, 0x61, 0x47, 0x81, 0x77, 0x9f, 0x84, 0xfa, 0x3e, 0x5e, 0x2e, 0x86,
0x98, 0x71, 0x50, 0x93, 0x41, 0x30, 0x8b, 0x43, 0xea, 0x93, 0xb9, 0x48, 0x64, 0xa2, 0xf0, 0xc2,
0xb8, 0xc3, 0xea, 0x19, 0xd0, 0x57, 0xc2, 0x03, 0x80, 0x09, 0x20, 0x9b, 0xa3, 0x4f, 0x92, 0x08,
0xda, 0x00, 0x80, 0xbf, 0x50, 0xb5, 0x46, 0x53, 0x35, 0x7a, 0x39, 0x1e, 0x9e, 0xb5, 0x4e, 0x4f,
0x01, 0xb9, 0x26, 0x4e, 0xee, 0x7e, 0x32, 0x61, 0x09, 0x82, 0x5a, 0x02, 0xe1, 0x0c, 0xfd, 0x1d,
0x96, 0x3b, 0x92, 0x42, 0x11, 0x84, 0xe3, 0x70, 0xc6, 0x06, 0x2f, 0x09, 0x8b, 0xd1, 0x46, 0x09,
0xa1, 0x80, 0x28, 0x04, 0x7d, 0x55, 0x57, 0xfc, 0x15, 0x70, 0x1c, 0xea, 0x23, 0x61, 0x21, 0xff,
0xb5, 0x56, 0x68, 0x4a, 0x81, 0x03, 0x9e, 0x3d, 0x5c, 0x11, 0xd5, 0x06, 0x29, 0x81, 0xda, 0x17,
0x4a, 0x46, 0x4d, 0xb0, 0x34, 0xe3, 0xfe, 0xaa, 0x79, 0xdd, 0xbc, 0x16, 0x08, 0xee, 0xc6, 0x06,
0x33, 0x6a, 0x2b, 0xf6, 0xae, 0xd7, 0xac, 0xb8, 0xe9, 0x4e, 0xa3, 0xb7, 0xdf, 0x9d, 0x46, 0x96,
0xc6, 0x67, 0xd6, 0xf2, 0x45, 0x84, 0xc6, 0x39, 0x15, 0x0c, 0xe4, 0x3c, 0x95, 0x73, 0x50, 0xfc,
0x91, 0x85, 0x0b, 0xa5, 0xb2, 0x15, 0x7e, 0x5b, 0x55, 0xe4, 0xb8, 0xe8, 0xa1, 0x2e, 0x7c, 0x46,
0x63, 0xb5, 0x3b, 0xc5, 0x48, 0xa6, 0x9c, 0xf9, 0xaa, 0x91, 0xf2, 0x74, 0xa2, 0xd4, 0x89, 0xea,
0x03, 0xf6, 0x85, 0x85, 0x09, 0x86, 0xc4, 0x06, 0x48, 0x18, 0xe3, 0x75, 0x4f, 0x01, 0x09, 0x18,
0x4a, 0x06, 0x86, 0x8d, 0x0e, 0x6c, 0xdd, 0x89, 0xe1, 0xfb, 0xae, 0x9e, 0xe5, 0xab, 0xd6, 0xbb,
0x17, 0x83, 0xae, 0x71, 0x39, 0xf8, 0x97, 0x2d, 0x7f, 0x33, 0xde, 0xcb, 0xf2, 0x37, 0x5f, 0x87,
0xb7, 0xa3, 0xbb, 0xcd, 0x65, 0x65, 0xeb, 0xdd, 0x4f, 0xd6, 0x36, 0x61, 0x0c, 0x6b, 0xad, 0x89,
0x0b, 0xd9, 0x0b, 0x6d, 0x17, 0xa7, 0x3e, 0x04, 0x5b, 0x8c, 0x91, 0x87, 0x3d, 0x18, 0x54, 0x71,
0x08, 0x1f, 0xa8, 0xe7, 0x10, 0x56, 0x29, 0xb6, 0xa7, 0x59, 0xa0, 0xe1, 0xa5, 0xa8, 0x0a, 0xc4,
0x2f, 0x0c, 0x49, 0xf2, 0xe8, 0x52, 0x92, 0x22, 0x58, 0x04, 0xda, 0x30, 0x8f, 0x4c, 0x05, 0x32,
0x0b, 0x98, 0x88, 0xf3, 0x40, 0x3e, 0xc8, 0x33, 0x00, 0xda, 0xbd, 0x78, 0x25, 0x81, 0x37, 0x19,
0xe0, 0xeb, 0xfd, 0xf8, 0x72, 0xb4, 0x62, 0x84, 0x13, 0x4b, 0xab, 0x3e, 0xcc, 0xd6, 0x28, 0x19,
0x3b, 0x5f, 0xba, 0xc0, 0x00, 0x30, 0xce, 0xf9, 0x78, 0xd5, 0x8e, 0xa7, 0x27, 0x5a, 0xc4, 0x85,
0xcf, 0x71, 0x8b, 0x83, 0xfe, 0x46, 0x0c, 0xc9, 0xd9, 0x2f, 0x06, 0x7d, 0x34, 0xe6, 0xba, 0x06,
0x59, 0xbc, 0xde, 0x89, 0x88, 0xbb, 0x6f, 0x49, 0xe8, 0xaf, 0x39, 0x51, 0x15, 0x93, 0x2b, 0xbc,
0x9e, 0xda, 0xcd, 0x7d, 0xb5, 0x0e, 0x61, 0x68, 0xf5, 0x61, 0x3a, 0x81, 0x5e, 0x7f, 0x5e, 0x3e,
0x89, 0xed, 0x08, 0xbd, 0xde, 0xcd, 0x0f, 0x1c, 0x3b, 0x7e, 0x2c, 0x67, 0x82, 0x7f, 0xa4, 0xdc,
0x90, 0x32, 0x2a, 0x1e, 0x56, 0x32, 0x66, 0xe9, 0xe4, 0xa6, 0x31, 0x18, 0x74, 0xf9, 0x4b, 0xa4,
0xc4, 0xa5, 0x98, 0xb7, 0x00, 0x54, 0x18, 0x46, 0x50, 0x12, 0x3d, 0x38, 0xd2, 0x0d, 0x86, 0x0a,
0xba, 0x70, 0xc4, 0xc7, 0x1a, 0x49, 0x74, 0x70, 0x83, 0x40, 0x35, 0xf6, 0xf3, 0x39, 0x1c, 0x78,
0xe5, 0xcf, 0x88, 0x78, 0xaa, 0x1e, 0x64, 0x58, 0x3b, 0x07, 0x04, 0x87, 0xad, 0xd4, 0x8d, 0xbc,
0xf9, 0x1f, 0x0a, 0x80, 0x72, 0xc4, 0x75, 0x2d, 0x64, 0x25, 0x79, 0xae, 0x3f, 0xbf, 0x59, 0xbd,
0xa1, 0x1d, 0x75, 0x08, 0x46, 0xf8, 0x6b, 0x09, 0x8c, 0xae, 0x07, 0x9b, 0xf9, 0x2c, 0x6b, 0xa5,
0xee, 0x63, 0xb9, 0xdf, 0x55, 0xdf, 0xae, 0x87, 0xda, 0x2b, 0x90, 0x89, 0x61, 0x0d, 0x1c, 0xa2,
0x8f, 0x50, 0x6f, 0x3a, 0xf2, 0xfa, 0x16, 0x8f, 0xfb, 0xb7, 0x61, 0xe3, 0x76, 0x3a, 0xdd, 0x71,
0x33, 0x70, 0x0d, 0x4d, 0x03, 0x59, 0xba, 0xfd, 0x20, 0x4b, 0x97, 0x16, 0xdb, 0x14, 0xba, 0x00,
0x16, 0x75, 0xe7, 0xa1, 0xea, 0x03, 0x18, 0xae, 0x97, 0xfb, 0xa3, 0xb3, 0x74, 0x4b, 0x9c, 0x11,
0x5b, 0x6b, 0xb8, 0x9f, 0xa1, 0x4c, 0x52, 0xea, 0xee, 0xb1, 0x51, 0x70, 0x48, 0xbd, 0x64, 0xff,
0xe6, 0x1a, 0x70, 0xfd, 0x10, 0xfb, 0xda, 0x95, 0xf7, 0x3a, 0xb7, 0xf1, 0x06, 0xfb, 0xf1, 0x6e,
0xf6, 0x05, 0x77, 0x0e, 0x99, 0x43, 0x75, 0xe9, 0x81, 0xa1, 0x16, 0xa5, 0xc9, 0xdc, 0xe7, 0xe1,
0x63, 0x9e, 0x84, 0x22, 0x5c, 0x0a, 0x5f, 0x30, 0xf5, 0x14, 0xbf, 0xed, 0xc8, 0x39, 0xd4, 0xee,
0x84, 0x3e, 0x65, 0xa7, 0x6d, 0xfc, 0x0e, 0x59, 0xa0, 0xa0, 0x51, 0x79, 0x9e, 0xab, 0x82, 0x15,
0x43, 0x2b, 0x90, 0x43, 0x6b, 0x38, 0xab, 0xe6, 0x86, 0x87, 0xce, 0x49, 0xa6, 0x18, 0x41, 0x78,
0xeb, 0x5d, 0x28, 0xc7, 0x23, 0x6c, 0x99, 0x75, 0x9f, 0xaf, 0x93, 0x01, 0xe4, 0x4e, 0x52, 0xee,
0x7b, 0xf8, 0x75, 0x07, 0x28, 0x55, 0xaa, 0x8d, 0x59, 0x0c, 0x60, 0xae, 0x92, 0xac, 0x47, 0x53,
0x8f, 0xc4, 0xd0, 0x78, 0x95, 0x0f, 0x11, 0xbd, 0xfe, 0xda, 0x21, 0xa2, 0xd9, 0x6c, 0x03, 0xca,
0xe0, 0xaf, 0x65, 0x6d, 0xed, 0xd9, 0x5b, 0xc7, 0x16, 0xa0, 0x28, 0xfe, 0x5a, 0xd6, 0xd6, 0xe6,
0xff, 0xd4, 0x82, 0x53, 0x33, 0xfe, 0xbe, 0x21, 0x48, 0x67, 0x09, 0xfe, 0x6e, 0x17, 0xd4, 0x7e,
0x77, 0x8a, 0x34, 0xf0, 0xfb, 0x86, 0xa0, 0xf7, 0xad, 0x26, 0x9c, 0x0d, 0xf0, 0x77, 0xbb, 0xa0,
0xa6, 0xa5, 0x56, 0x53, 0x7f, 0xde, 0x10, 0xd5, 0xd4, 0x4a, 0x35, 0xcb, 0x5a, 0xad, 0x9c, 0x31,
0x00, 0xb6, 0x7e, 0x63, 0x2c, 0xc2, 0xbe, 0x4c, 0xdb, 0x0a, 0x11, 0x14, 0xcb, 0xe0, 0x20, 0x88,
0x62, 0xf1, 0x54, 0x27, 0x63, 0x01, 0x7d, 0xf5, 0x44, 0xd0, 0xd8, 0xd3, 0x3d, 0x22, 0xd4, 0x41,
0x92, 0xa4, 0x91, 0xfa, 0xd6, 0x36, 0x87, 0x74, 0x54, 0xfe, 0xc8, 0x6f, 0x77, 0xf0, 0x9c, 0xfb,
0xf6, 0x97, 0xae, 0x1f, 0xf9, 0x68, 0x65, 0x2c, 0x7d, 0x10, 0xc3, 0x0f, 0x73, 0xf0, 0x07, 0x3f,
0xde, 0xe1, 0x97, 0x3c, 0xfc, 0x0f, 0x2d, 0xff, 0x03, 0xeb, 0x0a, 0x98, 0x3d, 0xe0, 0x22, 0x00,
0x00
0xbd, 0x1f, 0x4a, 0x6c, 0x49, 0x33, 0x1a, 0xcd, 0xcb, 0x33, 0x33, 0x72, 0xbb, 0xef, 0xfa, 0xb7,
0x17, 0x77, 0x7f, 0x0d, 0x2f, 0xc9, 0x5c, 0x06, 0xbe, 0xd3, 0xc5, 0x5f, 0xe2, 0xd3, 0x70, 0x66,
0x9b, 0x2c, 0x34, 0xe1, 0x9d, 0x51, 0xcf, 0xe9, 0x06, 0x4c, 0x52, 0x12, 0xd2, 0x80, 0xd9, 0xe6,
0x13, 0x67, 0xcf, 0x91, 0x88, 0xa5, 0x49, 0x5c, 0x11, 0x4a, 0x16, 0x4a, 0xdb, 0x7c, 0xe6, 0x9e,
0x9c, 0xdb, 0x6d, 0xcb, 0x32, 0x1d, 0x43, 0x2f, 0x35, 0x4a, 0x73, 0x1e, 0x7b, 0xe2, 0x2e, 0x3b,
0x54, 0x2f, 0x35, 0x1e, 0x72, 0xc9, 0xa9, 0x7f, 0x98, 0xb8, 0xd4, 0x67, 0x76, 0xb3, 0x16, 0xd0,
0x17, 0x1e, 0xa4, 0x41, 0xf1, 0x9e, 0x26, 0x2c, 0x56, 0x2f, 0x74, 0x02, 0xef, 0xa1, 0x30, 0x89,
0x51, 0xda, 0x3a, 0x13, 0xc8, 0x9d, 0xd3, 0x38, 0x61, 0xb0, 0x49, 0x2a, 0xa7, 0x87, 0xa7, 0x30,
0x2a, 0xb9, 0xf4, 0x99, 0x33, 0x7e, 0x0d, 0x5d, 0x32, 0x66, 0x52, 0xf2, 0x70, 0x96, 0x74, 0x1b,
0x7a, 0xb0, 0x9b, 0xb8, 0x31, 0x8f, 0xa4, 0x63, 0x3c, 0xd1, 0x98, 0xf8, 0xc2, 0xe5, 0x51, 0xcd,
0xb3, 0x3d, 0xe1, 0xa6, 0x01, 0x88, 0x59, 0x83, 0x01, 0xfb, 0x5d, 0xf3, 0x6c, 0x9a, 0x86, 0xae,
0xe4, 0x22, 0x24, 0xb3, 0x81, 0x57, 0x61, 0xd5, 0x6f, 0x31, 0x93, 0x69, 0x1c, 0x12, 0xaf, 0x3e,
0x63, 0xf2, 0xd2, 0x67, 0xb8, 0xb4, 0xf7, 0xaa, 0xa6, 0xbe, 0x17, 0x4b, 0xaf, 0x2b, 0xd5, 0x6f,
0xcf, 0x3c, 0xf4, 0xc4, 0x73, 0x5d, 0x44, 0x2c, 0xac, 0x98, 0x73, 0x29, 0xa3, 0xa4, 0xd3, 0x68,
0x3c, 0x86, 0xa2, 0xfe, 0xec, 0x33, 0x24, 0x6e, 0x70, 0xd0, 0x46, 0x3c, 0xa5, 0x2e, 0x4b, 0x1a,
0xa9, 0x17, 0x1d, 0x86, 0x42, 0xf2, 0x29, 0x67, 0x71, 0xc3, 0x5c, 0x62, 0xd4, 0x2b, 0x33, 0x6a,
0x24, 0xd9, 0x19, 0xcc, 0x9a, 0xf9, 0x77, 0xc2, 0xfc, 0xe9, 0xf2, 0x6a, 0xea, 0x3d, 0xc0, 0xfa,
0x93, 0xe3, 0xf6, 0xb1, 0x6d, 0x7b, 0xf5, 0xf1, 0xb4, 0xde, 0x1f, 0xd4, 0x9f, 0xa8, 0x9f, 0xb2,
0x8f, 0xcd, 0x6c, 0xe0, 0xf2, 0x5e, 0x0f, 0xfc, 0xf4, 0x53, 0x65, 0xe5, 0xdd, 0xb6, 0xaa, 0x9d,
0x76, 0xfb, 0xe4, 0xb4, 0x44, 0x07, 0xcb, 0xac, 0x7c, 0xe8, 0x7c, 0x95, 0x32, 0x7f, 0xb7, 0x9b,
0xd5, 0x9a, 0xb5, 0x8b, 0x7b, 0xb3, 0xba, 0x24, 0xa5, 0x2f, 0xa8, 0xf7, 0xeb, 0xb8, 0xc2, 0x6a,
0xd2, 0x7e, 0x67, 0x55, 0xbf, 0xf9, 0x4c, 0x12, 0x01, 0xf4, 0x6e, 0xcc, 0xa8, 0x64, 0x99, 0x46,
0x2b, 0xa6, 0x36, 0x8d, 0x59, 0x3d, 0x13, 0x75, 0x38, 0xf2, 0xb9, 0x94, 0x31, 0x9f, 0xa4, 0x92,
0xc1, 0x44, 0xec, 0x9a, 0x35, 0x56, 0xad, 0x95, 0xc7, 0xe5, 0x6b, 0xc4, 0x40, 0x29, 0x92, 0xbd,
0xc8, 0xc6, 0x03, 0x7d, 0xa2, 0x39, 0x83, 0xb5, 0x85, 0x34, 0x01, 0x5f, 0x30, 0x6b, 0xb2, 0x5a,
0xf3, 0xea, 0x13, 0xe1, 0xbd, 0xd6, 0x69, 0x04, 0xaa, 0xf5, 0x2e, 0xe6, 0xdc, 0xf7, 0x2a, 0x02,
0xd7, 0x53, 0xcf, 0xbb, 0x7c, 0x02, 0x29, 0x3e, 0xf3, 0x04, 0x1c, 0x96, 0xc5, 0x15, 0x13, 0x65,
0x36, 0x6b, 0x95, 0xaa, 0xed, 0x7c, 0xbb, 0x62, 0xf2, 0xf7, 0x4a, 0xb5, 0x06, 0xbe, 0xf4, 0x3b,
0xf5, 0x2b, 0xd5, 0xef, 0x9b, 0x09, 0x58, 0x1c, 0x8b, 0x18, 0xe4, 0x04, 0x02, 0x70, 0xfb, 0x44,
0xf8, 0xac, 0xee, 0x8b, 0x59, 0xc5, 0xbc, 0xc4, 0x71, 0x92, 0x69, 0x01, 0xec, 0x48, 0xa6, 0xdc,
0x67, 0xea, 0x3c, 0xe0, 0xe7, 0x31, 0x9c, 0xfb, 0x73, 0x36, 0x2e, 0xa6, 0x18, 0x4b, 0x53, 0x3e,
0x4b, 0x63, 0xaa, 0xd4, 0xa6, 0xcf, 0x43, 0xa6, 0x94, 0xa3, 0xff, 0xfc, 0x37, 0x1c, 0x84, 0xae,
0x08, 0x22, 0xd0, 0x1e, 0x23, 0x11, 0x9d, 0x31, 0xe2, 0x51, 0x49, 0xdf, 0x81, 0x37, 0x2c, 0x69,
0xfa, 0xd3, 0x05, 0xb8, 0xc3, 0x54, 0xc4, 0x95, 0x07, 0xdb, 0x3a, 0x7b, 0xe8, 0x9e, 0x9e, 0x3d,
0x1c, 0x1c, 0x54, 0xd1, 0x8d, 0xcd, 0x2b, 0xf3, 0xa0, 0xf2, 0x70, 0x00, 0x66, 0xa9, 0xbb, 0x73,
0xe6, 0x3e, 0x32, 0xcf, 0xd6, 0xc3, 0x63, 0xb3, 0xaa, 0x4d, 0xe6, 0x38, 0x0f, 0x3f, 0x35, 0x6b,
0x6a, 0x70, 0xb4, 0x65, 0xed, 0x68, 0x65, 0xed, 0x62, 0xd7, 0x2b, 0xdc, 0x15, 0x23, 0x0a, 0xbc,
0x0a, 0x6c, 0x6c, 0xd5, 0x84, 0x0d, 0x51, 0x54, 0x92, 0x82, 0x1d, 0xd8, 0x9b, 0x05, 0xf9, 0x45,
0xd4, 0x64, 0x36, 0x37, 0xda, 0x30, 0x27, 0x7e, 0xb1, 0x5b, 0x67, 0x25, 0x59, 0x6d, 0x56, 0x2b,
0x49, 0x64, 0xcb, 0x85, 0x38, 0xe3, 0x61, 0x21, 0xce, 0x8a, 0x6f, 0x6b, 0x2e, 0x2f, 0x11, 0xd0,
0x24, 0xf2, 0x15, 0xec, 0xe3, 0xf1, 0x24, 0xf2, 0xe9, 0xab, 0xcd, 0x1c, 0xeb, 0xa3, 0x19, 0x8a,
0x90, 0x99, 0x1d, 0x73, 0x02, 0x20, 0xf0, 0x08, 0xe6, 0x71, 0xac, 0xc2, 0xa7, 0x87, 0xf9, 0xa6,
0x4b, 0x8a, 0xce, 0x9d, 0xe1, 0x5b, 0xf2, 0xcc, 0xa5, 0x3b, 0xaf, 0x44, 0x88, 0x41, 0x03, 0x70,
0xe3, 0x15, 0x92, 0x6a, 0xf5, 0x9b, 0x4b, 0x13, 0x46, 0x30, 0xd0, 0x3a, 0x2b, 0xb2, 0xd8, 0x38,
0x74, 0x36, 0x81, 0x08, 0x78, 0x3c, 0x53, 0x4b, 0x30, 0x86, 0x4b, 0x4b, 0x70, 0x68, 0x79, 0xc9,
0xb1, 0x75, 0x5c, 0xe6, 0x82, 0x43, 0xdf, 0xf1, 0xbc, 0x35, 0xb4, 0xfc, 0x92, 0x78, 0x20, 0x99,
0x89, 0x8e, 0xd6, 0x31, 0x6d, 0x3b, 0x83, 0x13, 0x38, 0x98, 0xf2, 0xab, 0x7a, 0x14, 0x0b, 0x29,
0x5c, 0xe1, 0xc3, 0x01, 0x15, 0xe2, 0x59, 0xb5, 0x8a, 0x82, 0x42, 0x1b, 0x57, 0xf8, 0x63, 0x29,
0x62, 0xf0, 0x2e, 0x04, 0xbb, 0x81, 0x64, 0x01, 0x46, 0x82, 0x3b, 0x00, 0x9d, 0x55, 0xff, 0xfd,
0x37, 0x5b, 0x06, 0xf4, 0x41, 0x04, 0x8e, 0xfb, 0x09, 0xf8, 0x93, 0x1b, 0xe1, 0xb1, 0x3a, 0x19,
0xfa, 0x0c, 0x25, 0x64, 0x08, 0x70, 0xe4, 0x8f, 0xcf, 0x97, 0x7d, 0x32, 0x18, 0x82, 0x6b, 0xd6,
0x56, 0x38, 0x26, 0xab, 0x1c, 0x6b, 0x8a, 0x5b, 0xb5, 0x8a, 0xab, 0x14, 0x3e, 0x20, 0xfb, 0x8f,
0x0a, 0x38, 0x01, 0x37, 0xcd, 0x03, 0x35, 0xdd, 0x31, 0xcd, 0xea, 0xc1, 0x02, 0x03, 0x1b, 0x49,
0xfd, 0x21, 0xf9, 0x18, 0xd9, 0xc7, 0x66, 0xed, 0x5d, 0xb3, 0xfa, 0xdd, 0xe8, 0x36, 0x32, 0x40,
0xef, 0x2a, 0x8b, 0x3a, 0xff, 0xe1, 0x01, 0xa6, 0x06, 0x92, 0xc6, 0x3e, 0xe0, 0x86, 0x32, 0xb2,
0x9b, 0x24, 0x80, 0x29, 0xb0, 0x50, 0x2d, 0xe8, 0x36, 0x74, 0x2a, 0x43, 0x18, 0x80, 0xa0, 0xc4,
0x9d, 0x6d, 0x13, 0xb4, 0x05, 0x69, 0x03, 0x1c, 0x36, 0x30, 0x08, 0x87, 0x77, 0x7c, 0xfa, 0x3b,
0x31, 0xb3, 0x54, 0x37, 0x9e, 0x9a, 0x04, 0x12, 0xcd, 0x5c, 0xc0, 0x4c, 0x24, 0x12, 0x48, 0x79,
0x10, 0xde, 0xe9, 0x24, 0xe0, 0x90, 0x72, 0xd0, 0xf3, 0x81, 0xd4, 0xe3, 0x4f, 0xc4, 0xf5, 0x69,
0x92, 0xd8, 0xa6, 0x14, 0xa0, 0x9e, 0xe7, 0x6c, 0xcc, 0xc8, 0x06, 0xe7, 0xcc, 0x8f, 0x7a, 0x30,
0x06, 0x70, 0x24, 0xc1, 0x3a, 0x08, 0x5c, 0xb6, 0xa9, 0x5f, 0x90, 0x9b, 0xeb, 0x73, 0xf7, 0xd1,
0x36, 0xaf, 0x91, 0xd7, 0xc7, 0x6e, 0x43, 0x4f, 0x80, 0xa8, 0xc0, 0xa2, 0xa0, 0x31, 0xb6, 0x10,
0xf5, 0x90, 0xa8, 0x47, 0xdd, 0xc7, 0x05, 0xdd, 0xca, 0x2e, 0x5a, 0x52, 0xd3, 0x19, 0xd3, 0x27,
0xb6, 0x58, 0x32, 0x8f, 0x21, 0x47, 0x6b, 0xfe, 0xf3, 0x96, 0x4e, 0x95, 0xa0, 0xe2, 0x34, 0x02,
0xf5, 0xb4, 0x60, 0xe8, 0xc8, 0x51, 0x36, 0xec, 0xc5, 0xa0, 0x1e, 0x70, 0x3d, 0x09, 0xc3, 0x47,
0xce, 0x7d, 0x7f, 0x48, 0x86, 0xa0, 0xdc, 0x0e, 0xe9, 0xf2, 0x30, 0x4a, 0x65, 0xa6, 0x9e, 0xfb,
0xa1, 0x99, 0x0b, 0x17, 0xa6, 0xc1, 0x84, 0xc5, 0xa0, 0x2d, 0x1e, 0xda, 0x66, 0x13, 0xfe, 0xd2,
0x17, 0xdb, 0x3c, 0x69, 0xb7, 0x8f, 0xda, 0x66, 0xae, 0x1e, 0x0f, 0x1e, 0x63, 0xf6, 0x4f, 0xca,
0x63, 0x86, 0x56, 0x88, 0x9d, 0x56, 0xe8, 0xad, 0x72, 0xcd, 0xb2, 0xfc, 0x7d, 0xcb, 0x24, 0xff,
0x3f, 0x57, 0xf5, 0x6f, 0x85, 0x1f, 0x80, 0x87, 0xb2, 0x2d, 0xfe, 0x5d, 0xe5, 0xab, 0x1c, 0x03,
0x78, 0x68, 0x30, 0xe8, 0x28, 0x1c, 0x70, 0x56, 0xcf, 0x08, 0x38, 0xa3, 0x89, 0x47, 0x6b, 0x67,
0xdd, 0x48, 0xdd, 0x95, 0x58, 0xb4, 0xe4, 0x73, 0x01, 0x8d, 0x67, 0x3c, 0xec, 0x58, 0x84, 0xa6,
0x52, 0xe0, 0x24, 0xc8, 0x26, 0x3d, 0xac, 0x8e, 0xfc, 0x24, 0xa2, 0x70, 0xa8, 0x0f, 0x05, 0x1b,
0xcc, 0x65, 0x87, 0xd4, 0xe7, 0xb3, 0xb0, 0xe3, 0xaa, 0x60, 0x32, 0xb5, 0x71, 0x66, 0xb1, 0x48,
0x23, 0xac, 0x62, 0xe0, 0x78, 0x0d, 0x45, 0xaf, 0x78, 0x38, 0x7a, 0x04, 0xfe, 0x35, 0x8d, 0xe2,
0xb1, 0x55, 0x3c, 0x1d, 0x15, 0x4f, 0xc7, 0xc5, 0x53, 0xbb, 0x78, 0x3a, 0x29, 0x9e, 0xde, 0x17,
0x4f, 0xa7, 0x8b, 0x2d, 0x8c, 0x7c, 0x8f, 0x31, 0xa4, 0xca, 0x4e, 0xb1, 0x22, 0xd3, 0x8b, 0x56,
0x82, 0x42, 0xe9, 0x89, 0x78, 0xc9, 0xb4, 0xd3, 0xcc, 0x43, 0x06, 0x9e, 0x9c, 0x32, 0x85, 0xb1,
0x91, 0xa4, 0x55, 0x90, 0xb4, 0xd6, 0x49, 0x36, 0x52, 0x1c, 0x15, 0x85, 0x20, 0x3c, 0xee, 0x47,
0x72, 0x5c, 0x6c, 0x72, 0xbc, 0xaf, 0x5c, 0xed, 0x82, 0xa4, 0xbd, 0xe7, 0x26, 0x27, 0x0b, 0xb9,
0x4e, 0xf6, 0x24, 0x79, 0x5f, 0x6c, 0xf2, 0x7e, 0x5f, 0xb9, 0x4e, 0x0b, 0x92, 0xd3, 0x9c, 0x64,
0xd9, 0x1f, 0x46, 0xcc, 0x65, 0xfc, 0x89, 0x75, 0xf6, 0x62, 0x36, 0x2a, 0xec, 0x35, 0x6a, 0xee,
0x27, 0xf1, 0xa8, 0x55, 0x1c, 0x72, 0xb4, 0xa7, 0xbd, 0x46, 0x47, 0xc5, 0x26, 0x47, 0x7b, 0x1e,
0x72, 0x54, 0xd8, 0x6b, 0x74, 0xbc, 0xe7, 0x26, 0xed, 0x85, 0x5c, 0x7b, 0xda, 0x6b, 0x74, 0x52,
0x6c, 0x72, 0xb2, 0xaf, 0x5c, 0x85, 0xbd, 0x46, 0xef, 0xf7, 0xdc, 0xe4, 0x74, 0x21, 0xd7, 0xaa,
0xbd, 0x1a, 0x0a, 0x21, 0x14, 0x4e, 0x15, 0x36, 0x0b, 0xc5, 0x73, 0x4c, 0xa3, 0x6d, 0xfc, 0x72,
0x3e, 0x90, 0x47, 0x7a, 0x31, 0x9f, 0xcd, 0x65, 0xc8, 0x92, 0xa4, 0xd6, 0x6d, 0xe4, 0x54, 0x6f,
0x53, 0x67, 0xc4, 0x17, 0xa6, 0x73, 0x21, 0x7c, 0x11, 0xd7, 0x8c, 0x35, 0x42, 0x0a, 0x40, 0xfc,
0x36, 0xf1, 0x9f, 0xa6, 0x73, 0x39, 0x9d, 0x32, 0x57, 0x26, 0x0b, 0xe2, 0x02, 0x67, 0x8d, 0x2d,
0x54, 0xe3, 0x5b, 0x00, 0xd3, 0x31, 0x9b, 0x61, 0x8d, 0x4f, 0x44, 0x84, 0x05, 0x48, 0x52, 0x7b,
0x7b, 0xa3, 0xf1, 0x15, 0x74, 0x90, 0x64, 0x22, 0xd2, 0xd0, 0x4b, 0x70, 0x03, 0x04, 0x20, 0xa2,
0x9b, 0x25, 0x5d, 0xc1, 0x24, 0x58, 0x4e, 0x7b, 0x00, 0xf6, 0xae, 0xc4, 0xee, 0x2f, 0x9c, 0xb1,
0x0e, 0x79, 0x5b, 0x6b, 0xe3, 0xbe, 0xe9, 0x6c, 0x67, 0x95, 0x25, 0xcc, 0x28, 0x06, 0x8d, 0x12,
0x28, 0xd6, 0x07, 0xa3, 0x9d, 0xfc, 0x7a, 0x4b, 0xfc, 0xce, 0x7d, 0xf6, 0x42, 0x57, 0xb9, 0x76,
0x76, 0x9c, 0xf0, 0x5c, 0x93, 0x1b, 0x8a, 0x7e, 0x08, 0x7d, 0x08, 0x8f, 0x12, 0x72, 0x9d, 0xb2,
0xec, 0x38, 0x3f, 0xc6, 0xec, 0x7a, 0x99, 0xd9, 0x0d, 0x75, 0x63, 0xf1, 0x63, 0xf4, 0x37, 0xcb,
0xf4, 0xab, 0xca, 0x91, 0xcf, 0xd0, 0xb0, 0xef, 0xa2, 0x6f, 0x99, 0x99, 0x1f, 0x38, 0xc6, 0x88,
0x4d, 0x84, 0x90, 0x45, 0x2e, 0x26, 0x52, 0x10, 0xe8, 0xb5, 0xfc, 0xd7, 0xec, 0x5c, 0x49, 0xbd,
0xdb, 0xe0, 0xaa, 0xbe, 0x18, 0x84, 0x89, 0xa4, 0xa1, 0xcb, 0x08, 0x36, 0x50, 0xaa, 0xbc, 0x30,
0x2e, 0x43, 0x95, 0x34, 0x79, 0x3e, 0xe3, 0xc3, 0xcc, 0x8e, 0xad, 0xbf, 0x7c, 0xce, 0x44, 0xbf,
0xa1, 0x8f, 0x8c, 0xc8, 0x39, 0x4f, 0x16, 0xe4, 0x90, 0x91, 0x5d, 0xf1, 0xc4, 0x62, 0x64, 0xba,
0x8b, 0x0d, 0x5a, 0x13, 0x44, 0x18, 0x31, 0xea, 0x4b, 0x1e, 0x30, 0x43, 0x09, 0x94, 0xc5, 0x25,
0xc1, 0xba, 0x27, 0xce, 0x66, 0x76, 0x30, 0x1a, 0x65, 0x6e, 0x66, 0xdc, 0x43, 0x31, 0x1c, 0x50,
0x0e, 0x3d, 0x5c, 0xee, 0xf9, 0xa1, 0xff, 0xba, 0x83, 0xf8, 0xe6, 0xd6, 0x5c, 0xaa, 0x5d, 0x1c,
0xe3, 0x0b, 0x93, 0xcf, 0x22, 0x7e, 0x24, 0xfd, 0x9b, 0x3f, 0x89, 0xa2, 0x53, 0xba, 0x83, 0xc9,
0x3b, 0x20, 0x07, 0x5e, 0x09, 0xf3, 0x31, 0x00, 0x34, 0x71, 0x7f, 0xa0, 0x6a, 0x42, 0xa5, 0x65,
0x30, 0x09, 0x76, 0x04, 0xea, 0x6e, 0x00, 0x58, 0xea, 0xa0, 0x23, 0x86, 0xee, 0x18, 0x4c, 0x6c,
0x3c, 0x20, 0x90, 0x9b, 0xf5, 0xa3, 0x26, 0xa9, 0x24, 0xe7, 0x17, 0x5f, 0xaa, 0xdd, 0x86, 0x5e,
0x52, 0x2c, 0xcd, 0x56, 0x62, 0xff, 0x61, 0x3a, 0xe7, 0xb1, 0x3c, 0x04, 0x51, 0xd6, 0x16, 0xe5,
0xfc, 0x2c, 0x28, 0x5e, 0x94, 0x24, 0xd0, 0x26, 0x9a, 0xf9, 0x13, 0xc0, 0x4c, 0x9a, 0x48, 0x11,
0x10, 0xac, 0xc6, 0x17, 0xa4, 0x0d, 0x3d, 0xaf, 0x8f, 0x88, 0x05, 0x32, 0x82, 0x24, 0x34, 0x64,
0x8e, 0xb1, 0xa1, 0xb0, 0xbc, 0x1c, 0xee, 0x53, 0x01, 0x2e, 0x9f, 0xaa, 0xa8, 0xb7, 0xd7, 0xeb,
0x41, 0x55, 0xeb, 0xde, 0xa4, 0x60, 0x44, 0xac, 0x67, 0x77, 0x58, 0xe2, 0xb2, 0x88, 0x08, 0x49,
0xb1, 0x99, 0x08, 0xc1, 0x0d, 0xa0, 0xbd, 0x2b, 0xcb, 0x77, 0xbf, 0x51, 0x3e, 0x2b, 0x97, 0xef,
0xe8, 0xc3, 0x87, 0x0f, 0x25, 0x31, 0x0c, 0xb0, 0x6b, 0x29, 0x44, 0x54, 0x44, 0x90, 0x0b, 0x94,
0x80, 0x08, 0xe0, 0xdd, 0xa5, 0x64, 0x1e, 0xb3, 0xa9, 0x5d, 0x5c, 0x20, 0xcd, 0xb8, 0x9c, 0xa7,
0x93, 0x3a, 0xb4, 0xfe, 0x8d, 0xcf, 0xcc, 0xfb, 0xf4, 0xa2, 0x7f, 0xb1, 0x0e, 0x85, 0xb2, 0x12,
0xaf, 0xbd, 0xfe, 0x9e, 0xf8, 0x34, 0x7c, 0x34, 0x1d, 0x35, 0xde, 0x6d, 0x50, 0xe7, 0x9d, 0x42,
0xa6, 0x47, 0x1e, 0x21, 0xc3, 0x43, 0x31, 0x3d, 0x4c, 0x60, 0x2f, 0x86, 0x31, 0x11, 0x41, 0x9f,
0xc0, 0xe4, 0x02, 0x10, 0x8c, 0x2d, 0xe7, 0x1f, 0xeb, 0xf3, 0xa3, 0xe7, 0x25, 0x4a, 0x05, 0xd4,
0xf3, 0x10, 0x1c, 0x4b, 0x1a, 0xe8, 0x9f, 0x97, 0x35, 0x60, 0xac, 0x98, 0xa8, 0xdd, 0xb4, 0x4a,
0x0a, 0x40, 0x8e, 0x01, 0x74, 0x8c, 0x6b, 0xee, 0x7b, 0x63, 0x96, 0xbd, 0x0f, 0xaf, 0x11, 0xfb,
0x3c, 0xc1, 0xf0, 0xf5, 0xb6, 0x79, 0x28, 0x94, 0x2d, 0x63, 0x68, 0x0b, 0x01, 0x35, 0x46, 0x57,
0xbd, 0x6d, 0x8b, 0x00, 0x9e, 0x8c, 0x6c, 0x55, 0xff, 0x8d, 0x65, 0x47, 0x79, 0x76, 0xdb, 0xb6,
0x00, 0x62, 0x41, 0x39, 0x10, 0xee, 0x65, 0x6c, 0x5b, 0x04, 0xd5, 0x47, 0x9f, 0x07, 0x01, 0x74,
0xc1, 0x07, 0xa4, 0x58, 0xbd, 0x35, 0xc0, 0x40, 0xb2, 0x62, 0xd1, 0x1f, 0x5b, 0xc2, 0x84, 0x12,
0x63, 0xd5, 0x21, 0xb6, 0xdc, 0x28, 0x32, 0x8c, 0xe8, 0x43, 0x2f, 0x78, 0x69, 0x80, 0x51, 0x4a,
0xae, 0xa1, 0xa3, 0x9d, 0x87, 0x53, 0x81, 0xfe, 0x61, 0x28, 0x10, 0x01, 0x34, 0x03, 0xf7, 0x28,
0xfb, 0xf4, 0xdd, 0x8e, 0x98, 0xb3, 0xac, 0x65, 0x93, 0x92, 0x40, 0x25, 0x68, 0xe3, 0x93, 0x88,
0x5d, 0x04, 0xbc, 0x17, 0x32, 0x29, 0x4a, 0x93, 0x1d, 0x31, 0xf6, 0x29, 0xcb, 0xa0, 0xb9, 0x8d,
0x0b, 0x88, 0x25, 0x33, 0x1a, 0x04, 0x94, 0xb8, 0x22, 0xc6, 0xfc, 0x0e, 0xfa, 0xd8, 0x85, 0xb9,
0x57, 0x19, 0xa3, 0x1c, 0xbd, 0x09, 0xb6, 0xae, 0x62, 0x3a, 0x85, 0x86, 0xb6, 0x74, 0xba, 0x3f,
0x6e, 0x37, 0x9e, 0xee, 0xb0, 0xd5, 0x6e, 0x67, 0x07, 0x54, 0x4f, 0xc6, 0xc2, 0x65, 0x21, 0x0d,
0xe8, 0xec, 0xfe, 0xbb, 0x80, 0x44, 0x48, 0xce, 0x93, 0x84, 0x63, 0x7a, 0xd1, 0x19, 0xeb, 0x32,
0x48, 0x7d, 0x2a, 0x59, 0x96, 0xff, 0xf5, 0xe5, 0xf6, 0xae, 0xd0, 0x3a, 0xcf, 0x32, 0x96, 0xa6,
0xe1, 0xe1, 0x53, 0x76, 0x29, 0xa3, 0xa6, 0x4b, 0x27, 0xc5, 0x66, 0xb0, 0xa8, 0x38, 0xce, 0x07,
0x4a, 0x44, 0x9f, 0x85, 0x33, 0x39, 0x07, 0x6f, 0x6d, 0xe9, 0x94, 0xd5, 0xf3, 0x5f, 0xc3, 0x47,
0x25, 0x4d, 0x77, 0xe2, 0x18, 0xea, 0xad, 0x46, 0x6e, 0xbe, 0xde, 0xdd, 0x11, 0xac, 0xe7, 0xb0,
0xa2, 0xc0, 0xbb, 0x4f, 0x42, 0x7d, 0x1f, 0x2f, 0x17, 0x43, 0x8c, 0x38, 0xc8, 0xc9, 0xc0, 0x98,
0xc5, 0x21, 0xf5, 0xc9, 0x5c, 0x24, 0x32, 0x51, 0x78, 0x61, 0xdc, 0x61, 0xf6, 0x0c, 0xe8, 0x2b,
0xe1, 0x01, 0xc0, 0x04, 0x2c, 0x9b, 0xa3, 0x4d, 0x92, 0x08, 0xca, 0x00, 0x80, 0xbf, 0x50, 0x95,
0x46, 0x53, 0x35, 0x7a, 0x39, 0x1e, 0x9e, 0xb6, 0x4e, 0x4e, 0x00, 0xb9, 0x26, 0x4e, 0x6e, 0x7e,
0x32, 0x61, 0x09, 0x82, 0x5a, 0x02, 0xee, 0x0c, 0xf5, 0x1d, 0xa6, 0x3b, 0x92, 0x42, 0x12, 0x84,
0x76, 0x38, 0x23, 0x83, 0x97, 0x84, 0xc5, 0xa8, 0xa3, 0x84, 0x50, 0x40, 0x14, 0x82, 0xb6, 0xaa,
0x2b, 0xfa, 0x0a, 0x18, 0x0e, 0xe5, 0x91, 0xb0, 0x91, 0xff, 0x5a, 0x2b, 0x24, 0xa5, 0x40, 0x01,
0xcf, 0x1e, 0xee, 0x88, 0x62, 0x03, 0x97, 0x40, 0x9d, 0x0b, 0x39, 0xa3, 0x24, 0x98, 0x9a, 0xf1,
0x7c, 0xd5, 0x3c, 0x6f, 0x5e, 0x0b, 0x04, 0x77, 0x63, 0x83, 0x1a, 0xb5, 0x16, 0x7b, 0xd7, 0x6b,
0x5a, 0xdc, 0x74, 0xa7, 0xd1, 0xdb, 0xef, 0x4e, 0x23, 0x0b, 0xe3, 0x53, 0x6b, 0xf9, 0x22, 0x42,
0xe3, 0x9c, 0x72, 0x06, 0x72, 0x9e, 0xca, 0x39, 0x08, 0xfe, 0xc8, 0xc2, 0x85, 0x50, 0xd9, 0x0e,
0xbf, 0xad, 0x0a, 0x72, 0x54, 0xd4, 0x50, 0x17, 0x3e, 0xa3, 0xb1, 0x3a, 0x9d, 0x22, 0x24, 0x53,
0xce, 0x7c, 0x55, 0x48, 0x79, 0x3a, 0x50, 0xea, 0x44, 0xd5, 0x01, 0xfb, 0xc2, 0xc2, 0x04, 0x5d,
0x62, 0x03, 0x24, 0x8c, 0xf1, 0xba, 0xa7, 0x80, 0x04, 0x74, 0x25, 0x03, 0xdd, 0x46, 0x3b, 0xb6,
0xae, 0xc4, 0xf0, 0x7d, 0x57, 0xcd, 0xf2, 0x55, 0xcb, 0xdd, 0x8b, 0x41, 0xd6, 0xb8, 0xec, 0xfc,
0xcb, 0x9a, 0xbf, 0x19, 0xef, 0xa5, 0xf9, 0x9b, 0xaf, 0xc3, 0xdb, 0xd1, 0xdd, 0xdb, 0x69, 0x65,
0xed, 0xee, 0x27, 0x2b, 0x9b, 0xd0, 0x87, 0xb5, 0xd4, 0xc4, 0x85, 0xe8, 0x85, 0xb2, 0x8b, 0x53,
0x1f, 0x9c, 0x2d, 0x46, 0xcf, 0xc3, 0x1a, 0x0c, 0xb2, 0x38, 0xb8, 0x0f, 0xe4, 0x73, 0x70, 0xab,
0x14, 0xcb, 0xd3, 0xcc, 0xd1, 0xf0, 0x52, 0x54, 0x39, 0xe2, 0x17, 0x86, 0x4b, 0x72, 0xef, 0x52,
0x9c, 0x22, 0xd8, 0x04, 0xca, 0x30, 0x8f, 0x4c, 0x05, 0x12, 0x0b, 0x98, 0x88, 0x73, 0x47, 0x7e,
0x97, 0x47, 0x00, 0x94, 0x7b, 0xf1, 0x4a, 0x00, 0x6f, 0x52, 0xc0, 0xd7, 0xfb, 0xf1, 0xe5, 0x68,
0x45, 0x09, 0xc7, 0x96, 0x16, 0x7d, 0x98, 0xed, 0x51, 0x52, 0x76, 0xbe, 0x75, 0x81, 0x01, 0xa0,
0x9c, 0xf3, 0xf1, 0xaa, 0x1e, 0x4f, 0x8e, 0x35, 0x8b, 0x0b, 0x9f, 0xe3, 0x11, 0x07, 0xfd, 0x8d,
0x18, 0x92, 0x93, 0x5f, 0x0c, 0xfa, 0xa8, 0xcc, 0x75, 0x09, 0x32, 0x7f, 0xbd, 0x13, 0x11, 0x77,
0xdf, 0xe2, 0xd0, 0x5f, 0x33, 0xa2, 0x4a, 0x26, 0x57, 0x78, 0x3d, 0xb5, 0x9b, 0xfa, 0x6a, 0x1d,
0xc2, 0x50, 0xeb, 0xc3, 0x74, 0x02, 0xb5, 0xfe, 0xbc, 0xdc, 0x89, 0xed, 0x70, 0xbd, 0xde, 0xcd,
0x0f, 0xb4, 0x1d, 0x3f, 0x16, 0x33, 0xc1, 0x3f, 0x52, 0x6e, 0x08, 0x19, 0xe5, 0x0f, 0x2b, 0x11,
0xb3, 0xd4, 0xb9, 0x69, 0x0c, 0x06, 0x59, 0xfe, 0x12, 0x29, 0x71, 0x29, 0xc6, 0x2d, 0x00, 0x15,
0xba, 0x11, 0xa4, 0x44, 0x0f, 0x5a, 0xba, 0xc1, 0x50, 0x41, 0x17, 0x8e, 0xf8, 0x98, 0x23, 0x89,
0x76, 0x6e, 0x60, 0xa8, 0xc6, 0x7e, 0x3e, 0x87, 0x86, 0x57, 0xfe, 0x8c, 0x88, 0xa7, 0xf2, 0x41,
0x86, 0xb5, 0x73, 0x40, 0x70, 0x38, 0x4a, 0xdd, 0xc8, 0x8b, 0xff, 0xa1, 0x00, 0x28, 0x47, 0x5c,
0xd7, 0x4c, 0x56, 0x82, 0xe7, 0xfa, 0xf3, 0x9b, 0xd9, 0x1b, 0xca, 0x51, 0x87, 0xa0, 0x87, 0xbf,
0x96, 0xc0, 0xe8, 0x7a, 0xb0, 0x99, 0xce, 0xb2, 0x56, 0xf2, 0x3e, 0xa6, 0xfb, 0x5d, 0xf9, 0xed,
0x7a, 0xa8, 0xad, 0x02, 0x91, 0x18, 0xd6, 0xc0, 0x20, 0xba, 0x85, 0x7a, 0xd3, 0x90, 0xd7, 0xb7,
0xd8, 0xee, 0xdf, 0x86, 0x8d, 0xdb, 0xe9, 0x74, 0xc7, 0xcd, 0xc0, 0x35, 0x14, 0x0d, 0x64, 0xe9,
0xf6, 0x83, 0x2c, 0x5d, 0x5a, 0x6c, 0x13, 0xe8, 0x02, 0x48, 0xd4, 0x9d, 0x87, 0xca, 0x0f, 0xa0,
0xb8, 0x5e, 0x6e, 0x8f, 0xce, 0xd2, 0x2d, 0x71, 0xb6, 0xd8, 0x5a, 0xc3, 0xfd, 0x0c, 0x65, 0x92,
0x52, 0x75, 0x8f, 0x85, 0x82, 0x43, 0xea, 0x25, 0xfd, 0x37, 0xd7, 0x80, 0xeb, 0x87, 0xc8, 0xd7,
0xae, 0xbc, 0xd7, 0xa9, 0x8d, 0x37, 0xc8, 0x8f, 0x76, 0x93, 0x2f, 0xa8, 0x73, 0xc8, 0x1c, 0xaa,
0x4b, 0x0f, 0x74, 0xb5, 0x28, 0x4d, 0xe6, 0x3e, 0x0f, 0x1f, 0xf3, 0x20, 0x14, 0xe1, 0x92, 0xfb,
0x82, 0xaa, 0xa7, 0xf8, 0x6d, 0x47, 0xce, 0x21, 0x77, 0x27, 0xf4, 0x29, 0xeb, 0xb6, 0xf1, 0x3b,
0x64, 0x81, 0x82, 0x46, 0xe5, 0x79, 0xae, 0x12, 0x56, 0x0c, 0xa5, 0x40, 0x0e, 0xad, 0xe1, 0xac,
0x9a, 0x2b, 0x1e, 0x2a, 0x27, 0x99, 0xa2, 0x07, 0xe1, 0xad, 0x77, 0x21, 0x1c, 0x8f, 0xb0, 0x64,
0xd6, 0x75, 0xbe, 0x0e, 0x06, 0xe0, 0x3b, 0x49, 0xb9, 0xef, 0xe1, 0xd7, 0x1d, 0x58, 0xa9, 0x42,
0x6d, 0xcc, 0x62, 0x00, 0x73, 0x15, 0x64, 0x3d, 0x9a, 0x7a, 0x24, 0x86, 0xc2, 0xab, 0xdc, 0x44,
0xf4, 0xfa, 0x6b, 0x4d, 0x44, 0xb3, 0xd9, 0x06, 0x94, 0xc1, 0x5f, 0xcb, 0xda, 0x5a, 0xb3, 0xb7,
0x8e, 0x2c, 0x40, 0x51, 0xfc, 0xb5, 0xac, 0xad, 0xc5, 0xff, 0x89, 0x05, 0x5d, 0x33, 0xfe, 0xbe,
0xc1, 0x48, 0x47, 0x09, 0xfe, 0x6e, 0x67, 0xd4, 0x7e, 0x7f, 0x82, 0x6b, 0xe0, 0xf7, 0x0d, 0x46,
0x1f, 0x5a, 0x4d, 0xe8, 0x0d, 0xf0, 0x77, 0x3b, 0xa3, 0xa6, 0xa5, 0x76, 0x53, 0x7f, 0xde, 0x60,
0xd5, 0xd4, 0x42, 0x35, 0xcb, 0x52, 0xad, 0xf4, 0x18, 0x00, 0x5b, 0xbf, 0x31, 0x16, 0x61, 0x5d,
0xa6, 0x75, 0x85, 0x08, 0x8a, 0x69, 0x70, 0x10, 0x44, 0xb1, 0x78, 0xaa, 0x93, 0xb1, 0x80, 0xba,
0x7a, 0x22, 0x68, 0xec, 0xe9, 0x1a, 0x11, 0xf2, 0x20, 0x49, 0xd2, 0x48, 0x7d, 0x6b, 0x9b, 0x43,
0x38, 0x2a, 0x7b, 0xe4, 0xb7, 0x3b, 0xd8, 0xe7, 0xbe, 0xfd, 0xa5, 0xeb, 0x47, 0x3e, 0x5a, 0x19,
0x4b, 0x1f, 0xc4, 0xf0, 0xc3, 0x1c, 0xfc, 0xc1, 0x8f, 0x77, 0xf8, 0x25, 0x0f, 0xff, 0xab, 0xca,
0xff, 0x00, 0x30, 0x96, 0xbf, 0x5c, 0xba, 0x22, 0x00, 0x00
};

View File

@@ -186,18 +186,16 @@ void deserializeSegment(JsonObject elem, byte it, byte presetId)
byte fx = seg.mode;
if (getVal(elem["fx"], &fx, 0, strip.getModeCount())) { //load effect ('r' random, '~' inc/dec, 0-255 exact value)
if (!presetId && currentPlaylist>=0) unloadPlaylist();
if (fx != seg.mode) {
seg.setMode(fx, elem[F("fxdef")]);
}
if (fx != seg.mode) seg.setMode(fx, elem[F("fxdef")]);
}
//getVal also supports inc/decrementing and random
getVal(elem["sx"], &seg.speed);
getVal(elem["ix"], &seg.intensity);
uint8_t pal = seg.palette;
if (getVal(elem["pal"], &pal, 1, strip.getPaletteCount())) {
seg.setPalette(pal);
}
if (getVal(elem["pal"], &pal, 1, strip.getPaletteCount())) seg.setPalette(pal);
getVal(elem["c1"], &seg.custom1);
getVal(elem["c2"], &seg.custom2);
uint8_t cust3 = seg.custom3;

View File

@@ -888,17 +888,10 @@ bool handleSet(AsyncWebServerRequest *request, const String& req, bool apply)
for (uint8_t i = 0; i < strip.getSegmentsNum(); i++) {
Segment& seg = strip.getSegment(i);
if (i != selectedSeg && (singleSegment || !seg.isActive() || !seg.isSelected())) continue; // skip non main segments if not applying to all
if (fxModeChanged) {
seg.startTransition(strip.getTransition());
seg.mode = effectIn;
// TODO: we should load defaults here as well
}
if (fxModeChanged) seg.setMode(effectIn, req.indexOf(F("FXD="))>0); // apply defaults if FXD= is specified
if (speedChanged) seg.speed = speedIn;
if (intensityChanged) seg.intensity = intensityIn;
if (paletteChanged) {
if (strip.paletteBlend) seg.startTransition(strip.getTransition());
seg.palette = paletteIn;
}
if (paletteChanged) seg.setPalette(paletteIn);
}
//set advanced overlay

View File

@@ -110,8 +110,8 @@ void ESPAsyncE131::parsePacket(AsyncUDPPacket _packet) {
if (protocol == P_ARTNET) {
if (memcmp(sbuff->art_id, ESPAsyncE131::ART_ID, sizeof(sbuff->art_id)))
error = true; //not "Art-Net"
if (sbuff->art_opcode != ARTNET_OPCODE_OPDMX)
error = true; //not a DMX packet
if (sbuff->art_opcode != ARTNET_OPCODE_OPDMX && sbuff->art_opcode != ARTNET_OPCODE_OPPOLL)
error = true; //not a DMX or poll packet
} else { //E1.31 error handling
if (htonl(sbuff->root_vector) != ESPAsyncE131::VECTOR_ROOT)
error = true;

View File

@@ -57,6 +57,8 @@ typedef struct ip_addr ip4_addr_t;
#define DDP_TYPE_RGBW32 0x1A
#define ARTNET_OPCODE_OPDMX 0x5000
#define ARTNET_OPCODE_OPPOLL 0x2000
#define ARTNET_OPCODE_OPPOLLREPLY 0x2100
#define P_E131 0
#define P_ARTNET 1
@@ -154,6 +156,48 @@ typedef union {
uint8_t raw[1458];
} e131_packet_t;
typedef union {
struct {
uint8_t reply_id[8];
uint16_t reply_opcode;
uint8_t reply_ip[4];
uint16_t reply_port;
uint8_t reply_version_h;
uint8_t reply_version_l;
uint8_t reply_net_sw;
uint8_t reply_sub_sw;
uint8_t reply_oem_h;
uint8_t reply_oem_l;
uint8_t reply_ubea_ver;
uint8_t reply_status_1;
uint16_t reply_esta_man;
uint8_t reply_short_name[18];
uint8_t reply_long_name[64];
uint8_t reply_node_report[64];
uint8_t reply_num_ports_h;
uint8_t reply_num_ports_l;
uint8_t reply_port_types[4];
uint8_t reply_good_input[4];
uint8_t reply_good_output_a[4];
uint8_t reply_sw_in[4];
uint8_t reply_sw_out[4];
uint8_t reply_sw_video;
uint8_t reply_sw_macro;
uint8_t reply_sw_remote;
uint8_t reply_spare[3];
uint8_t reply_style;
uint8_t reply_mac[6];
uint8_t reply_bind_ip[4];
uint8_t reply_bind_index;
uint8_t reply_status_2;
uint8_t reply_good_output_b[4];
uint8_t reply_status_3;
uint8_t reply_filler[21];
} __attribute__((packed));
uint8_t raw[239];
} ArtPollReply;
// new packet callback
typedef void (*e131_packet_callback_function) (e131_packet_t* p, IPAddress clientIP, byte protocol);

View File

@@ -43,6 +43,34 @@ IPAddress NetworkClass::gatewayIP()
return INADDR_NONE;
}
void NetworkClass::localMAC(uint8_t* MAC)
{
#if defined(ARDUINO_ARCH_ESP32) && defined(WLED_USE_ETHERNET)
// ETH.macAddress(MAC); // Does not work because of missing ETHClass:: in ETH.ccp
// Start work around
String macString = ETH.macAddress();
char macChar[18];
char * octetEnd = macChar;
strlcpy(macChar, macString.c_str(), 18);
for (uint8_t i = 0; i < 6; i++) {
MAC[i] = (uint8_t)strtol(octetEnd, &octetEnd, 16);
octetEnd++;
}
// End work around
for (uint8_t i = 0; i < 6; i++) {
if (MAC[i] != 0x00) {
return;
}
}
#endif
WiFi.macAddress(MAC);
return;
}
bool NetworkClass::isConnected()
{
#if defined(ARDUINO_ARCH_ESP32) && defined(WLED_USE_ETHERNET)

View File

@@ -14,6 +14,7 @@ public:
IPAddress localIP();
IPAddress subnetMask();
IPAddress gatewayIP();
void localMAC(uint8_t* MAC);
bool isConnected();
bool isEthernet();
};

View File

@@ -383,10 +383,10 @@ WLED_GLOBAL uint16_t e131Universe _INIT(1); // settings fo
WLED_GLOBAL uint16_t e131Port _INIT(5568); // DMX in port. E1.31 default is 5568, Art-Net is 6454
WLED_GLOBAL byte DMXMode _INIT(DMX_MODE_MULTIPLE_RGB); // DMX mode (s.a.)
WLED_GLOBAL uint16_t DMXAddress _INIT(1); // DMX start address of fixture, a.k.a. first Channel [for E1.31 (sACN) protocol]
WLED_GLOBAL byte DMXOldDimmer _INIT(0); // only update brightness on change
WLED_GLOBAL byte e131LastSequenceNumber[E131_MAX_UNIVERSE_COUNT]; // to detect packet loss
WLED_GLOBAL bool e131Multicast _INIT(false); // multicast or unicast
WLED_GLOBAL bool e131SkipOutOfSequence _INIT(false); // freeze instead of flickering
WLED_GLOBAL uint16_t pollReplyCount _INIT(0); // count number of replies for ArtPoll node report
WLED_GLOBAL bool mqttEnabled _INIT(false);
WLED_GLOBAL char mqttDeviceTopic[33] _INIT(""); // main MQTT topic (individual per device, default is wled/mac)

View File

@@ -20,6 +20,8 @@ enum class AdaState {
};
uint16_t currentBaud = 1152; //default baudrate 115200 (divided by 100)
bool continuousSendLED = false;
uint32_t lastUpdate = 0;
void updateBaudRate(uint32_t rate){
uint16_t rate100 = rate/100;
@@ -33,7 +35,38 @@ void updateBaudRate(uint32_t rate){
Serial.flush();
Serial.begin(rate);
}
// RGB LED data return as JSON array. Slow, but easy to use on the other end.
void sendJSON(){
if (!pinManager.isPinAllocated(hardwareTX) || pinManager.getPinOwner(hardwareTX) == PinOwner::DebugOut) {
uint16_t used = strip.getLengthTotal();
Serial.write('[');
for (uint16_t i=0; i<used; i++) {
Serial.print(strip.getPixelColor(i));
if (i != used-1) Serial.write(',');
}
Serial.println("]");
}
}
// RGB LED data returned as bytes in TPM2 format. Faster, and slightly less easy to use on the other end.
void sendBytes(){
if (!pinManager.isPinAllocated(hardwareTX) || pinManager.getPinOwner(hardwareTX) == PinOwner::DebugOut) {
Serial.write(0xC9); Serial.write(0xDA);
uint16_t used = strip.getLengthTotal();
uint16_t len = used*3;
Serial.write(highByte(len));
Serial.write(lowByte(len));
for (uint16_t i=0; i < used; i++) {
uint32_t c = strip.getPixelColor(i);
Serial.write(qadd8(W(c), R(c))); //R, add white channel to RGB channels as a simple RGBW -> RGB map
Serial.write(qadd8(W(c), G(c))); //G
Serial.write(qadd8(W(c), B(c))); //B
}
Serial.write(0x36); Serial.write('\n');
}
}
void handleSerial()
{
if (pinManager.isPinAllocated(hardwareRX)) return;
@@ -70,32 +103,13 @@ void handleSerial()
} else if (next == 0xB5) {updateBaudRate( 921600);
} else if (next == 0xB6) {updateBaudRate(1000000);
} else if (next == 0xB7) {updateBaudRate(1500000);
} else if (next == 'l') { //RGB(W) LED data return as JSON array. Slow, but easy to use on the other end.
if (!pinManager.isPinAllocated(hardwareTX) || pinManager.getPinOwner(hardwareTX) == PinOwner::DebugOut){
uint16_t used = strip.getLengthTotal();
Serial.write('[');
for (uint16_t i=0; i<used; i+=1) {
Serial.print(strip.getPixelColor(i));
if (i != used-1) Serial.write(',');
}
Serial.println("]");
}
} else if (next == 'L') { //RGB LED data returned as bytes in tpm2 format. Faster, and slightly less easy to use on the other end.
if (!pinManager.isPinAllocated(hardwareTX) || pinManager.getPinOwner(hardwareTX) == PinOwner::DebugOut) {
Serial.write(0xC9); Serial.write(0xDA);
uint16_t used = strip.getLengthTotal();
uint16_t len = used*3;
Serial.write(highByte(len));
Serial.write(lowByte(len));
for (uint16_t i=0; i < used; i++) {
uint32_t c = strip.getPixelColor(i);
Serial.write(qadd8(W(c), R(c))); //R, add white channel to RGB channels as a simple RGBW -> RGB map
Serial.write(qadd8(W(c), G(c))); //G
Serial.write(qadd8(W(c), B(c))); //B
}
Serial.write(0x36); Serial.write('\n');
}
} else if (next == 'l') {sendJSON(); // Send LED data as JSON Array
} else if (next == 'L') {sendBytes(); // Send LED data as TPM2 Data Packet
} else if (next == 'o') {continuousSendLED = false; // Disable Continuous Serial Streaming
} else if (next == 'O') {continuousSendLED = true; // Enable Continuous Serial Streaming
} else if (next == '{') { //JSON API
bool verboseResponse = false;
if (!requestJSONBufferLock(16)) return;
@@ -177,7 +191,19 @@ void handleSerial()
}
break;
}
// All other received bytes will disable Continuous Serial Streaming
if (continuousSendLED && next != 'O'){
continuousSendLED = false;
}
Serial.read(); //discard the byte
}
#endif
// If Continuous Serial Streaming is enabled, send new LED data as bytes
if (continuousSendLED && (lastUpdate != strip.getLastShow())){
sendBytes();
lastUpdate = strip.getLastShow();
}
}