diff options
| -rw-r--r-- | bgpd/bgp_network.c | 41 | ||||
| -rw-r--r-- | eigrpd/eigrp_network.c | 77 | ||||
| -rw-r--r-- | ldpd/socket.c | 40 | ||||
| -rw-r--r-- | lib/sockunion.c | 14 | ||||
| -rw-r--r-- | lib/vrf.c | 14 | ||||
| -rw-r--r-- | lib/zclient.c | 6 | ||||
| -rw-r--r-- | ospfd/ospf_network.c | 82 | ||||
| -rw-r--r-- | ospfd/ospfd.c | 25 | ||||
| -rw-r--r-- | pimd/pim_msdp_socket.c | 16 | ||||
| -rw-r--r-- | tests/lib/test_privs.c | 14 | ||||
| -rw-r--r-- | zebra/if_ioctl_solaris.c | 37 | ||||
| -rw-r--r-- | zebra/kernel_netlink.c | 68 | ||||
| -rw-r--r-- | zebra/kernel_socket.c | 16 | ||||
| -rw-r--r-- | zebra/zapi_msg.c | 7 | ||||
| -rw-r--r-- | zebra/zserv.c | 17 | 
15 files changed, 170 insertions, 304 deletions
diff --git a/bgpd/bgp_network.c b/bgpd/bgp_network.c index f0d4305ba2..2bdd43c140 100644 --- a/bgpd/bgp_network.c +++ b/bgpd/bgp_network.c @@ -97,17 +97,9 @@ static int bgp_md5_set_connect(int socket, union sockunion *su,  	int ret = -1;  #if HAVE_DECL_TCP_MD5SIG -	if (bgpd_privs.change(ZPRIVS_RAISE)) { -		flog_err(LIB_ERR_PRIVILEGES, "%s: could not raise privs", -			  __func__); -		return ret; +	frr_elevate_privs(&bgpd_privs) { +		ret = bgp_md5_set_socket(socket, su, password);  	} - -	ret = bgp_md5_set_socket(socket, su, password); - -	if (bgpd_privs.change(ZPRIVS_LOWER)) -		flog_err(LIB_ERR_PRIVILEGES, "%s: could not lower privs", -			  __func__);  #endif /* HAVE_TCP_MD5SIG */  	return ret; @@ -119,27 +111,18 @@ static int bgp_md5_set_password(struct peer *peer, const char *password)  	int ret = 0;  	struct bgp_listener *listener; -	if (bgpd_privs.change(ZPRIVS_RAISE)) { -		flog_err(LIB_ERR_PRIVILEGES, "%s: could not raise privs", -			  __func__); -		return -1; -	} - +	frr_elevate_privs(&bgpd_privs) {  	/* Set or unset the password on the listen socket(s). Outbound -	 * connections -	 * are taken care of in bgp_connect() below. +	 * connections are taken care of in bgp_connect() below.  	 */ -	for (ALL_LIST_ELEMENTS_RO(bm->listen_sockets, node, listener)) -		if (listener->su.sa.sa_family == peer->su.sa.sa_family) { -			ret = bgp_md5_set_socket(listener->fd, &peer->su, -						 password); -			break; -		} - -	if (bgpd_privs.change(ZPRIVS_LOWER)) -		flog_err(LIB_ERR_PRIVILEGES, "%s: could not lower privs", -			  __func__); - +		for (ALL_LIST_ELEMENTS_RO(bm->listen_sockets, node, listener)) +			if (listener->su.sa.sa_family +			    == peer->su.sa.sa_family) { +				ret = bgp_md5_set_socket(listener->fd, +							 &peer->su, password); +				break; +			} +	}  	return ret;  } diff --git a/eigrpd/eigrp_network.c b/eigrpd/eigrp_network.c index d778578d80..8eaf1e82a3 100644 --- a/eigrpd/eigrp_network.c +++ b/eigrpd/eigrp_network.c @@ -61,65 +61,42 @@ int eigrp_sock_init(void)  	int hincl = 1;  #endif -	if (eigrpd_privs.change(ZPRIVS_RAISE)) -		flog_err(LIB_ERR_PRIVILEGES, -			  "eigrp_sock_init: could not raise privs, %s", -			  safe_strerror(errno)); - -	eigrp_sock = socket(AF_INET, SOCK_RAW, IPPROTO_EIGRPIGP); -	if (eigrp_sock < 0) { -		int save_errno = errno; -		if (eigrpd_privs.change(ZPRIVS_LOWER)) -			flog_err(LIB_ERR_PRIVILEGES, -				  "eigrp_sock_init: could not lower privs, %s", -				  safe_strerror(errno)); -		flog_err_sys(LIB_ERR_SOCKET, "eigrp_read_sock_init: socket: %s", -			     safe_strerror(save_errno)); -		exit(1); -	} +	frr_elevate_privs(&eigrpd_privs) { +		eigrp_sock = socket(AF_INET, SOCK_RAW, IPPROTO_EIGRPIGP); +		if (eigrp_sock < 0) { +			zlog_err("eigrp_read_sock_init: socket: %s", +				 safe_strerror(errno)); +			exit(1); +		}  #ifdef IP_HDRINCL -	/* we will include IP header with packet */ -	ret = setsockopt(eigrp_sock, IPPROTO_IP, IP_HDRINCL, &hincl, -			 sizeof(hincl)); -	if (ret < 0) { -		int save_errno = errno; -		if (eigrpd_privs.change(ZPRIVS_LOWER)) -			flog_err(LIB_ERR_PRIVILEGES, -				  "eigrp_sock_init: could not lower privs, %s", -				  safe_strerror(errno)); -		zlog_warn("Can't set IP_HDRINCL option for fd %d: %s", -			  eigrp_sock, safe_strerror(save_errno)); -	} +		/* we will include IP header with packet */ +		ret = setsockopt(eigrp_sock, IPPROTO_IP, IP_HDRINCL, &hincl, +				 sizeof(hincl)); +		if (ret < 0) { +			zlog_warn("Can't set IP_HDRINCL option for fd %d: %s", +				  eigrp_sock, safe_strerror(errno)); +		}  #elif defined(IPTOS_PREC_INTERNETCONTROL)  #warning "IP_HDRINCL not available on this system"  #warning "using IPTOS_PREC_INTERNETCONTROL" -	ret = setsockopt_ipv4_tos(eigrp_sock, IPTOS_PREC_INTERNETCONTROL); -	if (ret < 0) { -		int save_errno = errno; -		if (eigrpd_privs.change(ZPRIVS_LOWER)) -			flog_err(LIB_ERR_PRIVILEGES, -				  "eigrpd_sock_init: could not lower privs, %s", -				  safe_strerror(errno)); -		zlog_warn("can't set sockopt IP_TOS %d to socket %d: %s", tos, -			  eigrp_sock, safe_strerror(save_errno)); -		close(eigrp_sock); /* Prevent sd leak. */ -		return ret; -	} +		ret = setsockopt_ipv4_tos(eigrp_sock, +					  IPTOS_PREC_INTERNETCONTROL); +		if (ret < 0) { +			zlog_warn("can't set sockopt IP_TOS %d to socket %d: %s", +				  tos, eigrp_sock, safe_strerror(errno)); +			close(eigrp_sock); /* Prevent sd leak. */ +			return ret; +		}  #else /* !IPTOS_PREC_INTERNETCONTROL */  #warning "IP_HDRINCL not available, nor is IPTOS_PREC_INTERNETCONTROL" -	zlog_warn("IP_HDRINCL option not available"); +		zlog_warn("IP_HDRINCL option not available");  #endif /* IP_HDRINCL */ -	ret = setsockopt_ifindex(AF_INET, eigrp_sock, 1); - -	if (ret < 0) -		zlog_warn("Can't set pktinfo option for fd %d", eigrp_sock); - -	if (eigrpd_privs.change(ZPRIVS_LOWER)) { -		flog_err(LIB_ERR_PRIVILEGES, -			  "eigrp_sock_init: could not lower privs, %s", -			  safe_strerror(errno)); +		ret = setsockopt_ifindex(AF_INET, eigrp_sock, 1); +		if (ret < 0) +			zlog_warn("Can't set pktinfo option for fd %d", +				  eigrp_sock);  	}  	return eigrp_sock; diff --git a/ldpd/socket.c b/ldpd/socket.c index 1cdef83729..bebd7a7d61 100644 --- a/ldpd/socket.c +++ b/ldpd/socket.c @@ -41,7 +41,6 @@ ldp_create_socket(int af, enum socket_type type)  #ifdef __OpenBSD__  	int			 opt;  #endif -	int			 save_errno;  	/* create socket */  	switch (type) { @@ -80,25 +79,18 @@ ldp_create_socket(int af, enum socket_type type)  		sock_set_bindany(fd, 1);  		break;  	} -	if (ldpd_privs.change(ZPRIVS_RAISE)) -		log_warn("%s: could not raise privs", __func__); -	if (sock_set_reuse(fd, 1) == -1) { -		if (ldpd_privs.change(ZPRIVS_LOWER)) -			log_warn("%s: could not lower privs", __func__); -		close(fd); -		return (-1); -	} -	if (bind(fd, &local_su.sa, sockaddr_len(&local_su.sa)) == -1) { -		save_errno = errno; -		if (ldpd_privs.change(ZPRIVS_LOWER)) -			log_warn("%s: could not lower privs", __func__); -		log_warnx("%s: error binding socket: %s", __func__, -		    safe_strerror(save_errno)); -		close(fd); -		return (-1); +	frr_elevate_privs(&ldpd_privs) { +		if (sock_set_reuse(fd, 1) == -1) { +			close(fd); +			return (-1); +		} +		if (bind(fd, &local_su.sa, sockaddr_len(&local_su.sa)) == -1) { +			log_warnx("%s: error binding socket: %s", __func__, +			    safe_strerror(errno)); +			close(fd); +			return (-1); +		}  	} -	if (ldpd_privs.change(ZPRIVS_LOWER)) -		log_warn("%s: could not lower privs", __func__);  	/* set options */  	switch (af) { @@ -302,14 +294,10 @@ sock_set_md5sig(int fd, int af, union ldpd_addr *addr, const char *password)  #if HAVE_DECL_TCP_MD5SIG  	addr2sa(af, addr, 0, &su); -	if (ldpe_privs.change(ZPRIVS_RAISE)) { -		log_warn("%s: could not raise privs", __func__); -		return (-1); +	frr_elevate_privs(&ldpe_privs) { +		ret = sockopt_tcp_signature(fd, &su, password); +		save_errno = errno;  	} -	ret = sockopt_tcp_signature(fd, &su, password); -	save_errno = errno; -	if (ldpe_privs.change(ZPRIVS_LOWER)) -		log_warn("%s: could not lower privs", __func__);  #endif /* HAVE_TCP_MD5SIG */  	if (ret < 0)  		log_warnx("%s: can't set TCP_MD5SIG option on fd %d: %s", diff --git a/lib/sockunion.c b/lib/sockunion.c index 60597b5881..bbbfbfc424 100644 --- a/lib/sockunion.c +++ b/lib/sockunion.c @@ -366,16 +366,10 @@ int sockopt_mark_default(int sock, int mark, struct zebra_privs_t *cap)  #ifdef SO_MARK  	int ret; -	if (cap->change(ZPRIVS_RAISE)) -		flog_err(LIB_ERR_PRIVILEGES, -			  "routing_socket: Can't raise privileges"); - -	ret = setsockopt(sock, SOL_SOCKET, SO_MARK, &mark, sizeof(mark)); - -	if (cap->change(ZPRIVS_LOWER)) -		flog_err(LIB_ERR_PRIVILEGES, -			  "routing_socket: Can't lower privileges"); - +	frr_elevate_privs(cap) { +		ret = setsockopt(sock, SOL_SOCKET, SO_MARK, &mark, +				 sizeof(mark)); +	}  	return ret;  #else  	return 0; @@ -764,16 +764,10 @@ DEFUN_NOSH (vrf_netns,  	if (!pathname)  		return CMD_WARNING_CONFIG_FAILED; -	if (vrf_daemon_privs && vrf_daemon_privs->change(ZPRIVS_RAISE)) -		flog_err(LIB_ERR_PRIVILEGES, "%s: Can't raise privileges", -			  __func__); - -	ret = vrf_netns_handler_create(vty, vrf, pathname, -				       NS_UNKNOWN, NS_UNKNOWN); - -	if (vrf_daemon_privs && vrf_daemon_privs->change(ZPRIVS_LOWER)) -		flog_err(LIB_ERR_PRIVILEGES, "%s: Can't lower privileges", -			  __func__); +	frr_elevate_privs(vrf_daemon_privs) { +		ret = vrf_netns_handler_create(vty, vrf, pathname, +					       NS_UNKNOWN, NS_UNKNOWN); +	}  	return ret;  } diff --git a/lib/zclient.c b/lib/zclient.c index c501ac49c7..cc91705ee2 100644 --- a/lib/zclient.c +++ b/lib/zclient.c @@ -213,9 +213,9 @@ int zclient_socket_connect(struct zclient *zclient)  	set_cloexec(sock); -	zclient->privs->change(ZPRIVS_RAISE); -	setsockopt_so_sendbuf(sock, 1048576); -	zclient->privs->change(ZPRIVS_LOWER); +	frr_elevate_privs(zclient->privs) { +		setsockopt_so_sendbuf(sock, 1048576); +	}  	/* Connect to zebra. */  	ret = connect(sock, (struct sockaddr *)&zclient_addr, zclient_addr_len); diff --git a/ospfd/ospf_network.c b/ospfd/ospf_network.c index eac4453ed5..1fb930659e 100644 --- a/ospfd/ospf_network.c +++ b/ospfd/ospf_network.c @@ -186,67 +186,51 @@ int ospf_sock_init(struct ospf *ospf)  		/* silently return since VRF is not ready */  		return -1;  	} -	if (ospfd_privs.change(ZPRIVS_RAISE)) -		flog_err(LIB_ERR_PRIVILEGES, -			  "ospf_sock_init: could not raise privs, %s", -			  safe_strerror(errno)); - -	ospf_sock = vrf_socket(AF_INET, SOCK_RAW, IPPROTO_OSPFIGP, ospf->vrf_id, -			       ospf->name); -	if (ospf_sock < 0) { -		int save_errno = errno; - -		if (ospfd_privs.change(ZPRIVS_LOWER)) -			flog_err(LIB_ERR_PRIVILEGES, -				  "ospf_sock_init: could not lower privs, %s", -				  safe_strerror(save_errno)); - -		exit(1); -	} +	frr_elevate_privs(&ospfd_privs) { +		ospf_sock = vrf_socket(AF_INET, SOCK_RAW, IPPROTO_OSPFIGP, +				       ospf->vrf_id, ospf->name); +		if (ospf_sock < 0) { +			zlog_err("ospf_read_sock_init: socket: %s", +				 safe_strerror(errno)); +			exit(1); +		}  #ifdef IP_HDRINCL -	/* we will include IP header with packet */ -	ret = setsockopt(ospf_sock, IPPROTO_IP, IP_HDRINCL, &hincl, -			 sizeof(hincl)); -	if (ret < 0) { -		int save_errno = errno; - -		zlog_warn("Can't set IP_HDRINCL option for fd %d: %s", -			  ospf_sock, safe_strerror(save_errno)); -		close(ospf_sock); -		goto out; -	} +		/* we will include IP header with packet */ +		ret = setsockopt(ospf_sock, IPPROTO_IP, IP_HDRINCL, &hincl, +				 sizeof(hincl)); +		if (ret < 0) { +			zlog_warn("Can't set IP_HDRINCL option for fd %d: %s", +				  ospf_sock, safe_strerror(errno)); +			close(ospf_sock); +			break; +		}  #elif defined(IPTOS_PREC_INTERNETCONTROL)  #warning "IP_HDRINCL not available on this system"  #warning "using IPTOS_PREC_INTERNETCONTROL" -	ret = setsockopt_ipv4_tos(ospf_sock, IPTOS_PREC_INTERNETCONTROL); -	if (ret < 0) { -		int save_errno = errno; - -		zlog_warn("can't set sockopt IP_TOS %d to socket %d: %s", tos, -			  ospf_sock, safe_strerror(save_errno)); -		close(ospf_sock); /* Prevent sd leak. */ -		goto out; -	} +		ret = setsockopt_ipv4_tos(ospf_sock, +					  IPTOS_PREC_INTERNETCONTROL); +		if (ret < 0) { +			zlog_warn("can't set sockopt IP_TOS %d to socket %d: %s", +				  tos, ospf_sock, safe_strerror(errno)); +			close(ospf_sock); /* Prevent sd leak. */ +			break; +		}  #else /* !IPTOS_PREC_INTERNETCONTROL */  #warning "IP_HDRINCL not available, nor is IPTOS_PREC_INTERNETCONTROL" -	zlog_warn("IP_HDRINCL option not available"); +		zlog_warn("IP_HDRINCL option not available");  #endif /* IP_HDRINCL */ -	ret = setsockopt_ifindex(AF_INET, ospf_sock, 1); +		ret = setsockopt_ifindex(AF_INET, ospf_sock, 1); -	if (ret < 0) -		zlog_warn("Can't set pktinfo option for fd %d", ospf_sock); +		if (ret < 0) +			zlog_warn("Can't set pktinfo option for fd %d", +				  ospf_sock); -	setsockopt_so_sendbuf(ospf_sock, bufsize); -	setsockopt_so_recvbuf(ospf_sock, bufsize); +		setsockopt_so_sendbuf(ospf_sock, bufsize); +		setsockopt_so_recvbuf(ospf_sock, bufsize); +	}  	ospf->fd = ospf_sock; -out: -	if (ospfd_privs.change(ZPRIVS_LOWER)) -		flog_err(LIB_ERR_PRIVILEGES, -			  "ospf_sock_init: could not lower privs, %s", -			  safe_strerror(errno)); -  	return ret;  } diff --git a/ospfd/ospfd.c b/ospfd/ospfd.c index bee68622f2..ac8f0d92c3 100644 --- a/ospfd/ospfd.c +++ b/ospfd/ospfd.c @@ -2088,25 +2088,18 @@ static int ospf_vrf_enable(struct vrf *vrf)  				old_vrf_id);  		if (old_vrf_id != ospf->vrf_id) { -			if (ospfd_privs.change(ZPRIVS_RAISE)) -				flog_err( -					LIB_ERR_PRIVILEGES, -					"ospf_vrf_link: could not raise privs"); +			frr_elevate_privs(&ospfd_privs) { +				/* stop zebra redist to us for old vrf */ +				zclient_send_dereg_requests(zclient, +							    old_vrf_id); -			/* stop zebra redist to us for old vrf */ -			zclient_send_dereg_requests(zclient, old_vrf_id); +				ospf_set_redist_vrf_bitmaps(ospf); -			ospf_set_redist_vrf_bitmaps(ospf); - -			/* start zebra redist to us for new vrf */ -			ospf_zebra_vrf_register(ospf); - -			ret = ospf_sock_init(ospf); -			if (ospfd_privs.change(ZPRIVS_LOWER)) -				flog_err( -					LIB_ERR_PRIVILEGES, -					"ospf_sock_init: could not lower privs"); +				/* start zebra redist to us for new vrf */ +				ospf_zebra_vrf_register(ospf); +				ret = ospf_sock_init(ospf); +			}  			if (ret < 0 || ospf->fd <= 0)  				return 0;  			thread_add_read(master, ospf_read, ospf, ospf->fd, diff --git a/pimd/pim_msdp_socket.c b/pimd/pim_msdp_socket.c index b0e7b39d7b..feac42cf53 100644 --- a/pimd/pim_msdp_socket.c +++ b/pimd/pim_msdp_socket.c @@ -176,19 +176,9 @@ int pim_msdp_sock_listen(struct pim_instance *pim)  		}  	} -	if (pimd_privs.change(ZPRIVS_RAISE)) { -		flog_err(LIB_ERR_PRIVILEGES, -			  "pim_msdp_socket: could not raise privs, %s", -			  safe_strerror(errno)); -	} - -	/* bind to well known TCP port */ -	rc = bind(sock, (struct sockaddr *)&sin, socklen); - -	if (pimd_privs.change(ZPRIVS_LOWER)) { -		flog_err(LIB_ERR_PRIVILEGES, -			  "pim_msdp_socket: could not lower privs, %s", -			  safe_strerror(errno)); +	frr_elevate_privs(&pimd_privs) { +		/* bind to well known TCP port */ +		rc = bind(sock, (struct sockaddr *)&sin, socklen);  	}  	if (rc < 0) { diff --git a/tests/lib/test_privs.c b/tests/lib/test_privs.c index 421c345436..e203da8f6e 100644 --- a/tests/lib/test_privs.c +++ b/tests/lib/test_privs.c @@ -113,10 +113,9 @@ int main(int argc, char **argv)  	((test_privs.current_state() == ZPRIVS_RAISED) ? "Raised" : "Lowered")  	printf("%s\n", PRIV_STATE()); -	test_privs.change(ZPRIVS_RAISE); - -	printf("%s\n", PRIV_STATE()); -	test_privs.change(ZPRIVS_LOWER); +	frr_elevate_privs(&test_privs) { +		printf("%s\n", PRIV_STATE()); +	}  	printf("%s\n", PRIV_STATE());  	zprivs_get_ids(&ids); @@ -126,10 +125,9 @@ int main(int argc, char **argv)  	/* but these should continue to work... */  	printf("%s\n", PRIV_STATE()); -	test_privs.change(ZPRIVS_RAISE); - -	printf("%s\n", PRIV_STATE()); -	test_privs.change(ZPRIVS_LOWER); +	frr_elevate_privs(&test_privs) { +		printf("%s\n", PRIV_STATE()); +	}  	printf("%s\n", PRIV_STATE());  	zprivs_get_ids(&ids); diff --git a/zebra/if_ioctl_solaris.c b/zebra/if_ioctl_solaris.c index ee7f22e780..5a58fe1751 100644 --- a/zebra/if_ioctl_solaris.c +++ b/zebra/if_ioctl_solaris.c @@ -60,19 +60,21 @@ static int interface_list_ioctl(int af)  	char *buf = NULL;  	frr_elevate_privs(&zserv_privs) { -  		sock = socket(af, SOCK_DGRAM, 0); -		if (sock < 0) { -			zlog_warn("Can't make %s socket stream: %s", -				  (af == AF_INET ? "AF_INET" : "AF_INET6"), -				  safe_strerror(errno)); +	} -			return -1; -		} +	if (sock < 0) { +		zlog_warn("Can't make %s socket stream: %s", +			  (af == AF_INET ? "AF_INET" : "AF_INET6"), +			  safe_strerror(errno)); +		return -1; +	} -calculate_lifc_len: /* must hold privileges to enter here */ +calculate_lifc_len: +	frr_elevate_privs(&zserv_privs) {  		lifn.lifn_family = af; -		lifn.lifn_flags = LIFC_NOXMIT; /* we want NOXMIT interfaces too */ +		lifn.lifn_flags = LIFC_NOXMIT; +		/* we want NOXMIT interfaces too */  		ret = ioctl(sock, SIOCGLIFNUM, &lifn);  		save_errno = errno; @@ -105,27 +107,18 @@ calculate_lifc_len: /* must hold privileges to enter here */  	lifconf.lifc_len = needed;  	lifconf.lifc_buf = buf; -	if (zserv_privs.change(ZPRIVS_RAISE)) -		flog_err(LIB_ERR_PRIVILEGES, "Can't raise privileges"); - -	ret = ioctl(sock, SIOCGLIFCONF, &lifconf); +	frr_elevate_privs(&zserv_privs) { +		ret = ioctl(sock, SIOCGLIFCONF, &lifconf); +	}  	if (ret < 0) {  		if (errno == EINVAL) -			goto calculate_lifc_len; /* deliberately hold privileges -						    */ +			goto calculate_lifc_len;  		zlog_warn("SIOCGLIFCONF: %s", safe_strerror(errno)); - -		if (zserv_privs.change(ZPRIVS_LOWER)) -			flog_err(LIB_ERR_PRIVILEGES, "Can't lower privileges"); -  		goto end;  	} -	if (zserv_privs.change(ZPRIVS_LOWER)) -		flog_err(LIB_ERR_PRIVILEGES, "Can't lower privileges"); -  	/* Allocate interface. */  	lifreq = lifconf.lifc_req; diff --git a/zebra/kernel_netlink.c b/zebra/kernel_netlink.c index b397e95955..176ee93cdc 100644 --- a/zebra/kernel_netlink.c +++ b/zebra/kernel_netlink.c @@ -206,34 +206,26 @@ static int netlink_socket(struct nlsock *nl, unsigned long groups,  	struct sockaddr_nl snl;  	int sock;  	int namelen; -	int save_errno; - -	if (zserv_privs.change(ZPRIVS_RAISE)) { -		flog_err(LIB_ERR_PRIVILEGES, "Can't raise privileges"); -		return -1; -	} -	sock = ns_socket(AF_NETLINK, SOCK_RAW, NETLINK_ROUTE, ns_id); -	if (sock < 0) { -		flog_err_sys(LIB_ERR_SOCKET, "Can't open %s socket: %s", -			     nl->name, safe_strerror(errno)); -		return -1; -	} +	frr_elevate_privs(&zserv_privs) { +		sock = ns_socket(AF_NETLINK, SOCK_RAW, NETLINK_ROUTE, ns_id); +		if (sock < 0) { +			zlog_err("Can't open %s socket: %s", nl->name, +				 safe_strerror(errno)); +			return -1; +		} -	memset(&snl, 0, sizeof snl); -	snl.nl_family = AF_NETLINK; -	snl.nl_groups = groups; +		memset(&snl, 0, sizeof snl); +		snl.nl_family = AF_NETLINK; +		snl.nl_groups = groups; -	/* Bind the socket to the netlink structure for anything. */ -	ret = bind(sock, (struct sockaddr *)&snl, sizeof snl); -	save_errno = errno; -	if (zserv_privs.change(ZPRIVS_LOWER)) -		flog_err(LIB_ERR_PRIVILEGES, "Can't lower privileges"); +		/* Bind the socket to the netlink structure for anything. */ +		ret = bind(sock, (struct sockaddr *)&snl, sizeof snl); +	}  	if (ret < 0) { -		flog_err_sys(LIB_ERR_SOCKET, -			     "Can't bind %s socket to group 0x%x: %s", nl->name, -			     snl.nl_groups, safe_strerror(save_errno)); +		zlog_err("Can't bind %s socket to group 0x%x: %s", nl->name, +			 snl.nl_groups, safe_strerror(errno));  		close(sock);  		return -1;  	} @@ -340,15 +332,15 @@ static void netlink_write_incoming(const char *buf, const unsigned int size,  	char fname[MAXPATHLEN];  	FILE *f; -	zserv_privs.change(ZPRIVS_RAISE);  	snprintf(fname, MAXPATHLEN, "%s/%s_%u", DAEMON_VTY_DIR, "netlink",  		 counter); -	f = fopen(fname, "w"); +	frr_elevate_privs(&zserv_privs) { +		f = fopen(fname, "w"); +	}  	if (f) {  		fwrite(buf, 1, size, f);  		fclose(f);  	} -	zserv_privs.change(ZPRIVS_LOWER);  }  /** @@ -363,8 +355,9 @@ static long netlink_read_file(char *buf, const char *fname)  	FILE *f;  	long file_bytes = -1; -	zserv_privs.change(ZPRIVS_RAISE); -	f = fopen(fname, "r"); +	frr_elevate_privs(&zserv_privs) { +		f = fopen(fname, "r"); +	}  	if (f) {  		fseek(f, 0, SEEK_END);  		file_bytes = ftell(f); @@ -372,7 +365,6 @@ static long netlink_read_file(char *buf, const char *fname)  		fread(buf, NL_RCV_PKT_BUF_SIZE, 1, f);  		fclose(f);  	} -	zserv_privs.change(ZPRIVS_LOWER);  	return file_bytes;  } @@ -985,7 +977,6 @@ int netlink_request(struct nlsock *nl, struct nlmsghdr *n)  {  	int ret;  	struct sockaddr_nl snl; -	int save_errno;  	/* Check netlink socket. */  	if (nl->sock < 0) { @@ -1003,21 +994,14 @@ int netlink_request(struct nlsock *nl, struct nlmsghdr *n)  	snl.nl_family = AF_NETLINK;  	/* Raise capabilities and send message, then lower capabilities. */ -	if (zserv_privs.change(ZPRIVS_RAISE)) { -		flog_err(LIB_ERR_PRIVILEGES, "Can't raise privileges"); -		return -1; +	frr_elevate_privs(&zserv_privs) { +		ret = sendto(nl->sock, (void *)n, n->nlmsg_len, 0, +			     (struct sockaddr *)&snl, sizeof snl);  	} -	ret = sendto(nl->sock, (void *)n, n->nlmsg_len, 0, -		     (struct sockaddr *)&snl, sizeof snl); -	save_errno = errno; - -	if (zserv_privs.change(ZPRIVS_LOWER)) -		flog_err(LIB_ERR_PRIVILEGES, "Can't lower privileges"); -  	if (ret < 0) { -		flog_err_sys(LIB_ERR_SOCKET, "%s sendto failed: %s", nl->name, -			     safe_strerror(save_errno)); +		zlog_err("%s sendto failed: %s", nl->name, +			 safe_strerror(errno));  		return -1;  	} diff --git a/zebra/kernel_socket.c b/zebra/kernel_socket.c index 79721cf87a..78e25e7626 100644 --- a/zebra/kernel_socket.c +++ b/zebra/kernel_socket.c @@ -1385,17 +1385,11 @@ static int kernel_read(struct thread *thread)  /* Make routing socket. */  static void routing_socket(struct zebra_ns *zns)  { -	if (zserv_privs.change(ZPRIVS_RAISE)) -		flog_err(LIB_ERR_PRIVILEGES, -			  "routing_socket: Can't raise privileges"); - -	routing_sock = -		ns_socket(AF_ROUTE, SOCK_RAW, 0, zns->ns_id); +	frr_elevate_privs(&zserv_privs) { +		routing_sock = ns_socket(AF_ROUTE, SOCK_RAW, 0, zns->ns_id); +	}  	if (routing_sock < 0) { -		if (zserv_privs.change(ZPRIVS_LOWER)) -			flog_err(LIB_ERR_PRIVILEGES, -				  "routing_socket: Can't lower privileges");  		zlog_warn("Can't init kernel routing socket");  		return;  	} @@ -1407,10 +1401,6 @@ static void routing_socket(struct zebra_ns *zns)  	/*if (fcntl (routing_sock, F_SETFL, O_NONBLOCK) < 0)  	  zlog_warn ("Can't set O_NONBLOCK to routing socket");*/ -	if (zserv_privs.change(ZPRIVS_LOWER)) -		flog_err(LIB_ERR_PRIVILEGES, -			  "routing_socket: Can't lower privileges"); -  	/* kernel_read needs rewrite. */  	thread_add_read(zebrad.master, kernel_read, NULL, routing_sock, NULL);  } diff --git a/zebra/zapi_msg.c b/zebra/zapi_msg.c index a74c6bc4bf..008fc8f066 100644 --- a/zebra/zapi_msg.c +++ b/zebra/zapi_msg.c @@ -3087,12 +3087,13 @@ static void zserv_write_incoming(struct stream *orig, uint16_t command)  	copy = stream_dup(orig);  	stream_set_getp(copy, 0); -	zserv_privs.change(ZPRIVS_RAISE);  	snprintf(fname, MAXPATHLEN, "%s/%u", DAEMON_VTY_DIR, command); -	fd = open(fname, O_CREAT | O_WRONLY | O_EXCL, 0644); + +	frr_elevate_privs(&zserv_privs) { +		fd = open(fname, O_CREAT | O_WRONLY | O_EXCL, 0644); +	}  	stream_flush(copy, fd);  	close(fd); -	zserv_privs.change(ZPRIVS_LOWER);  	stream_free(copy);  }  #endif diff --git a/zebra/zserv.c b/zebra/zserv.c index 553331867c..174e010743 100644 --- a/zebra/zserv.c +++ b/zebra/zserv.c @@ -787,15 +787,14 @@ void zserv_start(char *path)  			unlink(suna->sun_path);  	} -	zserv_privs.change(ZPRIVS_RAISE); -	setsockopt_so_recvbuf(zebrad.sock, 1048576); -	setsockopt_so_sendbuf(zebrad.sock, 1048576); -	zserv_privs.change(ZPRIVS_LOWER); - -	if (sa.ss_family != AF_UNIX && zserv_privs.change(ZPRIVS_RAISE)) -		flog_err(LIB_ERR_PRIVILEGES, "Can't raise privileges"); +	frr_elevate_privs(&zserv_privs) { +		setsockopt_so_recvbuf(zebrad.sock, 1048576); +		setsockopt_so_sendbuf(zebrad.sock, 1048576); +	} -	ret = bind(zebrad.sock, (struct sockaddr *)&sa, sa_len); +	frr_elevate_privs((sa.ss_family != AF_UNIX) ? &zserv_privs : NULL) { +		ret = bind(zebrad.sock, (struct sockaddr *)&sa, sa_len); +	}  	if (ret < 0) {  		zlog_warn("Can't bind zserv socket on %s: %s", path,  			  safe_strerror(errno)); @@ -805,8 +804,6 @@ void zserv_start(char *path)  		zebrad.sock = -1;  		return;  	} -	if (sa.ss_family != AF_UNIX && zserv_privs.change(ZPRIVS_LOWER)) -		flog_err(LIB_ERR_PRIVILEGES, "Can't lower privileges");  	ret = listen(zebrad.sock, 5);  	if (ret < 0) {  | 
