Kenji Arai / mbed-os_TYBLE16

Dependents:   TYBLE16_simple_data_logger TYBLE16_MP3_Air

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers ws_pae_timers.c Source File

ws_pae_timers.c

00001 /*
00002  * Copyright (c) 2016-2018, Arm Limited and affiliates.
00003  * SPDX-License-Identifier: Apache-2.0
00004  *
00005  * Licensed under the Apache License, Version 2.0 (the "License");
00006  * you may not use this file except in compliance with the License.
00007  * You may obtain a copy of the License at
00008  *
00009  *     http://www.apache.org/licenses/LICENSE-2.0
00010  *
00011  * Unless required by applicable law or agreed to in writing, software
00012  * distributed under the License is distributed on an "AS IS" BASIS,
00013  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
00014  * See the License for the specific language governing permissions and
00015  * limitations under the License.
00016  */
00017 
00018 #include "nsconfig.h"
00019 #include <string.h>
00020 #include "ns_types.h"
00021 #include "ns_list.h"
00022 #include "ns_trace.h"
00023 #include "nsdynmemLIB.h"
00024 #include "fhss_config.h "
00025 #include "NWK_INTERFACE/Include/protocol.h"
00026 #include "6LoWPAN/ws/ws_config.h"
00027 #include "6LoWPAN/ws/ws_pae_timers.h"
00028 
00029 #ifdef HAVE_WS
00030 
00031 #define TRACE_GROUP "wspt"
00032 
00033 #define SECONDS_IN_DAY                          24 * 60 * 60
00034 #define SECONDS_IN_MONTH                        30 * SECONDS_IN_DAY
00035 #define SECONDS_IN_MINUTE                       60
00036 
00037 #define DEFAULT_GTK_EXPIRE_OFFSET               43200                   // 30 days
00038 #define DEFAULT_PMK_LIFETIME                    4                       // 4 months
00039 #define DEFAULT_PTK_LIFETIME                    2                       // 2 months
00040 #define DEFAULT_GTK_NEW_ACTIVATION_TIME         720                     // default 1/720 * 30 days --> 60 minutes
00041 #define DEFAULT_REVOCATION_LIFETIME_REDUCTION   30                      // default 1/30 * 30 days --> 1 day
00042 #define DEFAULT_GTK_REQUEST_IMIN                4                       // 4 minutes
00043 #define DEFAULT_GTK_REQUEST_IMAX                64                      // 64 minutes
00044 #define DEFAULT_GTK_MAX_MISMATCH                64                      // 64 minutes
00045 #define DEFAULT_GTK_NEW_INSTALL_REQUIRED        80                      // 80 percent of GTK lifetime --> 24 days
00046 
00047 static void ws_pae_timers_calculate(timer_settings_t *timer_settings);
00048 
00049 void ws_pae_timers_settings_init(timer_settings_t *timer_settings)
00050 {
00051     timer_settings->gtk_expire_offset = DEFAULT_GTK_EXPIRE_OFFSET * SECONDS_IN_MINUTE;
00052     timer_settings->pmk_lifetime = DEFAULT_PMK_LIFETIME * SECONDS_IN_MONTH;
00053     timer_settings->ptk_lifetime = DEFAULT_PTK_LIFETIME * SECONDS_IN_MONTH;
00054     timer_settings->gtk_new_act_time = DEFAULT_GTK_NEW_ACTIVATION_TIME;
00055     timer_settings->revocat_lifetime_reduct = DEFAULT_REVOCATION_LIFETIME_REDUCTION;
00056     timer_settings->gtk_request_imin = DEFAULT_GTK_REQUEST_IMIN * SECONDS_IN_MINUTE;
00057     timer_settings->gtk_request_imax = DEFAULT_GTK_REQUEST_IMAX * SECONDS_IN_MINUTE;
00058     timer_settings->gtk_max_mismatch = DEFAULT_GTK_MAX_MISMATCH * SECONDS_IN_MINUTE;
00059     timer_settings->gtk_new_install_req = DEFAULT_GTK_NEW_INSTALL_REQUIRED;
00060 }
00061 
00062 void ws_pae_timers_lifetime_set(timer_settings_t *timer_settings, uint32_t gtk_lifetime, uint32_t pmk_lifetime, uint32_t ptk_lifetime)
00063 {
00064     if (gtk_lifetime) {
00065         timer_settings->gtk_expire_offset = gtk_lifetime * 60;
00066     }
00067     if (pmk_lifetime) {
00068         timer_settings->pmk_lifetime = pmk_lifetime * 60;
00069     }
00070     if (ptk_lifetime) {
00071         timer_settings->ptk_lifetime = ptk_lifetime * 60;
00072     }
00073     ws_pae_timers_calculate(timer_settings);
00074 }
00075 
00076 void ws_pae_timers_gtk_time_settings_set(timer_settings_t *timer_settings, uint8_t revocat_lifetime_reduct, uint8_t new_activation_time, uint8_t new_install_req, uint32_t max_mismatch)
00077 {
00078     if (revocat_lifetime_reduct) {
00079         timer_settings->revocat_lifetime_reduct = revocat_lifetime_reduct;
00080     }
00081     if (new_activation_time) {
00082         timer_settings->gtk_new_act_time = new_activation_time;
00083     }
00084     if (new_install_req) {
00085         timer_settings->gtk_new_install_req = new_install_req;
00086     }
00087     if (max_mismatch) {
00088         timer_settings->gtk_max_mismatch = max_mismatch * 60;
00089     }
00090     ws_pae_timers_calculate(timer_settings);
00091 }
00092 
00093 static void ws_pae_timers_calculate(timer_settings_t *timer_settings)
00094 {
00095     // Calculate GTK_NEW_INSTALL_REQUIRED < 100 * (1 - 1 / REVOCATION_LIFETIME_REDUCTION)
00096     uint8_t calc_gtk_new_install_req = 100 - (100 / timer_settings->revocat_lifetime_reduct);
00097 
00098     if (timer_settings->gtk_expire_offset < 3600) {
00099         // For very short GTKs give some more time to distribute the new GTK key to network, tune this if needed
00100         calc_gtk_new_install_req = calc_gtk_new_install_req * 60 / 100;
00101     }
00102 
00103     if (timer_settings->gtk_new_install_req > calc_gtk_new_install_req) {
00104         tr_info("GTK new install required adjusted %i", calc_gtk_new_install_req);
00105         timer_settings->gtk_new_install_req = calc_gtk_new_install_req;
00106     }
00107 
00108     // Verify that GTK request Imin and Imax are sensible when compared to revocation lifetime
00109     timer_settings->gtk_request_imin = DEFAULT_GTK_REQUEST_IMIN * SECONDS_IN_MINUTE;
00110     timer_settings->gtk_request_imax = DEFAULT_GTK_REQUEST_IMAX * SECONDS_IN_MINUTE;
00111 
00112     uint32_t gtk_revocation_lifetime = timer_settings->gtk_expire_offset / timer_settings->revocat_lifetime_reduct;
00113     uint32_t new_activation_time = timer_settings->gtk_expire_offset / timer_settings->gtk_new_act_time;
00114 
00115     uint32_t time_to_update = gtk_revocation_lifetime;
00116     if (gtk_revocation_lifetime > new_activation_time) {
00117         time_to_update = gtk_revocation_lifetime - new_activation_time;
00118     }
00119 
00120     tr_info("Key timers revocation lifetime: %"PRIu32", new activation time: %"PRIu32", max mismatch %i, time to update: %"PRIu32"", gtk_revocation_lifetime, new_activation_time, timer_settings->gtk_max_mismatch, time_to_update);
00121 
00122     // If time to update results smaller GTK request Imax use it for calculation otherwise use GTK max mismatch
00123     if (time_to_update < timer_settings->gtk_max_mismatch) {
00124         // If time to update is smaller than GTK request Imax update GTK request values
00125         if (timer_settings->gtk_request_imax > time_to_update) {
00126             timer_settings->gtk_request_imin = time_to_update / 4;
00127             timer_settings->gtk_request_imax = time_to_update / 2;
00128             tr_info("GTK request timers adjusted Imin: %i, Imax: %i", timer_settings->gtk_request_imin, timer_settings->gtk_request_imax);
00129         }
00130     } else if (timer_settings->gtk_request_imax > timer_settings->gtk_max_mismatch) {
00131         // If GTK request Imax is larger than GTK max mismatch update GTK request values
00132 
00133         // For small GTK max mismatch times, scale the Imin to be larger than default  4 / 64;
00134         uint16_t scaler;
00135         if (timer_settings->gtk_max_mismatch < 50) {
00136             scaler = 10;
00137         } else if (timer_settings->gtk_max_mismatch > 600) {
00138             scaler = 1;
00139         } else {
00140             // About 1 minute mismatch, results 37 seconds Imin and 60 seconds Imax
00141             scaler = (600 - timer_settings->gtk_max_mismatch) / 54;
00142         }
00143 
00144         timer_settings->gtk_request_imin = timer_settings->gtk_max_mismatch * scaler * DEFAULT_GTK_REQUEST_IMIN / DEFAULT_GTK_REQUEST_IMAX;
00145         timer_settings->gtk_request_imax = timer_settings->gtk_max_mismatch;
00146         tr_info("GTK request timers adjusted Imin: %i, Imax: %i", timer_settings->gtk_request_imin, timer_settings->gtk_request_imax);
00147     }
00148 }
00149 
00150 bool ws_pae_timers_gtk_new_install_required(timer_settings_t *timer_settings, uint32_t seconds)
00151 {
00152     uint32_t gtk_new_install_req_seconds = timer_settings->gtk_expire_offset - timer_settings->gtk_new_install_req * timer_settings->gtk_expire_offset / 100;
00153 
00154     if (seconds < gtk_new_install_req_seconds) {
00155         return true;
00156     } else {
00157         return false;
00158     }
00159 }
00160 
00161 bool ws_pae_timers_gtk_new_activation_time(timer_settings_t *timer_settings, uint32_t seconds)
00162 {
00163     uint32_t gtk_gtk_new_activation_time_seconds = timer_settings->gtk_expire_offset / timer_settings->gtk_new_act_time;
00164 
00165     if (seconds < gtk_gtk_new_activation_time_seconds) {
00166         return true;
00167     } else {
00168         return false;
00169     }
00170 }
00171 
00172 uint32_t ws_pae_timers_gtk_revocation_lifetime_get(timer_settings_t *timer_settings)
00173 {
00174     return timer_settings->gtk_expire_offset / timer_settings->revocat_lifetime_reduct;
00175 }
00176 
00177 #endif /* HAVE_WS */