-
Notifications
You must be signed in to change notification settings - Fork 2k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #19849 from krzysztof-cabaj/LWIP-ifconfig-IPv4-con…
…figuration sys/shell/lwip: add IPv4 configuration to lwip ifconfig command
- Loading branch information
Showing
1 changed file
with
198 additions
and
10 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,5 +1,6 @@ | ||
/* | ||
* Copyright (C) 2021 Google LLC | ||
* 2024 Krzysztof Cabaj <[email protected]> | ||
* | ||
* This file is subject to the terms and conditions of the GNU Lesser | ||
* General Public License v2.1. See the file LICENSE in the top level | ||
|
@@ -12,8 +13,10 @@ | |
* | ||
* @file | ||
* @brief Shell command for printing lwIP network interface status | ||
* and configuration of IPv4 address | ||
* | ||
* @author Erik Ekman <[email protected]> | ||
* Krzysztof Cabaj <[email protected]> | ||
* | ||
* @} | ||
*/ | ||
|
@@ -26,6 +29,11 @@ | |
#include "net/netopt.h" | ||
#include "shell.h" | ||
|
||
#include "arch/sys_arch.h" | ||
#include <arpa/inet.h> | ||
|
||
#include "net/netif.h" | ||
|
||
#ifdef MODULE_LWIP_IPV6 | ||
static void _netif_list_ipv6(struct netif *netif, int addr_index, uint8_t state) | ||
{ | ||
|
@@ -34,17 +42,20 @@ static void _netif_list_ipv6(struct netif *netif, int addr_index, uint8_t state) | |
printf(" scope: "); | ||
if (ip6_addr_isglobal(netif_ip6_addr(netif, addr_index))) { | ||
printf("global"); | ||
} else if (ip6_addr_islinklocal(netif_ip6_addr(netif, addr_index))) { | ||
} | ||
else if (ip6_addr_islinklocal(netif_ip6_addr(netif, addr_index))) { | ||
printf("link"); | ||
} else if (ip6_addr_issitelocal(netif_ip6_addr(netif, addr_index))) { | ||
} | ||
else if (ip6_addr_issitelocal(netif_ip6_addr(netif, addr_index))) { | ||
printf("site"); | ||
} else { | ||
} | ||
else { | ||
printf("unknown"); | ||
} | ||
printf(" state:"); | ||
if (ip6_addr_istentative(state)) { | ||
printf(" tentative (%u probes send)", | ||
(unsigned)(state & IP6_ADDR_TENTATIVE_COUNT_MASK)); | ||
(unsigned)(state & IP6_ADDR_TENTATIVE_COUNT_MASK)); | ||
} | ||
if (ip6_addr_isvalid(state)) { | ||
printf(" valid"); | ||
|
@@ -65,20 +76,21 @@ static void _netif_list(struct netif *netif) | |
char name[CONFIG_NETIF_NAMELENMAX]; | ||
struct netdev *dev = netif->state; | ||
lwip_netif_t *compat = container_of(netif, lwip_netif_t, lwip_netif); | ||
|
||
netif_get_name(&compat->common_netif, name); | ||
printf("Iface %s HWaddr: ", name); | ||
for (i = 0; i < netif->hwaddr_len; i++) { | ||
printf("%02x", netif->hwaddr[i]); | ||
if ((i+1) < netif->hwaddr_len) { | ||
if ((i + 1) < netif->hwaddr_len) { | ||
printf(":"); | ||
} | ||
} | ||
printf(" Link: %s State: %s\n", | ||
netif_is_link_up(netif) ? "up" : "down", | ||
netif_is_up(netif) ? "up" : "down"); | ||
netif_is_link_up(netif) ? "up" : "down", | ||
netif_is_up(netif) ? "up" : "down"); | ||
printf(" Link type: %s\n", | ||
(dev->driver->get(dev, NETOPT_IS_WIRED, &i, sizeof(i)) > 0) ? | ||
"wired" : "wireless"); | ||
(dev->driver->get(dev, NETOPT_IS_WIRED, &i, sizeof(i)) > 0) ? | ||
"wired" : "wireless"); | ||
#ifdef MODULE_LWIP_IPV4 | ||
printf(" inet addr: "); | ||
ip_addr_debug_print(LWIP_DBG_ON, netif_ip_addr4(netif)); | ||
|
@@ -105,6 +117,133 @@ static void _netif_list(struct netif *netif) | |
#endif | ||
} | ||
|
||
#ifdef MODULE_LWIP_IPV4 | ||
static void _usage_add4(char *cmd) | ||
{ | ||
printf("usage: %s add <interface> <IPv4>/<prefix>\n", cmd); | ||
printf("usage: %s add <interface> <IPv4>/<prefix> gw <IPv4>\n", cmd); | ||
} | ||
|
||
static void _lwip_prefix_to_subnet(int prefix, ip4_addr_t *subnet) | ||
{ | ||
uint32_t value = 0; | ||
uint32_t tmp = 0x80000000; | ||
|
||
for (int i = 0; i < prefix; i++) { | ||
value += tmp; | ||
tmp = tmp >> 1; | ||
} | ||
subnet->addr = htonl(value); | ||
} | ||
|
||
static int _lwip_netif_add4(int argc, char **argv) | ||
{ | ||
struct netif *iface; | ||
char *ip_ptr, *prefix_ptr = NULL; | ||
ip4_addr_t ip, subnet, gw; | ||
int prefix; | ||
|
||
if (argc != 4 && argc != 6) { | ||
printf("error: invalid number of parameters\n"); | ||
_usage_add4(argv[0]); | ||
return 1; | ||
} | ||
|
||
sys_lock_tcpip_core(); | ||
iface = netif_find(argv[2]); | ||
|
||
if (iface == NULL) { | ||
printf("error: invalid interface name (names are case sensitive)\n"); | ||
sys_unlock_tcpip_core(); | ||
return 1; | ||
} | ||
|
||
ip_ptr = argv[3]; | ||
while ((*ip_ptr) != 0) { | ||
if ((*ip_ptr) == '/') { | ||
*ip_ptr = 0; | ||
prefix_ptr = ip_ptr + 1; | ||
} | ||
|
||
ip_ptr++; | ||
} | ||
ip_ptr = argv[3]; | ||
|
||
if (prefix_ptr == NULL) { | ||
printf("error: invalid IPv4 prefix notation\n"); | ||
_usage_add4(argv[0]); | ||
sys_unlock_tcpip_core(); | ||
return 1; | ||
} | ||
|
||
if (inet_pton(AF_INET, ip_ptr, &ip.addr) != 1) { | ||
printf("error:invalid IPv4 address\n"); | ||
sys_unlock_tcpip_core(); | ||
return 1; | ||
} | ||
|
||
prefix = atoi(prefix_ptr); | ||
|
||
if (prefix < 0 || prefix > 32) { | ||
printf("error:invalid prefix, should be in range <0, 32>\n"); | ||
sys_unlock_tcpip_core(); | ||
return 1; | ||
} | ||
|
||
_lwip_prefix_to_subnet(prefix, &subnet); | ||
|
||
if (argc == 4) { | ||
netif_set_addr(iface, &ip, &subnet, NULL); | ||
} | ||
else { | ||
if (strcmp("gw", argv[4]) != 0) { | ||
printf("error: invalid subcommand \"%s\"\n", argv[4]); | ||
_usage_add4(argv[0]); | ||
sys_unlock_tcpip_core(); | ||
return 1; | ||
} | ||
|
||
if (inet_pton(AF_INET, argv[5], &gw.addr) != 1) { | ||
printf("error: invalid gateway address\n"); | ||
sys_unlock_tcpip_core(); | ||
return 1; | ||
} | ||
netif_set_addr(iface, &ip, &subnet, &gw); | ||
} | ||
|
||
sys_unlock_tcpip_core(); | ||
return 0; | ||
} | ||
#endif | ||
|
||
#ifdef MODULE_LWIP_IPV6 | ||
static void _usage_add6(char *cmd) | ||
{ | ||
printf("usage: %s add for LWIP IPv6 currently not implemented\n", cmd); | ||
} | ||
|
||
static int _lwip_netif_add6(int argc, char **argv) | ||
{ | ||
(void)argc; | ||
(void)argv; | ||
printf("error: LWIP IPv6 configuration currently not implemented\n"); | ||
|
||
return 0; | ||
} | ||
#endif | ||
|
||
static void _lwip_netif_help(char *cmd) | ||
{ | ||
printf("usage: %s\n", cmd); | ||
printf("usage: %s help\n", cmd); | ||
#ifdef MODULE_LWIP_IPV4 | ||
_usage_add4(cmd); | ||
#endif | ||
#ifdef MODULE_LWIP_IPV6 | ||
_usage_add6(cmd); | ||
#endif | ||
} | ||
|
||
static int _lwip_netif_config(int argc, char **argv) | ||
{ | ||
if (argc < 2) { | ||
|
@@ -124,7 +263,56 @@ static int _lwip_netif_config(int argc, char **argv) | |
} | ||
return 0; | ||
} | ||
printf("%s takes no arguments.\n", argv[0]); | ||
else { | ||
if (strcmp("help", argv[1]) == 0) { | ||
_lwip_netif_help(argv[0]); | ||
} | ||
#if defined(MODULE_LWIP_IPV4) || defined(MODULE_LWIP_IPV6) | ||
else if (strcmp("add", argv[1]) == 0) { | ||
if (argc != 4 && argc != 6) { | ||
printf("error: invalid number of parameters\n"); | ||
#ifdef MODULE_LWIP_IPV4 | ||
_usage_add4(argv[0]); | ||
#endif | ||
#ifdef MODULE_LWIP_IPV6 | ||
_usage_add6(argv[0]); | ||
#endif | ||
return 0; | ||
} | ||
|
||
char *prefix_ptr = strchr(argv[3], '/'); | ||
|
||
if (prefix_ptr == NULL) { | ||
printf("error: provide IP address with prefix\n"); | ||
return 0; | ||
} | ||
|
||
*prefix_ptr = 0; | ||
|
||
#ifdef MODULE_LWIP_IPV4 | ||
ipv4_addr_t ip4; | ||
|
||
if (ipv4_addr_from_buf(&ip4, argv[3], strlen(argv[3])) != NULL) { | ||
*prefix_ptr = '/'; | ||
_lwip_netif_add4(argc, argv); | ||
return 1; | ||
} | ||
#endif | ||
#ifdef MODULE_LWIP_IPV6 | ||
ipv6_addr_t ip6; | ||
if (ipv6_addr_from_buf(&ip6, argv[3], strlen(argv[3])) != NULL) { | ||
*prefix_ptr = '/'; | ||
_lwip_netif_add6(argc, argv); | ||
return 1; | ||
} | ||
#endif | ||
printf("error: use proper IPv4 or IPv6 address\n"); | ||
} | ||
#endif | ||
else { | ||
printf("error: invalid subcommand - use help\n"); | ||
} | ||
} | ||
return 1; | ||
} | ||
|
||
|