Skip to content
This repository was archived by the owner on May 23, 2023. It is now read-only.

Commit c52b039

Browse files
author
Jarkko Paso
authored
Merge pull request ARMmbed#1584 from ARMmbed/IOTTHD-2055
FHSS: Synch callback to write ufsi
2 parents 3e8112b + ac58048 commit c52b039

File tree

11 files changed

+110
-78
lines changed

11 files changed

+110
-78
lines changed

nanostack/fhss_api.h

Lines changed: 4 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -38,15 +38,6 @@ typedef struct fhss_callback fhss_callback_t;
3838
#define FHSS_SYNCH_REQUEST_FRAME 1 /**< FHSS synchronization request frame */
3939
#define FHSS_DATA_FRAME 2 /**< FHSS data frame */
4040

41-
/**
42-
* @brief FHSS information element types.
43-
*/
44-
#define FHSS_UTT_IE 0 /**< UTT-IE */
45-
#define FHSS_BT_IE 1 /**< BT-IE */
46-
#define FHSS_US_IE 2 /**< US-IE */
47-
#define FHSS_BS_IE 3 /**< BS-IE */
48-
#define FHSS_PLAIN_SYNCH_INFO 4 /**< Plain synchronization information */
49-
5041
/**
5142
* @brief FHSS synchronization info length.
5243
*/
@@ -91,7 +82,6 @@ typedef bool fhss_use_broadcast_queue(const fhss_api_t *api, bool is_broadcast_a
9182
* @return -1 Transmission of the packet is currently not allowed, try again.
9283
* @return -2 Invalid api.
9384
* @return -3 Broadcast packet on Unicast channel (not allowed), push packet back to queue.
94-
* @return -4 Synchronization info missing.
9585
*/
9686
typedef int fhss_tx_handle(const fhss_api_t *api, bool is_broadcast_addr, uint8_t *destination_address, int frame_type, uint16_t frame_length, uint8_t phy_header_length, uint8_t phy_tail_length, uint32_t tx_time);
9787

@@ -164,13 +154,13 @@ typedef uint16_t fhss_get_retry_period(const fhss_api_t *api, uint8_t *destinati
164154
/**
165155
* @brief Write synchronization info to given pointer.
166156
* @param api FHSS instance.
167-
* @param info_ptr Pointer to written data.
168-
* @param info_type Type of the written info (UTT-IE, BT-IE, US-IE, BS-IE).
169-
* @param frame_type_id Frame type of packet which will be written in info element.
157+
* @param ptr Pointer to data. Start of written data for Synch frame. Start of IE header for Data frame.
158+
* @param length Length of IE header. Ignored when Synch frame.
159+
* @param frame_type Frame type of packet (Frames types are defined by FHSS api).
170160
* @param tx_time TX time must be referenced to the first symbol following the SFD of the transmitted frame.
171161
* @return -1 on fail, write length otherwise.
172162
*/
173-
typedef int16_t fhss_write_synch_info(const fhss_api_t *api, uint8_t *info_ptr, int info_type, int frame_type_id, uint32_t tx_time);
163+
typedef int16_t fhss_write_synch_info(const fhss_api_t *api, uint8_t *ptr, uint8_t length, int frame_type, uint32_t tx_time);
174164

175165
/**
176166
* @brief Initialize MAC functions.

nanostack/platform/arm_hal_phy.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,7 @@ typedef enum {
5656
PHY_EXTENSION_READ_LINK_STATUS, /**< Net library could read link status. */
5757
PHY_EXTENSION_CONVERT_SIGNAL_INFO, /**< Convert signal info. */
5858
PHY_EXTENSION_ACCEPT_ANY_BEACON, /**< Set boolean true or false for accept beacon from other Pan-ID than configured. Default value should be false */
59-
PHY_EXTENSION_SET_TX_TIME, /**< Net library sets transmission time based on global time stamp. Max. 65ms from setting to TX */
59+
PHY_EXTENSION_SET_TX_TIME, /**< Net library sets transmission time based on global time stamp. Max. 65ms from setting to TX. If TX time is set to zero, it should be ignored.*/
6060
PHY_EXTENSION_READ_RX_TIME, /**< Read the time of last reception based on global time stamp. */
6161
} phy_extension_type_e;
6262

source/MAC/IEEE802_15_4/mac_header_helper_functions.c

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@
2020
#include "ns_trace.h"
2121
#include "mlme.h"
2222
#include "mac_api.h"
23+
#include "fhss_api.h"
2324
#include "common_functions.h"
2425
#include "mac_common_defines.h"
2526
#include "MAC/IEEE802_15_4/mac_defines.h"
@@ -483,7 +484,7 @@ static uint8_t *mac_security_interface_aux_security_header_write(uint8_t *ptr, c
483484
return ptr;
484485
}
485486

486-
uint8_t * mac_generic_packet_write(uint8_t *ptr, const mac_pre_build_frame_t *buffer)
487+
uint8_t * mac_generic_packet_write(struct protocol_interface_rf_mac_setup *rf_ptr, uint8_t *ptr, const mac_pre_build_frame_t *buffer)
487488
{
488489
ptr = mac_header_write_fcf_dsn(&buffer->fcf_dsn, ptr);
489490

@@ -507,13 +508,16 @@ uint8_t * mac_generic_packet_write(uint8_t *ptr, const mac_pre_build_frame_t *bu
507508
if (buffer->fcf_dsn.securityEnabled) {
508509
ptr = mac_security_interface_aux_security_header_write(ptr, &buffer->aux_header);
509510
}
510-
511+
uint8_t *ie_start = ptr;
511512
//Copy Payload and set IE Elemets
512513
ptr = mac_header_information_elements_write(buffer, ptr);
513514
if (buffer->mac_payload_length) {
514515
memcpy(ptr, buffer->mac_payload, buffer->mac_payload_length );
515516
ptr += buffer->mac_payload_length;
516517
}
518+
if (rf_ptr->fhss_api) {
519+
rf_ptr->fhss_api->write_synch_info(rf_ptr->fhss_api, ie_start, buffer->headerIeLength, FHSS_DATA_FRAME, buffer->tx_time);
520+
}
517521
return ptr;
518522
}
519523

source/MAC/IEEE802_15_4/mac_header_helper_functions.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@ struct mac_pre_parsed_frame_s;
2525
struct mac_pre_build_frame;
2626
struct mac_aux_security_header_s;
2727
struct ns_ie_iovec;
28+
struct protocol_interface_rf_mac_setup;
2829

2930
uint8_t mac_security_mic_length_get(uint8_t security_level);
3031
uint8_t mac_header_security_aux_header_length(uint8_t security_level, uint8_t keyIdmode);
@@ -64,7 +65,7 @@ uint8_t mcps_mac_command_frame_id_get(const struct mac_pre_parsed_frame_s *buffe
6465
uint8_t *mcps_mac_payload_pointer_get(const struct mac_pre_parsed_frame_s *buffer);
6566
uint8_t *mcps_security_mic_pointer_get(const struct mac_pre_parsed_frame_s *buffer);
6667
/* Write Mac Header and payload */
67-
uint8_t * mac_generic_packet_write(uint8_t *ptr, const struct mac_pre_build_frame *buffer);
68+
uint8_t * mac_generic_packet_write(struct protocol_interface_rf_mac_setup *rf_ptr, uint8_t *ptr, const struct mac_pre_build_frame *buffer);
6869

6970

7071
/** get pointer to Mac header start point*/

source/MAC/IEEE802_15_4/mac_mcps_sap.c

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,9 @@
5151

5252
#define TRACE_GROUP "mMCp"
5353

54+
// Used to set TX time (us) with FHSS. Must be <= 65ms.
55+
#define MAC_TX_PROCESSING_DELAY_INITIAL 2000
56+
5457
typedef struct {
5558
uint8_t address[8];
5659
unsigned addr_type:2;
@@ -1362,6 +1365,17 @@ static void mac_security_authentication_data_params_set(ccm_globals_t *ccm_ptr,
13621365
}
13631366
}
13641367

1368+
static uint32_t mcps_calculate_tx_time(protocol_interface_rf_mac_setup_s *rf_mac_setup, uint16_t time_to_tx)
1369+
{
1370+
if (!rf_mac_setup->fhss_api) {
1371+
return 0;
1372+
}
1373+
// Max. time to TX is 65ms
1374+
if (time_to_tx > 65000) {
1375+
time_to_tx = 65000;
1376+
}
1377+
return rf_mac_setup->fhss_api->read_timestamp(rf_mac_setup->fhss_api) + time_to_tx;
1378+
}
13651379

13661380
static int8_t mcps_generic_packet_build(protocol_interface_rf_mac_setup_s *rf_ptr, mac_pre_build_frame_t *buffer) {
13671381
phy_device_driver_s *dev_driver = rf_ptr->dev_driver->phy_driver;
@@ -1435,7 +1449,8 @@ static int8_t mcps_generic_packet_build(protocol_interface_rf_mac_setup_s *rf_pt
14351449
tx_buf->len = frame_length;
14361450

14371451
uint8_t *mhr_start = ptr;
1438-
ptr = mac_generic_packet_write(ptr, buffer);
1452+
buffer->tx_time = mcps_calculate_tx_time(rf_ptr, MAC_TX_PROCESSING_DELAY_INITIAL);
1453+
ptr = mac_generic_packet_write(rf_ptr, ptr, buffer);
14391454

14401455
if (buffer->fcf_dsn.securityEnabled) {
14411456
mac_security_data_params_set(ccm_ptr, (mhr_start + (buffer->mac_header_length_with_security + open_payload)), (mac_payload_length - open_payload));

source/MAC/IEEE802_15_4/mac_mcps_sap.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -125,6 +125,7 @@ typedef struct mac_pre_build_frame{
125125
uint8_t *mac_payload;
126126
uint8_t status;
127127
uint8_t asynch_channel;
128+
uint32_t tx_time;
128129
bool upper_layer_request;
129130
bool mac_allocated_payload_ptr:1;
130131
bool asynch_request:1;

source/MAC/IEEE802_15_4/mac_pd_sap.c

Lines changed: 12 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -163,28 +163,19 @@ int8_t mac_pd_sap_req(protocol_interface_rf_mac_setup_s *rf_mac_setup)
163163
/**
164164
* Set PHY TX time.
165165
*
166-
* \param rf_mac_setup pointer to MAC
167-
* \param time_to_tx Time from present time to wanted TX time (us)
168-
* \return 0 if success, -1 when FHSS not registered
166+
* \param rf_mac_setup pointer to MAC.
167+
* \param tx_time TX timestamp to be set.
169168
*
170169
*/
171-
static int mac_pd_sap_set_tx_time(protocol_interface_rf_mac_setup_s *rf_mac_setup, uint16_t time_to_tx)
170+
static void mac_pd_sap_set_phy_tx_time(protocol_interface_rf_mac_setup_s *rf_mac_setup, uint32_t tx_time)
172171
{
173-
if (rf_mac_setup->fhss_api) {
174-
// Max. TX time is 65ms
175-
if (time_to_tx > 65000) {
176-
time_to_tx = 65000;
177-
}
178-
uint8_t tx_time_buffer[4];
179-
uint32_t tx_time = rf_mac_setup->fhss_api->read_timestamp(rf_mac_setup->fhss_api) + time_to_tx;
180-
if (!tx_time) {
181-
tx_time++;
182-
}
183-
common_write_32_bit(tx_time, tx_time_buffer);
184-
rf_mac_setup->dev_driver->phy_driver->extension(PHY_EXTENSION_SET_TX_TIME, tx_time_buffer);
185-
return 0;
172+
// With TX time set to zero, PHY sends immediately
173+
if (!tx_time) {
174+
tx_time++;
186175
}
187-
return -1;
176+
uint8_t tx_time_buffer[4];
177+
common_write_32_bit(tx_time, tx_time_buffer);
178+
rf_mac_setup->dev_driver->phy_driver->extension(PHY_EXTENSION_SET_TX_TIME, tx_time_buffer);
188179
}
189180

190181
/**
@@ -194,7 +185,7 @@ static int mac_pd_sap_set_tx_time(protocol_interface_rf_mac_setup_s *rf_mac_setu
194185
* \return Timestamp of last PHY reception
195186
*
196187
*/
197-
static uint32_t mac_pd_sap_get_rx_time(protocol_interface_rf_mac_setup_s *rf_mac_setup)
188+
static uint32_t mac_pd_sap_get_phy_rx_time(protocol_interface_rf_mac_setup_s *rf_mac_setup)
198189
{
199190
uint8_t rx_time_buffer[4];
200191
rf_mac_setup->dev_driver->phy_driver->extension(PHY_EXTENSION_READ_RX_TIME, rx_time_buffer);
@@ -216,12 +207,12 @@ void mac_pd_sap_state_machine(protocol_interface_rf_mac_setup_s *rf_mac_setup)
216207
if (!active_buf) {
217208
return;
218209
}
210+
mac_pd_sap_set_phy_tx_time(rf_mac_setup, active_buf->tx_time);
219211
if (active_buf->fcf_dsn.frametype == FC_BEACON_FRAME) {
220212
// FHSS synchronization info is written in the end of transmitted (Beacon) buffer
221213
dev_driver_tx_buffer_s *tx_buf = &rf_mac_setup->dev_driver_tx_buffer;
222214
synch_info = tx_buf->buf + rf_mac_setup->dev_driver->phy_driver->phy_header_length + tx_buf->len - FHSS_SYNCH_INFO_LENGTH;
223-
//TODO: Add proper frame type when they are defined
224-
rf_mac_setup->fhss_api->write_synch_info(rf_mac_setup->fhss_api, synch_info, FHSS_PLAIN_SYNCH_INFO, 0, 0);
215+
rf_mac_setup->fhss_api->write_synch_info(rf_mac_setup->fhss_api, synch_info, 0, FHSS_SYNCH_FRAME, 0);
225216
}
226217
// Change to destination channel and write synchronization info to Beacon frames here
227218
int tx_handle_retval = rf_mac_setup->fhss_api->tx_handle(rf_mac_setup->fhss_api, !mac_is_ack_request_set(active_buf),

source/Service_Libs/fhss/fhss.c

Lines changed: 4 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -929,22 +929,15 @@ static void fhss_update_channel_callback(fhss_structure_t *fhss_structure)
929929
}
930930
}
931931

932-
static int16_t fhss_write_synch_info_callback(const fhss_api_t *api, uint8_t *info_ptr, int info_type, int frame_type_id, uint32_t tx_time)
932+
static int16_t fhss_write_synch_info_callback(const fhss_api_t *api, uint8_t *ptr, uint8_t length, int frame_type, uint32_t tx_time)
933933
{
934934
fhss_structure_t *fhss_structure = fhss_get_object_with_api(api);
935-
(void) frame_type_id;
936935
(void) tx_time;
937-
if (!fhss_structure) {
936+
if (!fhss_structure || !ptr || (frame_type != FHSS_SYNCH_FRAME)) {
938937
return -1;
939938
}
940-
if (info_type == FHSS_PLAIN_SYNCH_INFO) {
941-
if (!info_ptr) {
942-
return -1;
943-
}
944-
fhss_beacon_build(fhss_structure, info_ptr);
945-
return FHSS_SYNCH_INFO_LENGTH;
946-
}
947-
return -1;
939+
fhss_beacon_build(fhss_structure, ptr);
940+
return FHSS_SYNCH_INFO_LENGTH;
948941
}
949942

950943
static void fhss_data_tx_done_callback(const fhss_api_t *api, bool waiting_ack, bool tx_completed, uint8_t handle)

source/Service_Libs/fhss/fhss_ws.c

Lines changed: 48 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@
2525
#include "fhss_ws.h"
2626
#include "fhss_mac_interface.h"
2727
#include "nsdynmemLIB.h"
28+
#include "common_functions.h"
2829
#include "ns_trace.h"
2930
#include <string.h>
3031

@@ -33,7 +34,17 @@
3334
// Enable this flag to use channel traces
3435
#define FHSS_CHANNEL_DEBUG
3536

36-
#define DEF_2E16 16777216
37+
#define DEF_2E24 0x1000000
38+
#define IE_HEADER_LENGTH_MASK 0x007f
39+
#define IE_HEADER_ID_MASK 0x7f80
40+
#define WH_IE_ID 0x2a
41+
#define WH_SUB_ID_UTT 1
42+
43+
struct ws_ie_t {
44+
uint8_t *content_ptr;
45+
unsigned length:7;
46+
uint8_t id;
47+
};
3748

3849
static void fhss_ws_update_uc_channel_callback(fhss_structure_t *fhss_structure);
3950
static void fhss_unicast_handler(const fhss_api_t *fhss_api, uint16_t delay);
@@ -137,14 +148,13 @@ static uint32_t fhss_ws_calculate_ufsi(fhss_structure_t *fhss_structure, uint32_
137148
cur_slot--;
138149
uint32_t remaining_time = (fhss_structure->platform_functions.fhss_get_remaining_slots(fhss_unicast_handler, fhss_structure->fhss_api) / 1000);
139150
uint32_t time_to_tx = (tx_time - fhss_structure->fhss_api->read_timestamp(fhss_structure->fhss_api)) / 1000;
140-
uint32_t ms_since_seq_start = (cur_slot * dwell_time) + (dwell_time-remaining_time) + time_to_tx;
151+
uint64_t ms_since_seq_start = (cur_slot * dwell_time) + (dwell_time-remaining_time) + time_to_tx;
141152
ms_since_seq_start %= (dwell_time*fhss_structure->number_of_channels);
142153
uint32_t seq_length = 0x10000;
143154
if (fhss_structure->ws->fhss_configuration.ws_channel_function == WS_TR51CF) {
144155
seq_length = fhss_structure->number_of_channels;
145156
}
146-
147-
return own_floor((float)(ms_since_seq_start * DEF_2E16) / (seq_length*dwell_time));
157+
return own_floor((float)(ms_since_seq_start * DEF_2E24) / (seq_length*dwell_time));
148158
}
149159

150160
static uint16_t fhss_ws_calculate_destination_slot(fhss_structure_t *fhss_structure, uint32_t ufsi, uint32_t ufsi_timestamp, uint8_t dwell_time, uint32_t tx_time)
@@ -153,7 +163,7 @@ static uint16_t fhss_ws_calculate_destination_slot(fhss_structure_t *fhss_struct
153163
if (fhss_structure->ws->fhss_configuration.ws_channel_function == WS_TR51CF) {
154164
seq_length = fhss_structure->number_of_channels;
155165
}
156-
uint32_t dest_ms_since_seq_start = own_ceil((float)(ufsi*seq_length*dwell_time) / DEF_2E16);
166+
uint32_t dest_ms_since_seq_start = own_ceil((float)(ufsi*seq_length*dwell_time) / DEF_2E24);
157167
return (own_floor(((float)((tx_time - ufsi_timestamp)/1000 + dest_ms_since_seq_start) / dwell_time)) % seq_length);
158168
}
159169

@@ -262,18 +272,43 @@ static bool fhss_ws_check_tx_conditions_callback(const fhss_api_t *api, bool is_
262272
return true;
263273
}
264274

265-
static int16_t fhss_ws_write_synch_info_callback(const fhss_api_t *api, uint8_t *info_ptr, int info_type, int frame_type_id, uint32_t tx_time)
275+
static uint8_t fhss_ws_ie_header_discover(uint8_t *header_ptr, uint16_t length, struct ws_ie_t *header_ie, uint8_t sub_id)
276+
{
277+
struct ws_ie_t ie_element;
278+
uint8_t *sub_id_ptr;
279+
uint16_t ie_dummy;
280+
while (length > 2) {
281+
ie_dummy = common_read_16_bit_inverse(header_ptr);
282+
ie_element.length = (ie_dummy & IE_HEADER_LENGTH_MASK);
283+
ie_element.id = ((ie_dummy & IE_HEADER_ID_MASK) >> 7);
284+
ie_element.content_ptr = header_ptr + 2;
285+
sub_id_ptr = ie_element.content_ptr;
286+
if (ie_element.length && (header_ie->id == ie_element.id) && (*sub_id_ptr == sub_id)) {
287+
sub_id_ptr++;
288+
ie_element.length--;
289+
header_ie->content_ptr = sub_id_ptr;
290+
header_ie->length = ie_element.length;
291+
return ie_element.length;
292+
}
293+
length -= ie_element.length + 2;
294+
header_ptr += ie_element.length + 2;
295+
}
296+
return 0;
297+
}
298+
299+
static int16_t fhss_ws_write_synch_info_callback(const fhss_api_t *api, uint8_t *ptr, uint8_t length, int frame_type, uint32_t tx_time)
266300
{
267301
fhss_structure_t *fhss_structure = fhss_get_object_with_api(api);
268-
(void) frame_type_id;
269-
(void) tx_time;
270-
(void) info_ptr;
271-
(void) info_type;
272-
if (!fhss_structure) {
302+
if (!fhss_structure || !ptr || (frame_type != FHSS_DATA_FRAME)) {
273303
return -1;
274304
}
275-
276-
return -1;
305+
struct ws_ie_t header_ie;
306+
header_ie.id = WH_IE_ID;
307+
if (fhss_ws_ie_header_discover(ptr, length, &header_ie, WH_SUB_ID_UTT)) {
308+
uint32_t ufsi = fhss_ws_calculate_ufsi(fhss_structure, tx_time);
309+
common_write_24_bit_inverse(ufsi, header_ie.content_ptr+1);
310+
}
311+
return 0;
277312
}
278313

279314
static void fhss_ws_data_tx_done_callback(const fhss_api_t *api, bool waiting_ack, bool tx_completed, uint8_t handle)

0 commit comments

Comments
 (0)