[iputils/f17: 2/7] Backport capability handling from master (#870722) and drop unnecessary patches

jsynacek jsynacek at fedoraproject.org
Fri Dec 7 14:11:17 UTC 2012


commit 5983ed68085d7bbe3b73cd71f10104e5bd488494
Author: Jan Synacek <jsynacek at redhat.com>
Date:   Fri Dec 7 14:35:57 2012 +0100

    Backport capability handling from master (#870722) and drop unnecessary patches
    
    fixes #870722 - ping -I interface isn't working

 iputils-20101006-caps.patch                        |  249 ++++++++++++++++++++
 iputils-20101006-drop_caps.patch                   |  107 ---------
 ...ping-defer-caps-drop-when-marking-packets.patch |  150 ------------
 iputils.spec                                       |   12 +-
 4 files changed, 256 insertions(+), 262 deletions(-)
---
diff --git a/iputils-20101006-caps.patch b/iputils-20101006-caps.patch
new file mode 100644
index 0000000..442013f
--- /dev/null
+++ b/iputils-20101006-caps.patch
@@ -0,0 +1,249 @@
+--- iputils-s20101006/ping.c.orig	2012-12-07 14:25:08.724509944 +0100
++++ iputils-s20101006/ping.c	2012-12-07 14:20:38.000000000 +0100
+@@ -115,7 +115,6 @@ struct sockaddr_in source;
+ char *device;
+ int pmtudisc = -1;
+ 
+-
+ int
+ main(int argc, char **argv)
+ {
+@@ -128,11 +127,17 @@ main(int argc, char **argv)
+ 
+ 	char *idn;
+ 	int rc = 0;
++
++	limit_capabilities();
+ 	setlocale(LC_ALL, "");
+ 
++	enable_capability_raw();
++
+ 	icmp_sock = socket(AF_INET, SOCK_RAW, IPPROTO_ICMP);
+ 	socket_errno = errno;
+ 
++	disable_capability_raw();
++
+ 	uid = getuid();
+ 	if (setuid(uid)) {
+ 		perror("ping: setuid");
+@@ -298,9 +303,16 @@ main(int argc, char **argv)
+ 		}
+ 		if (device) {
+ 			struct ifreq ifr;
++			int rc;
++
+ 			memset(&ifr, 0, sizeof(ifr));
+ 			strncpy(ifr.ifr_name, device, IFNAMSIZ-1);
+-			if (setsockopt(probe_fd, SOL_SOCKET, SO_BINDTODEVICE, device, strlen(device)+1) == -1) {
++
++			enable_capability_raw();
++			rc = setsockopt(probe_fd, SOL_SOCKET, SO_BINDTODEVICE, device, strlen(device)+1);
++			disable_capability_raw();
++
++			if (rc == -1) {
+ 				if (IN_MULTICAST(ntohl(dst.sin_addr.s_addr))) {
+ 					struct ip_mreqn imr;
+ 					if (ioctl(probe_fd, SIOCGIFINDEX, &ifr) < 0) {
+--- iputils-s20101006/ping_common.c.orig	2012-12-07 14:25:15.051513072 +0100
++++ iputils-s20101006/ping_common.c	2012-12-07 14:20:38.000000000 +0100
+@@ -58,10 +58,144 @@ int datalen = DEFDATALEN;
+ 
+ char *hostname;
+ int uid;
++uid_t euid;
+ int ident;			/* process id to identify our packets */
+ 
+ static int screen_width = INT_MAX;
+ 
++#ifdef HAVE_CAPABILITIES
++static cap_value_t cap_raw = CAP_NET_RAW;
++static cap_value_t cap_admin = CAP_NET_ADMIN;
++#endif
++
++void limit_capabilities(void)
++{
++#ifdef HAVE_CAPABILITIES
++	cap_t cap_cur_p;
++	cap_t cap_p;
++	cap_flag_value_t cap_ok;
++
++	cap_cur_p = cap_get_proc();
++	if (!cap_cur_p) {
++		perror("ping: cap_get_proc");
++		exit(-1);
++	}
++
++	cap_p = cap_init();
++	if (!cap_p) {
++		perror("ping: cap_init");
++		exit(-1);
++	}
++
++	cap_ok = CAP_CLEAR;
++	cap_get_flag(cap_cur_p, CAP_NET_ADMIN, CAP_PERMITTED, &cap_ok);
++
++	if (cap_ok != CAP_CLEAR)
++		cap_set_flag(cap_p, CAP_PERMITTED, 1, &cap_admin, CAP_SET);
++
++	cap_ok = CAP_CLEAR;
++	cap_get_flag(cap_cur_p, CAP_NET_RAW, CAP_PERMITTED, &cap_ok);
++
++	if (cap_ok != CAP_CLEAR)
++		cap_set_flag(cap_p, CAP_PERMITTED, 1, &cap_raw, CAP_SET);
++
++	if (cap_set_proc(cap_p) < 0) {
++		perror("ping: cap_set_proc");
++		exit(-1);
++	}
++
++	if (prctl(PR_SET_KEEPCAPS, 1) < 0) {
++		perror("ping: prctl");
++		exit(-1);
++	}
++
++	if (setuid(getuid()) < 0) {
++		perror("setuid");
++		exit(-1);
++	}
++
++	if (prctl(PR_SET_KEEPCAPS, 0) < 0) {
++		perror("ping: prctl");
++		exit(-1);
++	}
++
++	cap_free(cap_p);
++	cap_free(cap_cur_p);
++#endif
++	uid = getuid();
++	euid = geteuid();
++#ifndef HAVE_CAPABILITIES
++	if (seteuid(uid)) {
++		perror("ping: setuid");
++		exit(-1);
++	}
++#endif
++}
++
++#ifdef HAVE_CAPABILITIES
++int modify_capability(cap_value_t cap, cap_flag_value_t on)
++{
++	cap_t cap_p = cap_get_proc();
++	cap_flag_value_t cap_ok;
++	int rc = -1;
++
++	if (!cap_p) {
++		perror("ping: cap_get_proc");
++		goto out;
++	}
++
++	cap_ok = CAP_CLEAR;
++	cap_get_flag(cap_p, cap, CAP_PERMITTED, &cap_ok);
++	if (cap_ok == CAP_CLEAR) {
++		rc = on ? -1 : 0;
++		goto out;
++	}
++
++	cap_set_flag(cap_p, CAP_EFFECTIVE, 1, &cap, on);
++
++	if (cap_set_proc(cap_p) < 0) {
++		perror("ping: cap_set_proc");
++		goto out;
++	}
++
++	cap_free(cap_p);
++
++	rc = 0;
++out:
++	if (cap_p)
++		cap_free(cap_p);
++	return rc;
++}
++#else
++int modify_capability(int on)
++{
++	if (seteuid(on ? euid : getuid())) {
++		perror("seteuid");
++		return -1;
++	}
++
++	return 0;
++}
++#endif
++
++void drop_capabilities(void)
++{
++#ifdef HAVE_CAPABILITIES
++	cap_t cap = cap_init();
++	if (cap_set_proc(cap) < 0) {
++		perror("ping: cap_set_proc");
++		exit(-1);
++	}
++	cap_free(cap);
++#else
++	if (setuid(getuid())) {
++		perror("ping: setuid");
++		exit(-1);
++	}
++#endif
++}
++
++
+ /* Fills all the outpack, excluding ICMP header, but _including_
+  * timestamp area with supplied pattern.
+  */
+@@ -480,8 +614,13 @@ void setup(int icmp_sock)
+ 	}
+ #endif
+ 	if (options & F_MARK) {
+-		if (setsockopt(icmp_sock, SOL_SOCKET, SO_MARK,
+-				&mark, sizeof(mark)) == -1) {
++		int ret;
++
++		enable_capability_admin();
++		ret = setsockopt(icmp_sock, SOL_SOCKET, SO_MARK, &mark, sizeof(mark));
++		disable_capability_admin();
++
++		if (ret == -1) {
+ 			/* we probably dont wanna exit since old kernels
+ 			 * dont support mark ..
+ 			*/
+--- iputils-s20101006/ping_common.h.orig	2012-12-07 14:25:22.315516660 +0100
++++ iputils-s20101006/ping_common.h	2012-12-07 14:20:38.000000000 +0100
+@@ -17,6 +17,11 @@
+ #include <string.h>
+ #include <netdb.h>
+ 
++#ifdef HAVE_CAPABILITIES
++#include <sys/prctl.h>
++#include <sys/capability.h>
++#endif
++
+ #include <netinet/in.h>
+ #include <arpa/inet.h>
+ #include <linux/types.h>
+@@ -188,6 +193,25 @@ static inline void advance_ntransmitted(
+ 		acked = (__u16)ntransmitted + 1;
+ }
+ 
++extern void limit_capabilities(void);
++static int enable_capability_raw(void);
++static int disable_capability_raw(void);
++static int enable_capability_admin(void);
++static int disable_capability_admin(void);
++#ifdef HAVE_CAPABILITIES
++extern int modify_capability(cap_value_t, cap_flag_value_t);
++static inline int enable_capability_raw(void)		{ return modify_capability(CAP_NET_RAW,   CAP_SET);   };
++static inline int disable_capability_raw(void)		{ return modify_capability(CAP_NET_RAW,   CAP_CLEAR); };
++static inline int enable_capability_admin(void)		{ return modify_capability(CAP_NET_ADMIN, CAP_SET);   };
++static inline int disable_capability_admin(void)	{ return modify_capability(CAP_NET_ADMIN, CAP_CLEAR); };
++#else
++extern int modify_capability(int);
++static inline int enable_capability_raw(void)		{ return modify_capability(1); };
++static inline int disable_capability_raw(void)		{ return modify_capability(0); };
++static inline int enable_capability_admin(void)		{ return modify_capability(1); };
++static inline int disable_capability_admin(void)	{ return modify_capability(0); };
++#endif
++extern void drop_capabilities(void);
+ 
+ extern int send_probe(void);
+ extern int receive_error_msg(void);
diff --git a/iputils.spec b/iputils.spec
index a14b3a0..325e3ed 100644
--- a/iputils.spec
+++ b/iputils.spec
@@ -1,7 +1,7 @@
 Summary: Network monitoring tools including ping
 Name: iputils
 Version: 20101006
-Release: 15%{?dist}
+Release: 16%{?dist}
 License: BSD
 URL: http://www.skbuff.net/iputils
 Group: System Environment/Daemons
@@ -26,12 +26,11 @@ Patch10: iputils-20071127-corr_type.patch
 Patch11: iputils-20071127-infiniband.patch
 Patch12: iputils-20100418-convtoint.patch
 Patch13: iputils-20100418-flowlabel.patch
-Patch14: iputils-20101006-drop_caps.patch
 Patch15: iputils-20101006-unused.patch
 Patch16: iputils-20101006-man.patch
 Patch17: iputils-20101006-eth.patch
 Patch18: iputils-20101006-rr.patch
-Patch20: iputils-20101006-ping-defer-caps-drop-when-marking-packets.patch
+Patch21: iputils-20101006-caps.patch
 
 BuildRoot: %{_tmppath}/%{name}-%{version}-%{release}-root-%(%{__id_u} -n)
 BuildRequires: docbook-utils perl-SGMLSpm
@@ -84,12 +83,11 @@ The iputils-sysvinit contains SysV initscritps support.
 %patch11 -p1 -b .infiniband
 %patch12 -p1 -b .convtoint
 %patch13 -p1 -b .flowlabel
-%patch14 -p1 -b .drop_caps
 %patch15 -p1 -b .unused
 %patch16 -p1 -b .man
 %patch17 -p1 -b .eth
 %patch18 -p1 -b .rr
-%patch20 -p1
+%patch21 -p1 -b .caps
 
 %build
 %ifarch s390 s390x
@@ -193,6 +191,10 @@ rm -rf ${RPM_BUILD_ROOT}
 %{_sysconfdir}/rc.d/init.d/rdisc
 
 %changelog
+* Fri Dec 07 2012 Jan Synáček <jsynacek at redhat.com> 20101006-16
+- Backport capability handling from master (fixes #870722 - ping -I interface
+  isn't working) and drop unnecessary patches
+
 * Mon Jun 25 2012 Jan Synáček <jsynacek at redhat.com> 20101006-15
 - Ping fixes:
   + enable marking packets when the correct capabilities are set (#802197)


More information about the scm-commits mailing list