Beispiel #1
0
static void v202Nrf24Setup(rx_spi_protocol_e protocol)
{
    NRF24L01_Initialize(BV(NRF24L01_00_CONFIG_EN_CRC) | BV(NRF24L01_00_CONFIG_CRCO)); // 2-bytes CRC

    NRF24L01_WriteReg(NRF24L01_01_EN_AA, 0x00);      // No Auto Acknowledgment
    NRF24L01_WriteReg(NRF24L01_02_EN_RXADDR, BV(NRF24L01_02_EN_RXADDR_ERX_P0));  // Enable data pipe 0
    NRF24L01_WriteReg(NRF24L01_03_SETUP_AW, NRF24L01_03_SETUP_AW_5BYTES);   // 5-byte RX/TX address
    NRF24L01_WriteReg(NRF24L01_04_SETUP_RETR, 0xFF); // 4ms retransmit t/o, 15 tries
    if (protocol == RX_SPI_NRF24_V202_250K) {
        NRF24L01_WriteReg(NRF24L01_06_RF_SETUP, NRF24L01_06_RF_SETUP_RF_DR_250Kbps | NRF24L01_06_RF_SETUP_RF_PWR_n12dbm);
    } else {
        NRF24L01_WriteReg(NRF24L01_06_RF_SETUP, NRF24L01_06_RF_SETUP_RF_DR_1Mbps | NRF24L01_06_RF_SETUP_RF_PWR_n12dbm);
    }
    NRF24L01_WriteReg(NRF24L01_07_STATUS, BV(NRF24L01_07_STATUS_RX_DR) | BV(NRF24L01_07_STATUS_TX_DS) | BV(NRF24L01_07_STATUS_MAX_RT));     // Clear data ready, data sent, and retransmit
    NRF24L01_WriteReg(NRF24L01_11_RX_PW_P0, V2X2_PAYLOAD_SIZE);  // bytes of data payload for pipe 0
    NRF24L01_WriteReg(NRF24L01_17_FIFO_STATUS, 0x00); // Just in case, no real bits to write here
#define RX_TX_ADDR_LEN 5
    const uint8_t rx_tx_addr[RX_TX_ADDR_LEN] = {0x66, 0x88, 0x68, 0x68, 0x68};
    NRF24L01_WriteRegisterMulti(NRF24L01_0A_RX_ADDR_P0, rx_tx_addr, RX_TX_ADDR_LEN);
    NRF24L01_WriteRegisterMulti(NRF24L01_10_TX_ADDR, rx_tx_addr, RX_TX_ADDR_LEN);

    NRF24L01_FlushTx();
    NRF24L01_FlushRx();

    rf_ch_num = 0;
    bind_phase = PHASE_NOT_BOUND;
    prepare_to_bind();
    switch_channel();
    NRF24L01_SetRxMode(); // enter receive mode to start listening for packets
}
//Send a packet and receive the ACK
//Return true in case of success.
//Polling implementation
unsigned char NRF24L01_SendPacket(char *payload, char len, char *ackPayload, char *ackLen)
{
  char status = 0;
  
  //Send the packet
  NRF24L01_TxPacket(payload, len);
  //Wait for something to happen
  while(((status=NRF24L01_Nop())&0x70) == 0);
  
  // Clear the flags
  NRF24L01_WriteReg(REG_STATUS, 0x70);
  
  //Return FALSE if the packet has not been transmited
  if (status&BIT_MAX_RT) {
    NRF24L01_FlushTx();
    return 0;
  }
    
  //Receive the ackPayload if any has been received
  if (status&BIT_RX_DR)
    *ackLen = NRF24L01_RxPacket(ackPayload);
  else 
    *ackLen = 0;
  
  NRF24L01_FlushRx();
  
  return status&BIT_TX_DS;
}
Beispiel #3
0
int NRF24L01_Reset()
{
    NRF24L01_FlushTx();
    NRF24L01_FlushRx();
    u8 status1 = Strobe(NOP);
    u8 status2 = NRF24L01_ReadReg(0x07);
    NRF24L01_SetTxRxMode(TXRX_OFF);
    return (status1 == status2 && (status1 & 0x0f) == 0x0e);
}
Beispiel #4
0
void initrx(void)
{
    NRF24L01_Initialize();

    reset_beken();

    // 2-bytes CRC, radio off
    uint8_t config = BV(NRF24L01_00_EN_CRC) | BV(NRF24L01_00_CRCO) | BV(NRF24L01_00_PRIM_RX);

    NRF24L01_WriteReg(NRF24L01_00_CONFIG, config);
    NRF24L01_WriteReg(NRF24L01_01_EN_AA, 0x00);      // No Auto Acknoledgement
    NRF24L01_WriteReg(NRF24L01_02_EN_RXADDR, 0x01);  // Enable data pipe 0
    NRF24L01_WriteReg(NRF24L01_03_SETUP_AW, 0x03);   // 5-byte RX/TX address
    NRF24L01_WriteReg(NRF24L01_04_SETUP_RETR, 0xFF); // 4ms retransmit t/o, 15 tries
//    NRF24L01_WriteReg(NRF24L01_05_RF_CH, 0x08);      // Channel 8 - bind
    //NRF24L01_SetBitrate(NRF24L01_BR_1M);                          // 1Mbps
    NRF24L01_SetBitrate(NRF24L01_BR_250K); //250k for longer range.
    NRF24L01_SetPower(TXPOWER_100mW);
    NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70);     // Clear data ready, data sent, and retransmit
    NRF24L01_WriteReg(NRF24L01_11_RX_PW_P0, V2X2_PAYLOAD_SIZE);  // bytes of data payload for pipe 0
    NRF24L01_WriteReg(NRF24L01_17_FIFO_STATUS, 0x00); // Just in case, no real bits to write here
    uint8_t rx_tx_addr[] = {0x66, 0x88, 0x68, 0x68, 0x68};
//    uint8_t rx_p1_addr[] = {0x88, 0x66, 0x86, 0x86, 0x86};
    NRF24L01_WriteRegisterMulti(NRF24L01_0A_RX_ADDR_P0, rx_tx_addr, 5);
//    NRF24L01_WriteRegisterMulti(NRF24L01_0B_RX_ADDR_P1, rx_p1_addr, 5);
    NRF24L01_WriteRegisterMulti(NRF24L01_10_TX_ADDR, rx_tx_addr, 5);

    initialize_beken();

    lib_timers_delaymilliseconds(50);

    NRF24L01_FlushTx();
    NRF24L01_FlushRx();

    rf_ch_num = 0;

    // Turn radio power on
    config |= BV(NRF24L01_00_PWR_UP);
    NRF24L01_WriteReg(NRF24L01_00_CONFIG, config);
    // delayMicroseconds(150);
    lib_timers_delaymilliseconds(1); // 6 times more than needed

    valid_packets = missed_packets = bad_packets = 0;

    if (usersettings.boundprotocol == PROTO_NONE) {
        bind_phase = PHASE_NOT_BOUND;
        prepare_to_bind();
    } else {
        // Prepare to listen to bound protocol, if fails
        // try to bind
        bind_phase = PHASE_JUST_BOUND;
        set_bound();
    }
    switch_channel();
}
static uint16_t esky150_init2()
{
    NRF24L01_FlushTx();
    NRF24L01_FlushRx();
    packet_sent = 0;
    packet_count = 0;
    rf_ch_num = 0;

    // Turn radio power on
    NRF24L01_WriteReg(NRF24L01_00_CONFIG, CRC_CONFIG | BV(NRF24L01_00_PWR_UP));
    // delayMicroseconds(150);
    return 150u;
}
Beispiel #6
0
void init()
{
    NRF24L01_Initialize();
    NRF24L01_WriteReg(NRF24L01_03_SETUP_AW, 0x02);          // 4 bytes rx/tx address
    NRF24L01_WriteRegisterMulti(NRF24L01_10_TX_ADDR, (u8 *)"\x80\x80\x80\xB8", ADDRESS_LENGTH);     // Bind address
    NRF24L01_WriteRegisterMulti(NRF24L01_0A_RX_ADDR_P0, (u8 *)"\x80\x80\x80\xB8", ADDRESS_LENGTH);  // Bind address
    NRF24L01_FlushTx();
    NRF24L01_FlushRx();
    NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70);            // Clear data ready, data sent, and retransmit
    NRF24L01_WriteReg(NRF24L01_01_EN_AA, 0x00);             // No Auto Acknowldgement on all data pipes
    NRF24L01_WriteReg(NRF24L01_02_EN_RXADDR, 0x01);         // Enable data pipe 0 only
    NRF24L01_WriteReg(NRF24L01_11_RX_PW_P0, PACKET_SIZE);
    NRF24L01_SetPower(Model.tx_power);
}
Beispiel #7
0
static rx_spi_received_e readrx(uint8_t *packet)
{
    if (!(NRF24L01_ReadReg(NRF24L01_07_STATUS) & BV(NRF24L01_07_STATUS_RX_DR))) {
        uint32_t t = micros() - packet_timer;
        if (t > rx_timeout) {
            switch_channel();
            packet_timer = micros();
        }
        return RX_SPI_RECEIVED_NONE;
    }
    packet_timer = micros();
    NRF24L01_WriteReg(NRF24L01_07_STATUS, BV(NRF24L01_07_STATUS_RX_DR)); // clear the RX_DR flag
    NRF24L01_ReadPayload(packet, V2X2_PAYLOAD_SIZE);
    NRF24L01_FlushRx();

    switch_channel();
    return decode_packet(packet);
}
static int check_rx(void)
{

    union {
        u16 value;
        struct {
            u8 lsb;
            u8 msb;
        } bytes;
    } chanval;

    if (NRF24L01_ReadReg(NRF24L01_07_STATUS) & BV(NRF24L01_07_RX_DR)) {
        // data received from aircraft
        XN297_ReadPayload(packet, PACKET_SIZE);

        NRF24L01_WriteReg(NRF24L01_07_STATUS, 255);

        NRF24L01_FlushRx();
        // decode data , check sum is ok as well, since there is no crc
        if (packet[0] == 0x85 && packet[14] == checksum()) {
            // uncompensated battery volts*100
            chanval.bytes.msb = packet[3] & 0x7;
            u8 flags = packet[3] >> 3;
            chanval.bytes.lsb = packet[4] & 0xff;
            Telemetry.value[TELEM_DSM_FLOG_VOLT1] = chanval.value;
            TELEMETRY_SetUpdated(TELEM_DSM_FLOG_VOLT1);

            // compensated battery volts*100
            chanval.bytes.msb = packet[5] & 0x7;
            chanval.bytes.lsb = packet[6] & 0xff;
            Telemetry.value[TELEM_DSM_FLOG_VOLT2] = chanval.value;
            TELEMETRY_SetUpdated(TELEM_DSM_FLOG_VOLT2);

            // reception in packets / sec , multiplied by 2
            Telemetry.value[TELEM_DSM_FLOG_HOLDS] = packet[7] * 2;
            TELEMETRY_SetUpdated(TELEM_DSM_FLOG_HOLDS);

            // battery low flag
            Telemetry.value[TELEM_DSM_FLOG_FADESL] = (flags & 1) ? 100 : 0;
            TELEMETRY_SetUpdated(TELEM_DSM_FLOG_FADESL);

            telemetry_count++;
            return 1;
        }                       // end tel received
Beispiel #9
0
static void DM002_init()
{
    NRF24L01_Initialize();
    NRF24L01_SetTxRxMode(TX_EN);
    XN297_SetTXAddr((uint8_t *)"\x26\xA8\x67\x35\xCC", DM002_ADDRESS_SIZE);

    NRF24L01_FlushTx();
    NRF24L01_FlushRx();
    NRF24L01_WriteReg(NRF24L01_07_STATUS, 0x70);     // Clear data ready, data sent, and retransmit
    NRF24L01_WriteReg(NRF24L01_01_EN_AA, 0x00);      // No Auto Acknowldgement on all data pipes
    NRF24L01_WriteReg(NRF24L01_02_EN_RXADDR, 0x01);  // Enable data pipe 0 only
    NRF24L01_SetBitrate(NRF24L01_BR_1M);             // 1Mbps
    NRF24L01_SetPower(Model.tx_power);
    
    // Check for Beken BK2421/BK2423 chip
    // It is done by using Beken specific activate code, 0x53
    // and checking that status register changed appropriately
    // There is no harm to run it on nRF24L01 because following
    // closing activate command changes state back even if it
    // does something on nRF24L01
    NRF24L01_Activate(0x53); // magic for BK2421 bank switch
    dbgprintf("Trying to switch banks\n");
    if (NRF24L01_ReadReg(NRF24L01_07_STATUS) & 0x80) {
        dbgprintf("BK2421 detected\n");
        // Beken registers don't have such nice names, so we just mention
        // them by their numbers
        // It's all magic, eavesdropped from real transfer and not even from the
        // data sheet - it has slightly different values
        NRF24L01_WriteRegisterMulti(0x00, (u8 *) "\x40\x4B\x01\xE2", 4);
        NRF24L01_WriteRegisterMulti(0x01, (u8 *) "\xC0\x4B\x00\x00", 4);
        NRF24L01_WriteRegisterMulti(0x02, (u8 *) "\xD0\xFC\x8C\x02", 4);
        NRF24L01_WriteRegisterMulti(0x03, (u8 *) "\x99\x00\x39\x21", 4);
        NRF24L01_WriteRegisterMulti(0x04, (u8 *) "\xD9\x96\x82\x1B", 4);
        NRF24L01_WriteRegisterMulti(0x05, (u8 *) "\x24\x06\x7F\xA6", 4);
        NRF24L01_WriteRegisterMulti(0x0C, (u8 *) "\x00\x12\x73\x00", 4);
        NRF24L01_WriteRegisterMulti(0x0D, (u8 *) "\x46\xB4\x80\x00", 4);
        NRF24L01_WriteRegisterMulti(0x04, (u8 *) "\xDF\x96\x82\x1B", 4);
        NRF24L01_WriteRegisterMulti(0x04, (u8 *) "\xD9\x96\x82\x1B", 4);
    } else {
        dbgprintf("nRF24L01 detected\n");
    }
    NRF24L01_Activate(0x53); // switch bank back
}
Beispiel #10
0
// Helper for sending a packet
// Assumes packet data has been put in tx_packet
// and tx_payload_len has been set correctly
static void send_packet()
{
    // clear packet status bits and Tx/Rx FIFOs
    NRF24L01_WriteReg(NRF24L01_07_STATUS, (BV(NRF24L01_07_TX_DS) | BV(NRF24L01_07_MAX_RT)));
    NRF24L01_FlushTx();
    NRF24L01_FlushRx();

    // Transmit the payload
    NRF24L01_WritePayload(tx_packet, tx_payload_len);

    ++packet_counter;

    // Check and adjust transmission power. We do this after
    // transmission to not bother with timeout after power
    // settings change -  we have plenty of time until next
    // packet.
    if (tx_power != Model.tx_power) {
        //Keep transmit power updated
        tx_power = Model.tx_power;
        NRF24L01_SetPower(tx_power);
    }
}
Beispiel #11
0
void readrx(void)
{
    int chan;
    uint16_t data[8];

    if (!(NRF24L01_ReadReg(NRF24L01_07_STATUS) & BV(NRF24L01_07_RX_DR))) {
        uint32_t t = lib_timers_gettimermicroseconds(packet_timer);
        if (t > rx_timeout) {
            if (boundprotocol != PROTO_NONE) {
                if (++missed_packets > 500 && bind_phase == PHASE_JUST_BOUND) {
                    valid_packets = missed_packets = bad_packets = 0;
                    bind_phase = PHASE_LOST_BINDING;
                    prepare_to_bind();
                }
            } else switch_channel();
            packet_timer = lib_timers_starttimer();
        }
        return;
    }
    packet_timer = lib_timers_starttimer();
    NRF24L01_WriteReg(NRF24L01_07_STATUS, BV(NRF24L01_07_RX_DR));
    NRF24L01_ReadPayload(packet, V2X2_PAYLOAD_SIZE);
    NRF24L01_FlushRx();
    switch_channel();
    if (!decode_packet(packet, data))
        return;
    
    for (chan = 0; chan < 8; ++chan) {
//        data = pwmRead(chan);
//    if (data < 750 || data > 2250)
//        data = 1500;

        // convert from 1000-2000 range to -1 to 1 fixedpointnum range and low pass filter to remove glitches
        lib_fp_lowpassfilter(&global.rxvalues[chan], ((fixedpointnum) data[chan] - 1500) * 131L, global.timesliver, FIXEDPOINTONEOVERONESIXTYITH, TIMESLIVEREXTRASHIFT);
    }
    // reset the failsafe timer
    global.failsafetimer = lib_timers_starttimer();
}