diff --git a/esp32/mods/machrtc.c b/esp32/mods/machrtc.c index f2a819b68b..df91a404ce 100644 --- a/esp32/mods/machrtc.c +++ b/esp32/mods/machrtc.c @@ -48,7 +48,6 @@ typedef struct _mach_rtc_obj_t { bool synced; } mach_rtc_obj_t; -static RTC_DATA_ATTR uint64_t delta_from_epoch_til_boot; static RTC_DATA_ATTR uint32_t rtc_user_mem_len; static RTC_DATA_ATTR uint8_t rtc_user_mem_data[MEM_USER_MAXLEN]; @@ -61,10 +60,10 @@ void rtc_init0(void) { void mach_rtc_set_us_since_epoch(uint64_t nowus) { struct timeval tv; - // store the packet timestamp - gettimeofday(&tv, NULL); - delta_from_epoch_til_boot = nowus - (uint64_t)((tv.tv_sec * 1000000ull) + tv.tv_usec); + tv.tv_usec = nowus % 1000000ull; + tv.tv_sec = nowus / 1000000ull; + settimeofday(&tv, NULL); } void mach_rtc_synced (void) { @@ -78,8 +77,9 @@ bool mach_is_rtc_synced (void) { uint64_t mach_rtc_get_us_since_epoch(void) { struct timeval tv; gettimeofday(&tv, NULL); - return (uint64_t)((tv.tv_sec * 1000000ull) + tv.tv_usec) + delta_from_epoch_til_boot; -}; + return (uint64_t)(tv.tv_sec * 1000000ull ) + (tv.tv_usec); + +} STATIC uint64_t mach_rtc_datetime_us(const mp_obj_t datetime) { timeutils_struct_time_t tm; @@ -132,8 +132,6 @@ STATIC void mach_rtc_datetime(const mp_obj_t datetime) { if (datetime != mp_const_none) { useconds = mach_rtc_datetime_us(datetime); mach_rtc_set_us_since_epoch(useconds); - } else { - mach_rtc_set_us_since_epoch(0); } } @@ -197,14 +195,10 @@ STATIC MP_DEFINE_CONST_FUN_OBJ_KW(mach_rtc_init_obj, 1, mach_rtc_init); STATIC mp_obj_t mach_rtc_now (mp_obj_t self_in) { timeutils_struct_time_t tm; uint64_t useconds; + + useconds = mach_rtc_get_us_since_epoch(); - struct timeval now; - gettimeofday(&now, NULL); - - // get the time from the RTC - useconds = (now.tv_sec * 1000000ull ) + (now.tv_usec); timeutils_seconds_since_epoch_to_struct_time((useconds) / 1000000ull, &tm); - mp_obj_t tuple[8] = { mp_obj_new_int(tm.tm_year), mp_obj_new_int(tm.tm_mon), diff --git a/esp32/mods/modbt.c b/esp32/mods/modbt.c index 8b8ae40d1d..529159630b 100644 --- a/esp32/mods/modbt.c +++ b/esp32/mods/modbt.c @@ -1062,12 +1062,9 @@ static void gatts_event_handler(esp_gatts_cb_event_t event, esp_gatt_if_t gatts_ /// \class Bluetooth static mp_obj_t bt_init_helper(bt_obj_t *self, const mp_arg_val_t *args) { if (!self->init) { - if (!self->controller_active) { - esp_bt_controller_config_t bt_cfg = BT_CONTROLLER_INIT_CONFIG_DEFAULT(); - esp_bt_controller_init(&bt_cfg); - self->controller_active = true; - } + esp_bt_controller_config_t bt_cfg = BT_CONTROLLER_INIT_CONFIG_DEFAULT(); + esp_bt_controller_init(&bt_cfg); esp_bt_controller_enable(ESP_BT_MODE_BLE); if (ESP_OK != esp_bluedroid_init()) { diff --git a/esp32/mods/modcoap.c b/esp32/mods/modcoap.c index cae166d61d..ac8a98be41 100644 --- a/esp32/mods/modcoap.c +++ b/esp32/mods/modcoap.c @@ -43,7 +43,6 @@ typedef struct mod_coap_resource_obj_s { coap_resource_t* coap_resource; struct mod_coap_resource_obj_s* next; uint8_t* value; - unsigned char* uri; uint32_t max_age; uint16_t etag_value; uint16_t value_len; @@ -208,9 +207,10 @@ STATIC mod_coap_resource_obj_t* add_resource(const char* uri, uint8_t mediatype, resource->next = NULL; // uri parameter pointer will be destroyed, pass a pointer to a permanent location - resource->uri = m_malloc(strlen(uri)); - memcpy(resource->uri, uri, strlen(uri)); - resource->coap_resource = coap_resource_init((const unsigned char* )resource->uri, strlen(uri), 0); + unsigned char* uri_ptr = (unsigned char*)malloc(strlen(uri)); + memcpy(uri_ptr, uri, strlen(uri)); + // Pass COAP_RESOURCE_FLAGS_RELEASE_URI so Coap Library will free up the memory allocated to store the URI when the Resource is deleted + resource->coap_resource = coap_resource_init(uri_ptr, strlen(uri), COAP_RESOURCE_FLAGS_RELEASE_URI); if(resource->coap_resource != NULL) { // Add the resource to the Coap context coap_add_resource(context->context, resource->coap_resource); @@ -238,7 +238,7 @@ STATIC mod_coap_resource_obj_t* add_resource(const char* uri, uint8_t mediatype, return resource; } else { - m_free(resource->uri); + free(uri_ptr); m_del_obj(mod_coap_resource_obj_t, resource); // Resource cannot be created return NULL; @@ -278,14 +278,12 @@ STATIC void remove_resource_by_key(coap_key_t key) { previous->next = current->next; } - // Free the URI - m_free(current->uri); // Free the resource in coap's scope coap_delete_resource(context->context, key); // Free the element in MP scope - m_free(current->value); + free(current->value); // Free the resource itself - m_free(current); + m_del_obj(mod_coap_resource_obj_t, current); return; } @@ -320,7 +318,7 @@ STATIC void resource_update_value(mod_coap_resource_obj_t* resource, mp_obj_t ne // Invalidate current data first resource->value_len = 0; - m_free(resource->value); + free(resource->value); if (mp_obj_is_integer(new_value)) { @@ -334,7 +332,7 @@ STATIC void resource_update_value(mod_coap_resource_obj_t* resource, mp_obj_t ne } // Allocate memory for the new data - resource->value = m_malloc(resource->value_len); + resource->value = malloc(resource->value_len); memcpy(resource->value, &value, sizeof(value)); } else { @@ -344,7 +342,7 @@ STATIC void resource_update_value(mod_coap_resource_obj_t* resource, mp_obj_t ne resource->value_len = value_bufinfo.len; // Allocate memory for the new data - resource->value = m_malloc(resource->value_len); + resource->value = malloc(resource->value_len); memcpy(resource->value, value_bufinfo.buf, resource->value_len); } } @@ -748,16 +746,13 @@ STATIC coap_pdu_t * modcoap_new_request // Helper function to create a new option for a request message STATIC coap_list_t * modcoap_new_option_node(unsigned short key, unsigned int length, unsigned char *data) { - coap_list_t *node = m_malloc(sizeof(coap_list_t) + sizeof(coap_option) + length); + coap_list_t *node = malloc(sizeof(coap_list_t) + sizeof(coap_option) + length); if (node) { coap_option *option; option = (coap_option *)(node->data); COAP_OPTION_KEY(*option) = key; COAP_OPTION_LENGTH(*option) = length; memcpy(COAP_OPTION_DATA(*option), data, length); - } else { - m_free(node); - node = NULL; } return node; @@ -937,7 +932,7 @@ STATIC mp_obj_t mod_coap_init(mp_uint_t n_args, const mp_obj_t *pos_args, mp_map // Only 1 context is supported currently if(initialized == false) { - MP_STATE_PORT(coap_ptr) = m_malloc(sizeof(mod_coap_obj_t)); + MP_STATE_PORT(coap_ptr) = m_new_obj(mod_coap_obj_t); coap_obj_ptr = MP_STATE_PORT(coap_ptr); coap_obj_ptr->context = NULL; coap_obj_ptr->resources = NULL; @@ -1235,19 +1230,21 @@ STATIC mp_obj_t mod_coap_send_request(mp_uint_t n_args, const mp_obj_t *pos_args //TODO: allocate the proper length size_t length = 300; unsigned char* path = malloc(length); - int segments = coap_split_path(coap_uri.path.s, coap_uri.path.length, path, &length); + // Need to use a different pointer because when the segments are composed the pointer itself is moved + unsigned char* path_segment = path; + int segments = coap_split_path(coap_uri.path.s, coap_uri.path.length, path_segment, &length); // Insert the segments as separate URI-Path options while (segments--) { - node = modcoap_new_option_node(COAP_OPTION_URI_PATH, COAP_OPT_LENGTH(path), COAP_OPT_VALUE(path)); + node = modcoap_new_option_node(COAP_OPTION_URI_PATH, COAP_OPT_LENGTH(path_segment), COAP_OPT_VALUE(path_segment)); if(node != NULL) { LL_APPEND(coap_obj_ptr->optlist, node); } - - path += COAP_OPT_SIZE(path); + // Move the path_segment pointer to the next segment + path_segment += COAP_OPT_SIZE(path_segment); } - + // Free up the memory using the pointer pointing to the beginning of the memory area free(path); // Put Content Format option if given @@ -1271,7 +1268,7 @@ STATIC mp_obj_t mod_coap_send_request(mp_uint_t n_args, const mp_obj_t *pos_args while(coap_obj_ptr->optlist != NULL) { next = coap_obj_ptr->optlist->next; coap_obj_ptr->optlist->next = NULL; - m_free(coap_obj_ptr->optlist); + free(coap_obj_ptr->optlist); coap_obj_ptr->optlist = next; } diff --git a/esp32/mods/modpycom.c b/esp32/mods/modpycom.c index a4007622f0..0e7f99ce0f 100644 --- a/esp32/mods/modpycom.c +++ b/esp32/mods/modpycom.c @@ -1013,6 +1013,53 @@ STATIC mp_obj_t mod_pycom_sigfox_info (size_t n_args, const mp_obj_t *pos_args, } STATIC MP_DEFINE_CONST_FUN_OBJ_KW(mod_pycom_sigfox_info_obj, 0, mod_pycom_sigfox_info); +// This function creates a 128 bit long UUID stored in a byte array in Little Endian order from an input String +STATIC mp_obj_t create_128bit_le_uuid_from_string(mp_obj_t uuid_in) { + + size_t length; + uint8_t new_uuid[16]; + uint8_t i, j; + + const char* uuid_char_in = mp_obj_str_get_data(uuid_in, &length); + // 1 character is stored on 1 byte because we received a String + // For 128 bit UUID maximum 32 characters long String can be accepted + if (length > 32) { + nlr_raise(mp_obj_new_exception_msg(&mp_type_ValueError, "Input string must not be longer than 32 characters!")); + } + + // Pre-fill the whole array with 0 because the remaining/not given digits will be 0 + char uuid_char[32] = {0}; + memcpy(uuid_char, uuid_char_in, length); + + for(i = 0, j = 0; i < 32; i = i+2) { + + uint8_t lower_nibble = 0; + uint8_t upper_nibble = 0; + + if(uuid_char[i] > 0) { + upper_nibble = hex_from_char(uuid_char[i]); + } + + if(uuid_char[i+1] > 0) { + lower_nibble = hex_from_char(uuid_char[i+1]); + } + + if(lower_nibble == 16 || upper_nibble == 16) { + nlr_raise(mp_obj_new_exception_msg(&mp_type_ValueError, "UUID must only contain hexadecimal digits!")); + } + + // Pack together the 4 bits digits into 1 byte + // Convert to Little Endian order because we expect that the digits of the input String follows the Natural Byte (Big Endian) order + new_uuid[15-j] = lower_nibble | (upper_nibble << 4); + j++; + } + + mp_obj_t new_uuid_mp = mp_obj_new_bytearray(16, new_uuid); + return new_uuid_mp; + +} +STATIC MP_DEFINE_CONST_FUN_OBJ_1(create_128bit_le_uuid_from_string_obj, create_128bit_le_uuid_from_string); + STATIC const mp_map_elem_t pycom_module_globals_table[] = { { MP_OBJ_NEW_QSTR(MP_QSTR___name__), MP_OBJ_NEW_QSTR(MP_QSTR_pycom) }, { MP_OBJ_NEW_QSTR(MP_QSTR_heartbeat), (mp_obj_t)&mod_pycom_heartbeat_obj }, @@ -1039,6 +1086,8 @@ STATIC const mp_map_elem_t pycom_module_globals_table[] = { { MP_OBJ_NEW_QSTR(MP_QSTR_wifi_pwd_sta), (mp_obj_t)&mod_pycom_wifi_pwd_sta_obj }, { MP_OBJ_NEW_QSTR(MP_QSTR_wifi_pwd_ap), (mp_obj_t)&mod_pycom_wifi_pwd_ap_obj }, { MP_OBJ_NEW_QSTR(MP_QSTR_wifi_mode_on_boot), (mp_obj_t)&mod_pycom_wifi_mode_obj }, + { MP_OBJ_NEW_QSTR(MP_QSTR_create_128bit_le_uuid_from_string), (mp_obj_t)&create_128bit_le_uuid_from_string_obj }, + #if defined(FIPY) || defined(LOPY4) || defined(SIPY) { MP_OBJ_NEW_QSTR(MP_QSTR_sigfox_info), (mp_obj_t)&mod_pycom_sigfox_info_obj }, diff --git a/esp32/pycom_version.h b/esp32/pycom_version.h index b85d758bb1..3a24ceee49 100644 --- a/esp32/pycom_version.h +++ b/esp32/pycom_version.h @@ -10,7 +10,7 @@ #ifndef VERSION_H_ #define VERSION_H_ -#define SW_VERSION_NUMBER "1.20.2.r3" +#define SW_VERSION_NUMBER "1.20.2.r4" #define LORAWAN_VERSION_NUMBER "1.0.2"