Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Dependents: TYBLE16_simple_data_logger TYBLE16_MP3_Air
ws_eapol_auth_relay.c
00001 /* 00002 * Copyright (c) 2018-2019, 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 "mac_api.h" 00027 #include "mac_mcps.h" 00028 #include "Common_Protocols/ipv6_constants.h" 00029 #include "socket_api.h" 00030 #include "6LoWPAN/MAC/mac_helper.h" 00031 #include "6LoWPAN/MAC/mpx_api.h" 00032 #include "6LoWPAN/ws/ws_config.h" 00033 #include "6LoWPAN/ws/ws_eapol_pdu.h" 00034 #include "6LoWPAN/ws/ws_eapol_relay_lib.h" 00035 #include "6LoWPAN/ws/ws_eapol_auth_relay.h" 00036 #include "common_functions.h" 00037 00038 #ifdef HAVE_WS 00039 #ifdef HAVE_PAE_AUTH 00040 00041 #define TRACE_GROUP "wsar" 00042 00043 typedef struct { 00044 protocol_interface_info_entry_t *interface_ptr; /**< Interface pointer */ 00045 ns_address_t remote_addr; /**< Remote address and port */ 00046 ns_address_t relay_addr; /**< Relay address */ 00047 int8_t socket_id; /**< Socket ID for relay */ 00048 ns_list_link_t link; /**< Link */ 00049 } eapol_auth_relay_t; 00050 00051 static eapol_auth_relay_t *ws_eapol_auth_relay_get(protocol_interface_info_entry_t *interface_ptr); 00052 static void ws_eapol_auth_relay_socket_cb(void *cb); 00053 static int8_t ws_eapol_auth_relay_send_to_kmp(eapol_auth_relay_t *eapol_auth_relay, const uint8_t *eui_64, const uint8_t *ip_addr, uint16_t port, const void *data, uint16_t data_len); 00054 00055 static NS_LIST_DEFINE(eapol_auth_relay_list, eapol_auth_relay_t, link); 00056 00057 int8_t ws_eapol_auth_relay_start(protocol_interface_info_entry_t *interface_ptr, uint16_t local_port, const uint8_t *remote_addr, uint16_t remote_port) 00058 { 00059 if (!interface_ptr || !remote_addr) { 00060 return -1; 00061 } 00062 00063 if (ws_eapol_auth_relay_get(interface_ptr)) { 00064 return 0; 00065 } 00066 00067 eapol_auth_relay_t *eapol_auth_relay = ns_dyn_mem_alloc(sizeof(eapol_auth_relay_t)); 00068 if (!eapol_auth_relay) { 00069 return -1; 00070 } 00071 00072 eapol_auth_relay->interface_ptr = interface_ptr; 00073 00074 eapol_auth_relay->remote_addr.type = ADDRESS_IPV6; 00075 memcpy(&eapol_auth_relay->relay_addr.address, remote_addr, 16); 00076 eapol_auth_relay->relay_addr.identifier = remote_port; 00077 00078 eapol_auth_relay->socket_id = socket_open(IPV6_NH_UDP, local_port, &ws_eapol_auth_relay_socket_cb); 00079 if (eapol_auth_relay->socket_id < 0) { 00080 ns_dyn_mem_free(eapol_auth_relay); 00081 return -1; 00082 } 00083 00084 ns_list_add_to_end(&eapol_auth_relay_list, eapol_auth_relay); 00085 00086 return 0; 00087 } 00088 00089 int8_t ws_eapol_auth_relay_delete(protocol_interface_info_entry_t *interface_ptr) 00090 { 00091 if (!interface_ptr) { 00092 return -1; 00093 } 00094 00095 eapol_auth_relay_t *eapol_auth_relay = ws_eapol_auth_relay_get(interface_ptr); 00096 if (!eapol_auth_relay) { 00097 return -1; 00098 } 00099 00100 socket_close(eapol_auth_relay->socket_id); 00101 00102 ns_list_remove(&eapol_auth_relay_list, eapol_auth_relay); 00103 ns_dyn_mem_free(eapol_auth_relay); 00104 00105 return 0; 00106 } 00107 00108 static eapol_auth_relay_t *ws_eapol_auth_relay_get(protocol_interface_info_entry_t *interface_ptr) 00109 { 00110 ns_list_foreach(eapol_auth_relay_t, entry, &eapol_auth_relay_list) { 00111 if (entry->interface_ptr == interface_ptr) { 00112 return entry; 00113 } 00114 } 00115 00116 return NULL; 00117 } 00118 00119 static void ws_eapol_auth_relay_socket_cb(void *cb) 00120 { 00121 socket_callback_t *cb_data = cb; 00122 00123 if (cb_data->event_type != SOCKET_DATA) { 00124 return; 00125 } 00126 00127 eapol_auth_relay_t *eapol_auth_relay = NULL; 00128 00129 ns_list_foreach(eapol_auth_relay_t, entry, &eapol_auth_relay_list) { 00130 if (entry->socket_id == cb_data->socket_id) { 00131 eapol_auth_relay = entry; 00132 break; 00133 } 00134 } 00135 00136 if (!eapol_auth_relay) { 00137 return; 00138 } 00139 00140 uint8_t *socket_pdu = ns_dyn_mem_temporary_alloc(cb_data->d_len); 00141 if (!socket_pdu) { 00142 return; 00143 } 00144 00145 ns_address_t src_addr; 00146 00147 if (socket_recvfrom(cb_data->socket_id, socket_pdu, cb_data->d_len, 0, &src_addr) != cb_data->d_len) { 00148 ns_dyn_mem_free(socket_pdu); 00149 return; 00150 } 00151 00152 // Message from source port 10254 (KMP service) -> to IP relay on node or on authenticator 00153 if (src_addr.identifier == eapol_auth_relay->relay_addr.identifier) { 00154 uint8_t *ptr = socket_pdu; 00155 uint8_t *eui_64; 00156 ns_address_t relay_ip_addr; 00157 relay_ip_addr.type = ADDRESS_IPV6; 00158 memcpy(relay_ip_addr.address, ptr, 16); 00159 ptr += 16; 00160 relay_ip_addr.identifier = common_read_16_bit(ptr); 00161 ptr += 2; 00162 eui_64 = ptr; 00163 ptr += 8; 00164 uint16_t data_len = cb_data->d_len - 26; 00165 ws_eapol_relay_lib_send_to_relay(eapol_auth_relay->socket_id, eui_64, &relay_ip_addr, 00166 ptr, data_len); 00167 ns_dyn_mem_free(socket_pdu); 00168 // Other source port (either 10253 or node relay source port) -> to KMP service 00169 } else { 00170 uint8_t *ptr = socket_pdu; 00171 ws_eapol_auth_relay_send_to_kmp(eapol_auth_relay, ptr, src_addr.address, src_addr.identifier, 00172 ptr + 8, cb_data->d_len - 8); 00173 ns_dyn_mem_free(socket_pdu); 00174 } 00175 } 00176 00177 static int8_t ws_eapol_auth_relay_send_to_kmp(eapol_auth_relay_t *eapol_auth_relay, const uint8_t *eui_64, const uint8_t *ip_addr, uint16_t port, const void *data, uint16_t data_len) 00178 { 00179 ns_address_t dest_addr = eapol_auth_relay->relay_addr; 00180 00181 uint8_t temp_array[26]; 00182 ns_iovec_t msg_iov[2]; 00183 ns_msghdr_t msghdr; 00184 //Set messages name buffer 00185 msghdr.msg_name = &dest_addr; 00186 msghdr.msg_namelen = sizeof(dest_addr); 00187 msghdr.msg_iov = &msg_iov[0]; 00188 msghdr.msg_iovlen = 2; 00189 msghdr.msg_control = NULL; 00190 msghdr.msg_controllen = 0; 00191 uint8_t *ptr = temp_array; 00192 memcpy(ptr, ip_addr, 16); 00193 ptr += 16; 00194 ptr = common_write_16_bit(port, ptr); 00195 memcpy(ptr, eui_64, 8); 00196 msg_iov[0].iov_base = temp_array; 00197 msg_iov[0].iov_len = 26; 00198 msg_iov[1].iov_base = (void *)data; 00199 msg_iov[1].iov_len = data_len; 00200 socket_sendmsg(eapol_auth_relay->socket_id, &msghdr, NS_MSG_LEGACY0); 00201 return 0; 00202 } 00203 00204 #endif /* HAVE_PAE_AUTH */ 00205 #endif /* HAVE_WS */
Generated on Tue Jul 12 2022 13:55:04 by
1.7.2