diff --git a/Multiprotocol/FrSkyD_cc2500.cpp b/Multiprotocol/FrSkyD_cc2500.cpp
index b656f22..3aa90d4 100644
--- a/Multiprotocol/FrSkyD_cc2500.cpp
+++ b/Multiprotocol/FrSkyD_cc2500.cpp
@@ -17,6 +17,7 @@
#include "cc2500_spi.h"
#include "Multiprotocol.h"
+uint16_t counter;
void frsky2way_init(uint8_t bind)
{
//debugln("frsky2way_init");
@@ -105,12 +106,10 @@ uint16_t initFrSky_2way()
{
frsky2way_init(1);
state = FRSKY_BIND;
- debugln("initFrSky_2way bind");
- }
- else
- {
+ debugln("initFrSky_2way bind");
+ } else {
state = FRSKY_BIND_DONE;
- debugln("initFrSky_2way bind done");
+ debugln("initFrSky_2way bind done");
}
return 10000;
}
@@ -119,8 +118,7 @@ uint16_t ReadFrSky_2way()
{
//debugln("%s",__func__);
- if (state < FRSKY_BIND_DONE)
- {
+ if (state < FRSKY_BIND_DONE) {
frsky2way_build_bind_packet();
CC2500_Strobe(CC2500_SIDLE);
CC2500_WriteReg(CC2500_0A_CHANNR, 0x00);
@@ -129,50 +127,43 @@ uint16_t ReadFrSky_2way()
CC2500_WriteData(packet, packet[0]+1);
if(IS_BIND_DONE) {
state = FRSKY_BIND;
- debugln("%s bind done",__func__);
- } else
- state++;
-
- if(state == FRSKY_BIND_DONE) {
- debugln("%s bind done fr",__func__);
- }
+ debugln("%s bind done",__func__);
+ } else {
+ // menu tells us to stop so do not inc state
+ //state++;
+ }
+
+ if(state == FRSKY_BIND_DONE) {
+ debugln("%s bind done fr",__func__);
+ }
return 9000;
}
- if (state == FRSKY_BIND_DONE)
- {
+ if (state == FRSKY_BIND_DONE) {
//debugln("%s bind done",__func__);
state = FRSKY_DATA2;
frsky2way_init(0);
counter = 0;
BIND_DONE;
- }
- else
- if (state == FRSKY_DATA5)
- {
+ } else if (state == FRSKY_DATA5) {
CC2500_Strobe(CC2500_SRX);//0x34 RX enable
state = FRSKY_DATA1;
return 9200;
}
counter = (counter + 1) % 188;
- if (state == FRSKY_DATA4)
- { //telemetry receive
+ if (state == FRSKY_DATA4) { //telemetry receive
CC2500_SetTxRxMode(RX_EN);
CC2500_Strobe(CC2500_SIDLE);
CC2500_WriteReg(CC2500_0A_CHANNR, hopping_frequency[counter % 47]);
CC2500_WriteReg(CC2500_23_FSCAL3, 0x89);
state++;
return 1300;
- }
- else
- {
- if (state == FRSKY_DATA1)
- {
+ } else {
+ if (state == FRSKY_DATA1) {
len = CC2500_ReadReg(CC2500_3B_RXBYTES | CC2500_READ_BURST) & 0x7F;
//debugln("%d len",len);
- if (len && len<=(0x11+3))// 20bytes
- {
+ if (len && len<=(0x11+3)) { // 20bytes
CC2500_ReadData(pkt, len); //received telemetry packets
#if defined(TELEMETRY)
if(pkt[len-1] & 0x80)
@@ -181,13 +172,10 @@ uint16_t ReadFrSky_2way()
frsky_check_telemetry(pkt,len); //check if valid telemetry packets and buffer them.
}
#endif
- }
- else
- {
+ } else {
packet_count++;
// restart sequence on missed packet - might need count or timeout instead of one missed
- if(packet_count>100)
- {//~1sec
+ if(packet_count > 100) {//~1sec
packet_count=0;
#if defined TELEMETRY
telemetry_link=0;//no link frames
@@ -200,8 +188,7 @@ uint16_t ReadFrSky_2way()
}
CC2500_Strobe(CC2500_SIDLE);
CC2500_WriteReg(CC2500_0A_CHANNR, hopping_frequency[counter % 47]);
- if ( prev_option != option )
- {
+ if ( prev_option != option ) {
CC2500_WriteReg(CC2500_0C_FSCTRL0,option); // Frequency offset hack
prev_option = option ;
}
diff --git a/Multiprotocol/FrSkyV_cc2500.cpp b/Multiprotocol/FrSkyV_cc2500.cpp
deleted file mode 100644
index b6c5a0a..0000000
--- a/Multiprotocol/FrSkyV_cc2500.cpp
+++ /dev/null
@@ -1,155 +0,0 @@
-/*
- This project is free software: you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation, either version 3 of the License, or
- (at your option) any later version.
-
- Multiprotocol is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
-
- You should have received a copy of the GNU General Public License
- along with Multiprotocol. If not, see .
- */
-
-#define FRSKYV_BIND_COUNT 200
-#include "FrSkyV_cc2500.h"
-#include "cc2500_spi.h"
-#include "common.h"
-
-uint8_t FRSKYV_crc8(uint8_t result, uint8_t *data, uint8_t len)
-{
- for(uint8_t i = 0; i < len; i++)
- {
- result = result ^ data[i];
- for(uint8_t j = 0; j < 8; j++)
- if(result & 0x80)
- result = (result << 1) ^ 0x07;
- else
- result = result << 1;
- }
- return result;
-}
-
-uint8_t FRSKYV_crc8_le(uint8_t *data, uint8_t len)
-{
- uint8_t result = 0xD6;
-
- for(uint8_t i = 0; i < len; i++)
- {
- result = result ^ data[i];
- for(uint8_t j = 0; j < 8; j++)
- if(result & 0x01)
- result = (result >> 1) ^ 0x83;
- else
- result = result >> 1;
- }
- return result;
-}
-
-void FRSKYV_build_bind_packet()
-{
- //0e 03 01 57 12 00 06 0b 10 15 1a 00 00 00 61
- packet[0] = 0x0e; //Length
- packet[1] = 0x03; //Packet type
- packet[2] = 0x01; //Packet type
- packet[3] = rx_tx_addr[3];
- packet[4] = rx_tx_addr[2];
- packet[5] = (binding_idx % 10) * 5;
- packet[6] = packet[5] * 5 + 6;
- packet[7] = packet[5] * 5 + 11;
- packet[8] = packet[5] * 5 + 16;
- packet[9] = packet[5] * 5 + 21;
- packet[10] = packet[5] * 5 + 26;
- packet[11] = 0x00;
- packet[12] = 0x00;
- packet[13] = 0x00;
- packet[14] = FRSKYV_crc8(0x93, packet, 14);
-}
-
-uint8_t FRSKYV_calc_channel()
-{
- uint32_t temp=seed;
- temp = (temp * 0xaa) % 0x7673;
- seed = temp;
- return (seed & 0xff) % 0x32;
-}
-
-void FRSKYV_build_data_packet()
-{
- uint8_t idx = 0; // transmit lower channels
-
- packet[0] = 0x0e;
- packet[1] = rx_tx_addr[3];
- packet[2] = rx_tx_addr[2];
- packet[3] = seed & 0xff;
- packet[4] = seed >> 8;
- if (phase == FRSKYV_DATA1 || phase == FRSKYV_DATA3)
- packet[5] = 0x0f;
- else
- if(phase == FRSKYV_DATA2 || phase == FRSKYV_DATA4)
- {
- packet[5] = 0xf0;
- idx=4; // transmit upper channels
- }
- else
- packet[5] = 0x00;
- for(uint8_t i = 0; i < 4; i++)
- {
- uint16_t value = convert_channel_frsky(i+idx);
- packet[2*i + 6] = value & 0xff;
- packet[2*i + 7] = value >> 8;
- }
- packet[14] = FRSKYV_crc8(crc8, packet, 14);
-}
-
-uint16_t ReadFRSKYV()
-{
- if(IS_BIND_DONE)
- { // Normal operation
- uint8_t chan = FRSKYV_calc_channel();
- CC2500_Strobe(CC2500_SIDLE);
- if (option != prev_option)
- {
- CC2500_WriteReg(CC2500_0C_FSCTRL0, option);
- prev_option=option;
- }
- CC2500_WriteReg(CC2500_0A_CHANNR, chan * 5 + 6);
- FRSKYV_build_data_packet();
-
- if (phase == FRSKYV_DATA5)
- {
- CC2500_SetPower();
- phase = FRSKYV_DATA1;
- }
- else
- phase++;
-
- CC2500_WriteData(packet, packet[0]+1);
- return 9006;
- }
- // Bind mode
- FRSKYV_build_bind_packet();
- CC2500_Strobe(CC2500_SIDLE);
- CC2500_WriteReg(CC2500_0A_CHANNR, 0x00);
- CC2500_WriteData(packet, packet[0]+1);
- binding_idx++;
- if(binding_idx>=FRSKYV_BIND_COUNT)
- BIND_DONE;
- return 53460;
-}
-
-uint16_t initFRSKYV()
-{
- //ID is 15 bits. Using rx_tx_addr[2] and rx_tx_addr[3] since we want to use RX_Num for model match
- rx_tx_addr[2]&=0x7F;
- crc8 = FRSKYV_crc8_le(rx_tx_addr+2, 2);
-
- FRSKY_init_cc2500(FRSKYV_cc2500_conf);
- seed = 1;
- binding_idx=0;
- phase = FRSKYV_DATA1;
- return 10000;
-}
-
diff --git a/Multiprotocol/FrSkyV_cc2500.h b/Multiprotocol/FrSkyV_cc2500.h
deleted file mode 100644
index 10294a0..0000000
--- a/Multiprotocol/FrSkyV_cc2500.h
+++ /dev/null
@@ -1,39 +0,0 @@
-/*
- This project is free software: you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation, either version 3 of the License, or
- (at your option) any later version.
-
- Multiprotocol is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
-
- You should have received a copy of the GNU General Public License
- along with Multiprotocol. If not, see .
- */
-
-#ifndef _FRSKYV_CC2500_H_
-#define _FRSKYV_CC2500_H_
-
-#define FRSKYV_BIND_COUNT 200
-#include
-#include "Multiprotocol.h"
-
-enum frskyv_data_e {
- FRSKYV_DATA1=0,
- FRSKYV_DATA2,
- FRSKYV_DATA3,
- FRSKYV_DATA4,
- FRSKYV_DATA5
-};
-
-uint8_t FRSKYV_crc8(uint8_t result, uint8_t *data, uint8_t len);
-
-uint8_t FRSKYV_crc8_le(uint8_t *data, uint8_t len);
-void FRSKYV_build_bind_packet(void);
-uint8_t FRSKYV_calc_channel(void);
-void FRSKYV_build_data_packet(void);
-uint16_t ReadFRSKYV(void);
-uint16_t initFRSKYV(void);
-#endif
diff --git a/Multiprotocol/FrSkyX_cc2500.cpp b/Multiprotocol/FrSkyX_cc2500.cpp
deleted file mode 100644
index 3aeb3a2..0000000
--- a/Multiprotocol/FrSkyX_cc2500.cpp
+++ /dev/null
@@ -1,363 +0,0 @@
-/* **************************
- * By Midelic on RCGroups *
- **************************
- This project is free software: you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation, either version 3 of the License, or
- (at your option) any later version.
-
- Multiprotocol is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
-
- You should have received a copy of the GNU General Public License
- along with Multiprotocol. If not, see .
-*/
-
-
-
-#include "Arduino.h"
-#include "Multiprotocol.h"
-#include "FrSkyX_cc2500.h"
-#include
-#include "common.h"
-#include "cc2500_spi.h"
-
-uint8_t FrX_chanskip;
-uint8_t FrX_send_seq ;
-uint8_t FrX_receive_seq ;
-
-void frskyX_set_start(uint8_t ch)
-{
- CC2500_Strobe(CC2500_SIDLE);
- CC2500_WriteReg(CC2500_25_FSCAL1, calData[ch]);
- CC2500_WriteReg(CC2500_0A_CHANNR, hopping_frequency[ch]);
-}
-
-void frskyX_init(void)
-{
- FRSKY_init_cc2500((sub_protocol&2)?FRSKYXEU_cc2500_conf:FRSKYX_cc2500_conf); // LBT or FCC
- //
- for(uint8_t c=0;c < 48;c++)
- {//calibrate hop channels
- CC2500_Strobe(CC2500_SIDLE);
- CC2500_WriteReg(CC2500_0A_CHANNR,hopping_frequency[c]);
- CC2500_Strobe(CC2500_SCAL);
- delayMicroseconds(900);//
- calData[c] = CC2500_ReadReg(CC2500_25_FSCAL1);
- }
- //#######END INIT########
-}
-
-void frskyX_initialize_data(uint8_t adr)
-{
- CC2500_WriteReg(CC2500_0C_FSCTRL0,option); // Frequency offset hack
- CC2500_WriteReg(CC2500_18_MCSM0, 0x8);
- CC2500_WriteReg(CC2500_09_ADDR, adr ? 0x03 : rx_tx_addr[3]);
- CC2500_WriteReg(CC2500_07_PKTCTRL1,0x05);
-}
-
-//**CRC**
-const uint16_t frskyX_CRC_Short[]={
- 0x0000, 0x1189, 0x2312, 0x329B, 0x4624, 0x57AD, 0x6536, 0x74BF,
- 0x8C48, 0x9DC1, 0xAF5A, 0xBED3, 0xCA6C, 0xDBE5, 0xE97E, 0xF8F7 };
-
-uint16_t frskyX_CRCTable(uint8_t val)
-{
- uint16_t word ;
- word = pgm_read_word(&frskyX_CRC_Short[val&0x0F]) ;
- val /= 16 ;
- return word ^ (0x1081 * val) ;
-}
-
-uint16_t frskyX_crc_x(uint8_t *data, uint8_t len)
-{
- uint16_t crc = 0;
- for(uint8_t i=0; i < len; i++)
- crc = (crc<<8) ^ frskyX_CRCTable((uint8_t)(crc>>8) ^ *data++);
- return crc;
-}
-
-void frskyX_build_bind_packet(void)
-{
- // debugln("%s:%d build bind", __func__, __LINE__);
- packet[0] = (sub_protocol & 2 ) ? 0x20 : 0x1D ; // LBT or FCC
- packet[1] = 0x03;
- packet[2] = 0x01;
- //
- packet[3] = rx_tx_addr[3];
- packet[4] = rx_tx_addr[2];
- int idx = ((state -FRSKY_BIND) % 10) * 5;
- packet[5] = idx;
- packet[6] = hopping_frequency[idx++];
- packet[7] = hopping_frequency[idx++];
- packet[8] = hopping_frequency[idx++];
- packet[9] = hopping_frequency[idx++];
- packet[10] = hopping_frequency[idx++];
- packet[11] = 0x02;
- packet[12] = RX_num;
- //
- uint8_t limit = (sub_protocol & 2 ) ? 31 : 28 ;
- memset(&packet[13], 0, limit - 13);
- uint16_t lcrc = frskyX_crc_x(&packet[3], limit-3);
- //
- packet[limit++] = lcrc >> 8;
- packet[limit] = lcrc;
- //
-}
-
-// 0-2047, 0 = 817, 1024 = 1500, 2047 = 2182
-//64=860,1024=1500,1984=2140//Taranis 125%
-uint16_t frskyX_scaleForPXX(uint8_t i)
-{ //mapped 860,2140(125%) range to 64,1984(PXX values);
- uint16_t chan_val=convert_channel_frsky(i)-1226;
- if(i>7) chan_val|=2048; // upper channels offset
- return chan_val;
-}
-
-uint16_t frskyX_scaleForPXX_FS(uint8_t i)
-{ //mapped 1,2046(125%) range to 64,1984(PXX values);
- uint16_t chan_val=((Failsafe_data[i]*15)>>4)+64;
- if(Failsafe_data[i]==FAILSAFE_CHANNEL_NOPULSES)
- chan_val=FAILSAFE_CHANNEL_NOPULSES;
- else if(Failsafe_data[i]==FAILSAFE_CHANNEL_HOLD)
- chan_val=FAILSAFE_CHANNEL_HOLD;
- if(i>7) chan_val|=2048; // upper channels offset
- return chan_val;
-}
-
-void frskyX_data_frame(void)
-{
- //0x1D 0xB3 0xFD 0x02 0x56 0x07 0x15 0x00 0x00 0x00 0x04 0x40 0x00 0x04 0x40 0x00 0x04 0x40 0x00 0x04 0x40 0x08 0x00 0x00 0x00 0x00 0x00 0x00 0x96 0x12
- //
- static uint8_t chan_offset=0;
- uint16_t chan_0 ;
- uint16_t chan_1 ;
- //
- // data frames sent every 9ms; failsafe every 9 seconds
- #ifdef FAILSAFE_ENABLE
- static uint16_t failsafe_count=0;
- static uint8_t FS_flag=0,failsafe_chan=0;
- if (FS_flag == 0 && failsafe_count > FRX_FAILSAFE_TIME && chan_offset == 0 && IS_FAILSAFE_VALUES_on)
- {
- FS_flag = 0x10;
- failsafe_chan = 0;
- } else if (FS_flag & 0x10 && failsafe_chan < (sub_protocol & 0x01 ? 8-1:16-1))
- {
- FS_flag = 0x10 | ((FS_flag + 2) & 0x0F); //10, 12, 14, 16, 18, 1A, 1C, 1E - failsafe packet
- failsafe_chan ++;
- } else if (FS_flag & 0x10)
- {
- FS_flag = 0;
- failsafe_count = 0;
- }
- failsafe_count++;
- #endif
-
- packet[0] = (sub_protocol & 0x02 ) ? 0x20 : 0x1D ; // LBT or FCC
- packet[1] = rx_tx_addr[3];
- packet[2] = rx_tx_addr[2];
- packet[3] = 0x02;
- //
- packet[4] = (FrX_chanskip<<6)|hopping_frequency_no;
- packet[5] = FrX_chanskip>>2;
- packet[6] = RX_num;
- //packet[7] = FLAGS 00 - standard packet
- //10, 12, 14, 16, 18, 1A, 1C, 1E - failsafe packet
- //20 - range check packet
- #ifdef FAILSAFE_ENABLE
- packet[7] = FS_flag;
- #else
- packet[7] = 0;
- #endif
- packet[8] = 0;
- //
- uint8_t startChan = chan_offset; for(uint8_t i = 0; i <12 ; i+=3)
- {//12 bytes of channel data
- #ifdef FAILSAFE_ENABLE
- if( (FS_flag & 0x10) && ((failsafe_chan & 0x07) == (startChan & 0x07)) )
- chan_0 = frskyX_scaleForPXX_FS(failsafe_chan);
- else
- #endif
- chan_0 = frskyX_scaleForPXX(startChan);
- startChan++;
- //
- #ifdef FAILSAFE_ENABLE
- if( (FS_flag & 0x10) && ((failsafe_chan & 0x07) == (startChan & 0x07)) )
- chan_1 = frskyX_scaleForPXX_FS(failsafe_chan);
- else
- #endif
- chan_1 = frskyX_scaleForPXX(startChan);
- startChan++;
- //
- packet[9+i] = lowByte(chan_0); //3 bytes*4
- packet[9+i+1]=(((chan_0>>8) & 0x0F)|(chan_1 << 4));
- packet[9+i+2]=chan_1>>4;
- }
- packet[21] = (FrX_receive_seq << 4) | FrX_send_seq ;//8 at start
-
- if(sub_protocol & 0x01 ) // in X8 mode send only 8ch every 9ms
- chan_offset = 0 ;
- else
- chan_offset^=0x08;
-
- uint8_t limit = (sub_protocol & 2 ) ? 31 : 28 ;
- for (uint8_t i=22;i>8;//high byte
- packet[limit]=lcrc;//low byte
-}
-
-uint16_t ReadFrSkyX(void)
-{
- switch(state)
- {
- default:
- frskyX_set_start(47);
- CC2500_SetPower();
- CC2500_Strobe(CC2500_SFRX);
- //
- frskyX_build_bind_packet();
- CC2500_Strobe(CC2500_SIDLE);
- CC2500_WriteData(packet, packet[0]+1);
- if(IS_BIND_DONE) {
- state = FRSKY_BIND_DONE;
- //debugln("%s:%d bind done", __func__, __LINE__);
- }
- else
- state++;
- return 9000;
- case FRSKY_BIND_DONE:
- frskyX_initialize_data(0);
- hopping_frequency_no=0;
- BIND_DONE;
- state++;
- break;
- case FRSKY_DATA1:
- if ( prev_option != option )
- {
- CC2500_WriteReg(CC2500_0C_FSCTRL0,option); // Frequency offset hack
- prev_option = option ;
- }
- CC2500_SetTxRxMode(TX_EN);
- frskyX_set_start(hopping_frequency_no);
- CC2500_SetPower();
- CC2500_Strobe(CC2500_SFRX);
- hopping_frequency_no = (hopping_frequency_no+FrX_chanskip)%47;
- CC2500_Strobe(CC2500_SIDLE);
- CC2500_WriteData(packet, packet[0]+1);
- //
-// frskyX_data_frame();
- state++;
- return 5200;
- case FRSKY_DATA2:
- CC2500_SetTxRxMode(RX_EN);
- CC2500_Strobe(CC2500_SIDLE);
- state++;
- return 200;
- case FRSKY_DATA3:
- CC2500_Strobe(CC2500_SRX);
- state++;
- return 3100;
- case FRSKY_DATA4:
- len = CC2500_ReadReg(CC2500_3B_RXBYTES | CC2500_READ_BURST) & 0x7F;
- if (len && (len<=(0x0E + 3))) //Telemetry frame is 17
- {
- packet_count=0;
- CC2500_ReadData(pkt, len);
- #if defined TELEMETRY
- frsky_check_telemetry(pkt,len); //check if valid telemetry packets
- //parse telemetry packets here
- //The same telemetry function used by FrSky(D8).
- #endif
- }
- else
- {
- packet_count++;
- // restart sequence on missed packet - might need count or timeout instead of one missed
- if(packet_count>100)
- {//~1sec
-// seq_last_sent = 0;
-// seq_last_rcvd = 8;
- FrX_send_seq = 0x08 ;
-// FrX_receive_seq = 0 ;
- packet_count=0;
- #if defined TELEMETRY
- telemetry_lost=1;
- #endif
- }
- CC2500_Strobe(CC2500_SFRX); //flush the RXFIFO
- }
- frskyX_data_frame();
- if ( FrX_send_seq != 0x08 )
- {
- FrX_send_seq = ( FrX_send_seq + 1 ) & 0x03 ;
- }
- state = FRSKY_DATA1;
- return 500;
- }
- return 1;
-}
-
-uint16_t initFrSkyX(void)
-{
- set_rx_tx_addr(MProtocol_id_master);
- Frsky_init_hop();
- packet_count=0;
- while(!FrX_chanskip)
- FrX_chanskip=random(0xfefefefe)%47;
-
- //for test***************
- rx_tx_addr[3]=0xB3;
- rx_tx_addr[2]=0xFD;
- //************************
- frskyX_init();
-#if defined SPORT_POLLING
-#ifdef INVERT_SERIAL
- start_timer4() ;
-#endif
-#endif
- //
- if(IS_BIND_IN_PROGRESS)
- {
- state = FRSKY_BIND;
- frskyX_initialize_data(1);
- }
- else
- {
- state = FRSKY_DATA1;
- frskyX_initialize_data(0);
- }
-// seq_last_sent = 0;
-// seq_last_rcvd = 8;
- FrX_send_seq = 0x08 ;
- FrX_receive_seq = 0 ;
- return 10000;
-}
diff --git a/Multiprotocol/FrSkyX_cc2500.h b/Multiprotocol/FrSkyX_cc2500.h
deleted file mode 100644
index 9bab442..0000000
--- a/Multiprotocol/FrSkyX_cc2500.h
+++ /dev/null
@@ -1,37 +0,0 @@
-/* **************************
- * By Midelic on RCGroups *
- **************************
- This project is free software: you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation, either version 3 of the License, or
- (at your option) any later version.
-
- Multiprotocol is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
-
- You should have received a copy of the GNU General Public License
- along with Multiprotocol. If not, see .
-*/
-
-#ifndef _FRSKYX_CC2500_H_
-#define _FRSKYX_CC2500_H_
-#include
-
-#define FRX_FAILSAFE_TIMEOUT 1032
-#define FRX_FAILSAFE_TIME 1032
-
-void frskyX_set_start(uint8_t ch);
-void frskyX_init(void);
-void frskyX_initialize_data(uint8_t adr);
-uint16_t frskyX_CRCTable(uint8_t val);
-uint16_t frskyX_crc_x(uint8_t *data, uint8_t len);
-void frskyX_build_bind_packet(void);
-uint16_t frskyX_scaleForPXX(uint8_t i);
-uint16_t frskyX_scaleForPXX_FS(uint8_t i);
-
-void frskyX_data_frame(void);
-uint16_t ReadFrSkyX(void);
-uint16_t initFrSkyX(void);
-#endif
diff --git a/Multiprotocol/Multiprotocol.h b/Multiprotocol/Multiprotocol.h
index 5c69e8d..0ae59e9 100644
--- a/Multiprotocol/Multiprotocol.h
+++ b/Multiprotocol/Multiprotocol.h
@@ -25,7 +25,6 @@
void set_rx_tx_addr(uint32_t id);
#define MAX_PKT 29
-extern volatile uint16_t PPM_data[NUM_CHN];
extern uint8_t hopping_frequency_no;
extern uint8_t sub_protocol;
extern uint8_t calData[48];
@@ -34,11 +33,8 @@ extern uint8_t protocol_flags;
extern uint8_t protocol_flags2;
extern uint8_t pkt[MAX_PKT];//telemetry receiving packets
extern uint8_t prev_option;
-extern uint8_t prev_power; // unused power value
-extern uint16_t counter;
extern uint8_t hopping_frequency[50];
extern uint8_t crc8;
-extern uint16_t Channel_data[NUM_CHN];
extern uint8_t packet_count;
extern uint8_t RX_num;
extern uint8_t binding_idx;
@@ -67,14 +63,13 @@ enum MultiPacketTypes
};
// Macros
+#ifndef _BV
#define _BV(i) (1<CHANNEL_SWITCH)
-#define CH14_SW (Channel_data[CH14]>CHANNEL_SWITCH)
-#define CH15_SW (Channel_data[CH15]>CHANNEL_SWITCH)
-#define CH16_SW (Channel_data[CH16]>CHANNEL_SWITCH)
-
-//************************
-//*** Power settings ***
-//************************
-enum {
- TXPOWER_100uW,
- TXPOWER_300uW,
- TXPOWER_1mW,
- TXPOWER_3mW,
- TXPOWER_10mW,
- TXPOWER_30mW,
- TXPOWER_100mW,
- TXPOWER_150mW
-};
-
-// A7105 power
-// Power amp is ~+16dBm so:
-enum A7105_POWER
-{
- A7105_POWER_0 = 0x00<<3 | 0x00, // TXPOWER_100uW = -23dBm == PAC=0 TBG=0
- A7105_POWER_1 = 0x00<<3 | 0x01, // TXPOWER_300uW = -20dBm == PAC=0 TBG=1
- A7105_POWER_2 = 0x00<<3 | 0x02, // TXPOWER_1mW = -16dBm == PAC=0 TBG=2
- A7105_POWER_3 = 0x00<<3 | 0x04, // TXPOWER_3mW = -11dBm == PAC=0 TBG=4
- A7105_POWER_4 = 0x01<<3 | 0x05, // TXPOWER_10mW = -6dBm == PAC=1 TBG=5
- A7105_POWER_5 = 0x02<<3 | 0x07, // TXPOWER_30mW = 0dBm == PAC=2 TBG=7
- A7105_POWER_6 = 0x03<<3 | 0x07, // TXPOWER_100mW = 1dBm == PAC=3 TBG=7
- A7105_POWER_7 = 0x03<<3 | 0x07 // TXPOWER_150mW = 1dBm == PAC=3 TBG=7
-};
-#define A7105_HIGH_POWER A7105_POWER_7
-#define A7105_LOW_POWER A7105_POWER_3
-#define A7105_RANGE_POWER A7105_POWER_0
-#define A7105_BIND_POWER A7105_POWER_0
-
-// NRF Power
-// Power setting is 0..3 for nRF24L01
-// Claimed power amp for nRF24L01 from eBay is 20dBm.
-enum NRF_POWER
-{ // Raw w 20dBm PA
- NRF_POWER_0 = 0x00, // 0 : -18dBm (16uW) 2dBm (1.6mW)
- NRF_POWER_1 = 0x01, // 1 : -12dBm (60uW) 8dBm (6mW)
- NRF_POWER_2 = 0x02, // 2 : -6dBm (250uW) 14dBm (25mW)
- NRF_POWER_3 = 0x03 // 3 : 0dBm (1mW) 20dBm (100mW)
-};
-#define NRF_HIGH_POWER NRF_POWER_3
-#define NRF_LOW_POWER NRF_POWER_1
-#define NRF_RANGE_POWER NRF_POWER_0
-#define NRF_BIND_POWER NRF_POWER_0
-
-// CC2500 power output from the chip itself
-// The numbers do not take into account any outside amplifier
-enum CC2500_POWER
-{
- CC2500_POWER_0 = 0x00, // -55dbm or less
- CC2500_POWER_1 = 0x50, // -30dbm
- CC2500_POWER_2 = 0x44, // -28dbm
- CC2500_POWER_3 = 0xC0, // -26dbm
- CC2500_POWER_4 = 0x84, // -24dbm
- CC2500_POWER_5 = 0x81, // -22dbm
- CC2500_POWER_6 = 0x46, // -20dbm
- CC2500_POWER_7 = 0x93, // -18dbm
- CC2500_POWER_8 = 0x55, // -16dbm
- CC2500_POWER_9 = 0x8D, // -14dbm
- CC2500_POWER_10 = 0xC6, // -12dbm
- CC2500_POWER_11 = 0x97, // -10dbm
- CC2500_POWER_12 = 0x6E, // -8dbm
- CC2500_POWER_13 = 0x7F, // -6dbm
- CC2500_POWER_14 = 0xA9, // -4dbm
- CC2500_POWER_15 = 0xBB, // -2dbm
- CC2500_POWER_16 = 0xFE, // 0dbm
- CC2500_POWER_17 = 0xFF // +1dbm
-};
-#define CC2500_HIGH_POWER CC2500_POWER_1
-#define CC2500_LOW_POWER CC2500_POWER_1
-#define CC2500_RANGE_POWER CC2500_POWER_1
-#define CC2500_BIND_POWER CC2500_POWER_1
-
-// CYRF power
-enum CYRF_POWER
-{
- CYRF_POWER_0 = 0x00, // -35dbm
- CYRF_POWER_1 = 0x01, // -30dbm
- CYRF_POWER_2 = 0x02, // -24dbm
- CYRF_POWER_3 = 0x03, // -18dbm
- CYRF_POWER_4 = 0x04, // -13dbm
- CYRF_POWER_5 = 0x05, // -5dbm
- CYRF_POWER_6 = 0x06, // 0dbm
- CYRF_POWER_7 = 0x07 // +4dbm
-};
-#define CYRF_HIGH_POWER CYRF_POWER_7
-#define CYRF_LOW_POWER CYRF_POWER_3
-#define CYRF_RANGE_POWER CYRF_POWER_1 // 1/30 of the full power distance
-#define CYRF_BIND_POWER CYRF_POWER_0
-
-enum TXRX_State {
- TXRX_OFF,
- TX_EN,
- RX_EN
-};
-
-// Packet ack status values
-enum {
- PKT_PENDING = 0,
- PKT_ACKED,
- PKT_TIMEOUT
-};
-
-// baudrate defines for serial
-#define SPEED_100K 0
-#define SPEED_9600 1
-#define SPEED_57600 2
-#define SPEED_125K 3
-
-/** EEPROM Layout */
-#define EEPROM_ID_OFFSET 10 // Module ID (4 bytes)
-#define EEPROM_BANK_OFFSET 15 // Current bank number (1 byte)
-#define EEPROM_ID_VALID_OFFSET 20 // 1 byte flag that ID is valid
-#define MODELMODE_EEPROM_OFFSET 30 // Autobind mode, 1 byte per model, end is 30+16=46
-#define AFHDS2A_EEPROM_OFFSET 50 // RX ID, 4 byte per model id, end is 50+64=114
-#define BUGS_EEPROM_OFFSET 114 // RX ID, 4 byte per model id, end is 114+64=178
-//#define CONFIG_EEPROM_OFFSET 178 // Current configuration of the multimodule
-
-//****************************************
-//*** MULTI protocol serial definition ***
-//****************************************
-/*
-**************************
-16 channels serial protocol
-**************************
-Serial: 100000 Baud 8e2 _ xxxx xxxx p --
- Total of 26 bytes
- Stream[0] = 0x55 sub_protocol values are 0..31 Stream contains channels
- Stream[0] = 0x54 sub_protocol values are 32..63 Stream contains channels
- Stream[0] = 0x57 sub_protocol values are 0..31 Stream contains failsafe
- Stream[0] = 0x56 sub_protocol values are 32..63 Stream contains failsafe
- header
- Stream[1] = sub_protocol|BindBit|RangeCheckBit|AutoBindBit;
- sub_protocol is 0..31 (bits 0..4), value should be added with 32 if Stream[0] = 0x54
- => Reserved 0
- Flysky 1
- Hubsan 2
- FrskyD 3
- Hisky 4
- V2x2 5
- DSM 6
- Devo 7
- YD717 8
- KN 9
- SymaX 10
- SLT 11
- CX10 12
- CG023 13
- Bayang 14
- FrskyX 15
- ESky 16
- MT99XX 17
- MJXQ 18
- SHENQI 19
- FY326 20
- SFHSS 21
- J6PRO 22
- FQ777 23
- ASSAN 24
- FrskyV 25
- HONTAI 26
- OpenLRS 27
- AFHDS2A 28
- Q2X2 29
- WK2x01 30
- Q303 31
- GW008 32
- DM002 33
- CABELL 34
- ESKY150 35
- H8_3D 36
- CORONA 37
- CFlie 38
- Hitec 39
- WFLY 40
- BUGS 41
- BindBit=> 0x80 1=Bind/0=No
- AutoBindBit=> 0x40 1=Yes /0=No
- RangeCheck=> 0x20 1=Yes /0=No
- Stream[2] = RxNum | Power | Type;
- RxNum value is 0..15 (bits 0..3)
- Type is 0..7 <<4 (bit 4..6)
- sub_protocol==Flysky
- Flysky 0
- V9x9 1
- V6x6 2
- V912 3
- CX20 4
- sub_protocol==Hubsan
- H107 0
- H301 1
- H501 2
- sub_protocol==Hisky
- Hisky 0
- HK310 1
- sub_protocol==DSM
- DSM2_22 0
- DSM2_11 1
- DSMX_22 2
- DSMX_11 3
- DSM_AUTO 4
- sub_protocol==YD717
- YD717 0
- SKYWLKR 1
- SYMAX4 2
- XINXUN 3
- NIHUI 4
- sub_protocol==KN
- WLTOYS 0
- FEILUN 1
- sub_protocol==SYMAX
- SYMAX 0
- SYMAX5C 1
- sub_protocol==CX10
- CX10_GREEN 0
- CX10_BLUE 1 // also compatible with CX10-A, CX12
- DM007 2
- --- 3
- JC3015_1 4
- JC3015_2 5
- MK33041 6
- sub_protocol==Q2X2
- Q222 0
- Q242 1
- Q282 2
- sub_protocol==CG023
- CG023 0
- YD829 1
- sub_protocol==BAYANG
- BAYANG 0
- H8S3D 1
- X16_AH 2
- IRDRONE 3
- sub_protocol==MT99XX
- MT99 0
- H7 1
- YZ 2
- LS 3
- FY805 4
- sub_protocol==MJXQ
- WLH08 0
- X600 1
- X800 2
- H26D 3
- E010 4
- H26WH 5
- sub_protocol==FRSKYX
- CH_16 0
- CH_8 1
- EU_16 2
- EU_8 3
- sub_protocol==HONTAI
- HONTAI 0
- JJRCX1 1
- X5C1 2
- FQ777_951 3
- sub_protocol==AFHDS2A
- PWM_IBUS 0
- PPM_IBUS 1
- PWM_SBUS 2
- PPM_SBUS 3
- sub_protocol==V2X2
- V2X2 0
- JXD506 1
- sub_protocol==FY326
- FY326 0
- FY319 1
- sub_protocol==WK2x01
- WK2801 0
- WK2401 1
- W6_5_1 2
- W6_6_1 3
- W6_HEL 4
- W6_HEL_I 5
- sub_protocol==Q303
- Q303 0
- CX35 1
- CX10D 2
- CX10WD 3
- sub_protocol==CABELL
- CABELL_V3 0
- CABELL_V3_TELEMETRY 1
- CABELL_SET_FAIL_SAFE 6
- CABELL_UNBIND 7
- sub_protocol==H8_3D
- H8_3D 0
- H20H 1
- H20MINI 2
- H30MINI 3
- sub_protocol==CORONA
- COR_V1 0
- COR_V2 1
- FD_V3 2
- sub_protocol==HITEC
- OPT_FW 0
- OPT_HUB 1
- MINIMA 2
- sub_protocol==SLT
- SLT_V1 0
- SLT_V2 1
- Q100 2
- Q200 3
- MR100 4
-
- Power value => 0x80 0=High/1=Low
- Stream[3] = option_protocol;
- option_protocol value is -128..127
- Stream[4] to [25] = Channels or failsafe depending on Steam[0]
- 16 Channels on 11 bits (0..2047)
- 0 -125%
- 204 -100%
- 1024 0%
- 1843 +100%
- 2047 +125%
- Values are concatenated to fit in 22 bytes like in SBUS protocol.
- Failsafe values have exactly the same range/values than normal channels except the extremes where
- 0=hold, 2047=no pulse. If failsafe is not set or RX then failsafe packets should not be sent.
-*/
-/*
- Multimodule Status
- Based on #define MULTI_STATUS
-
- Serial: 100000 Baud 8e2 (same as input)
-
- Format: header (2 bytes) + data (variable)
- [0] = 'M' (0x4d)
- [1] Length (excluding the 2 header bytes)
- [2-xx] data
-
- Type = 0x01 Multimodule Status:
- [2] Flags
- 0x01 = Input signal detected
- 0x02 = Serial mode enabled
- 0x04 = Protocol is valid
- 0x08 = Module is in binding mode
- 0x10 = Module waits a bind event to load the protocol
- 0x20 = Failsafe supported by currently running protocol
- [3] major
- [4] minor
- [5] revision
- [6] patchlevel,
- version of multi code, should be displayed as major.minor.revision.patchlevel
-*/
-/*
- Multiprotocol telemetry/command definition for OpenTX
- Based on #define MULTI_TELEMETRY enables OpenTX to get the multimodule status and select the correct telemetry type automatically.
-
- Serial: 100000 Baud 8e2 (same as input)
-
- TLV Protocol (type, length, value), allows a TX to ignore unknown messages
-
- Format: header (4 byte) + data (variable)
- [0] = 'M' (0x4d)
- [1] = 'P' (0x50)
-
- The first byte is deliberatly chosen to be different from other telemetry protocols
- (e.g. 0xAA for DSM/Multi, 0xAA for FlySky and 0x7e for Frsky) to allow a TX to detect
- the telemetry format of older versions
-
- [2] Type (see below)
- [3] Length (excluding the 4 header bytes)
-
- [4-xx] data#define EEPROM_BANK_OFFSET 15 // Current bank number (1 byte)
-
-
- Commands from TX to multi cannot be longer than 22 bytes (RXLen -4byte header)
-
- Type = 0x01 Multimodule Status:
- [4] Flags
- 0x01 = Input signal detected
- 0x02 = Serial mode enabled
- 0x04 = protocol is valid
- 0x08 = module is in binding mode
- 0x10 = module waits a bind event to load the protocol
- [5] major
- [6] minor
- [7] revision
- [8] patchlevel,
- version of multi code, should be displayed as major.minor.revision.patchlevel
-
- more information can be added by specifing a longer length of the type, the TX will just ignore these bytes
-
-
- Type 0x02 Frksy S.port telemetry
- Type 0x03 Frsky Hub telemetry
-
- *No* usual frsky byte stuffing and without start/stop byte (0x7e)
-
-
- Type 0x04 Spektrum telemetry data
- data[0] TX RSSI
- data[1-15] telemetry data
-
- Type 0x05 DSM bind data
- data[0-16] DSM bind data
-
- technically DSM bind data is only 10 bytes but multi sends 16
- like with telemtery, check length field)
-
- Type 0x06 Flysky AFHDS2 telemetry data
- length: 29
- data[0] = RSSI value
- data[1-28] telemetry data
-
- Type 0x0A Hitec telemetry data
- length: 8
- data[0] = TX RSSI value
- data[1] = TX LQI value
- data[2] = frame number
- data[3-7] telemetry data
- Full description at the bottom of Hitec_cc2500.ino
-
-*/
#endif
diff --git a/Multiprotocol/Multiprotocol.ino b/Multiprotocol/Multiprotocol.ino
index d1ea344..af1e8c1 100644
--- a/Multiprotocol/Multiprotocol.ino
+++ b/Multiprotocol/Multiprotocol.ino
@@ -22,18 +22,13 @@
*/
-//#define DEBUG_PIN // Use pin TX for AVR and SPI_CS for STM32 => DEBUG_PIN_on, DEBUG_PIN_off, DEBUG_PIN_toggle
#define DEBUG_SERIAL // Only for STM32_BOARD compiled with Upload method "Serial"->usart1, "STM32duino bootloader"->USB serial
-#if defined (ARDUINO_AVR_XMEGA32D4) || defined (ARDUINO_MULTI_ORANGERX)
- #include "MultiOrange.h"
-#endif
#include "config.h"
#include "tx_def.h"
#include "Multiprotocol.h"
-//Multiprotocol module configuration file
#include "pins.h"
#include "Validate.h"
@@ -42,8 +37,8 @@
#include "input.h"
#include "cc2500_spi.h"
-#include "FrSkyX_cc2500.h"
-#include "FrSkyV_cc2500.h"
+//#include "FrSkyX_cc2500.h"
+//#include "FrSkyV_cc2500.h"
#include "FrSkyD_cc2500.h"
//Global constants/variables
@@ -52,13 +47,11 @@ uint32_t MProtocol_id_master;
uint32_t blink=0,last_signal=0;
uint8_t protocol_flags=0,protocol_flags2=0;
//
-uint16_t counter;
uint8_t channel;
uint8_t packet[40];
-// Servo data
-uint16_t Channel_data[NUM_CHN];
-uint8_t Channel_AUX;
+
+uint16_t seed;
// Protocol variables
uint8_t cyrfmfg_id[6];//for dsm2 and devo
@@ -80,7 +73,6 @@ uint8_t throttle, rudder, elevator, aileron;
uint8_t flags;
uint16_t crc;
uint8_t crc8;
-uint16_t seed;
uint16_t failsafe_count;
uint16_t state;
uint8_t len;
@@ -89,18 +81,12 @@ uint8_t len;
uint8_t calData[48];
#endif
-//Channel mapping for protocols
-const uint8_t CH_AETR[]={AILERON, ELEVATOR, THROTTLE, RUDDER, CH5, CH6, CH7, CH8, CH9, CH10, CH11, CH12, CH13, CH14, CH15, CH16};
-const uint8_t CH_TAER[]={THROTTLE, AILERON, ELEVATOR, RUDDER, CH5, CH6, CH7, CH8, CH9, CH10, CH11, CH12, CH13, CH14, CH15, CH16};
-const uint8_t CH_RETA[]={RUDDER, ELEVATOR, THROTTLE, AILERON, CH5, CH6, CH7, CH8, CH9, CH10, CH11, CH12, CH13, CH14, CH15, CH16};
-const uint8_t CH_EATR[]={ELEVATOR, AILERON, THROTTLE, RUDDER, CH5, CH6, CH7, CH8, CH9, CH10, CH11, CH12, CH13, CH14, CH15, CH16};
// Mode_select variables
uint8_t mode_select;
#ifdef ENABLE_PPM
// PPM variable
-volatile uint16_t PPM_data[NUM_CHN];
volatile uint8_t PPM_chan_max=0;
#endif
@@ -115,7 +101,6 @@ uint8_t protocol;
uint8_t option;
uint8_t cur_protocol[3];
uint8_t prev_option;
-uint8_t prev_power=0xFD; // unused power value
uint8_t RX_num;
//Serial RX variables
@@ -136,36 +121,24 @@ void_function_t remote_callback = 0;
void setup()
{
// Setup diagnostic uart before anything else
- #ifdef DEBUG_SERIAL
+ #ifdef ENABLE_DBEUG
Serial.begin(115200,SERIAL_8N1);
while (!Serial); // Wait for ever for the serial port to connect...
debugln("Multiprotocol startup");
debugln("time %s ", __TIME__);
#endif
- // General pinout
- //ATMEGA328p
// all inputs
// outputs
SDI_output;
SCLK_output;
CC25_CSN_output;
- // Timer1 config
- #ifdef TCCR1A
- TCCR1A = 0;
- TCCR1B = (1 << CS11); //prescaler8, set timer1 to increment every 0.5us(16Mhz) and start timer
- #endif
// Random
//random_init();
CC25_CSN_on;
- // Set SPI lines
- #ifdef STM32_BOARD
- initSPI2();
- #else
SDI_on;
SCLK_off;
- #endif
//Wait for every component to start
delay(100);
@@ -217,13 +190,6 @@ void setup()
}
debugln("Protocol selection switch reads as %d", mode_select);
- #ifdef ENABLE_PPM
- uint8_t bank=bank_switch();
- #endif
-
- // Set default channels' value
- InitChannel();
- InitPPM();
// Update LED
LED_off;
LED_output;
@@ -231,18 +197,20 @@ void setup()
//Init RF modules
modules_reset();
- randomSeed(42);
+ {
+ seed = analogRead(PA0);
+ randomSeed(seed);
+ }
// Read or create protocol id
- MProtocol_id_master=random_id(10,false);
+ MProtocol_id_master=random_id(false);
debugln("Module Id: %lx", MProtocol_id_master);
#ifdef ENABLE_PPM
//Protocol and interrupts initialization
- if(mode_select != MODE_SERIAL)
- { // PPM
- uint8_t line=bank*14+mode_select-1;
+ {
+ uint8_t line=curr_bank*14+mode_select-1;
protocol = PPM_prot[line].protocol;
cur_protocol[1] = protocol;
sub_protocol = PPM_prot[line].sub_proto;
@@ -265,8 +233,7 @@ void setup()
debugln("freq offset: %d", option);
if(PPM_prot[line].power)
POWER_FLAG_on;
- if(PPM_prot[line].autobind)
- {
+ if(PPM_prot[line].autobind) {
AUTOBIND_FLAG_on;
BIND_IN_PROGRESS; // Force a bind at protocol startup
}
@@ -274,11 +241,7 @@ void setup()
protocol_init();
- #if defined(TELEMETRY)
- PPM_Telemetry_serial_init();// Configure serial for telemetry
- #endif
}
- else
#endif //ENABLE_PPM
debugln("Init complete");
input.init();
@@ -310,8 +273,15 @@ void loop()
next_callback = remote_callback();
if (next_callback > 4000) {
+ uint32_t s;
+
+ s =micros();
input.update();
- //update_state();
+ debugln("input took %lu", (micros()-s));
+
+ s =micros();
+ update_state();
+ debugln("state took %lu", (micros()-s));
}
uint32_t wait_until = start + next_callback;
@@ -328,47 +298,21 @@ void loop()
}
uint8_t Update_All() {
- #ifdef ENABLE_SERIAL
- if(mode_select==MODE_SERIAL && IS_RX_FLAG_on) // Serial mode and something has been received
- {
- update_serial_data(); // Update protocol and data
- update_channels_aux();
- last_signal=millis();
- }
- #endif //ENABLE_SERIAL
- #ifdef ENABLE_PPM
- if(mode_select!=MODE_SERIAL && IS_PPM_FLAG_on) // PPM mode and a full frame has been received
- {
- debugln("%s:%d",__func__, __LINE__);
- for(uint8_t i=0;iCHANNEL_MAX_125) val=CHANNEL_MAX_125;
- //Channel_data[i]=val;
- }
- PPM_FLAG_off; // wait for next frame before update
- update_channels_aux();
- last_signal=millis();
- }
- #endif //ENABLE_PPM
-
-
+
#ifdef ENABLE_BIND_CH
- if(IS_AUTOBIND_FLAG_on && IS_BIND_CH_PREV_off && Channel_data[BIND_CH-1]>CHANNEL_MAX_COMMAND && Channel_data[THROTTLE]<(CHANNEL_MIN_100+50))
- { // Autobind is on and BIND_CH went up and Throttle is low
+ if(IS_AUTOBIND_FLAG_on &&
+ IS_BIND_CH_PREV_off &&
+ Channel_data[BIND_CH-1] > CHANNEL_MAX_COMMAND &&
+ Channel_data[Input::CH_THROTTLE] < (CHANNEL_MIN_100+50)
+ ) { // Autobind is on and BIND_CH went up and Throttle is low
CHANGE_PROTOCOL_FLAG_on; //reload protocol
BIND_IN_PROGRESS; //enable bind
- debugln("%s:%d set bind prog",__func__, __LINE__);
+ debugln("%s:%d set bind prog",__func__, __LINE__);
BIND_CH_PREV_on;
}
- if(IS_AUTOBIND_FLAG_on && IS_BIND_CH_PREV_on && Channel_data[BIND_CH-1]CHANNEL_SWITCH)
- Channel_AUX|=1<=NBR_BANKS)
- { // Wrong number of bank
- curr_bank = 0; // set bank to 0
- bank=0;
- }
- debugln("Using bank %d", bank);
-
- phase=3;
- uint32_t check=millis();
- blink=millis();
- while(mode_select==15)
- { //loop here if the dial is on position 15 for user to select the bank
- if(blink>2) >= bank)
- {
- phase=0;
- blink+=BLINK_BANK_REPEAT;
- }
- else
- phase+=2;
- break;
- case 3:
- blink+=BLINK_BANK_TIME_LOW;
- phase=0;
- break;
- }
- }
- if(check=NBR_BANKS)
- bank=0;
- curr_bank = bank;
- debugln("Using bank %d", bank);
- phase=3;
- blink+=BLINK_BANK_REPEAT;
- check+=2*BLINK_BANK_REPEAT;
- }
- check+=1;
- }
- }
- return bank;
-}
-#endif
-
-inline void tx_pause()
-{
- #ifdef TELEMETRY
- // Pause telemetry by disabling transmitter interrupt
- #ifdef ORANGE_TX
- USARTC0.CTRLA &= ~0x03 ;
- #else
- #ifndef BASH_SERIAL
- #ifdef STM32_BOARD
- USART3_BASE->CR1 &= ~ USART_CR1_TXEIE;
- #else
- UCSR0B &= ~_BV(UDRIE0);
- #endif
- #endif
- #endif
- #endif
-}
-
-inline void tx_resume()
-{
- #ifdef TELEMETRY
- // Resume telemetry by enabling transmitter interrupt
- #ifndef SPORT_POLLING
- if(!IS_TX_PAUSE_on)
- #endif
- {
- #ifdef ORANGE_TX
- cli() ;
- USARTC0.CTRLA = (USARTC0.CTRLA & 0xFC) | 0x01 ;
- sei() ;
- #else
- #ifndef BASH_SERIAL
- #ifdef STM32_BOARD
- USART3_BASE->CR1 |= USART_CR1_TXEIE;
- #else
- UCSR0B |= _BV(UDRIE0);
- #endif
- #else
- resumeBashSerial();
- #endif
- #endif
- }
- #endif
-}
-
// Protocol start
static void protocol_init() {
static uint16_t next_callback;
@@ -536,10 +348,6 @@ static void protocol_init() {
MProtocol_id = RX_num + MProtocol_id_master;
set_rx_tx_addr(MProtocol_id);
- #ifdef FAILSAFE_ENABLE
- InitFailsafe();
- #endif
-
blink=millis();
debugln("Protocol selected: %d, sub proto %d, rxnum %d, option %d", protocol, sub_protocol, RX_num, option);
@@ -550,20 +358,12 @@ static void protocol_init() {
next_callback = initFrSky_2way();
remote_callback = ReadFrSky_2way;
break;
- case PROTO_FRSKYV:
- next_callback = initFRSKYV();
- remote_callback = ReadFRSKYV;
- break;
- case PROTO_FRSKYX:
- next_callback = initFrSkyX();
- remote_callback = ReadFrSkyX;
- break;
}
}
#if defined(WAIT_FOR_BIND) && defined(ENABLE_BIND_CH)
- if( IS_AUTOBIND_FLAG_on && IS_BIND_CH_PREV_off && (cur_protocol[1]&0x80)==0 && mode_select == MODE_SERIAL)
- { // Autobind is active but no bind requested by either BIND_CH or BIND. But do not wait if in PPM mode...
+ if( IS_AUTOBIND_FLAG_on && IS_BIND_CH_PREV_off && (cur_protocol[1]&0x80)==0 && mode_select == MODE_SERIAL) {
+ // Autobind is active but no bind requested by either BIND_CH or BIND. But do not wait if in PPM mode...
WAIT_BIND_on;
return;
}
@@ -577,74 +377,36 @@ static void protocol_init() {
void update_serial_data()
{
- RX_DONOTUPDATE_on;
- RX_FLAG_off; //data is being processed
- #ifdef SAMSON // Extremely dangerous, do not enable this unless you know what you are doing...
- if( rx_ok_buff[0]==0x55 && (rx_ok_buff[1]&0x1F)==PROTO_FRSKYD && rx_ok_buff[2]==0x7F && rx_ok_buff[24]==217 && rx_ok_buff[25]==202 )
- {//proto==FRSKYD+sub==7+rx_num==7+CH15==73%+CH16==73%
- rx_ok_buff[1]=(rx_ok_buff[1]&0xE0) | PROTO_FLYSKY; // change the protocol to Flysky
- memcpy((void*)(rx_ok_buff+4),(void*)(rx_ok_buff+4+11),11); // reassign channels 9-16 to 1-8
- }
- #endif
if(rx_ok_buff[1]&0x20) //check range
RANGE_FLAG_on;
else
RANGE_FLAG_off;
+
if(rx_ok_buff[1]&0x40) //check autobind
AUTOBIND_FLAG_on;
else
AUTOBIND_FLAG_off;
+
if(rx_ok_buff[2]&0x80) //if rx_ok_buff[2] ==1,power is low ,0-power high
POWER_FLAG_off; //power low
else
POWER_FLAG_on; //power high
//Forced frequency tuning values for CC2500 protocols
- #if defined(FORCE_FRSKYD_TUNING) && defined(FRSKYD_CC2500_INO)
+ #if defined(FORCE_FRSKYD_TUNING)
if(protocol==PROTO_FRSKYD)
option=FORCE_FRSKYD_TUNING; // Use config-defined tuning value for FrSkyD
else
- #endif
- #if defined(FORCE_FRSKYV_TUNING) && defined(FRSKYV_CC2500_INO)
- if(protocol==PROTO_FRSKYV)
- option=FORCE_FRSKYV_TUNING; // Use config-defined tuning value for FrSkyV
- else
- #endif
- #if defined(FORCE_FRSKYX_TUNING) && defined(FRSKYX_CC2500_INO)
- if(protocol==PROTO_FRSKYX)
- option=FORCE_FRSKYX_TUNING; // Use config-defined tuning value for FrSkyX
- else
- #endif
- #if defined(FORCE_SFHSS_TUNING) && defined(SFHSS_CC2500_INO)
- if (protocol==PROTO_SFHSS)
- option=FORCE_SFHSS_TUNING; // Use config-defined tuning value for SFHSS
- else
- #endif
- #if defined(FORCE_CORONA_TUNING) && defined(CORONA_CC2500_INO)
- if (protocol==PROTO_CORONA)
- option=FORCE_CORONA_TUNING; // Use config-defined tuning value for CORONA
- else
- #endif
- #if defined(FORCE_HITEC_TUNING) && defined(HITEC_CC2500_INO)
- if (protocol==PROTO_HITEC)
- option=FORCE_HITEC_TUNING; // Use config-defined tuning value for HITEC
- else
#endif
option=rx_ok_buff[3]; // Use radio-defined option value
#ifdef FAILSAFE_ENABLE
bool failsafe=false;
- if(rx_ok_buff[0]&0x02)
- { // Packet contains failsafe instead of channels
+ if(rx_ok_buff[0]&0x02) { // Packet contains failsafe instead of channels
failsafe=true;
rx_ok_buff[0]&=0xFD; //remove the failsafe flag
- FAILSAFE_VALUES_on; //failsafe data has been received
}
#endif
- #ifdef BONI
- if(CH14_SW)
- rx_ok_buff[2]=(rx_ok_buff[2]&0xF0)|((rx_ok_buff[2]+1)&0x0F); // Extremely dangerous, do not enable this!!! This is really for a special case...
- #endif
if( (rx_ok_buff[0] != cur_protocol[0]) || ((rx_ok_buff[1]&0x5F) != (cur_protocol[1]&0x5F)) || ( (rx_ok_buff[2]&0x7F) != (cur_protocol[2]&0x7F) ) )
{ // New model has been selected
CHANGE_PROTOCOL_FLAG_on; //change protocol
@@ -656,14 +418,11 @@ void update_serial_data()
protocol=(rx_ok_buff[0]==0x55?0:32) + (rx_ok_buff[1]&0x1F); //protocol no (0-63) bits 4-6 of buff[1] and bit 0 of buf[0]
sub_protocol=(rx_ok_buff[2]>>4)& 0x07; //subprotocol no (0-7) bits 4-6
RX_num=rx_ok_buff[2]& 0x0F; // rx_num bits 0---3
- }
- else
- if( ((rx_ok_buff[1]&0x80)!=0) && ((cur_protocol[1]&0x80)==0) ) // Bind flag has been set
+ } else if( ((rx_ok_buff[1]&0x80)!=0) && ((cur_protocol[1]&0x80)==0) ) // Bind flag has been set
{ // Restart protocol with bind
CHANGE_PROTOCOL_FLAG_on;
BIND_IN_PROGRESS;
- }
- else
+ } else {
if( ((rx_ok_buff[1]&0x80)==0) && ((cur_protocol[1]&0x80)!=0) ) // Bind flag has been reset
{ // Request protocol to end bind
#if defined(FRSKYD_CC2500_INO) || defined(FRSKYX_CC2500_INO) || defined(FRSKYV_CC2500_INO)
@@ -674,6 +433,7 @@ void update_serial_data()
if(bind_counter>2)
bind_counter=2;
}
+ }
//store current protocol values
for(uint8_t i=0;i<3;i++)
@@ -682,104 +442,35 @@ void update_serial_data()
// decode channel/failsafe values
volatile uint8_t *p=rx_ok_buff+3;
uint8_t dec=-3;
- for(uint8_t i=0;i=8)
- {
+ if(dec>=8) {
dec-=8;
p++;
}
p++;
uint16_t temp=((*((uint32_t *)p))>>dec)&0x7FF;
- #ifdef FAILSAFE_ENABLE
if(failsafe)
Failsafe_data[i]=temp; //value range 0..2047, 0=no pulses, 2047=hold
else
- #endif
Channel_data[i]=temp; //value range 0..2047, 0=-125%, 2047=+125%
}
- RX_DONOTUPDATE_off;
cli();
if(IS_RX_MISSED_BUFF_on) // If the buffer is still valid
{ memcpy((void*)rx_ok_buff,(const void*)rx_buff,RXBUFFER_SIZE);// Duplicate the buffer
- RX_FLAG_on; // data to be processed next time...
RX_MISSED_BUFF_off;
}
sei();
- #ifdef FAILSAFE_ENABLE
- if(failsafe)
- debugln("RX_FS:%d,%d,%d,%d",Failsafe_data[0],Failsafe_data[1],Failsafe_data[2],Failsafe_data[3]);
- #endif
}
void modules_reset()
{
- #ifdef CC2500_INSTALLED
- CC2500_Reset();
- #endif
- #ifdef A7105_INSTALLED
- A7105_Reset();
- #endif
- #ifdef CYRF6936_INSTALLED
- CYRF_Reset();
- #endif
- #ifdef NRF24L01_INSTALLED
- NRF24L01_Reset();
- #endif
+ CC2500_Reset();
//Wait for every component to reset
delay(100);
- prev_power=0xFD; // unused power value
}
-#ifdef STM32_BOARD
- void usart2_begin(uint32_t baud,uint32_t config )
- {
- usart_init(USART2);
- usart_config_gpios_async(USART2,GPIOA,PIN_MAP[PA3].gpio_bit,GPIOA,PIN_MAP[PA2].gpio_bit,config);
- LED2_output;
- usart_set_baud_rate(USART2, STM32_PCLK1, baud);
- usart_enable(USART2);
- }
- void usart3_begin(uint32_t baud,uint32_t config )
- {
- usart_init(USART3);
- usart_config_gpios_async(USART3,GPIOB,PIN_MAP[PB11].gpio_bit,GPIOB,PIN_MAP[PB10].gpio_bit,config);
- usart_set_baud_rate(USART3, STM32_PCLK1, baud);
- usart_enable(USART3);
- }
- void init_HWTimer()
- {
- HWTimer2.pause(); // Pause the timer2 while we're configuring it
-
- TIMER2_BASE->PSC = 35; // 36-1;for 72 MHZ /0.5sec/(35+1)
- TIMER2_BASE->ARR = 0xFFFF; // Count until 0xFFFF
-
- HWTimer2.setMode(TIMER_CH1, TIMER_OUTPUT_COMPARE); // Main scheduler
- HWTimer2.setMode(TIMER_CH2, TIMER_OUTPUT_COMPARE); // Serial check
-
- TIMER2_BASE->SR = 0x1E5F & ~TIMER_SR_CC2IF; // Clear Timer2/Comp2 interrupt flag
- HWTimer2.attachInterrupt(TIMER_CH2,ISR_COMPB); // Assign function to Timer2/Comp2 interrupt
- TIMER2_BASE->DIER &= ~TIMER_DIER_CC2IE; // Disable Timer2/Comp2 interrupt
-
- HWTimer2.refresh(); // Refresh the timer's count, prescale, and overflow
- HWTimer2.resume();
- }
-#endif
-
-#if defined(TELEMETRY)
-void PPM_Telemetry_serial_init()
-{
- if( (protocol==PROTO_FRSKYD))
- initTXSerial( SPEED_9600 ) ;
- if(protocol==PROTO_FRSKYX)
- initTXSerial( SPEED_57600 ) ;
- if(protocol==PROTO_DSM)
- initTXSerial( SPEED_125K ) ;
-}
-#endif
-
// Convert 32b id to rx_tx_addr
void set_rx_tx_addr(uint32_t id)
{ // Used by almost all protocols
@@ -790,18 +481,19 @@ void set_rx_tx_addr(uint32_t id)
rx_tx_addr[4] = (rx_tx_addr[2]&0xF0)|(rx_tx_addr[3]&0x0F);
}
-uint32_t random_id(uint16_t address, uint8_t create_new)
+uint32_t random_id(bool create_new)
{
- #ifndef FORCE_GLOBAL_ID
+ #ifdef FORCE_GLOBAL_ID
+ (void)create_new;
+ return FORCE_GLOBAL_ID;
+ #else
uint32_t id=0;
- #if 0
- //(eeprom_read_byte((EE_ADDR)(address+10))==0xf0 && !create_new)
- { // TXID exists in EEPROM
- for(uint8_t i=4;i>0;i--)
- {
+ if (eeprom_read_byte((EE_ADDR)(10))==0xf0 && !create_new) {
+ // TXID exists in EEPROM
+ for(uint8_t i=4;i>0;i--) {
id<<=8;
- id|=eeprom_read_byte((EE_ADDR)address+i-1);
+ id|=eeprom_read_byte((EE_ADDR)i-1);
}
if(id!=0x2AD141A7) //ID with seed=0
{
@@ -809,18 +501,14 @@ uint32_t random_id(uint16_t address, uint8_t create_new)
return id;
}
}
- // Generate a random ID
- #if defined STM32_BOARD
+ // Generate a random ID from UUID
#define STM32_UUID ((uint32_t *)0x1FFFF7E8)
- if (!create_new)
- {
+ if (!create_new) {
id = STM32_UUID[0] ^ STM32_UUID[1] ^ STM32_UUID[2];
- debugln("Generated ID from STM32 UUID");
+ debugln("Generated ID from STM32 UUID %x", id);
+ } else {
+ id = random(0xfefefefe) + ((uint32_t)random(0xfefefefe) << 16);
}
- else
- #endif
- #endif
- id = random(0xfefefefe) + ((uint32_t)random(0xfefefefe) << 16);
#if 0
for(uint8_t i=0;i<4;i++)
@@ -828,166 +516,6 @@ uint32_t random_id(uint16_t address, uint8_t create_new)
eeprom_write_byte((EE_ADDR)(address+10),0xf0);//write bind flag in eeprom.
#endif
return id;
- #else
- (void)address;
- (void)create_new;
- return FORCE_GLOBAL_ID;
- #endif
-}
-
-/**************************/
-/**************************/
-/** Interrupt routines **/
-/**************************/
-/**************************/
-
-//PPM
-#ifdef blubber // ENABLE_PPM
- #ifdef ORANGE_TX
- #if PPM_pin == 2
- ISR(PORTD_INT0_vect)
- #else
- ISR(PORTD_INT1_vect)
- #endif
- #elif defined STM32_BOARD
- void PPM_decode()
- #else
- #if PPM_pin == 2
- ISR(INT0_vect, ISR_NOBLOCK)
- #else
- ISR(INT1_vect, ISR_NOBLOCK)
- #endif
- #endif
- { // Interrupt on PPM pin
- static int8_t chan=0,bad_frame=1;
- static uint16_t Prev_TCNT1=0;
- uint16_t Cur_TCNT1;
-
- Cur_TCNT1 = TCNT1 - Prev_TCNT1 ; // Capture current Timer1 value
- if(Cur_TCNT1<1600)
- bad_frame=1; // bad frame
- else
- if(Cur_TCNT1>4400)
- { //start of frame
- if(chan>=MIN_PPM_CHANNELS)
- {
- PPM_FLAG_on; // good frame received if at least 4 channels have been seen
- if(chan>PPM_chan_max) PPM_chan_max=chan; // Saving the number of channels received
- }
- chan=0; // reset channel counter
- bad_frame=0;
- }
- else
- if(bad_frame==0) // need to wait for start of frame
- { //servo values between 800us and 2200us will end up here
- PPM_data[chan]=Cur_TCNT1;
- if(chan++>=MAX_PPM_CHANNELS)
- bad_frame=1; // don't accept any new channels
- }
- Prev_TCNT1+=Cur_TCNT1;
- }
-#endif //ENABLE_PPM
-
-//Serial RX
-#ifdef ENABLE_SERIAL
- #ifdef ORANGE_TX
- ISR(USARTC0_RXC_vect)
- #elif defined STM32_BOARD
- void __irq_usart2()
- #else
- ISR(USART_RX_vect)
#endif
- { // RX interrupt
- static uint8_t idx=0;
- #ifdef ORANGE_TX
- if((USARTC0.STATUS & 0x1C)==0) // Check frame error, data overrun and parity error
- #elif defined STM32_BOARD
- if((USART2_BASE->SR & USART_SR_RXNE) && (USART2_BASE->SR &0x0F)==0)
- #else
- UCSR0B &= ~_BV(RXCIE0) ; // RX interrupt disable
- sei() ;
- if((UCSR0A&0x1C)==0) // Check frame error, data overrun and parity error
- #endif
- { // received byte is ok to process
- if(idx==0||discard_frame==1)
- { // Let's try to sync at this point
- idx=0;discard_frame=0;
- RX_MISSED_BUFF_off; // If rx_buff was good it's not anymore...
- rx_buff[0]=UDR0;
- #ifdef FAILSAFE_ENABLE
- if((rx_buff[0]&0xFC)==0x54) // If 1st byte is 0x54, 0x55, 0x56 or 0x57 it looks ok
- #else
- if((rx_buff[0]&0xFE)==0x54) // If 1st byte is 0x54 or 0x55 it looks ok
- #endif
- {
- TX_RX_PAUSE_on;
- tx_pause();
- #if defined STM32_BOARD
- TIMER2_BASE->CCR2=TIMER2_BASE->CNT+(6500L); // Full message should be received within timer of 3250us
- TIMER2_BASE->SR = 0x1E5F & ~TIMER_SR_CC2IF; // Clear Timer2/Comp2 interrupt flag
- TIMER2_BASE->DIER |= TIMER_DIER_CC2IE; // Enable Timer2/Comp2 interrupt
- #else
- OCR1B = TCNT1+(6500L) ; // Full message should be received within timer of 3250us
- TIFR1 = OCF1B_bm ; // clear OCR1B match flag
- SET_TIMSK1_OCIE1B ; // enable interrupt on compare B match
- #endif
- idx++;
- }
- }
- else
- {
- rx_buff[idx++]=UDR0; // Store received byte
- if(idx>=RXBUFFER_SIZE)
- { // A full frame has been received
- if(!IS_RX_DONOTUPDATE_on)
- { //Good frame received and main is not working on the buffer
- memcpy((void*)rx_ok_buff,(const void*)rx_buff,RXBUFFER_SIZE);// Duplicate the buffer
- RX_FLAG_on; // flag for main to process servo data
- }
- else
- RX_MISSED_BUFF_on; // notify that rx_buff is good
- discard_frame=1; // start again
- }
- }
- }
- else
- {
- idx=UDR0; // Dummy read
- discard_frame=1; // Error encountered discard full frame...
- debugln("Bad frame RX");
- }
- if(discard_frame==1)
- {
- #ifdef STM32_BOARD
- TIMER2_BASE->DIER &= ~TIMER_DIER_CC2IE; // Disable Timer2/Comp2 interrupt
- #else
- CLR_TIMSK1_OCIE1B; // Disable interrupt on compare B match
- #endif
- TX_RX_PAUSE_off;
- tx_resume();
- }
- #if not defined (ORANGE_TX) && not defined (STM32_BOARD)
- cli() ;
- UCSR0B |= _BV(RXCIE0) ; // RX interrupt enable
- #endif
- }
- //Serial timer
- #ifdef ORANGE_TX
- ISR(TCC1_CCB_vect)
- #elif defined STM32_BOARD
- void ISR_COMPB()
- #else
- ISR(TIMER1_COMPB_vect, ISR_NOBLOCK )
- #endif
- { // Timer1 compare B interrupt
- discard_frame=1;
- #ifdef STM32_BOARD
- TIMER2_BASE->DIER &= ~TIMER_DIER_CC2IE; // Disable Timer2/Comp2 interrupt
- debugln("Bad frame timer");
- #else
- CLR_TIMSK1_OCIE1B; // Disable interrupt on compare B match
- #endif
- tx_resume();
- }
-#endif //ENABLE_SERIAL
+}
diff --git a/Multiprotocol/Validate.h b/Multiprotocol/Validate.h
index 6699eb3..6969b55 100644
--- a/Multiprotocol/Validate.h
+++ b/Multiprotocol/Validate.h
@@ -3,69 +3,6 @@
#include "config.h"
#include "tx_def.h"
-// Check selected board type
-#if defined (STM32_BOARD) && defined (ORANGE_TX)
- #error You must comment the board type STM32_BOARD in _Config.h to compile ORANGE_TX
-#endif
-#if not defined (ORANGE_TX) && not defined (STM32_BOARD)
- //Atmega328p
- #if (not defined(ARDUINO_AVR_PRO) && not defined(ARDUINO_AVR_LEONARDO) )&& not defined(ARDUINO_MULTI_NO_BOOT) && not defined(ARDUINO_MULTI_FLASH_FROM_TX) && not defined(ARDUINO_AVR_MINI) && not defined(ARDUINO_AVR_NANO)
- #warning You must select one of these boards: "Multi 4-in-1", "Arduino Pro or Pro Mini" or "Arduino Mini"
- #endif
- #if F_CPU != 16000000L || not defined(__AVR_ATmega328P__) || not defined(__AVR_ATmega32U4__)
- #warning You must select the processor type "ATmega328(5V, 16MHz)"
- #endif
-#endif
-#if defined (STM32_BOARD) && not defined (ORANGE_TX)
- //STM32
- #if not defined(ARDUINO_GENERIC_STM32F103C) && not defined(ARDUINO_MULTI_STM32_FLASH_FROM_TX) && not defined(ARDUINO_MULTI_STM32_NO_BOOT) && not defined(ARDUINO_MULTI_STM32_WITH_BOOT)
- #error You must select one of these boards: "Multi 4-in-1 (STM32F103CB)" or "Generic STM32F103C series"
- #endif
-#endif
-
-// Check for minimum version of multi-module boards
-#define MIN_AVR_BOARD 103
-#define MIN_ORX_BOARD 103
-#define MIN_STM32_BOARD 104
-//AVR
-#if (defined(ARDUINO_MULTI_NO_BOOT) && ARDUINO_MULTI_NO_BOOT < MIN_AVR_BOARD) || (defined(ARDUINO_MULTI_FLASH_FROM_TX) && ARDUINO_MULTI_FLASH_FROM_TX < MIN_AVR_BOARD)
- #error You need to update your Multi 4-in-1 board definition. Open Boards Manager and update to the latest version of the Multi 4-in-1 AVR Boards.
-#endif
-//OrangeRX
-#if (defined(ARDUINO_MULTI_ORANGERX) && ARDUINO_MULTI_ORANGERX < MIN_ORX_BOARD)
- #error You need to update your Multi 4-in-1 board definition. Open Boards Manager and update to the latest version of the Multi 4-in-1 AVR Boards.
-#endif
-//STM32
-#if (defined(ARDUINO_MULTI_STM32_NO_BOOT) && ARDUINO_MULTI_STM32_NO_BOOT < MIN_STM32_BOARD) || (defined(ARDUINO_MULTI_STM32_FLASH_FROM_TX) && ARDUINO_MULTI_STM32_FLASH_FROM_TX < MIN_STM32_BOARD) || (defined(ARDUINO_MULTI_STM32_WITH_BOOT) && ARDUINO_MULTI_STM32_WITH_BOOT < MIN_STM32_BOARD)
- #error You need to update your Multi 4-in-1 board definition. Open Boards Manager and update to the latest version of the Multi 4-in-1 STM32 Board.
-#endif
-
-// Error if CHECK_FOR_BOOTLOADER is not enabled but a FLASH_FROM_TX board is selected
-#if (defined(ARDUINO_MULTI_FLASH_FROM_TX) || defined(ARDUINO_MULTI_STM32_FLASH_FROM_TX)) &! defined(CHECK_FOR_BOOTLOADER)
- #if defined(STM32_BOARD)
- #error "You have selected the 'Flash from TX' upload method but not enabled CHECK_FOR_BOOTLOADER."
- #else
- #error "You have selected the 'Flash from TX' bootloader but not enabled CHECK_FOR_BOOTLOADER."
- #endif
-#endif
-
-// Error if CHECK_FOR_BOOTLOADER is enabled but the 'Flash from TX' bootloader
-#if defined(ARDUINO_MULTI_NO_BOOT) && defined(CHECK_FOR_BOOTLOADER)
- #error "You have enabled CHECK_FOR_BOOTLOADER but not selected the 'Flash from TX' bootloader."
-#endif
-
-//Check number of banks
-#if NBR_BANKS < 1 || NBR_BANKS > 5
- #error "You need to select a number of banks between 1 and 5."
-#endif
-
-//Check failsafe throttle value
-#ifdef FAILSAFE_ENABLE
- #if ( FAILSAFE_THROTTLE_LOW < -125 ) || ( FAILSAFE_THROTTLE_LOW > 125 )
- #error "The failsafe value for throttle is outside of the range -125..125."
- #endif
-#endif
-
// Check forced tuning values are valid
#ifdef FORCE_FRSKYD_TUNING
#if ( FORCE_FRSKYD_TUNING < -127 ) || ( FORCE_FRSKYD_TUNING > 127 )
@@ -82,179 +19,7 @@
#error "The FrSkyX forced frequency tuning value is outside of the range -127..127."
#endif
#endif
-#ifdef FORCE_SFHSS_TUNING
- #if ( FORCE_SFHSS_TUNING < -127 ) || ( FORCE_SFHSS_TUNING > 127 )
- #error "The SFHSS forced frequency tuning value is outside of the range -127..127."
- #endif
-#endif
-#ifdef FORCE_CORONA_TUNING
- #if ( FORCE_CORONA_TUNING < -127 ) || ( FORCE_CORONA_TUNING > 127 )
- #error "The CORONA forced frequency tuning value is outside of the range -127..127."
- #endif
-#endif
-#ifdef FORCE_HITEC_TUNING
- #if ( FORCE_HITEC_TUNING < -127 ) || ( FORCE_HITEC_TUNING > 127 )
- #error "The HITEC forced frequency tuning value is outside of the range -127..127."
- #endif
-#endif
-#ifdef FORCE_FLYSKY_TUNING
- #if ( FORCE_FLYSKY_TUNING < -300 ) || ( FORCE_FLYSKY_TUNING > 300 )
- #error "The Flysky forced frequency tuning value is outside of the range -300..300."
- #endif
-#endif
-#ifdef FORCE_HUBSAN_TUNING
- #if ( FORCE_HUBSAN_TUNING < -300 ) || ( FORCE_HUBSAN_TUNING > 300 )
- #error "The Hubsan forced frequency tuning value is outside of the range -300..300."
- #endif
-#endif
-#ifdef FORCE_AFHDS2A_TUNING
- #if ( FORCE_AFHDS2A_TUNING < -300 ) || ( FORCE_AFHDS2A_TUNING > 300 )
- #error "The AFHDS2A forced frequency tuning value is outside of the range -300..300."
- #endif
-#endif
-#ifndef USE_A7105_CH15_TUNING
- #ifndef FORCE_FLYSKY_TUNING
- #define FORCE_FLYSKY_TUNING 0
- #endif
- #ifndef FORCE_HUBSAN_TUNING
- #define FORCE_HUBSAN_TUNING 0
- #endif
- #ifndef FORCE_AFHDS2A_TUNING
- #define FORCE_AFHDS2A_TUNING 0
- #endif
-#endif
-
-//Change/Force configuration if OrangeTX
-#ifdef ORANGE_TX
- #undef ENABLE_PPM // Disable PPM for OrangeTX module
- #undef A7105_INSTALLED // Disable A7105 for OrangeTX module
- #undef A7105_CSN_pin
- #undef CC2500_INSTALLED // Disable CC2500 for OrangeTX module
- #undef CC25_CSN_pin
- #undef NRF24L01_INSTALLED // Disable NRF for OrangeTX module
- #undef NRF_CSN_pin
- #define TELEMETRY // Enable telemetry
- #define INVERT_TELEMETRY // Enable invert telemetry
- #define DSM_TELEMETRY // Enable DSM telemetry
-#endif
-
-//Make sure protocols are selected correctly
-#ifndef A7105_INSTALLED
- #undef FLYSKY_A7105_INO
- #undef HUBSAN_A7105_INO
- #undef AFHDS2A_A7105_INO
- #undef BUGS_A7105_INO
-#endif
-#ifndef CYRF6936_INSTALLED
- #undef DEVO_CYRF6936_INO
- #undef DSM_CYRF6936_INO
- #undef J6PRO_CYRF6936_INO
- #undef WFLY_CYRF6936_INO
- #undef WK2x01_CYRF6936_INO
-#endif
-#ifndef CC2500_INSTALLED
- #undef FRSKYD_CC2500_INO
- #undef FRSKYV_CC2500_INO
- #undef FRSKYX_CC2500_INO
- #undef SFHSS_CC2500_INO
- #undef CORONA_CC2500_INO
- #undef HITEC_CC2500_INO
-#endif
-#ifndef NRF24L01_INSTALLED
- #undef BAYANG_NRF24L01_INO
- #undef CG023_NRF24L01_INO
- #undef CX10_NRF24L01_INO
- #undef ESKY_NRF24L01_INO
- #undef HISKY_NRF24L01_INO
- #undef KN_NRF24L01_INO
- #undef SLT_NRF24L01_INO
- #undef SYMAX_NRF24L01_INO
- #undef V2X2_NRF24L01_INO
- #undef YD717_NRF24L01_INO
- #undef MT99XX_NRF24L01_INO
- #undef MJXQ_NRF24L01_INO
- #undef SHENQI_NRF24L01_INO
- #undef FY326_NRF24L01_INO
- #undef FQ777_NRF24L01_INO
- #undef ASSAN_NRF24L01_INO
- #undef HONTAI_NRF24L01_INO
- #undef Q303_NRF24L01_INO
- #undef GW008_NRF24L01_INO
- #undef DM002_NRF24L01_INO
- #undef CABELL_NRF24L01_INO
- #undef ESKY150_NRF24L01_INO
- #undef H8_3D_NRF24L01_INO
- #undef CFLIE_NRF24L01_INO
-#endif
-
-//Make sure telemetry is selected correctly
-#ifndef TELEMETRY
- #undef INVERT_TELEMETRY
- #undef AFHDS2A_FW_TELEMETRY
- #undef AFHDS2A_HUB_TELEMETRY
- #undef HITEC_FW_TELEMETRY
- #undef HITEC_HUB_TELEMETRY
- #undef BAYANG_HUB_TELEMETRY
- #undef CABELL_HUB_TELEMETRY
- #undef HUBSAN_HUB_TELEMETRY
- #undef BUGS_HUB_TELEMETRY
- #undef HUB_TELEMETRY
- #undef SPORT_TELEMETRY
- #undef SPORT_POLLING
- #undef DSM_TELEMETRY
- #undef MULTI_STATUS
- #undef MULTI_TELEMETRY
-#else
- #if defined MULTI_TELEMETRY && not defined INVERT_TELEMETRY
- #warning MULTI_TELEMETRY has been defined but not INVERT_TELEMETRY. They should be both enabled for OpenTX telemetry and status to work.
- #endif
- #if not defined(BAYANG_NRF24L01_INO)
- #undef BAYANG_HUB_TELEMETRY
- #endif
- #if not defined(CABELL_NRF24L01_INO)
- #undef CABELL_HUB_TELEMETRY
- #endif
- #if not defined(HUBSAN_A7105_INO)
- #undef HUBSAN_HUB_TELEMETRY
- #endif
- #if not defined(AFHDS2A_A7105_INO)
- #undef AFHDS2A_HUB_TELEMETRY
- #undef AFHDS2A_FW_TELEMETRY
- #endif
- #if not defined(HITEC_CC2500_INO)
- #undef HITEC_HUB_TELEMETRY
- #undef HITEC_FW_TELEMETRY
- #endif
- #if not defined(FRSKYD_CC2500_INO)
- #undef HUB_TELEMETRY
- #endif
- #if not defined(FRSKYX_CC2500_INO)
- #undef SPORT_TELEMETRY
- #undef SPORT_POLLING
- #endif
- #if not defined (SPORT_TELEMETRY) || not defined (STM32_BOARD)
- #undef SPORT_POLLING
- #endif
- #if defined SPORT_POLLING && not defined INVERT_TELEMETRY
- #error SPORT_POLLING has been defined but not INVERT_TELEMETRY. They should be both enabled to work.
- #endif
- #if not defined(DSM_CYRF6936_INO)
- #undef DSM_TELEMETRY
- #endif
- #if not defined(DSM_TELEMETRY) && not defined(SPORT_TELEMETRY) && not defined(HUB_TELEMETRY) && not defined(HUBSAN_HUB_TELEMETRY) && not defined(BUGS_HUB_TELEMETRY) && not defined(BAYANG_HUB_TELEMETRY) && not defined(CABELL_HUB_TELEMETRY) && not defined(AFHDS2A_HUB_TELEMETRY) && not defined(AFHDS2A_FW_TELEMETRY) && not defined(MULTI_TELEMETRY) && not defined(MULTI_STATUS) && not defined(HITEC_HUB_TELEMETRY) && not defined(HITEC_FW_TELEMETRY)
- #undef TELEMETRY
- #undef INVERT_TELEMETRY
- #undef SPORT_POLLING
- #endif
-#endif
-//Make sure TX is defined correctly
-#ifndef AILERON
- #error You must select a correct channel order.
-#endif
-#if not defined(PPM_MAX_100) || not defined(PPM_MIN_100)
- #error You must set correct PPM end points for your TX.
-#endif
#if defined(ENABLE_BIND_CH)
#if BIND_CH<4
@@ -265,17 +30,4 @@
#endif
#endif
-#if MIN_PPM_CHANNELS>16
- #error MIN_PPM_CHANNELS must be below or equal to 16. The default for this value is 4.
-#endif
-#if MIN_PPM_CHANNELS<2
- #error MIN_PPM_CHANNELS must be larger than 1. The default for this value is 4.
-#endif
-#if MAX_PPM_CHANNELS16
- #error MAX_PPM_CHANNELS must be below or equal to 16. The default for this value is 16.
-#endif
-
#endif
diff --git a/Multiprotocol/cc2500_spi.cpp b/Multiprotocol/cc2500_spi.cpp
index f72df9a..35fa423 100644
--- a/Multiprotocol/cc2500_spi.cpp
+++ b/Multiprotocol/cc2500_spi.cpp
@@ -23,6 +23,7 @@
#include "cc2500_spi.h"
#include "spi.h"
+uint8_t prev_power=0xFD; // unused power value
void CC2500_WriteReg(uint8_t address, uint8_t data)
{
CC25_CSN_off;
@@ -85,14 +86,12 @@ void CC2500_SetTxRxMode(uint8_t mode)
//from deviation firmware
CC2500_WriteReg(CC2500_00_IOCFG2, 0x2F);
CC2500_WriteReg(CC2500_02_IOCFG0, 0x2F | 0x40);
- } else {
- if (mode == RX_EN) {
+ } else if (mode == RX_EN) {
CC2500_WriteReg(CC2500_02_IOCFG0, 0x2F);
CC2500_WriteReg(CC2500_00_IOCFG2, 0x2F | 0x40);
- } else {
+ } else {
CC2500_WriteReg(CC2500_02_IOCFG0, 0x2F);
CC2500_WriteReg(CC2500_00_IOCFG2, 0x2F);
- }
}
}
uint8_t CC2500_Reset()
@@ -100,21 +99,22 @@ uint8_t CC2500_Reset()
CC2500_Strobe(CC2500_SRES);
delay(1);
CC2500_SetTxRxMode(TXRX_OFF);
+ prev_power=0xFD; // unused power value
return CC2500_ReadReg(CC2500_0E_FREQ1) == 0xC4;//check if reset
}
void CC2500_SetPower()
{
uint8_t power=CC2500_BIND_POWER;
- if(IS_BIND_DONE)
+ if(IS_BIND_DONE) {
#ifdef CC2500_ENABLE_LOW_POWER
power=IS_POWER_FLAG_on?CC2500_HIGH_POWER:CC2500_LOW_POWER;
#else
power=CC2500_HIGH_POWER;
#endif
+ }
if(IS_RANGE_FLAG_on)
power=CC2500_RANGE_POWER;
- if(prev_power != power)
- {
+ if(prev_power != power) {
CC2500_WriteReg(CC2500_3E_PATABLE, power);
prev_power=power;
}
diff --git a/Multiprotocol/cc2500_spi.h b/Multiprotocol/cc2500_spi.h
index 8123e87..0d452b7 100644
--- a/Multiprotocol/cc2500_spi.h
+++ b/Multiprotocol/cc2500_spi.h
@@ -160,4 +160,37 @@ enum {
#define CC2500_LQI_CRC_OK_BM 0x80
#define CC2500_LQI_EST_BM 0x7F
+// CC2500 power output from the chip itself
+// The numbers do not take into account any outside amplifier
+enum CC2500_POWER
+{
+ CC2500_POWER_0 = 0x00, // -55dbm or less
+ CC2500_POWER_1 = 0x50, // -30dbm
+ CC2500_POWER_2 = 0x44, // -28dbm
+ CC2500_POWER_3 = 0xC0, // -26dbm
+ CC2500_POWER_4 = 0x84, // -24dbm
+ CC2500_POWER_5 = 0x81, // -22dbm
+ CC2500_POWER_6 = 0x46, // -20dbm
+ CC2500_POWER_7 = 0x93, // -18dbm
+ CC2500_POWER_8 = 0x55, // -16dbm
+ CC2500_POWER_9 = 0x8D, // -14dbm
+ CC2500_POWER_10 = 0xC6, // -12dbm
+ CC2500_POWER_11 = 0x97, // -10dbm
+ CC2500_POWER_12 = 0x6E, // -8dbm
+ CC2500_POWER_13 = 0x7F, // -6dbm
+ CC2500_POWER_14 = 0xA9, // -4dbm
+ CC2500_POWER_15 = 0xBB, // -2dbm
+ CC2500_POWER_16 = 0xFE, // 0dbm
+ CC2500_POWER_17 = 0xFF // +1dbm
+};
+#define CC2500_HIGH_POWER CC2500_POWER_1
+#define CC2500_LOW_POWER CC2500_POWER_1
+#define CC2500_RANGE_POWER CC2500_POWER_1
+#define CC2500_BIND_POWER CC2500_POWER_1
+
+enum TXRX_State {
+ TXRX_OFF,
+ TX_EN,
+ RX_EN
+};
#endif
diff --git a/Multiprotocol/common.cpp b/Multiprotocol/common.cpp
index d24416d..88606a7 100644
--- a/Multiprotocol/common.cpp
+++ b/Multiprotocol/common.cpp
@@ -18,32 +18,9 @@
#include "Multiprotocol.h"
#include "cc2500_spi.h"
-#ifdef FAILSAFE_ENABLE
- uint16_t Failsafe_data[NUM_CHN];
-#endif
+#include "input.h"
-void InitFailsafe(void)
-{
- for (uint8_t i = 0; i < NUM_CHN; i++)
- Failsafe_data[i] = 1024;
- Failsafe_data[THROTTLE] = (uint16_t)204; //1=-125%, 204=-100%
- FAILSAFE_VALUES_on;
-}
-
-void InitPPM(void)
-{
- for(uint8_t i=0;icurr = &(this->input[0]);
this->old = &(this->input[1]);
memset(this->input,0, sizeof(this->input));
+ //InitFailsafe
+ for (uint8_t i = 0; i < NUM_TX_CHN; i++)
+ Failsafe_data[i] = (CHANNEL_MAX_100 - CHANNEL_MIN_100) / 2 + CHANNEL_MIN_100;
+ Failsafe_data[CH_THROTTLE] = CHANNEL_MIN_100; //1=-125%, 204=-100%
+
+ // init channel
+
+ for (uint8_t i = 0; i < NUM_TX_CHN; i++)
+ Channel_data[i] = 1024;
+ Channel_data[CH_THROTTLE] = 204;
}
void Input::mark_processed(void) {
struct data* temp = this->old;
@@ -28,40 +55,63 @@ struct Input::data* Input::get_old_input(void) {
}
void Input::init() {
- analogReadResolution(16);
-
- pinMode(Throttle_pin,INPUT);
- pinMode(Yaw_pin,INPUT);
- pinMode(Roll_pin,INPUT);
- pinMode(Aux1_pin,INPUT);
- pinMode(Aux2_pin,INPUT);
- pinMode(Aux3_pin,INPUT);
- pinMode(Aux4_pin,INPUT);
- pinMode(Aux5_pin,INPUT);
- pinMode(Aux6_pin,INPUT);
+ this->pins[CH_THROTTLE] = Throttle_pin;
+ this->ch_config[CH_THROTTLE].is_analog = true;
+
+ this->pins[CH_YAW] = Yaw_pin;
+ this->ch_config[CH_YAW].is_analog = true;
+
+ this->pins[CH_PITCH] = Pitch_pin;
+ this->ch_config[CH_PITCH].is_analog = true;
+
+ this->pins[CH_ROLL] = Roll_pin;
+ this->ch_config[CH_ROLL].is_analog = true;
+
+ this->pins[CH_AUX1] = Aux1_pin;
+ this->ch_config[CH_AUX1].is_analog = false;
+
+ this->pins[CH_AUX2] = Aux2_pin;
+ this->ch_config[CH_AUX2].is_analog = false;
+
+ this->pins[CH_AUX3] = Aux3_pin;
+ this->ch_config[CH_AUX3].is_analog = false;
+
+ this->pins[CH_AUX4] = Aux4_pin;
+ this->ch_config[CH_AUX4].is_analog = false;
+
+ this->pins[CH_AUX5] = Aux5_pin;
+ this->ch_config[CH_AUX5].is_analog = false;
+
+ this->pins[CH_AUX6] = Aux6_pin;
+ this->ch_config[CH_AUX6].is_analog = false;
+
+ for (uint8_t i = 0; i < CH_COUNT; ++i) {
+ pinMode(this->pins[i], INPUT);
+ }
pinMode(Menu_pin,INPUT);
- this->throttle.inverted = true;
- this->yaw.inverted = false;
- this->roll.inverted = false;
- this->pitch.inverted = false;
- this->aux[0].inverted = false;
- this->aux[1].inverted = false;
- this->aux[2].inverted = false;
- this->aux[3].inverted = false;
- this->aux[4].inverted = false;
- this->aux[5].inverted = false;
-
-
- this->throttle.min = 500;
- this->yaw.min = 500;
- this->roll.min = 500;
- this->pitch.min = 500;
-
- this->throttle.max = 500;
- this->yaw.max = 500;
- this->roll.max = 500;
- this->pitch.max = 500;
+ //analogReadResolution(16);
+
+ // move this to eeprom later
+ this->ch_config[CH_THROTTLE].inverted = false;
+ this->ch_config[CH_YAW].inverted = false;
+ this->ch_config[CH_ROLL].inverted = false;
+ this->ch_config[CH_PITCH].inverted = false;
+ this->ch_config[CH_AUX1].inverted = false;
+ this->ch_config[CH_AUX2].inverted = false;
+ this->ch_config[CH_AUX3].inverted = false;
+ this->ch_config[CH_AUX4].inverted = false;
+ this->ch_config[CH_AUX5].inverted = false;
+
+ this->ch_config[CH_THROTTLE].min = 0;
+ this->ch_config[CH_YAW].min = 0;
+ this->ch_config[CH_ROLL].min = 0;
+ this->ch_config[CH_PITCH].min = 0;
+
+ this->ch_config[CH_THROTTLE].max = 4096;
+ this->ch_config[CH_YAW].max = 4096;
+ this->ch_config[CH_ROLL].max = 4096;
+ this->ch_config[CH_PITCH].max = 4096;
}
void Input::do_calibration(void) {
int8_t turns = 50;
@@ -71,24 +121,19 @@ void Input::do_calibration(void) {
i = turns;
while(i > 0) {
this->update();
- if (true == this->save_calibration()) {
+ if (true == this->calibration_update()) {
i = turns;
debugln("new values t %d-%d r %d-%d p %d-%d y %d-%d",
- this->throttle.min,this->throttle.max,
- this->roll.min, this->roll.max,
- this->pitch.min, this->pitch.max,
- this->yaw.min, this->yaw.max);
+ this->ch_config[CH_THROTTLE].min, this->ch_config[CH_THROTTLE].max,
+ this->ch_config[CH_ROLL].min, this->ch_config[CH_ROLL].max,
+ this->ch_config[CH_PITCH].min, this->ch_config[CH_PITCH].max,
+ this->ch_config[CH_YAW].min, this->ch_config[CH_YAW].max);
}else {
i -= 1;
}
delay(100);
}
- debugln("end values t %d-%d r %d-%d p %d-%d y %d-%d",
- this->throttle.min,this->throttle.max,
- this->roll.min, this->roll.max,
- this->pitch.min, this->pitch.max,
- this->yaw.min, this->yaw.max);
// center
debugln("now center all sticks");
@@ -104,199 +149,64 @@ void Input::do_calibration(void) {
}
- debugln("now Move throttle to max");
+ for (int ch = 0; ch < 4 ; ++ch) {
+ debugln("now Move %s to max", ch_name[ch]);
i = turns;
while(i>0) {
- delay(100);
+ delay(50);
this->update();
- if (true == this->is_throttle_up()) {
+ if (true == this->is_high((enum input_channels)ch)) {
+ debug("u");
i--;
continue;
}
- if (true == this->is_throttle_down()) {
- this->throttle.inverted = ! this->throttle.inverted;
- i = turns;
- continue;
- }
- }
- debugln("throttle invert is %d", this->throttle.inverted);
-
-
- debugln("now Move yaw to max");
- i = turns;
- while(i>0) {
- delay(100);
- this->update();
-
- if (true == this->is_yaw_up()) {
- i--;
- continue;
- }
- if (true == this->is_yaw_down()) {
- this->yaw.inverted = ! this->yaw.inverted;
- i = turns;
- continue;
- }
- }
- debugln("yaw invert is %d", this->yaw.inverted);
- debugln("now Move pitch to max");
- i = turns;
- while(i>0) {
- delay(100);
- this->update();
- if (true == this->is_pitch_up()) {
- i--;
- continue;
- }
- if (true == this->is_pitch_down()) {
- this->pitch.inverted = ! this->pitch.inverted;
- i = turns;
- continue;
- }
- }
- debugln("pitch invert is %d", this->pitch.inverted);
-
- debugln("now Move roll to max");
+ if (true == this->is_low((enum input_channels)ch)) {
+ debug("dI");
+ this->ch_config[CH_THROTTLE].inverted = !this->ch_config[CH_THROTTLE].inverted;
i = turns;
- while(i>0) {
- delay(100);
- this->update();
-
- if (true == this->is_roll_up()) {
- i--;
continue;
}
- if (true == this->is_roll_down()) {
- this->roll.inverted = ! this->roll.inverted;
- i = turns;
- continue;
}
}
- debugln("roll invert is %d", this->roll.inverted);
}
bool Input::is_centered(void) {
- return this->is_centered_left() && this->is_centered_right();
+ return
+ this->is_centered(CH_ROLL) &&
+ this->is_centered(CH_PITCH) &&
+ this->is_centered(CH_THROTTLE) &&
+ this->is_centered(CH_YAW);
}
-bool Input::is_centered_left(void) {
- uint16_t range;
- uint16_t delta;
-
- range = this->throttle.max - this->throttle.min;
- delta = range >>4;
- if ( this->curr->throttle < this->throttle.min + range/2 - delta ||
- this->curr->throttle > this->throttle.min + range/2 + delta
- ) {
- // throttle is not centered
- return false;
- }
-
+bool Input::is_centered(enum Input::input_channels ch) {
+ uint16_t range = this->ch_config[ch].max - this->ch_config[ch].min;
+ uint16_t delta = range / 5;
- range = this->yaw.max - this->yaw.min;
- delta = range >>4;
- if ( this->curr->yaw < this->yaw.min + range/2 - delta ||
- this->curr->yaw > this->yaw.min + range/2 + delta
- ) {
- // yaw is not centered
- return false;
- }
- return true;
-}
-bool Input::is_centered_right(void) {
- uint16_t range;
- uint16_t delta;
-
- range = this->pitch.max - this->pitch.min;
- delta = range >>4;
- if ( this->curr->pitch < this->pitch.min + range/2 - delta ||
- this->curr->pitch > this->pitch.min + range/2 + delta
+ if ( this->curr->ch_data[ch] < this->ch_config[ch].min + range / 2 - delta ||
+ this->curr->ch_data[ch] > this->ch_config[ch].min + range / 2 + delta
) {
// pitch is not centered
return false;
}
-
- range = this->roll.max - this->roll.min;
- delta = range >>4;
- if ( this->curr->roll < this->roll.min + range/2 - delta ||
- this->curr->roll > this->roll.min + range/2 + delta
- ) {
- // roll is not centered
- return false;
- }
return true;
}
-bool Input::is_menu_left(void) {
- return this->is_roll_down();
-}
-bool Input::is_menu_right(void) {
- return this->is_roll_up();
-}
-bool Input::is_menu_down(void) {
- return this->is_pitch_down();
-}
-bool Input::is_menu_up(void) {
- return this->is_pitch_up();
-}
-bool Input::is_throttle_down(void) {
- uint16_t delta = (this->throttle.max - this->throttle.min)/3;
- if ( this->curr->throttle < this->throttle.min + delta) {
+bool Input::is_high(enum Input::input_channels ch) {
+ uint16_t range = this->ch_config[ch].max - this->ch_config[ch].min;
+ uint16_t delta = range / 3;
+ if ( this->curr->ch_data[ch] < this->ch_config[ch].max - delta) {
return true;
}
return false;
}
-bool Input::is_throttle_up(void) {
- uint16_t delta = (this->throttle.max - this->throttle.min)/3;
- if ( this->curr->throttle > this->throttle.max - delta) {
- return true;
- }
- return false;
-}
-bool Input::is_yaw_up(void) {
- uint16_t delta = (this->yaw.max - this->yaw.min)/3;
- if ( this->curr->yaw > this->yaw.max - delta) {
- return true;
- }
- return false;
-}
-bool Input::is_yaw_down(void) {
- uint16_t delta = (this->yaw.max - this->yaw.min)/3;
- if ( this->curr->yaw > this->yaw.min + delta) {
- return true;
- }
- return false;
-}
-
-bool Input::is_roll_down(void) {
- uint16_t delta = (this->roll.max - this->roll.min)/3;
- if ( this->curr->roll < this->roll.min + delta) {
- return true;
- }
- return false;
-
-}
-bool Input::is_roll_up(void) {
- uint16_t delta = (this->roll.max - this->roll.min)/3;
- if ( this->curr->roll > this->roll.max - delta) {
- return true;
- }
- return false;
-}
-bool Input::is_pitch_up(void) {
- uint16_t delta = (this->pitch.max - this->pitch.min)/3;
- if ( this->curr->pitch > this->pitch.max - delta) {
- return true;
- }
- return false;
-}
-bool Input::is_pitch_down(void) {
- uint16_t delta = (this->pitch.max - this->pitch.min)/3;
- if ( this->curr->pitch > this->pitch.min + delta) {
+bool Input::is_low(enum Input::input_channels ch) {
+ uint16_t range = this->ch_config[ch].max - this->ch_config[ch].min;
+ uint16_t delta = range / 3;
+ if ( this->curr->ch_data[ch] < this->ch_config[ch].min + delta) {
return true;
}
return false;
@@ -306,56 +216,48 @@ bool Input::is_menu_triggered(void) {
return this->curr->menu;
}
-bool Input::save_calibration(void) {
+bool Input::calibration_update(void) {
bool changed = false;
- if (this->throttle.min > this->curr->throttle){
- changed = true;
- this->throttle.min = this->curr->throttle;
- } else if (this->throttle.max < this->curr->throttle) {
- changed = true;
- this->throttle.max = this->curr->throttle;
- }
- if (this->yaw.min > this->curr->yaw){
+ for (uint8_t ch = 0; ch < CH_COUNT; ch++) {
+ if (this->ch_config[ch].min > this->ch_raw[ch]) {
+ this->ch_config[ch].min = this->ch_raw[ch];
changed = true;
- this->yaw.min = this->curr->yaw;
- } else if (this->yaw.max < this->curr->yaw) {
+ } else if (this->ch_config[ch].max < this->ch_raw[ch]) {
changed = true;
- this->yaw.max = this->curr->yaw;
+ this->ch_config[ch].max = this->ch_raw[ch];
}
- if (this->roll.min > this->curr->roll){
- changed = true;
- this->roll.min = this->curr->roll;
- } else if (this->roll.max < this->curr->roll) {
- changed = true;
- this->roll.max = this->curr->roll;
}
- if (this->pitch.min > this->curr->pitch){
- changed = true;
- this->pitch.min = this->curr->pitch;
- } else if (this->roll.max < this->curr->pitch) {
- changed = true;
- this->pitch.max = this->curr->pitch;
- }
+ // TODO save in eeprom
return changed;
}
void Input::update(void) {
- this->curr->throttle = analogRead(Throttle_pin);
- this->curr->yaw = analogRead(Yaw_pin);
- this->curr->roll = analogRead(Roll_pin);
- this->curr->pitch = analogRead(Pitch_pin);
- this->curr->aux[0] = digitalRead(Aux1_pin);
- this->curr->aux[1] = digitalRead(Aux2_pin);
- this->curr->aux[2] = digitalRead(Aux3_pin);
- this->curr->aux[3] = digitalRead(Aux4_pin);
- this->curr->aux[4] = digitalRead(Aux5_pin);
- this->curr->aux[5] = digitalRead(Aux6_pin);
+ for (uint8_t ch = 0; ch < CH_MAX; ch ++) {
+
+ if (this->ch_config[ch].is_analog)
+ this->ch_raw[ch] = analogRead(this->pins[ch]);
+ else
+ this->ch_raw[ch] = digitalRead(this->pins[ch]) == HIGH;
- this->curr->menu = digitalRead(Menu_pin);
+ // do inverting
+ if (this->ch_config[ch].inverted)
+ this->curr->ch_data[ch] = this->ch_config[ch].max - this->ch_raw[ch];
+ else
+ this->curr->ch_data[ch] = this->ch_raw[ch];
+
+ // cap on max
+
+ if (this->ch_config[ch].min > this->curr->ch_data[ch]) {
+ this->curr->ch_data[ch] = this->ch_config[ch].min;
+ } else if (this->ch_config[ch].max < this->curr->ch_data[ch]) {
+ this->curr->ch_data[ch] = this->ch_config[ch].max;
+ }
+ }
+ this->curr->menu = digitalRead(Menu_pin) == HIGH;
/*debug_input("t%d y%d r%d p%d a1_%d a2_%d a3_%d a4_%d a5_%d m%d",
@@ -368,32 +270,7 @@ void Input::update(void) {
if (curr_state != s_fly)
return;
- if(this->throttle.inverted)
- Channel_data[THROTTLE] = map(this->curr->throttle, this->throttle.min, this->throttle.max, CHANNEL_MAX_100, CHANNEL_MIN_100);
- else
- Channel_data[THROTTLE] = map(this->curr->throttle, this->throttle.min, this->throttle.max, CHANNEL_MIN_100, CHANNEL_MAX_100);
-
-
- if(this->yaw.inverted)
- Channel_data[RUDDER] = map(this->curr->yaw, this->yaw.min, this->yaw.max, CHANNEL_MAX_100, CHANNEL_MIN_100);
- else
- Channel_data[RUDDER] = map(this->curr->yaw, this->yaw.min, this->yaw.max, CHANNEL_MIN_100, CHANNEL_MAX_100);
-
- if(this->roll.inverted)
- Channel_data[AILERON] = map(this->curr->roll, this->roll.min, this->roll.max, CHANNEL_MAX_100, CHANNEL_MIN_100);
- else
- Channel_data[AILERON] = map(this->curr->roll, this->roll.min, this->roll.max, CHANNEL_MIN_100, CHANNEL_MAX_100);
-
-
- if(this->pitch.inverted)
- Channel_data[ELEVATOR] = map(this->curr->pitch, this->pitch.min, this->pitch.max, CHANNEL_MAX_100, CHANNEL_MIN_100);
- else
- Channel_data[ELEVATOR] = map(this->curr->pitch, this->pitch.min, this->pitch.max, CHANNEL_MIN_100, CHANNEL_MAX_100);
-
- for (uint8_t i = 0; i<6; ++i) {
- if(this->aux[i].inverted)
- Channel_data[CH5+i] = (this->curr->aux[i]) ? CHANNEL_MIN_100 : CHANNEL_MAX_100;
- else
- Channel_data[CH5+i] = (this->curr->aux[i]) ? CHANNEL_MAX_100 : CHANNEL_MIN_100;
+ for (uint8_t ch = 0; ch < CH_COUNT; ++ch) {
+ Channel_data[ch] = map(this->curr->ch_data[ch], this->ch_config[ch].min, this->ch_config[ch].max, CHANNEL_MAX_100, CHANNEL_MIN_100);
}
}
diff --git a/Multiprotocol/input.h b/Multiprotocol/input.h
index 43787f1..910904d 100644
--- a/Multiprotocol/input.h
+++ b/Multiprotocol/input.h
@@ -3,31 +3,37 @@
#include
#include "tx_def.h"
+#define NUM_TX_CHN 16
+
+extern uint16_t Channel_data[NUM_TX_CHN];
+extern uint16_t Failsafe_data[NUM_TX_CHN];
class Input {
- private:
- struct data {
- uint16_t throttle;
- uint16_t yaw;
- uint16_t roll;
- uint16_t pitch;
+ public:
+ enum input_channels {
+ CH_ROLL = 0,
+ CH_PITCH = 1,
+ CH_THROTTLE = 2,
+ CH_YAW = 3,
- bool aux[6];
+ CH_AUX1 = 4,
+ CH_AUX2 = 5,
+ CH_AUX3 = 6,
+ CH_AUX4 = 7,
+ CH_AUX5 = 8,
+ CH_AUX6 = 8,
- bool menu;
+ CH_MAX = 8,
+ CH_COUNT = 9,
+ MENU_UP_DOWN = CH_PITCH,
+ MENU_LEFT_RIGHT = CH_ROLL,
};
- struct data input[2];
- struct data* curr;
- struct data* old;
- struct {
- uint16_t max;
- uint16_t min;
- uint8_t inverted;
- } throttle, yaw, roll, pitch, aux[5];
+ struct data {
+ uint16_t ch_data[CH_COUNT];
+ bool menu;
+ };
- bool save_calibration(void);
- public:
Input(void);
void init(void);
@@ -40,27 +46,31 @@ class Input {
void mark_processed(void);
bool is_centered(void);
- bool is_centered_left(void);
- bool is_centered_right(void);
+ bool is_centered(enum input_channels ch);
+ bool is_low(enum input_channels ch);
+ bool is_high(enum input_channels ch);
// menu inputs
bool is_menu_triggered(void);
- bool is_menu_left(void);
- bool is_menu_right(void);
- bool is_menu_down(void);
- bool is_menu_up(void);
+ private:
+ struct data input[2];
+ struct data* curr;
+ struct data* old;
+
+ uint16_t ch_raw[CH_COUNT];
+
+ struct {
+ uint16_t max;
+ uint16_t min;
+ bool inverted;
+ bool is_analog;
+ } ch_config[CH_COUNT];
- bool is_throttle_up(void);
- bool is_throttle_down(void);
- bool is_yaw_up(void);
- bool is_yaw_down(void);
+ uint32_t pins[CH_COUNT];
- bool is_roll_up(void);
- bool is_roll_down(void);
- bool is_pitch_up(void);
- bool is_pitch_down(void);
+ bool calibration_update(void);
};
-extern uint16_t Channel_data[NUM_CHN];
+extern uint16_t Channel_data[NUM_TX_CHN];
extern Input input;
#endif
diff --git a/Multiprotocol/state.cpp b/Multiprotocol/state.cpp
index 6c7a8e9..d6e61d3 100644
--- a/Multiprotocol/state.cpp
+++ b/Multiprotocol/state.cpp
@@ -10,10 +10,11 @@ LiquidCrystal_I2C lcd(0x27,16,2);
State *curr_state = NULL;
State *new_state = NULL;
-State *s_init = new LCD_state_init();
-State *s_bind = new LCD_state_bind();
-State *s_fly = new LCD_state_fly();
-State *s_menu = new LCD_state_menu();
+State *s_init = NULL;
+State *s_bind = NULL;
+State *s_fly = NULL;
+State *s_joy = NULL;
+State *s_menu = NULL;
enum lcd_special_chars {
@@ -58,11 +59,17 @@ void install_special_caracters(void)
}
void init_state(void) {
+ #if 0
Wire.setSDA(PB9);
Wire.setSCL(PB8);
+ #endif
Wire.begin();
lcd.init();
+ s_init = new LCD_state_init();
+ s_bind = new LCD_state_bind();
+ s_fly = new LCD_state_fly();
+ s_menu = new LCD_state_menu();
lcd.backlight();
curr_state = NULL;
new_state = s_init;
@@ -89,14 +96,12 @@ void update_state(void) {
//LCD_state_init
LCD_state_init::LCD_state_init(void) {
- snprintf(this->line[0],sizeof(this->line[0])," wellcome ");
- snprintf(this->line[1],sizeof(this->line[1])," phschoen ");
}
void LCD_state_init::enter(void) {
lcd.setCursor(0,0);
- lcd.print(this->line[0]);
+ lcd.print(" wellcome ");
lcd.setCursor(0,1);
- lcd.print(this->line[1]);
+ lcd.print(" phschoen ");
this->time_enter = millis();
}
void LCD_state_init::update(void)
@@ -113,28 +118,29 @@ void LCD_state_init::leave(void)
}
//LCD_state_bind
LCD_state_bind::LCD_state_bind(void) {
- snprintf(this->line[0],sizeof(this->line[0]),"bind mode ");
- snprintf(this->line[1],sizeof(this->line[1])," ");
this->bind_time = 20;
}
void LCD_state_bind::enter(void) {
lcd.setCursor(0,0);
- lcd.print(this->line[0]);
+ lcd.print("bind mode ");
lcd.setCursor(0,1);
- lcd.print(this->line[1]);
+ lcd.print(" ");
this->time_enter = millis();
}
void LCD_state_bind::update(void)
{
debugln("blubber\n");
+ char line[17];
unsigned long time_in_ms = millis() - this->time_enter;
unsigned long time_in_s = time_in_ms/1000; // to sec
unsigned long remain_s = this->bind_time - time_in_s;
- snprintf(this->line[0],sizeof(this->line[1]),"remaining sec %02d",remain_s);
+ snprintf(line,sizeof(line),"remaining sec %02d",remain_s);
lcd.setCursor(0,1);
- lcd.print(this->line[0]);
+ lcd.print(line);
+
+ // cange to menu when done
if (time_in_s >= this->bind_time)
new_state = s_menu;
}
@@ -146,15 +152,12 @@ void LCD_state_bind::leave(void)
// LCD_state_menu
LCD_state_menu::LCD_state_menu(void) {
- snprintf(this->line[0],sizeof(this->line[0]),"Menubind mode ");
- snprintf(this->line[1],sizeof(this->line[1])," ");
- this->curr_selected = 0;
}
void LCD_state_menu::enter(void) {
lcd.setCursor(0,0);
- lcd.print(this->line[0]);
+ lcd.print("menu mode ");
lcd.setCursor(0,1);
- lcd.print(this->line[1]);
+ lcd.print(" ");
this->time_enter = millis();
}
@@ -169,15 +172,13 @@ void LCD_state_menu::leave(void)
// LCD_state_fly
LCD_state_fly::LCD_state_fly(void) {
- snprintf(this->line[0],sizeof(this->line[0]),"fly mode ");
- snprintf(this->line[1],sizeof(this->line[1])," ");
}
void LCD_state_fly::enter(void) {
lcd.setCursor(0,0);
- lcd.print(this->line[0]);
+ lcd.print("fly mode ");
lcd.setCursor(0,1);
- lcd.print(this->line[1]);
+ lcd.print(" ");
this->time_enter = millis();
}
diff --git a/Multiprotocol/state.h b/Multiprotocol/state.h
index 0a79e9f..99a631b 100644
--- a/Multiprotocol/state.h
+++ b/Multiprotocol/state.h
@@ -12,7 +12,6 @@ void update_state(void);
class State {
protected:
- char line[2][17];
public:
virtual void enter(void) {
@@ -73,11 +72,21 @@ public:
void leave(void);
};
+class LCD_state_calibration: public State {
+private:
+ unsigned long time_enter;
+public:
+ LCD_state_calibration(void);
+ void enter(void);
+ void update(void);
+ void leave(void);
+};
extern State *curr_state;
extern State *new_state;
extern State *s_init;
extern State *s_bind;
extern State *s_fly;
+extern State *s_joy;
extern State *s_menu;
#endif /*_STATE_H_*/
diff --git a/Multiprotocol/tx_def.h b/Multiprotocol/tx_def.h
index ec33aad..0887996 100644
--- a/Multiprotocol/tx_def.h
+++ b/Multiprotocol/tx_def.h
@@ -48,170 +48,6 @@
#define CHANNEL_MAX_COMMAND 1424 // 1750us
//Channel definitions
-#ifdef AETR
- #define AILERON 0
- #define ELEVATOR 1
- #define THROTTLE 2
- #define RUDDER 3
-#endif
-#ifdef AERT
- #define AILERON 0
- #define ELEVATOR 1
- #define THROTTLE 3
- #define RUDDER 2
-#endif
-#ifdef ARET
- #define AILERON 0
- #define ELEVATOR 2
- #define THROTTLE 3
- #define RUDDER 1
-#endif
-#ifdef ARTE
- #define AILERON 0
- #define ELEVATOR 3
- #define THROTTLE 2
- #define RUDDER 1
-#endif
-#ifdef ATRE
- #define AILERON 0
- #define ELEVATOR 3
- #define THROTTLE 1
- #define RUDDER 2
-#endif
-#ifdef ATER
- #define AILERON 0
- #define ELEVATOR 2
- #define THROTTLE 1
- #define RUDDER 3
-#endif
-
-#ifdef EATR
- #define AILERON 1
- #define ELEVATOR 0
- #define THROTTLE 2
- #define RUDDER 3
-#endif
-#ifdef EART
- #define AILERON 1
- #define ELEVATOR 0
- #define THROTTLE 3
- #define RUDDER 2
-#endif
-#ifdef ERAT
- #define AILERON 2
- #define ELEVATOR 0
- #define THROTTLE 3
- #define RUDDER 1
-#endif
-#ifdef ERTA
- #define AILERON 3
- #define ELEVATOR 0
- #define THROTTLE 2
- #define RUDDER 1
-#endif
-#ifdef ETRA
- #define AILERON 3
- #define ELEVATOR 0
- #define THROTTLE 1
- #define RUDDER 2
-#endif
-#ifdef ETAR
- #define AILERON 2
- #define ELEVATOR 0
- #define THROTTLE 1
- #define RUDDER 3
-#endif
-
-#ifdef TEAR
- #define AILERON 2
- #define ELEVATOR 1
- #define THROTTLE 0
- #define RUDDER 3
-#endif
-#ifdef TERA
- #define AILERON 3
- #define ELEVATOR 1
- #define THROTTLE 0
- #define RUDDER 2
-#endif
-#ifdef TREA
- #define AILERON 3
- #define ELEVATOR 2
- #define THROTTLE 0
- #define RUDDER 1
-#endif
-#ifdef TRAE
- #define AILERON 2
- #define ELEVATOR 3
- #define THROTTLE 0
- #define RUDDER 1
-#endif
-#ifdef TARE
- #define AILERON 1
- #define ELEVATOR 3
- #define THROTTLE 0
- #define RUDDER 2
-#endif
-#ifdef TAER
- #define AILERON 1
- #define ELEVATOR 2
- #define THROTTLE 0
- #define RUDDER 3
-#endif
-
-#ifdef RETA
- #define AILERON 3
- #define ELEVATOR 1
- #define THROTTLE 2
- #define RUDDER 0
-#endif
-#ifdef REAT
- #define AILERON 2
- #define ELEVATOR 1
- #define THROTTLE 3
- #define RUDDER 0
-#endif
-#ifdef RAET
- #define AILERON 1
- #define ELEVATOR 2
- #define THROTTLE 3
- #define RUDDER 0
-#endif
-#ifdef RATE
- #define AILERON 1
- #define ELEVATOR 3
- #define THROTTLE 2
- #define RUDDER 0
-#endif
-#ifdef RTAE
- #define AILERON 2
- #define ELEVATOR 3
- #define THROTTLE 1
- #define RUDDER 0
-#endif
-#ifdef RTEA
- #define AILERON 3
- #define ELEVATOR 2
- #define THROTTLE 1
- #define RUDDER 0
-#endif
-#define CH1 0
-#define CH2 1
-#define CH3 2
-#define CH4 3
-#define CH5 4
-#define CH6 5
-#define CH7 6
-#define CH8 7
-#define CH9 8
-#define CH10 9
-#define CH11 10
-#define CH12 11
-#define CH13 12
-#define CH14 13
-#define CH15 14
-#define CH16 15
-#define NUM_CHN 16
#endif /* _TX_DEV_H_ */