Skip to content

Commit 1c263fd

Browse files
author
Juha Heiskanen
committed
FHSS exclude channel usage from mask and Brazilian Domain support
Add support for regulator domain based exluded channel to Brazil. Fix Barzilian domain that it not advertise excluded channels. FHHS system select active channel from list add support for excluded channel usage in real network.
1 parent 841dcbe commit 1c263fd

File tree

9 files changed

+70
-37
lines changed

9 files changed

+70
-37
lines changed

source/6LoWPAN/ws/ws_bootstrap.c

Lines changed: 14 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -493,14 +493,23 @@ static void ws_bootstrap_llc_hopping_update(struct protocol_interface_info_entry
493493
cur->ws_info->hopping_schdule.fhss_bsi = fhss_configuration->bsi;
494494
}
495495

496-
static uint8_t ws_generate_exluded_channel_list_from_active_channels(ws_excluded_channel_data_t *excluded_data, const uint32_t *selected_channel_mask, uint16_t number_of_channels)
496+
static uint8_t ws_generate_exluded_channel_list_from_active_channels(ws_excluded_channel_data_t *excluded_data, const uint32_t *selected_channel_mask, const uint32_t *global_channel_mask, uint16_t number_of_channels)
497497
{
498498
bool active_range = false;
499499

500500
//Clear Old Data
501501
memset(excluded_data, 0, sizeof(ws_excluded_channel_data_t));
502502

503503
for (uint8_t i = 0; i < number_of_channels; i++) {
504+
if (!(global_channel_mask[0 + (i / 32)] & (1 << (i % 32)))) {
505+
//Global exluded channel
506+
if (active_range) {
507+
//Mark range stop here
508+
active_range = false;
509+
}
510+
continue;
511+
}
512+
504513
if (selected_channel_mask[0 + (i / 32)] & (1 << (i % 32))) {
505514
if (active_range) {
506515
//Mark range stop here
@@ -556,7 +565,7 @@ static void ws_fhss_configure_channel_masks(protocol_interface_info_entry_t *cur
556565
fhss_configuration->unicast_channel_mask[n] &= cur->ws_info->cfg->fhss.fhss_channel_mask[n];
557566
}
558567
//Update Exluded channels
559-
cur->ws_info->hopping_schdule.channel_plan = ws_generate_exluded_channel_list_from_active_channels(&cur->ws_info->hopping_schdule.excluded_channels, fhss_configuration->unicast_channel_mask, cur->ws_info->hopping_schdule.number_of_channels);
568+
cur->ws_info->hopping_schdule.channel_plan = ws_generate_exluded_channel_list_from_active_channels(&cur->ws_info->hopping_schdule.excluded_channels, fhss_configuration->unicast_channel_mask, fhss_configuration->channel_mask, cur->ws_info->hopping_schdule.number_of_channels);
560569
}
561570

562571
static int8_t ws_fhss_initialize(protocol_interface_info_entry_t *cur)
@@ -1431,7 +1440,7 @@ static void ws_bootstrap_pan_config_analyse(struct protocol_interface_info_entry
14311440
etx_lqi_dbm_update(cur->id, data->mpduLinkQuality, data->signal_dbm, neighbor_info.neighbor->index, neighbor_info.neighbor->mac64);
14321441
//Update Neighbor Broadcast and Unicast Parameters
14331442
ws_neighbor_class_neighbor_unicast_time_info_update(neighbor_info.ws_neighbor, ws_utt, data->timestamp);
1434-
ws_neighbor_class_neighbor_unicast_schedule_set(neighbor_info.ws_neighbor, ws_us);
1443+
ws_neighbor_class_neighbor_unicast_schedule_set(neighbor_info.ws_neighbor, ws_us, &cur->ws_info->hopping_schdule);
14351444
ws_neighbor_class_neighbor_broadcast_time_info_update(neighbor_info.ws_neighbor, &ws_bt_ie, data->timestamp);
14361445
ws_neighbor_class_neighbor_broadcast_schedule_set(neighbor_info.ws_neighbor, &ws_bs_ie);
14371446
}
@@ -1515,7 +1524,7 @@ static void ws_bootstrap_pan_config_solicit_analyse(struct protocol_interface_in
15151524
if (ws_bootstrap_neighbor_info_request(cur, data->SrcAddr, &neighbor_info, false)) {
15161525
etx_lqi_dbm_update(cur->id, data->mpduLinkQuality, data->signal_dbm, neighbor_info.neighbor->index, neighbor_info.neighbor->mac64);
15171526
ws_neighbor_class_neighbor_unicast_time_info_update(neighbor_info.ws_neighbor, ws_utt, data->timestamp);
1518-
ws_neighbor_class_neighbor_unicast_schedule_set(neighbor_info.ws_neighbor, ws_us);
1527+
ws_neighbor_class_neighbor_unicast_schedule_set(neighbor_info.ws_neighbor, ws_us, &cur->ws_info->hopping_schdule);
15191528
}
15201529

15211530

@@ -3180,7 +3189,7 @@ static int8_t ws_bootstrap_neighbor_set(protocol_interface_info_entry_t *cur, pa
31803189
}
31813190

31823191
ws_neighbor_class_neighbor_unicast_time_info_update(neighbor_info.ws_neighbor, &parent_ptr->ws_utt, parent_ptr->timestamp);
3183-
ws_neighbor_class_neighbor_unicast_schedule_set(neighbor_info.ws_neighbor, &parent_ptr->ws_us);
3192+
ws_neighbor_class_neighbor_unicast_schedule_set(neighbor_info.ws_neighbor, &parent_ptr->ws_us, &cur->ws_info->hopping_schdule);
31843193
return 0;
31853194
}
31863195

source/6LoWPAN/ws/ws_common.c

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -81,6 +81,18 @@ int8_t ws_generate_channel_list(uint32_t *channel_mask, uint16_t number_of_chann
8181
return 0;
8282
}
8383

84+
uint16_t ws_active_channel_count(uint32_t *channel_mask, uint16_t number_of_channels)
85+
{
86+
uint16_t active_channels = 0;
87+
// Set channel maks outside excluded channels
88+
for (uint16_t i = 0; i < number_of_channels; i++) {
89+
if (channel_mask[0 + (i / 32)] & (1 << (i % 32))) {
90+
active_channels++;
91+
}
92+
}
93+
return active_channels;
94+
}
95+
8496
uint32_t ws_decode_channel_spacing(uint8_t channel_spacing)
8597
{
8698
if (CHANNEL_SPACING_100 == channel_spacing) {

source/6LoWPAN/ws/ws_common.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -115,6 +115,8 @@ typedef struct ws_info_s {
115115

116116
int8_t ws_generate_channel_list(uint32_t *channel_mask, uint16_t number_of_channels, uint8_t regulatory_domain, uint8_t operating_class);
117117

118+
uint16_t ws_active_channel_count(uint32_t *channel_mask, uint16_t number_of_channels);
119+
118120
uint32_t ws_decode_channel_spacing(uint8_t channel_spacing);
119121

120122
uint32_t ws_get_datarate_using_operating_mode(uint8_t operating_mode);

source/6LoWPAN/ws/ws_llc_data_service.c

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -655,7 +655,7 @@ static void ws_llc_data_indication_cb(const mac_api_t *api, const mcps_data_ind_
655655

656656
ws_neighbor_class_neighbor_unicast_time_info_update(neighbor_info.ws_neighbor, &ws_utt, data->timestamp);
657657
if (us_ie_inline) {
658-
ws_neighbor_class_neighbor_unicast_schedule_set(neighbor_info.ws_neighbor, &us_ie);
658+
ws_neighbor_class_neighbor_unicast_schedule_set(neighbor_info.ws_neighbor, &us_ie, &interface->ws_info->hopping_schdule);
659659
}
660660
//Update BS if it is part of message
661661
if (bs_ie_inline) {
@@ -755,7 +755,7 @@ static void ws_llc_eapol_indication_cb(const mac_api_t *api, const mcps_data_ind
755755
uint8_t auth_eui64[8];
756756
ws_neighbor_class_neighbor_unicast_time_info_update(neighbor_info.ws_neighbor, &ws_utt, data->timestamp);
757757
if (us_ie_inline) {
758-
ws_neighbor_class_neighbor_unicast_schedule_set(neighbor_info.ws_neighbor, &us_ie);
758+
ws_neighbor_class_neighbor_unicast_schedule_set(neighbor_info.ws_neighbor, &us_ie, &interface->ws_info->hopping_schdule);
759759
}
760760
//Update BS if it is part of message
761761
if (bs_ie_inline) {

source/6LoWPAN/ws/ws_neighbor_class.c

Lines changed: 9 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -95,28 +95,6 @@ void ws_neighbor_class_neighbor_unicast_time_info_update(ws_neighbor_class_entry
9595
ws_neighbor->fhss_data.uc_timing_info.ufsi = ws_utt->ufsi;
9696
}
9797

98-
static void ws_neighbour_channel_list_enable_all(ws_channel_mask_t *channel_info, uint16_t number_of_channels)
99-
{
100-
uint32_t mask;
101-
channel_info->channel_count = number_of_channels;
102-
for (uint8_t n = 0; n < 8; n++) {
103-
if (number_of_channels >= 32) {
104-
mask = 0xffffffff;
105-
number_of_channels -= 32;
106-
} else if (number_of_channels) {
107-
mask = 0;
108-
//Start bit enable to MSB
109-
for (uint16_t i = 0; i < (number_of_channels % 32); i++) {
110-
mask |= 1 << i;
111-
}
112-
number_of_channels = 0;
113-
} else {
114-
mask = 0;
115-
}
116-
channel_info->channel_mask[n] = mask;
117-
}
118-
}
119-
12098
static void ws_neighbour_excluded_mask_by_range(ws_channel_mask_t *channel_info, ws_excluded_channel_range_t *range_info, uint16_t number_of_channels)
12199
{
122100
uint16_t range_start, range_stop;
@@ -210,29 +188,34 @@ static void ws_neighbour_excluded_mask_by_mask(ws_channel_mask_t *channel_info,
210188
}
211189
}
212190

213-
void ws_neighbor_class_neighbor_unicast_schedule_set(ws_neighbor_class_entry_t *ws_neighbor, ws_us_ie_t *ws_us)
191+
void ws_neighbor_class_neighbor_unicast_schedule_set(ws_neighbor_class_entry_t *ws_neighbor, ws_us_ie_t *ws_us, ws_hopping_schedule_t *own_shedule)
214192
{
215193
ws_neighbor->fhss_data.uc_timing_info.unicast_channel_function = ws_us->channel_function;
216194
if (ws_us->channel_function == WS_FIXED_CHANNEL) {
217195
ws_neighbor->fhss_data.uc_timing_info.fixed_channel = ws_us->function.zero.fixed_channel;
218196
ws_neighbor->fhss_data.uc_timing_info.unicast_number_of_channels = 1;
219197
} else {
198+
220199
if (ws_us->channel_plan == 0) {
221200
ws_neighbor->fhss_data.uc_timing_info.unicast_number_of_channels = ws_common_channel_number_calc(ws_us->plan.zero.regulator_domain, ws_us->plan.zero.operation_class);
222201
} else if (ws_us->channel_plan == 1) {
223202
ws_neighbor->fhss_data.uc_timing_info.unicast_number_of_channels = ws_us->plan.one.number_of_channel;
203+
224204
}
225205

226206
//Handle excluded channel and generate activate channel list
227207
if (ws_us->excluded_channel_ctrl == WS_EXC_CHAN_CTRL_RANGE) {
228-
ws_neighbour_channel_list_enable_all(&ws_neighbor->fhss_data.uc_channel_list, ws_neighbor->fhss_data.uc_timing_info.unicast_number_of_channels);
208+
ws_generate_channel_list(ws_neighbor->fhss_data.uc_channel_list.channel_mask, ws_neighbor->fhss_data.uc_timing_info.unicast_number_of_channels, own_shedule->regulatory_domain, own_shedule->operating_class);
209+
ws_neighbor->fhss_data.uc_channel_list.channel_count = ws_active_channel_count(ws_neighbor->fhss_data.uc_channel_list.channel_mask, ws_neighbor->fhss_data.uc_timing_info.unicast_number_of_channels);
229210
ws_neighbour_excluded_mask_by_range(&ws_neighbor->fhss_data.uc_channel_list, &ws_us->excluded_channels.range, ws_neighbor->fhss_data.uc_timing_info.unicast_number_of_channels);
230211
} else if (ws_us->excluded_channel_ctrl == WS_EXC_CHAN_CTRL_BITMASK) {
231-
ws_neighbour_channel_list_enable_all(&ws_neighbor->fhss_data.uc_channel_list, ws_neighbor->fhss_data.uc_timing_info.unicast_number_of_channels);
212+
ws_generate_channel_list(ws_neighbor->fhss_data.uc_channel_list.channel_mask, ws_neighbor->fhss_data.uc_timing_info.unicast_number_of_channels, own_shedule->regulatory_domain, own_shedule->operating_class);
213+
ws_neighbor->fhss_data.uc_channel_list.channel_count = ws_active_channel_count(ws_neighbor->fhss_data.uc_channel_list.channel_mask, ws_neighbor->fhss_data.uc_timing_info.unicast_number_of_channels);
232214
ws_neighbour_excluded_mask_by_mask(&ws_neighbor->fhss_data.uc_channel_list, &ws_us->excluded_channels.mask, ws_neighbor->fhss_data.uc_timing_info.unicast_number_of_channels);
233215
} else if (ws_us->excluded_channel_ctrl == WS_EXC_CHAN_CTRL_NONE) {
234216
if (ws_neighbor->fhss_data.uc_timing_info.unicast_number_of_channels != ws_neighbor->fhss_data.uc_channel_list.channel_count) {
235-
ws_neighbour_channel_list_enable_all(&ws_neighbor->fhss_data.uc_channel_list, ws_neighbor->fhss_data.uc_timing_info.unicast_number_of_channels);
217+
ws_generate_channel_list(ws_neighbor->fhss_data.uc_channel_list.channel_mask, ws_neighbor->fhss_data.uc_timing_info.unicast_number_of_channels, own_shedule->regulatory_domain, own_shedule->operating_class);
218+
ws_neighbor->fhss_data.uc_channel_list.channel_count = ws_active_channel_count(ws_neighbor->fhss_data.uc_channel_list.channel_mask, ws_neighbor->fhss_data.uc_timing_info.unicast_number_of_channels);
236219
}
237220
}
238221

source/6LoWPAN/ws/ws_neighbor_class.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -115,7 +115,7 @@ void ws_neighbor_class_neighbor_unicast_time_info_update(ws_neighbor_class_entry
115115
* \param ws_us Unicast schedule IE data
116116
*
117117
*/
118-
void ws_neighbor_class_neighbor_unicast_schedule_set(ws_neighbor_class_entry_t *ws_neighbor, ws_us_ie_t *ws_us);
118+
void ws_neighbor_class_neighbor_unicast_schedule_set(ws_neighbor_class_entry_t *ws_neighbor, ws_us_ie_t *ws_us, ws_hopping_schedule_t *own_shedule);
119119

120120

121121
/**

source/Service_Libs/fhss/fhss_ws.c

Lines changed: 25 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -83,6 +83,7 @@ static void fhss_event_timer_cb(int8_t timer_id, uint16_t slots);
8383
static void fhss_ws_update_uc_channel_callback(fhss_structure_t *fhss_structure);
8484
static void fhss_unicast_handler(const fhss_api_t *fhss_api, uint16_t delay);
8585
static bool fhss_ws_check_tx_allowed(fhss_structure_t *fhss_structure);
86+
static int32_t fhss_channel_index_from_mask(const uint32_t *channel_mask, int32_t channel_index, uint16_t number_of_channels);
8687

8788
// This function supports rounding up
8889
static int64_t divide_integer(int64_t dividend, int32_t divisor)
@@ -235,12 +236,14 @@ static int32_t fhss_ws_calc_bc_channel(fhss_structure_t *fhss_structure)
235236

236237
if (fhss_structure->ws->fhss_configuration.ws_bc_channel_function == WS_TR51CF) {
237238
next_channel = tr51_get_bc_channel_index(fhss_structure->ws->tr51_channel_table, fhss_structure->ws->tr51_output_table, fhss_structure->ws->bc_slot, fhss_structure->ws->fhss_configuration.bsi, fhss_structure->number_of_channels, NULL);
239+
next_channel = fhss_channel_index_from_mask(fhss_structure->ws->fhss_configuration.channel_mask, next_channel, fhss_structure->number_of_channels);
238240
if (++fhss_structure->ws->bc_slot == fhss_structure->number_of_channels) {
239241
fhss_structure->ws->bc_slot = 0;
240242
}
241243
} else if (fhss_structure->ws->fhss_configuration.ws_bc_channel_function == WS_DH1CF) {
242244
fhss_structure->ws->bc_slot++;
243245
next_channel = dh1cf_get_bc_channel_index(fhss_structure->ws->bc_slot, fhss_structure->ws->fhss_configuration.bsi, fhss_structure->number_of_channels);
246+
next_channel = fhss_channel_index_from_mask(fhss_structure->ws->fhss_configuration.channel_mask, next_channel, fhss_structure->number_of_channels);
244247
} else if (fhss_structure->ws->fhss_configuration.ws_bc_channel_function == WS_VENDOR_DEF_CF) {
245248
if (fhss_structure->ws->fhss_configuration.vendor_defined_cf) {
246249
next_channel = fhss_structure->ws->fhss_configuration.vendor_defined_cf(fhss_structure->fhss_api, fhss_structure->ws->bc_slot, NULL, fhss_structure->ws->fhss_configuration.bsi, fhss_structure->number_of_channels);
@@ -264,6 +267,22 @@ static uint8_t calc_own_tx_trig_slot(uint8_t own_hop)
264267
return (own_hop & 1);
265268
}
266269

270+
static int32_t fhss_channel_index_from_mask(const uint32_t *channel_mask, int32_t channel_index, uint16_t number_of_channels)
271+
{
272+
//Function will return real active channel index at list
273+
int32_t active_channels = 0;
274+
// Set channel maks outside excluded channels
275+
for (int32_t i = 0; i < number_of_channels; i++) {
276+
if (channel_mask[0 + (i / 32)] & (1 << (i % 32))) {
277+
if (channel_index == active_channels) {
278+
return i;
279+
}
280+
active_channels++;
281+
}
282+
}
283+
return 0;
284+
}
285+
267286
static void fhss_broadcast_handler(const fhss_api_t *fhss_api, uint16_t delay)
268287
{
269288
int32_t next_channel;
@@ -477,12 +496,14 @@ static void fhss_ws_update_uc_channel_callback(fhss_structure_t *fhss_structure)
477496
if (fhss_structure->ws->fhss_configuration.ws_uc_channel_function == WS_FIXED_CHANNEL) {
478497
return;
479498
} else if (fhss_structure->ws->fhss_configuration.ws_uc_channel_function == WS_TR51CF) {
480-
next_channel = fhss_structure->rx_channel = tr51_get_uc_channel_index(fhss_structure->ws->tr51_channel_table, fhss_structure->ws->tr51_output_table, fhss_structure->ws->uc_slot, mac_address, fhss_structure->number_of_uc_channels, NULL);
499+
next_channel = tr51_get_uc_channel_index(fhss_structure->ws->tr51_channel_table, fhss_structure->ws->tr51_output_table, fhss_structure->ws->uc_slot, mac_address, fhss_structure->number_of_uc_channels, NULL);
500+
next_channel = fhss_structure->rx_channel = fhss_channel_index_from_mask(fhss_structure->ws->fhss_configuration.unicast_channel_mask, next_channel, fhss_structure->number_of_channels);
481501
if (++fhss_structure->ws->uc_slot == fhss_structure->number_of_uc_channels) {
482502
fhss_structure->ws->uc_slot = 0;
483503
}
484504
} else if (fhss_structure->ws->fhss_configuration.ws_uc_channel_function == WS_DH1CF) {
485-
next_channel = fhss_structure->rx_channel = dh1cf_get_uc_channel_index(fhss_structure->ws->uc_slot, mac_address, fhss_structure->number_of_uc_channels);
505+
next_channel = dh1cf_get_uc_channel_index(fhss_structure->ws->uc_slot, mac_address, fhss_structure->number_of_uc_channels);
506+
next_channel = fhss_structure->rx_channel = fhss_channel_index_from_mask(fhss_structure->ws->fhss_configuration.unicast_channel_mask, next_channel, fhss_structure->number_of_channels);
486507
fhss_structure->ws->uc_slot++;
487508
} else if (fhss_structure->ws->fhss_configuration.ws_uc_channel_function == WS_VENDOR_DEF_CF) {
488509
if (fhss_structure->ws->fhss_configuration.vendor_defined_cf) {
@@ -540,8 +561,10 @@ static int fhss_ws_tx_handle_callback(const fhss_api_t *api, bool is_broadcast_a
540561
int32_t tx_channel = neighbor_timing_info->uc_timing_info.fixed_channel;
541562
if (neighbor_timing_info->uc_timing_info.unicast_channel_function == WS_TR51CF) {
542563
tx_channel = tr51_get_uc_channel_index(fhss_structure->ws->tr51_channel_table, fhss_structure->ws->tr51_output_table, destination_slot, destination_address, neighbor_timing_info->uc_timing_info.unicast_number_of_channels, NULL);
564+
tx_channel = fhss_channel_index_from_mask(neighbor_timing_info->uc_channel_list.channel_mask, tx_channel, fhss_structure->number_of_channels);
543565
} else if (neighbor_timing_info->uc_timing_info.unicast_channel_function == WS_DH1CF) {
544566
tx_channel = dh1cf_get_uc_channel_index(destination_slot, destination_address, neighbor_timing_info->uc_channel_list.channel_count);
567+
tx_channel = fhss_channel_index_from_mask(neighbor_timing_info->uc_channel_list.channel_mask, tx_channel, fhss_structure->number_of_channels);
545568
} else if (neighbor_timing_info->uc_timing_info.unicast_channel_function == WS_VENDOR_DEF_CF) {
546569
if (fhss_structure->ws->fhss_configuration.vendor_defined_cf) {
547570
tx_channel = fhss_structure->ws->fhss_configuration.vendor_defined_cf(fhss_structure->fhss_api, fhss_structure->ws->bc_slot, destination_address, fhss_structure->ws->fhss_configuration.bsi, neighbor_timing_info->uc_timing_info.unicast_number_of_channels);

test/nanostack/unittest/stub/ws_common_stub.c

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -98,3 +98,7 @@ uint32_t ws_common_network_size_estimate_get(protocol_interface_info_entry_t *cu
9898
return 0;
9999
}
100100

101+
uint16_t ws_active_channel_count(uint32_t *channel_mask, uint16_t number_of_channels)
102+
{
103+
return 35;
104+
}

test/nanostack/unittest/stub/ws_neighbour_class_stub.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -74,7 +74,7 @@ void ws_neighbor_class_neighbor_unicast_time_info_update(ws_neighbor_class_entry
7474

7575
}
7676

77-
void ws_neighbor_class_neighbor_unicast_schedule_set(ws_neighbor_class_entry_t *ws_neighbor, ws_us_ie_t *ws_us)
77+
void ws_neighbor_class_neighbor_unicast_schedule_set(ws_neighbor_class_entry_t *ws_neighbor, ws_us_ie_t *ws_us, ws_hopping_schedule_t *own_shedule)
7878
{
7979

8080
}

0 commit comments

Comments
 (0)