From a08370ce97e2777825d55bb2144474619091a4da Mon Sep 17 00:00:00 2001 From: tipouic Date: Sat, 19 Nov 2016 22:54:18 +0100 Subject: [PATCH] Suivit --- Multiprotocol/A7105_joysway.ino | 156 ++++++++++++++++---------------- Multiprotocol/Multiprotocol.ino | 43 ++++++--- Multiprotocol/SLT_nrf24l01.ino | 118 +++++++++++------------- Multiprotocol/TX_Def.h | 1 + Multiprotocol/V2X2_nrf24l01.ino | 11 +-- Multiprotocol/_Config.h | 2 +- Multiprotocol/multiprotocol.h | 9 +- Multiprotocol/sync.ffs_db | Bin 1094 -> 1013 bytes 8 files changed, 173 insertions(+), 167 deletions(-) diff --git a/Multiprotocol/A7105_joysway.ino b/Multiprotocol/A7105_joysway.ino index 572ca9f..e29fc2b 100644 --- a/Multiprotocol/A7105_joysway.ino +++ b/Multiprotocol/A7105_joysway.ino @@ -20,108 +20,106 @@ #define EVEN_ODD 0x00 //#define EVEN_ODD 0x01 -static uint8_t PROGMEM A7105_regs[] = { +const uint8_t PROGMEM JOYSWAY_A7105_regs[] = { 0x00, 0x62, 0xFF, 0x0f, 0x00, 0xFF , 0xFF , 0x00, 0x00, 0x05, 0x00, 0x01, 0x00, 0xf5, 0x00, 0x15, 0x9e, 0x4b, 0x00, 0x03, 0x56, 0x2b, 0x12, 0x4a, 0x02, 0x80, 0x80, 0x00, 0x0e, 0x91, 0x03, 0x0f, 0x16, 0x2a, 0x00, 0xFF, 0xFF, 0xFF, 0x3a, 0x06, 0x1f, 0x47, 0x80, 0x01, 0x05, 0x45, 0x18, 0x00, 0x01, 0x0f, 0x00 }; -static void joysway_build_packet() -{ - int i; - //-100% =~ 0x03e8 - //+100% =~ 0x07ca - //Calculate: - //Center = 0x5d9 - //1 % = 5 - packet[0] = phase == 0 ? 0xdd : 0xff; - packet[1] = (MProtocol_id >> 24) & 0xff; - packet[2] = (MProtocol_id >> 16) & 0xff; - packet[3] = (MProtocol_id >> 8) & 0xff; - packet[4] = (MProtocol_id >> 0) & 0xff; - packet[5] = 0x00; - static const int chmap[4] = {6, 7, 10, 11}; - for (i = 0; i < 4; i++) { -// if (i >= Model.num_channels) { packet[chmap[i]] = 0x64; continue; } - packet[chmap[i]] = map(limit_channel_100(i),servo_min_100,servo_max_100,0,204); - } - packet[8] = 0x64; - packet[9] = 0x64; - packet[12] = 0x64; - packet[13] = 0x64; - packet[14] = phase == 0 ? 0x30 : 0xaa; - uint8_t value = 0; - for (int i = 0; i < 15; i++) { value += packet[i]; } - packet[15] = value; +static void joysway_build_packet() { + int i; + //-100% =~ 0x03e8 + //+100% =~ 0x07ca + //Calculate: + //Center = 0x5d9 + //1 % = 5 + packet[0] = phase == 0 ? 0xdd : 0xff; + packet[1] = (MProtocol_id >> 24) & 0xff; + packet[2] = (MProtocol_id >> 16) & 0xff; + packet[3] = (MProtocol_id >> 8) & 0xff; + packet[4] = (MProtocol_id >> 0) & 0xff; + packet[5] = 0x00; + static const int chmap[4] = {6, 7, 10, 11}; + for (i = 0; i < 4; i++) { +// if (i >= Model.num_channels) { packet[chmap[i]] = 0x64; continue; } + packet[chmap[i]] = map(limit_channel_100(i),servo_min_100,servo_max_100,0,204); + } + packet[8] = 0x64; + packet[9] = 0x64; + packet[12] = 0x64; + packet[13] = 0x64; + packet[14] = phase == 0 ? 0x30 : 0xaa; + uint8_t value = 0; + for (int i = 0; i < 15; i++) { value += packet[i]; } + packet[15] = value; } -static uint16_t joysway_cb() -{ - if (phase == 254) { - phase = 0; - A7105_WriteID(0x5475c52a); - hopping_frequency_no = 0x0a; - } else if (phase == 2) { - A7105_WriteID(MProtocol_id); - hopping_frequency_no = 0x30; - } else { - if ((phase & 0x01) ^ EVEN_ODD) { - hopping_frequency_no = 0x30; - } else { - hopping_frequency_no = rf_ch_num; - } - } - if (! ((phase & 0x01) ^ EVEN_ODD)) { - rf_ch_num++; - if (rf_ch_num == 0x45) - rf_ch_num = 0x30; - } - joysway_build_packet(); - A7105_Strobe(A7105_STANDBY); - A7105_WriteData(16, hopping_frequency_no); - phase++; - return 6000; +static uint16_t joysway_cb() { + if (phase == 254) { + phase = 0; + A7105_WriteID(0x5475c52a); + hopping_frequency_no = 0x0a; + } else if (phase == 2) { + A7105_WriteID(MProtocol_id); + hopping_frequency_no = 0x30; + } else { + if ((phase & 0x01) ^ EVEN_ODD) { + hopping_frequency_no = 0x30; + } else { + hopping_frequency_no = rf_ch_num; + } + } + if (! ((phase & 0x01) ^ EVEN_ODD)) { + rf_ch_num++; + if (rf_ch_num == 0x45) + rf_ch_num = 0x30; + } + joysway_build_packet(); + A7105_Strobe(A7105_STANDBY); + A7105_WriteData(16, hopping_frequency_no); + phase++; + return 6000; } static uint16_t JOYSWAY_Setup() { - int i; - u8 if_calibration1; - //u8 vco_calibration0; - //u8 vco_calibration1; + int i; + u8 if_calibration1; + //u8 vco_calibration0; + //u8 vco_calibration1; - counter = 0; - next_ch = 0x30; + counter = 0; +// next_ch = 0x30; - for (i = 0; i < 0x33; i++) { - uint8_t val=pgm_read_byte_near(&A7105_Regs[i]); + for (i = 0; i < 0x33; i++) { + uint8_t val=pgm_read_byte_near(&JOYSWAY_A7105_regs[i]); if( val != 0xFF) A7105_WriteReg(i, val); } - A7105_WriteID(0x5475c52a); + A7105_WriteID(0x5475c52a); - A7105_Strobe(A7105_PLL); + A7105_Strobe(A7105_PLL); - //IF Filter Bank Calibration - A7105_WriteReg(0x02, 1); + //IF Filter Bank Calibration + A7105_WriteReg(0x02, 1); while(A7105_ReadReg(A7105_02_CALC)); // Wait for calibration to end - A7105_Strobe(A7105_STANDBY); + A7105_Strobe(A7105_STANDBY); - //VCO Current Calibration - A7105_WriteReg(0x24, 0x13); //Recomended calibration from A7105 Datasheet - A7105_WriteReg(0x25, 0x09); //Recomended calibration from A7105 Datasheet + //VCO Current Calibration + A7105_WriteReg(0x24, 0x13); //Recomended calibration from A7105 Datasheet + A7105_WriteReg(0x25, 0x09); //Recomended calibration from A7105 Datasheet - A7105_WriteID(MProtocol_id); - A7105_Strobe(A7105_PLL); - A7105_WriteReg(0x02, 1); + A7105_WriteID(MProtocol_id); + A7105_Strobe(A7105_PLL); + A7105_WriteReg(0x02, 1); while(A7105_ReadReg(A7105_02_CALC)); // Wait for calibration to end - A7105_Strobe(A7105_STANDBY); - A7105_WriteReg(0x24, 0x13); //Recomended calibration from A7105 Datasheet - A7105_WriteReg(0x25, 0x09); //Recomended calibration from A7105 Datasheet + A7105_Strobe(A7105_STANDBY); + A7105_WriteReg(0x24, 0x13); //Recomended calibration from A7105 Datasheet + A7105_WriteReg(0x25, 0x09); //Recomended calibration from A7105 Datasheet - A7105_SetTxRxMode(TX_EN); - A7105_SetPower(); + A7105_SetTxRxMode(TX_EN); + A7105_SetPower(); - A7105_Strobe(A7105_STANDBY); + A7105_Strobe(A7105_STANDBY); return 2400; } #endif diff --git a/Multiprotocol/Multiprotocol.ino b/Multiprotocol/Multiprotocol.ino index 636e627..94ca4f4 100644 --- a/Multiprotocol/Multiprotocol.ino +++ b/Multiprotocol/Multiprotocol.ino @@ -477,13 +477,15 @@ void Update_All() } update_aux_flags(); PPM_FLAG_off; // wait for next frame before update + INPUT_SIGNAL_on; //valid signal received + last_signal=millis(); } #endif //ENABLE_PPM - update_led_status(); #if defined(TELEMETRY) if((protocol==MODE_FRSKYD) || (protocol==MODE_HUBSAN) || (protocol==MODE_AFHDS2A) || (protocol==MODE_FRSKYX) || (protocol==MODE_DSM) ) TelemetryUpdate(); #endif + update_led_status(); } // Update Servo_AUX flags based on servo AUX positions @@ -508,23 +510,32 @@ static void update_aux_flags(void) // Update led status based on binding and serial static void update_led_status(void) { + if(IS_INPUT_SIGNAL_on) + if(millis()-last_signal>50) + INPUT_SIGNAL_off; //no valid signal (PPM or Serial) received for 50ms if(blink led on else + { + if(IS_BIND_DONE_on) + LED_off; //bind completed force led on blink+=BLINK_BIND_TIME; //blink fastly during binding + } LED_toggle; } } @@ -1150,25 +1161,27 @@ static uint32_t random_id(uint16_t adress, uint8_t create_new) #endif #endif { // Interrupt on PPM pin - static int8_t chan=-1; + static int8_t chan=0,bad_frame=1; static uint16_t Prev_TCNT1=0; uint16_t Cur_TCNT1; Cur_TCNT1=TCNT1-Prev_TCNT1; // Capture current Timer1 value if(Cur_TCNT1<1000) - chan=-1; // bad frame + bad_frame=1; // bad frame else if(Cur_TCNT1>4840) - { - chan=0; // start of frame - PPM_FLAG_on; // full frame present (even at startup since PPM_data has been initialized) + { //start of frame + if(chan>3) + PPM_FLAG_on; // good frame received if at least 4 channels have been seen + chan=0; // reset channel counter + bad_frame=0; } else - if(chan!=-1) // need to wait for start of frame + if(bad_frame==0) // need to wait for start of frame { //servo values between 500us and 2420us will end up here PPM_data[chan]= Cur_TCNT1>>1;; if(chan++>=NUM_CHN) - chan=-1; // don't accept any new channels + bad_frame=1; // don't accept any new channels } Prev_TCNT1+=Cur_TCNT1; } diff --git a/Multiprotocol/SLT_nrf24l01.ino b/Multiprotocol/SLT_nrf24l01.ino index 8d4e486..9778d3c 100644 --- a/Multiprotocol/SLT_nrf24l01.ino +++ b/Multiprotocol/SLT_nrf24l01.ino @@ -12,7 +12,7 @@ You should have received a copy of the GNU General Public License along with Multiprotocol. If not, see . */ -// Last sync with hexfet new_protocols/slt_nrf24l01.c dated 2015-02-13 +// Last sync with deviation main github branch #if defined(SLT_NRF24L01_INO) @@ -24,11 +24,11 @@ #define SLT_TXID_SIZE 4 enum { - SLT_INIT2 = 0, - SLT_BIND, + SLT_BUILD=0, SLT_DATA1, SLT_DATA2, - SLT_DATA3 + SLT_DATA3, + SLT_BIND }; static void __attribute__((unused)) SLT_init() @@ -45,24 +45,18 @@ static void __attribute__((unused)) SLT_init() NRF24L01_SetPower(); NRF24L01_WriteRegisterMulti(NRF24L01_0A_RX_ADDR_P0, (uint8_t*)"\xC3\xC3\xAA\x55", 4); NRF24L01_FlushRx(); -} - -static void __attribute__((unused)) SLT_init2() -{ + NRF24L01_WriteRegisterMulti(NRF24L01_10_TX_ADDR, rx_tx_addr, SLT_TXID_SIZE); NRF24L01_FlushTx(); - packet_sent = 0; - hopping_frequency_no = 0; - // Turn radio power on NRF24L01_SetTxRxMode(TX_EN); } -static void __attribute__((unused)) SLT_set_tx_id(void) +static void __attribute__((unused)) SLT_set_freq(void) { // Frequency hopping sequence generation - for (uint8_t i = 0; i < 4; ++i) + for (uint8_t i = 0; i < SLT_TXID_SIZE; ++i) { - uint8_t next_i = (i+1) % 4; // is & 3 better than % 4 ? + uint8_t next_i = (i+1) % SLT_TXID_SIZE; // is & 3 better than % 4 ? uint8_t base = i < 2 ? 0x03 : 0x10; hopping_frequency[i*4 + 0] = (rx_tx_addr[i] & 0x3f) + base; hopping_frequency[i*4 + 1] = (rx_tx_addr[i] >> 2) + base; @@ -72,8 +66,9 @@ static void __attribute__((unused)) SLT_set_tx_id(void) } // unique - uint8_t done = 0; for (uint8_t i = 0; i < SLT_NFREQCHANNELS; ++i) + { + uint8_t done = 0; while (!done) { done = 1; @@ -86,14 +81,13 @@ static void __attribute__((unused)) SLT_set_tx_id(void) hopping_frequency[i] = hopping_frequency[i] - 0x50 + 0x03; } } - - NRF24L01_WriteRegisterMulti(NRF24L01_10_TX_ADDR, rx_tx_addr, 4); + } } static void __attribute__((unused)) SLT_wait_radio() { if (packet_sent) - while (!(NRF24L01_ReadReg(NRF24L01_07_STATUS) & _BV(NRF24L01_07_TX_DS))) ; + while (!(NRF24L01_ReadReg(NRF24L01_07_STATUS) & _BV(NRF24L01_07_TX_DS))); packet_sent = 0; } @@ -109,9 +103,15 @@ static void __attribute__((unused)) SLT_send_data(uint8_t *data, uint8_t len) static void __attribute__((unused)) SLT_build_packet() { - // aileron, elevator, throttle, rudder, gear, pitch + // Set radio channel - once per packet batch + NRF24L01_WriteReg(NRF24L01_05_RF_CH, hopping_frequency[hopping_frequency_no]); + if (++hopping_frequency_no >= SLT_NFREQCHANNELS) + hopping_frequency_no = 0; + + // aileron, elevator, throttle, rudder, gear, pitch uint8_t e = 0; // byte where extension 2 bits for every 10-bit channel are packed - for (uint8_t i = 0; i < 4; ++i) { + for (uint8_t i = 0; i < 4; ++i) + { uint16_t v = convert_channel_10b(CH_AETR[i]); packet[i] = v; e = (e >> 2) | (uint8_t) ((v >> 2) & 0xC0); @@ -121,81 +121,71 @@ static void __attribute__((unused)) SLT_build_packet() // 8-bit channels packet[5] = convert_channel_8b(AUX1); packet[6] = convert_channel_8b(AUX2); - - // Set radio channel - once per packet batch - NRF24L01_WriteReg(NRF24L01_05_RF_CH, hopping_frequency[hopping_frequency_no]); - if (++hopping_frequency_no >= SLT_NFREQCHANNELS) - hopping_frequency_no = 0; } static void __attribute__((unused)) SLT_send_bind_packet() { SLT_wait_radio(); - BIND_IN_PROGRESS; // autobind protocol + BIND_IN_PROGRESS; //Limit TX power to bind level NRF24L01_SetPower(); - NRF24L01_WriteRegisterMulti(NRF24L01_10_TX_ADDR, (uint8_t *)"\x7E\xB8\x63\xA9", 4); + BIND_DONE; + NRF24L01_WriteRegisterMulti(NRF24L01_10_TX_ADDR, (uint8_t *)"\x7E\xB8\x63\xA9", SLT_TXID_SIZE); NRF24L01_WriteReg(NRF24L01_05_RF_CH, 0x50); - SLT_send_data(rx_tx_addr, 4); + SLT_send_data(rx_tx_addr, SLT_TXID_SIZE); - // NB: we should wait until the packet's sent before changing TX address! - SLT_wait_radio(); + SLT_wait_radio(); //Wait until the packet's sent before changing TX address! - BIND_DONE; - NRF24L01_SetPower(); - NRF24L01_WriteRegisterMulti(NRF24L01_10_TX_ADDR, rx_tx_addr, 4); + NRF24L01_SetPower(); //Change power back to normal level + NRF24L01_WriteRegisterMulti(NRF24L01_10_TX_ADDR, rx_tx_addr, SLT_TXID_SIZE); } uint16_t SLT_callback() { - uint16_t delay_us = 20000; // 3 packets with 1ms intervals every 22ms switch (phase) { - case SLT_INIT2: - SLT_init2(); - phase = SLT_BIND; - delay_us = 150; - break; - case SLT_BIND: - SLT_send_bind_packet(); - phase = SLT_DATA1; - delay_us = 19000; - break; - case SLT_DATA1: + case SLT_BUILD: SLT_build_packet(); - SLT_send_data(packet, 7); - phase = SLT_DATA2; - delay_us = 1000; - break; + phase++; + return 1000; + case SLT_DATA1: + SLT_send_data(packet, SLT_PAYLOADSIZE); + phase++; + return 1000; case SLT_DATA2: - SLT_send_data(packet, 7); - phase = SLT_DATA3; - delay_us = 1000; - break; + SLT_send_data(packet, SLT_PAYLOADSIZE); + phase++; + return 1000; case SLT_DATA3: - SLT_send_data(packet, 7); - if (++counter >= 100) + SLT_send_data(packet, SLT_PAYLOADSIZE); + if (++packet_count >= 100) { - counter = 0; - phase = SLT_BIND; - delay_us = 1000; + packet_count = 0; + phase++; + return 1000; } else { NRF24L01_SetPower(); // Set tx_power - phase = SLT_DATA1; + phase = SLT_BUILD; + return 19000; } - break; + case SLT_BIND: + SLT_send_bind_packet(); + phase = SLT_BUILD; + return 18000; } - return delay_us; + return 19000; } uint16_t initSLT() { - counter = 0; + packet_count = 0; + packet_sent = 0; + hopping_frequency_no = 0; + SLT_set_freq(); SLT_init(); - phase = SLT_INIT2; - SLT_set_tx_id(); + phase = SLT_BIND; return 50000; } diff --git a/Multiprotocol/TX_Def.h b/Multiprotocol/TX_Def.h index caef39d..ef18d5e 100644 --- a/Multiprotocol/TX_Def.h +++ b/Multiprotocol/TX_Def.h @@ -56,6 +56,7 @@ //PPM values used to compare #define PPM_MIN_COMMAND 1250 #define PPM_SWITCH 1550 +#define PPM_SWITCH_B 1450 #define PPM_MAX_COMMAND 1750 //Channel definitions diff --git a/Multiprotocol/V2X2_nrf24l01.ino b/Multiprotocol/V2X2_nrf24l01.ino index fc5aa9d..999410f 100644 --- a/Multiprotocol/V2X2_nrf24l01.ino +++ b/Multiprotocol/V2X2_nrf24l01.ino @@ -196,14 +196,11 @@ static void __attribute__((unused)) V2X2_send_packet(uint8_t bind) // Channel 11 if (Servo_AUX7) flags2 |= JXD_FLAG_EMERGENCY; -/* // Channel 12 down - if (num_channels < 11 || Channels[CHANNEL11] >= CHAN_MIN_VALUE/2) *flags2 &= ~FLAG_CAMERA_DN; - else *flags2 |= JXD_FLAG_CAMERA_DN; - + // Channel 12 down + if (Servo_data[AUX8] < PPM_SWITCH_B) flags2 |= JXD_FLAG_CAMERA_DN; // Channel 12 up - if (num_channels < 11 || Channels[CHANNEL11] <= CHAN_MAX_VALUE/2) *flags2 &= ~FLAG_CAMERA_UP; - else *flags2 |= JXD_FLAG_CAMERA_UP; -*/ + if (Servo_data[AUX8] > PPM_SWITCH) flags2 |= JXD_FLAG_CAMERA_UP; + } else { // Channel 10 if (Servo_AUX6) diff --git a/Multiprotocol/_Config.h b/Multiprotocol/_Config.h index 07f5dc2..50d574f 100644 --- a/Multiprotocol/_Config.h +++ b/Multiprotocol/_Config.h @@ -60,7 +60,7 @@ //Comment the protocols you are not using with "//" to save Flash space. //The protocols below need an A7105 to be installed -// #define JOYSWAY_A7105_INO + #define JOYSWAY_A7105_INO #define FLYSKY_A7105_INO #define HUBSAN_A7105_INO diff --git a/Multiprotocol/multiprotocol.h b/Multiprotocol/multiprotocol.h index be11096..68caa59 100644 --- a/Multiprotocol/multiprotocol.h +++ b/Multiprotocol/multiprotocol.h @@ -167,7 +167,7 @@ enum FY326 FY326 = 0, FY319 = 1 }; -enum{ +enum V2X2 { FORMAT_V202 = 0, FORMAT_JXD506 = 1, }; @@ -266,12 +266,18 @@ struct PPM_Parameters #define IS_TX_RX_PAUSE_on ( ( protocol_flags2 & _BV(4) ) !=0 ) #define IS_TX_PAUSE_on ( ( protocol_flags2 & (_BV(4)|_BV(3)) ) !=0 ) +//Signal OK +#define INPUT_SIGNAL_off protocol_flags2 &= ~_BV(5) +#define INPUT_SIGNAL_on protocol_flags2 |= _BV(5) +#define IS_INPUT_SIGNAL_on ( ( protocol_flags2 & _BV(5) ) !=0 ) +#define IS_INPUT_SIGNAL_off ( ( protocol_flags2 & _BV(5) ) ==0 ) //******************** //*** Blink timing *** //******************** #define BLINK_BIND_TIME 100 #define BLINK_SERIAL_TIME 500 +#define BLINK_PPM_TIME 1000 #define BLINK_BAD_PROTO_TIME_LOW 1000 #define BLINK_BAD_PROTO_TIME_HIGH 50 @@ -461,6 +467,7 @@ Serial: 100000 Baud 8e2 _ xxxx xxxx p -- DSM2_11 1 DSMX_22 2 DSMX_11 3 + DSM_AUTO 4 sub_protocol==YD717 YD717 0 SKYWLKR 1 diff --git a/Multiprotocol/sync.ffs_db b/Multiprotocol/sync.ffs_db index c065aeab6f818e680712ab90da67f39103e03519..ef0ab5b6e240d7449385800e71903eb8a557b56e 100644 GIT binary patch delta 1002 zcmV41Xj_iBpaOC2~V&feyW5 zt*wp3`T`A27L@|tTHuGi<-1u`dE~4C^yBR&N`Vg^p(xa`TZL4%X$8@iM_(`kbmu%j z*~}F;!nPY9uHSiQf@?9yvRwxYm0u_Sqk>5T<|pF;=-kg?CyUgJggRDiQoKVMkF2-as?srn12aW zXTGV^+aP_UHLtS}6c?UG9Y^fHqceOnc^Zz_XQled=MLto(Wsk-)|}DAJ@J9h)iwe) zwW(@dQ`q$|%a3-5W#~1-7&|nU`Nx3kMopVvoRPY*oPU}+W3DCPm-*qh1tgMN^=#^9 zG=@DSx49U1AhxiJdpHc@ruwQe6X5=6waqHFnGJuSlgR@2m(;c@4-c;}II@IXr$gqK zZ9Shl9&XoB*p&wA30O`R6mYp(%FE~Yd43as(I&a;Z08;mS9p2g4m35b(OjsD;@oDU z@%jhy9e<&8+5rFncm@Cf00000cwTkYO(?^07zgmbZDAp_T)e*);dsFe763_^}k*tZAgcAKH4zD!tu;60^%d$C?qctvgz+zNlMN~8Q55AEz`;l8@yxq80GZn&n1y+_FD z72E>1_&@2~tZ?Uvj_U7&-x_#d8+`kf=VQbkyO%qDuKR_02H^4UlR>yv#qWUt{5zCR zbq)!0;t<|%4y;e!F;UJ0d_BzdJB54~@|Ui;&S9)S{;H;Y7kodH_Z@*xd3gTa!W?>p Ydc5$HApehy#^!38=XMPK19yU7Wf7yoZ%S+000620002u0RR9100014P*M!! zE>QHzbSlkJag!APWA`MUG#kaAavU63C^bX55-#vcfN^j`?$rj*9RwC*l)sLB9HI!v zq0)=`5aRX!KhPZD78+;+JFbTn(USn2n`1dr!a`?7^6w;10e>uRv@4b2P@bDNdXpSk_PDWAqZlLinHz&(jGZ+ zHqADn^or$j(tkw98DT7wUjI@tiL#xK8@QfC!u8RXka+z2cO-nQl@f{n_+iE*?iSUe zka)mP0=Ki&GU#iN9cis=ECj`cr*YR6`)?Tx-$A~n>krsfec^ovebsC>EK_gI>*Aew z$@^+20bBZPt)VOId06119b%bA-83hL#u`5ixNg?&ygrKiVCuh8R?@gU&(NbH^dji)KSG=y@H1-?Nq+`E9oYfmJ57#5hR63we~$R?rFP=1 z=7i&yd|X$2iQ!t4zwfxN7vQLMZMwtts{AdJuZ#272>B_n@Ut}#&Z~0v;8V?8hQ4hi z#D7p-h2Z~a{!Mwy5wE4MkX~V-zl0vlc|`mo@TXI`|GVhJOmK(zmEh!$@mxy4@$c}y zWnk`2$y`_IUEU8<#IFK>TG6Ya`*XigyyO~lu}f>!Q>rTydDT82nswR5b9+D>7x?PD z8eK+ww44v}`zp7X`+ylA8!`7GQ+LRx6n}n4UgVu?V*hX9|3cBbp{w&cMqO!6p5rU{ z)G}B-@N_Co;##&A({H`LEa5F=dFkS^_cgh0lH_K-}T(Q!PiCg zc?Cb}J;??q#>RJ`5&Eq^o_w}g+<{t)`xeBzQ1_}1@sk1e-)_NgK>X+$`|QPhXEiUG z^BSDK&pP>kkNxcQ^8O5hqwe!ZGhUCl+c&7|+f^3ve|n5~o1}H|-lm)WW92`;*JlgL C_$$Hy