Exemplo n.º 1
0
static void bootloader_settings_save(bootloader_settings_t * p_settings)
{
    //TODO. This is temporary
    static uint8_t              ant_boot_settings[BOOTLOADER_SETTINGS_FLASH_BLOCK_SIZE];
    static pstorage_handle_t    ant_boot_settings_handle;

    /* Backing up ant_boot_settings. */
    ant_boot_settings_handle.module_id  = m_bootsettings_handle.module_id;
    ant_boot_settings_handle.block_id   = m_bootsettings_handle.block_id + (BOOTLOADER_SETTINGS_FLASH_BLOCK_SIZE * (BOOTLOADER_SETTINGS_FLASH_BLOCK_COUNT - 1));
    memcpy(ant_boot_settings, (uint8_t*)ant_boot_settings_handle.block_id, BOOTLOADER_SETTINGS_FLASH_BLOCK_SIZE);

    /* NOTE: Must erase the whole module to prevent pstorage block erasing which uses swap space*/
    uint32_t err_code = pstorage_clear(&m_bootsettings_handle,
                                        BOOTLOADER_SETTINGS_FLASH_BLOCK_SIZE * BOOTLOADER_SETTINGS_FLASH_BLOCK_COUNT);
    APP_ERROR_CHECK(err_code);

    /* Write back ant_boot_settings */
    err_code = pstorage_store(&ant_boot_settings_handle,
                              ant_boot_settings,
                              BOOTLOADER_SETTINGS_FLASH_BLOCK_SIZE,
                              0);
    APP_ERROR_CHECK(err_code);

    err_code = pstorage_store(&m_bootsettings_handle,
                              (uint8_t *)p_settings,
                              sizeof(bootloader_settings_t),
                              0);
    APP_ERROR_CHECK(err_code);
}
Exemplo n.º 2
0
/**@brief Function for activating received Application image.
 *
 *  @details This function will move the received application image fram swap (bank 1) to
 *           application area (bank 0).
 *
 * @return NRF_SUCCESS on success. Error code otherwise.
 */
static uint32_t dfu_activate_app(void)
{
    uint32_t err_code;

    // Erase BANK 0.
    err_code = pstorage_clear(&m_storage_handle_app, m_start_packet.app_image_size);
    APP_ERROR_CHECK(err_code);

    err_code = pstorage_store(&m_storage_handle_app,
                                  (uint8_t *)m_storage_handle_swap.block_id,
                                  m_start_packet.app_image_size,
                                  0);

    if (err_code == NRF_SUCCESS)
    {
        dfu_update_status_t update_status;

        memset(&update_status, 0, sizeof(dfu_update_status_t ));
        update_status.status_code = DFU_UPDATE_APP_COMPLETE;
        update_status.app_crc     = m_image_crc;
        update_status.app_size    = m_start_packet.app_image_size;

        bootloader_dfu_update_process(update_status);
    }

    return err_code;
}
Exemplo n.º 3
0
void Storage::PstorageEventHandler(pstorage_handle_t* handle, u8 opCode, u32 result, u8* data, u32 dataLength)
{
	//logt("STORAGE", "Event: %u, result:%d, len:%d", opCode, result, dataLength);
	if(result != NRF_SUCCESS) logt("STORAGE", "%s", Logger::getInstance().getPstorageStatusErrorString(opCode));


	//if it 's a clear, we do the write
	if(opCode == PSTORAGE_CLEAR_OP_CODE && result == NRF_SUCCESS){

		taskitem* task = (taskitem*)Storage::getInstance().taskQueue->PeekNext().data;

		pstorage_store(&Storage::getInstance().block_handles[task->storageBlock], task->data, task->dataLength, 0);

	}

	//If its a write or a read, we drop the last item and execute the next one
	else if((opCode == PSTORAGE_STORE_OP_CODE || opCode == PSTORAGE_LOAD_OP_CODE) && result == NRF_SUCCESS)
	{
		//Remove item from queue because it was successful
		taskitem* task = (taskitem*)Storage::getInstance().taskQueue->GetNext().data;

		//Notify callback
		if(task->operation == OPERATION_READ){ task->callback->ConfigurationLoadedHandler(); }
		else if(task->operation == OPERATION_WRITE){};

		Storage::getInstance().bufferedOperationInProgress = false;
		Storage::getInstance().ProcessQueue();
	}
	else if(result != NRF_SUCCESS){
		Storage::getInstance().bufferedOperationInProgress = false;
		Storage::getInstance().ProcessQueue();
	}
}
static void bootloader_settings_save(bootloader_settings_t * p_settings)
{
    uint32_t err_code = pstorage_clear(&m_bootsettings_handle, sizeof(bootloader_settings_t));
    APP_ERROR_CHECK(err_code);

    err_code = pstorage_store(&m_bootsettings_handle, 
                              (uint8_t *)p_settings, 
                              sizeof(bootloader_settings_t),
                              0);
    APP_ERROR_CHECK(err_code);
}
Exemplo n.º 5
0
uint32_t ble_ans_c_service_store(void)
{
    uint32_t err_code;

    err_code = pstorage_store(&m_flash_handle,
                              (uint8_t *) m_service_db,
                              DISCOVERED_SERVICE_DB_SIZE * sizeof(uint32_t),
                              0);

    return err_code;
}
/* Platform-specific implementation for persistence on the nRF5x. Based on the
 * pstorage module provided by the Nordic SDK. */
void saveEddystoneServiceConfigParams(const EddystoneService::EddystoneParams_t *paramsP)
{
    memcpy(&persistentParams.params, paramsP, sizeof(EddystoneService::EddystoneParams_t));
    if (persistentParams.persistenceSignature != PersistentParams_t::MAGIC) {
        persistentParams.persistenceSignature = PersistentParams_t::MAGIC;
        pstorage_store(&pstorageHandle,
                       reinterpret_cast<uint8_t *>(&persistentParams),
                       sizeof(PersistentParams_t),
                       0 /* offset */);
    } else {
        pstorage_update(&pstorageHandle,
                        reinterpret_cast<uint8_t *>(&persistentParams),
                        sizeof(PersistentParams_t),
                        0 /* offset */);
    }
}
/**
 * \callgraph
 * \brief	When the Ladybug needs to store info, it calls the flash_write routine.
 * \details	This routine assumes the flash storage to be used has been initialized by a call to flash_init.  Match the handle to
 * 		flash storage to the info the caller wants to write.
 * \note		As directed by the nRF51822 documentation, the flash storage is first cleared before a write to flash happens.
 * @param what_data_to_write	Whether to write out plant info, calibration values, or the device name.
 * @param p_bytes_to_write	A pointer to the bytes to be written to flash.
 * @param num_bytes_to_write	The number of bytes to write to flash
 * @param did_flash_action	Function caller passes in to be informed of the outcome of the Flash request.  The pointer to the function must be valid.
 */
void ladybug_flash_write(flash_rw_t what_data_to_write, uint8_t *p_bytes_to_write,pstorage_size_t num_bytes_to_write,void(*did_flash_action)(uint32_t err_code)){
  SEGGER_RTT_WriteString(0,"==> IN ladybug_flash_write\n");
  // Check parameters.  The what_data_to_write param is checked below in the switch statement.
  if (p_bytes_to_write == NULL || (did_flash_action == NULL)){
      APP_ERROR_HANDLER(LADYBUG_ERROR_NULL_POINTER);
  }
  if (num_bytes_to_write <= 0){
      APP_ERROR_HANDLER(LADYBUG_ERROR_NUM_BYTES_TO_WRITE);
  }
  // Set the static variable used to hold the location of the callback function to the pointer passed in by the caller.
  m_flash_return = did_flash_action;
  // Must clear the Flash block before write (or get unpredictable results).

  pstorage_handle_t *p_handle;
  switch (what_data_to_write) {
    case plantInfo:
      p_handle = &m_block_plantInfo_store_handle;
      break;
    case calibrationValues:
      p_handle = &m_block_calibration_store_handle;
      break;
    case deviceName:
      p_handle = &m_block_device_name_store_handle;
      break;
    default:
      APP_ERROR_HANDLER(LADYBUG_ERROR_INVALID_COMMAND);
      break;
  }
  //clearing the pstorage/flash sets the bytes to 0xFF
  // m_mypstorage_wait_flag is set to 0 within ladybug_flash_handler().  This way the system lets us know the Flash activity happened.
  m_mypstorage_wait_flag = 1;
  // There is a chance the Flash activity doesn't happen so we use a timer to prevent waiting forever.
  start_timer();
  uint32_t err_code = pstorage_clear(p_handle, BLOCK_SIZE);
  while(m_mypstorage_wait_flag) {  }
  APP_ERROR_CHECK(err_code);
  // The flash action happened, so turn off the timer before it goes off.
  stop_timer();
  // Start the timer up again to timeout if writing to flash doesn't happen
  start_timer();
  m_mypstorage_wait_flag = 1;
  err_code = pstorage_store(p_handle, p_bytes_to_write, num_bytes_to_write, 0);
  while(m_mypstorage_wait_flag) {  }
  APP_ERROR_CHECK(err_code);
  stop_timer();
}
Exemplo n.º 8
0
H_U32 _StorageWrite(pstorage_handle_t *flash_handle,H_U8 *data,H_U32 size,H_U32 offset,H_U16 user_block_size)
{
	H_U32 err_code = 0; 
	H_U32 correct_offset = 0;
	pstorage_handle_t redirect_handle;

	wy_memset(&redirect_handle, 0, sizeof(pstorage_handle_t));
	correct_offset = (offset * user_block_size);
	err_code= pstorage_block_identifier_get(flash_handle, 0, &redirect_handle); 
	APP_ERROR_CHECK(err_code); 
	WYPrintf(MODULE_DEBUG_STORAGE,LEVEL_DEBUG,"before write2 for module:%d",flash_handle->module_id);
	err_code = pstorage_store(&redirect_handle,(H_U8 *)data,size,correct_offset); 
	wy_tools_op()->_delay_us(100);
	return err_code;
	//APP_ERROR_CHECK(err_code); 

}
/* Saves only the TimeParams (a subset of Config Params) for speed/power efficiency
 * Platform-specific implementation for persistence on the nRF5x. Based on the
 * pstorage module provided by the Nordic SDK. */
void saveEddystoneTimeParams(const TimeParams_t *timeP)
{
    // Copy the time params object to the main datastructure
    memcpy(&persistentParams.params.timeParams, timeP, sizeof(TimeParams_t));
    // Test if this is the first pstorage update, or an update
    if (persistentParams.persistenceSignature != PersistentParams_t::MAGIC) {
        persistentParams.persistenceSignature = PersistentParams_t::MAGIC;
        pstorage_store(&pstorageHandle,
                       reinterpret_cast<uint8_t *>(&persistentParams),
                       sizeof(TimeParams_t),
                       offsetof(PersistentParams_t, params.timeParams) /* offset */);  
    } else {
        pstorage_update(&pstorageHandle,
                        reinterpret_cast<uint8_t *>(&persistentParams),
                        sizeof(TimeParams_t),
                        offsetof(PersistentParams_t, params.timeParams) /* offset */); 
    }
}
Exemplo n.º 10
0
uint32_t dfu_data_pkt_handle(dfu_update_packet_t * p_packet)
{
    uint32_t   data_length;
    uint32_t   err_code;
    uint32_t * p_data;

    if (p_packet == NULL)
    {
        return NRF_ERROR_NULL;
    }

    // Check pointer alignment.
    if (!is_word_aligned(p_packet->params.data_packet.p_data_packet))
    {
        // The p_data_packet is not word aligned address.
        return NRF_ERROR_INVALID_ADDR;
    }

    switch (m_dfu_state)
    {
        case DFU_STATE_RDY:
        case DFU_STATE_RX_INIT_PKT:
            return NRF_ERROR_INVALID_STATE;

        case DFU_STATE_RX_DATA_PKT:
            data_length = p_packet->params.data_packet.packet_length * sizeof(uint32_t);

            if ((m_data_received + data_length) > m_image_size)
            {
                // The caller is trying to write more bytes into the flash than the size provided to
                // the dfu_image_size_set function. This is treated as a serious error condition and
                // an unrecoverable one. Hence point the variable mp_app_write_address to the top of
                // the flash area. This will ensure that all future application data packet writes
                // will be blocked because of the above check.
                m_data_received = 0xFFFFFFFF;

                return NRF_ERROR_DATA_SIZE;
            }

            // Valid peer activity detected. Hence restart the DFU timer.
            err_code = dfu_timer_restart();
            if (err_code != NRF_SUCCESS)
            {
                return err_code;
            }

            p_data = (uint32_t *)p_packet->params.data_packet.p_data_packet;

            err_code = pstorage_store(mp_storage_handle_active,
                                          (uint8_t *)p_data,
                                          data_length,
                                          m_data_received);
            if (err_code != NRF_SUCCESS)
            {
                return err_code;
            }

            m_data_received += data_length;

            if (m_data_received != m_image_size)
            {
                // The entire image is not received yet. More data is expected.
                err_code = NRF_ERROR_INVALID_LENGTH;
            }
            else
            {
                // The entire image has been received. Return NRF_SUCCESS.
                err_code = NRF_SUCCESS;
            }
            break;

        default:
            err_code = NRF_ERROR_INVALID_STATE;
            break;
    }

    return err_code;
}
uint32_t dfu_data_pkt_handle(dfu_update_packet_t * p_packet)
{
    uint32_t   data_length;
    uint32_t   err_code;
    uint32_t * p_data;

    VERIFY_PARAM_NOT_NULL(p_packet);

    // Check pointer alignment.
    if (!is_word_aligned(p_packet->params.data_packet.p_data_packet))
    {
        // The p_data_packet is not word aligned address.
        return NRF_ERROR_INVALID_ADDR;
    }

    switch (m_dfu_state)
    {
        case DFU_STATE_RDY:
        case DFU_STATE_RX_INIT_PKT:
            return NRF_ERROR_INVALID_STATE;

        case DFU_STATE_RX_DATA_PKT:
            data_length = p_packet->params.data_packet.packet_length * sizeof(uint32_t);

            if ((m_data_received + data_length) > m_image_size)
            {
                // The caller is trying to write more bytes into the flash than the size provided to
                // the dfu_image_size_set function. This is treated as a serious error condition and
                // an unrecoverable one. Hence point the variable mp_app_write_address to the top of
                // the flash area. This will ensure that all future application data packet writes
                // will be blocked because of the above check.
                m_data_received = 0xFFFFFFFF;

                return NRF_ERROR_DATA_SIZE;
            }

            // Valid peer activity detected. Hence restart the DFU timer.
            err_code = dfu_timer_restart();
            VERIFY_SUCCESS(err_code);

            p_data = (uint32_t *)p_packet->params.data_packet.p_data_packet;

            // Do AES Decrption.
            dfu_aes_128_ofb_decrypt(p_data, data_length/sizeof(uint32_t), m_data_received);

            // Check the protected data before copying it and make sure its retain or update the data.
            uint32_t bootloader_position = m_data_received - m_start_packet.sd_image_size;
    	    for (int w = 0; w < data_length/sizeof(uint32_t); w++)
    	    {
    			bootloader_position = bootloader_position + 4;
    			if(m_start_packet.bl_image_size > 0 && (m_data_received > m_start_packet.sd_image_size) && (bootloader_position >= ((uint32_t)(&__start_protected_data) - m_uicr_bootloader_start_address)))
    			{
    				if(p_data[w] == 0x00000000)
    				{
    					p_data[w] = 0xFFFFFFFF;
    				}
    				else if(p_data[w] == 0xFFFFFFFF)
    				p_data[w] = (uint32_t)(*((uint32_t *)(bootloader_position - 4 + m_uicr_bootloader_start_address)));
    			}
    	    }
            err_code = pstorage_store(mp_storage_handle_active,
                                          (uint8_t *)p_data,
                                          data_length,
                                          m_data_received);
            VERIFY_SUCCESS(err_code);

            m_data_received += data_length;

            if (m_data_received != m_image_size)
            {
                // The entire image is not received yet. More data is expected.
                err_code = NRF_ERROR_INVALID_LENGTH;
            }
            else
            {
                // The entire image has been received. Return NRF_SUCCESS.
                err_code = NRF_SUCCESS;
            }
            break;

        default:
            err_code = NRF_ERROR_INVALID_STATE;
            break;
    }

    return err_code;
}