Exemplo n.º 1
0
int16_t ns_dyn_mem_longest_free_sector(void)
{

    int *ptr;
    int size, h_size;
    int scanned = 0;
    int16_t longest_sector = 0;
    if (heap_main) {
        h_size = heap_size / 4;
        ptr = heap_main;
        platform_enter_critical();
        while (scanned < h_size) {
            size = *ptr;
            if (size < 0) {
                size = -size;
                if (size > longest_sector) {
                    longest_sector = size;
                }
            }
            if (size == 0) {
                heap_failure(NS_DYN_MEM_HEAP_SECTOR_CORRUPTED);
                platform_exit_critical();
                return 0;
            }
            ptr += size + 2;
            scanned += (size + 2);
        }
        platform_exit_critical();
    }
    return longest_sector;
}
Exemplo n.º 2
0
void ns_dyn_mem_free(void *block)
{
#ifndef STANDARD_MALLOC
    int *ptr = block;
    int size;

    if (!block) {
        return;
    }

    if (!heap_main) {
        heap_failure(NS_DYN_MEM_HEAP_SECTOR_UNITIALIZED);
        return;
    }

    platform_enter_critical();
    ptr --;
    //Read Current Size
    size = *ptr;
    if (size < 0) {
        heap_failure(NS_DYN_MEM_DOUBLE_FREE);
    } else if (ptr < heap_main || ptr >= heap_main_end) {
        heap_failure(NS_DYN_MEM_POINTER_NOT_VALID);
    } else if ((size < 0) || ((ptr + size) >= heap_main_end)) {
        heap_failure(NS_DYN_MEM_POINTER_NOT_VALID);
    } else {
        // Validate Sector
        if (ns_sector_validate(ptr, 1) != 0) {
            heap_failure(NS_DYN_MEM_HEAP_SECTOR_CORRUPTED);
        } else {
            //Set Pointer to sector end len
            //Link always prev sector
            //Sub sequency Free
            //Check  prev sector
            //Try Link Next between cur
            ns_free_and_merge_next_sector(ptr, size);
            //Try Merge Prev with cur
            ns_merge_prev_sector(ptr);
            if (mem_stat_info_ptr) {
                //Update Free Counter
                size = (size * sizeof(int));
                dev_stat_update(DEV_HEAP_FREE, size);
            }
        }
    }
    platform_exit_critical();
#else
    platform_enter_critical();
    free(block);
    platform_exit_critical();
#endif
}
Exemplo n.º 3
0
void fhss_receive_frame_cb(const fhss_api_t *api, uint16_t pan_id, uint8_t *source_address, uint32_t timestamp, uint8_t *synch_info, int frame_type)
{
    fhss_structure_t *fhss_structure = fhss_get_object_with_api(api);
    if (!fhss_structure) {
        return;
    }
    if (FHSS_SYNCH_FRAME == frame_type) {
        if ((fhss_structure->fhss_state == FHSS_UNSYNCHRONIZED) || fhss_structure->synch_panid != pan_id) {
            fhss_add_beacon_info(fhss_structure, pan_id, source_address, timestamp, synch_info);
        } else {
            if (!fhss_compare_with_synch_parent_address(fhss_structure, source_address)) {
                // Synch parent address needs to be updated in case parent has changed
                fhss_update_synch_parent_address(fhss_structure);
                platform_enter_critical();
                // Calculate time since the Beacon was received
                uint32_t elapsed_time = api->read_timestamp(api) - timestamp;
                // Synchronize to given PAN
                fhss_beacon_received(fhss_structure, synch_info, elapsed_time);
                platform_exit_critical();
            }
        }
    } else if (FHSS_SYNCH_REQUEST_FRAME == frame_type) {
        // If current channel is broadcast, we don't need to send another synch info on next broadcast channel.
        // Only send number of MAX_SYNCH_INFOS_PER_CHANNEL_LIST synch infos per one channel list cycle
        if ((fhss_structure->fhss_state == FHSS_SYNCHRONIZED) && (fhss_is_current_channel_broadcast(fhss_structure) == false)
                && (fhss_structure->synch_infos_sent_counter < MAX_SYNCH_INFOS_PER_CHANNEL_LIST)) {
            fhss_structure->send_synch_info_on_next_broadcast_channel = true;
        }
    }
}
Exemplo n.º 4
0
void flash_eeprom_erase_uint32(uint32_t offset)
{
    // Check offset
    if (offset >= FLASH_SIZE_EEPROM)
    {
        return;
    }

    // Disable interrupts during write
    platform_enter_critical();

    // Unlock PECR
    // Write the keys to PEKEYR
    *flash_get_PEKEYR() = PEKEY1;
    *flash_get_PEKEYR() = PEKEY2;

    // Erase word
    *mem_get_reg32(EEPROM_ADDRESS + offset) = 0;

    // Wait end of operation
    while (*flash_get_SR() & FLASH_SR__BSY)
    {
    }

    // Lock PECR
    // Set PELOCK bit in PECR
    *flash_get_PECR() |= FLASH_PECR__PELOCK;

    // Enable interrupts after write
    platform_exit_critical();
}
/*
 * \brief Function starts the CCA process before starting data transmission and copies the data to RF TX FIFO.
 *
 * \param data_ptr Pointer to TX data
 * \param data_length Length of the TX data
 * \param tx_handle Handle to transmission
 * \return 0 Success
 * \return -1 Busy
 */
int8_t rf_start_cca(uint8_t *data_ptr, uint16_t data_length, uint8_t tx_handle, data_protocol_e data_protocol )
{
    (void)data_protocol;
    /*Check if transmitter is busy*/
    if(rf_if_read_trx_state() == BUSY_RX_AACK)
    {
        /*Return busy*/
        return -1;
    }
    else
    {
        platform_enter_critical();
        /*Check if transmitted data needs to be acked*/
        if(*data_ptr & 0x20)
            need_ack = 1;
        else
            need_ack = 0;
        /*Store the sequence number for ACK handling*/
        tx_sequence = *(data_ptr + 2);

        /*Write TX FIFO*/
        rf_if_write_frame_buffer(data_ptr, (uint8_t)data_length);
        rf_flags_set(RFF_CCA);
        /*Start CCA timeout*/
        rf_cca_timer_start(RF_CCA_TIMEOUT);
        /*Store TX handle*/
        mac_tx_handle = tx_handle;
        platform_exit_critical();
    }

    /*Return success*/
    return 0;
}
/*
 * \brief Function sets the RF channel.
 *
 * \param ch New channel
 *
 * \return none
 */
void rf_channel_set(uint8_t ch)
{
    platform_enter_critical();
    rf_phy_channel = ch;
    if(ch < 0x1f)
        rf_if_set_channel_register(ch);
    platform_exit_critical();
}
/*
 * \brief Function writes various RF settings in startup.
 *
 * \param none
 *
 * \return none
 */
void rf_write_settings(void)
{
    platform_enter_critical();
    rf_if_write_rf_settings();
    /*Set output power*/
    rf_if_write_set_tx_power_register(radio_tx_power);
    /*Initialise Antenna Diversity*/
    if(rf_use_antenna_diversity)
        rf_if_write_antenna_diversity_settings();
    platform_exit_critical();
}
/*
 * \brief Function is a call back for ACK wait timeout.
 *
 * \param none
 *
 * \return none
 */
void rf_ack_wait_timer_interrupt(void)
{
    platform_enter_critical();
    /*Force PLL state*/
    rf_if_change_trx_state(FORCE_PLL_ON);
    rf_poll_trx_state_change(PLL_ON);
    /*Start receiver in RX_AACK_ON state*/
    rf_rx_mode = 0;
    rf_flags_clear(RFF_RX);
    rf_receive();
    platform_exit_critical();
}
Exemplo n.º 9
0
uint8_t heap_cor_scan(void)
{
#ifndef STANDARD_MALLOC
#ifdef HEAP_CORRUPT_CHECK
    if (heap_main) {
        int *ptr;
        int size, tail_size, h_size;
        int jump_size;
        int scanned = 0;
        h_size = heap_size / 4;
        ptr = heap_main;

        platform_enter_critical();
        while (scanned < h_size) {
            size = *ptr++;
            if (size < 0) {
                jump_size = -size;

            } else {
                jump_size = size;
            }
            if (jump_size == 0) {
                platform_exit_critical();
                return 0;
            }
            ptr += jump_size;
            tail_size = *ptr++;
            if (size != tail_size) {
                platform_exit_critical();
                return 0;
            }
            scanned += (jump_size + 2);
        }
        platform_exit_critical();
    }
#endif
#endif
    return 0;
}
Exemplo n.º 10
0
static void rf_thread_loop()
{
    for (;;) {
        ThisThread::flags_wait_all(1);

        platform_enter_critical();

        handle_IRQ_events();

        platform_exit_critical();
        NVIC_ClearPendingIRQ(Radio_1_IRQn);
        NVIC_EnableIRQ(Radio_1_IRQn);
    }
}
Exemplo n.º 11
0
void fhss_synch_state_set_cb(const fhss_api_t *api, fhss_states fhss_state, uint16_t pan_id)
{
    fhss_structure_t *fhss_structure = fhss_get_object_with_api(api);
    if (!fhss_structure) {
        return;
    }

    // State is already set
    if (fhss_structure->fhss_state == fhss_state) {
        tr_debug("Synch same state %u", fhss_state);
        return;
    }

    if (fhss_state == FHSS_UNSYNCHRONIZED) {
        tr_debug("FHSS down");
        fhss_down(fhss_structure);
    } else {
        // Do not synchronize to current pan
        if (fhss_structure->synch_panid == pan_id) {
            tr_debug("Synch same panid %u", pan_id);
            return;
        }
        uint32_t datarate = fhss_structure->callbacks.read_datarate(api);
        fhss_set_datarate(fhss_structure, datarate);
        uint8_t mac_address[8];
        fhss_structure->callbacks.read_mac_address(fhss_structure->fhss_api, mac_address);
        fhss_structure->uc_channel_index = fhss_get_offset(fhss_structure, mac_address);
        // Get Beacon info from storage
        fhss_beacon_info_t *beacon_info = fhss_get_beacon_info(fhss_structure, pan_id);
        if (beacon_info) {
            memcpy(fhss_structure->synch_parent, beacon_info->source_address, 8);
            platform_enter_critical();
            // Calculate time since the Beacon was received
            uint32_t elapsed_time = api->read_timestamp(api) - beacon_info->timestamp;
            // Synchronize to given PAN
            fhss_beacon_received(fhss_structure, beacon_info->synch_info, elapsed_time);
            platform_exit_critical();
            // Delete stored Beacon infos
            fhss_flush_beacon_info_storage(fhss_structure);
            fhss_structure->synch_panid = pan_id;
        } else if (fhss_is_synch_root(fhss_structure) == true) {
            // Synch root will start new network
            fhss_start_timer(fhss_structure, fhss_structure->synch_configuration.fhss_superframe_length, fhss_superframe_handler);
        } else {
            tr_error("Synch info not find");
        }
    }
    fhss_structure->fhss_state = fhss_state;
}
Exemplo n.º 12
0
void flash_memory_copy_upper_to_lower()
{
    // Disable interrupts during write
    platform_enter_critical();

    // Set high power mode
    pwr_main_mode(PWR_VRANGE_1);

    // Unlock program memory
    unlock_program_memory();

    // Clear PECR
    *flash_get_PECR() = 0;

    // Set the ERASE bit in PECR
    *flash_get_PECR() |= FLASH_PECR__ERASE;

    // Set the PROG bit in PECR
    *flash_get_PECR() |= FLASH_PECR__PROG;

    // Wait for BSY to be cleared
    while (*flash_get_SR() & FLASH_SR__BSY)
    {
    }

#define RAM_CODE_LENGTH ((uint32_t) flash_ram_copy_all_end - (uint32_t) flash_ram_copy_all)
    uint8_t ram_code[RAM_CODE_LENGTH + 3];

    void (*ram_func)() = (void( *)())(((uint32_t) ram_code + 3) & ~0x3);

    uint32_t func_i, copy_i;
    func_i = ((uint32_t) ram_func) & ~0x3;
    copy_i = ((uint32_t) flash_ram_copy_all) & ~0x3;

    // Copy
    memcpy((void *) func_i, (void *) copy_i, RAM_CODE_LENGTH);

    // Set pointer
    ram_func = (void( *)())(func_i | 0x1);

    // Call
    ram_func();

    // Enable interrupts after write
    platform_exit_critical();
}
/*
 * \brief Function writes 16-bit address in RF address filter.
 *
 * \param short_address Given short address
 *
 * \return none
 */
void rf_set_short_adr(uint8_t * short_address)
{
    uint8_t rf_off_flag = 0;
    platform_enter_critical();
    /*Wake up RF if sleeping*/
    if(rf_if_read_trx_state() == 0x00 || rf_if_read_trx_state() == 0x1F)
    {
        rf_if_disable_slptr();
        rf_off_flag = 1;
        rf_poll_trx_state_change(TRX_OFF);
    }
    /*Write address filter registers*/
    rf_if_write_short_addr_registers(short_address);
    /*RF back to sleep*/
    if(rf_off_flag)
        rf_if_enable_slptr();
    platform_exit_critical();
}
/*
 * \brief Function handles the received ACK frame.
 *
 * \param seq_number Sequence number of received ACK
 * \param data_pending Pending bit state in received ACK
 *
 * \return none
 */
void rf_handle_ack(uint8_t seq_number, uint8_t data_pending)
{
    phy_link_tx_status_e phy_status;
    platform_enter_critical();
    /*Received ACK sequence must be equal with transmitted packet sequence*/
    if(tx_sequence == seq_number)
    {
        rf_ack_wait_timer_stop();
        /*When data pending bit in ACK frame is set, inform NET library*/
        if(data_pending)
            phy_status = PHY_LINK_TX_DONE_PENDING;
        else
            phy_status = PHY_LINK_TX_DONE;
        /*Call PHY TX Done API*/
        arm_net_phy_tx_done(rf_radio_driver_id, mac_tx_handle,phy_status, 1, 1);
    }
    platform_exit_critical();
}
Exemplo n.º 15
0
static int8_t rf_interface_state_control(phy_interface_state_e new_state, uint8_t rf_channel)
{
    platform_enter_critical();

    switch (new_state)
    {
        /*Reset PHY driver and set to idle*/
        case PHY_INTERFACE_RESET:
            rf_abort();
            break;
        /*Disable PHY Interface driver*/
        case PHY_INTERFACE_DOWN:
            rf_abort();
            break;
        /*Enable PHY Interface driver*/
        case PHY_INTERFACE_UP:
            if (PhyPlmeSetCurrentChannelRequest(rf_channel, 0)) {
                return 1;
            }
            rf_receive();
            break;
        /*Enable wireless interface ED scan mode*/
        case PHY_INTERFACE_RX_ENERGY_STATE:
            if (PhyPlmeSetCurrentChannelRequest(rf_channel, 0)) {
                return 1;
            }
            rf_abort();
            rf_mac_ed_state_enable();
            break;
        case PHY_INTERFACE_SNIFFER_STATE:             /**< Enable Sniffer state */
            rf_promiscuous(1);
            if (PhyPlmeSetCurrentChannelRequest(rf_channel, 0)) {
                return 1;
            }
            rf_receive();
            break;
    }

    platform_exit_critical();

    return 0;
}
Exemplo n.º 16
0
flash_status_t flash_memory_erase_page(uint32_t address)
{
    // Check the address is a page border
    if (address % FLASH_SIZE_PAGE)
    {
        return FLASH_ERR_INVALID_ADDRESS;
    }

    // Disable interrupts during write
    platform_enter_critical();

    // Unlock program memory
    unlock_program_memory();

    // Set the ERASE bit in PECR
    *flash_get_PECR() |= FLASH_PECR__ERASE;

    // Set the PROG bit in PECR
    *flash_get_PECR() |= FLASH_PECR__PROG;

    // Wait for BSY to be cleared
    while (*flash_get_SR() & FLASH_SR__BSY)
    {
    }

    // Write 0x0 to start erasing
    *mem_get_reg32(address) = 0x0;

    // Wait for end of operation
    while (*flash_get_SR() & FLASH_SR__BSY)
    {
    }

    // Lock program memory
    lock_program_memory();

    // Enable interrupts after write
    platform_exit_critical();

    return FLASH_OK;
}
/*
 * \brief Function polls the RF state until it has changed to desired state.
 *
 * \param trx_state RF state
 *
 * \return none
 */
void rf_poll_trx_state_change(rf_trx_states_t trx_state)
{
    uint16_t while_counter = 0;
    platform_enter_critical();

    if(trx_state != RF_TX_START)
    {
        if(trx_state == FORCE_PLL_ON)
            trx_state = PLL_ON;
        else if(trx_state == FORCE_TRX_OFF)
            trx_state = TRX_OFF;

        while(rf_if_read_trx_state() != trx_state)
        {
            while_counter++;
            if(while_counter == 0x1ff)
                break;
        }
    }
    platform_exit_critical();
}
/*
 * \brief Function calibrates the radio.
 *
 * \param none
 *
 * \return none
 */
void rf_calibration_cb(void)
{
    /*clear tuned flag to start tuning in rf_receive*/
    rf_tuned = 0;
    /*If RF is in default receive state, start calibration*/
    if(rf_if_read_trx_state() == RX_AACK_ON)
    {
        platform_enter_critical();
        /*Set RF in PLL_ON state*/
        rf_if_change_trx_state(PLL_ON);
        /*Set RF in TRX_OFF state to start PLL tuning*/
        rf_if_change_trx_state(TRX_OFF);
        /*Set RF in RX_ON state to calibrate*/
        rf_if_change_trx_state(RX_ON);
        /*Calibrate FTN*/
        rf_if_calibration();
        /*RF is tuned now*/
        rf_tuned = 1;
        /*Back to default receive state*/
        rf_flags_clear(RFF_RX);
        rf_receive();
        platform_exit_critical();
    }
}
Exemplo n.º 19
0
flash_status_t flash_memory_write_word(uint32_t address, uint32_t word)
{
    // Disable interrupts during write
    asm volatile("cpsid i\n");

    // Unlock program memory
    unlock_program_memory();

    // Write the word to the address
    *mem_get_reg32(address) = word;

    // Wait for end of operation
    while (*flash_get_SR() & FLASH_SR__BSY)
    {
    }

    // Lock program memory
    lock_program_memory();

    // Enable interrupts after write
    platform_exit_critical();

    return FLASH_OK;
}
Exemplo n.º 20
0
static void rf_thread_loop(const void *arg)
{
    SL_DEBUG_PRINT("rf_thread_loop: starting (id: %d)\n", (int)rf_thread_id);
    for (;;) {
        osEvent event = osSignalWait(0, osWaitForever);

        if (event.status != osEventSignal) {
            continue;
        }

        platform_enter_critical();

        if (event.value.signals & SL_RX_DONE) {
            while(rx_queue_tail != rx_queue_head) {
                uint8_t* packet = (uint8_t*) rx_queue[rx_queue_tail];
                SL_DEBUG_PRINT("rPKT %d\n", packet[MAC_PACKET_INFO_LENGTH] - 2);
                device_driver.phy_rx_cb(
                        &packet[MAC_PACKET_INFO_LENGTH + 1], /* Data payload for Nanostack starts at FCS */
                        packet[MAC_PACKET_INFO_LENGTH] - 2, /* Payload length is part of frame, but need to subtract CRC bytes */
                        packet[MAC_PACKET_OFFSET_LQI], /* LQI in second byte */
                        packet[MAC_PACKET_OFFSET_RSSI], /* RSSI in first byte */
                        rf_radio_driver_id);
                rx_queue_tail = (rx_queue_tail + 1) % RF_QUEUE_SIZE;
            }

        } else if (event.value.signals & SL_TX_DONE) {
            device_driver.phy_tx_done_cb(rf_radio_driver_id,
                    current_tx_handle,
                    PHY_LINK_TX_SUCCESS,
                    1,
                    1);
        } else if (event.value.signals & SL_ACK_RECV) {
            device_driver.phy_tx_done_cb( rf_radio_driver_id,
                    current_tx_handle,
                    (event.value.signals & SL_ACK_PEND) ? PHY_LINK_TX_DONE_PENDING : PHY_LINK_TX_DONE,
                    1,
                    1);
        } else if (event.value.signals & SL_ACK_TIMEOUT) {
            waiting_for_ack = false;
            device_driver.phy_tx_done_cb(rf_radio_driver_id,
                    current_tx_handle,
                    PHY_LINK_TX_FAIL,
                    1,
                    1);
        } else if(event.value.signals & SL_TX_ERR) {
            device_driver.phy_tx_done_cb( rf_radio_driver_id,
                    current_tx_handle,
                    PHY_LINK_CCA_FAIL,
                    8,
                    1);
        } else if(event.value.signals & SL_TX_TIMEOUT) {
            device_driver.phy_tx_done_cb( rf_radio_driver_id,
                    current_tx_handle,
                    PHY_LINK_CCA_FAIL,
                    8,
                    1);
        } else if(event.value.signals & SL_CAL_REQ) {
            SL_DEBUG_PRINT("rf_thread_loop: SL_CAL_REQ signal received (unhandled)\n");
        } else if(event.value.signals & SL_RXFIFO_ERR) {
            SL_DEBUG_PRINT("rf_thread_loop: SL_RXFIFO_ERR signal received (unhandled)\n");
        } else if(event.value.signals & SL_TXFIFO_ERR) {
            SL_DEBUG_PRINT("rf_thread_loop: SL_TXFIFO_ERR signal received (unhandled)\n");
        } else if(event.value.signals & SL_QUEUE_FULL) {
            SL_DEBUG_PRINT("rf_thread_loop: SL_QUEUE_FULL signal received (packet dropped)\n");
        } else {
            SL_DEBUG_PRINT("rf_thread_loop unhandled event status: %d value: %d\n", event.status, (int)event.value.signals);
        }

        platform_exit_critical();
    }
}
/*
 * \brief Function sets the RF in RX state.
 *
 * \param none
 *
 * \return none
 */
void rf_receive(void)
{
    uint16_t while_counter = 0;
    if(rf_flags_check(RFF_ON) == 0)
    {
        rf_on();
    }
    /*If not yet in RX state set it*/
    if(rf_flags_check(RFF_RX) == 0)
    {
        platform_enter_critical();
        /*Wait while receiving data*/
        while(rf_if_read_trx_state() == BUSY_RX_AACK)
        {
            while_counter++;
            if(while_counter == 0xffff)
            {
                break;
            }
        }
        //TODO: rf_if_delay_function(50);
        /*Wake up from sleep state*/
        if(rf_if_read_trx_state() == 0x00 || rf_if_read_trx_state() == 0x1f)
        {
            rf_if_disable_slptr();
            rf_poll_trx_state_change(TRX_OFF);
        }

        rf_if_change_trx_state(PLL_ON);

        if(rf_mode == RF_MODE_SNIFFER)
        {
            rf_if_change_trx_state(RX_ON);
        }
        else
        {
            /*ACK is always received in promiscuous mode to bypass address filters*/
            if(rf_rx_mode)
            {
                rf_rx_mode = 0;
                rf_if_enable_promiscuous_mode();
            }
            else
            {
                rf_if_disable_promiscuous_mode();
            }
            rf_if_change_trx_state(RX_AACK_ON);
        }
        /*If calibration timer was unable to calibrate the RF, run calibration now*/
        if(!rf_tuned)
        {
            /*Start calibration. This can be done in states TRX_OFF, PLL_ON or in any receive state*/
            rf_if_calibration();
            /*RF is tuned now*/
            rf_tuned = 1;
        }

        rf_channel_set(rf_phy_channel);
        rf_flags_set(RFF_RX);
        rf_if_enable_rx_end_interrupt();
        platform_exit_critical();
    }
    /*Stop the running CCA process*/
    if(rf_flags_check(RFF_CCA))
        rf_cca_abort();
}
Exemplo n.º 22
0
flash_status_t flash_memory_write_half_pages(uint32_t address,
        const uint32_t *words, uint32_t words_number)
{
    // Check the address is a half page border
    if (address % (FLASH_SIZE_PAGE / 2))
    {
        return FLASH_ERR_INVALID_ADDRESS;
    }

    // Check if length has a correct words number 32 words per half page
    if (words_number % 32)
    {
        return FLASH_ERR_INVALID_LENGTH;
    }

    // Disable interrupts during write
    platform_enter_critical();

    // Unlock program memory
    unlock_program_memory();

    // Set the FPRG bit in PECR
    *flash_get_PECR() |= FLASH_PECR__FPRG;

    // Set the PROG bit in PECR
    *flash_get_PECR() |= FLASH_PECR__PROG;

    // Wait for BSY to be cleared
    while (*flash_get_SR() & FLASH_SR__BSY)
    {
    }

#define RAM_COPY_CODE_LENGTH ((uint32_t) flash_ram_copy_end - (uint32_t) flash_ram_copy)
    uint8_t ram_code[RAM_COPY_CODE_LENGTH + 3];

    void
    (*ram_func)(uint32_t * dst, const uint32_t * src, uint32_t length) =
        (void( *)(uint32_t * dst, const uint32_t * src,
                  uint32_t length))(((uint32_t) ram_code + 3) & ~0x3);

    uint32_t func_i, copy_i;
    func_i = ((uint32_t) ram_func) & ~0x3;
    copy_i = ((uint32_t) flash_ram_copy) & ~0x3;

    // Copy
    memcpy((void *) func_i, (void *) copy_i, RAM_COPY_CODE_LENGTH);

    // Set pointer
    ram_func
    = (void( *)(uint32_t * dst, const uint32_t * src, uint32_t length))(func_i
            | 0x1);

    // Call
    ram_func((uint32_t *) address, words, words_number);

    // Lock the program memory
    lock_program_memory();

    // Enable interrupts after write
    platform_exit_critical();

    return FLASH_OK;
}
Exemplo n.º 23
0
void *ns_dyn_mem_temporary_alloc(int16_t alloc_size)
{
#ifndef STANDARD_MALLOC
    int *ptr = heap_main;
    void *retval = 0;
    int h_size, alloc_sector, s_size;
    int moved = 0; //int16_t -->int

    alloc_sector = heap_alloc_internal_check(alloc_size);
    if (alloc_sector) {
        h_size = (heap_size / sizeof(int));
        platform_enter_critical();
        while (moved < h_size) {
            if (ns_sector_validate(ptr, 1) == 0) {
                s_size = *ptr;
                if (s_size == 0) {
                    heap_failure(NS_DYN_MEM_HEAP_SECTOR_CORRUPTED);
                    retval = 0;
                    break;
                } else if (s_size < 0) {
                    //Free
                    if (((-s_size) >= alloc_sector)) {
                        /*found block*/
                        //Convert Current size
                        s_size = -s_size;
                        if (s_size > (alloc_sector + 4)) {
                            //debug("Bigger\r\n");
                            //Set sectror start len & Move pointer to Allocated data sector
                            *ptr++ = alloc_sector;
                            //Set return Pointer
                            retval = (void *) ptr;
                            ptr += alloc_sector;
                            *ptr++ = alloc_sector;
                            //Now set new slice start & End len fields
                            //Move pointer to New Free Sector
                            //Calculate new sector size
                            alloc_sector += 2; //
                            s_size = (s_size - alloc_sector);

                            *ptr++ = -(s_size);
                            ptr += s_size;
                            *ptr = -(s_size);
                            if (mem_stat_info_ptr) {
                                alloc_sector -= 2;
                            }
                        } else {
                            //debug("USE Same\r\n");
                            //Move pointer to Allocated data sector
                            *ptr++ = s_size;
                            //Set return Pointer
                            retval = (void *) ptr;
                            ptr += s_size;//Move Pointer  to next free place
                            *ptr = s_size;
                        }
                        break;
                    } else {
                        //Set Number from negative to Positive
                        s_size = -s_size;
                    }

                }
                //Allocated sector
                //Move
                //Set Move field
                moved += (s_size + 2);
                ptr += 2; //Skip Both of length fileds
                ptr += s_size; //Move Pointer  to next free place
                if (heap_main_end == ptr) {
                    break;
                }
            } else {
                heap_failure(NS_DYN_MEM_HEAP_SECTOR_CORRUPTED);
                retval = 0;
                break;
            }
        }
        if (mem_stat_info_ptr) {
            alloc_size = (alloc_sector * sizeof(int));
            if (retval) {

                //Update Allocate OK
                dev_stat_update(DEV_HEAP_ALLOC_OK, alloc_size);

            } else {
                //Update Allocate Fail
                dev_stat_update(DEV_HEAP_ALLOC_FAIL, alloc_size);
            }
        }
        platform_exit_critical();
    }
    return retval;

#else

    void *retval = 0;
    if (alloc_size) {
        platform_enter_critical();
        retval = malloc(alloc_size);
        platform_exit_critical();
    }
    return retval;
#endif
}
Exemplo n.º 24
0
static int8_t rf_start_cca(uint8_t *data_ptr, uint16_t data_length, uint8_t tx_handle, data_protocol_e data_protocol)
{
    uint32_t reg, tx_len;
    uint32_t irqSts;
    volatile uint8_t *pPB;
    uint8_t i;
    uint32_t tx_warmup_time;

    platform_enter_critical();

    if (mPhySeqState == gRX_c) {
        rf_abort();
    }

    /* Check if transmitter is busy*/
    if (mPhySeqState != gIdle_c) {
        platform_exit_critical();
        /*Return busy*/
        return -1;
    }

    /*Store TX handle*/
    rf_mac_handle = tx_handle;

    /* Check if transmitted data needs to be acked */
    need_ack = (*data_ptr & 0x20) == 0x20;

    /* Load data into Packet Buffer */
    pPB = (uint8_t*)ZLL->PKT_BUFFER_TX;

    tx_len = data_length + 2;
    *pPB++ = tx_len; /* including 2 bytes of FCS */

    for (i = 0; i < data_length; i++) {
        *pPB++ = *data_ptr++;
    }

    reg = ZLL->PHY_CTRL;

    /* Perform CCA before TX */
    reg |= ZLL_PHY_CTRL_CCABFRTX_MASK;

    /* Set CCA mode 1 */
    reg &= ~(ZLL_PHY_CTRL_CCATYPE_MASK);
    reg |= ZLL_PHY_CTRL_CCATYPE(gCcaCCA_MODE1_c);
    ZLL->PHY_CTRL = reg;

    /* Perform TxRxAck sequence if required by phyTxMode */
    if (need_ack) {
        ZLL->PHY_CTRL |= ZLL_PHY_CTRL_RXACKRQD_MASK;
        mPhySeqState = gTR_c;
    } else {
        ZLL->PHY_CTRL &= ~ZLL_PHY_CTRL_RXACKRQD_MASK;
        mPhySeqState = gTX_c;
    }

    /* Ensure that no spurious interrupts are raised */
    irqSts = ZLL->IRQSTS;
    irqSts &= ~(ZLL_IRQSTS_TMR1IRQ_MASK | ZLL_IRQSTS_TMR4IRQ_MASK);
    irqSts |= ZLL_IRQSTS_TMR3MSK_MASK;
    ZLL->IRQSTS = irqSts;

    tx_warmup_time = (XCVR_TSM->END_OF_SEQ & XCVR_TSM_END_OF_SEQ_END_OF_TX_WU_MASK) >>
                      XCVR_TSM_END_OF_SEQ_END_OF_TX_WU_SHIFT;

    /* Compute warmup times (scaled to 16us) */
    if (tx_warmup_time & 0x0F) {
        tx_warmup_time = 1 + (tx_warmup_time >> 4);
    } else {
Exemplo n.º 25
0
/*
 * \brief Function starts the CCA process before starting data transmission and copies the data to RF TX FIFO.
 *
 * \param data_ptr Pointer to TX data
 * \param data_length Length of the TX data
 * \param tx_handle Handle to transmission
 * \return 0 Success
 * \return -1 Busy
 */
static int8_t rf_start_cca(uint8_t *data_ptr, uint16_t data_length, uint8_t tx_handle, data_protocol_e data_protocol )
{
    switch(radio_state) {
    case RADIO_UNINIT:
        SL_DEBUG_PRINT("rf_start_cca: Radio uninit\n");
        return -1;
    case RADIO_INITING:
        SL_DEBUG_PRINT("rf_start_cca: Radio initing\n");
        return -1;
    case RADIO_CALIBRATION:
        SL_DEBUG_PRINT("rf_start_cca: Radio calibrating\n");
        return -1;
    case RADIO_TX:
        SL_DEBUG_PRINT("rf_start_cca: Radio in TX mode\n");
        return -1;
    case RADIO_IDLE:
    case RADIO_RX:
        // If we're still waiting for an ACK, don't mess up the internal state
        if(waiting_for_ack || RAIL_GetRadioState(gRailHandle) == RAIL_RF_STATE_TX) {
            if((RAIL_GetTime() - last_tx) < 30000) {
                SL_DEBUG_PRINT("rf_start_cca: Still waiting on previous ACK\n");
                return -1;
            } else {
                SL_DEBUG_PRINT("rf_start_cca: TXerr\n");
            }
        }

        platform_enter_critical();

        /* Since we set up Nanostack to give us a 1-byte PHY header, we get the one extra byte at the start of data_ptr
         * and need to populate it with the MAC-frame length byte (including the 2-byte hardware-inserted CRC) */
        data_ptr[0] = data_length + 2;

        RAIL_Idle(gRailHandle, RAIL_IDLE_ABORT, true);
        RAIL_WriteTxFifo(gRailHandle, data_ptr, data_length + 1, true);
        radio_state = RADIO_TX;

        RAIL_TxOptions_t txOpt = RAIL_TX_OPTIONS_DEFAULT;
        //Check to see whether we'll be waiting for an ACK
        if(data_ptr[1] & (1 << 5)) {
            txOpt |= RAIL_TX_OPTION_WAIT_FOR_ACK;
            waiting_for_ack = true;
        } else {
            waiting_for_ack = false;
        }

        SL_DEBUG_PRINT("rf_start_cca: Called TX, len %d, chan %d, ack %d\n", data_length, channel, waiting_for_ack ? 1 : 0);

        if(RAIL_StartCcaCsmaTx(gRailHandle, channel, txOpt, &csma_config, NULL) == 0) {
          //Save packet number and sequence
          current_tx_handle = tx_handle;
          current_tx_sequence = data_ptr[3];
          platform_exit_critical();
          return 0;
        } else {
          RAIL_Idle(gRailHandle, RAIL_IDLE_ABORT, true);
          RAIL_StartRx(gRailHandle, channel, NULL);
          radio_state = RADIO_RX;
          platform_exit_critical();
          return -1;
        }
    }
    //Should never get here...
    return -1;
}
Exemplo n.º 26
0
static void rf_if_unlock(void)
{
    platform_exit_critical();
}
Exemplo n.º 27
0
/*
 * \brief Function starts the CCA process before starting data transmission and copies the data to RF TX FIFO.
 *
 * \param data_ptr Pointer to TX data
 * \param data_length Length of the TX data
 * \param tx_handle Handle to transmission
 * \return 0 Success
 * \return -1 Busy
 */
static int8_t rf_start_cca(uint8_t *data_ptr, uint16_t data_length, uint8_t tx_handle, data_protocol_e data_protocol )
{

    RAIL_TxData_t txData = {
        data_ptr,
        data_length + 3
    };

    switch(radio_state) {
    case RADIO_UNINIT:
        SL_DEBUG_PRINT("rf_start_cca: Radio uninit\n");
        return -1;
    case RADIO_INITING:
        SL_DEBUG_PRINT("rf_start_cca: Radio initing\n");
        return -1;
    case RADIO_CALIBRATION:
        SL_DEBUG_PRINT("rf_start_cca: Radio calibrating\n");
        return -1;
    case RADIO_TX:
        SL_DEBUG_PRINT("rf_start_cca: Radio in TX mode\n");
        return -1;
    case RADIO_IDLE:
    case RADIO_RX:
        // If we're still waiting for an ACK, don't mess up the internal state
        if(waiting_for_ack || RAIL_RfStateGet() == RAIL_RF_STATE_TX) {
            if((RAIL_GetTime() - last_tx) < 30000) {
                SL_DEBUG_PRINT("rf_start_cca: Still waiting on previous ACK\n");
                return -1;
            } else {
                SL_DEBUG_PRINT("rf_start_cca: TXerr\n");
            }
        }

        platform_enter_critical();

        data_ptr[0] = data_length + 2;
        RAIL_RfIdleExt(RAIL_IDLE_ABORT , true);
        RAIL_TxDataLoad(&txData);
        radio_state = RADIO_TX;

        RAIL_TxOptions_t txOpt;
        //Check to see whether we'll be waiting for an ACK
        if(data_ptr[1] & (1 << 5)) {
            txOpt.waitForAck = true;
            waiting_for_ack = true;
        } else {
            txOpt.waitForAck = false;
        }

        SL_DEBUG_PRINT("rf_start_cca: Called TX, len %d, chan %d, ack %d\n", data_length, channel, waiting_for_ack ? 1 : 0);

        if(RAIL_TxStartWithOptions(channel, &txOpt, &RAIL_CcaCsma, (RAIL_CsmaConfig_t*) &csma_config) == 0) {
          //Save packet number and sequence
          current_tx_handle = tx_handle;
          current_tx_sequence = data_ptr[3];
          platform_exit_critical();
          return 0;
        } else {
          RAIL_RfIdle();
          RAIL_RxStart(channel);
          radio_state = RADIO_RX;
          platform_exit_critical();
          return -1;
        }
    }
    //Should never get here...
    platform_exit_critical();
    return -1;
}
Exemplo n.º 28
0
static void rf_thread_loop(const void *arg)
{
    SL_DEBUG_PRINT("rf_thread_loop: starting (id: %d)\n", rf_thread_id);
    for (;;) {
        osEvent event = osSignalWait(0, osWaitForever);

        if (event.status != osEventSignal) {
            continue;
        }

        platform_enter_critical();

        if (event.value.signals & SL_RX_DONE) {
            while(rx_queue_tail != rx_queue_head) {
                void* handle = (void*) rx_queue[rx_queue_tail];
                RAIL_RxPacketInfo_t* info = (RAIL_RxPacketInfo_t*) memoryPtrFromHandle(handle);
                device_driver.phy_rx_cb(
                        info->dataPtr + 1,
                        info->dataLength - 1, 
                        info->appendedInfo.lqi, 
                        info->appendedInfo.rssiLatch, 
                        rf_radio_driver_id);

                memoryFree(handle);
                rx_queue[rx_queue_tail] = NULL;
                rx_queue_tail = (rx_queue_tail + 1) % RF_QUEUE_SIZE;
            }

        } else if (event.value.signals & SL_TX_DONE) {
            device_driver.phy_tx_done_cb(rf_radio_driver_id,
                    current_tx_handle,
                    PHY_LINK_TX_SUCCESS,
                    1,
                    1);
        } else if (event.value.signals & SL_ACK_RECV) {
            device_driver.phy_tx_done_cb( rf_radio_driver_id,
                    current_tx_handle,
                    (event.value.signals & SL_ACK_PEND) ? PHY_LINK_TX_DONE_PENDING : PHY_LINK_TX_DONE,
                    1,
                    1);
        } else if (event.value.signals & SL_ACK_TIMEOUT) {
            waiting_for_ack = false;
            device_driver.phy_tx_done_cb(rf_radio_driver_id,
                    current_tx_handle,
                    PHY_LINK_TX_FAIL,
                    1,
                    1);
        } else if(event.value.signals & SL_TX_ERR) {
            device_driver.phy_tx_done_cb( rf_radio_driver_id,
                    current_tx_handle,
                    PHY_LINK_CCA_FAIL,
                    8,
                    1);
        } else if(event.value.signals & SL_CAL_REQ) {
            SL_DEBUG_PRINT("rf_thread_loop: SL_CAL_REQ signal received (unhandled)\n");
        } else if(event.value.signals & SL_RXFIFO_ERR) {
            SL_DEBUG_PRINT("rf_thread_loop: SL_RXFIFO_ERR signal received (unhandled)\n");
        } else if(event.value.signals & SL_TXFIFO_ERR) {
            SL_DEBUG_PRINT("rf_thread_loop: SL_TXFIFO_ERR signal received (unhandled)\n");
        } else if(event.value.signals & SL_QUEUE_FULL) {
            SL_DEBUG_PRINT("rf_thread_loop: SL_QUEUE_FULL signal received (packet dropped)\n");
        } else {
            SL_DEBUG_PRINT("rf_thread_loop unhandled event status: %d value: %d\n", event.status, event.value.signals);
        }

        platform_exit_critical();
    }
}