Re: MPLS pseudowire over IPv6 1/2: ifconfig(8) diff

2018-12-23 Thread Denis Fondras
On Sun, Dec 23, 2018 at 10:05:01AM +, Jason McIntyre wrote:
> unless you're trying somehow to emphasise that both types of address are
> supported, you could simplify the text to just:
> 
>   The
>   .Ar dest-address
>   is used to find ...
> 

Thank you for your input.

Index: ifconfig.8
===
RCS file: /cvs/src/sbin/ifconfig/ifconfig.8,v
retrieving revision 1.324
diff -u -p -r1.324 ifconfig.8
--- ifconfig.8  16 Nov 2018 12:25:29 -  1.324
+++ ifconfig.8  23 Dec 2018 10:22:56 -
@@ -1344,8 +1344,7 @@ is another 20-bit number which will be u
 Sets the destination address where this mpw should output.
 The
 .Ar dest-address
-is an IPv4 address that will be used to find the nexthop in the MPLS
-network.
+is used to find the nexthop in the MPLS network.
 .El
 .Sh PAIR
 .nr nS 1
Index: ifconfig.c
===
RCS file: /cvs/src/sbin/ifconfig/ifconfig.c,v
retrieving revision 1.387
diff -u -p -r1.387 ifconfig.c
--- ifconfig.c  29 Nov 2018 00:12:34 -  1.387
+++ ifconfig.c  23 Dec 2018 10:22:57 -
@@ -3802,8 +3802,9 @@ mpe_status(void)
 void
 mpw_status(void)
 {
-   struct sockaddr_in *sin;
-   struct ifmpwreq imr;
+   struct sockaddr_storage *ss;
+   struct ifmpwreq  imr;
+   char hbuf[NI_MAXHOST];
 
bzero(, sizeof(imr));
ifr.ifr_data = (caddr_t) 
@@ -3842,11 +3843,19 @@ mpw_status(void)
else
printf("remote %u\n", imr.imr_rshim.shim_label);
 
-   sin = (struct sockaddr_in *) _nexthop;
-   if (sin->sin_addr.s_addr == 0)
-   printf("\tneighbor: none\n");
-   else
-   printf("\tneighbor: %s\n", inet_ntoa(sin->sin_addr));
+   printf("\tneighbor: ");
+   switch (imr.imr_nexthop.ss_family) {
+   case AF_INET6:
+   case AF_INET:
+   ss = (struct sockaddr_storage *) _nexthop;
+   if (getnameinfo((struct sockaddr *)ss, ss->ss_len, hbuf,
+   sizeof(hbuf), NULL, 0, NI_NUMERICHOST) != 0)
+   strlcpy(hbuf, "???", sizeof(hbuf));
+   printf("%s\n", hbuf);
+   break;
+   default:
+   printf("none\n");
+   }
 }
 
 /* ARGSUSED */
@@ -3870,6 +3879,7 @@ void
 process_mpw_commands(void)
 {
struct  sockaddr_in *sin, *sinn;
+   struct  sockaddr_in6 *sin6, *sin6n;
struct  ifmpwreq imr;
 
if (wconfig == 0)
@@ -3899,14 +3909,29 @@ process_mpw_commands(void)
imrsave.imr_rshim.shim_label = imr.imr_rshim.shim_label;
}
 
-   sin = (struct sockaddr_in *) _nexthop;
-   sinn = (struct sockaddr_in *) _nexthop;
-   if (sin->sin_addr.s_addr == 0) {
-   if (sinn->sin_addr.s_addr == 0)
+   switch (imrsave.imr_nexthop.ss_family) {
+   case AF_INET6:
+   case AF_INET:
+   /* neighbor was set earlier, nothing to do */
+   break;
+   default:
+   switch (imr.imr_nexthop.ss_family) {
+   case AF_INET6:
+   sin6 = (struct sockaddr_in6 *) _nexthop;
+   sin6n = (struct sockaddr_in6 *) _nexthop;
+   sin6->sin6_family = sin6n->sin6_family;
+   memcpy(>sin6_addr, >sin6_addr,
+   sizeof(struct in6_addr));
+   break;
+   case AF_INET:
+   sin = (struct sockaddr_in *) _nexthop;
+   sinn = (struct sockaddr_in *) _nexthop;
+   sin->sin_family = sinn->sin_family;
+   sin->sin_addr.s_addr = sinn->sin_addr.s_addr;
+   break;
+   default:
errx(1, "mpw neighbor address not specified");
-
-   sin->sin_family = sinn->sin_family;
-   sin->sin_addr.s_addr = sinn->sin_addr.s_addr;
+   }
}
 
ifr.ifr_data = (caddr_t) 
@@ -3949,14 +3974,41 @@ void
 setmpwneighbor(const char *value, int d)
 {
struct sockaddr_in *sin;
+   struct sockaddr_in6 *sin6;
+   struct addrinfo hints, *res;
+   int rv;
 
wconfig = 1;
 
-   sin = (struct sockaddr_in *) _nexthop;
-   if (inet_aton(value, >sin_addr) == 0)
+   memset(, 0, sizeof(hints));
+   hints.ai_family = AF_UNSPEC;
+   hints.ai_socktype = SOCK_DGRAM;
+   hints.ai_protocol = 0;
+   hints.ai_flags = AI_PASSIVE;
+
+   rv = getaddrinfo(value, NULL, , );
+   if (rv != 0)
+   errx(1, "neighbor %s: %s", value, gai_strerror(rv));
+
+   switch (res->ai_family) {
+   case AF_INET:
+   sin = (struct sockaddr_in *) _nexthop;
+   sin->sin_family = res->ai_family;
+   sin->sin_addr.s_addr =
+   ((struct sockaddr_in *)res->ai_addr)->sin_addr.s_addr;
+   break;
+  

Re: MPLS pseudowire over IPv6 1/2: ifconfig(8) diff

2018-12-23 Thread Jason McIntyre
On Sun, Dec 23, 2018 at 10:28:30AM +0100, Denis Fondras wrote:
> On Sat, Dec 22, 2018 at 11:42:36PM +0100, Klemens Nanni wrote:
> > I have no clue about MPLS, so this feedback is code-wise only:
> > 
> > Did you consider using more AF agnostic code for parsing the IP address?
> > 
> 
> You are right, it is simpler. Thank you for the clue :)
> 
> Updated diff :
> 
> Index: ifconfig.8
> ===
> RCS file: /cvs/src/sbin/ifconfig/ifconfig.8,v
> retrieving revision 1.324
> diff -u -p -r1.324 ifconfig.8
> --- ifconfig.816 Nov 2018 12:25:29 -  1.324
> +++ ifconfig.823 Dec 2018 09:25:36 -
> @@ -1344,7 +1344,7 @@ is another 20-bit number which will be u
>  Sets the destination address where this mpw should output.
>  The
>  .Ar dest-address
> -is an IPv4 address that will be used to find the nexthop in the MPLS
> +is an IPv4 or IPv6 address that will be used to find the nexthop in the MPLS
>  network.
>  .El
>  .Sh PAIR

morning.

unless you're trying somehow to emphasise that both types of address are
supported, you could simplify the text to just:

The
.Ar dest-address
is used to find ...

jmc



Re: MPLS pseudowire over IPv6 1/2: ifconfig(8) diff

2018-12-23 Thread Denis Fondras
On Sat, Dec 22, 2018 at 11:42:36PM +0100, Klemens Nanni wrote:
> I have no clue about MPLS, so this feedback is code-wise only:
> 
> Did you consider using more AF agnostic code for parsing the IP address?
> 

You are right, it is simpler. Thank you for the clue :)

Updated diff :

Index: ifconfig.8
===
RCS file: /cvs/src/sbin/ifconfig/ifconfig.8,v
retrieving revision 1.324
diff -u -p -r1.324 ifconfig.8
--- ifconfig.8  16 Nov 2018 12:25:29 -  1.324
+++ ifconfig.8  23 Dec 2018 09:25:36 -
@@ -1344,7 +1344,7 @@ is another 20-bit number which will be u
 Sets the destination address where this mpw should output.
 The
 .Ar dest-address
-is an IPv4 address that will be used to find the nexthop in the MPLS
+is an IPv4 or IPv6 address that will be used to find the nexthop in the MPLS
 network.
 .El
 .Sh PAIR
Index: ifconfig.c
===
RCS file: /cvs/src/sbin/ifconfig/ifconfig.c,v
retrieving revision 1.387
diff -u -p -r1.387 ifconfig.c
--- ifconfig.c  29 Nov 2018 00:12:34 -  1.387
+++ ifconfig.c  23 Dec 2018 09:25:36 -
@@ -3802,8 +3802,9 @@ mpe_status(void)
 void
 mpw_status(void)
 {
-   struct sockaddr_in *sin;
-   struct ifmpwreq imr;
+   struct sockaddr_storage *ss;
+   struct ifmpwreq  imr;
+   char hbuf[NI_MAXHOST];
 
bzero(, sizeof(imr));
ifr.ifr_data = (caddr_t) 
@@ -3842,11 +3843,19 @@ mpw_status(void)
else
printf("remote %u\n", imr.imr_rshim.shim_label);
 
-   sin = (struct sockaddr_in *) _nexthop;
-   if (sin->sin_addr.s_addr == 0)
-   printf("\tneighbor: none\n");
-   else
-   printf("\tneighbor: %s\n", inet_ntoa(sin->sin_addr));
+   printf("\tneighbor: ");
+   switch (imr.imr_nexthop.ss_family) {
+   case AF_INET6:
+   case AF_INET:
+   ss = (struct sockaddr_storage *) _nexthop;
+   if (getnameinfo((struct sockaddr *)ss, ss->ss_len, hbuf,
+   sizeof(hbuf), NULL, 0, NI_NUMERICHOST) != 0)
+   strlcpy(hbuf, "???", sizeof(hbuf));
+   printf("%s\n", hbuf);
+   break;
+   default:
+   printf("none\n");
+   }
 }
 
 /* ARGSUSED */
@@ -3870,6 +3879,7 @@ void
 process_mpw_commands(void)
 {
struct  sockaddr_in *sin, *sinn;
+   struct  sockaddr_in6 *sin6, *sin6n;
struct  ifmpwreq imr;
 
if (wconfig == 0)
@@ -3899,14 +3909,29 @@ process_mpw_commands(void)
imrsave.imr_rshim.shim_label = imr.imr_rshim.shim_label;
}
 
-   sin = (struct sockaddr_in *) _nexthop;
-   sinn = (struct sockaddr_in *) _nexthop;
-   if (sin->sin_addr.s_addr == 0) {
-   if (sinn->sin_addr.s_addr == 0)
+   switch (imrsave.imr_nexthop.ss_family) {
+   case AF_INET6:
+   case AF_INET:
+   /* neighbor was set earlier, nothing to do */
+   break;
+   default:
+   switch (imr.imr_nexthop.ss_family) {
+   case AF_INET6:
+   sin6 = (struct sockaddr_in6 *) _nexthop;
+   sin6n = (struct sockaddr_in6 *) _nexthop;
+   sin6->sin6_family = sin6n->sin6_family;
+   memcpy(>sin6_addr, >sin6_addr,
+   sizeof(struct in6_addr));
+   break;
+   case AF_INET:
+   sin = (struct sockaddr_in *) _nexthop;
+   sinn = (struct sockaddr_in *) _nexthop;
+   sin->sin_family = sinn->sin_family;
+   sin->sin_addr.s_addr = sinn->sin_addr.s_addr;
+   break;
+   default:
errx(1, "mpw neighbor address not specified");
-
-   sin->sin_family = sinn->sin_family;
-   sin->sin_addr.s_addr = sinn->sin_addr.s_addr;
+   }
}
 
ifr.ifr_data = (caddr_t) 
@@ -3949,14 +3974,41 @@ void
 setmpwneighbor(const char *value, int d)
 {
struct sockaddr_in *sin;
+   struct sockaddr_in6 *sin6;
+   struct addrinfo hints, *res;
+   int rv;
 
wconfig = 1;
 
-   sin = (struct sockaddr_in *) _nexthop;
-   if (inet_aton(value, >sin_addr) == 0)
+   memset(, 0, sizeof(hints));
+   hints.ai_family = AF_UNSPEC;
+   hints.ai_socktype = SOCK_DGRAM;
+   hints.ai_protocol = 0;
+   hints.ai_flags = AI_PASSIVE;
+
+   rv = getaddrinfo(value, NULL, , );
+   if (rv != 0)
+   errx(1, "neighbor %s: %s", value, gai_strerror(rv));
+
+   switch (res->ai_family) {
+   case AF_INET:
+   sin = (struct sockaddr_in *) _nexthop;
+   sin->sin_family = res->ai_family;
+   sin->sin_addr.s_addr =
+   ((struct sockaddr_in *)res->ai_addr)->sin_addr.s_addr;
+

MPLS pseudowire over IPv6 1/2: ifconfig(8) diff

2018-12-22 Thread Denis Fondras
Allow the mpw(4) interface to establish VPLS tunnel over an IPv6-only MPLS core.

This is the ifconfig(8) bit providing display and configuration of IPv6
neighbor on mpw(4) interface.

pe1# ifconfig mpw0
mpw0: flags=51 mtu 1500
index 7 priority 0 llprio 3
encapsulation-type ethernet, control-word
mpls label: local 16 remote 16
neighbor: 2001:db8:ff::e2
groups: mpw


Index: ifconfig.8
===
RCS file: /cvs/src/sbin/ifconfig/ifconfig.8,v
retrieving revision 1.324
diff -u -p -r1.324 ifconfig.8
--- ifconfig.8  16 Nov 2018 12:25:29 -  1.324
+++ ifconfig.8  22 Dec 2018 15:55:01 -
@@ -1344,7 +1344,7 @@ is another 20-bit number which will be u
 Sets the destination address where this mpw should output.
 The
 .Ar dest-address
-is an IPv4 address that will be used to find the nexthop in the MPLS
+is an IPv4 or IPv6 address that will be used to find the nexthop in the MPLS
 network.
 .El
 .Sh PAIR
Index: ifconfig.c
===
RCS file: /cvs/src/sbin/ifconfig/ifconfig.c,v
retrieving revision 1.387
diff -u -p -r1.387 ifconfig.c
--- ifconfig.c  29 Nov 2018 00:12:34 -  1.387
+++ ifconfig.c  22 Dec 2018 15:55:02 -
@@ -3803,7 +3803,9 @@ void
 mpw_status(void)
 {
struct sockaddr_in *sin;
+   struct sockaddr_in6 *sin6;
struct ifmpwreq imr;
+   char hbuf[NI_MAXHOST];
 
bzero(, sizeof(imr));
ifr.ifr_data = (caddr_t) 
@@ -3842,11 +3844,22 @@ mpw_status(void)
else
printf("remote %u\n", imr.imr_rshim.shim_label);
 
-   sin = (struct sockaddr_in *) _nexthop;
-   if (sin->sin_addr.s_addr == 0)
-   printf("\tneighbor: none\n");
-   else
-   printf("\tneighbor: %s\n", inet_ntoa(sin->sin_addr));
+   printf("\tneighbor: ");
+   switch (imr.imr_nexthop.ss_family) {
+   case AF_INET6:
+   sin6 = (struct sockaddr_in6 *) _nexthop;
+   if (getnameinfo((struct sockaddr *)sin6, sin6->sin6_len,
+   hbuf, sizeof(hbuf), NULL, 0, NI_NUMERICHOST) != 0)
+   strlcpy(hbuf, "???", sizeof(hbuf));
+   printf("%s\n", hbuf);
+   break;
+   case AF_INET:
+   sin = (struct sockaddr_in *) _nexthop;
+   printf("%s\n", inet_ntoa(sin->sin_addr));
+   break;
+   default:
+   printf("none\n");
+   }
 }
 
 /* ARGSUSED */
@@ -3870,6 +3883,7 @@ void
 process_mpw_commands(void)
 {
struct  sockaddr_in *sin, *sinn;
+   struct  sockaddr_in6 *sin6, *sin6n;
struct  ifmpwreq imr;
 
if (wconfig == 0)
@@ -3899,14 +3913,29 @@ process_mpw_commands(void)
imrsave.imr_rshim.shim_label = imr.imr_rshim.shim_label;
}
 
-   sin = (struct sockaddr_in *) _nexthop;
-   sinn = (struct sockaddr_in *) _nexthop;
-   if (sin->sin_addr.s_addr == 0) {
-   if (sinn->sin_addr.s_addr == 0)
+   switch (imrsave.imr_nexthop.ss_family) {
+   case AF_INET6:
+   case AF_INET:
+   /* neighbor was set earlier, nothing to do */
+   break;
+   default:
+   switch (imr.imr_nexthop.ss_family) {
+   case AF_INET6:
+   sin6 = (struct sockaddr_in6 *) _nexthop;
+   sin6n = (struct sockaddr_in6 *) _nexthop;
+   sin6->sin6_family = sin6n->sin6_family;
+   memcpy(>sin6_addr, >sin6_addr,
+   sizeof(struct in6_addr));
+   break;
+   case AF_INET:
+   sin = (struct sockaddr_in *) _nexthop;
+   sinn = (struct sockaddr_in *) _nexthop;
+   sin->sin_family = sinn->sin_family;
+   sin->sin_addr.s_addr = sinn->sin_addr.s_addr;
+   break;
+   default:
errx(1, "mpw neighbor address not specified");
-
-   sin->sin_family = sinn->sin_family;
-   sin->sin_addr.s_addr = sinn->sin_addr.s_addr;
+   }
}
 
ifr.ifr_data = (caddr_t) 
@@ -3949,14 +3978,41 @@ void
 setmpwneighbor(const char *value, int d)
 {
struct sockaddr_in *sin;
+   struct sockaddr_in6 *sin6;
+   struct addrinfo hints, *res;
+   int rv;
 
wconfig = 1;
 
-   sin = (struct sockaddr_in *) _nexthop;
-   if (inet_aton(value, >sin_addr) == 0)
+   memset(, 0, sizeof(hints));
+   hints.ai_family = AF_UNSPEC;
+   hints.ai_socktype = SOCK_DGRAM;
+   hints.ai_protocol = 0;
+   hints.ai_flags = AI_PASSIVE;
+
+   rv = getaddrinfo(value, NULL, , );
+   if (rv != 0)
+   errx(1, "neighbor %s: %s", value, gai_strerror(rv));
+
+   switch (res->ai_family) {
+   case AF_INET:
+   sin = (struct sockaddr_in