summaryrefslogtreecommitdiff
path: root/usr.sbin/ldpd
diff options
context:
space:
mode:
authorRenato Westphal <renato@cvs.openbsd.org>2016-07-01 23:14:32 +0000
committerRenato Westphal <renato@cvs.openbsd.org>2016-07-01 23:14:32 +0000
commitdfb16013b421d49c330b7e33674c5b1db89f6931 (patch)
tree51cfdf953504834c8fe109bc4dce04a5e64416f6 /usr.sbin/ldpd
parent5bb202e21db7646a722a95c67eb7e29ba711849e (diff)
Add GTSM support (RFC 6720).
This also finishes the missing bits from our RFC 7552 implementation because GTSM is mandatory for LDPv6. To avoid any kind of interoperability problems, I included a few knobs to enable/disable GTSM on a per-address-family and per-neighbor basis. Cisco's LDPv6 implementation, for instance, doesn't support GTSM. "reads good" claudio@
Diffstat (limited to 'usr.sbin/ldpd')
-rw-r--r--usr.sbin/ldpd/hello.c12
-rw-r--r--usr.sbin/ldpd/ldp.h3
-rw-r--r--usr.sbin/ldpd/ldpd.812
-rw-r--r--usr.sbin/ldpd/ldpd.c26
-rw-r--r--usr.sbin/ldpd/ldpd.conf.537
-rw-r--r--usr.sbin/ldpd/ldpd.h14
-rw-r--r--usr.sbin/ldpd/ldpe.h8
-rw-r--r--usr.sbin/ldpd/neighbor.c90
-rw-r--r--usr.sbin/ldpd/packet.c7
-rw-r--r--usr.sbin/ldpd/parse.y22
-rw-r--r--usr.sbin/ldpd/printconf.c17
-rw-r--r--usr.sbin/ldpd/socket.c106
12 files changed, 322 insertions, 32 deletions
diff --git a/usr.sbin/ldpd/hello.c b/usr.sbin/ldpd/hello.c
index 5eb82617733..09c3976ed1e 100644
--- a/usr.sbin/ldpd/hello.c
+++ b/usr.sbin/ldpd/hello.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: hello.c,v 1.52 2016/06/27 19:18:54 renato Exp $ */
+/* $OpenBSD: hello.c,v 1.53 2016/07/01 23:14:31 renato Exp $ */
/*
* Copyright (c) 2013, 2016 Renato Westphal <renato@openbsd.org>
@@ -53,6 +53,8 @@ send_hello(enum hello_type type, struct iface_af *ia, struct tnbr *tnbr)
/* multicast destination address */
switch (af) {
case AF_INET:
+ if (!(leconf->ipv4.flags & F_LDPD_AF_NO_GTSM))
+ flags |= GTSM_HELLO;
dst.v4 = global.mcast_addr_v4;
break;
case AF_INET6:
@@ -363,6 +365,14 @@ recv_hello(struct in_addr lsr_id, struct ldp_msg *lm, int af,
(trans_pref == DUAL_STACK_LDPOV6 && af == AF_INET6))))
nbr = nbr_new(lsr_id, af, ds_tlv, &trans_addr, scope_id);
+ /* dynamic LDPv4 GTSM negotiation as per RFC 6720 */
+ if (nbr) {
+ if (flags & GTSM_HELLO)
+ nbr->flags |= F_NBR_GTSM_NEGOTIATED;
+ else
+ nbr->flags &= ~F_NBR_GTSM_NEGOTIATED;
+ }
+
/* update neighbor's configuration sequence number */
if (nbr && (tlvs_rcvd & F_HELLO_TLV_RCVD_CONF)) {
if (conf_seqnum > nbr->conf_seqnum &&
diff --git a/usr.sbin/ldpd/ldp.h b/usr.sbin/ldpd/ldp.h
index 964a0be8dec..281decc7729 100644
--- a/usr.sbin/ldpd/ldp.h
+++ b/usr.sbin/ldpd/ldp.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: ldp.h,v 1.29 2016/05/23 19:14:03 renato Exp $ */
+/* $OpenBSD: ldp.h,v 1.30 2016/07/01 23:14:31 renato Exp $ */
/*
* Copyright (c) 2013, 2016 Renato Westphal <renato@openbsd.org>
@@ -142,6 +142,7 @@ struct hello_prms_tlv {
#define TARGETED_HELLO 0x8000
#define REQUEST_TARG_HELLO 0x4000
+#define GTSM_HELLO 0x2000
struct hello_prms_opt4_tlv {
uint16_t type;
diff --git a/usr.sbin/ldpd/ldpd.8 b/usr.sbin/ldpd/ldpd.8
index b4de0adc9e0..6c2fd9b4801 100644
--- a/usr.sbin/ldpd/ldpd.8
+++ b/usr.sbin/ldpd/ldpd.8
@@ -1,4 +1,4 @@
-.\" $OpenBSD: ldpd.8,v 1.15 2016/05/23 19:14:03 renato Exp $
+.\" $OpenBSD: ldpd.8,v 1.16 2016/07/01 23:14:31 renato Exp $
.\"
.\" Copyright (c) 2013, 2016 Renato Westphal <renato@openbsd.org>
.\" Copyright (c) 2009 Michele Marchetto <michele@openbsd.org>
@@ -16,7 +16,7 @@
.\" ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
.\" OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
.\"
-.Dd $Mdocdate: May 23 2016 $
+.Dd $Mdocdate: July 1 2016 $
.Dt LDPD 8
.Os
.Sh NAME
@@ -129,6 +129,14 @@ socket used for communication with
.Re
.Pp
.Rs
+.%A C. Pignataro
+.%A R. Asati
+.%D August 2012
+.%R RFC 6720
+.%T The Generalized TTL Security Mechanism (GTSM) for the Label Distribution Protocol (LDP)
+.Re
+.Pp
+.Rs
.%A R. Asati
.%A C. Pignataro
.%A K. Raza
diff --git a/usr.sbin/ldpd/ldpd.c b/usr.sbin/ldpd/ldpd.c
index 9ef1e63d2a6..e2bc9d9a14b 100644
--- a/usr.sbin/ldpd/ldpd.c
+++ b/usr.sbin/ldpd/ldpd.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: ldpd.c,v 1.54 2016/06/18 17:13:05 renato Exp $ */
+/* $OpenBSD: ldpd.c,v 1.55 2016/07/01 23:14:31 renato Exp $ */
/*
* Copyright (c) 2013, 2016 Renato Westphal <renato@openbsd.org>
@@ -813,6 +813,7 @@ static void
merge_af(int af, struct ldpd_af_conf *af_conf, struct ldpd_af_conf *xa)
{
int egress_label_changed = 0;
+ int update_sockets = 0;
if (af_conf->keepalive != xa->keepalive) {
af_conf->keepalive = xa->keepalive;
@@ -828,6 +829,16 @@ merge_af(int af, struct ldpd_af_conf *af_conf, struct ldpd_af_conf *xa)
!(xa->flags & F_LDPD_AF_THELLO_ACCEPT))
ldpe_remove_dynamic_tnbrs(af);
+ if ((af_conf->flags & F_LDPD_AF_NO_GTSM) !=
+ (xa->flags & F_LDPD_AF_NO_GTSM)) {
+ if (af == AF_INET6)
+ /* need to set/unset IPV6_MINHOPCOUNT */
+ update_sockets = 1;
+ else if (ldpd_process == PROC_LDP_ENGINE)
+ /* for LDPv4 just resetting the neighbors is enough */
+ ldpe_reset_nbrs(af);
+ }
+
if ((af_conf->flags & F_LDPD_AF_EXPNULL) !=
(xa->flags & F_LDPD_AF_EXPNULL))
egress_label_changed = 1;
@@ -851,10 +862,12 @@ merge_af(int af, struct ldpd_af_conf *af_conf, struct ldpd_af_conf *xa)
if (ldp_addrcmp(af, &af_conf->trans_addr, &xa->trans_addr)) {
af_conf->trans_addr = xa->trans_addr;
- if (ldpd_process == PROC_MAIN)
- imsg_compose_event(iev_ldpe, IMSG_CLOSE_SOCKETS, af,
- 0, -1, NULL, 0);
+ update_sockets = 1;
}
+
+ if (ldpd_process == PROC_MAIN && update_sockets)
+ imsg_compose_event(iev_ldpe, IMSG_CLOSE_SOCKETS, af, 0, -1,
+ NULL, 0);
}
static void
@@ -988,7 +1001,10 @@ merge_nbrps(struct ldpd_conf *conf, struct ldpd_conf *xconf)
}
/* update existing nbrps */
- if (nbrp->keepalive != xn->keepalive ||
+ if (nbrp->flags != xn->flags ||
+ nbrp->keepalive != xn->keepalive ||
+ nbrp->gtsm_enabled != xn->gtsm_enabled ||
+ nbrp->gtsm_hops != xn->gtsm_hops ||
nbrp->auth.method != xn->auth.method ||
strcmp(nbrp->auth.md5key, xn->auth.md5key) != 0)
nbrp_changed = 1;
diff --git a/usr.sbin/ldpd/ldpd.conf.5 b/usr.sbin/ldpd/ldpd.conf.5
index c9dbb9de895..686e3ccfc6d 100644
--- a/usr.sbin/ldpd/ldpd.conf.5
+++ b/usr.sbin/ldpd/ldpd.conf.5
@@ -1,4 +1,4 @@
-.\" $OpenBSD: ldpd.conf.5,v 1.29 2016/05/23 21:05:07 jmc Exp $
+.\" $OpenBSD: ldpd.conf.5,v 1.30 2016/07/01 23:14:31 renato Exp $
.\"
.\" Copyright (c) 2013, 2016 Renato Westphal <renato@openbsd.org>
.\" Copyright (c) 2009 Michele Marchetto <michele@openbsd.org>
@@ -19,7 +19,7 @@
.\" ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
.\" OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
.\"
-.Dd $Mdocdate: May 23 2016 $
+.Dd $Mdocdate: July 1 2016 $
.Dt LDPD.CONF 5
.Os
.Sh NAME
@@ -145,6 +145,28 @@ connected prefixes.
The default is
.Ic no .
.Pp
+.It Xo
+.Ic gtsm-enable
+.Pq Ic yes Ns | Ns Ic no
+.Xc
+If set to
+.Ic yes ,
+.Xr ldpd 8
+will use the GTSM procedures described in RFC 6720 (for the IPv4 address-family)
+and RFC 7552 (for the IPv6 address-family).
+.Pp
+Since GTSM is mandatory for LDPv6, the only effect of disabling GTSM for the
+IPv6 address-family is that
+.Xr ldpd 8
+will not check the incoming packets' Hop Limit.
+Outgoing packets will still be sent using a Hop Limit of 255 to guarantee
+interoperability.
+.Pp
+If GTSM is enabled, multi-hop neighbors should have either GTSM disabled
+individually or configured with an appropriate gtsm-hops distance.
+The default is
+.Ic yes .
+.Pp
.It Ic keepalive Ar seconds
Set the keepalive timeout in seconds.
The default value is 180; valid range is 3\-65535.
@@ -239,6 +261,17 @@ Neighbor-specific parameters are listed below.
Set the keepalive timeout in seconds.
Inherited from the global configuration if not given.
The default value is 180; valid range is 3\-65535.
+.It Xo
+.Ic gtsm-enable
+.Pq Ic yes Ns | Ns Ic no
+.Xc
+Override the inherited configuration and enable/disable GTSM for this neighbor.
+.It Ic gtsm-hops Ar hops
+Set the maximum number of hops the neighbor may be away.
+When GTSM is enabled for this neighbor, incoming packets are required to have
+a TTL/Hop Limit of 256 minus this value, ensuring they have not passed
+through more than the expected number of hops.
+The default value is 1; valid range is 1\-255.
.It Ic password Ar secret
Enable TCP MD5 signatures per RFC 5036.
.El
diff --git a/usr.sbin/ldpd/ldpd.h b/usr.sbin/ldpd/ldpd.h
index 3c59cc19783..03a90a46a12 100644
--- a/usr.sbin/ldpd/ldpd.h
+++ b/usr.sbin/ldpd/ldpd.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: ldpd.h,v 1.77 2016/06/13 23:01:37 renato Exp $ */
+/* $OpenBSD: ldpd.h,v 1.78 2016/07/01 23:14:31 renato Exp $ */
/*
* Copyright (c) 2013, 2016 Renato Westphal <renato@openbsd.org>
@@ -288,6 +288,8 @@ struct nbr_params {
LIST_ENTRY(nbr_params) entry;
struct in_addr lsr_id;
uint16_t keepalive;
+ int gtsm_enabled;
+ uint8_t gtsm_hops;
struct {
enum auth_method method;
char md5key[TCP_MD5_KEY_LEN];
@@ -296,6 +298,8 @@ struct nbr_params {
uint8_t flags;
};
#define F_NBRP_KEEPALIVE 0x01
+#define F_NBRP_GTSM 0x02
+#define F_NBRP_GTSM_HOPS 0x04
struct l2vpn_if {
LIST_ENTRY(l2vpn_if) entry;
@@ -368,6 +372,7 @@ struct ldpd_af_conf {
#define F_LDPD_AF_ENABLED 0x0001
#define F_LDPD_AF_THELLO_ACCEPT 0x0002
#define F_LDPD_AF_EXPNULL 0x0004
+#define F_LDPD_AF_NO_GTSM 0x0008
struct ldpd_conf {
struct in_addr rtr_id;
@@ -574,13 +579,18 @@ int ldp_create_socket(int, enum socket_type);
void sock_set_recvbuf(int);
int sock_set_reuse(int, int);
int sock_set_bindany(int, int);
-int sock_set_ipv4_mcast_ttl(int, uint8_t);
int sock_set_ipv4_tos(int, int);
int sock_set_ipv4_recvif(int, int);
+int sock_set_ipv4_minttl(int, int);
+int sock_set_ipv4_ucast_ttl(int fd, int);
+int sock_set_ipv4_mcast_ttl(int, uint8_t);
int sock_set_ipv4_mcast(struct iface *);
int sock_set_ipv4_mcast_loop(int);
int sock_set_ipv6_dscp(int, int);
int sock_set_ipv6_pktinfo(int, int);
+int sock_set_ipv6_minhopcount(int, int);
+int sock_set_ipv6_ucast_hops(int, int);
+int sock_set_ipv6_mcast_hops(int, int);
int sock_set_ipv6_mcast(struct iface *);
int sock_set_ipv6_mcast_loop(int);
diff --git a/usr.sbin/ldpd/ldpe.h b/usr.sbin/ldpd/ldpe.h
index dade57be7d3..ac0a285f8b7 100644
--- a/usr.sbin/ldpd/ldpe.h
+++ b/usr.sbin/ldpd/ldpe.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: ldpe.h,v 1.63 2016/06/27 19:06:33 renato Exp $ */
+/* $OpenBSD: ldpe.h,v 1.64 2016/07/01 23:14:31 renato Exp $ */
/*
* Copyright (c) 2013, 2016 Renato Westphal <renato@openbsd.org>
@@ -101,7 +101,10 @@ struct nbr {
enum auth_method method;
char md5key[TCP_MD5_KEY_LEN];
} auth;
+ int flags;
};
+#define F_NBR_GTSM_NEGOTIATED 0x01
+
RB_HEAD(nbr_id_head, nbr);
RB_PROTOTYPE(nbr_id_head, nbr, id_tree, nbr_id_compare)
RB_HEAD(nbr_addr_head, nbr);
@@ -236,6 +239,9 @@ void nbr_stop_idtimer(struct nbr *);
int nbr_pending_idtimer(struct nbr *);
int nbr_pending_connect(struct nbr *);
int nbr_establish_connection(struct nbr *);
+int nbr_gtsm_enabled(struct nbr *, struct nbr_params *);
+int nbr_gtsm_setup(int, int, struct nbr_params *);
+int nbr_gtsm_check(int, struct nbr *, struct nbr_params *);
struct nbr_params *nbr_params_new(struct in_addr);
struct nbr_params *nbr_params_find(struct ldpd_conf *, struct in_addr);
uint16_t nbr_get_keepalive(int, struct in_addr);
diff --git a/usr.sbin/ldpd/neighbor.c b/usr.sbin/ldpd/neighbor.c
index 8f8cf4fe003..bf62c0dc5ad 100644
--- a/usr.sbin/ldpd/neighbor.c
+++ b/usr.sbin/ldpd/neighbor.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: neighbor.c,v 1.74 2016/06/13 23:01:37 renato Exp $ */
+/* $OpenBSD: neighbor.c,v 1.75 2016/07/01 23:14:31 renato Exp $ */
/*
* Copyright (c) 2013, 2016 Renato Westphal <renato@openbsd.org>
@@ -608,6 +608,11 @@ nbr_establish_connection(struct nbr *nbr)
return (-1);
}
+ if (nbr_gtsm_check(nbr->fd, nbr, nbrp)) {
+ close(nbr->fd);
+ return (-1);
+ }
+
/*
* Send an extra hello to guarantee that the remote peer has formed
* an adjacency as well.
@@ -636,6 +641,89 @@ nbr_establish_connection(struct nbr *nbr)
return (0);
}
+int
+nbr_gtsm_enabled(struct nbr *nbr, struct nbr_params *nbrp)
+{
+ /*
+ * RFC 6720 - Section 3:
+ * "This document allows for the implementation to provide an option to
+ * statically (e.g., via configuration) and/or dynamically override the
+ * default behavior and enable/disable GTSM on a per-peer basis".
+ */
+ if (nbrp && (nbrp->flags & F_NBRP_GTSM))
+ return (nbrp->gtsm_enabled);
+
+ if ((ldp_af_conf_get(leconf, nbr->af))->flags & F_LDPD_AF_NO_GTSM)
+ return (0);
+
+ /* By default, GTSM support has to be negotiated for LDPv4 */
+ if (nbr->af == AF_INET && !(nbr->flags & F_NBR_GTSM_NEGOTIATED))
+ return (0);
+
+ return (1);
+}
+
+int
+nbr_gtsm_setup(int fd, int af, struct nbr_params *nbrp)
+{
+ int ttl = 255;
+
+ if (nbrp && (nbrp->flags & F_NBRP_GTSM_HOPS))
+ ttl = 256 - nbrp->gtsm_hops;
+
+ switch (af) {
+ case AF_INET:
+ if (sock_set_ipv4_minttl(fd, ttl) == -1)
+ return (-1);
+ ttl = 255;
+ if (sock_set_ipv4_ucast_ttl(fd, ttl) == -1)
+ return (-1);
+ break;
+ case AF_INET6:
+ if (sock_set_ipv6_minhopcount(fd, ttl) == -1)
+ return (-1);
+ ttl = 255;
+ if (sock_set_ipv6_ucast_hops(fd, ttl) == -1)
+ return (-1);
+ break;
+ default:
+ fatalx("nbr_gtsm_setup: unknown af");
+ }
+
+ return (0);
+}
+
+int
+nbr_gtsm_check(int fd, struct nbr *nbr, struct nbr_params *nbrp)
+{
+ if (!nbr_gtsm_enabled(nbr, nbrp)) {
+ switch (nbr->af) {
+ case AF_INET:
+ sock_set_ipv4_ucast_ttl(fd, -1);
+ break;
+ case AF_INET6:
+ /*
+ * Send packets with a Hop Limit of 255 even when GSTM
+ * is disabled to guarantee interoperability.
+ */
+ sock_set_ipv6_ucast_hops(fd, 255);
+ break;
+ default:
+ fatalx("nbr_gtsm_check: unknown af");
+ break;
+ }
+ return (0);
+ }
+
+ if (nbr_gtsm_setup(fd, nbr->af, nbrp) == -1) {
+ log_warnx("%s: error enabling GTSM for lsr-id %s", __func__,
+ inet_ntoa(nbr->id));
+ return (-1);
+ }
+
+ return (0);
+}
+
static int
nbr_act_session_operational(struct nbr *nbr)
{
diff --git a/usr.sbin/ldpd/packet.c b/usr.sbin/ldpd/packet.c
index a211994a9a2..ababd18b7ba 100644
--- a/usr.sbin/ldpd/packet.c
+++ b/usr.sbin/ldpd/packet.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: packet.c,v 1.64 2016/06/18 17:31:32 renato Exp $ */
+/* $OpenBSD: packet.c,v 1.65 2016/07/01 23:14:31 renato Exp $ */
/*
* Copyright (c) 2013, 2016 Renato Westphal <renato@openbsd.org>
@@ -387,6 +387,11 @@ session_accept_nbr(struct nbr *nbr, int fd)
socklen_t len;
nbrp = nbr_params_find(leconf, nbr->id);
+ if (nbr_gtsm_check(fd, nbr, nbrp)) {
+ close(fd);
+ return;
+ }
+
if (nbrp && nbrp->auth.method == AUTH_MD5SIG) {
if (sysdep.no_pfkey || sysdep.no_md5sig) {
log_warnx("md5sig configured but not available");
diff --git a/usr.sbin/ldpd/parse.y b/usr.sbin/ldpd/parse.y
index 4ba0249eaa0..98f0e1e3b7f 100644
--- a/usr.sbin/ldpd/parse.y
+++ b/usr.sbin/ldpd/parse.y
@@ -1,4 +1,4 @@
-/* $OpenBSD: parse.y,v 1.56 2016/06/21 21:35:24 benno Exp $ */
+/* $OpenBSD: parse.y,v 1.57 2016/07/01 23:14:31 renato Exp $ */
/*
* Copyright (c) 2013, 2015, 2016 Renato Westphal <renato@openbsd.org>
@@ -136,7 +136,7 @@ static int pushback_index;
%token INTERFACE TNEIGHBOR ROUTERID FIBUPDATE EXPNULL
%token LHELLOHOLDTIME LHELLOINTERVAL
%token THELLOHOLDTIME THELLOINTERVAL
-%token THELLOACCEPT AF IPV4 IPV6
+%token THELLOACCEPT AF IPV4 IPV6 GTSMENABLE GTSMHOPS
%token KEEPALIVE TRANSADDRESS TRANSPREFERENCE DSCISCOINTEROP
%token NEIGHBOR PASSWORD
%token L2VPN TYPE VPLS PWTYPE MTU BRIDGE
@@ -324,6 +324,10 @@ afoptsl : TRANSADDRESS STRING {
YYERROR;
}
}
+ | GTSMENABLE yesno {
+ if ($2 == 0)
+ defs->afflags |= F_LDPD_AF_NO_GTSM;
+ }
| af_defaults
| iface_defaults
| tnbr_defaults
@@ -413,6 +417,18 @@ nbr_opts : KEEPALIVE NUMBER {
nbrp->auth.method = AUTH_MD5SIG;
free($2);
}
+ | GTSMENABLE yesno {
+ nbrp->flags |= F_NBRP_GTSM;
+ nbrp->gtsm_enabled = $2;
+ }
+ | GTSMHOPS NUMBER {
+ if ($2 < 1 || $2 > 255) {
+ yyerror("invalid number of hops %lld", $2);
+ YYERROR;
+ }
+ nbrp->gtsm_hops = $2;
+ nbrp->flags |= F_NBRP_GTSM_HOPS;
+ }
;
pw_defaults : STATUSTLV yesno {
@@ -807,6 +823,8 @@ lookup(char *s)
{"ethernet-tagged", ETHERNETTAGGED},
{"explicit-null", EXPNULL},
{"fib-update", FIBUPDATE},
+ {"gtsm-enable", GTSMENABLE},
+ {"gtsm-hops", GTSMHOPS},
{"include", INCLUDE},
{"interface", INTERFACE},
{"ipv4", IPV4},
diff --git a/usr.sbin/ldpd/printconf.c b/usr.sbin/ldpd/printconf.c
index e26b57ebe73..32db88109df 100644
--- a/usr.sbin/ldpd/printconf.c
+++ b/usr.sbin/ldpd/printconf.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: printconf.c,v 1.25 2016/05/23 19:14:03 renato Exp $ */
+/* $OpenBSD: printconf.c,v 1.26 2016/07/01 23:14:31 renato Exp $ */
/*
* Copyright (c) 2013, 2016 Renato Westphal <renato@openbsd.org>
@@ -74,6 +74,11 @@ print_af(int af, struct ldpd_conf *conf, struct ldpd_af_conf *af_conf)
else
printf("\texplicit-null no\n");
+ if (af_conf->flags & F_LDPD_AF_NO_GTSM)
+ printf("\tgtsm-enable no\n");
+ else
+ printf("\tgtsm-enable yes\n");
+
printf("\tkeepalive %u\n", af_conf->keepalive);
printf("\ttransport-address %s\n", log_addr(af, &af_conf->trans_addr));
@@ -116,6 +121,16 @@ print_nbrp(struct nbr_params *nbrp)
if (nbrp->flags & F_NBRP_KEEPALIVE)
printf("\tkeepalive %u\n", nbrp->keepalive);
+ if (nbrp->flags & F_NBRP_GTSM) {
+ if (nbrp->gtsm_enabled)
+ printf("\tgtsm-enable yes\n");
+ else
+ printf("\tgtsm-enable no\n");
+ }
+
+ if (nbrp->flags & F_NBRP_GTSM_HOPS)
+ printf("\tgtsm-hops %u\n", nbrp->gtsm_hops);
+
if (nbrp->auth.method == AUTH_MD5SIG)
printf("\tpassword XXXXXX\n");
diff --git a/usr.sbin/ldpd/socket.c b/usr.sbin/ldpd/socket.c
index 231bee08856..039241a6fb2 100644
--- a/usr.sbin/ldpd/socket.c
+++ b/usr.sbin/ldpd/socket.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: socket.c,v 1.7 2016/05/23 19:09:25 renato Exp $ */
+/* $OpenBSD: socket.c,v 1.8 2016/07/01 23:14:31 renato Exp $ */
/*
* Copyright (c) 2016 Renato Westphal <renato@openbsd.org>
@@ -112,6 +112,12 @@ ldp_create_socket(int af, enum socket_type type)
return (-1);
}
}
+ if (type == LDP_SOCKET_SESSION) {
+ if (sock_set_ipv4_ucast_ttl(fd, 255) == -1) {
+ close(fd);
+ return (-1);
+ }
+ }
break;
case AF_INET6:
if (sock_set_ipv6_dscp(fd, IPTOS_PREC_INTERNETCONTROL) == -1) {
@@ -123,6 +129,16 @@ ldp_create_socket(int af, enum socket_type type)
close(fd);
return (-1);
}
+ if (sock_set_ipv6_mcast_hops(fd, 255) == -1) {
+ close(fd);
+ return (-1);
+ }
+ if (!(ldpd_conf->ipv6.flags & F_LDPD_AF_NO_GTSM)) {
+ if (sock_set_ipv6_minhopcount(fd, 255) == -1) {
+ close(fd);
+ return (-1);
+ }
+ }
}
if (type == LDP_SOCKET_DISC || type == LDP_SOCKET_EDISC) {
if (sock_set_ipv6_pktinfo(fd, 1) == -1) {
@@ -130,6 +146,12 @@ ldp_create_socket(int af, enum socket_type type)
return (-1);
}
}
+ if (type == LDP_SOCKET_SESSION) {
+ if (sock_set_ipv6_ucast_hops(fd, 255) == -1) {
+ close(fd);
+ return (-1);
+ }
+ }
break;
}
switch (type) {
@@ -194,12 +216,10 @@ sock_set_bindany(int fd, int enable)
}
int
-sock_set_ipv4_mcast_ttl(int fd, uint8_t ttl)
+sock_set_ipv4_tos(int fd, int tos)
{
- if (setsockopt(fd, IPPROTO_IP, IP_MULTICAST_TTL,
- (char *)&ttl, sizeof(ttl)) < 0) {
- log_warn("%s: error setting IP_MULTICAST_TTL to %d",
- __func__, ttl);
+ if (setsockopt(fd, IPPROTO_IP, IP_TOS, (int *)&tos, sizeof(tos)) < 0) {
+ log_warn("%s: error setting IP_TOS to 0x%x", __func__, tos);
return (-1);
}
@@ -207,10 +227,21 @@ sock_set_ipv4_mcast_ttl(int fd, uint8_t ttl)
}
int
-sock_set_ipv4_tos(int fd, int tos)
+sock_set_ipv4_recvif(int fd, int enable)
{
- if (setsockopt(fd, IPPROTO_IP, IP_TOS, (int *)&tos, sizeof(tos)) < 0) {
- log_warn("%s: error setting IP_TOS to 0x%x", __func__, tos);
+ if (setsockopt(fd, IPPROTO_IP, IP_RECVIF, &enable,
+ sizeof(enable)) < 0) {
+ log_warn("%s: error setting IP_RECVIF", __func__);
+ return (-1);
+ }
+ return (0);
+}
+
+int
+sock_set_ipv4_minttl(int fd, int ttl)
+{
+ if (setsockopt(fd, IPPROTO_IP, IP_MINTTL, &ttl, sizeof(ttl)) < 0) {
+ log_warn("%s: error setting IP_MINTTL", __func__);
return (-1);
}
@@ -218,13 +249,26 @@ sock_set_ipv4_tos(int fd, int tos)
}
int
-sock_set_ipv4_recvif(int fd, int enable)
+sock_set_ipv4_ucast_ttl(int fd, int ttl)
{
- if (setsockopt(fd, IPPROTO_IP, IP_RECVIF, &enable,
- sizeof(enable)) < 0) {
- log_warn("%s: error setting IP_RECVIF", __func__);
+ if (setsockopt(fd, IPPROTO_IP, IP_TTL, &ttl, sizeof(ttl)) < 0) {
+ log_warn("%s: error setting IP_TTL", __func__);
return (-1);
}
+
+ return (0);
+}
+
+int
+sock_set_ipv4_mcast_ttl(int fd, uint8_t ttl)
+{
+ if (setsockopt(fd, IPPROTO_IP, IP_MULTICAST_TTL,
+ (char *)&ttl, sizeof(ttl)) < 0) {
+ log_warn("%s: error setting IP_MULTICAST_TTL to %d",
+ __func__, ttl);
+ return (-1);
+ }
+
return (0);
}
@@ -284,6 +328,42 @@ sock_set_ipv6_pktinfo(int fd, int enable)
}
int
+sock_set_ipv6_minhopcount(int fd, int hoplimit)
+{
+ if (setsockopt(fd, IPPROTO_IPV6, IPV6_MINHOPCOUNT,
+ &hoplimit, sizeof(hoplimit)) < 0) {
+ log_warn("%s: error setting IPV6_MINHOPCOUNT", __func__);
+ return (-1);
+ }
+
+ return (0);
+}
+
+int
+sock_set_ipv6_ucast_hops(int fd, int hoplimit)
+{
+ if (setsockopt(fd, IPPROTO_IPV6, IPV6_UNICAST_HOPS,
+ &hoplimit, sizeof(hoplimit)) < 0) {
+ log_warn("%s: error setting IPV6_UNICAST_HOPS", __func__);
+ return (-1);
+ }
+
+ return (0);
+}
+
+int
+sock_set_ipv6_mcast_hops(int fd, int hoplimit)
+{
+ if (setsockopt(fd, IPPROTO_IPV6, IPV6_MULTICAST_HOPS,
+ &hoplimit, sizeof(hoplimit)) < 0) {
+ log_warn("%s: error setting IPV6_MULTICAST_HOPS", __func__);
+ return (-1);
+ }
+
+ return (0);
+}
+
+int
sock_set_ipv6_mcast(struct iface *iface)
{
if (setsockopt(global.ipv6.ldp_disc_socket, IPPROTO_IPV6,