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.
LWIPInterfaceEMAC.cpp
00001 /* mbed Microcontroller Library 00002 * Copyright (c) 2016 ARM Limited 00003 * 00004 * Licensed under the Apache License, Version 2.0 (the "License"); 00005 * you may not use this file except in compliance with the License. 00006 * You may obtain a copy of the License at 00007 * 00008 * http://www.apache.org/licenses/LICENSE-2.0 00009 * 00010 * Unless required by applicable law or agreed to in writing, software 00011 * distributed under the License is distributed on an "AS IS" BASIS, 00012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 00013 * See the License for the specific language governing permissions and 00014 * limitations under the License. 00015 */ 00016 00017 #include "lwip/tcpip.h" 00018 #include "lwip/tcp.h" 00019 #include "lwip/ip.h" 00020 #include "netif/etharp.h" 00021 #include "lwip/ethip6.h" 00022 #include "netsocket/nsapi_types.h" 00023 #include "netsocket/EMAC.h" 00024 00025 #include "LWIPStack.h" 00026 00027 #if LWIP_ETHERNET 00028 00029 err_t LWIP::Interface::emac_low_level_output(struct netif *netif, struct pbuf *p) 00030 { 00031 /* Increase reference counter since lwip stores handle to pbuf and frees 00032 it after output */ 00033 pbuf_ref(p); 00034 00035 LWIP::Interface *mbed_if = static_cast<LWIP::Interface *>(netif->state); 00036 bool ret = mbed_if->emac->link_out(p); 00037 return ret ? ERR_OK : ERR_IF; 00038 } 00039 00040 void LWIP::Interface::emac_input(emac_mem_buf_t *buf) 00041 { 00042 struct pbuf *p = static_cast<struct pbuf *>(buf); 00043 00044 /* pass all packets to ethernet_input, which decides what packets it supports */ 00045 if (netif.input(p, &netif) != ERR_OK) { 00046 LWIP_DEBUGF(NETIF_DEBUG, ("Emac LWIP: IP input error\n")); 00047 00048 pbuf_free(p); 00049 } 00050 } 00051 00052 void LWIP::Interface::emac_state_change(bool up) 00053 { 00054 if (up) { 00055 tcpip_callback_with_block((tcpip_callback_fn)netif_set_link_up, &netif, 1); 00056 } else { 00057 tcpip_callback_with_block((tcpip_callback_fn)netif_set_link_down, &netif, 1); 00058 } 00059 } 00060 00061 #if LWIP_IGMP 00062 00063 #include "lwip/igmp.h" 00064 /** 00065 * IPv4 address filtering setup. 00066 * 00067 * \param[in] netif the lwip network interface structure 00068 * \param[in] group IPv4 group to modify 00069 * \param[in] action 00070 * \return ERR_OK or error code 00071 */ 00072 err_t LWIP::Interface::emac_igmp_mac_filter(struct netif *netif, const ip4_addr_t *group, enum netif_mac_filter_action action) 00073 { 00074 LWIP::Interface *mbed_if = static_cast<LWIP::Interface *>(netif->state); 00075 00076 switch (action) { 00077 case NETIF_ADD_MAC_FILTER: 00078 { 00079 uint32_t group23 = ntohl(group->addr) & 0x007FFFFF; 00080 uint8_t addr[6]; 00081 addr[0] = LL_IP4_MULTICAST_ADDR_0; 00082 addr[1] = LL_IP4_MULTICAST_ADDR_1; 00083 addr[2] = LL_IP4_MULTICAST_ADDR_2; 00084 addr[3] = group23 >> 16; 00085 addr[4] = group23 >> 8; 00086 addr[5] = group23; 00087 mbed_if->emac->add_multicast_group(addr); 00088 return ERR_OK; 00089 } 00090 case NETIF_DEL_MAC_FILTER: 00091 /* As we don't reference count, silently ignore delete requests */ 00092 return ERR_OK; 00093 default: 00094 return ERR_ARG; 00095 } 00096 } 00097 #endif 00098 00099 #if LWIP_IPV6_MLD 00100 00101 #include "lwip/mld6.h" 00102 /** 00103 * IPv6 address filtering setup. 00104 * 00105 * \param[in] netif the lwip network interface structure 00106 * \param[in] group IPv6 group to modify 00107 * \param[in] action 00108 * \return ERR_OK or error code 00109 */ 00110 err_t LWIP::Interface::emac_mld_mac_filter(struct netif *netif, const ip6_addr_t *group, enum netif_mac_filter_action action) 00111 { 00112 LWIP::Interface *mbed_if = static_cast<LWIP::Interface *>(netif->state); 00113 00114 switch (action) { 00115 case NETIF_ADD_MAC_FILTER: 00116 { 00117 uint32_t group32 = ntohl(group->addr[3]); 00118 uint8_t addr[6]; 00119 addr[0] = LL_IP6_MULTICAST_ADDR_0; 00120 addr[1] = LL_IP6_MULTICAST_ADDR_1; 00121 addr[2] = group32 >> 24; 00122 addr[3] = group32 >> 16; 00123 addr[4] = group32 >> 8; 00124 addr[5] = group32; 00125 mbed_if->emac->add_multicast_group(addr); 00126 return ERR_OK; 00127 } 00128 case NETIF_DEL_MAC_FILTER: 00129 /* As we don't reference count, silently ignore delete requests */ 00130 return ERR_OK; 00131 default: 00132 return ERR_ARG; 00133 } 00134 } 00135 #endif 00136 00137 err_t LWIP::Interface::emac_if_init(struct netif *netif) 00138 { 00139 int err = ERR_OK; 00140 LWIP::Interface *mbed_if = static_cast<LWIP::Interface *>(netif->state); 00141 00142 mbed_if->emac->set_memory_manager(*mbed_if->memory_manager); 00143 mbed_if->emac->set_link_input_cb(mbed::callback(mbed_if, &LWIP::Interface::emac_input)); 00144 mbed_if->emac->set_link_state_cb(mbed::callback(mbed_if, &LWIP::Interface::emac_state_change)); 00145 00146 /* Interface capabilities */ 00147 netif->flags = NETIF_FLAG_BROADCAST | NETIF_FLAG_ETHARP | NETIF_FLAG_ETHERNET; 00148 00149 if (!mbed_if->emac->power_up()) { 00150 err = ERR_IF; 00151 } 00152 00153 netif->mtu = mbed_if->emac->get_mtu_size(); 00154 /* We have a default MAC address, so do don't force them to supply one */ 00155 netif->hwaddr_len = mbed_if->emac->get_hwaddr_size(); 00156 /* They may or may not update hwaddr with their address */ 00157 mbed_if->emac->get_hwaddr(netif->hwaddr); 00158 /* Then we write back either what they gave us, or our default */ 00159 mbed_if->emac->set_hwaddr(netif->hwaddr); 00160 00161 mbed_if->emac->get_ifname(netif->name, 2); 00162 00163 #if LWIP_IPV4 00164 netif->output = etharp_output; 00165 #if LWIP_IGMP 00166 netif->igmp_mac_filter = &LWIP::Interface::emac_igmp_mac_filter; 00167 netif->flags |= NETIF_FLAG_IGMP; 00168 #endif /* LWIP_IGMP */ 00169 #endif /* LWIP_IPV4 */ 00170 #if LWIP_IPV6 00171 netif->output_ip6 = ethip6_output; 00172 #if LWIP_IPV6_MLD 00173 netif->mld_mac_filter = &LWIP::Interface::emac_mld_mac_filter; 00174 netif->flags |= NETIF_FLAG_MLD6; 00175 #else 00176 // Would need to enable all multicasts here - no API in fsl_enet to do that 00177 #error "IPv6 multicasts won't be received if LWIP_IPV6_MLD is disabled, breaking the system" 00178 #endif 00179 #endif 00180 00181 netif->linkoutput = &LWIP::Interface::emac_low_level_output; 00182 00183 return err; 00184 } 00185 00186 #endif 00187
Generated on Tue Jul 12 2022 12:44:52 by
