diff --git a/Lua_scripts/MultiChan.txt b/Lua_scripts/MultiChan.txt index 86445a6..3054514 100644 --- a/Lua_scripts/MultiChan.txt +++ b/Lua_scripts/MultiChan.txt @@ -38,7 +38,6 @@ 70,1,DSM_RX,CPPM,0,CH5,CH6,CH7,CH8,CH9,CH10,CH11,CH12 45,0,E01X,E012,1,n-a,Flip,n-a,HLess,RTH 45,1,E01X,E015,1,Arm,Flip,LED,HLess,RTH -45,2,E01X,E016H,1,Stop,Flip,n-a,HLess,RTH 16,0,ESKY,Std,0,Gyro,Pitch 16,1,ESKY,ET4,0,Gyro,Pitch 35,0,ESKY150,4CH,0 @@ -190,3 +189,4 @@ 82,0,LOLI,Std,0,CH5,CH6,CH7,CH8,1SwSePpPw,2SwSePw,3SwSe,4SwSe,5SwSeSb,6SwSe,7SwSePw,8SwSe 83,0,E129,E129,1,TakLan,EmStop,TrimA,TrimE,TrimR 84,0,JOYSWAY,Std,0 +85,0,E016H,Std,1,Stop,Flip,n-a,HLess,RTH diff --git a/Multiprotocol/BUGSMINI_nrf24l01.ino b/Multiprotocol/BUGSMINI_nrf24l01.ino index 0e45c35..36d4a36 100644 --- a/Multiprotocol/BUGSMINI_nrf24l01.ino +++ b/Multiprotocol/BUGSMINI_nrf24l01.ino @@ -16,7 +16,7 @@ #if defined(BUGSMINI_NRF24L01_INO) -#include "iface_nrf24l01.h" +#include "iface_xn297.h" #define BUGSMINI_INITIAL_WAIT 500 #define BUGSMINI_PACKET_INTERVAL 6840 @@ -59,9 +59,8 @@ enum { static void __attribute__((unused)) BUGSMINI_RF_init() { - NRF24L01_Initialize(); - - NRF24L01_WriteReg(NRF24L01_11_RX_PW_P0, BUGSMINI_RX_PAYLOAD_SIZE); // bytes of data payload for rx pipe 1 + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_1M); + //XN297_HoppingCalib(BUGSMINI_NUM_RF_CHANNELS*2); } static void __attribute__((unused)) BUGSMINI_check_arming() @@ -148,15 +147,14 @@ static void __attribute__((unused)) BUGSMINI_send_packet() hopping_frequency_no++; if(hopping_frequency_no >= BUGSMINI_NUM_RF_CHANNELS) hopping_frequency_no = 0; - NRF24L01_WriteReg(NRF24L01_05_RF_CH, IS_BIND_IN_PROGRESS ? hopping_frequency[hopping_frequency_no+BUGSMINI_NUM_RF_CHANNELS] : hopping_frequency[hopping_frequency_no]); + XN297_Hopping(IS_BIND_IN_PROGRESS ? hopping_frequency[hopping_frequency_no+BUGSMINI_NUM_RF_CHANNELS] : hopping_frequency[hopping_frequency_no]); } - // Power on, TX mode, 2byte CRC - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP)); - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); - NRF24L01_FlushTx(); + // Send + XN297_SetPower(); + XN297_SetTxRxMode(TXRX_OFF); + XN297_SetTxRxMode(TX_EN); XN297_WritePayload(packet, BUGSMINI_TX_PAYLOAD_SIZE); - NRF24L01_SetPower(); } // compute final address for the rxid received during bind @@ -220,37 +218,37 @@ static void __attribute__((unused)) BUGSMINI_make_address() // Something wrong happened if we arrive here.... } +#if defined(BUGS_HUB_TELEMETRY) static void __attribute__((unused)) BUGSMINI_update_telemetry() { -#if defined(BUGS_HUB_TELEMETRY) uint8_t checksum = 0x6d; for(uint8_t i=1; i<12; i++) - checksum += packet[i]; - if(packet[0] == checksum) + checksum += packet_in[i]; + if(packet_in[0] == checksum) { - RX_RSSI = packet[3]; + RX_RSSI = packet_in[3]; if(sub_protocol==BUGS3H) { - if(packet[11] & 0x40) + if(packet_in[11] & 0x40) v_lipo1 = 0x40; // Warning - else if(packet[11] & 0x80) + else if(packet_in[11] & 0x80) v_lipo1 = 0x20; // Critical else v_lipo1 = 0x80; // Ok } else { - if(packet[11] & 0x80) + if(packet_in[11] & 0x80) v_lipo1 = 0x80; // Ok - else if(packet[11] & 0x40) + else if(packet_in[11] & 0x40) v_lipo1 = 0x40; // Warning else v_lipo1 = 0x20; // Critical } telemetry_link=1; } -#endif } +#endif uint16_t BUGSMINI_callback() { @@ -258,58 +256,52 @@ uint16_t BUGSMINI_callback() switch(phase) { case BUGSMINI_BIND1: - if( NRF24L01_ReadReg(NRF24L01_07_STATUS) & _BV(NRF24L01_07_RX_DR)) + if( XN297_IsRX() ) { // RX fifo data ready - XN297_ReadPayload(packet, BUGSMINI_RX_PAYLOAD_SIZE); + XN297_ReadPayload(packet, BUGSMINI_RX_PAYLOAD_SIZE); // Not checking the CRC?? base_adr=BUGSMINI_EEPROM_OFFSET+(RX_num&0x0F)*2; - eeprom_write_byte((EE_ADDR)(base_adr+0),packet[1]); // Save rxid in EEPROM - eeprom_write_byte((EE_ADDR)(base_adr+1),packet[2]); // Save rxid in EEPROM - NRF24L01_SetTxRxMode(TXRX_OFF); - NRF24L01_SetTxRxMode(TX_EN); + eeprom_write_byte((EE_ADDR)(base_adr+0),packet[1]); // Save rxid in EEPROM + eeprom_write_byte((EE_ADDR)(base_adr+1),packet[2]); // Save rxid in EEPROM BUGSMINI_make_address(); XN297_SetTXAddr(rx_tx_addr, 5); - XN297_SetRXAddr(rx_tx_addr, 5); + XN297_SetRXAddr(rx_tx_addr, BUGSMINI_RX_PAYLOAD_SIZE); phase = BUGSMINI_DATA1; BIND_DONE; - return BUGSMINI_PACKET_INTERVAL; + break; } - NRF24L01_SetTxRxMode(TXRX_OFF); - NRF24L01_SetTxRxMode(TX_EN); BUGSMINI_send_packet(); phase = BUGSMINI_BIND2; return BUGSMINI_WRITE_WAIT; case BUGSMINI_BIND2: // switch to RX mode - NRF24L01_SetTxRxMode(TXRX_OFF); - NRF24L01_SetTxRxMode(RX_EN); - NRF24L01_FlushRx(); - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) - | _BV(NRF24L01_00_PWR_UP) | _BV(NRF24L01_00_PRIM_RX)); + XN297_SetTxRxMode(TXRX_OFF); + XN297_SetTxRxMode(RX_EN); phase = BUGSMINI_BIND1; return BUGSMINI_PACKET_INTERVAL - BUGSMINI_WRITE_WAIT; case BUGSMINI_DATA1: #ifdef MULTI_SYNC telemetry_set_input_sync(BUGSMINI_PACKET_INTERVAL); #endif - if( NRF24L01_ReadReg(NRF24L01_07_STATUS) & _BV(NRF24L01_07_RX_DR)) - { // RX fifo data ready => read only 12 bytes to not overwrite channel change flag - XN297_ReadPayload(packet, 12); - BUGSMINI_update_telemetry(); - } - NRF24L01_SetTxRxMode(TXRX_OFF); - NRF24L01_SetTxRxMode(TX_EN); + #if defined(BUGS_HUB_TELEMETRY) + if( XN297_IsRX() ) + { + XN297_ReadPayload(packet_in, BUGSMINI_RX_PAYLOAD_SIZE); // Not checking the CRC?? + BUGSMINI_update_telemetry(); + } + #endif BUGSMINI_send_packet(); + #if not defined(BUGS_HUB_TELEMETRY) + break; + #else phase = BUGSMINI_DATA2; return BUGSMINI_WRITE_WAIT; case BUGSMINI_DATA2: // switch to RX mode - NRF24L01_SetTxRxMode(TXRX_OFF); - NRF24L01_FlushRx(); - NRF24L01_SetTxRxMode(RX_EN); - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) - | _BV(NRF24L01_00_PWR_UP) | _BV(NRF24L01_00_PRIM_RX)); + XN297_SetTxRxMode(TXRX_OFF); + XN297_SetTxRxMode(RX_EN); phase = BUGSMINI_DATA1; return BUGSMINI_PACKET_INTERVAL - BUGSMINI_WRITE_WAIT; + #endif } return BUGSMINI_PACKET_INTERVAL; } @@ -349,19 +341,19 @@ static void __attribute__((unused)) BUGSMINI_initialize_txid() void BUGSMINI_init() { BUGSMINI_initialize_txid(); - memset(packet, (uint8_t)0, BUGSMINI_TX_PAYLOAD_SIZE); BUGSMINI_RF_init(); + memset(packet, (uint8_t)0, BUGSMINI_TX_PAYLOAD_SIZE); if(IS_BIND_IN_PROGRESS) { XN297_SetTXAddr((const uint8_t*)"mjxRC", 5); - XN297_SetRXAddr((const uint8_t*)"mjxRC", 5); + XN297_SetRXAddr((const uint8_t*)"mjxRC", BUGSMINI_RX_PAYLOAD_SIZE); phase = BUGSMINI_BIND1; } else { BUGSMINI_make_address(); XN297_SetTXAddr(rx_tx_addr, 5); - XN297_SetRXAddr(rx_tx_addr, 5); + XN297_SetRXAddr(rx_tx_addr, BUGSMINI_RX_PAYLOAD_SIZE); phase = BUGSMINI_DATA1; } armed = 0; diff --git a/Multiprotocol/Bayang_Rx_nrf24l01.ino b/Multiprotocol/Bayang_Rx_nrf24l01.ino index f2eb40e..f29b3fa 100644 --- a/Multiprotocol/Bayang_Rx_nrf24l01.ino +++ b/Multiprotocol/Bayang_Rx_nrf24l01.ino @@ -15,7 +15,7 @@ Multiprotocol is distributed in the hope that it will be useful, #if defined(BAYANG_RX_NRF24L01_INO) -#include "iface_nrf24l01.h" +#include "iface_xn297.h" #define BAYANG_RX_PACKET_SIZE 15 #define BAYANG_RX_RF_NUM_CHANNELS 4 @@ -27,18 +27,15 @@ enum { BAYANG_RX_DATA }; -static void __attribute__((unused)) Bayang_Rx_init_nrf24l01() +static void __attribute__((unused)) Bayang_Rx_RF_init() { const uint8_t bind_address[BAYANG_RX_ADDRESS_LENGTH] = { 0,0,0,0,0 }; - NRF24L01_Initialize(); + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_1M); XN297_SetTXAddr(bind_address, BAYANG_RX_ADDRESS_LENGTH); - XN297_SetRXAddr(bind_address, BAYANG_RX_ADDRESS_LENGTH); - NRF24L01_WriteReg(NRF24L01_11_RX_PW_P0, BAYANG_RX_PACKET_SIZE + 2); // 2 extra bytes for xn297 crc - NRF24L01_WriteReg(NRF24L01_05_RF_CH, BAYANG_RX_RF_BIND_CHANNEL); - NRF24L01_SetTxRxMode(TXRX_OFF); - NRF24L01_FlushRx(); - NRF24L01_SetTxRxMode(RX_EN); - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP) | _BV(NRF24L01_00_PRIM_RX)); + XN297_SetRXAddr(bind_address, BAYANG_RX_PACKET_SIZE); + XN297_RFChannel(BAYANG_RX_RF_BIND_CHANNEL); + XN297_SetTxRxMode(TXRX_OFF); + XN297_SetTxRxMode(RX_EN); } static uint8_t __attribute__((unused)) Bayang_Rx_check_validity() { @@ -91,7 +88,7 @@ static void __attribute__((unused)) Bayang_Rx_build_telemetry_packet() void BAYANG_RX_init() { uint8_t i; - Bayang_Rx_init_nrf24l01(); + Bayang_Rx_RF_init(); hopping_frequency_no = 0; rx_data_started = false; rx_data_received = false; @@ -105,8 +102,9 @@ void BAYANG_RX_init() rx_tx_addr[i] = eeprom_read_byte((EE_ADDR)temp++); for (i = 0; i < BAYANG_RX_RF_NUM_CHANNELS; i++) hopping_frequency[i] = eeprom_read_byte((EE_ADDR)temp++); + //XN297_HoppingCalib(BAYANG_RX_RF_NUM_CHANNELS); XN297_SetTXAddr(rx_tx_addr, BAYANG_RX_ADDRESS_LENGTH); - XN297_SetRXAddr(rx_tx_addr, BAYANG_RX_ADDRESS_LENGTH); + XN297_SetRXAddr(rx_tx_addr, BAYANG_RX_PACKET_SIZE); phase = BAYANG_RX_DATA; } } @@ -116,86 +114,89 @@ uint16_t BAYANG_RX_callback() uint8_t i; static int8_t read_retry; - switch (phase) { - case BAYANG_RX_BIND: - if(IS_BIND_DONE) - { - BAYANG_RX_init(); // Abort bind - break; - } - if (NRF24L01_ReadReg(NRF24L01_07_STATUS) & _BV(NRF24L01_07_RX_DR)) { - // data received from TX - if (XN297_ReadPayload(packet, BAYANG_RX_PACKET_SIZE) && ( packet[0] == 0xA4 || packet[0] == 0xA2 ) && Bayang_Rx_check_validity()) { - // store tx info into eeprom - uint16_t temp = BAYANG_RX_EEPROM_OFFSET; - for (i = 0; i < 5; i++) { - rx_tx_addr[i] = packet[i + 1]; - eeprom_write_byte((EE_ADDR)temp++, rx_tx_addr[i]); - } - for (i = 0; i < 4; i++) { - hopping_frequency[i] = packet[i + 6]; - eeprom_write_byte((EE_ADDR)temp++, hopping_frequency[i]); - } - XN297_SetTXAddr(rx_tx_addr, BAYANG_RX_ADDRESS_LENGTH); - XN297_SetRXAddr(rx_tx_addr, BAYANG_RX_ADDRESS_LENGTH); - BIND_DONE; - phase = BAYANG_RX_DATA; - } - NRF24L01_FlushRx(); - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); - } - break; - case BAYANG_RX_DATA: - if (NRF24L01_ReadReg(NRF24L01_07_STATUS) & _BV(NRF24L01_07_RX_DR)) { - if (XN297_ReadPayload(packet, BAYANG_RX_PACKET_SIZE) && packet[0] == 0xA5 && Bayang_Rx_check_validity()) { - if ((telemetry_link & 0x7F) == 0) { - Bayang_Rx_build_telemetry_packet(); - telemetry_link = 1; - #ifdef SEND_CPPM - if(sub_protocol>0) - telemetry_link |= 0x80; // Disable telemetry output - #endif - } - rx_data_started = true; - rx_data_received = true; - read_retry = 8; - pps_counter++; - } - } - // packets per second - if (millis() - pps_timer >= 1000) { - pps_timer = millis(); - debugln("%d pps", pps_counter); - RX_LQI = pps_counter >> 1; - pps_counter = 0; - } - // frequency hopping - if (read_retry++ >= 8) { - hopping_frequency_no++; - if (hopping_frequency_no >= BAYANG_RX_RF_NUM_CHANNELS) - hopping_frequency_no = 0; - NRF24L01_WriteReg(NRF24L01_05_RF_CH, hopping_frequency[hopping_frequency_no]); - NRF24L01_FlushRx(); - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); - if (rx_data_started) + switch (phase) + { + case BAYANG_RX_BIND: + if(IS_BIND_DONE) { - if(rx_data_received) - { // In sync - rx_data_received = false; - read_retry = 5; - return 1500; + BAYANG_RX_init(); // Abort bind + break; + } + if ( XN297_IsRX() ) + { + debugln("RX"); + // data received from TX + if (XN297_ReadPayload(packet, BAYANG_RX_PACKET_SIZE) && ( packet[0] == 0xA4 || packet[0] == 0xA2 ) && Bayang_Rx_check_validity()) + { + // store tx info into eeprom + uint16_t temp = BAYANG_RX_EEPROM_OFFSET; + for (i = 0; i < 5; i++) { + rx_tx_addr[i] = packet[i + 1]; + eeprom_write_byte((EE_ADDR)temp++, rx_tx_addr[i]); + } + for (i = 0; i < 4; i++) { + hopping_frequency[i] = packet[i + 6]; + eeprom_write_byte((EE_ADDR)temp++, hopping_frequency[i]); + } + //XN297_HoppingCalib(BAYANG_RX_RF_NUM_CHANNELS); + XN297_SetTXAddr(rx_tx_addr, BAYANG_RX_ADDRESS_LENGTH); + XN297_SetRXAddr(rx_tx_addr, BAYANG_RX_PACKET_SIZE); + BIND_DONE; + phase = BAYANG_RX_DATA; + } + XN297_SetTxRxMode(RX_EN); + } + break; + case BAYANG_RX_DATA: + if ( XN297_IsRX() ) { + if (XN297_ReadPayload(packet, BAYANG_RX_PACKET_SIZE) && packet[0] == 0xA5 && Bayang_Rx_check_validity()) { + if ((telemetry_link & 0x7F) == 0) { + Bayang_Rx_build_telemetry_packet(); + telemetry_link = 1; + #ifdef SEND_CPPM + if(sub_protocol>0) + telemetry_link |= 0x80; // Disable telemetry output + #endif + } + rx_data_started = true; + rx_data_received = true; + read_retry = 8; + pps_counter++; + } + } + // packets per second + if (millis() - pps_timer >= 1000) { + pps_timer = millis(); + debugln("%d pps", pps_counter); + RX_LQI = pps_counter >> 1; + pps_counter = 0; + } + // frequency hopping + if (read_retry++ >= 8) { + hopping_frequency_no++; + if (hopping_frequency_no >= BAYANG_RX_RF_NUM_CHANNELS) + hopping_frequency_no = 0; + XN297_Hopping(hopping_frequency_no); + XN297_SetTxRxMode(RX_EN); + if (rx_data_started) + { + if(rx_data_received) + { // In sync + rx_data_received = false; + read_retry = 5; + return 1500; + } + else + { // packet lost + read_retry = 0; + if(RX_LQI==0) // communication lost + rx_data_started=false; + } } else - { // packet lost - read_retry = 0; - if(RX_LQI==0) // communication lost - rx_data_started=false; - } + read_retry = -16; // retry longer until first packet is caught } - else - read_retry = -16; // retry longer until first packet is caught - } - return 250; + return 250; } return 1000; } diff --git a/Multiprotocol/Bayang_nrf24l01.ino b/Multiprotocol/Bayang_nrf24l01.ino index e5e4ae3..fa9dc4c 100644 --- a/Multiprotocol/Bayang_nrf24l01.ino +++ b/Multiprotocol/Bayang_nrf24l01.ino @@ -17,7 +17,7 @@ Multiprotocol is distributed in the hope that it will be useful, #if defined(BAYANG_NRF24L01_INO) -#include "iface_nrf24l01.h" +#include "iface_xn297.h" #define BAYANG_BIND_COUNT 1000 #define BAYANG_PACKET_PERIOD 2000 @@ -97,6 +97,8 @@ static void __attribute__((unused)) BAYANG_send_packet() } else { + XN297_Hopping(hopping_frequency_no++); + hopping_frequency_no%=BAYANG_RF_NUM_CHANNELS; uint16_t val; uint8_t dyntrim = 1; switch (sub_protocol) @@ -192,28 +194,18 @@ static void __attribute__((unused)) BAYANG_send_packet() for (uint8_t i=0; i < BAYANG_PACKET_SIZE-1; i++) packet[14] += packet[i]; - NRF24L01_WriteReg(NRF24L01_05_RF_CH, IS_BIND_IN_PROGRESS ? rf_ch_num:hopping_frequency[hopping_frequency_no++]); - hopping_frequency_no%=BAYANG_RF_NUM_CHANNELS; - - // Power on, TX mode, 2byte CRC - // Why CRC0? xn297 does not interpret it - either 16-bit CRC or nothing - NRF24L01_FlushTx(); - NRF24L01_SetTxRxMode(TX_EN); - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP)); + // Send + XN297_SetPower(); + XN297_SetTxRxMode(TX_EN); XN297_WritePayload(packet, BAYANG_PACKET_SIZE); - - NRF24L01_SetPower(); // Set tx_power } #ifdef BAYANG_HUB_TELEMETRY static void __attribute__((unused)) BAYANG_check_rx(void) { - if (NRF24L01_ReadReg(NRF24L01_07_STATUS) & _BV(NRF24L01_07_RX_DR)) + if( XN297_IsRX() ) { // data received from model - XN297_ReadPayload(packet, BAYANG_PACKET_SIZE); - NRF24L01_WriteReg(NRF24L01_07_STATUS, 255); - - NRF24L01_FlushRx(); + XN297_ReadPayload(packet, BAYANG_PACKET_SIZE); // Strange can't test the CRC since it seems to be disabled on telemetry packets... uint8_t check = packet[0]; for (uint8_t i=1; i < BAYANG_PACKET_SIZE-1; i++) check += packet[i]; @@ -242,27 +234,21 @@ static void __attribute__((unused)) BAYANG_check_rx(void) telemetry_link=0; // Don't send anything yet } } - NRF24L01_SetTxRxMode(TXRX_OFF); + XN297_SetTxRxMode(TXRX_OFF); } #endif static void __attribute__((unused)) BAYANG_RF_init() { - NRF24L01_Initialize(); - + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_1M); XN297_SetTXAddr((uint8_t *)"\x00\x00\x00\x00\x00", BAYANG_ADDRESS_LENGTH); - NRF24L01_WriteReg(NRF24L01_11_RX_PW_P0, BAYANG_PACKET_SIZE); + //XN297_HoppingCalib(BAYANG_RF_NUM_CHANNELS); - switch (sub_protocol) - { - case X16_AH: - case IRDRONE: - rf_ch_num = BAYANG_RF_BIND_CHANNEL_X16_AH; - break; - default: - rf_ch_num = BAYANG_RF_BIND_CHANNEL; - break; - } + //Set bind channel + uint8_t ch = BAYANG_RF_BIND_CHANNEL; + if(sub_protocol == X16_AH || sub_protocol == IRDRONE) + ch = BAYANG_RF_BIND_CHANNEL_X16_AH; + XN297_RFChannel(ch); } enum { @@ -287,7 +273,7 @@ uint16_t BAYANG_callback() { XN297_SetTXAddr(rx_tx_addr, BAYANG_ADDRESS_LENGTH); #ifdef BAYANG_HUB_TELEMETRY - XN297_SetRXAddr(rx_tx_addr, BAYANG_ADDRESS_LENGTH); + XN297_SetRXAddr(rx_tx_addr, BAYANG_PACKET_SIZE); #endif BIND_DONE; phase++; //WRITE @@ -322,9 +308,9 @@ uint16_t BAYANG_callback() // switch radio to rx as soon as packet is sent start=(uint16_t)micros(); while ((uint16_t)((uint16_t)micros()-(uint16_t)start) < 1000) // Wait max 1ms - if((NRF24L01_ReadReg(NRF24L01_07_STATUS) & _BV(NRF24L01_07_TX_DS))) + if(XN297_IsPacketSent()) break; - NRF24L01_WriteReg(NRF24L01_00_CONFIG, 0x03); + XN297_SetTxRxMode(RX_EN); phase++; // READ return BAYANG_PACKET_TELEM_PERIOD - BAYANG_CHECK_DELAY - BAYANG_READ_DELAY; case BAYANG_READ: diff --git a/Multiprotocol/CC2500_SPI.ino b/Multiprotocol/CC2500_SPI.ino index 55a6317..4006e0e 100644 --- a/Multiprotocol/CC2500_SPI.ino +++ b/Multiprotocol/CC2500_SPI.ino @@ -195,6 +195,7 @@ void __attribute__((unused)) CC2500_250K_Init() // TX Power = 0 // Whitening = false // Fast Frequency Hopping - no PLL auto calibration +/* //Previous config CC2500_WriteReg(CC2500_08_PKTCTRL0, 0x01); // Packet Automation Control CC2500_WriteReg(CC2500_0B_FSCTRL1, 0x0A); // Frequency Synthesizer Control CC2500_WriteReg(CC2500_0C_FSCTRL0, option); // Frequency offset hack @@ -217,6 +218,42 @@ void __attribute__((unused)) CC2500_250K_Init() CC2500_WriteReg(CC2500_23_FSCAL3, 0xEA); // Frequency Synthesizer Calibration CC2500_WriteReg(CC2500_25_FSCAL1, 0x00); // Frequency Synthesizer Calibration CC2500_WriteReg(CC2500_26_FSCAL0, 0x11); // Frequency Synthesizer Calibration +*/ + CC2500_WriteReg(CC2500_07_PKTCTRL1, 0x05); // Packet Automation Control, address check true auto append RSSI & LQI + CC2500_WriteReg(CC2500_08_PKTCTRL0, 0x00); // Packet Automation Control, fixed packet len + CC2500_WriteReg(CC2500_0B_FSCTRL1, 0x0A); // Frequency Synthesizer Control (IF Frequency) + CC2500_WriteReg(CC2500_0C_FSCTRL0, 0x00); // Frequency Synthesizer Control + CC2500_WriteReg(CC2500_0D_FREQ2, 0x5C); // Frequency Control Word, High Byte + CC2500_WriteReg(CC2500_0E_FREQ1, 0x4E); // Frequency Control Word, Middle Byte + CC2500_WriteReg(CC2500_0F_FREQ0, 0xC5); // Frequency Control Word, Low Byte + CC2500_WriteReg(CC2500_10_MDMCFG4, 0x3D); // Modem Configuration Set to 406kHz BW filter + CC2500_WriteReg(CC2500_11_MDMCFG3, 0x3B); // Modem Configuration + CC2500_WriteReg(CC2500_12_MDMCFG2, 0x10); // Modem Configuration, GFSK, no preambule and no sync word -> TX by default + CC2500_WriteReg(CC2500_13_MDMCFG1, 0x03); // Modem Configuration, 2 bytes of preamble + CC2500_WriteReg(CC2500_14_MDMCFG0, 0xA4); // Modem Configuration + CC2500_WriteReg(CC2500_15_DEVIATN, 0x62); // Modem Deviation Setting + CC2500_WriteReg(CC2500_18_MCSM0, 0x08); // Main Radio Control State Machine Configuration + CC2500_WriteReg(CC2500_19_FOCCFG, 0x1D); // Frequency Offset Compensation Configuration + CC2500_WriteReg(CC2500_1A_BSCFG, 0x1C); // Bit Synchronization Configuration + CC2500_WriteReg(CC2500_1B_AGCCTRL2, 0xC7); // AGC Control + CC2500_WriteReg(CC2500_1C_AGCCTRL1, 0x00); // AGC Control + CC2500_WriteReg(CC2500_1D_AGCCTRL0, 0xB0); // AGC Control + CC2500_WriteReg(CC2500_21_FREND1, 0xB6); // Front End RX Configuration + CC2500_WriteReg(CC2500_23_FSCAL3, 0xEA); // Frequency Synthesizer Calibration + CC2500_WriteReg(CC2500_25_FSCAL1, 0x00); // Frequency Synthesizer Calibration + CC2500_WriteReg(CC2500_26_FSCAL0, 0x11); // Frequency Synthesizer Calibration + + //Prep RX + // Set first 3 bytes of rx addr in [0]->SYNC1, [1]->SYNC0 and [2]->ADDR + // CC2500_WriteReg(CC2500_04_SYNC1, [0]); // Sync word, high byte + // CC2500_WriteReg(CC2500_05_SYNC0, [1]); // Sync word, low byte + // CC2500_WriteReg(CC2500_09_ADDR, [2]); // Set addr + //RX + // CC2500_WriteReg(CC2500_12_MDMCFG2, 0x12); // Modem Configuration, GFSK, 16/16 Sync Word TX&RX + //TX + // CC2500_WriteReg(CC2500_12_MDMCFG2, 0x10); // Modem Configuration, GFSK, no preambule and no sync word + // need to set packet length before sending/receiving + // CC2500_WriteReg(CC2500_06_PKTLEN, cc2500_packet_len); // Packet len, fix packet len CC2500_SetTxRxMode(TX_EN); CC2500_SetPower(); @@ -250,87 +287,4 @@ void __attribute__((unused)) CC2500_250K_RFChannel(uint8_t number) CC2500_Strobe(CC2500_SCAL); delayMicroseconds(900); } - -//NRF emulation layer with CRC16 enabled -uint8_t cc2500_nrf_tx_addr[5], cc2500_nrf_addr_len; -void __attribute__((unused)) CC2500_250K_NRF_SetTXAddr(uint8_t* addr, uint8_t len) -{ - cc2500_nrf_addr_len = len; - memcpy(cc2500_nrf_tx_addr, addr, len); -} -void __attribute__((unused)) CC2500_250K_NRF_WritePayload(uint8_t* msg, uint8_t len) -{ - #if defined(ESKY150V2_CC2500_INO) - uint8_t buf[158]; - #else - uint8_t buf[35]; - #endif - uint8_t last = 0; - uint8_t i; - - //nrf preamble - if(cc2500_nrf_tx_addr[cc2500_nrf_addr_len - 1] & 0x80) - buf[0]=0xAA; - else - buf[0]=0x55; - last++; - // address - for (i = 0; i < cc2500_nrf_addr_len; ++i) - buf[last++] = cc2500_nrf_tx_addr[cc2500_nrf_addr_len - i - 1]; - // payload - for (i = 0; i < len; ++i) - buf[last++] = msg[i]; - - // crc - crc = 0xffff; - for (uint8_t i = 1; i < last; ++i) - crc16_update( buf[i], 8); - buf[last++] = crc >> 8; - buf[last++] = crc & 0xff; - buf[last++] = 0; - - //for(uint8_t i=0;i63) - { - CC2500_WriteRegisterMulti(CC2500_3F_TXFIFO, buff, 63); - CC2500_Strobe(CC2500_STX); - last-=63; - buff+=63; - while(last) - {//Loop until all the data is sent - do - {// Wait for the FIFO to become available - status=CC2500_ReadReg(CC2500_3A_TXBYTES | CC2500_READ_BURST); - } - while((status&0x7F)>31 && (status&0x80)==0); - if(last>31) - {//Send 31 bytes - CC2500_WriteRegisterMulti(CC2500_3F_TXFIFO, buff, 31); - last-=31; - buff+=31; - } - else - {//Send last bytes - CC2500_WriteRegisterMulti(CC2500_3F_TXFIFO, buff, last); - last=0; - } - } - } - else - {//Send packet - CC2500_WriteRegisterMulti(CC2500_3F_TXFIFO, buff, last); - CC2500_Strobe(CC2500_STX); - } -} #endif \ No newline at end of file diff --git a/Multiprotocol/CG023_nrf24l01.ino b/Multiprotocol/CG023_nrf24l01.ino index 9acb9b3..d0a422f 100644 --- a/Multiprotocol/CG023_nrf24l01.ino +++ b/Multiprotocol/CG023_nrf24l01.ino @@ -63,9 +63,15 @@ static void __attribute__((unused)) CG023_send_packet() aileron = convert_channel_16b_limit(AILERON, 0x43, 0xBB); if (IS_BIND_IN_PROGRESS) + { packet[0]= 0xaa; + XN297_RFChannel(CG023_RF_BIND_CHANNEL); + } else + { packet[0]= 0x55; + XN297_RFChannel(hopping_frequency_no); + } // transmitter id packet[1] = rx_tx_addr[0]; packet[2] = rx_tx_addr[1]; @@ -85,7 +91,7 @@ static void __attribute__((unused)) CG023_send_packet() if(sub_protocol==CG023) { // rate - packet[13] = CG023_FLAG_RATE_HIGH + packet[13] = CG023_FLAG_RATE_HIGH | GET_FLAG(CH5_SW,CG023_FLAG_FLIP) | GET_FLAG(CH6_SW,CG023_FLAG_LED_OFF) | GET_FLAG(CH7_SW,CG023_FLAG_STILL) @@ -95,7 +101,7 @@ static void __attribute__((unused)) CG023_send_packet() else {// YD829 // rate - packet[13] = YD829_FLAG_RATE_HIGH + packet[13] = YD829_FLAG_RATE_HIGH | GET_FLAG(CH5_SW,YD829_FLAG_FLIP) | GET_FLAG(CH7_SW,YD829_FLAG_STILL) | GET_FLAG(CH8_SW,YD829_FLAG_VIDEO) @@ -103,25 +109,15 @@ static void __attribute__((unused)) CG023_send_packet() } packet[14] = 0; - // Power on, TX mode, 2byte CRC - // Why CRC0? xn297 does not interpret it - either 16-bit CRC or nothing - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP)); - if (IS_BIND_IN_PROGRESS) - NRF24L01_WriteReg(NRF24L01_05_RF_CH, CG023_RF_BIND_CHANNEL); - else - NRF24L01_WriteReg(NRF24L01_05_RF_CH, hopping_frequency_no); - - // clear packet status bits and TX FIFO - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); - NRF24L01_FlushTx(); + // Send + XN297_SetTxRxMode(TX_EN); + XN297_SetPower(); XN297_WritePayload(packet, CG023_PACKET_SIZE); - - NRF24L01_SetPower(); // Set tx_power } static void __attribute__((unused)) CG023_RF_init() { - NRF24L01_Initialize(); + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_1M); XN297_SetTXAddr((uint8_t *)"\x26\xA8\x67\x35\xCC", 5); } @@ -144,7 +140,7 @@ uint16_t CG023_callback() static void __attribute__((unused)) CG023_initialize_txid() { rx_tx_addr[0]= 0x80 | (rx_tx_addr[0] % 0x40); - if( rx_tx_addr[0] == 0xAA) // avoid using same freq for bind and data channel + if( rx_tx_addr[0] == 0xAA) // avoid using same freq for bind and data channel rx_tx_addr[0] ++; hopping_frequency_no = rx_tx_addr[0] - 0x7D; // rf channel for data packets } diff --git a/Multiprotocol/CX10_nrf24l01.ino b/Multiprotocol/CX10_nrf24l01.ino index 692e581..d792c5f 100644 --- a/Multiprotocol/CX10_nrf24l01.ino +++ b/Multiprotocol/CX10_nrf24l01.ino @@ -17,7 +17,7 @@ #if defined(CX10_NRF24L01_INO) -#include "iface_nrf24l01.h" +#include "iface_xn297.h" #define CX10_BIND_COUNT 4360 // 6 seconds #define CX10_PACKET_SIZE 15 @@ -46,12 +46,12 @@ enum { CX10_DATA }; -static void __attribute__((unused)) CX10_Write_Packet(uint8_t bind) +static void __attribute__((unused)) CX10_Write_Packet() { uint8_t offset = 0; if(sub_protocol == CX10_BLUE) offset = 4; - packet[0] = bind ? 0xAA : 0x55; + packet[0] = IS_BIND_IN_PROGRESS ? 0xAA : 0x55; packet[1] = rx_tx_addr[0]; packet[2] = rx_tx_addr[1]; packet[3] = rx_tx_addr[2]; @@ -62,57 +62,57 @@ static void __attribute__((unused)) CX10_Write_Packet(uint8_t bind) uint16_t throttle=convert_channel_16b_limit(THROTTLE,1000,2000); uint16_t rudder= convert_channel_16b_limit(RUDDER ,2000,1000); // Channel 5 - flip flag - packet[12+offset] = GET_FLAG(CH5_SW,CX10_FLAG_FLIP); // flip flag applied on rudder + packet[12+offset] = GET_FLAG(CH5_SW,CX10_FLAG_FLIP); // flip flag applied on rudder // Channel 6 - rate mode is 2 lsb of packet 13 - if(CH6_SW) // rate 3 / headless on CX-10A + if(CH6_SW) // rate 3 / headless on CX-10A flags = 0x02; else if(Channel_data[CH6] < CHANNEL_MIN_COMMAND) - flags = 0x00; // rate 1 + flags = 0x00; // rate 1 else - flags = 0x01; // rate 2 - uint8_t flags2=0; // packet 14 + flags = 0x01; // rate 2 + uint8_t flags2=0; // packet 14 uint8_t video_state=packet[14] & 0x21; switch(sub_protocol) { case CX10_BLUE: - flags |= GET_FLAG(!CH7_SW, 0x10) // Channel 7 - picture - |GET_FLAG( CH8_SW, 0x08); // Channel 8 - video + flags |= GET_FLAG(!CH7_SW, 0x10) // Channel 7 - picture + |GET_FLAG( CH8_SW, 0x08); // Channel 8 - video break; case F_Q282: case F_Q242: case F_Q222: memcpy(&packet[15], "\x10\x10\xaa\xaa\x00\x00", 6); //FLIP|LED|PICTURE|VIDEO|HEADLESS|RTH|XCAL|YCAL - flags2 = GET_FLAG(CH5_SW, 0x80) // Channel 5 - FLIP - |GET_FLAG(!CH6_SW, 0x40) // Channel 6 - LED - |GET_FLAG(CH9_SW, 0x08) // Channel 9 - HEADLESS - |GET_FLAG(CH11_SW, 0x04) // Channel 11 - XCAL - |GET_FLAG(CH12_SW, 0x02); // Channel 12 - YCAL or Start/Stop motors on JXD 509 + flags2 = GET_FLAG(CH5_SW, 0x80) // Channel 5 - FLIP + |GET_FLAG(!CH6_SW, 0x40) // Channel 6 - LED + |GET_FLAG(CH9_SW, 0x08) // Channel 9 - HEADLESS + |GET_FLAG(CH11_SW, 0x04) // Channel 11 - XCAL + |GET_FLAG(CH12_SW, 0x02); // Channel 12 - YCAL or Start/Stop motors on JXD 509 if(sub_protocol==F_Q242) { flags=2; - flags2|= GET_FLAG(CH7_SW,0x01) // Channel 7 - picture - |GET_FLAG(CH8_SW,0x10); // Channel 8 - video + flags2|= GET_FLAG(CH7_SW,0x01) // Channel 7 - picture + |GET_FLAG(CH8_SW,0x10); // Channel 8 - video packet[17]=0x00; packet[18]=0x00; } else { // F_Q282 & F_Q222 - flags=3; // expert - if(CH8_SW) // Channel 8 - F_Q282 video / F_Q222 Module 1 + flags=3; // expert + if(CH8_SW) // Channel 8 - F_Q282 video / F_Q222 Module 1 { if (!(video_state & 0x20)) video_state ^= 0x21; } else if (video_state & 0x20) video_state &= 0x01; flags2 |= video_state - |GET_FLAG(CH7_SW,0x10); // Channel 7 - F_Q282 picture / F_Q222 Module 2 + |GET_FLAG(CH7_SW,0x10); // Channel 7 - F_Q282 picture / F_Q222 Module 2 } - if(CH10_SW) flags |=0x80; // Channel 10 - RTH + if(CH10_SW) flags |=0x80; // Channel 10 - RTH break; case DM007: aileron = 3000 - aileron; @@ -128,16 +128,16 @@ static void __attribute__((unused)) CX10_Write_Packet(uint8_t bind) if(CH8_SW) packet[12] &= ~CX10_FLAG_FLIP; case JC3015_1: //FLIP|MODE|PICTURE|VIDEO - flags2= GET_FLAG(CH7_SW,_BV(3)) // Channel 7 - |GET_FLAG(CH8_SW,_BV(4)); // Channel 8 + flags2= GET_FLAG(CH7_SW,_BV(3)) // Channel 7 + |GET_FLAG(CH8_SW,_BV(4)); // Channel 8 break; case MK33041: elevator = 3000 - elevator; //FLIP|MODE|PICTURE|VIDEO|HEADLESS|RTH - flags|=GET_FLAG(CH7_SW,_BV(7)) // Channel 7 - picture - |GET_FLAG(CH10_SW,_BV(2)); // Channel 10 - rth - flags2=GET_FLAG(CH8_SW,_BV(0)) // Channel 8 - video - |GET_FLAG(CH9_SW,_BV(5)); // Channel 9 - headless + flags|=GET_FLAG(CH7_SW,_BV(7)) // Channel 7 - picture + |GET_FLAG(CH10_SW,_BV(2)); // Channel 10 - rth + flags2=GET_FLAG(CH8_SW,_BV(0)) // Channel 8 - video + |GET_FLAG(CH9_SW,_BV(5)); // Channel 9 - headless break; } packet[5+offset] = lowByte(aileron); @@ -151,32 +151,23 @@ static void __attribute__((unused)) CX10_Write_Packet(uint8_t bind) packet[13+offset]=flags; packet[14+offset]=flags2; - // Power on, TX mode, 2byte CRC - // Why CRC0? xn297 does not interpret it - either 16-bit CRC or nothing - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP)); - if (bind) - NRF24L01_WriteReg(NRF24L01_05_RF_CH, CX10_RF_BIND_CHANNEL); - else + // Send + if(IS_BIND_DONE) { - NRF24L01_WriteReg(NRF24L01_05_RF_CH, hopping_frequency[hopping_frequency_no++]); + XN297_Hopping(hopping_frequency_no++); hopping_frequency_no %= CX10_NUM_RF_CHANNELS; } - // clear packet status bits and TX FIFO - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); - NRF24L01_FlushTx(); - + XN297_SetPower(); + XN297_SetTxRxMode(TX_EN); XN297_WritePayload(packet, packet_length); - NRF24L01_SetPower(); } static void __attribute__((unused)) CX10_RF_init() { - NRF24L01_Initialize(); - - XN297_SetTXAddr((uint8_t *)"\xcc\xcc\xcc\xcc\xcc",5); - XN297_SetRXAddr((uint8_t *)"\xcc\xcc\xcc\xcc\xcc",5); - NRF24L01_WriteReg(NRF24L01_11_RX_PW_P0, packet_length); // rx pipe 0 (used only for blue board) - NRF24L01_WriteReg(NRF24L01_05_RF_CH, CX10_RF_BIND_CHANNEL); + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_1M); + XN297_SetTXAddr((uint8_t *)"\xcc\xcc\xcc\xcc\xcc", 5); + XN297_SetRXAddr((uint8_t *)"\xcc\xcc\xcc\xcc\xcc", packet_length); + XN297_RFChannel(CX10_RF_BIND_CHANNEL); } uint16_t CX10_callback() @@ -190,43 +181,39 @@ uint16_t CX10_callback() } else { - CX10_Write_Packet(1); + CX10_Write_Packet(); bind_counter--; } break; case CX10_BIND2: - if( NRF24L01_ReadReg(NRF24L01_07_STATUS) & _BV(NRF24L01_07_RX_DR)) + // switch to TX mode + if( XN297_IsRX() ) { // RX fifo data ready - XN297_ReadPayload(packet, packet_length); - NRF24L01_SetTxRxMode(TXRX_OFF); - NRF24L01_SetTxRxMode(TX_EN); - if(packet[9] == 1) + debugln("RX"); + if(XN297_ReadPayload(packet, packet_length) && packet[9] == 1) { BIND_DONE; + XN297_SetTxRxMode(TXRX_OFF); phase = CX10_DATA; + break; } } else { - // switch to TX mode - NRF24L01_SetTxRxMode(TXRX_OFF); - NRF24L01_FlushTx(); - NRF24L01_SetTxRxMode(TX_EN); - CX10_Write_Packet(1); + XN297_SetTxRxMode(TXRX_OFF); + CX10_Write_Packet(); // wait for packet to be sent - while( (NRF24L01_ReadReg(NRF24L01_07_STATUS) & _BV(NRF24L01_07_TX_DS)) == 0); //delayMicroseconds(400); - // switch to RX mode - NRF24L01_SetTxRxMode(TXRX_OFF); - NRF24L01_FlushRx(); - NRF24L01_SetTxRxMode(RX_EN); - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP) | _BV(NRF24L01_00_PRIM_RX)); + while( !XN297_IsPacketSent()); //delayMicroseconds(400); } + // switch to RX mode + XN297_SetTxRxMode(TXRX_OFF); + XN297_SetTxRxMode(RX_EN); break; case CX10_DATA: #ifdef MULTI_SYNC telemetry_set_input_sync(packet_period); #endif - CX10_Write_Packet(0); + CX10_Write_Packet(); break; } return packet_period; diff --git a/Multiprotocol/DM002_nrf24l01.ino b/Multiprotocol/DM002_nrf24l01.ino index 201e14a..868e759 100644 --- a/Multiprotocol/DM002_nrf24l01.ino +++ b/Multiprotocol/DM002_nrf24l01.ino @@ -16,7 +16,7 @@ #if defined(DM002_NRF24L01_INO) -#include "iface_nrf24l01.h" +#include "iface_xn297.h" #define DM002_PACKET_PERIOD 6100 // Timeout for callback in uSec #define DM002_INITIAL_WAIT 500 @@ -24,7 +24,6 @@ #define DM002_RF_BIND_CHANNEL 0x27 #define DM002_BIND_COUNT 655 // 4 seconds - enum DM002_FLAGS { // flags going to packet[9] DM002_FLAG_FLIP = 0x01, @@ -75,28 +74,23 @@ static void __attribute__((unused)) DM002_send_packet() packet_count&=0x0F; packet[10] = packet_count; packet_count++; + XN297_Hopping(hopping_frequency_no); } //CRC for(uint8_t i=0;i. + */ +// compatible with E016H + +#if defined(E016H_NRF24L01_INO) + +#include "iface_xn297.h" + +//Protocols constants +#define E016H_BIND_COUNT 500 +#define E016H_ADDRESS_LENGTH 5 + +#define E016H_PACKET_PERIOD 4080 +#define E016H_PACKET_SIZE 10 +#define E016H_BIND_CHANNEL 80 +#define E016H_NUM_CHANNELS 4 + +//Channels +#define E016H_STOP_SW CH5_SW +#define E016H_FLIP_SW CH6_SW +#define E016H_HEADLESS_SW CH8_SW +#define E016H_RTH_SW CH9_SW + +// E016H flags packet[1] +#define E016H_FLAG_CALIBRATE 0x80 +#define E016H_FLAG_STOP 0x20 +#define E016H_FLAG_FLIP 0x04 +// E016H flags packet[3] +#define E016H_FLAG_HEADLESS 0x10 +#define E016H_FLAG_RTH 0x04 +// E016H flags packet[7] +#define E016H_FLAG_TAKEOFF 0x80 +#define E016H_FLAG_HIGHRATE 0x08 + +static void __attribute__((unused)) E016H_send_packet() +{ + uint8_t can_flip = 0, calibrate = 1; + + if(IS_BIND_IN_PROGRESS) + { + memcpy(packet, &rx_tx_addr[1], 4); + memcpy(&packet[4], hopping_frequency, 4); + packet[8] = 0x23; + } + else + { + // trim commands + packet[0] = 0; + // aileron + uint16_t val = convert_channel_16b_limit(AILERON, 0, 0x3ff); + can_flip |= (val < 0x100) || (val > 0x300); + packet[1] = val >> 8; + packet[2] = val & 0xff; + if(val < 0x300) calibrate = 0; + // elevator + val = convert_channel_16b_limit(ELEVATOR, 0x3ff, 0); + can_flip |= (val < 0x100) || (val > 0x300); + packet[3] = val >> 8; + packet[4] = val & 0xff; + if(val < 0x300) calibrate = 0; + // throttle + val = convert_channel_16b_limit(THROTTLE, 0, 0x3ff); + packet[5] = val >> 8; + packet[6] = val & 0xff; + if(val > 0x100) calibrate = 0; + // rudder + val = convert_channel_16b_limit(RUDDER, 0, 0x3ff); + packet[7] = val >> 8; + packet[8] = val & 0xff; + if(val > 0x100) calibrate = 0; + // flags + packet[1] |= GET_FLAG(E016H_STOP_SW, E016H_FLAG_STOP) + | (can_flip ? GET_FLAG(E016H_FLIP_SW, E016H_FLAG_FLIP) : 0) + | (calibrate ? E016H_FLAG_CALIBRATE : 0); + packet[3] |= GET_FLAG(E016H_HEADLESS_SW, E016H_FLAG_HEADLESS) + | GET_FLAG(E016H_RTH_SW, E016H_FLAG_RTH); + packet[7] |= E016H_FLAG_HIGHRATE; + // frequency hopping + XN297_Hopping(hopping_frequency_no++ & 0x03); + } + // checksum + packet[9] = packet[0]; + for (uint8_t i=1; i < E016H_PACKET_SIZE-1; i++) + packet[9] += packet[i]; + + // Send + XN297_SetPower(); + XN297_SetTxRxMode(TX_EN); + XN297_WritePayload(packet, E016H_PACKET_SIZE); +} + +static void __attribute__((unused)) E016H_RF_init() +{ + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_1M); + XN297_SetTXAddr((uint8_t *)"\x5a\x53\x46\x30\x31", 5); // bind address + //XN297_HoppingCalib(E016H_NUM_CHANNELS); + XN297_RFChannel(E016H_BIND_CHANNEL); +} + +uint16_t E016H_callback() +{ + #ifdef MULTI_SYNC + telemetry_set_input_sync(packet_period); + #endif + if(bind_counter) + { + bind_counter--; + if (bind_counter == 0) + { + XN297_SetTXAddr(rx_tx_addr, E016H_ADDRESS_LENGTH); + BIND_DONE; + } + } + E016H_send_packet(); + return E016H_PACKET_PERIOD; +} + +static void __attribute__((unused)) E016H_initialize_txid() +{ + // tx id + rx_tx_addr[0] = 0xa5; + rx_tx_addr[1] = 0x00; + + // rf channels + uint32_t lfsr=random(0xfefefefe); + for(uint8_t i=0; i>=8; + } +} + +void E016H_init() +{ + BIND_IN_PROGRESS; + E016H_initialize_txid(); + E016H_RF_init(); + bind_counter = E016H_BIND_COUNT; + hopping_frequency_no = 0; +} + +#endif diff --git a/Multiprotocol/E01X_nrf24l01.ino b/Multiprotocol/E01X_nrf24l01.ino index 690968f..b0b59b8 100644 --- a/Multiprotocol/E01X_nrf24l01.ino +++ b/Multiprotocol/E01X_nrf24l01.ino @@ -33,11 +33,6 @@ #define E015_PACKET_SIZE 10 #define E015_BIND_PACKET_SIZE 9 -#define E016H_PACKET_PERIOD 4080 -#define E016H_PACKET_SIZE 10 -#define E016H_BIND_CHANNEL 80 -#define E016H_NUM_CHANNELS 4 - //Channels #define E01X_ARM_SW CH5_SW #define E016H_STOP_SW CH5_SW @@ -64,17 +59,6 @@ #define E015_FLAG_EXPERT 0x02 #define E015_FLAG_INTERMEDIATE 0x01 -// E016H flags packet[1] -#define E016H_FLAG_CALIBRATE 0x80 -#define E016H_FLAG_STOP 0x20 -#define E016H_FLAG_FLIP 0x04 -// E016H flags packet[3] -#define E016H_FLAG_HEADLESS 0x10 -#define E016H_FLAG_RTH 0x04 -// E016H flags packet[7] -#define E016H_FLAG_TAKEOFF 0x80 -#define E016H_FLAG_HIGHRATE 0x08 - static void __attribute__((unused)) E015_check_arming() { uint8_t arm_channel = E01X_ARM_SW; @@ -97,7 +81,6 @@ static void __attribute__((unused)) E015_check_arming() static void __attribute__((unused)) E01X_send_packet() { - uint8_t can_flip = 0, calibrate = 1; if(sub_protocol==E012) { packet_length=E012_PACKET_SIZE; @@ -132,7 +115,7 @@ static void __attribute__((unused)) E01X_send_packet() packet[13] = 0x56; packet[14] = rx_tx_addr[2]; } - else if(sub_protocol==E015) + else { // E015 if(IS_BIND_IN_PROGRESS) { @@ -170,72 +153,14 @@ static void __attribute__((unused)) E01X_send_packet() packet_length=E015_PACKET_SIZE; } } - else - { // E016H - packet_length=E016H_PACKET_SIZE; - if(IS_BIND_IN_PROGRESS) - { - rf_ch_num=E016H_BIND_CHANNEL; - memcpy(packet, &rx_tx_addr[1], 4); - memcpy(&packet[4], hopping_frequency, 4); - packet[8] = 0x23; - } - else - { - // trim commands - packet[0] = 0; - // aileron - uint16_t val = convert_channel_16b_limit(AILERON, 0, 0x3ff); - can_flip |= (val < 0x100) || (val > 0x300); - packet[1] = val >> 8; - packet[2] = val & 0xff; - if(val < 0x300) calibrate = 0; - // elevator - val = convert_channel_16b_limit(ELEVATOR, 0x3ff, 0); - can_flip |= (val < 0x100) || (val > 0x300); - packet[3] = val >> 8; - packet[4] = val & 0xff; - if(val < 0x300) calibrate = 0; - // throttle - val = convert_channel_16b_limit(THROTTLE, 0, 0x3ff); - packet[5] = val >> 8; - packet[6] = val & 0xff; - if(val > 0x100) calibrate = 0; - // rudder - val = convert_channel_16b_limit(RUDDER, 0, 0x3ff); - packet[7] = val >> 8; - packet[8] = val & 0xff; - if(val > 0x100) calibrate = 0; - // flags - packet[1] |= GET_FLAG(E016H_STOP_SW, E016H_FLAG_STOP) - | (can_flip ? GET_FLAG(E01X_FLIP_SW, E016H_FLAG_FLIP) : 0) - | (calibrate ? E016H_FLAG_CALIBRATE : 0); - packet[3] |= GET_FLAG(E01X_HEADLESS_SW, E016H_FLAG_HEADLESS) - | GET_FLAG(E01X_RTH_SW, E016H_FLAG_RTH); - packet[7] |= E016H_FLAG_HIGHRATE; - // frequency hopping - rf_ch_num=hopping_frequency[hopping_frequency_no++ & 0x03]; - } - // checksum - packet[9] = packet[0]; - for (uint8_t i=1; i < E016H_PACKET_SIZE-1; i++) - packet[9] += packet[i]; - } - // Power on, TX mode, CRC enabled - if(sub_protocol==E016H) - XN297_Configure( _BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP)); - else //E012 & E015 - HS6200_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP)); + HS6200_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP)); NRF24L01_WriteReg(NRF24L01_05_RF_CH, rf_ch_num); NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); NRF24L01_FlushTx(); - if(sub_protocol==E016H) - XN297_WritePayload(packet, packet_length); - else - HS6200_WritePayload(packet, packet_length); + HS6200_WritePayload(packet, packet_length); // Check and adjust transmission power. We do this after // transmission to not bother with timeout after power @@ -250,10 +175,8 @@ static void __attribute__((unused)) E01X_RF_init() if(sub_protocol==E012) HS6200_SetTXAddr((uint8_t *)"\x55\x42\x9C\x8F\xC9", E01X_ADDRESS_LENGTH); - else if(sub_protocol==E015) + else //E015 HS6200_SetTXAddr((uint8_t *)"\x62\x54\x79\x38\x53", E01X_ADDRESS_LENGTH); - else //E016H - XN297_SetTXAddr((uint8_t *)"\x5a\x53\x46\x30\x31", 5); // bind address } uint16_t E01X_callback() @@ -266,10 +189,7 @@ uint16_t E01X_callback() bind_counter--; if (bind_counter == 0) { - if(sub_protocol==E016H) - XN297_SetTXAddr(rx_tx_addr, E01X_ADDRESS_LENGTH); - else - HS6200_SetTXAddr(rx_tx_addr, E01X_ADDRESS_LENGTH); + HS6200_SetTXAddr(rx_tx_addr, E01X_ADDRESS_LENGTH); BIND_DONE; } } @@ -288,21 +208,6 @@ static void __attribute__((unused)) E012_initialize_txid() } } -static void __attribute__((unused)) E016H_initialize_txid() -{ - // tx id - rx_tx_addr[0] = 0xa5; - rx_tx_addr[1] = 0x00; - - // rf channels - uint32_t lfsr=random(0xfefefefe); - for(uint8_t i=0; i>=8; - } -} - void E01X_init() { BIND_IN_PROGRESS; @@ -311,7 +216,7 @@ void E01X_init() E012_initialize_txid(); packet_period=E012_PACKET_PERIOD; } - else if(sub_protocol==E015) + else //E015 { packet_period=E015_PACKET_PERIOD; rf_ch_num=E015_RF_CHANNEL; @@ -319,11 +224,6 @@ void E01X_init() arm_flags = 0; arm_channel_previous = E01X_ARM_SW; } - else - { // E016H - E016H_initialize_txid(); - packet_period=E016H_PACKET_PERIOD; - } E01X_RF_init(); bind_counter = E01X_BIND_COUNT; hopping_frequency_no = 0; diff --git a/Multiprotocol/ESky150v2_cc2500.ino b/Multiprotocol/ESky150v2_cc2500.ino index 8c8f2c1..a978fe6 100644 --- a/Multiprotocol/ESky150v2_cc2500.ino +++ b/Multiprotocol/ESky150v2_cc2500.ino @@ -15,7 +15,7 @@ #if defined(ESKY150V2_CC2500_INO) -#include "iface_cc2500.h" +#include "iface_nrf250k.h" //#define ESKY150V2_FORCE_ID @@ -74,7 +74,7 @@ static void __attribute__((unused)) ESKY150V2_send_packet() packet[4+2*i] = channel; packet[5+2*i] = channel>>8; } - CC2500_250K_NRF_WritePayload(packet, ESKY150V2_PAYLOADSIZE); + NRF250K_WritePayload(packet, ESKY150V2_PAYLOADSIZE); } uint16_t ESKY150V2_callback() @@ -91,12 +91,12 @@ uint16_t ESKY150V2_callback() BIND_DONE; //Need full power for bind to work... CC2500_SetPower(); //Set power level BIND_IN_PROGRESS; - CC2500_250K_NRF_WritePayload(packet, ESKY150V2_BINDPAYLOADSIZE); + NRF250K_WritePayload(packet, ESKY150V2_BINDPAYLOADSIZE); if (--bind_counter == 0) { BIND_DONE; // Change TX address from bind to normal mode - CC2500_250K_NRF_SetTXAddr(rx_tx_addr, ESKY150V2_TXID_SIZE); + NRF250K_SetTXAddr(rx_tx_addr, ESKY150V2_TXID_SIZE); memset(packet,0x00,ESKY150V2_PAYLOADSIZE); } return 30000; //ESKY150V2_BINDING_PACKET_PERIOD; @@ -118,7 +118,7 @@ void ESKY150V2_init() if(IS_BIND_IN_PROGRESS) { - CC2500_250K_NRF_SetTXAddr((uint8_t *)"\x73\x73\x74\x63", ESKY150V2_TXID_SIZE); //Bind address + NRF250K_SetTXAddr((uint8_t *)"\x73\x73\x74\x63", ESKY150V2_TXID_SIZE); //Bind address CC2500_250K_Hopping(ESKY150V2_NFREQCHANNELS); //Bind channel memcpy(packet,"\x73\x73\x74\x63", ESKY150V2_TXID_SIZE); memcpy(&packet[ESKY150V2_TXID_SIZE],rx_tx_addr, ESKY150V2_TXID_SIZE); @@ -132,7 +132,7 @@ void ESKY150V2_init() bind_counter=100; } else - CC2500_250K_NRF_SetTXAddr(rx_tx_addr, ESKY150V2_TXID_SIZE); + NRF250K_SetTXAddr(rx_tx_addr, ESKY150V2_TXID_SIZE); } #endif diff --git a/Multiprotocol/FX816_nrf24l01.ino b/Multiprotocol/FX816_nrf24l01.ino index 9d1abae..eac739f 100644 --- a/Multiprotocol/FX816_nrf24l01.ino +++ b/Multiprotocol/FX816_nrf24l01.ino @@ -16,7 +16,7 @@ Multiprotocol is distributed in the hope that it will be useful, #if defined(FX816_NRF24L01_INO) -#include "iface_nrf24l01.h" +#include "iface_xn297.h" #define FX816_INITIAL_WAIT 500 #define FX816_PACKET_PERIOD 10000 @@ -27,7 +27,14 @@ Multiprotocol is distributed in the hope that it will be useful, static void __attribute__((unused)) FX816_send_packet() { - packet[0] = IS_BIND_IN_PROGRESS?0x55:0xAA; + if(IS_BIND_IN_PROGRESS) + packet[0] = 0x55; + else + { + XN297_Hopping(hopping_frequency_no++); + hopping_frequency_no%=FX816_RF_NUM_CHANNELS; + packet[0] = 0xAA; + } packet[1] = rx_tx_addr[0]; packet[2] = rx_tx_addr[1]; uint8_t val=convert_channel_8b(AILERON); @@ -44,25 +51,18 @@ static void __attribute__((unused)) FX816_send_packet() val+=packet[i]; packet[5]=val; - NRF24L01_WriteReg(NRF24L01_05_RF_CH, IS_BIND_IN_PROGRESS ? FX816_RF_BIND_CHANNEL:hopping_frequency[hopping_frequency_no++]); - hopping_frequency_no%=FX816_RF_NUM_CHANNELS; - - // clear packet status bits and TX FIFO - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); - NRF24L01_FlushTx(); + // Send + XN297_SetPower(); + XN297_SetTxRxMode(TX_EN); XN297_WritePayload(packet, FX816_PAYLOAD_SIZE); - - // Power on, TX mode, 2byte CRC - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP)); - - NRF24L01_SetPower(); // Set tx_power } static void __attribute__((unused)) FX816_RF_init() { - NRF24L01_Initialize(); - + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_1M); XN297_SetTXAddr((uint8_t *)"\xcc\xcc\xcc\xcc\xcc", 5); + //XN297_HoppingCalib(FX816_RF_NUM_CHANNELS); + XN297_RFChannel(FX816_RF_BIND_CHANNEL); } static void __attribute__((unused)) FX816_initialize_txid() diff --git a/Multiprotocol/GD00X_ccnrf.ino b/Multiprotocol/GD00X_ccnrf.ino index 092d0a7..b66f3d3 100644 --- a/Multiprotocol/GD00X_ccnrf.ino +++ b/Multiprotocol/GD00X_ccnrf.ino @@ -113,7 +113,7 @@ static void __attribute__((unused)) GD00X_send_packet() if(IS_BIND_DONE) { - XN297L_Hopping(hopping_frequency_no); + XN297_Hopping(hopping_frequency_no); if(sub_protocol==GD_V1) { hopping_frequency_no++; @@ -121,21 +121,22 @@ static void __attribute__((unused)) GD00X_send_packet() } } - XN297L_WritePayload(packet, packet_length); - - XN297L_SetPower(); // Set tx_power - XN297L_SetFreqOffset(); // Set frequency offset + // Send + XN297_SetFreqOffset(); + XN297_SetPower(); + XN297_SetTxRxMode(TX_EN); + XN297_WritePayload(packet, packet_length); } static void __attribute__((unused)) GD00X_RF_init() { - XN297L_Init(); + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_250K); if(sub_protocol==GD_V1) - XN297L_SetTXAddr((uint8_t*)"\xcc\xcc\xcc\xcc\xcc", 5); + XN297_SetTXAddr((uint8_t*)"\xcc\xcc\xcc\xcc\xcc", 5); else - XN297L_SetTXAddr((uint8_t*)"GDKNx", 5); - XN297L_HoppingCalib(sub_protocol==GD_V1?GD00X_RF_NUM_CHANNELS:GD00X_V2_RF_NUM_CHANNELS); // Calibrate all channels - XN297L_RFChannel(sub_protocol==GD_V1?GD00X_RF_BIND_CHANNEL:GD00X_V2_RF_BIND_CHANNEL); // Set bind channel + XN297_SetTXAddr((uint8_t*)"GDKNx", 5); + XN297_HoppingCalib(sub_protocol==GD_V1?GD00X_RF_NUM_CHANNELS:GD00X_V2_RF_NUM_CHANNELS); // Calibrate all channels + XN297_RFChannel(sub_protocol==GD_V1?GD00X_RF_BIND_CHANNEL:GD00X_V2_RF_BIND_CHANNEL); // Set bind channel } static void __attribute__((unused)) GD00X_initialize_txid() diff --git a/Multiprotocol/GW008_nrf24l01.ino b/Multiprotocol/GW008_nrf24l01.ino index f4c95e1..6eebf4f 100644 --- a/Multiprotocol/GW008_nrf24l01.ino +++ b/Multiprotocol/GW008_nrf24l01.ino @@ -19,7 +19,7 @@ Multiprotocol is distributed in the hope that it will be useful, #if defined(GW008_NRF24L01_INO) -#include "iface_nrf24l01.h" +#include "iface_xn297.h" #define GW008_INITIAL_WAIT 500 #define GW008_PACKET_PERIOD 2400 @@ -47,6 +47,9 @@ static void __attribute__((unused)) GW008_send_packet() } else { + XN297_Hopping((hopping_frequency_no++)/2); + hopping_frequency_no %= 8; + packet[1] = 0x01 | GET_FLAG(CH5_SW, 0x40); // flip packet[2] = convert_channel_16b_limit(AILERON , 200, 0); // aileron packet[3] = convert_channel_16b_limit(ELEVATOR, 0, 200); // elevator @@ -63,25 +66,21 @@ static void __attribute__((unused)) GW008_send_packet() } packet[14] = rx_tx_addr[1]; - // Power on, TX mode, CRC enabled - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP)); - NRF24L01_WriteReg(NRF24L01_05_RF_CH, IS_BIND_IN_PROGRESS ? GW008_RF_BIND_CHANNEL : hopping_frequency[(hopping_frequency_no++)/2]); - hopping_frequency_no %= 8; - - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); - NRF24L01_FlushTx(); + // Send + XN297_SetPower(); + XN297_SetTxRxMode(TX_EN); XN297_WriteEnhancedPayload(packet, GW008_PAYLOAD_SIZE, 0); - - NRF24L01_SetPower(); // Set tx_power } static void __attribute__((unused)) GW008_RF_init() { - NRF24L01_Initialize(); - + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_1M); + XN297_SetTXAddr((uint8_t*)"\xcc\xcc\xcc\xcc\xcc", 5); - XN297_SetRXAddr((uint8_t*)"\xcc\xcc\xcc\xcc\xcc", 5); - NRF24L01_WriteReg(NRF24L01_11_RX_PW_P0, GW008_PAYLOAD_SIZE+2); // payload + 2 bytes for pcf + XN297_SetRXAddr((uint8_t*)"\xcc\xcc\xcc\xcc\xcc", GW008_PAYLOAD_SIZE); + + //XN297_HoppingCalib(8); + XN297_RFChannel(GW008_RF_BIND_CHANNEL); } static void __attribute__((unused)) GW008_initialize_txid() @@ -96,20 +95,20 @@ uint16_t GW008_callback() switch(phase) { case GW008_BIND1: - if((NRF24L01_ReadReg(NRF24L01_07_STATUS) & _BV(NRF24L01_07_RX_DR)) && // RX fifo data ready + if(XN297_IsRX() && // RX fifo data ready XN297_ReadEnhancedPayload(packet, GW008_PAYLOAD_SIZE) == GW008_PAYLOAD_SIZE && // check payload size packet[0] == rx_tx_addr[0] && packet[14] == rx_tx_addr[1]) // check tx id { - NRF24L01_SetTxRxMode(TXRX_OFF); - NRF24L01_SetTxRxMode(TX_EN); + XN297_SetTxRxMode(TXRX_OFF); + XN297_SetTxRxMode(TX_EN); rx_tx_addr[2] = packet[13]; BIND_DONE; phase = GW008_DATA; } else { - NRF24L01_SetTxRxMode(TXRX_OFF); - NRF24L01_SetTxRxMode(TX_EN); + XN297_SetTxRxMode(TXRX_OFF); + XN297_SetTxRxMode(TX_EN); GW008_send_packet(); phase = GW008_BIND2; return 850; // minimum value 750 for STM32 @@ -117,14 +116,10 @@ uint16_t GW008_callback() break; case GW008_BIND2: // switch to RX mode - NRF24L01_SetTxRxMode(TXRX_OFF); - NRF24L01_FlushRx(); - NRF24L01_SetTxRxMode(RX_EN); - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) - | _BV(NRF24L01_00_PWR_UP) | _BV(NRF24L01_00_PRIM_RX)); + XN297_SetTxRxMode(TXRX_OFF); + XN297_SetTxRxMode(RX_EN); phase = GW008_BIND1; return 5000; - break; case GW008_DATA: #ifdef MULTI_SYNC telemetry_set_input_sync(GW008_PACKET_PERIOD); diff --git a/Multiprotocol/H8_3D_nrf24l01.ino b/Multiprotocol/H8_3D_nrf24l01.ino index 71b8c1d..eb7a3b0 100644 --- a/Multiprotocol/H8_3D_nrf24l01.ino +++ b/Multiprotocol/H8_3D_nrf24l01.ino @@ -19,7 +19,7 @@ #if defined(H8_3D_NRF24L01_INO) -#include "iface_nrf24l01.h" +#include "iface_xn297.h" #define H8_3D_PACKET_PERIOD 1800 #define H20H_PACKET_PERIOD 9340 @@ -122,17 +122,15 @@ static void __attribute__((unused)) H8_3D_send_packet() sum += packet[i]; packet[19] = sum; // data checksum - // Power on, TX mode, 2byte CRC - // Why CRC0? xn297 does not interpret it - either 16-bit CRC or nothing - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP)); + // RF channel if(sub_protocol!=H20H) { // H8_3D, H20MINI, H30MINI - NRF24L01_WriteReg(NRF24L01_05_RF_CH, IS_BIND_IN_PROGRESS ? hopping_frequency[0] : hopping_frequency[hopping_frequency_no++]); + XN297_RFChannel(IS_BIND_IN_PROGRESS ? hopping_frequency[0] : hopping_frequency[hopping_frequency_no++]); hopping_frequency_no %= H8_3D_RF_NUM_CHANNELS; } else - { //H20H - NRF24L01_WriteReg(NRF24L01_05_RF_CH, IS_BIND_IN_PROGRESS ? H20H_BIND_RF : hopping_frequency[packet_count>>3]); + { // H20H + XN297_RFChannel(IS_BIND_IN_PROGRESS ? H20H_BIND_RF : hopping_frequency[packet_count>>3]); if(IS_BIND_DONE) { packet_count++; @@ -147,17 +145,15 @@ static void __attribute__((unused)) H8_3D_send_packet() } } - // clear packet status bits and TX FIFO - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); - NRF24L01_FlushTx(); + // Send + XN297_SetPower(); + XN297_SetTxRxMode(TX_EN); XN297_WritePayload(packet, H8_3D_PACKET_SIZE); - - NRF24L01_SetPower(); // Set tx_power } static void __attribute__((unused)) H8_3D_RF_init() { - NRF24L01_Initialize(); + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_1M); if(sub_protocol==H20H) XN297_SetTXAddr((uint8_t *)"\xEE\xDD\xCC\xBB\x11", 5); diff --git a/Multiprotocol/Hontai_nrf24l01.ino b/Multiprotocol/Hontai_nrf24l01.ino index 033f8db..fc865a7 100644 --- a/Multiprotocol/Hontai_nrf24l01.ino +++ b/Multiprotocol/Hontai_nrf24l01.ino @@ -15,7 +15,7 @@ #if defined(HONTAI_NRF24L01_INO) -#include "iface_nrf24l01.h" +#include "iface_xn297.h" // mix of nrf and xn297 at 1Mb... #define HONTAI_BIND_COUNT 80 #define HONTAI_PACKET_PERIOD 13500 @@ -44,6 +44,11 @@ static void __attribute__((unused)) HONTAI_send_packet() } else { + /*if(sub_protocol == JJRCX1) + NRF24L01_WriteReg(NRF24L01_05_RF_CH, hopping_frequency[hopping_frequency_no++]); + else*/ + XN297_Hopping(hopping_frequency_no++); + hopping_frequency_no %= 3; memset(packet,0,HONTAI_PACKET_SIZE); packet[3] = convert_channel_16b_limit(THROTTLE, 0, 127) << 1; // Throttle packet[4] = convert_channel_16b_limit(AILERON, 63, 0); // Aileron @@ -113,42 +118,44 @@ static void __attribute__((unused)) HONTAI_send_packet() packet[packet_length-1]=bit_reverse(crc); // Power on, TX mode, 2byte CRC - if(sub_protocol == JJRCX1) + /*if(sub_protocol == JJRCX1) + { + NRF24L01_SetPower(); NRF24L01_SetTxRxMode(TX_EN); - else - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP)); - - NRF24L01_WriteReg(NRF24L01_05_RF_CH, IS_BIND_IN_PROGRESS ? HONTAI_RF_BIND_CHANNEL : hopping_frequency[hopping_frequency_no++]); - hopping_frequency_no %= 3; - - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); - NRF24L01_FlushTx(); + NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); + NRF24L01_FlushTx(); + } + else*/ + { + XN297_SetPower(); + XN297_SetTxRxMode(TX_EN); + } if(sub_protocol == JJRCX1) NRF24L01_WritePayload(packet, packet_length); else XN297_WritePayload(packet, packet_length); - - NRF24L01_SetPower(); } static void __attribute__((unused)) HONTAI_RF_init() { - NRF24L01_Initialize(); - - if(sub_protocol == JJRCX1) - NRF24L01_WriteRegisterMulti(NRF24L01_10_TX_ADDR, (uint8_t*)"\xd2\xb5\x99\xb3\x4a", 5); - else - XN297_SetTXAddr((const uint8_t*)"\xd2\xb5\x99\xb3\x4a", 5); + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_1M); // this will select the nrf and initialize it, therefore both sub protocols can use common instructions if(sub_protocol == JJRCX1) { + //NRF24L01_Initialize(); + NRF24L01_WriteRegisterMulti(NRF24L01_10_TX_ADDR, (uint8_t*)"\xd2\xb5\x99\xb3\x4a", 5); NRF24L01_WriteReg(NRF24L01_04_SETUP_RETR, 0xff); // JJRC uses dynamic payload length NRF24L01_WriteReg(NRF24L01_1C_DYNPD, 0x3f); // match other stock settings even though AA disabled... NRF24L01_WriteReg(NRF24L01_1D_FEATURE, 0x07); + //NRF24L01_WriteReg(NRF24L01_05_RF_CH, HONTAI_RF_BIND_CHANNEL); } - - NRF24L01_SetTxRxMode(TX_EN); // Clear data ready, data sent, retransmit and enable CRC 16bits, ready for TX + else + { + XN297_SetTXAddr((const uint8_t*)"\xd2\xb5\x99\xb3\x4a", 5); + //XN297_HoppingCalib(3); + } + XN297_RFChannel(HONTAI_RF_BIND_CHANNEL); } const uint8_t PROGMEM HONTAI_hopping_frequency_nonels[][3] = { @@ -172,9 +179,9 @@ static void __attribute__((unused)) HONTAI_init2() data_tx_addr[3] = pgm_read_byte_near( &HONTAI_addr_vals[3][(rx_tx_addr[4] >> 4) & 0x0f]); data_tx_addr[4] = 0x24; if(sub_protocol == JJRCX1) - NRF24L01_WriteRegisterMulti(NRF24L01_10_TX_ADDR, data_tx_addr, sizeof(data_tx_addr)); + NRF24L01_WriteRegisterMulti(NRF24L01_10_TX_ADDR, data_tx_addr, 5); else - XN297_SetTXAddr(data_tx_addr, sizeof(data_tx_addr)); + XN297_SetTXAddr(data_tx_addr, 5); //Hopping frequency table for(uint8_t i=0;i<3;i++) diff --git a/Multiprotocol/JJRC345_nrf24l01.ino b/Multiprotocol/JJRC345_nrf24l01.ino index 59fa23e..96de2ff 100644 --- a/Multiprotocol/JJRC345_nrf24l01.ino +++ b/Multiprotocol/JJRC345_nrf24l01.ino @@ -71,7 +71,7 @@ static void __attribute__((unused)) JJRC345_send_packet() } else { //00 41 00 0A 00 80 80 80 00 00 40 46 00 49 F1 18 - NRF24L01_WriteReg(NRF24L01_05_RF_CH, hopping_frequency[hopping_frequency_no]); + XN297_Hopping(hopping_frequency_no); hopping_frequency_no++; hopping_frequency_no %= JJRC345_NUM_CHANNELS; packet[1] = hopping_frequency[hopping_frequency_no]; // next packet will be sent on this channel @@ -121,21 +121,18 @@ static void __attribute__((unused)) JJRC345_send_packet() packet[14] = rx_tx_addr[2]; packet[15] = rx_tx_addr[3]; - // Power on, TX mode - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP)); - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); - NRF24L01_FlushTx(); + // Send + XN297_SetPower(); + XN297_SetTxRxMode(TX_EN); XN297_WritePayload(packet, JJRC345_PACKET_SIZE); - - NRF24L01_SetPower(); // Set tx_power } static void __attribute__((unused)) JJRC345_RF_init() { - NRF24L01_Initialize(); - + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_1M); XN297_SetTXAddr((uint8_t*)"\xcc\xcc\xcc\xcc\xcc", 5); - NRF24L01_WriteReg(NRF24L01_05_RF_CH, sub_protocol == JJRC345 ? JJRC345_RF_BIND_CHANNEL:SKYTMBLR_RF_BIND_CHANNEL); // Bind channel + //XN297_HoppingCalib(JJRC345_NUM_CHANNELS); + XN297_RFChannel(sub_protocol == JJRC345 ? JJRC345_RF_BIND_CHANNEL:SKYTMBLR_RF_BIND_CHANNEL); // Bind channel } uint16_t JJRC345_callback() diff --git a/Multiprotocol/KF606_ccnrf.ino b/Multiprotocol/KF606_ccnrf.ino index 81094eb..2447a19 100644 --- a/Multiprotocol/KF606_ccnrf.ino +++ b/Multiprotocol/KF606_ccnrf.ino @@ -45,14 +45,15 @@ static void __attribute__((unused)) KF606_send_packet() } if(IS_BIND_DONE) { - XN297L_Hopping(hopping_frequency_no); + XN297_Hopping(hopping_frequency_no); hopping_frequency_no ^= 1; // 2 RF channels } - XN297L_WritePayload(packet, KF606_PAYLOAD_SIZE); - - XN297L_SetPower(); // Set tx_power - XN297L_SetFreqOffset(); // Set frequency offset + // Send + XN297_SetPower(); + XN297_SetFreqOffset(); + XN297_SetTxRxMode(TX_EN); + XN297_WritePayload(packet, KF606_PAYLOAD_SIZE); } static void __attribute__((unused)) KF606_initialize_txid() @@ -78,10 +79,10 @@ static void __attribute__((unused)) KF606_initialize_txid() static void __attribute__((unused)) KF606_RF_init() { - XN297L_Init(); - XN297L_SetTXAddr((uint8_t*)"\xe7\xe7\xe7\xe7\xe7", 5); - XN297L_HoppingCalib(KF606_RF_NUM_CHANNELS); // Calibrate all channels - XN297L_RFChannel(KF606_RF_BIND_CHANNEL); // Set bind channel + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_250K); + XN297_SetTXAddr((uint8_t*)"\xe7\xe7\xe7\xe7\xe7", 5); + XN297_HoppingCalib(KF606_RF_NUM_CHANNELS); // Calibrate all channels + XN297_RFChannel(KF606_RF_BIND_CHANNEL); // Set bind channel } uint16_t KF606_callback() @@ -93,7 +94,7 @@ uint16_t KF606_callback() if(--bind_counter==0) { BIND_DONE; - XN297L_SetTXAddr(rx_tx_addr, 3); + XN297_SetTXAddr(rx_tx_addr, 3); } KF606_send_packet(); return KF606_PACKET_PERIOD; diff --git a/Multiprotocol/MJXQ_nrf24l01.ino b/Multiprotocol/MJXQ_ccnrf.ino similarity index 88% rename from Multiprotocol/MJXQ_nrf24l01.ino rename to Multiprotocol/MJXQ_ccnrf.ino index 87f3096..bbc41bd 100644 --- a/Multiprotocol/MJXQ_nrf24l01.ino +++ b/Multiprotocol/MJXQ_ccnrf.ino @@ -15,10 +15,9 @@ // compatible with MJX WLH08, X600, X800, H26D, Eachine E010 // Last sync with hexfet new_protocols/mjxq_nrf24l01.c dated 2016-01-17 -#if defined(MJXQ_NRF24L01_INO) +#if defined(MJXQ_CCNRF_INO) -#include "iface_nrf24l01.h" -#include "iface_nrf250k.h" +#include "iface_xn297.h" #define MJXQ_BIND_COUNT 150 #define MJXQ_PACKET_PERIOD 4000 // Timeout for callback in uSec @@ -103,6 +102,12 @@ static uint8_t __attribute__((unused)) MJXQ_pan_tilt_value() #define MJXQ_CHAN2TRIM(X) (((X) & 0x80 ? (X) : 0x7f - (X)) >> 1) static void __attribute__((unused)) MJXQ_send_packet(uint8_t bind) { + //RF freq + hopping_frequency_no++; + XN297_Hopping(hopping_frequency_no / 2); + hopping_frequency_no %= 2 * MJXQ_RF_NUM_CHANNELS; // channels repeated + + //Build packet packet[0] = convert_channel_8b(THROTTLE); packet[1] = convert_channel_s8b(RUDDER); packet[4] = 0x40; // rudder does not work well with dyntrim @@ -192,35 +197,26 @@ static void __attribute__((unused)) MJXQ_send_packet(uint8_t bind) uint8_t sum = packet[0]; for (uint8_t i=1; i < MJXQ_PACKET_SIZE-1; i++) sum += packet[i]; packet[15] = sum; - hopping_frequency_no++; - if (sub_protocol == E010 || sub_protocol == PHOENIX) + + // Send + XN297_SetTxRxMode(TX_EN); + XN297_SetPower(); +#ifdef NRF24L01_INSTALLED + if (sub_protocol == H26D || sub_protocol == H26WH) { - XN297L_Hopping(hopping_frequency_no / 2); - XN297L_SetFreqOffset(); - XN297L_SetPower(); - XN297L_WritePayload(packet, MJXQ_PACKET_SIZE); + //NRF24L01_WriteReg(NRF24L01_05_RF_CH, hopping_frequency[hopping_frequency_no / 2]); + //NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); + //NRF24L01_FlushTx(); + //NRF24L01_SetTxRxMode(TX_EN); + //NRF24L01_SetPower(); + NRF24L01_WritePayload(packet, MJXQ_PACKET_SIZE); } else - { - NRF24L01_WriteReg(NRF24L01_05_RF_CH, hopping_frequency[hopping_frequency_no / 2]); - - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); - NRF24L01_FlushTx(); - - // Power on, TX mode, 2byte CRC and send packet - if (sub_protocol == H26D || sub_protocol == H26WH) - { - NRF24L01_SetTxRxMode(TX_EN); - NRF24L01_WritePayload(packet, MJXQ_PACKET_SIZE); - } - else - { - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP)); - XN297_WritePayload(packet, MJXQ_PACKET_SIZE); - } - NRF24L01_SetPower(); +#endif + {//E010, PHOENIX, WLH08, X600, X800 + XN297_SetFreqOffset(); + XN297_WritePayload(packet, MJXQ_PACKET_SIZE); } - hopping_frequency_no %= 2 * MJXQ_RF_NUM_CHANNELS; // channels repeated } static void __attribute__((unused)) MJXQ_RF_init() @@ -239,22 +235,20 @@ static void __attribute__((unused)) MJXQ_RF_init() } if (sub_protocol == E010 || sub_protocol == PHOENIX) { - XN297L_Init(); - XN297L_SetTXAddr(addr, sizeof(addr)); - XN297L_HoppingCalib(MJXQ_RF_NUM_CHANNELS); + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_250K); + XN297_SetTXAddr(addr, MJXQ_ADDRESS_LENGTH); + XN297_HoppingCalib(MJXQ_RF_NUM_CHANNELS); } else { - NRF24L01_Initialize(); - + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_1M); // this will select the nrf and initialize it, therefore both H26 sub protocols can use common instructions +#ifdef NRF24L01_INSTALLED if (sub_protocol == H26D || sub_protocol == H26WH) - { NRF24L01_WriteRegisterMulti(NRF24L01_10_TX_ADDR, addr, MJXQ_ADDRESS_LENGTH); - } else +#endif XN297_SetTXAddr(addr, MJXQ_ADDRESS_LENGTH); - - NRF24L01_WriteReg(NRF24L01_11_RX_PW_P0, MJXQ_PACKET_SIZE); + //NRF24L01_WriteReg(NRF24L01_11_RX_PW_P0, MJXQ_PACKET_SIZE); // no RX??? } } @@ -275,7 +269,7 @@ static void __attribute__((unused)) MJXQ_init2() hopping_frequency[i]=pgm_read_byte_near( &E010_map_rfchan[rx_tx_addr[3]&0x0F][i] ); hopping_frequency[i+2]=hopping_frequency[i]+0x10; } - XN297L_HoppingCalib(MJXQ_RF_NUM_CHANNELS); + XN297_HoppingCalib(MJXQ_RF_NUM_CHANNELS); break; case WLH08: // do nothing diff --git a/Multiprotocol/MT99xx_nrf24l01.ino b/Multiprotocol/MT99xx_ccnrf.ino similarity index 93% rename from Multiprotocol/MT99xx_nrf24l01.ino rename to Multiprotocol/MT99xx_ccnrf.ino index 836bf10..cd6e85c 100644 --- a/Multiprotocol/MT99xx_nrf24l01.ino +++ b/Multiprotocol/MT99xx_ccnrf.ino @@ -15,10 +15,9 @@ // compatible with MT99xx, Eachine H7, Yi Zhan i6S and LS114/124 // Last sync with Goebish mt99xx_nrf24l01.c dated 2016-01-29 -#if defined(MT99XX_NRF24L01_INO) +#if defined(MT99XX_CCNRF_INO) -#include "iface_nrf24l01.h" -#include "iface_nrf250k.h" +#include "iface_xn297.h" #define MT99XX_BIND_COUNT 928 #define MT99XX_PACKET_PERIOD_FY805 2460 @@ -246,17 +245,14 @@ static void __attribute__((unused)) MT99XX_send_packet() } } + //RF freq if(sub_protocol == LS) - NRF24L01_WriteReg(NRF24L01_05_RF_CH, 0x2D); // LS always transmits on the same channel + XN297_RFChannel(0x2D); // LS always transmits on the same channel else if(sub_protocol==FY805) - NRF24L01_WriteReg(NRF24L01_05_RF_CH, 0x4B); // FY805 always transmits on the same channel + XN297_RFChannel(0x4B); // FY805 always transmits on the same channel else // MT99 & H7 & YZ & A180 & DRAGON - NRF24L01_WriteReg(NRF24L01_05_RF_CH, hopping_frequency[hopping_frequency_no]); - - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); - NRF24L01_FlushTx(); - XN297_WritePayload(packet, MT99XX_PACKET_SIZE); + XN297_Hopping(hopping_frequency_no); if(sub_protocol == DRAGON) { @@ -269,23 +265,24 @@ static void __attribute__((unused)) MT99XX_send_packet() hopping_frequency_no++; if(sub_protocol == YZ || sub_protocol == A180 || sub_protocol == DRAGON ) hopping_frequency_no++; // skip every other channel - if(hopping_frequency_no > 15) hopping_frequency_no = 0; - NRF24L01_SetPower(); + // Send + XN297_SetPower(); + XN297_SetFreqOffset(); + XN297_SetTxRxMode(TX_EN); + XN297_WritePayload(packet, MT99XX_PACKET_SIZE); } static void __attribute__((unused)) MT99XX_RF_init() { - NRF24L01_Initialize(); - if(sub_protocol == YZ) - XN297_SetScrambledMode(XN297_UNSCRAMBLED); + XN297_Configure(XN297_CRCEN, XN297_UNSCRAMBLED, XN297_250K); + else + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_1M); XN297_SetTXAddr((uint8_t *)"\xCC\xCC\xCC\xCC\xCC", 5); - if(sub_protocol == YZ) - NRF24L01_SetBitrate(NRF24L01_BR_250K); // 250Kbps (nRF24L01+ only) - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP) ); + XN297_HoppingCalib(16); } static void __attribute__((unused)) MT99XX_initialize_txid() @@ -360,6 +357,7 @@ uint16_t MT99XX_callback() uint8_t channel_offset = ((crc8>>4) + (crc8 & 0x0f)) % 8; for(uint8_t i=0;i<16;i++) hopping_frequency[i] += channel_offset; + XN297_HoppingCalib(16); BIND_DONE; } } diff --git a/Multiprotocol/Multi.txt b/Multiprotocol/Multi.txt index bda7221..ad4a237 100644 --- a/Multiprotocol/Multi.txt +++ b/Multiprotocol/Multi.txt @@ -42,7 +42,7 @@ 42,BUGSMINI,BUGSMINI,BUGS3H 43,Traxxas,RX6519 44,NCC1701 -45,E01X,E012,E015,E016H +45,E01X,E012,E015 46,V911S,V911S,E119 47,GD00x,GD_V1,GD_V2 48,V761,3CH,4CH @@ -81,4 +81,5 @@ 81,E010r5 82,LOLI 83,E129 -84,JOYSWAY \ No newline at end of file +84,JOYSWAY +85,E016H \ No newline at end of file diff --git a/Multiprotocol/Multi_Protos.ino b/Multiprotocol/Multi_Protos.ino index 6bc85ec..3f83650 100644 --- a/Multiprotocol/Multi_Protos.ino +++ b/Multiprotocol/Multi_Protos.ino @@ -97,6 +97,7 @@ const char STR_E016HV2[] ="E016Hv2"; const char STR_E010R5[] ="E010r5"; const char STR_LOLI[] ="LOLI"; const char STR_E129[] ="E129"; +const char STR_E016H[] ="E016H"; const char STR_SUBTYPE_FLYSKY[] = "\x04""Std\0""V9x9""V6x6""V912""CX20"; const char STR_SUBTYPE_HUBSAN[] = "\x04""H107""H301""H501"; @@ -233,6 +234,9 @@ const mm_protocol_definition multi_protocols[] = { #if defined(E010R5_CYRF6936_INO) {PROTO_E010R5, STR_E010R5, NO_SUBTYPE, 0, OPTION_NONE, 0, 0, SW_CYRF, E010R5_init, E010R5_callback }, #endif + #if defined(E016H_NRF24L01_INO) + {PROTO_E016H, STR_E016H, NO_SUBTYPE, 0, OPTION_NONE, 0, 0, SW_NRF, E016H_init, E016H_callback }, + #endif #if defined(E016HV2_CC2500_INO) {PROTO_E016HV2, STR_E016HV2, NO_SUBTYPE, 0, OPTION_RFTUNE, 0, 0, SW_CC2500, E016HV2_init, E016HV2_callback }, #endif @@ -345,20 +349,20 @@ const mm_protocol_definition multi_protocols[] = { #if defined(LOLI_NRF24L01_INO) {PROTO_LOLI, STR_LOLI, NO_SUBTYPE, 0, OPTION_NONE, 1, 0, SW_NRF, LOLI_init, LOLI_callback }, #endif - #if defined(MJXQ_NRF24L01_INO) - {PROTO_MJXQ, STR_MJXQ, STR_SUBTYPE_MJXQ, 7, OPTION_RFTUNE, 0, 0, SW_NRF, MJXQ_init, MJXQ_callback }, + #if defined(MJXQ_CCNRF_INO) + {PROTO_MJXQ, STR_MJXQ, STR_SUBTYPE_MJXQ, 7, OPTION_NONE, 0, 0, SW_NRF, MJXQ_init, MJXQ_callback }, #endif #if defined(MLINK_CYRF6936_INO) {PROTO_MLINK, STR_MLINK, NO_SUBTYPE, 0, OPTION_NONE, 1, 0, SW_CYRF, MLINK_init, MLINK_callback }, #endif - #if defined(MT99XX_NRF24L01_INO) + #if defined(MT99XX_CCNRF_INO) {PROTO_MT99XX, STR_MT99XX, STR_SUBTYPE_MT99, 7, OPTION_NONE, 0, 0, SW_NRF, MT99XX_init, MT99XX_callback }, #endif #if defined(NCC1701_NRF24L01_INO) {PROTO_NCC1701, STR_NCC1701, NO_SUBTYPE, 0, OPTION_NONE, 0, 0, SW_NRF, NCC_init, NCC_callback }, #endif - #if defined(OMP_CC2500_INO) - {PROTO_OMP, STR_OMP, NO_SUBTYPE, 0, OPTION_RFTUNE, 0, 0, SW_NRF, OMP_init, OMP_callback }, + #if defined(OMP_CCNRF_INO) + {PROTO_OMP, STR_OMP, NO_SUBTYPE, 0, OPTION_NONE, 0, 0, SW_NRF, OMP_init, OMP_callback }, #endif #if defined(PELIKAN_A7105_INO) {PROTO_PELIKAN, STR_PELIKAN, STR_SUBTYPE_PELIKAN, 2, OPTION_NONE, 0, 1, SW_A7105, PELIKAN_init, PELIKAN_callback }, @@ -372,7 +376,7 @@ const mm_protocol_definition multi_protocols[] = { #if defined(CX10_NRF24L01_INO) {PROTO_Q2X2, STR_Q2X2, STR_SUBTYPE_Q2X2, 3, OPTION_NONE, 0, 0, SW_NRF, CX10_init, CX10_callback }, #endif - #if defined(Q303_NRF24L01_INO) + #if defined(Q303_CCNRF_INO) {PROTO_Q303, STR_Q303, STR_SUBTYPE_Q303, 4, OPTION_NONE, 0, 0, SW_NRF, Q303_init, Q303_callback }, #endif #if defined(Q90C_CCNRF_INO) @@ -427,7 +431,7 @@ const mm_protocol_definition multi_protocols[] = { {PROTO_WFLY2, STR_WFLY2, STR_SUBTYPE_WFLY2, 1, OPTION_OPTION, 1, 0, SW_A7105, WFLY2_init, WFLY2_callback }, // {PROTO_WFLY2, STR_WFLY2, STR_SUBTYPE_WFLY2, 1, OPTION_WBUS, 1, 0, SW_A7105, WFLY2_init, WFLY2_callback },// crash OpenTX... #endif - #if defined(XK_NRF24L01_INO) + #if defined(XK_CCNRF_INO) {PROTO_XK, STR_XK, STR_SUBTYPE_XK, 2, OPTION_RFTUNE, 0, 0, SW_NRF, XK_init, XK_callback }, #endif #if defined(XN297DUMP_NRF24L01_INO) diff --git a/Multiprotocol/Multiprotocol.h b/Multiprotocol/Multiprotocol.h index 9ba165f..372e1bc 100644 --- a/Multiprotocol/Multiprotocol.h +++ b/Multiprotocol/Multiprotocol.h @@ -19,7 +19,7 @@ #define VERSION_MAJOR 1 #define VERSION_MINOR 3 #define VERSION_REVISION 2 -#define VERSION_PATCH_LEVEL 61 +#define VERSION_PATCH_LEVEL 62 #define MODE_SERIAL 0 @@ -112,6 +112,7 @@ enum PROTOCOLS PROTO_LOLI = 82, // =>NRF24L01 PROTO_E129 = 83, // =>CYRF6936 PROTO_JOYSWAY = 84, // =>A7105 + PROTO_E016H = 85, // =>NRF24L01 PROTO_NANORF = 126, // =>NRF24L01 PROTO_TEST = 127, // =>CC2500 @@ -587,6 +588,11 @@ enum MultiPacketTypes #define DISABLE_TELEM_on protocol_flags3 |= _BV(3) #define IS_DISABLE_TELEM_on ( ( protocol_flags3 & _BV(3) ) !=0 ) #define IS_DISABLE_TELEM_off ( ( protocol_flags3 & _BV(3) ) ==0 ) +//Valid/invalid sub_proto +#define SUB_PROTO_VALID protocol_flags3 &= ~_BV(6) +#define SUB_PROTO_INVALID protocol_flags3 |= _BV(6) +#define IS_SUB_PROTO_INVALID ( ( protocol_flags3 & _BV(6) ) !=0 ) +#define IS_SUB_PROTO_VALID ( ( protocol_flags3 & _BV(6) ) ==0 ) //LBT power #define LBT_POWER_off protocol_flags3 &= ~_BV(7) #define LBT_POWER_on protocol_flags3 |= _BV(7) @@ -890,6 +896,8 @@ Serial: 100000 Baud 8e2 _ xxxx xxxx p -- E010R5 81 LOLI 82 E129 83 + JOYSWAY 84 + E016H 85 BindBit=> 0x80 1=Bind/0=No AutoBindBit=> 0x40 1=Yes /0=No RangeCheck=> 0x20 1=Yes /0=No @@ -1035,7 +1043,6 @@ Serial: 100000 Baud 8e2 _ xxxx xxxx p -- sub_protocol==E01X E012 0 E015 1 - E016H 2 sub_protocol==GD00X GD_V1 0 GD_V2 1 diff --git a/Multiprotocol/Multiprotocol.ino b/Multiprotocol/Multiprotocol.ino index 73ea7d0..5c12a80 100644 --- a/Multiprotocol/Multiprotocol.ino +++ b/Multiprotocol/Multiprotocol.ino @@ -158,6 +158,7 @@ uint8_t CH_EATR[]={ELEVATOR, AILERON, THROTTLE, RUDDER, CH5, CH6, CH7, CH8, CH9, // Mode_select variables uint8_t mode_select; uint8_t protocol_flags=0,protocol_flags2=0,protocol_flags3=0; +uint8_t option_override; #ifdef ENABLE_PPM // PPM variable @@ -1179,6 +1180,9 @@ static void protocol_init() FAILSAFE_VALUES_off; #endif DATA_BUFFER_LOW_off; + + SUB_PROTO_VALID; + option_override = 0xFF; blink=millis(); diff --git a/Multiprotocol/NRF24l01_SPI.ino b/Multiprotocol/NRF24l01_SPI.ino index 9b0753a..22e0c2a 100644 --- a/Multiprotocol/NRF24l01_SPI.ino +++ b/Multiprotocol/NRF24l01_SPI.ino @@ -28,7 +28,6 @@ void NRF24L01_Initialize() { rf_setup = 0x09; prev_power = 0x00; // Make sure prev_power is inline with current power - XN297_SetScrambledMode(XN297_SCRAMBLED); //Load most likely default NRF config NRF24L01_FlushTx(); @@ -196,11 +195,11 @@ void NRF24L01_SetPower() void NRF24L01_SetTxRxMode(enum TXRX_State mode) { + NRF24L01_WriteReg(NRF24L01_07_STATUS, (1 << NRF24L01_07_RX_DR) //reset the flag(s) + | (1 << NRF24L01_07_TX_DS) + | (1 << NRF24L01_07_MAX_RT)); if(mode == TX_EN) { NRF_CE_off; - NRF24L01_WriteReg(NRF24L01_07_STATUS, (1 << NRF24L01_07_RX_DR) //reset the flag(s) - | (1 << NRF24L01_07_TX_DS) - | (1 << NRF24L01_07_MAX_RT)); NRF24L01_WriteReg(NRF24L01_00_CONFIG, (1 << NRF24L01_00_EN_CRC) // switch to TX mode | (1 << NRF24L01_00_CRCO) | (1 << NRF24L01_00_PWR_UP)); @@ -211,9 +210,6 @@ void NRF24L01_SetTxRxMode(enum TXRX_State mode) if (mode == RX_EN) { NRF_CE_off; - NRF24L01_WriteReg(NRF24L01_07_STATUS, (1 << NRF24L01_07_RX_DR) //reset the flag(s) - | (1 << NRF24L01_07_TX_DS) - | (1 << NRF24L01_07_MAX_RT)); NRF24L01_WriteReg(NRF24L01_00_CONFIG, (1 << NRF24L01_00_EN_CRC) // switch to RX mode | (1 << NRF24L01_00_CRCO) | (1 << NRF24L01_00_PWR_UP) diff --git a/Multiprotocol/NRF250K_EMU.ino b/Multiprotocol/NRF250K_EMU.ino index 27712b1..44da9b8 100644 --- a/Multiprotocol/NRF250K_EMU.ino +++ b/Multiprotocol/NRF250K_EMU.ino @@ -15,223 +15,16 @@ #if defined(CC2500_INSTALLED) || defined(NRF24L01_INSTALLED) #include "iface_nrf250k.h" -#include "iface_xn297.h" -static void __attribute__((unused)) XN297L_Init() -{ - //CC2500 - #if defined(CC2500_INSTALLED) - debugln("Using CC2500"); - xn297_scramble_enabled=XN297_SCRAMBLED; //enabled by default - rf_switch(SW_CC2500); - CC2500_250K_Init(); - #elif defined(NRF24L01_INSTALLED) - debugln("Using NRF"); - rf_switch(SW_NRF); - NRF24L01_Initialize(); - NRF24L01_SetBitrate(NRF24L01_BR_250K); // 250Kbps - #endif -} - -static void __attribute__((unused)) XN297L_SetTXAddr(const uint8_t* addr, uint8_t len) -{ - #if defined(CC2500_INSTALLED) - if (len > 5) len = 5; - if (len < 3) len = 3; - xn297_addr_len = len; - memcpy(xn297_tx_addr, addr, len); - #elif defined(NRF24L01_INSTALLED) - XN297_SetTXAddr(addr,len); - #endif -} - -static void __attribute__((unused)) XN297L_WritePayload(uint8_t* msg, uint8_t len) -{ - #if defined(CC2500_INSTALLED) - uint8_t buf[32]; - uint8_t last = 0; - uint8_t i; - - // address - for (i = 0; i < xn297_addr_len; ++i) - { - buf[last] = xn297_tx_addr[xn297_addr_len - i - 1]; - if(xn297_scramble_enabled) - buf[last] ^= xn297_scramble[i]; - last++; - } - - // payload - for (i = 0; i < len; ++i) { - // bit-reverse bytes in packet - buf[last] = bit_reverse(msg[i]); - if(xn297_scramble_enabled) - buf[last] ^= xn297_scramble[xn297_addr_len+i]; - last++; - } - - // crc - crc = 0xb5d2; - for (uint8_t i = 0; i < last; ++i) - crc16_update( buf[i], 8); - if(xn297_scramble_enabled) - crc ^= pgm_read_word(&xn297_crc_xorout_scrambled[xn297_addr_len - 3 + len]); - else - crc ^= pgm_read_word(&xn297_crc_xorout[xn297_addr_len - 3 + len]); - buf[last++] = crc >> 8; - buf[last++] = crc & 0xff; - - // stop TX/RX - CC2500_Strobe(CC2500_SIDLE); - // flush tx FIFO - CC2500_Strobe(CC2500_SFTX); - // packet length - CC2500_WriteReg(CC2500_3F_TXFIFO, last + 3); - // xn297L preamble - CC2500_WriteRegisterMulti(CC2500_3F_TXFIFO, (uint8_t*)"\x71\x0f\x55", 3); - // xn297 packet - CC2500_WriteRegisterMulti(CC2500_3F_TXFIFO, buf, last); - // transmit - CC2500_Strobe(CC2500_STX); - #elif defined(NRF24L01_INSTALLED) - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP)); - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); - NRF24L01_FlushTx(); - XN297_WritePayload(msg, len); - #endif -} - -static void __attribute__((unused)) XN297L_WriteEnhancedPayload(uint8_t* msg, uint8_t len, uint8_t noack) -{ - #if defined(CC2500_INSTALLED) - uint8_t buf[32]; - uint8_t scramble_index=0; - uint8_t last = 0; - static uint8_t pid=0; - - // address - for (uint8_t i = 0; i < xn297_addr_len; ++i) - { - buf[last] = xn297_tx_addr[xn297_addr_len-i-1]; - if(xn297_scramble_enabled) - buf[last] ^= xn297_scramble[scramble_index++]; - last++; - } - - // pcf - buf[last] = (len << 1) | (pid>>1); - if(xn297_scramble_enabled) - buf[last] ^= xn297_scramble[scramble_index++]; - last++; - buf[last] = (pid << 7) | (noack << 6); - - // payload - buf[last]|= bit_reverse(msg[0]) >> 2; // first 6 bit of payload - if(xn297_scramble_enabled) - buf[last] ^= xn297_scramble[scramble_index++]; - - for (uint8_t i = 0; i < len-1; ++i) - { - last++; - buf[last] = (bit_reverse(msg[i]) << 6) | (bit_reverse(msg[i+1]) >> 2); - if(xn297_scramble_enabled) - buf[last] ^= xn297_scramble[scramble_index++]; - } - - last++; - buf[last] = bit_reverse(msg[len-1]) << 6; // last 2 bit of payload - if(xn297_scramble_enabled) - buf[last] ^= xn297_scramble[scramble_index++] & 0xc0; - - // crc - //if (xn297_crc) - { - crc = 0xb5d2; - for (uint8_t i = 0; i < last; ++i) - crc16_update( buf[i], 8); - crc16_update( buf[last] & 0xc0, 2); - if (xn297_scramble_enabled) - crc ^= pgm_read_word(&xn297_crc_xorout_scrambled_enhanced[xn297_addr_len-3+len]); - //else - // crc ^= pgm_read_word(&xn297_crc_xorout_enhanced[xn297_addr_len - 3 + len]); - - buf[last++] |= (crc >> 8) >> 2; - buf[last++] = ((crc >> 8) << 6) | ((crc & 0xff) >> 2); - buf[last++] = (crc & 0xff) << 6; - } - - pid++; - pid &= 3; - - // stop TX/RX - CC2500_Strobe(CC2500_SIDLE); - // flush tx FIFO - CC2500_Strobe(CC2500_SFTX); - // packet length - CC2500_WriteReg(CC2500_3F_TXFIFO, last + 3); - // xn297L preamble - CC2500_WriteRegisterMulti(CC2500_3F_TXFIFO, (uint8_t*)"\x71\x0F\x55", 3); - // xn297 packet - CC2500_WriteRegisterMulti(CC2500_3F_TXFIFO, buf, last); - // transmit - CC2500_Strobe(CC2500_STX); - #elif defined(NRF24L01_INSTALLED) - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP)); - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); - NRF24L01_FlushTx(); - XN297_WriteEnhancedPayload(msg, len, noack); - #endif -} - -static void __attribute__((unused)) XN297L_HoppingCalib(uint8_t num_freq) -{ //calibrate hopping frequencies - #if defined(CC2500_INSTALLED) - CC2500_250K_HoppingCalib(num_freq); - #elif defined(NRF24L01_INSTALLED) - (void)num_freq; - #endif -} - -static void __attribute__((unused)) XN297L_Hopping(uint8_t index) -{ - #if defined(CC2500_INSTALLED) - CC2500_250K_Hopping(index); - #elif defined(NRF24L01_INSTALLED) - NRF24L01_WriteReg(NRF24L01_05_RF_CH, hopping_frequency[index]); - #endif -} - -static void __attribute__((unused)) XN297L_RFChannel(uint8_t number) -{ //change channel - #if defined(CC2500_INSTALLED) - CC2500_250K_RFChannel(number); - #elif defined(NRF24L01_INSTALLED) - NRF24L01_WriteReg(NRF24L01_05_RF_CH, number); - #endif -} - -static void __attribute__((unused)) XN297L_SetPower() -{ - #if defined(CC2500_INSTALLED) - CC2500_SetPower(); - #elif defined(NRF24L01_INSTALLED) - NRF24L01_SetPower(); - #endif -} - -static void __attribute__((unused)) XN297L_SetFreqOffset() -{ // Frequency offset - #if defined(CC2500_INSTALLED) - CC2500_SetFreqOffset(); - #endif -} +uint8_t cc2500_nrf_tx_addr[5], cc2500_nrf_addr_len; static void __attribute__((unused)) NRF250K_SetTXAddr(uint8_t* addr, uint8_t len) { if (len > 5) len = 5; if (len < 3) len = 3; #if defined(CC2500_INSTALLED) - CC2500_250K_NRF_SetTXAddr(addr, len); + cc2500_nrf_addr_len = len; + memcpy(cc2500_nrf_tx_addr, addr, len); #elif defined(NRF24L01_INSTALLED) NRF24L01_WriteReg(NRF24L01_03_SETUP_AW, len-2); NRF24L01_WriteRegisterMulti(NRF24L01_10_TX_ADDR, addr, len); @@ -241,20 +34,86 @@ static void __attribute__((unused)) NRF250K_SetTXAddr(uint8_t* addr, uint8_t len static void __attribute__((unused)) NRF250K_WritePayload(uint8_t* msg, uint8_t len) { #if defined(CC2500_INSTALLED) - CC2500_250K_NRF_WritePayload(msg, len); + #if defined(ESKY150V2_CC2500_INO) + uint8_t buf[158]; + #else + uint8_t buf[35]; + #endif + uint8_t last = 0; + uint8_t i; + + //nrf preamble + if(cc2500_nrf_tx_addr[cc2500_nrf_addr_len - 1] & 0x80) + buf[0]=0xAA; + else + buf[0]=0x55; + last++; + // address + for (i = 0; i < cc2500_nrf_addr_len; ++i) + buf[last++] = cc2500_nrf_tx_addr[cc2500_nrf_addr_len - i - 1]; + // payload + for (i = 0; i < len; ++i) + buf[last++] = msg[i]; + + // crc + crc = 0xffff; + for (uint8_t i = 1; i < last; ++i) + crc16_update( buf[i], 8); + buf[last++] = crc >> 8; + buf[last++] = crc & 0xff; + buf[last++] = 0; + + //for(uint8_t i=0;i63) + { + CC2500_WriteRegisterMulti(CC2500_3F_TXFIFO, buff, 63); + CC2500_Strobe(CC2500_STX); + last-=63; + buff+=63; + while(last) + {//Loop until all the data is sent + do + {// Wait for the FIFO to become available + status=CC2500_ReadReg(CC2500_3A_TXBYTES | CC2500_READ_BURST); + } + while((status&0x7F)>31 && (status&0x80)==0); + if(last>31) + {//Send 31 bytes + CC2500_WriteRegisterMulti(CC2500_3F_TXFIFO, buff, 31); + last-=31; + buff+=31; + } + else + {//Send last bytes + CC2500_WriteRegisterMulti(CC2500_3F_TXFIFO, buff, last); + last=0; + } + } + } + else + {//Send packet + CC2500_WriteRegisterMulti(CC2500_3F_TXFIFO, buff, last); + CC2500_Strobe(CC2500_STX); + } #elif defined(NRF24L01_INSTALLED) - NRF24L01_FlushTx(); - NRF24L01_WriteReg(NRF24L01_07_STATUS, _BV(NRF24L01_07_TX_DS) | _BV(NRF24L01_07_RX_DR) | _BV(NRF24L01_07_MAX_RT)); - NRF24L01_WritePayload(msg, len); + if(len<=32) + { + NRF24L01_FlushTx(); + NRF24L01_WriteReg(NRF24L01_07_STATUS, _BV(NRF24L01_07_TX_DS) | _BV(NRF24L01_07_RX_DR) | _BV(NRF24L01_07_MAX_RT)); + NRF24L01_WritePayload(msg, len); + } #endif } -static boolean __attribute__((unused)) NRF250K_IsPacketSent() -{ - #if defined(CC2500_INSTALLED) - return true; // don't know on the CC2500 how to detect if the packet has been transmitted... - #elif defined(NRF24L01_INSTALLED) - return NRF24L01_ReadReg(NRF24L01_07_STATUS) & _BV(NRF24L01_07_TX_DS); - #endif -} #endif diff --git a/Multiprotocol/OMP_cc2500.ino b/Multiprotocol/OMP_ccnrf.ino similarity index 80% rename from Multiprotocol/OMP_cc2500.ino rename to Multiprotocol/OMP_ccnrf.ino index 5cb5630..a2900fc 100644 --- a/Multiprotocol/OMP_cc2500.ino +++ b/Multiprotocol/OMP_ccnrf.ino @@ -13,13 +13,9 @@ Multiprotocol is distributed in the hope that it will be useful, along with Multiprotocol. If not, see . */ -#if defined(OMP_CC2500_INO) +#if defined(OMP_CCNRF_INO) -#ifndef NRF24L01_INSTALLED - #undef OMP_HUB_TELEMETRY -#endif - -#include "iface_nrf250k.h" +#include "iface_xn297.h" //#define FORCE_OMP_ORIGINAL_ID //#define OMP_TELEM_DEBUG @@ -33,10 +29,6 @@ Multiprotocol is distributed in the hope that it will be useful, static void __attribute__((unused)) OMP_send_packet() { - #ifdef OMP_HUB_TELEMETRY - rf_switch(SW_CC2500); - #endif - if(IS_BIND_IN_PROGRESS) { memcpy(packet,"BND",3); @@ -52,15 +44,12 @@ static void __attribute__((unused)) OMP_send_packet() packet_sent++; packet_sent %= OMP_RF_NUM_CHANNELS-1; // Change telem RX channels every time if(packet_sent==0) - { packet[0] |= 0x40; // |0x40 to request RX telemetry - NRF24L01_WriteReg(NRF24L01_05_RF_CH, hopping_frequency[hopping_frequency_no]); - } #endif //hopping frequency packet[0 ] |= hopping_frequency_no; - XN297L_Hopping(hopping_frequency_no); + XN297_Hopping(hopping_frequency_no); hopping_frequency_no++; hopping_frequency_no &= OMP_RF_NUM_CHANNELS-1; // 8 RF channels @@ -103,27 +92,22 @@ static void __attribute__((unused)) OMP_send_packet() packet[15] = 0x04; } - XN297L_SetPower(); // Set tx_power - XN297L_SetFreqOffset(); // Set frequency offset - XN297L_WriteEnhancedPayload(packet, OMP_PAYLOAD_SIZE, packet_sent!=0); + XN297_SetPower(); // Set tx_power + XN297_SetFreqOffset(); // Set frequency offset + XN297_SetTxRxMode(TX_EN); + XN297_WriteEnhancedPayload(packet, OMP_PAYLOAD_SIZE, packet_sent!=0); } static void __attribute__((unused)) OMP_RF_init() { //Config CC2500 - XN297L_Init(); - XN297L_SetTXAddr((uint8_t*)"FLPBD", 5); - XN297L_HoppingCalib(OMP_RF_NUM_CHANNELS); // Calibrate all channels - XN297L_RFChannel(OMP_RF_BIND_CHANNEL); // Set bind channel + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_250K); + XN297_SetTXAddr((uint8_t*)"FLPBD", 5); + XN297_HoppingCalib(OMP_RF_NUM_CHANNELS); // Calibrate all channels + XN297_RFChannel(OMP_RF_BIND_CHANNEL); // Set bind channel #ifdef OMP_HUB_TELEMETRY - //Config NRF - NRF24L01_Initialize(); - NRF24L01_SetBitrate(NRF24L01_BR_250K); // 250Kbps - XN297_Configure(_BV(NRF24L01_00_EN_CRC)); - XN297_SetRXAddr(rx_tx_addr, 5); // Set the RX address - NRF24L01_SetTxRxMode(TXRX_OFF); // Turn it off for now - NRF24L01_WriteReg(NRF24L01_11_RX_PW_P0, OMP_PAYLOAD_SIZE + 4); // packet length +4 bytes of PCF+CRC + XN297_SetRXAddr(rx_tx_addr, OMP_PAYLOAD_SIZE); #endif } @@ -167,6 +151,8 @@ enum { uint16_t OMP_callback() { + bool rx; + switch(phase) { case OMP_BIND: @@ -176,12 +162,15 @@ uint16_t OMP_callback() return OMP_PACKET_PERIOD; case OMP_PREPDATA: BIND_DONE; - XN297L_SetTXAddr(rx_tx_addr, 5); + XN297_SetTXAddr(rx_tx_addr, 5); phase++; // OMP_DATA case OMP_DATA: #ifdef MULTI_SYNC telemetry_set_input_sync(OMP_PACKET_PERIOD); #endif + #ifdef OMP_HUB_TELEMETRY + rx = XN297_IsRX(); // Needed for the NRF24L01 since otherwise the bit gets cleared + #endif OMP_send_packet(); #ifdef OMP_HUB_TELEMETRY if(packet_sent == 0) @@ -191,8 +180,11 @@ uint16_t OMP_callback() } else if(packet_sent == 1) { - if( NRF24L01_ReadReg(NRF24L01_07_STATUS) & _BV(NRF24L01_07_RX_DR)) + if( rx ) { // a packet has been received + #ifdef OMP_TELEM_DEBUG + debug("RX :"); + #endif if(XN297_ReadEnhancedPayload(packet_in, OMP_PAYLOAD_SIZE) == OMP_PAYLOAD_SIZE) { // packet with good CRC and length #ifdef OMP_TELEM_DEBUG @@ -238,7 +230,7 @@ uint16_t OMP_callback() debugln(""); #endif } - NRF24L01_SetTxRxMode(TXRX_OFF); + XN297_SetTxRxMode(TXRX_OFF); packet_count++; if(packet_count>=100) {//LQI calculation @@ -254,21 +246,15 @@ uint16_t OMP_callback() return OMP_PACKET_PERIOD; #ifdef OMP_HUB_TELEMETRY case OMP_RX: - NRF24L01_WriteReg(NRF24L01_07_STATUS, (1 << NRF24L01_07_RX_DR) //reset the flag(s) - | (1 << NRF24L01_07_TX_DS) - | (1 << NRF24L01_07_MAX_RT)); - NRF24L01_FlushRx(); - NRF24L01_WriteReg(NRF24L01_00_CONFIG, (1 << NRF24L01_00_PWR_UP) | (1 << NRF24L01_00_PRIM_RX) ); // Start RX { uint16_t start=(uint16_t)micros(); while ((uint16_t)((uint16_t)micros()-(uint16_t)start) < 500) { - if(CC2500_ReadReg(CC2500_35_MARCSTATE | CC2500_READ_BURST) != 0x13) + if(XN297_IsPacketSent()) break; } } - NRF_CE_on; - rf_switch(SW_NRF); + XN297_SetTxRxMode(RX_EN); phase = OMP_DATA; return OMP_PACKET_PERIOD-OMP_WRITE_TIME; #endif diff --git a/Multiprotocol/POTENSIC_nrf24l01.ino b/Multiprotocol/POTENSIC_nrf24l01.ino index 74fde10..77826e8 100644 --- a/Multiprotocol/POTENSIC_nrf24l01.ino +++ b/Multiprotocol/POTENSIC_nrf24l01.ino @@ -61,19 +61,20 @@ static void __attribute__((unused)) POTENSIC_send_packet() } POTENSIC_set_checksum(); packet[9] = hopping_frequency_no; - NRF24L01_WriteReg(NRF24L01_05_RF_CH, hopping_frequency[hopping_frequency_no&0x03]); + + //RF channel + XN297_Hopping(hopping_frequency_no&0x03); hopping_frequency_no++; - // Power on, TX mode, 2byte CRC - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP)); - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); - NRF24L01_FlushTx(); + + // Send + XN297_SetPower(); + XN297_SetTxRxMode(TX_EN); XN297_WritePayload(packet, POTENSIC_PACKET_SIZE); - NRF24L01_SetPower(); } static void __attribute__((unused)) POTENSIC_RF_init() { - NRF24L01_Initialize(); + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_1M); if(IS_BIND_IN_PROGRESS) XN297_SetTXAddr((uint8_t*)"\x01\x01\x01\x01\x06", 5); // Bind address diff --git a/Multiprotocol/Q303_nrf24l01.ino b/Multiprotocol/Q303_ccnrf.ino similarity index 94% rename from Multiprotocol/Q303_nrf24l01.ino rename to Multiprotocol/Q303_ccnrf.ino index 9544f60..f22f018 100644 --- a/Multiprotocol/Q303_nrf24l01.ino +++ b/Multiprotocol/Q303_ccnrf.ino @@ -13,7 +13,7 @@ along with Multiprotocol. If not, see . */ -#if defined(Q303_NRF24L01_INO) +#if defined(Q303_CCNRF_INO) #include "iface_nrf24l01.h" @@ -185,6 +185,11 @@ static void __attribute__((unused)) Q303_send_packet() } else { + //RF freq + XN297_Hopping(hopping_frequency_no++); + hopping_frequency_no %= rf_ch_num; + + //Build packet packet[0] = 0x55; // sticks switch(sub_protocol) @@ -267,32 +272,27 @@ static void __attribute__((unused)) Q303_send_packet() } } - // Power on, TX mode, CRC enabled - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP)); - - NRF24L01_WriteReg(NRF24L01_05_RF_CH, IS_BIND_IN_PROGRESS ? Q303_RF_BIND_CHANNEL : hopping_frequency[hopping_frequency_no++]); - hopping_frequency_no %= rf_ch_num; - - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); - NRF24L01_FlushTx(); - + // Send + XN297_SetPower(); + XN297_SetFreqOffset(); + XN297_SetTxRxMode(TX_EN); XN297_WritePayload(packet, packet_length); - - NRF24L01_SetPower(); // Set tx_power } static void __attribute__((unused)) Q303_RF_init() { const uint8_t bind_address[] = {0xcc,0xcc,0xcc,0xcc,0xcc}; - NRF24L01_Initialize(); - if(sub_protocol==Q303) { - XN297_SetScrambledMode(XN297_UNSCRAMBLED); - NRF24L01_SetBitrate(NRF24L01_BR_250K); + XN297_Configure(XN297_CRCEN, XN297_UNSCRAMBLED, XN297_250K); + XN297_HoppingCalib(rf_ch_num); } + else + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_1M); + XN297_SetTXAddr(bind_address, 5); + XN297_RFChannel(Q303_RF_BIND_CHANNEL); } static void __attribute__((unused)) Q303_initialize_txid() diff --git a/Multiprotocol/Q90C_ccnrf.ino b/Multiprotocol/Q90C_ccnrf.ino index a6a9d17..078df73 100644 --- a/Multiprotocol/Q90C_ccnrf.ino +++ b/Multiprotocol/Q90C_ccnrf.ino @@ -51,7 +51,7 @@ static void __attribute__((unused)) Q90C_send_packet() } else { - XN297L_Hopping(hopping_frequency_no++); // RF Freq + XN297_Hopping(hopping_frequency_no++); // RF Freq hopping_frequency_no %= Q90C_RF_NUM_CHANNELS; packet[0]= convert_channel_8b(THROTTLE); // 0..255 // A,E,R have weird scaling, 0x00-0xff range (unsigned) but center isn't 7f or 80 @@ -108,9 +108,11 @@ static void __attribute__((unused)) Q90C_send_packet() packet[11] = sum ^ crc8; } - XN297L_SetFreqOffset(); // Set frequency offset - XN297L_SetPower(); // Set tx_power - XN297L_WriteEnhancedPayload(packet, Q90C_PACKET_SIZE, 0); + // Send + XN297_SetFreqOffset(); // Set frequency offset + XN297_SetPower(); // Set tx_power + XN297_SetTxRxMode(TX_EN); + XN297_WriteEnhancedPayload(packet, Q90C_PACKET_SIZE, 0); } static void __attribute__((unused)) Q90C_initialize_txid() @@ -133,13 +135,13 @@ static void __attribute__((unused)) Q90C_initialize_txid() static void __attribute__((unused)) Q90C_RF_init() { - XN297L_Init(); + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_250K); if(IS_BIND_IN_PROGRESS) - XN297L_SetTXAddr((uint8_t*)"\x4F\x43\x54\x81\x81", Q90C_ADDRESS_LENGTH); + XN297_SetTXAddr((uint8_t*)"\x4F\x43\x54\x81\x81", Q90C_ADDRESS_LENGTH); else - XN297L_SetTXAddr(rx_tx_addr, Q90C_ADDRESS_LENGTH); - XN297L_HoppingCalib(Q90C_RF_NUM_CHANNELS); // Calibrate all channels - XN297L_RFChannel(Q90C_RF_BIND_CHANNEL); // Set bind channel + XN297_SetTXAddr(rx_tx_addr, Q90C_ADDRESS_LENGTH); + XN297_HoppingCalib(Q90C_RF_NUM_CHANNELS); // Calibrate all channels + XN297_RFChannel(Q90C_RF_BIND_CHANNEL); // Set bind channel } uint16_t Q90C_callback() @@ -151,7 +153,7 @@ uint16_t Q90C_callback() if(--bind_counter==0) { BIND_DONE; - XN297L_SetTXAddr(rx_tx_addr, Q90C_ADDRESS_LENGTH); + XN297_SetTXAddr(rx_tx_addr, Q90C_ADDRESS_LENGTH); } Q90C_send_packet(); return Q90C_PACKET_PERIOD; diff --git a/Multiprotocol/REALACC_nrf24l01.ino b/Multiprotocol/REALACC_nrf24l01.ino index 3d2fc51..d900791 100644 --- a/Multiprotocol/REALACC_nrf24l01.ino +++ b/Multiprotocol/REALACC_nrf24l01.ino @@ -51,7 +51,7 @@ static void __attribute__((unused)) REALACC_send_packet() | GET_FLAG(CH5_SW, 0x01) // Flip | GET_FLAG(CH6_SW, 0x80); // Light - NRF24L01_WriteReg(NRF24L01_05_RF_CH, hopping_frequency_no); + XN297_Hopping(hopping_frequency_no); hopping_frequency_no++; hopping_frequency_no %= REALACC_RF_NUM_CHANNELS; XN297_WriteEnhancedPayload(packet, REALACC_PAYLOAD_SIZE,0); @@ -88,10 +88,9 @@ static void __attribute__((unused)) REALACC_initialize_txid() static void __attribute__((unused)) REALACC_RF_init() { - NRF24L01_Initialize(); - + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_1M); XN297_SetTXAddr((uint8_t*)"MAIN", 4); - NRF24L01_WriteReg(NRF24L01_05_RF_CH, REALACC_BIND_RF_CHANNEL); // Set bind channel + XN297_RFChannel(REALACC_BIND_RF_CHANNEL); // Set bind channel } uint16_t REALACC_callback() @@ -99,10 +98,8 @@ uint16_t REALACC_callback() #ifdef MULTI_SYNC telemetry_set_input_sync(REALACC_PACKET_PERIOD); #endif - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP)); - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); - NRF24L01_FlushTx(); - NRF24L01_SetPower(); + XN297_SetPower(); + XN297_SetTxRxMode(TX_EN); if(IS_BIND_IN_PROGRESS) { REALACC_send_bind_packet(); diff --git a/Multiprotocol/Telemetry.ino b/Multiprotocol/Telemetry.ino index 322aa80..6813dfd 100644 --- a/Multiprotocol/Telemetry.ino +++ b/Multiprotocol/Telemetry.ino @@ -139,11 +139,15 @@ static void multi_send_status() if(protocol!=PROTO_SCANNER) flags &= ~0x04; //Invalid protocol } + else if(IS_SUB_PROTO_INVALID) + { + flags &= ~0x04; //Invalid sub protocol + } else if(sub_protocol&0x07) { uint8_t nbr=multi_protocols[multi_protocols_index].nbrSubProto; //if(protocol==PROTO_DSM) nbr++; //Auto sub_protocol - if((sub_protocol&0x07)>=nbr) + if((sub_protocol&0x07)>=nbr ) flags &= ~0x04; //Invalid sub protocol } if (IS_WAIT_BIND_on) @@ -174,12 +178,12 @@ static void multi_send_status() // Channel order Serial_write(RUDDER<<6|THROTTLE<<4|ELEVATOR<<2|AILERON); - if(multi_protocols_index == 0xFF) // selection out of list... send first available protocol + if(multi_protocols_index == 0xFF) // selection out of list... send first available protocol { - Serial_write(multi_protocols[0].protocol); // begining of list - Serial_write(multi_protocols[0].protocol); // begining of list + Serial_write(multi_protocols[0].protocol); // begining of list + Serial_write(multi_protocols[0].protocol); // begining of list for(uint8_t i=0;i<16;i++) - Serial_write(0x00); // everything else is invalid + Serial_write(0x00); // everything else is invalid } else { @@ -191,13 +195,13 @@ static void multi_send_status() if(multi_protocols[multi_protocols_index+2].protocol != 0) Serial_write(multi_protocols[multi_protocols_index+2].protocol); // skip to next protocol number else - Serial_write(multi_protocols[multi_protocols_index].protocol); // or end of list + Serial_write(multi_protocols[multi_protocols_index].protocol); // or end of list } else - Serial_write(multi_protocols[multi_protocols_index+1].protocol); // next protocol number + Serial_write(multi_protocols[multi_protocols_index+1].protocol); // next protocol number } else - Serial_write(multi_protocols[multi_protocols_index].protocol); // end of list + Serial_write(multi_protocols[multi_protocols_index].protocol); // end of list if(multi_protocols_index>0) { if(multi_protocols[multi_protocols_index-1].protocol==PROTO_SCANNER) @@ -205,19 +209,22 @@ static void multi_send_status() if(multi_protocols_index > 1) Serial_write(multi_protocols[multi_protocols_index-2].protocol); // skip to prev protocol number else - Serial_write(multi_protocols[multi_protocols_index].protocol); // begining of list + Serial_write(multi_protocols[multi_protocols_index].protocol); // begining of list } else - Serial_write(multi_protocols[multi_protocols_index-1].protocol); // prev protocol number + Serial_write(multi_protocols[multi_protocols_index-1].protocol); // prev protocol number } else - Serial_write(multi_protocols[multi_protocols_index].protocol); // begining of list + Serial_write(multi_protocols[multi_protocols_index].protocol); // begining of list // Protocol for(uint8_t i=0;i<7;i++) - Serial_write(multi_protocols[multi_protocols_index].ProtoString[i]); // protocol name + Serial_write(multi_protocols[multi_protocols_index].ProtoString[i]); // protocol name // Sub-protocol uint8_t nbr=multi_protocols[multi_protocols_index].nbrSubProto; - Serial_write(nbr | (multi_protocols[multi_protocols_index].optionType<<4)); // number of sub protocols && option type + if(option_override>0x0F) + Serial_write(nbr | (multi_protocols[multi_protocols_index].optionType<<4)); // number of sub protocols && option type + else + Serial_write(nbr | (option_override<<4)); // number of sub protocols && option_override type uint8_t j=0; if(nbr && (sub_protocol&0x07)>1]); + XN297_Hopping(hopping_frequency_no>>1); hopping_frequency_no++; if(IS_BIND_IN_PROGRESS) { @@ -79,22 +79,16 @@ static void __attribute__((unused)) TIGER_send_packet() hopping_frequency_no=2*TIGER_BIND_RF_NUM_CHANNELS; } - //Clear packet status bits and TX FIFO - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); - NRF24L01_FlushTx(); - //Send packet + //Send + XN297_SetPower(); + XN297_SetTxRxMode(TX_EN); XN297_WritePayload(packet, TIGER_PAYLOAD_SIZE); - //Set tx_power - NRF24L01_SetPower(); } static void __attribute__((unused)) TIGER_RF_init() { - NRF24L01_Initialize(); - + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_1M); XN297_SetTXAddr((uint8_t *)"\x68\x94\xA6\xD5\xC3", 5); - // Power on, TX mode, 2byte CRC - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP)); } static void __attribute__((unused)) TIGER_initialize_txid() diff --git a/Multiprotocol/V761_nrf24l01.ino b/Multiprotocol/V761_nrf24l01.ino index 30007c9..8bd17fe 100644 --- a/Multiprotocol/V761_nrf24l01.ino +++ b/Multiprotocol/V761_nrf24l01.ino @@ -115,18 +115,16 @@ static void __attribute__((unused)) V761_send_packet() hopping_frequency_no = 0; } V761_set_checksum(); - // Power on, TX mode, 2byte CRC - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP)); - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); - NRF24L01_FlushTx(); + + // Send + XN297_SetPower(); + XN297_SetTxRxMode(TX_EN); XN297_WritePayload(packet, V761_PACKET_SIZE); - NRF24L01_SetPower(); } static void __attribute__((unused)) V761_RF_init() { - NRF24L01_Initialize(); - NRF24L01_WriteReg(NRF24L01_03_SETUP_AW, 0x02); // set address length (4 bytes) + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_1M); } static void __attribute__((unused)) V761_initialize_txid() @@ -175,7 +173,7 @@ uint16_t V761_callback() if(bind_counter) bind_counter--; packet_count ++; - NRF24L01_WriteReg(NRF24L01_05_RF_CH, V761_BIND_FREQ); + XN297_RFChannel(V761_BIND_FREQ); XN297_SetTXAddr((uint8_t*)"\x34\x43\x10\x10", 4); V761_send_packet(); if(packet_count >= 20) @@ -188,7 +186,7 @@ uint16_t V761_callback() if(bind_counter) bind_counter--; packet_count ++; - NRF24L01_WriteReg(NRF24L01_05_RF_CH, hopping_frequency[0]); + XN297_Hopping(0); XN297_SetTXAddr(rx_tx_addr, 4); V761_send_packet(); if(bind_counter == 0) diff --git a/Multiprotocol/V911S_ccnrf.ino b/Multiprotocol/V911S_ccnrf.ino index 8461cda..7eef1d9 100644 --- a/Multiprotocol/V911S_ccnrf.ino +++ b/Multiprotocol/V911S_ccnrf.ino @@ -58,7 +58,7 @@ static void __attribute__((unused)) V911S_send_packet() } if(rf_ch_num&2) channel=7-channel; - XN297L_Hopping(channel); + XN297_Hopping(channel); hopping_frequency_no++; hopping_frequency_no&=7; // 8 RF channels @@ -102,23 +102,23 @@ static void __attribute__((unused)) V911S_send_packet() } if(sub_protocol==V911S_STD) - XN297L_WritePayload(packet, V911S_PACKET_SIZE); + XN297_WritePayload(packet, V911S_PACKET_SIZE); else - XN297L_WriteEnhancedPayload(packet, V911S_PACKET_SIZE, IS_BIND_IN_PROGRESS?0:1); + XN297_WriteEnhancedPayload(packet, V911S_PACKET_SIZE, IS_BIND_IN_PROGRESS?0:1); - XN297L_SetPower(); // Set tx_power - XN297L_SetFreqOffset(); // Set frequency offset + XN297_SetPower(); // Set tx_power + XN297_SetFreqOffset(); // Set frequency offset } static void __attribute__((unused)) V911S_RF_init() { - XN297L_Init(); + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_250K); if(sub_protocol==V911S_STD) - XN297L_SetTXAddr((uint8_t *)"KNBND",5); // V911S Bind address + XN297_SetTXAddr((uint8_t *)"KNBND",5); // V911S Bind address else - XN297L_SetTXAddr((uint8_t *)"XPBND",5); // E119 Bind address - XN297L_HoppingCalib(V911S_NUM_RF_CHANNELS); // Calibrate all channels - XN297L_RFChannel(V911S_RF_BIND_CHANNEL); // Set bind channel + XN297_SetTXAddr((uint8_t *)"XPBND",5); // E119 Bind address + XN297_HoppingCalib(V911S_NUM_RF_CHANNELS); // Calibrate all channels + XN297_RFChannel(V911S_RF_BIND_CHANNEL); // Set bind channel } static void __attribute__((unused)) V911S_initialize_txid() @@ -144,7 +144,7 @@ uint16_t V911S_callback() if (bind_counter == 0) { BIND_DONE; - XN297L_SetTXAddr(rx_tx_addr, 5); + XN297_SetTXAddr(rx_tx_addr, 5); packet_period=V911S_PACKET_PERIOD; } else if(bind_counter==100) // same as original TX... @@ -193,7 +193,7 @@ void V911S_init(void) } else { - XN297L_SetTXAddr(rx_tx_addr, 5); + XN297_SetTXAddr(rx_tx_addr, 5); packet_period= V911S_PACKET_PERIOD; } hopping_frequency_no=0; diff --git a/Multiprotocol/Validate.h b/Multiprotocol/Validate.h index dba0e2f..34f13c4 100644 --- a/Multiprotocol/Validate.h +++ b/Multiprotocol/Validate.h @@ -276,7 +276,6 @@ #undef FRSKY_RX_CC2500_INO #undef HITEC_CC2500_INO #undef HOTT_CC2500_INO - #undef OMP_CC2500_INO //CC2500 for control and NRF for telemetry #undef REDPINE_CC2500_INO #undef RLINK_CC2500_INO #undef SCANNER_CC2500_INO @@ -293,6 +292,7 @@ #undef CG023_NRF24L01_INO #undef CX10_NRF24L01_INO #undef DM002_NRF24L01_INO + #undef E016H_NRF24L01_INO #undef E01X_NRF24L01_INO #undef ESKY_NRF24L01_INO #undef ESKY150_NRF24L01_INO @@ -306,28 +306,29 @@ #undef JJRC345_NRF24L01_INO #undef KN_NRF24L01_INO #undef LOLI_NRF24L01_INO - #undef MJXQ_NRF24L01_INO - #undef MT99XX_NRF24L01_INO #undef NCC1701_NRF24L01_INO #undef POTENSIC_NRF24L01_INO #undef PROPEL_NRF24L01_INO - #undef Q303_NRF24L01_INO #undef REALACC_NRF24L01_INO #undef SHENQI_NRF24L01_INO #undef SYMAX_NRF24L01_INO #undef TIGER_NRF24L01_INO #undef V2X2_NRF24L01_INO #undef V761_NRF24L01_INO - #undef XK_NRF24L01_INO #undef YD717_NRF24L01_INO #undef ZSX_NRF24L01_INO #endif #if not defined(CC2500_INSTALLED) && not defined(NRF24L01_INSTALLED) #undef GD00X_CCNRF_INO #undef KF606_CCNRF_INO + #undef MJXQ_CCNRF_INO + #undef MT99XX_CCNRF_INO + #undef OMP_CCNRF_INO + #undef Q303_CCNRF_INO #undef Q90C_CCNRF_INO #undef SLT_CCNRF_INO #undef V911S_CCNRF_INO + #undef XK_CCNRF_INO #endif #if not defined(STM32_BOARD) #undef SX1276_INSTALLED @@ -401,7 +402,7 @@ #if not defined(DEVO_CYRF6936_INO) #undef DEVO_HUB_TELEMETRY #endif - #if not defined(OMP_CC2500_INO) + #if not defined(OMP_CCNRF_INO) #undef OMP_HUB_TELEMETRY #endif #if not defined(PROPEL_NRF24L01_INO) diff --git a/Multiprotocol/XK_nrf24l01.ino b/Multiprotocol/XK_ccnrf.ino similarity index 83% rename from Multiprotocol/XK_nrf24l01.ino rename to Multiprotocol/XK_ccnrf.ino index fd4a8e8..0f44035 100644 --- a/Multiprotocol/XK_nrf24l01.ino +++ b/Multiprotocol/XK_ccnrf.ino @@ -14,7 +14,7 @@ Multiprotocol is distributed in the hope that it will be useful, */ // Compatible with X450 and X420/X520 plane. -#if defined(XK_NRF24L01_INO) +#if defined(XK_CCNRF_INO) #include "iface_nrf250k.h" @@ -56,6 +56,13 @@ static uint16_t __attribute__((unused)) XK_convert_channel(uint8_t num) static void __attribute__((unused)) XK_send_packet() { + // RF channel + XN297_Hopping((IS_BIND_IN_PROGRESS?0:XK_RF_BIND_NUM_CHANNELS)+(hopping_frequency_no>>1)); + hopping_frequency_no++; + if(hopping_frequency_no >= (IS_BIND_IN_PROGRESS?XK_RF_BIND_NUM_CHANNELS*2:XK_RF_NUM_CHANNELS*2)) + hopping_frequency_no=0; + + // Build packet memset(packet,0x00,7); memset(&packet[10],0x00,5); @@ -101,32 +108,16 @@ static void __attribute__((unused)) XK_send_packet() crc+=packet[i]; packet[15]=crc; - rf_ch_num = (IS_BIND_IN_PROGRESS?0:XK_RF_BIND_NUM_CHANNELS)+(hopping_frequency_no>>1); - hopping_frequency_no++; - if(hopping_frequency_no >= (IS_BIND_IN_PROGRESS?XK_RF_BIND_NUM_CHANNELS*2:XK_RF_NUM_CHANNELS*2)) - hopping_frequency_no=0; - // debug("C: %02X, P:",hopping_frequency[rf_ch_num]); // for(uint8_t i=0; iSR & TIMER_SR_UIF) {//timer just rolled over... @@ -412,29 +411,20 @@ static uint16_t XN297Dump_callback() timeL=0; } time=(timeH<<16)+timeL; - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); // Clear data ready, data sent, and retransmit - NRF24L01_SetTxRxMode(TXRX_OFF); - NRF24L01_SetTxRxMode(RX_EN); - NRF24L01_FlushRx(); - NRF24L01_WriteReg(NRF24L01_00_CONFIG, (0 << NRF24L01_00_EN_CRC) // switch to RX mode and disable CRC - | (1 << NRF24L01_00_CRCO) - | (1 << NRF24L01_00_PWR_UP) - | (1 << NRF24L01_00_PRIM_RX)); + XN297_SetTxRxMode(TXRX_OFF); + XN297_SetTxRxMode(RX_EN); XN297Dump_overflow(); break; } debug(",%d",hopping_frequency_no); - NRF24L01_WriteReg(NRF24L01_05_RF_CH,hopping_frequency_no); + XN297_RFChannel(hopping_frequency_no); // switch to RX mode - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); // Clear data ready, data sent, and retransmit - NRF24L01_SetTxRxMode(TXRX_OFF); - NRF24L01_SetTxRxMode(RX_EN); - NRF24L01_FlushRx(); - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP) | _BV(NRF24L01_00_PRIM_RX)); + XN297_SetTxRxMode(TXRX_OFF); + XN297_SetTxRxMode(RX_EN); } - if( NRF24L01_ReadReg(NRF24L01_07_STATUS) & _BV(NRF24L01_07_RX_DR)) + if( XN297_IsRX() ) { // RX fifo data ready - if(NRF24L01_ReadReg(NRF24L01_09_CD)) + // if(NRF24L01_ReadReg(NRF24L01_09_CD)) { boolean res; if(enhanced) @@ -471,11 +461,8 @@ static uint16_t XN297Dump_callback() } } // restart RX mode - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); // Clear data ready, data sent, and retransmit - NRF24L01_SetTxRxMode(TXRX_OFF); - NRF24L01_SetTxRxMode(RX_EN); - NRF24L01_FlushRx(); - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP) | _BV(NRF24L01_00_PRIM_RX)); + XN297_SetTxRxMode(TXRX_OFF); + XN297_SetTxRxMode(RX_EN); } XN297Dump_overflow(); break; @@ -518,7 +505,7 @@ static uint16_t XN297Dump_callback() } debugln("Time between CH:%d and CH:%d",hopping_frequency[0],hopping_frequency[hopping_frequency_no]); time_rf[hopping_frequency_no]=-1; - NRF24L01_WriteReg(NRF24L01_05_RF_CH,hopping_frequency[0]); + XN297_RFChannel(hopping_frequency[0]); uint16_t timeL=TCNT1; if(TIMER2_BASE->SR & TIMER_SR_UIF) {//timer just rolled over... @@ -527,15 +514,12 @@ static uint16_t XN297Dump_callback() } time=(timeH<<16)+timeL; // switch to RX mode - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); // Clear data ready, data sent, and retransmit - NRF24L01_SetTxRxMode(TXRX_OFF); - NRF24L01_SetTxRxMode(RX_EN); - NRF24L01_FlushRx(); - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP) | _BV(NRF24L01_00_PRIM_RX)); + XN297_SetTxRxMode(TXRX_OFF); + XN297_SetTxRxMode(RX_EN); } - if( NRF24L01_ReadReg(NRF24L01_07_STATUS) & _BV(NRF24L01_07_RX_DR)) + if( XN297_IsRX() ) { // RX fifo data ready - if(NRF24L01_ReadReg(NRF24L01_09_CD)) + //if(NRF24L01_ReadReg(NRF24L01_09_CD)) { boolean res; if(enhanced) @@ -557,12 +541,12 @@ static uint16_t XN297Dump_callback() if(time_rf[hopping_frequency_no] > (time>>1)) time_rf[hopping_frequency_no]=time>>1; debugln("Time: %5luus", time>>1); - NRF24L01_WriteReg(NRF24L01_05_RF_CH,hopping_frequency[0]); + XN297_RFChannel(hopping_frequency[0]); } else { time=(timeH<<16)+timeL; - NRF24L01_WriteReg(NRF24L01_05_RF_CH,hopping_frequency[hopping_frequency_no]); + XN297_RFChannel(hopping_frequency[hopping_frequency_no]); } packet_count++; if(packet_count>24) @@ -573,18 +557,15 @@ static uint16_t XN297Dump_callback() } } // restart RX mode - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); // Clear data ready, data sent, and retransmit - NRF24L01_SetTxRxMode(TXRX_OFF); - NRF24L01_SetTxRxMode(RX_EN); - NRF24L01_FlushRx(); - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP) | _BV(NRF24L01_00_PRIM_RX)); + XN297_SetTxRxMode(TXRX_OFF); + XN297_SetTxRxMode(RX_EN); } XN297Dump_overflow(); break; case 4: - if( NRF24L01_ReadReg(NRF24L01_07_STATUS) & _BV(NRF24L01_07_RX_DR)) + if( XN297_IsRX() ) { // RX fifo data ready - if(NRF24L01_ReadReg(NRF24L01_09_CD)) + //if(NRF24L01_ReadReg(NRF24L01_09_CD)) { boolean res; if(enhanced) @@ -604,11 +585,8 @@ static uint16_t XN297Dump_callback() } } // restart RX mode - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); // Clear data ready, data sent, and retransmit - NRF24L01_SetTxRxMode(TXRX_OFF); - NRF24L01_SetTxRxMode(RX_EN); - NRF24L01_FlushRx(); - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP) | _BV(NRF24L01_00_PRIM_RX)); + XN297_SetTxRxMode(TXRX_OFF); + XN297_SetTxRxMode(RX_EN); } break; } @@ -618,10 +596,10 @@ static uint16_t XN297Dump_callback() if(phase==0) { address_length=4; - memcpy(rx_tx_addr, (uint8_t *)"\x5A\x20\x12\xAC", address_length); //"\xA3\x05\x22\xC1" - bitrate=XN297DUMP_1M; + memcpy(rx_tx_addr, (uint8_t *)"\x5A\xF6\xC1\x71", address_length); //"\xA3\x05\x22\xC1""\x5A\x20\x12\xAC" + bitrate=XN297DUMP_250K; packet_length=32; - hopping_frequency_no=60; //bind ?, normal 60 + hopping_frequency_no=58; //bind ?, normal 60 NRF24L01_Initialize(); NRF24L01_SetTxRxMode(TXRX_OFF); @@ -658,12 +636,18 @@ static uint16_t XN297Dump_callback() if(NRF24L01_ReadReg(NRF24L01_09_CD)) { NRF24L01_ReadPayload(packet, packet_length); - bool ok=true; + //bool ok=true; uint8_t buffer[40]; memcpy(buffer,packet,packet_length); if(memcmp(&packet_in[0],&packet[0],packet_length)) { - //realign bits + debug("P:"); + for(uint8_t i=0;i 5) len = 5; - if (len < 3) len = 3; - uint8_t buf[] = { 0x55, 0x0F, 0x71, 0x0C, 0x00 }; // bytes for XN297 preamble 0xC710F55 (28 bit) - xn297_addr_len = len; - if (xn297_addr_len < 4) - for (uint8_t i = 0; i < 4; ++i) - buf[i] = buf[i+1]; - NRF24L01_WriteReg(NRF24L01_03_SETUP_AW, len-2); - NRF24L01_WriteRegisterMulti(NRF24L01_10_TX_ADDR, buf, 5); - // Receive address is complicated. We need to use scrambled actual address as a receive address - // but the TX code now assumes fixed 4-byte transmit address for preamble. We need to adjust it - // first. Also, if the scrambled address begins with 1 nRF24 will look for preamble byte 0xAA - // instead of 0x55 to ensure enough 0-1 transitions to tune the receiver. Still need to experiment - // with receiving signals. - memcpy(xn297_tx_addr, addr, len); + xn297_crc = crc_en; + xn297_scramble_enabled = scramble_en; + xn297_bitrate = bitrate; + xn297_rf = XN297_NRF; + + #if defined(NRF24L01_INSTALLED) and defined(CC2500_INSTALLED) + if(bitrate == XN297_1M) + xn297_rf = XN297_NRF; // Use NRF24L01 + else + xn297_rf = XN297_CC2500; // Use CC2500 + #elif defined(NRF24L01_INSTALLED) and not defined(CC2500_INSTALLED) + xn297_rf = XN297_NRF; // Use NRF24L01 + #else //CC2500 only + xn297_rf = XN297_CC2500; // Use CC2500 + if(bitrate == XN297_1M) + { + xn297_rf = XN297_NRF; // Use NRF24L01 which does not exist, nothing will happen... + SUB_PROTO_INVALID; + return false; // Can't do... + } + #endif + + #if defined(NRF24L01_INSTALLED) + if(xn297_rf == XN297_NRF) + { + debugln("Using NRF"); + rf_switch(SW_NRF); + NRF24L01_Initialize(); + if(bitrate == XN297_250K) + NRF24L01_SetBitrate(NRF24L01_BR_250K); // 250Kbps + } + #endif + #if defined(CC2500_INSTALLED) + if(xn297_rf == XN297_CC2500) + { + debugln("Using CC2500"); + rf_switch(SW_CC2500); + CC2500_250K_Init(); + option_override = 2; // OPTION_RFTUNE + } + #endif + return true; } -void XN297_SetRXAddr(const uint8_t* addr, uint8_t len) +static void __attribute__((unused)) XN297_SetTXAddr(const uint8_t* addr, uint8_t len) { if (len > 5) len = 5; if (len < 3) len = 3; - uint8_t buf[] = { 0, 0, 0, 0, 0 }; - memcpy(buf, addr, len); - memcpy(xn297_rx_addr, addr, len); + xn297_addr_len = len; + memcpy(xn297_tx_addr, addr, len); + #ifdef NRF24L01_INSTALLED + if(xn297_rf == XN297_NRF) + { + uint8_t buf[] = { 0x55, 0x0F, 0x71, 0x0C, 0x00 }; // bytes for XN297 preamble 0xC710F55 (28 bit) + NRF24L01_WriteReg(NRF24L01_03_SETUP_AW, len-2); + NRF24L01_WriteRegisterMulti(NRF24L01_10_TX_ADDR, xn297_addr_len == 3 ? buf+1 : buf, 5); + } + #endif +}; + +static void __attribute__((unused)) XN297_SetRXAddr(const uint8_t* addr, uint8_t rx_packet_len) +{ + //Scramble address for (uint8_t i = 0; i < xn297_addr_len; ++i) { - buf[i] = xn297_rx_addr[i]; + xn297_rx_addr[i] = addr[i]; if(xn297_scramble_enabled) - buf[i] ^= xn297_scramble[xn297_addr_len-i-1]; + xn297_rx_addr[i] ^= xn297_scramble[xn297_addr_len-i-1]; } - NRF24L01_WriteReg(NRF24L01_03_SETUP_AW, len-2); - NRF24L01_WriteRegisterMulti(NRF24L01_0A_RX_ADDR_P0, buf, 5); + + if(xn297_crc) + rx_packet_len += 2; // Include CRC + rx_packet_len += 2; // Include pcf, will this be a problem timing wise even if not enhanced? + + #ifdef NRF24L01_INSTALLED + if(xn297_rf == XN297_NRF) + { + NRF24L01_WriteRegisterMulti(NRF24L01_0A_RX_ADDR_P0, xn297_rx_addr, xn297_addr_len); + if(rx_packet_len >= 32) + NRF24L01_WriteReg(NRF24L01_11_RX_PW_P0, 32); + else + NRF24L01_WriteReg(NRF24L01_11_RX_PW_P0, rx_packet_len); + } + #endif + #ifdef CC2500_INSTALLED + if(xn297_rf == XN297_CC2500) + {// TX: Sync1, Sync0, Address + CC2500_WriteReg(CC2500_04_SYNC1, xn297_rx_addr[xn297_addr_len-1]); // Sync word, high byte + CC2500_WriteReg(CC2500_05_SYNC0, xn297_rx_addr[xn297_addr_len-2]); // Sync word, low byte + CC2500_WriteReg(CC2500_09_ADDR, xn297_rx_addr[xn297_addr_len-3]); // Address + rx_packet_len += 1 + xn297_addr_len - 3; // The Address field above will be in the payload then the end of the XN297 address + } + #endif + xn297_rx_packet_len = rx_packet_len; } -void XN297_Configure(uint8_t flags) +static void __attribute__((unused)) XN297_SetTxRxMode(enum TXRX_State mode) { - xn297_crc = !!(flags & _BV(NRF24L01_00_EN_CRC)); - flags &= ~(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO)); - NRF24L01_WriteReg(NRF24L01_00_CONFIG, flags & 0xFF); + static enum TXRX_State cur_mode=TXRX_OFF; + #ifdef NRF24L01_INSTALLED + if(xn297_rf == XN297_NRF) + { + + NRF24L01_WriteReg(NRF24L01_07_STATUS, (1 << NRF24L01_07_RX_DR) //reset the flag(s) + | (1 << NRF24L01_07_TX_DS) + | (1 << NRF24L01_07_MAX_RT)); + if(mode==TXRX_OFF) + { + NRF24L01_WriteReg(NRF24L01_00_CONFIG, 0); //PowerDown + NRF_CE_off; + return; + } + NRF_CE_off; + if(mode == TX_EN) + { + NRF24L01_FlushTx(); + NRF24L01_WriteReg(NRF24L01_00_CONFIG, 1 << NRF24L01_00_PWR_UP); + } + else + { + NRF24L01_FlushRx(); + NRF24L01_WriteReg(NRF24L01_00_CONFIG, (1 << NRF24L01_00_PWR_UP) + | (1 << NRF24L01_00_PRIM_RX)); // RX + } + if(mode != cur_mode) + { + //delayMicroseconds(130); + cur_mode=mode; + } + NRF_CE_on; + } + #endif + #ifdef CC2500_INSTALLED + if(xn297_rf == XN297_CC2500) + { + if(mode != cur_mode) + { + CC2500_SetTxRxMode(mode); + if(mode == RX_EN) + { + CC2500_WriteReg(CC2500_12_MDMCFG2, 0x12); // Modem Configuration, GFSK, 16/16 Sync Word TX&RX + CC2500_WriteReg(CC2500_06_PKTLEN, xn297_rx_packet_len); // Packet len + CC2500_Strobe(CC2500_SFRX); + CC2500_Strobe(CC2500_SRX); + } + else + CC2500_WriteReg(CC2500_12_MDMCFG2, 0x10); // Modem Configuration, GFSK, no preambule and no sync word + cur_mode=mode; + } + } + #endif } -void XN297_SetScrambledMode(const uint8_t mode) +static void __attribute__((unused)) XN297_SendPayload(uint8_t* msg, uint8_t len) { - xn297_scramble_enabled = mode; + #ifdef NRF24L01_INSTALLED + if(xn297_rf == XN297_NRF) + { + NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); + NRF24L01_FlushTx(); + NRF24L01_WritePayload(msg, len); + } + #endif + #ifdef CC2500_INSTALLED + if(xn297_rf == XN297_CC2500) + { + // stop TX/RX + CC2500_Strobe(CC2500_SIDLE); + // flush tx FIFO + CC2500_Strobe(CC2500_SFTX); + // packet length + CC2500_WriteReg(CC2500_06_PKTLEN, len + 4); // Packet len, fix packet len + // xn297L preamble + CC2500_WriteRegisterMulti(CC2500_3F_TXFIFO, (uint8_t*)"\x0C\x71\x0F\x55", 4); + // xn297 packet + CC2500_WriteRegisterMulti(CC2500_3F_TXFIFO, msg, len); + // transmit + CC2500_Strobe(CC2500_STX); + } + #endif } -void XN297_WritePayload(uint8_t* msg, uint8_t len) +static void __attribute__((unused)) XN297_WritePayload(uint8_t* msg, uint8_t len) { uint8_t buf[32]; uint8_t last = 0; - if (xn297_addr_len < 4) - { - // If address length (which is defined by receive address length) - // is less than 4 the TX address can't fit the preamble, so the last - // byte goes here + if (xn297_rf == XN297_NRF && xn297_addr_len < 4) + { // If address length (which is defined by receiver address length) is less than 4 the TX address can't fit the preamble, so the last byte goes here buf[last++] = 0x55; } + + // address for (uint8_t i = 0; i < xn297_addr_len; ++i) { buf[last] = xn297_tx_addr[xn297_addr_len-i-1]; @@ -72,6 +255,8 @@ void XN297_WritePayload(uint8_t* msg, uint8_t len) buf[last] ^= xn297_scramble[i]; last++; } + + // payload for (uint8_t i = 0; i < len; ++i) { // bit-reverse bytes in packet @@ -80,6 +265,8 @@ void XN297_WritePayload(uint8_t* msg, uint8_t len) buf[last] ^= xn297_scramble[xn297_addr_len+i]; last++; } + + // crc if (xn297_crc) { uint8_t offset = xn297_addr_len < 4 ? 1 : 0; @@ -93,56 +280,56 @@ void XN297_WritePayload(uint8_t* msg, uint8_t len) buf[last++] = crc >> 8; buf[last++] = crc & 0xff; } - NRF24L01_WritePayload(buf, last); + + // send packet + XN297_SendPayload(buf, last); } -void XN297_WriteEnhancedPayload(uint8_t* msg, uint8_t len, uint8_t noack) +static void __attribute__((unused)) XN297_WriteEnhancedPayload(uint8_t* msg, uint8_t len, uint8_t noack) { - uint8_t packet[32]; + uint8_t buf[32]; uint8_t scramble_index=0; uint8_t last = 0; static uint8_t pid=0; - // address - if (xn297_addr_len < 4) - { - // If address length (which is defined by receive address length) - // is less than 4 the TX address can't fit the preamble, so the last - // byte goes here - packet[last++] = 0x55; + if (xn297_rf == XN297_NRF && xn297_addr_len < 4) + { // If address length (which is defined by receiver address length) is less than 4 the TX address can't fit the preamble, so the last byte goes here + buf[last++] = 0x55; } + + // address for (uint8_t i = 0; i < xn297_addr_len; ++i) { - packet[last] = xn297_tx_addr[xn297_addr_len-i-1]; + buf[last] = xn297_tx_addr[xn297_addr_len-i-1]; if(xn297_scramble_enabled) - packet[last] ^= xn297_scramble[scramble_index++]; + buf[last] ^= xn297_scramble[scramble_index++]; last++; } // pcf - packet[last] = (len << 1) | (pid>>1); + buf[last] = (len << 1) | (pid>>1); if(xn297_scramble_enabled) - packet[last] ^= xn297_scramble[scramble_index++]; + buf[last] ^= xn297_scramble[scramble_index++]; last++; - packet[last] = (pid << 7) | (noack << 6); + buf[last] = (pid << 7) | (noack << 6); // payload - packet[last]|= bit_reverse(msg[0]) >> 2; // first 6 bit of payload + buf[last]|= bit_reverse(msg[0]) >> 2; // first 6 bit of payload if(xn297_scramble_enabled) - packet[last] ^= xn297_scramble[scramble_index++]; + buf[last] ^= xn297_scramble[scramble_index++]; for (uint8_t i = 0; i < len-1; ++i) { last++; - packet[last] = (bit_reverse(msg[i]) << 6) | (bit_reverse(msg[i+1]) >> 2); + buf[last] = (bit_reverse(msg[i]) << 6) | (bit_reverse(msg[i+1]) >> 2); if(xn297_scramble_enabled) - packet[last] ^= xn297_scramble[scramble_index++]; + buf[last] ^= xn297_scramble[scramble_index++]; } last++; - packet[last] = bit_reverse(msg[len-1]) << 6; // last 2 bit of payload + buf[last] = bit_reverse(msg[len-1]) << 6; // last 2 bit of payload if(xn297_scramble_enabled) - packet[last] ^= xn297_scramble[scramble_index++] & 0xc0; + buf[last] ^= xn297_scramble[scramble_index++] & 0xc0; // crc if (xn297_crc) @@ -150,31 +337,69 @@ void XN297_WriteEnhancedPayload(uint8_t* msg, uint8_t len, uint8_t noack) uint8_t offset = xn297_addr_len < 4 ? 1 : 0; crc = 0xb5d2; for (uint8_t i = offset; i < last; ++i) - crc16_update( packet[i], 8); - crc16_update( packet[last] & 0xc0, 2); + crc16_update( buf[i], 8); + crc16_update( buf[last] & 0xc0, 2); if (xn297_scramble_enabled) crc ^= pgm_read_word(&xn297_crc_xorout_scrambled_enhanced[xn297_addr_len-3+len]); //else // crc ^= pgm_read_word(&xn297_crc_xorout_enhanced[xn297_addr_len - 3 + len]); - packet[last++] |= (crc >> 8) >> 2; - packet[last++] = ((crc >> 8) << 6) | ((crc & 0xff) >> 2); - packet[last++] = (crc & 0xff) << 6; + buf[last++] |= (crc >> 8) >> 2; + buf[last++] = ((crc >> 8) << 6) | ((crc & 0xff) >> 2); + buf[last++] = (crc & 0xff) << 6; } - NRF24L01_WritePayload(packet, last); - pid++; if(pid>3) pid=0; + + // send packet + XN297_SendPayload(buf, last); } -boolean XN297_ReadPayload(uint8_t* msg, uint8_t len) -{ //!!! Don't forget if using CRC to do a +2 on any of the used NRF24L01_11_RX_PW_Px !!! - uint8_t buf[32]; +static bool __attribute__((unused)) XN297_IsRX() +{ + #ifdef NRF24L01_INSTALLED + if(xn297_rf == XN297_NRF) + return (NRF24L01_ReadReg(NRF24L01_07_STATUS) & _BV(NRF24L01_07_RX_DR)); + #endif + #ifdef CC2500_INSTALLED + if(xn297_rf == XN297_CC2500) + { + if((CC2500_ReadReg(CC2500_3B_RXBYTES | CC2500_READ_BURST) & 0x7F) != xn297_rx_packet_len + 2) // 2 = RSSI + LQI + return false; // Buffer does not contain the expected number of bytes + // Check the address + uint8_t buf[3]; + CC2500_ReadData(buf, xn297_addr_len-3 + 1); + for(uint8_t i=0; i < xn297_addr_len-3 + 1; i++) + if(buf[i] != xn297_rx_addr[xn297_addr_len-3 - i]) + return false; // Bad address + return true; // Address is correct + } + #endif + return false; +} + +static void __attribute__((unused)) XN297_ReceivePayload(uint8_t* msg, uint8_t len) +{ if (xn297_crc) - NRF24L01_ReadPayload(buf, len+2); // Read payload + CRC - else - NRF24L01_ReadPayload(buf, len); + len += 2; // Include CRC + #ifdef NRF24L01_INSTALLED + if(xn297_rf == XN297_NRF) + NRF24L01_ReadPayload(msg, len); // Read payload and CRC + #endif + #ifdef CC2500_INSTALLED + if(xn297_rf == XN297_CC2500) + CC2500_ReadData(msg, len); + #endif +} + +static bool __attribute__((unused)) XN297_ReadPayload(uint8_t* msg, uint8_t len) +{ //!!! Don't forget if using CRC to do a +2 on the received packet length (NRF24L01_11_RX_PW_Px !!! or CC2500_06_PKTLEN) + uint8_t buf[32]; + + // Read payload + XN297_ReceivePayload(buf, len); + // Decode payload for(uint8_t i=0; i>6) ; if( crc == crcxored) - return pcf_size; // CRC OK - return 0; // CRC NOK + return pcf_size; // CRC OK + return 0; // CRC NOK } +static bool __attribute__((unused)) XN297_IsPacketSent() +{ + #ifdef NRF24L01_INSTALLED + if(xn297_rf == XN297_NRF) + return (NRF24L01_ReadReg(NRF24L01_07_STATUS) & _BV(NRF24L01_07_TX_DS)); + #endif + #ifdef CC2500_INSTALLED + if(xn297_rf == XN297_CC2500) + return (CC2500_ReadReg(CC2500_35_MARCSTATE | CC2500_READ_BURST) != 0x13); + #endif + return true; // packet sent to not block +} + +static void __attribute__((unused)) XN297_HoppingCalib(uint8_t num_freq) +{ //calibrate hopping frequencies + #ifdef NRF24L01_INSTALLED + (void)num_freq; + #endif + #ifdef CC2500_INSTALLED + if(xn297_rf == XN297_CC2500) + CC2500_250K_HoppingCalib(num_freq); + #endif +} + +static void __attribute__((unused)) XN297_Hopping(uint8_t index) +{ + #ifdef NRF24L01_INSTALLED + if(xn297_rf == XN297_NRF) + NRF24L01_WriteReg(NRF24L01_05_RF_CH, hopping_frequency[index]); + #endif + #ifdef CC2500_INSTALLED + if(xn297_rf == XN297_CC2500) + CC2500_250K_Hopping(index); + #endif +} + +static void __attribute__((unused)) XN297_RFChannel(uint8_t number) +{ //change channel + #ifdef NRF24L01_INSTALLED + if(xn297_rf == XN297_NRF) + NRF24L01_WriteReg(NRF24L01_05_RF_CH, number); + #endif + #ifdef CC2500_INSTALLED + if(xn297_rf == XN297_CC2500) + CC2500_250K_RFChannel(number); + #endif +} + +static void __attribute__((unused)) XN297_SetPower() +{ + #ifdef NRF24L01_INSTALLED + if(xn297_rf == XN297_NRF) + NRF24L01_SetPower(); + #endif + #ifdef CC2500_INSTALLED + if(xn297_rf == XN297_CC2500) + CC2500_SetPower(); + #endif +} + +static void __attribute__((unused)) XN297_SetFreqOffset() +{ // Frequency offset + #ifdef CC2500_INSTALLED + if(xn297_rf == XN297_CC2500) + CC2500_SetFreqOffset(); + #endif +} + // End of XN297 emulation #endif diff --git a/Multiprotocol/ZSX_nrf24l01.ino b/Multiprotocol/ZSX_nrf24l01.ino index f36a225..2e7fcd8 100644 --- a/Multiprotocol/ZSX_nrf24l01.ino +++ b/Multiprotocol/ZSX_nrf24l01.ino @@ -44,12 +44,10 @@ static void __attribute__((unused)) ZSX_send_packet() | GET_FLAG(CH5_SW, 0x80); // Light } - XN297_Configure(_BV(NRF24L01_00_EN_CRC) | _BV(NRF24L01_00_CRCO) | _BV(NRF24L01_00_PWR_UP)); - NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70); - NRF24L01_FlushTx(); + // Send + XN297_SetPower(); + XN297_SetTxRxMode(TX_EN); XN297_WritePayload(packet, ZSX_PAYLOAD_SIZE); - - NRF24L01_SetPower(); // Set tx_power } static void __attribute__((unused)) ZSX_initialize_txid() @@ -65,10 +63,9 @@ static void __attribute__((unused)) ZSX_initialize_txid() static void __attribute__((unused)) ZSX_RF_init() { - NRF24L01_Initialize(); - + XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_1M); XN297_SetTXAddr((uint8_t*)"\xc1\xc2\xc3", 3); - NRF24L01_WriteReg(NRF24L01_05_RF_CH, ZSX_RF_BIND_CHANNEL); // Set bind channel + XN297_RFChannel(ZSX_RF_BIND_CHANNEL); // Set bind channel } uint16_t ZSX_callback() @@ -81,7 +78,7 @@ uint16_t ZSX_callback() { BIND_DONE; XN297_SetTXAddr(rx_tx_addr, 3); - NRF24L01_WriteReg(NRF24L01_05_RF_CH, 0x00); + XN297_RFChannel(0x00); } ZSX_send_packet(); return ZSX_PACKET_PERIOD; diff --git a/Multiprotocol/_Config.h b/Multiprotocol/_Config.h index 3d9245b..49a5b13 100644 --- a/Multiprotocol/_Config.h +++ b/Multiprotocol/_Config.h @@ -203,7 +203,6 @@ #define FRSKY_RX_CC2500_INO #define HITEC_CC2500_INO #define HOTT_CC2500_INO -#define OMP_CC2500_INO //CC2500 for control and NRF for telemetry #define SCANNER_CC2500_INO #define FUTABA_CC2500_INO #define SKYARTEC_CC2500_INO @@ -220,6 +219,7 @@ #define CG023_NRF24L01_INO #define CX10_NRF24L01_INO //Include Q2X2 protocol #define DM002_NRF24L01_INO +#define E016H_NRF24L01_INO #define E01X_NRF24L01_INO #define ESKY_NRF24L01_INO #define ESKY150_NRF24L01_INO @@ -233,28 +233,29 @@ #define JJRC345_NRF24L01_INO #define KN_NRF24L01_INO #define LOLI_NRF24L01_INO -#define MJXQ_NRF24L01_INO -#define MT99XX_NRF24L01_INO #define NCC1701_NRF24L01_INO #define POTENSIC_NRF24L01_INO #define PROPEL_NRF24L01_INO -#define Q303_NRF24L01_INO #define REALACC_NRF24L01_INO #define SHENQI_NRF24L01_INO #define SYMAX_NRF24L01_INO #define TIGER_NRF24L01_INO #define V2X2_NRF24L01_INO #define V761_NRF24L01_INO -#define XK_NRF24L01_INO #define YD717_NRF24L01_INO #define ZSX_NRF24L01_INO //The protocols below need either a CC2500 or NRF24L01 to be installed #define GD00X_CCNRF_INO #define KF606_CCNRF_INO +#define MJXQ_CCNRF_INO +#define MT99XX_CCNRF_INO +#define OMP_CCNRF_INO +#define Q303_CCNRF_INO #define Q90C_CCNRF_INO #define SLT_CCNRF_INO #define V911S_CCNRF_INO +#define XK_CCNRF_INO //The protocols below need a SX1276 to be installed #define FRSKYR9_SX1276_INO @@ -592,12 +593,13 @@ const PPM_Parameters PPM_prot[14*NBR_BANKS]= { NONE PROTO_E010R5 NONE + PROTO_E016H + NONE PROTO_E016HV2 NONE PROTO_E01X E012 E015 - E016H PROTO_E129 NONE PROTO_ESKY diff --git a/Multiprotocol/_MyConfig.h.example b/Multiprotocol/_MyConfig.h.example index 105f35c..bc0b07a 100644 --- a/Multiprotocol/_MyConfig.h.example +++ b/Multiprotocol/_MyConfig.h.example @@ -35,7 +35,7 @@ #undef FQ777_NRF24L01_INO #undef ASSAN_NRF24L01_INO #undef HONTAI_NRF24L01_INO - #undef Q303_NRF24L01_INO + #undef Q303_CCNRF_INO #undef GW008_NRF24L01_INO #undef DM002_NRF24L01_INO #undef CABELL_NRF24L01_INO diff --git a/Multiprotocol/iface_nrf250k.h b/Multiprotocol/iface_nrf250k.h index 854e167..15d0f8b 100644 --- a/Multiprotocol/iface_nrf250k.h +++ b/Multiprotocol/iface_nrf250k.h @@ -1,34 +1,28 @@ #ifndef _IFACE_NRF250K_H_ - #define _IFACE_NRF250K_H_ -#if defined (CC2500_INSTALLED) +#ifdef CC2500_INSTALLED #include "iface_cc2500.h" -#elif defined (NRF24L01_INSTALLED) +#endif +#ifdef NRF24L01_INSTALLED #include "iface_nrf24l01.h" #endif #include "iface_xn297.h" -//XN297L -static void __attribute__((unused)) XN297L_Init(); -static void __attribute__((unused)) XN297L_SetTXAddr(const uint8_t*, uint8_t); -static void __attribute__((unused)) XN297L_WritePayload(uint8_t*, uint8_t); -static void __attribute__((unused)) XN297L_WriteEnhancedPayload(uint8_t*, uint8_t, uint8_t); -static void __attribute__((unused)) XN297L_HoppingCalib(__attribute__((unused)) uint8_t); -static void __attribute__((unused)) XN297L_Hopping(uint8_t); -static void __attribute__((unused)) XN297L_RFChannel(uint8_t); -static void __attribute__((unused)) XN297L_SetPower(); -static void __attribute__((unused)) XN297L_SetFreqOffset(); +#if defined (CC2500_INSTALLED) || defined (NRF24L01_INSTALLED) -//NRF250K -#define NRF250K_Init() XN297L_Init() -#define NRF250K_HoppingCalib(X) XN297L_HoppingCalib(X) -#define NRF250K_Hopping(X) XN297L_Hopping(X) -#define NRF250K_RFChannel(X) XN297L_RFChannel(X) -#define NRF250K_SetPower() XN297L_SetPower() -#define NRF250K_SetFreqOffset() XN297L_SetFreqOffset() +////////////// +// Functions +#define NRF250K_Init() XN297_Configure(XN297_CRCEN, XN297_SCRAMBLED, XN297_250K) +#define NRF250K_HoppingCalib(X) XN297_HoppingCalib(X) +#define NRF250K_Hopping(X) XN297_Hopping(X) +#define NRF250K_RFChannel(X) XN297_RFChannel(X) +#define NRF250K_SetPower() XN297_SetPower() +#define NRF250K_SetFreqOffset() XN297_SetFreqOffset() +#define NRF250K_IsPacketSent() XN297_IsPacketSent() static void __attribute__((unused)) NRF250K_SetTXAddr(uint8_t*, uint8_t); static void __attribute__((unused)) NRF250K_WritePayload(uint8_t*, uint8_t); -static boolean __attribute__((unused)) NRF250K_IsPacketSent(); -#endif \ No newline at end of file +#endif + +#endif diff --git a/Multiprotocol/iface_xn297.h b/Multiprotocol/iface_xn297.h index 9cd24ae..bd50122 100644 --- a/Multiprotocol/iface_xn297.h +++ b/Multiprotocol/iface_xn297.h @@ -8,76 +8,39 @@ #include "iface_nrf24l01.h" #endif -/////////////// -// XN297 emulation layer -// XN297 emulation layer -enum { - XN297_UNSCRAMBLED = 0, - XN297_SCRAMBLED -}; +#if defined (CC2500_INSTALLED) || defined (NRF24L01_INSTALLED) -uint8_t xn297_scramble_enabled=XN297_SCRAMBLED; //enabled by default -uint8_t xn297_addr_len; -uint8_t xn297_tx_addr[5]; -uint8_t xn297_rx_addr[5]; -uint8_t xn297_crc = 0; +////////////////// +// Configuration +#define XN297_UNSCRAMBLED false +#define XN297_SCRAMBLED true +#define XN297_CRCDIS false +#define XN297_CRCEN true +#define XN297_1M false +#define XN297_250K true +#define XN297_NRF false +#define XN297_CC2500 true -// xn297 address / pcf / payload scramble table -const uint8_t xn297_scramble[] = { - 0xE3, 0xB1, 0x4B, 0xEA, 0x85, 0xBC, 0xE5, 0x66, - 0x0D, 0xAE, 0x8C, 0x88, 0x12, 0x69, 0xEE, 0x1F, - 0xC7, 0x62, 0x97, 0xD5, 0x0B, 0x79, 0xCA, 0xCC, - 0x1B, 0x5D, 0x19, 0x10, 0x24, 0xD3, 0xDC, 0x3F, - 0x8E, 0xC5, 0x2F, 0xAA, 0x16, 0xF3, 0x95 }; +////////////// +// Functions +static bool __attribute__((unused)) XN297_Configure(bool, bool, bool); +static void __attribute__((unused)) XN297_SetTXAddr(const uint8_t*, uint8_t); +static void __attribute__((unused)) XN297_SetRXAddr(const uint8_t*, uint8_t); +static void __attribute__((unused)) XN297_SetTxRxMode(enum TXRX_State); +static void __attribute__((unused)) XN297_SendPayload(uint8_t*, uint8_t); +static void __attribute__((unused)) XN297_WritePayload(uint8_t*, uint8_t); +static void __attribute__((unused)) XN297_WriteEnhancedPayload(uint8_t*, uint8_t, uint8_t); +static bool __attribute__((unused)) XN297_IsRX(); +static void __attribute__((unused)) XN297_ReceivePayload(uint8_t*, uint8_t); +static bool __attribute__((unused)) XN297_ReadPayload(uint8_t*, uint8_t); +static uint8_t __attribute__((unused)) XN297_ReadEnhancedPayload(uint8_t*, uint8_t); +static void __attribute__((unused)) XN297_HoppingCalib(uint8_t); +static void __attribute__((unused)) XN297_Hopping(uint8_t); +static void __attribute__((unused)) XN297_RFChannel(uint8_t); +static void __attribute__((unused)) XN297_SetPower(); +static void __attribute__((unused)) XN297_SetFreqOffset(); +static bool __attribute__((unused)) XN297_IsPacketSent(); -// scrambled, standard mode crc xorout table -const uint16_t PROGMEM xn297_crc_xorout_scrambled[] = { - 0x0000, 0x3448, 0x9BA7, 0x8BBB, 0x85E1, 0x3E8C, - 0x451E, 0x18E6, 0x6B24, 0xE7AB, 0x3828, 0x814B, - 0xD461, 0xF494, 0x2503, 0x691D, 0xFE8B, 0x9BA7, - 0x8B17, 0x2920, 0x8B5F, 0x61B1, 0xD391, 0x7401, - 0x2138, 0x129F, 0xB3A0, 0x2988, 0x23CA, 0xC0CB, - 0x0C6C, 0xB329, 0xA0A1, 0x0A16, 0xA9D0 }; - -// unscrambled, standard mode crc xorout table -const uint16_t PROGMEM xn297_crc_xorout[] = { - 0x0000, 0x3D5F, 0xA6F1, 0x3A23, 0xAA16, 0x1CAF, - 0x62B2, 0xE0EB, 0x0821, 0xBE07, 0x5F1A, 0xAF15, - 0x4F0A, 0xAD24, 0x5E48, 0xED34, 0x068C, 0xF2C9, - 0x1852, 0xDF36, 0x129D, 0xB17C, 0xD5F5, 0x70D7, - 0xB798, 0x5133, 0x67DB, 0xD94E, 0x0A5B, 0xE445, - 0xE6A5, 0x26E7, 0xBDAB, 0xC379, 0x8E20 }; - -// scrambled enhanced mode crc xorout table -const uint16_t PROGMEM xn297_crc_xorout_scrambled_enhanced[] = { - 0x0000, 0x7EBF, 0x3ECE, 0x07A4, 0xCA52, 0x343B, - 0x53F8, 0x8CD0, 0x9EAC, 0xD0C0, 0x150D, 0x5186, - 0xD251, 0xA46F, 0x8435, 0xFA2E, 0x7EBD, 0x3C7D, - 0x94E0, 0x3D5F, 0xA685, 0x4E47, 0xF045, 0xB483, - 0x7A1F, 0xDEA2, 0x9642, 0xBF4B, 0x032F, 0x01D2, - 0xDC86, 0x92A5, 0x183A, 0xB760, 0xA953 }; - -// unscrambled enhanced mode crc xorout table -// unused so far -#ifdef XN297DUMP_NRF24L01_INO -const uint16_t xn297_crc_xorout_enhanced[] = { - 0x0000, 0x8BE6, 0xD8EC, 0xB87A, 0x42DC, 0xAA89, - 0x83AF, 0x10E4, 0xE83E, 0x5C29, 0xAC76, 0x1C69, - 0xA4B2, 0x5961, 0xB4D3, 0x2A50, 0xCB27, 0x5128, - 0x7CDB, 0x7A14, 0xD5D2, 0x57D7, 0xE31D, 0xCE42, - 0x648D, 0xBF2D, 0x653B, 0x190C, 0x9117, 0x9A97, - 0xABFC, 0xE68E, 0x0DE7, 0x28A2, 0x1965 }; -#endif - -#ifdef NRF24L01_INSTALLED -void XN297_SetTXAddr(const uint8_t*, uint8_t); -void XN297_SetRXAddr(const uint8_t*, uint8_t); -void XN297_Configure(uint8_t); -void XN297_SetScrambledMode(const uint8_t); -void XN297_WritePayload(uint8_t*, uint8_t); -void XN297_WriteEnhancedPayload(uint8_t*, uint8_t, uint8_t); -boolean XN297_ReadPayload(uint8_t*, uint8_t); -uint8_t XN297_ReadEnhancedPayload(uint8_t*, uint8_t); #endif #endif diff --git a/Protocols_Details.md b/Protocols_Details.md index d1d8938..c04535b 100644 --- a/Protocols_Details.md +++ b/Protocols_Details.md @@ -77,8 +77,9 @@ CFlie|38|CFlie||||||||NRF24L01| [DSM](Protocols_Details.md#DSM---6)|6|DSM2_1F|DSM2_2F|DSMX_1F|DSMX_2F|AUTO||||CYRF6936| [DSM_RX](Protocols_Details.md#DSM_RX---70)|70|Multi|CPPM|||||||CYRF6936| [E010R5](Protocols_Details.md#E010R5---81)|81|||||||||CYRF6936/NRF24L01|RF2500 +[E016H](Protocols_Details.md#E016H---85)|85|||||||||NRF24L01|XN297 [E016HV2](Protocols_Details.md#E016HV2---80)|80|||||||||CC2500/NRF24L01|unknown -[E01X](Protocols_Details.md#E01X---45)|45|E012|E015|E016H||||||NRF24L01|XN297/HS6200 +[E01X](Protocols_Details.md#E01X---45)|45|E012|E015|||||||NRF24L01|HS6200 [E129](Protocols_Details.md#E129---83)|83|||||||||CYRF6936/NRF24L01|RF2500 [ESky](Protocols_Details.md#ESKY---16)|16|ESky|ET4|||||||NRF24L01| [ESky150](Protocols_Details.md#ESKY150---35)|35|||||||||NRF24L01| @@ -884,28 +885,6 @@ Recommended for best telemetry performance. Telemetry compatibility mode when Sync does not work due to an old firmware on the RX. You should definitively upgrade your receivers/sensors to the latest firmware versions: https://www.rcgroups.com/forums/showpost.php?p=44668015&postcount=18022 -## OMP - *77* -Model: OMPHOBBY M1 & M2 Helis, T720 RC Glider - -Telemetry is supported only if a NRF24L01 RF component is installed: -- A1 = battery voltage including "recovered" battery voltage from corrupted telemetry packets -- A2 = battery voltage from only good telemetry packets -- How to calculate accurately the OpenTX Ratio and Offset: -Set the Ratio to 12.7 and Offset to 0, plug 2 batteries with extreme voltage values, write down the values Batt1=12.5V & Telem1=12.2V, Batt2=7V & Telem2=6.6V then calculate/set Ratio=12.7*[(12.5-7)/(12.2-6.6)]=12.47 => 12.5 and Offset=12.5-12.2*[(12.5-7)/(12.2-6.6)]=0.517 => 0.5 -- RX_RSSI = TQly = percentage of received telemetry packets (good and corrupted) from the model which has nothing to do with how well the RX is receiving the TX - -Option for this protocol corresponds to the CC2500 fine frequency tuning. This value is different for each Module and **must** be accurate otherwise the link will not be stable. -Check the [Frequency Tuning page](/docs/Frequency_Tuning.md) to determine it. - -CH1|CH2|CH3|CH4|CH5|CH6|CH7 ----|---|---|---|---|---|--- -A|E|T_PITCH|R|T_HOLD|IDLE|MODE - -IDLE= 3 pos switch: -100% Normal, 0% Idle1, +100% Idle2 - -From the TX manual: MODE= 3 pos switch -100% Attitude, 0% Attitude(?), +100% 3D -For M2: MODE= 3 pos switch -100% 6G, 0% 3D, +100% 3D - ## Scanner - *54* 2.4GHz scanner accessible using the OpenTX 2.3 Spectrum Analyser tool. @@ -968,7 +947,7 @@ A|E|T|R|CH5|CH6|CH7 If a CC2500 is installed it will be used for all the below protocols. Option in this case is used for fine frequency tuning like any CC2500 protocols so check the [Frequency Tuning page](/docs/Frequency_Tuning.md). -If only a NRF24L01 is installed then these protocols might be problematic because they are using the xn297L emulation with a transmission speed of 250kbps which doesn't work very well with every NRF24L01, this is an hardware issue with the authenticity and accuracy of the components. +If only a NRF24L01 is installed then these protocols might be problematic because they are using the XN297L emulation with a transmission speed of 250kbps which doesn't work very well with every NRF24L01, this is an hardware issue with the authenticity and accuracy of the components. ## GD00X - *47* Model: GD005 C-17 Transport, GD006 DA62 and ZC-Z50 @@ -994,6 +973,176 @@ CH1|CH2|CH3|CH4|CH5 ---|---|---|---|--- A||T||TRIM +## MJXQ - *18* +Autobind protocol + +CH1|CH2|CH3|CH4|CH5|CH6|CH7|CH8|CH9|CH10|CH11|CH12|CH13|CH14 +---|---|---|---|---|---|---|---|---|----|----|----|----|---- +A|E|T|R|FLIP|LED|PICTURE|VIDEO|HEADLESS|RTH|AUTOFLIP|PAN|TILT|RATE + +RATE: -100%(default)=>higher rates by enabling dynamic trims (except for Headless), 100%=>disable dynamic trims + +CC2500: only E010 and PHOENIX are supported. + +### Sub_protocol WLH08 - *0* + +### Sub_protocol X600 - *1* +Only 3 TX IDs available, change RX_Num value 0..2 to cycle through them +### Sub_protocol X800 - *2* +Only 3 TX IDs available, change RX_Num value 0..2 to cycle through them +### Sub_protocol H26D - *3* +Only 3 TX IDs available, change RX_Num value 0..2 to cycle through them +### Sub_protocol E010 - *4* +15 TX IDs available, change RX_Num value 0..14 to cycle through them + +If a CC2500 is installed it will be used for this sub protocol. Option in this case is used for fine frequency tuning like any CC2500 protocols so check the [Frequency Tuning page](/docs/Frequency_Tuning.md). + +If only a NRF24L01 is installed then this sub protocol might be problematic because it is using the xn297L emulation with a transmission speed of 250kbps which doesn't work very well with every NRF24L01, this is an hardware issue with the authenticity and accuracy of the components. + +### Sub_protocol H26WH - *5* +CH6| +---| +ARM| + +Only 1 TX ID available + +### Sub_protocol PHOENIX - *6* +CH6| +---| +ARM| + +If a CC2500 is installed it will be used for this sub protocol. Option in this case is used for fine frequency tuning like any CC2500 protocols so check the [Frequency Tuning page](/docs/Frequency_Tuning.md). + +If only a NRF24L01 is installed then this sub protocol might be problematic because it is using the xn297L emulation with a transmission speed of 250kbps which doesn't work very well with every NRF24L01, this is an hardware issue with the authenticity and accuracy of the components. + +## MT99XX - *17* +Autobind protocol + +CH1|CH2|CH3|CH4|CH5|CH6|CH7|CH8|CH9 +---|---|---|---|---|---|---|---|--- +A|E|T|R|FLIP|LED|PICTURE|VIDEO|HEADLESS + +CC2500: only YZ is supported. + +### Sub_protocol MT99 - *0* +Models: MT99xx +### Sub_protocol H7 - *1* +Models: Eachine H7, Cheerson CX023 +### Sub_protocol YZ - *2* +Model: Yi Zhan i6S + +Only one model can be flown at the same time since the ID is hardcoded. + +If a CC2500 is installed it will be used for this sub protocol. Option in this case is used for fine frequency tuning like any CC2500 protocols so check the [Frequency Tuning page](/docs/Frequency_Tuning.md). + +If only a NRF24L01 is installed then this sub protocol might be problematic because it is using the xn297L emulation with a transmission speed of 250kbps which doesn't work very well with every NRF24L01, this is an hardware issue with the authenticity and accuracy of the components. + +### Sub_protocol LS - *3* +Models: LS114, 124, 215 + +CH1|CH2|CH3|CH4|CH5|CH6|CH7|CH8|CH9 +---|---|---|---|---|---|---|---|--- +A|E|T|R|FLIP|INVERT|PICTURE|VIDEO|HEADLESS + +### Sub_protocol FY805 - *4* +Model: FY805 + +**Only 1 ID available** + +CH1|CH2|CH3|CH4|CH5|CH6|CH7|CH8|CH9 +---|---|---|---|---|---|---|---|--- +A|E|T|R|FLIP||||HEADLESS + +### Sub_protocol A180 - *5* +Model: XK A180 + +CH1|CH2|CH3|CH4|CH5 +---|---|---|---|--- +A|E|T|R|3D6G + +### Sub_protocol DRAGON - *6* +Model: Eachine Mini Wing Dragon + +CH1|CH2|CH3|CH4|CH5|CH6 +---|---|---|---|---|--- +A|E|T|R|MODE|RTH + +MODE: -100%=Beginner, 0%=Intermediate, +100%=Advanced + +## OMP - *77* +Model: OMPHOBBY M1 & M2 Helis, T720 RC Glider + +If a CC2500 is installed it will be used for this sub protocol. Option in this case is used for fine frequency tuning like any CC2500 protocols so check the [Frequency Tuning page](/docs/Frequency_Tuning.md). + +If only a NRF24L01 is installed then this sub protocol might be problematic because it is using the xn297L emulation with a transmission speed of 250kbps which doesn't work very well with every NRF24L01, this is an hardware issue with the authenticity and accuracy of the components. + +Telemetry is supported: +- A1 = battery voltage including "recovered" battery voltage from corrupted telemetry packets +- A2 = battery voltage from only good telemetry packets +- How to calculate accurately the OpenTX Ratio and Offset: +Set the Ratio to 12.7 and Offset to 0, plug 2 batteries with extreme voltage values, write down the values Batt1=12.5V & Telem1=12.2V, Batt2=7V & Telem2=6.6V then calculate/set Ratio=12.7*[(12.5-7)/(12.2-6.6)]=12.47 => 12.5 and Offset=12.5-12.2*[(12.5-7)/(12.2-6.6)]=0.517 => 0.5 +- RX_RSSI = TQly = percentage of received telemetry packets (good and corrupted) from the model which has nothing to do with how well the RX is receiving the TX + +Option for this protocol corresponds to the CC2500 fine frequency tuning. This value is different for each Module and **must** be accurate otherwise the link will not be stable. +Check the [Frequency Tuning page](/docs/Frequency_Tuning.md) to determine it. + +CH1|CH2|CH3|CH4|CH5|CH6|CH7 +---|---|---|---|---|---|--- +A|E|T_PITCH|R|T_HOLD|IDLE|MODE + +IDLE= 3 pos switch: -100% Normal, 0% Idle1, +100% Idle2 + +From the TX manual: MODE= 3 pos switch -100% Attitude, 0% Attitude(?), +100% 3D +For M2: MODE= 3 pos switch -100% 6G, 0% 3D, +100% 3D + +## Q303 - *31* +Autobind protocol + +CH1|CH2|CH3|CH4 +---|---|---|--- +A|E|T|R + +CC2500: only Q303 is supported. + +### Sub_protocol Q303 - *0* + +If a CC2500 is installed it will be used for this sub protocol. Option in this case is used for fine frequency tuning like any CC2500 protocols so check the [Frequency Tuning page](/docs/Frequency_Tuning.md). + +If only a NRF24L01 is installed then this sub protocol might be problematic because it is using the xn297L emulation with a transmission speed of 250kbps which doesn't work very well with every NRF24L01, this is an hardware issue with the authenticity and accuracy of the components. + +CH5|CH6|CH7|CH8|CH9|CH10|CH11 +---|---|---|---|---|---|--- +AHOLD|FLIP|PICTURE|VIDEO|HEADLESS|RTH|GIMBAL + +GIMBAL needs 3 position -100%/0%/100% + +### Sub_protocol CX35 - *1* +CH5|CH6|CH7|CH8|CH9|CH10|CH11 +---|---|---|---|---|---|--- +ARM|VTX|PICTURE|VIDEO||RTH|GIMBAL + +ARM is 2 positions: land / take off + +Each toggle of VTX will increment the channel. + +Gimbal is full range. + +### Sub_protocol CX10D - *2* +Models CX10D and CX33W + +CH5|CH6 +---|--- +ARM|FLIP + +ARM is 3 positions: -100%=land / 0%=manual / +100%=take off + +### Sub_protocol CX10WD - *3* +CH5|CH6 +---|--- +ARM|FLIP + +ARM is 3 positions: -100%=land / 0%=manual / +100%=take off + ## Q90C - *72* CH1|CH2|CH3|CH4|CH5|CH6 @@ -1087,6 +1236,26 @@ Models: WLtoys V911S, XK A110 ### Sub_protocol E119 - *1* Models: Eachine E119 +## XK - *62* + +CH1|CH2|CH3|CH4|CH5|CH6|CH7|CH8|CH9|CH10 +---|---|---|---|---|---|---|---|---|---- +A|E|T|R|Flight_modes|Take_off|Emerg stop|3D/6G|Picture|Video + +Flight_modes: -100%=M-Mode, 0%=6G-Mode, +100%=V-Mode. CH6-CH10 are mementary switches. + +CC2500: only X450 is supported. + +### Sub_protocol X450 - *0* +Models: XK X450 (TX=X8) + +If a CC2500 is installed it will be used for this sub protocol. Option in this case is used for fine frequency tuning like any CC2500 protocols so check the [Frequency Tuning page](/docs/Frequency_Tuning.md). + +If only a NRF24L01 is installed then this sub protocol might be problematic because it is using the xn297L emulation with a transmission speed of 250kbps which doesn't work very well with every NRF24L01, this is an hardware issue with the authenticity and accuracy of the components. + +### Sub_protocol X420 - *1* +Models: XK X420/X520 (TX=X4) + *** # NRF24L01 RF Module @@ -1286,6 +1455,15 @@ CH1|CH2|CH3|CH4|CH5|CH6|CH7|CH8|CH9|CH10|CH11 ---|---|---|---|---|---|---|---|---|----|---- A|E|T|R|FLIP|LED|CAMERA1|CAMERA2|HEADLESS|RTH|RATE_LOW +## E016H - *85* +Autobind protocol + +Model: Eachine E016H + +CH1|CH2|CH3|CH4|CH5|CH6|CH7|CH8|CH9 +---|---|---|---|---|---|---|---|--- +A|E|T|R|STOP|FLIP|-|HEADLESS|RTH + ## E01X - *45* Autobind protocol @@ -1307,13 +1485,6 @@ CH1|CH2|CH3|CH4|CH5|CH6|CH7|CH8|CH9 ---|---|---|---|---|---|---|---|--- A|E|T|R|ARM|FLIP|LED|HEADLESS|RTH -### Sub_protocol E016H - *2* -Models: Eachine E016H - -CH1|CH2|CH3|CH4|CH5|CH6|CH7|CH8|CH9 ----|---|---|---|---|---|---|---|--- -A|E|T|R|STOP|FLIP|-|HEADLESS|RTH - ## ESKY - *16* CH1|CH2|CH3|CH4|CH5|CH6 @@ -1493,93 +1664,6 @@ CH14| CH6 | -100% | 0% | | - | - CH15| CH7 | -100% | 0% | - | - | +100% CH16| CH8 | -100% | 0% | - | - | - -## MJXQ - *18* -Autobind protocol - -CH1|CH2|CH3|CH4|CH5|CH6|CH7|CH8|CH9|CH10|CH11|CH12|CH13|CH14 ----|---|---|---|---|---|---|---|---|----|----|----|----|---- -A|E|T|R|FLIP|LED|PICTURE|VIDEO|HEADLESS|RTH|AUTOFLIP|PAN|TILT|RATE - -RATE: -100%(default)=>higher rates by enabling dynamic trims (except for Headless), 100%=>disable dynamic trims - -### Sub_protocol WLH08 - *0* -### Sub_protocol X600 - *1* -Only 3 TX IDs available, change RX_Num value 0..2 to cycle through them -### Sub_protocol X800 - *2* -Only 3 TX IDs available, change RX_Num value 0..2 to cycle through them -### Sub_protocol H26D - *3* -Only 3 TX IDs available, change RX_Num value 0..2 to cycle through them -### Sub_protocol E010 - *4* -15 TX IDs available, change RX_Num value 0..14 to cycle through them - -If a CC2500 is installed it will be used for this sub protocol. Option in this case is used for fine frequency tuning like any CC2500 protocols so check the [Frequency Tuning page](/docs/Frequency_Tuning.md). - -If only a NRF24L01 is installed then this sub protocol might be problematic because it is using the xn297L emulation with a transmission speed of 250kbps which doesn't work very well with every NRF24L01, this is an hardware issue with the authenticity and accuracy of the components. - -### Sub_protocol H26WH - *5* -CH6| ----| -ARM| - -Only 1 TX ID available - -### Sub_protocol PHOENIX - *6* -CH6| ----| -ARM| - -## MT99XX - *17* -Autobind protocol - -CH1|CH2|CH3|CH4|CH5|CH6|CH7|CH8|CH9 ----|---|---|---|---|---|---|---|--- -A|E|T|R|FLIP|LED|PICTURE|VIDEO|HEADLESS - -### Sub_protocol MT99 - *0* -Models: MT99xx -### Sub_protocol H7 - *1* -Models: Eachine H7, Cheerson CX023 -### Sub_protocol YZ - *2* -Model: Yi Zhan i6S - -Only one model can be flown at the same time since the ID is hardcoded. - -If a CC2500 is installed it will be used for this sub protocol. Option in this case is used for fine frequency tuning like any CC2500 protocols so check the [Frequency Tuning page](/docs/Frequency_Tuning.md). - -If only a NRF24L01 is installed then this sub protocol might be problematic because it is using the xn297L emulation with a transmission speed of 250kbps which doesn't work very well with every NRF24L01, this is an hardware issue with the authenticity and accuracy of the components. - -### Sub_protocol LS - *3* -Models: LS114, 124, 215 - -CH1|CH2|CH3|CH4|CH5|CH6|CH7|CH8|CH9 ----|---|---|---|---|---|---|---|--- -A|E|T|R|FLIP|INVERT|PICTURE|VIDEO|HEADLESS - -### Sub_protocol FY805 - *4* -Model: FY805 - -**Only 1 ID available** - -CH1|CH2|CH3|CH4|CH5|CH6|CH7|CH8|CH9 ----|---|---|---|---|---|---|---|--- -A|E|T|R|FLIP||||HEADLESS - -### Sub_protocol A180 - *5* -Model: XK A180 - -CH1|CH2|CH3|CH4|CH5 ----|---|---|---|--- -A|E|T|R|3D6G - -### Sub_protocol DRAGON - *6* -Model: Eachine Mini Wing Dragon - -CH1|CH2|CH3|CH4|CH5|CH6 ----|---|---|---|---|--- -A|E|T|R|MODE|RTH - -MODE: -100%=Beginner, 0%=Intermediate, +100%=Advanced - ## NCC1701 - *44* Model: Air Hogs Star Trek USS Enterprise NCC-1701-A @@ -1635,52 +1719,6 @@ A|E|T|R|FLIP|LED|PICTURE|VIDEO|HEADLESS|RTH|XCAL|YCAL Model: JXD 509 is using Q282 with CH12=Start/Stop motors -## Q303 - *31* -Autobind protocol - -CH1|CH2|CH3|CH4 ----|---|---|--- -A|E|T|R - -### Sub_protocol Q303 - *0* - -If a CC2500 is installed it will be used for this sub protocol. Option in this case is used for fine frequency tuning like any CC2500 protocols so check the [Frequency Tuning page](/docs/Frequency_Tuning.md). - -If only a NRF24L01 is installed then this sub protocol might be problematic because it is using the xn297L emulation with a transmission speed of 250kbps which doesn't work very well with every NRF24L01, this is an hardware issue with the authenticity and accuracy of the components. - -CH5|CH6|CH7|CH8|CH9|CH10|CH11 ----|---|---|---|---|---|--- -AHOLD|FLIP|PICTURE|VIDEO|HEADLESS|RTH|GIMBAL - -GIMBAL needs 3 position -100%/0%/100% - -### Sub_protocol CX35 - *1* -CH5|CH6|CH7|CH8|CH9|CH10|CH11 ----|---|---|---|---|---|--- -ARM|VTX|PICTURE|VIDEO||RTH|GIMBAL - -ARM is 2 positions: land / take off - -Each toggle of VTX will increment the channel. - -Gimbal is full range. - -### Sub_protocol CX10D - *2* -Models CX10D and CX33W - -CH5|CH6 ----|--- -ARM|FLIP - -ARM is 3 positions: -100%=land / 0%=manual / +100%=take off - -### Sub_protocol CX10WD - *3* -CH5|CH6 ----|--- -ARM|FLIP - -ARM is 3 positions: -100%=land / 0%=manual / +100%=take off - ## Realacc - *76* Model: Realacc R11 @@ -1792,25 +1830,6 @@ CH1|CH2|CH3|CH4|CH5|CH6|CH7|CH8|CH9 ---|---|---|---|---|---|---|---|--- A|E|T|R|GYRO|CALIB|FLIP|RTN_ACT|RTN - -## XK - *62* - -CH1|CH2|CH3|CH4|CH5|CH6|CH7|CH8|CH9|CH10 ----|---|---|---|---|---|---|---|---|---- -A|E|T|R|Flight_modes|Take_off|Emerg stop|3D/6G|Picture|Video - -Flight_modes: -100%=M-Mode, 0%=6G-Mode, +100%=V-Mode. CH6-CH10 are mementary switches. - -### Sub_protocol X450 - *0* -Models: XK X450 (TX=X8) - -If a CC2500 is installed it will be used for this sub protocol. Option in this case is used for fine frequency tuning like any CC2500 protocols so check the [Frequency Tuning page](/docs/Frequency_Tuning.md). - -If only a NRF24L01 is installed then this sub protocol might be problematic because it is using the xn297L emulation with a transmission speed of 250kbps which doesn't work very well with every NRF24L01, this is an hardware issue with the authenticity and accuracy of the components. - -### Sub_protocol X420 - *1* -Models: XK X420/X520 (TX=X4) - ## YD717 - *8* Autobind protocol