/* * nRF51 has a TRNG that we can access using SoftDevice. */ int eddystoneEntropyPoll(void *data, unsigned char *output, size_t len, size_t *olen) { uint8_t bytes_available = 0; // get the number of random bytes available if (sd_rand_application_bytes_available_get(&bytes_available) != NRF_SUCCESS) { return MBEDTLS_ERR_ENTROPY_SOURCE_FAILED; } // if there is more bytes available that what is requested, // truncate the number of bytes in output to len, otherwise use the total // of bytes available. const uint8_t output_len = bytes_available > len ? len : bytes_available; if (output_len) { // transfer "output_len" random bytes to output. if (sd_rand_application_vector_get(output, output_len) != NRF_SUCCESS) { return MBEDTLS_ERR_ENTROPY_SOURCE_FAILED; } } // Everything went fine, commit the output_len to the output parameter *olen = output_len; return 0; }
void trickle_setup(uint32_t i_min, uint32_t i_max, uint8_t k) { g_i_min = i_min; g_i_max = i_max; g_k = k; uint32_t error_code; rng_index = 0; /* Fill rng pool */ uint8_t bytes_available; do { error_code = sd_rand_application_bytes_available_get(&bytes_available); APP_ERROR_CHECK(error_code); if (bytes_available > 0) { uint8_t byte_count = ((bytes_available > TRICKLE_RNG_POOL_SIZE - rng_index)? (TRICKLE_RNG_POOL_SIZE - rng_index) : (bytes_available)); error_code = sd_rand_application_vector_get(&rng_vals[rng_index], byte_count); APP_ERROR_CHECK(error_code); rng_index += byte_count; } } while (rng_index < TRICKLE_RNG_POOL_SIZE); }
ret_code_t nrf_drv_rng_rand(uint8_t * p_buff, uint8_t length) { ret_code_t result; ASSERT(m_rng_cb.state == NRF_DRV_STATE_INITIALIZED); #ifndef SOFTDEVICE_PRESENT if (FIFO_LENGTH(m_rng_cb.rand_pool) >= length) { result = NRF_SUCCESS; for (uint32_t i = 0; (i < length) && (result == NRF_SUCCESS); i++) { result = app_fifo_get(&(m_rng_cb.rand_pool), &p_buff[i]); } rng_start(); } else { result = NRF_ERROR_NO_MEM; } #else result = sd_rand_application_vector_get(p_buff, length); #endif // SOFTDEVICE_PRESENT return result; }
uint8_t RNG::getRandom8() { uint8_t bytes_available = 0; uint32_t err_code; while (bytes_available < 1) { err_code = sd_rand_application_bytes_available_get(&bytes_available); APP_ERROR_CHECK(err_code); } err_code = sd_rand_application_vector_get(_randomBytes, 1); APP_ERROR_CHECK(err_code); return _randomBytes[0]; };
void random_create(uint8_t* p_result, uint8_t length) { uint32_t err_code; while (length) { uint8_t available = 0; err_code = sd_rand_application_bytes_available_get(&available); APP_ERROR_CHECK(err_code); if (available) { available = available < length ? available : length; err_code = sd_rand_application_vector_get(p_result, available); APP_ERROR_CHECK(err_code); p_result += available; length -= available; } } }
uint16_t RNG::getRandom16() { uint8_t bytes_available = 0; uint32_t err_code; while (bytes_available < 2) { err_code = sd_rand_application_bytes_available_get(&bytes_available); APP_ERROR_CHECK(err_code); } err_code = sd_rand_application_vector_get(_randomBytes, 2); APP_ERROR_CHECK(err_code); conv8_16 converter; converter.a[0] = _randomBytes[0]; converter.a[1] = _randomBytes[1]; return converter.b; };
void Node::ConfigurationLoadedHandler() { u32 err; //If config is unset, set to default if (persistentConfig.version == 0xFF) { logt("NODE", "config was empty, default config set"); persistentConfig.version = 0; persistentConfig.connectionLossCounter = 0; persistentConfig.networkId = Config->meshNetworkIdentifier; persistentConfig.reserved = 0; //Get a random number for the connection loss counter (hard on system start,...stat) while(persistentConfig.connectionLossCounter == 0){ sd_rand_application_vector_get((u8*) &persistentConfig.connectionLossCounter, 2); } //Get an id for our testdevices when not working with persistent storage InitWithTestDeviceSettings(); } clusterId = this->GenerateClusterID(); //Set the BLE address so that we have the same on every startup err = sd_ble_gap_address_set(BLE_GAP_ADDR_CYCLE_MODE_NONE, &persistentConfig.nodeAddress); APP_ERROR_CHECK(err); //Init softdevice and c libraries ScanController::Initialize(); AdvertisingController::Initialize(persistentConfig.networkId); //Fill JOIN_ME packet with data this->UpdateJoinMePacket(NULL); //Print configuration and start node logt("NODE", "Config loaded nodeId:%d, connLossCount:%u, netowrkId:%d", persistentConfig.nodeId, persistentConfig.connectionLossCounter, persistentConfig.networkId); //Go to Discovery ChangeState(discoveryState::DISCOVERY); }
ret_code_t nrf_drv_rng_rand(uint8_t * p_buff, uint8_t length) { ret_code_t err_code = NRF_SUCCESS; ASSERT(m_rng_cb.state == NRFX_DRV_STATE_INITIALIZED); #ifdef SOFTDEVICE_PRESENT do { bool sd_is_enabled; NRF_DRV_RNG_LOCK(); sd_is_enabled = NRF_DRV_RNG_SD_IS_ENABLED(); if (!sd_is_enabled) #endif // SOFTDEVICE_PRESENT { err_code = nrf_queue_read(&m_rand_pool, p_buff, (uint32_t)length); nrfx_rng_start(); } #ifdef SOFTDEVICE_PRESENT NRF_DRV_RNG_RELEASE(); if (sd_is_enabled) { err_code = sd_rand_application_vector_get(p_buff, length); if (err_code == NRF_ERROR_SOC_RAND_NOT_ENOUGH_VALUES) { err_code = NRF_ERROR_NOT_FOUND; } } } while (err_code == NRF_ERROR_SOFTDEVICE_NOT_ENABLED); #endif // SOFTDEVICE_PRESENT ASSERT((err_code == NRF_SUCCESS) || (err_code == NRF_ERROR_NOT_FOUND)); #if defined(RNG_CONFIG_RANDOM_NUMBER_LOG_ENABLED) && (RNG_CONFIG_RANDOM_NUMBER_LOG_ENABLED != 0) NRF_LOG_DEBUG("Rand buffer data:"); NRF_LOG_HEXDUMP_DEBUG((uint8_t *)p_buff, length); #endif // RNG_CONFIG_RANDOM_NUMBER_LOG_ENABLED NRF_LOG_WARNING("Function: %s, error code: %s.", (uint32_t)__func__, (uint32_t)NRF_LOG_ERROR_STRING_GET(err_code)); return err_code; }
uint32_t rand_hw_rng_get(uint8_t* p_result, uint16_t len) { #ifdef SOFTDEVICE_PRESENT uint32_t error_code; uint8_t bytes_available; uint32_t count = 0; while (count < len) { do { sd_rand_application_bytes_available_get(&bytes_available); } while (bytes_available == 0); if (bytes_available > len - count) { bytes_available = len - count; } error_code = sd_rand_application_vector_get(&p_result[count], bytes_available); if (error_code != NRF_SUCCESS) { return NRF_ERROR_INTERNAL; } count += bytes_available; } #else NRF_RNG->TASKS_START = 1; while (len) { while (!NRF_RNG->EVENTS_VALRDY); p_result[--len] = NRF_RNG->VALUE; NRF_RNG->EVENTS_VALRDY = 0; } NRF_RNG->TASKS_STOP = 1; #endif return NRF_SUCCESS; }
/** @brief Processes a ANT messages while in the requesting state. * * @param[in] Pointer to the raw ant message received. */ static void ascs_process_message_requesting(uint8_t event, uint8_t * p_event_message_buffer) { uint32_t err_code; switch (event) { case EVENT_TRANSFER_TX_FAILED: { //Randomly get a backoff between MIN_BACKOFF to m_backoff_range uint8_t num_rand_bytes_available; err_code = sd_rand_application_bytes_available_get(&num_rand_bytes_available); APP_ERROR_CHECK(err_code); //update the backoff if there is a randon number available if(num_rand_bytes_available > 0) { uint8_t rand_number; err_code = sd_rand_application_vector_get(&rand_number, 1); APP_ERROR_CHECK(err_code); m_backoff = (uint8_t) (rand_number % m_backoff_range + MIN_BACKOFF); } ascs_set_state(SEARCHING); break; } case EVENT_TRANSFER_TX_COMPLETED: { ascs_set_state(WAITING); break; } case EVENT_CHANNEL_CLOSED: case EVENT_RX: //Intentional fallthrough default: { break; } } }
/*---------------------------------------------------------------------------*/ PROCESS_THREAD(hello_world_process, ev, data) { PROCESS_BEGIN(); uint32_t err_code; // Initialize the SoftDevice handler module. SOFTDEVICE_HANDLER_INIT(NRF_CLOCK_LFCLKSRC_XTAL_20_PPM, false); // Register with the SoftDevice handler module for BLE events. err_code = softdevice_ble_evt_handler_set(ble_evt_dispatch); APP_ERROR_CHECK(err_code); // Register with the SoftDevice handler module for BLE events. err_code = softdevice_sys_evt_handler_set(sys_evt_dispatch); APP_ERROR_CHECK(err_code); ble_gap_conn_sec_mode_t sec_mode; char name_buffer[9]; sprintf(name_buffer, "%08X",(unsigned int) NRF_FICR->DEVICEID[0]); BLE_GAP_CONN_SEC_MODE_SET_OPEN(&sec_mode); err_code = sd_ble_gap_device_name_set(&sec_mode, (const uint8_t *)name_buffer, strlen(name_buffer)); APP_ERROR_CHECK(err_code); ble_advdata_t advdata; uint8_t flags = BLE_GAP_ADV_FLAG_BR_EDR_NOT_SUPPORTED; ble_advdata_service_data_t service_data[2]; uint8_t battery_data = 98;//battery_level_get(); uint32_t temperature_data = 0xFE001213; service_data[0].service_uuid = BLE_UUID_BATTERY_SERVICE; service_data[0].data.size = sizeof(battery_data); service_data[0].data.p_data = &battery_data; service_data[1].service_uuid = BLE_UUID_HEALTH_THERMOMETER_SERVICE; service_data[1].data.size = sizeof(temperature_data); service_data[1].data.p_data = (uint8_t *) &temperature_data; // Build and set advertising data memset(&advdata, 0, sizeof(advdata)); advdata.name_type = BLE_ADVDATA_FULL_NAME; advdata.include_appearance = false; advdata.flags.size = sizeof(flags); advdata.flags.p_data = &flags; advdata.service_data_count = 2; advdata.p_service_data_array = service_data; err_code = ble_advdata_set(&advdata, NULL); APP_ERROR_CHECK(err_code); ble_gap_adv_params_t adv_params; // Start advertising memset(&adv_params, 0, sizeof(adv_params)); adv_params.type = BLE_GAP_ADV_TYPE_ADV_NONCONN_IND; adv_params.p_peer_addr = NULL; adv_params.fp = BLE_GAP_ADV_FP_ANY; adv_params.interval = ADV_INTERVAL; adv_params.timeout = ADV_TIMEOUT_IN_SECONDS; err_code = sd_ble_gap_adv_start(&adv_params); APP_ERROR_CHECK(err_code); leds_off(LEDS_ALL); leds_on(LEDS_RED); PROCESS_PAUSE(); etimer_set(&et_hello, CLOCK_SECOND/2); rand_val = 0; blinks = 0; while(1) { PROCESS_WAIT_EVENT(); if(ev == PROCESS_EVENT_TIMER) { sd_rand_application_vector_get(&blinks,1); printf("Sensor says #%X\n", (unsigned int) blinks); etimer_reset(&et_hello); } } PROCESS_END(); }
/**@brief Timer callback used for transmitting Echo Request and UDP6 packets depending on * application state. * * @param[in] p_context Pointer used for passing context. No context used in this application. */ static void tx_timeout_handler(void * p_context) { uint32_t err_code; switch (m_node_state) { case APP_STATE_IPV6_IF_DOWN: { return; } case APP_STATE_IPV6_IF_UP: { APPL_LOG("[APPL]: Ping remote node. \r\n"); iot_pbuffer_alloc_param_t pbuff_param; iot_pbuffer_t * p_buffer; pbuff_param.flags = PBUFFER_FLAG_DEFAULT; pbuff_param.type = ICMP6_PACKET_TYPE; pbuff_param.length = ICMP6_ECHO_REQUEST_PAYLOAD_OFFSET + 10; // Allocate packet buffer. err_code = iot_pbuffer_allocate(&pbuff_param, &p_buffer); APP_ERROR_CHECK(err_code); ipv6_addr_t dest_ipv6_addr; memcpy(&dest_ipv6_addr.u8[0], (uint8_t[]){SERVER_IPV6_ADDRESS}, IPV6_ADDR_SIZE); iot_interface_t * p_interface; ipv6_addr_t src_ipv6_addr; err_code = ipv6_address_find_best_match(&p_interface, &src_ipv6_addr, &dest_ipv6_addr); APP_ERROR_CHECK(err_code); memset(p_buffer->p_payload + ICMP6_ECHO_REQUEST_PAYLOAD_OFFSET, 'A', 10); // Send Echo Request to peer. err_code = icmp6_echo_request(p_interface, &src_ipv6_addr, &dest_ipv6_addr, p_buffer); APP_ERROR_CHECK(err_code); err_code = app_timer_start(m_tx_node_timer, APP_PING_INTERVAL, NULL); APP_ERROR_CHECK(err_code); break; } case APP_STATE_PEER_REACHABLE: { uint32_t ind_buff = 0; err_code = get_packet_buffer_index(&ind_buff, (uint32_t *)&m_invalid_pkt_seq_num); if (err_code == NRF_ERROR_NOT_FOUND) { // Buffer of expected packets full, checking if peer is reachable. APPL_LOG("[APPL]: %ld packets transmitted, %d packets lost. Resetting counter. \r\n", \ m_pkt_seq_num, PACKET_BUFFER_LEN); m_node_state = APP_STATE_IPV6_IF_UP; m_display_state = LEDS_TX_ECHO_REQUEST; m_pkt_seq_num = 0; memset(&m_packet_buffer[0][0], 0x00, sizeof(m_packet_buffer)); err_code = app_timer_start(m_tx_node_timer, APP_PING_INTERVAL, NULL); APP_ERROR_CHECK(err_code); return; } ++m_pkt_seq_num; if (m_pkt_seq_num == INVALID_PACKET_SEQ_NUMBER) { ++m_pkt_seq_num; } test_packet_payload_t packet; uint8_t encoded_seq_num[TEST_PACKET_NUM_LEN]; UNUSED_VARIABLE(uint32_encode(m_pkt_seq_num, &encoded_seq_num[0])); // The first 4 bytes of the payload is the packet sequence number. memcpy(&packet.packet_seq_num[0], &encoded_seq_num[0], TEST_PACKET_NUM_LEN); // The rest of the payload is random bytes. do { err_code = sd_rand_application_vector_get(&packet.packet_data[0], \ sizeof(packet.packet_data)); } while (err_code == NRF_ERROR_SOC_RAND_NOT_ENOUGH_VALUES); APP_ERROR_CHECK(err_code); iot_pbuffer_alloc_param_t pbuff_param; iot_pbuffer_t * p_buffer; pbuff_param.flags = PBUFFER_FLAG_DEFAULT; pbuff_param.type = UDP6_PACKET_TYPE; pbuff_param.length = TEST_PACKET_PAYLOAD_LEN; // Allocate packet buffer. err_code = iot_pbuffer_allocate(&pbuff_param, &p_buffer); APP_ERROR_CHECK(err_code); memcpy(p_buffer->p_payload, &packet.packet_seq_num[0], TEST_PACKET_NUM_LEN); memcpy(p_buffer->p_payload+TEST_PACKET_NUM_LEN, &packet.packet_data[0], TEST_PACKET_DATA_LEN); ipv6_addr_t dest_ipv6_addr; memset(&dest_ipv6_addr, 0x00, sizeof(ipv6_addr_t)); memcpy(&dest_ipv6_addr.u8[0], (uint8_t[]){SERVER_IPV6_ADDRESS}, IPV6_ADDR_SIZE); // Transmit UDP6 packet. err_code = udp6_socket_sendto(&m_udp_socket, &dest_ipv6_addr, HTONS(UDP_PORT), p_buffer); APP_ERROR_CHECK(err_code); APPL_LOG("[APPL]: Transmitted UDP packet sequence number: %ld\r\n", m_pkt_seq_num); // Store sent packet amongst expected packets. memcpy(&m_packet_buffer[ind_buff][0], &packet.packet_seq_num[0], TEST_PACKET_NUM_LEN); memcpy(&m_packet_buffer[ind_buff][TEST_PACKET_NUM_LEN], &packet.packet_data[0], TEST_PACKET_DATA_LEN); if (m_pkt_seq_num == 1) { err_code = app_timer_start(m_tx_node_timer, (TX_INTERVAL*5), NULL); // Slow start. APP_ERROR_CHECK(err_code); } else { err_code = app_timer_start(m_tx_node_timer, TX_INTERVAL, NULL); APP_ERROR_CHECK(err_code); } break; } default: { break; } } }