* [gentoo-commits] proj/portage:master commit in: man/, pym/portage/package/ebuild/, pym/portage/
@ 2011-04-05 22:23 Zac Medico
0 siblings, 0 replies; 5+ messages in thread
From: Zac Medico @ 2011-04-05 22:23 UTC (permalink / raw
To: gentoo-commits
commit: 1944622240d87dfa90d88ba19d68f023eed9949f
Author: Zac Medico <zmedico <AT> gentoo <DOT> org>
AuthorDate: Tue Apr 5 22:23:28 2011 +0000
Commit: Zac Medico <zmedico <AT> gentoo <DOT> org>
CommitDate: Tue Apr 5 22:23:28 2011 +0000
URL: http://git.overlays.gentoo.org/gitweb/?p=proj/portage.git;a=commit;h=19446222
Add force-mirror FEATURE.
force-mirror: Only fetch files from configured mirrors, ignoring
SRC_URI, except when mirror is in the ebuild(5) RESTRICT variable.
BUG=chromium-os:13221
TEST=Test that ebuilds now fail with FEATURES=force-mirror if files are
not in the configured mirror.
Change-Id: I8484d5af8dff97b431398030b33c024ff1295ba0
Review URL: http://codereview.chromium.org/6677171
---
man/make.conf.5 | 4 ++++
pym/portage/const.py | 4 ++--
pym/portage/package/ebuild/fetch.py | 10 +++++-----
3 files changed, 11 insertions(+), 7 deletions(-)
diff --git a/man/make.conf.5 b/man/make.conf.5
index a86f257..cf8d217 100644
--- a/man/make.conf.5
+++ b/man/make.conf.5
@@ -304,6 +304,10 @@ enabled for more than a short period of time.
Modifies .la files to not include other .la files and some other
fixes (order of flags, duplicated entries, ...)
.TP
+.B force\-mirror
+Only fetch files from configured mirrors, ignoring \fBSRC_URI\fR,
+except when \fImirror\fR is in the \fBebuild\fR(5) \fBRESTRICT\fR variable.
+.TP
.B lmirror
When \fImirror\fR is enabled in \fBFEATURES\fR, fetch files even
when \fImirror\fR is also in the \fBebuild\fR(5) \fBRESTRICT\fR variable.
diff --git a/pym/portage/const.py b/pym/portage/const.py
index 89fdda1..b92149d 100644
--- a/pym/portage/const.py
+++ b/pym/portage/const.py
@@ -88,8 +88,8 @@ EBUILD_PHASES = ("pretend", "setup", "unpack", "prepare", "configure"
SUPPORTED_FEATURES = frozenset([
"assume-digests", "binpkg-logs", "buildpkg", "buildsyspkg", "candy",
"ccache", "chflags", "collision-protect", "compress-build-logs",
- "digest", "distcc", "distlocks",
- "fakeroot", "fail-clean", "fixpackages", "getbinpkg",
+ "digest", "distcc", "distlocks", "fakeroot",
+ "fail-clean", "fixpackages", "force-mirror", "getbinpkg",
"installsources", "keeptemp", "keepwork", "fixlafiles", "lmirror",
"metadata-transfer", "mirror", "multilib-strict", "news",
"noauto", "noclean", "nodoc", "noinfo", "noman", "nostrip",
diff --git a/pym/portage/package/ebuild/fetch.py b/pym/portage/package/ebuild/fetch.py
index c33375c..6e4c728 100644
--- a/pym/portage/package/ebuild/fetch.py
+++ b/pym/portage/package/ebuild/fetch.py
@@ -245,8 +245,8 @@ def fetch(myuris, mysettings, listonly=0, fetchonly=0,
userpriv = secpass >= 2 and "userpriv" in features
# 'nomirror' is bad/negative logic. You Restrict mirroring, not no-mirroring.
- if "mirror" in restrict or \
- "nomirror" in restrict:
+ restrict_mirror = "mirror" in restrict or "nomirror" in restrict
+ if restrict_mirror:
if ("mirror" in features) and ("lmirror" not in features):
# lmirror should allow you to bypass mirror restrictions.
# XXX: This is not a good thing, and is temporary at best.
@@ -344,8 +344,7 @@ def fetch(myuris, mysettings, listonly=0, fetchonly=0,
if "local" in custommirrors:
mymirrors += custommirrors["local"]
- if "nomirror" in restrict or \
- "mirror" in restrict:
+ if restrict_mirror:
# We don't add any mirrors.
pass
else:
@@ -374,6 +373,7 @@ def fetch(myuris, mysettings, listonly=0, fetchonly=0,
del mymirrors[x]
restrict_fetch = "fetch" in restrict
+ force_mirror = "force-mirror" in features and not restrict_mirror
custom_local_mirrors = custommirrors.get("local", [])
if restrict_fetch:
# With fetch restriction, a normal uri may only be fetched from
@@ -430,7 +430,7 @@ def fetch(myuris, mysettings, listonly=0, fetchonly=0,
writemsg(_("Invalid mirror definition in SRC_URI:\n"), noiselevel=-1)
writemsg(" %s\n" % (myuri), noiselevel=-1)
else:
- if restrict_fetch:
+ if restrict_fetch or force_mirror:
# Only fetch from specific mirrors is allowed.
continue
if "primaryuri" in restrict:
^ permalink raw reply related [flat|nested] 5+ messages in thread
* [gentoo-commits] proj/portage:master commit in: man/, pym/portage/package/ebuild/, pym/portage/
@ 2011-04-07 23:50 Zac Medico
0 siblings, 0 replies; 5+ messages in thread
From: Zac Medico @ 2011-04-07 23:50 UTC (permalink / raw
To: gentoo-commits
commit: b773f82f3ab84270d6541b84298013b6221ebcac
Author: David James <davidjames <AT> google <DOT> com>
AuthorDate: Thu Apr 7 23:49:58 2011 +0000
Commit: Zac Medico <zmedico <AT> gentoo <DOT> org>
CommitDate: Thu Apr 7 23:49:58 2011 +0000
URL: http://git.overlays.gentoo.org/gitweb/?p=proj/portage.git;a=commit;h=b773f82f
Add force-mirror FEATURE.
force-mirror: Only fetch files from configured mirrors, ignoring
SRC_URI, except when mirror is in the ebuild(5) RESTRICT variable.
BUG=chromium-os:13221
TEST=Test that ebuilds now fail with FEATURES=force-mirror if files are
not in the configured mirror.
Change-Id: I8484d5af8dff97b431398030b33c024ff1295ba0
Review URL: http://codereview.chromium.org/6677171
---
man/make.conf.5 | 4 ++++
pym/portage/const.py | 4 ++--
pym/portage/package/ebuild/fetch.py | 10 +++++-----
3 files changed, 11 insertions(+), 7 deletions(-)
diff --git a/man/make.conf.5 b/man/make.conf.5
index a86f257..cf8d217 100644
--- a/man/make.conf.5
+++ b/man/make.conf.5
@@ -304,6 +304,10 @@ enabled for more than a short period of time.
Modifies .la files to not include other .la files and some other
fixes (order of flags, duplicated entries, ...)
.TP
+.B force\-mirror
+Only fetch files from configured mirrors, ignoring \fBSRC_URI\fR,
+except when \fImirror\fR is in the \fBebuild\fR(5) \fBRESTRICT\fR variable.
+.TP
.B lmirror
When \fImirror\fR is enabled in \fBFEATURES\fR, fetch files even
when \fImirror\fR is also in the \fBebuild\fR(5) \fBRESTRICT\fR variable.
diff --git a/pym/portage/const.py b/pym/portage/const.py
index 89fdda1..b92149d 100644
--- a/pym/portage/const.py
+++ b/pym/portage/const.py
@@ -88,8 +88,8 @@ EBUILD_PHASES = ("pretend", "setup", "unpack", "prepare", "configure"
SUPPORTED_FEATURES = frozenset([
"assume-digests", "binpkg-logs", "buildpkg", "buildsyspkg", "candy",
"ccache", "chflags", "collision-protect", "compress-build-logs",
- "digest", "distcc", "distlocks",
- "fakeroot", "fail-clean", "fixpackages", "getbinpkg",
+ "digest", "distcc", "distlocks", "fakeroot",
+ "fail-clean", "fixpackages", "force-mirror", "getbinpkg",
"installsources", "keeptemp", "keepwork", "fixlafiles", "lmirror",
"metadata-transfer", "mirror", "multilib-strict", "news",
"noauto", "noclean", "nodoc", "noinfo", "noman", "nostrip",
diff --git a/pym/portage/package/ebuild/fetch.py b/pym/portage/package/ebuild/fetch.py
index c33375c..6e4c728 100644
--- a/pym/portage/package/ebuild/fetch.py
+++ b/pym/portage/package/ebuild/fetch.py
@@ -245,8 +245,8 @@ def fetch(myuris, mysettings, listonly=0, fetchonly=0,
userpriv = secpass >= 2 and "userpriv" in features
# 'nomirror' is bad/negative logic. You Restrict mirroring, not no-mirroring.
- if "mirror" in restrict or \
- "nomirror" in restrict:
+ restrict_mirror = "mirror" in restrict or "nomirror" in restrict
+ if restrict_mirror:
if ("mirror" in features) and ("lmirror" not in features):
# lmirror should allow you to bypass mirror restrictions.
# XXX: This is not a good thing, and is temporary at best.
@@ -344,8 +344,7 @@ def fetch(myuris, mysettings, listonly=0, fetchonly=0,
if "local" in custommirrors:
mymirrors += custommirrors["local"]
- if "nomirror" in restrict or \
- "mirror" in restrict:
+ if restrict_mirror:
# We don't add any mirrors.
pass
else:
@@ -374,6 +373,7 @@ def fetch(myuris, mysettings, listonly=0, fetchonly=0,
del mymirrors[x]
restrict_fetch = "fetch" in restrict
+ force_mirror = "force-mirror" in features and not restrict_mirror
custom_local_mirrors = custommirrors.get("local", [])
if restrict_fetch:
# With fetch restriction, a normal uri may only be fetched from
@@ -430,7 +430,7 @@ def fetch(myuris, mysettings, listonly=0, fetchonly=0,
writemsg(_("Invalid mirror definition in SRC_URI:\n"), noiselevel=-1)
writemsg(" %s\n" % (myuri), noiselevel=-1)
else:
- if restrict_fetch:
+ if restrict_fetch or force_mirror:
# Only fetch from specific mirrors is allowed.
continue
if "primaryuri" in restrict:
^ permalink raw reply related [flat|nested] 5+ messages in thread
* [gentoo-commits] proj/portage:master commit in: man/, pym/portage/package/ebuild/, pym/portage/
@ 2013-08-17 20:45 Zac Medico
0 siblings, 0 replies; 5+ messages in thread
From: Zac Medico @ 2013-08-17 20:45 UTC (permalink / raw
To: gentoo-commits
commit: 39db5201e087156ed46f6cac4dc9a69a2f3cc81c
Author: Michał Górny <mgorny <AT> gentoo <DOT> org>
AuthorDate: Sat Aug 17 10:28:05 2013 +0000
Commit: Zac Medico <zmedico <AT> gentoo <DOT> org>
CommitDate: Sat Aug 17 20:38:53 2013 +0000
URL: http://git.overlays.gentoo.org/gitweb/?p=proj/portage.git;a=commit;h=39db5201
Add FEATURES=network-sandbox support, bug #481450
This way, only privileged phases (pkg_* and src_unpack) have network
access during the ebuild run. All of the src_* phases are completely
detached from host's network interfaces.
---
man/make.conf.5 | 4 +++
pym/portage/const.py | 3 +-
pym/portage/package/ebuild/doebuild.py | 21 ++++++++++++-
pym/portage/process.py | 54 ++++++++++++++++++++++++++++++----
4 files changed, 75 insertions(+), 7 deletions(-)
diff --git a/man/make.conf.5 b/man/make.conf.5
index 63e2097..461172c 100644
--- a/man/make.conf.5
+++ b/man/make.conf.5
@@ -415,6 +415,10 @@ isn't a symlink to /usr/lib64. To find the bad packages, we have a
portage feature called \fImultilib\-strict\fR. It will prevent emerge
from putting 64bit libraries into anything other than (/usr)/lib64.
.TP
+.B network\-sandbox
+Isolate the ebuild phase functions from host network interfaces.
+Supported only on Linux. Requires network namespace support in kernel.
+.TP
.B news
Enable GLEP 42 news support. See
\fIhttp://www.gentoo.org/proj/en/glep/glep-0042.html\fR.
diff --git a/pym/portage/const.py b/pym/portage/const.py
index bd55cb1..cde0079 100644
--- a/pym/portage/const.py
+++ b/pym/portage/const.py
@@ -104,7 +104,8 @@ SUPPORTED_FEATURES = frozenset([
"fail-clean", "force-mirror", "force-prefix", "getbinpkg",
"installsources", "keeptemp", "keepwork", "fixlafiles", "lmirror",
"merge-sync",
- "metadata-transfer", "mirror", "multilib-strict", "news",
+ "metadata-transfer", "mirror", "multilib-strict",
+ "network-sandbox", "news",
"noauto", "noclean", "nodoc", "noinfo", "noman",
"nostrip", "notitles", "parallel-fetch", "parallel-install",
"prelink-checksums", "preserve-libs",
diff --git a/pym/portage/package/ebuild/doebuild.py b/pym/portage/package/ebuild/doebuild.py
index 1cf5dc6..a35e717 100644
--- a/pym/portage/package/ebuild/doebuild.py
+++ b/pym/portage/package/ebuild/doebuild.py
@@ -12,6 +12,7 @@ import io
from itertools import chain
import logging
import os as _os
+import platform
import pwd
import re
import signal
@@ -81,6 +82,15 @@ _unsandboxed_phases = frozenset([
"prerm", "setup"
])
+# phases in which networking access is allowed
+_networked_phases = frozenset([
+ # for VCS fetching
+ "unpack",
+ # for IPC
+ "setup", "pretend",
+ "preinst", "postinst", "prerm", "postrm",
+])
+
_phase_func_map = {
"config": "pkg_config",
"setup": "pkg_setup",
@@ -110,6 +120,8 @@ def _doebuild_spawn(phase, settings, actionmap=None, **kwargs):
if phase in _unsandboxed_phases:
kwargs['free'] = True
+ if phase in _networked_phases:
+ kwargs['networked'] = True
if phase == 'depend':
kwargs['droppriv'] = 'userpriv' in settings.features
@@ -1387,7 +1399,7 @@ def _validate_deps(mysettings, myroot, mydo, mydbapi):
# XXX This would be to replace getstatusoutput completely.
# XXX Issue: cannot block execution. Deadlock condition.
-def spawn(mystring, mysettings, debug=0, free=0, droppriv=0, sesandbox=0, fakeroot=0, **keywords):
+def spawn(mystring, mysettings, debug=0, free=0, droppriv=0, sesandbox=0, fakeroot=0, networked=0, **keywords):
"""
Spawn a subprocess with extra portage-specific options.
Optiosn include:
@@ -1417,6 +1429,8 @@ def spawn(mystring, mysettings, debug=0, free=0, droppriv=0, sesandbox=0, fakero
@type sesandbox: Boolean
@param fakeroot: Run this command with faked root privileges
@type fakeroot: Boolean
+ @param networked: Run this command with networking access enabled
+ @type networked: Boolean
@param keywords: Extra options encoded as a dict, to be passed to spawn
@type keywords: Dictionary
@rtype: Integer
@@ -1444,6 +1458,11 @@ def spawn(mystring, mysettings, debug=0, free=0, droppriv=0, sesandbox=0, fakero
break
features = mysettings.features
+
+ # Unshare network namespace to keep ebuilds sanitized
+ if not networked and uid == 0 and platform.system() == 'Linux' and "network-sandbox" in features:
+ keywords['unshare_net'] = True
+
# TODO: Enable fakeroot to be used together with droppriv. The
# fake ownership/permissions will have to be converted to real
# permissions in the merge phase.
diff --git a/pym/portage/process.py b/pym/portage/process.py
index 5f6a172..a7464c7 100644
--- a/pym/portage/process.py
+++ b/pym/portage/process.py
@@ -5,8 +5,11 @@
import atexit
import errno
+import fcntl
import platform
import signal
+import socket
+import struct
import sys
import traceback
import os as _os
@@ -21,6 +24,7 @@ portage.proxy.lazyimport.lazyimport(globals(),
from portage.const import BASH_BINARY, SANDBOX_BINARY, FAKEROOT_BINARY
from portage.exception import CommandNotFound
+from portage.util._ctypes import find_library, LoadLibrary, ctypes
try:
import resource
@@ -180,7 +184,7 @@ def cleanup():
def spawn(mycommand, env={}, opt_name=None, fd_pipes=None, returnpid=False,
uid=None, gid=None, groups=None, umask=None, logfile=None,
- path_lookup=True, pre_exec=None, close_fds=True):
+ path_lookup=True, pre_exec=None, close_fds=True, unshare_net=False):
"""
Spawns a given command.
@@ -213,7 +217,9 @@ def spawn(mycommand, env={}, opt_name=None, fd_pipes=None, returnpid=False,
@param close_fds: If True, then close all file descriptors except those
referenced by fd_pipes (default is True).
@type close_fds: Boolean
-
+ @param unshare_net: If True, networking will be unshared from the spawned process
+ @type unshare_net: Boolean
+
logfile requires stdout and stderr to be assigned to this process (ie not pointed
somewhere else.)
@@ -276,6 +282,12 @@ def spawn(mycommand, env={}, opt_name=None, fd_pipes=None, returnpid=False,
fd_pipes[1] = pw
fd_pipes[2] = pw
+ # This caches the libc library lookup in the current
+ # process, so that it's only done once rather than
+ # for each child process.
+ if unshare_net:
+ find_library("c")
+
parent_pid = os.getpid()
pid = None
try:
@@ -284,7 +296,8 @@ def spawn(mycommand, env={}, opt_name=None, fd_pipes=None, returnpid=False,
if pid == 0:
try:
_exec(binary, mycommand, opt_name, fd_pipes,
- env, gid, groups, uid, umask, pre_exec, close_fds)
+ env, gid, groups, uid, umask, pre_exec, close_fds,
+ unshare_net)
except SystemExit:
raise
except Exception as e:
@@ -354,7 +367,7 @@ def spawn(mycommand, env={}, opt_name=None, fd_pipes=None, returnpid=False,
return 0
def _exec(binary, mycommand, opt_name, fd_pipes, env, gid, groups, uid, umask,
- pre_exec, close_fds):
+ pre_exec, close_fds, unshare_net):
"""
Execute a given binary with options
@@ -379,10 +392,12 @@ def _exec(binary, mycommand, opt_name, fd_pipes, env, gid, groups, uid, umask,
@type umask: Integer
@param pre_exec: A function to be called with no arguments just prior to the exec call.
@type pre_exec: callable
+ @param unshare_net: If True, networking will be unshared from the spawned process
+ @type unshare_net: Boolean
@rtype: None
@return: Never returns (calls os.execve)
"""
-
+
# If the process we're creating hasn't been given a name
# assign it the name of the executable.
if not opt_name:
@@ -415,6 +430,35 @@ def _exec(binary, mycommand, opt_name, fd_pipes, env, gid, groups, uid, umask,
_setup_pipes(fd_pipes, close_fds=close_fds)
+ # Unshare network (while still uid==0)
+ if unshare_net:
+ filename = find_library("c")
+ if filename is not None:
+ libc = LoadLibrary(filename)
+ if libc is not None:
+ CLONE_NEWNET = 0x40000000
+ try:
+ if libc.unshare(CLONE_NEWNET) != 0:
+ writemsg("Unable to unshare network: %s\n" % (
+ errno.errorcode.get(ctypes.get_errno(), '?')),
+ noiselevel=-1)
+ else:
+ # 'up' the loopback
+ IFF_UP = 0x1
+ ifreq = struct.pack('16sh', b'lo', IFF_UP)
+ SIOCSIFFLAGS = 0x8914
+
+ sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM, 0)
+ try:
+ fcntl.ioctl(sock, SIOCSIFFLAGS, ifreq)
+ except IOError as e:
+ writemsg("Unable to enable loopback interface: %s\n" % (
+ errno.errorcode.get(e.errno, '?')),
+ noiselevel=-1)
+ except AttributeError:
+ # unshare() not supported by libc
+ pass
+
# Set requested process permissions.
if gid:
# Cast proxies to int, in case it matters.
^ permalink raw reply related [flat|nested] 5+ messages in thread
* [gentoo-commits] proj/portage:master commit in: man/, pym/portage/package/ebuild/, pym/portage/
@ 2013-08-18 23:33 Zac Medico
0 siblings, 0 replies; 5+ messages in thread
From: Zac Medico @ 2013-08-18 23:33 UTC (permalink / raw
To: gentoo-commits
commit: f0711200ce35920552962190c9a1f7b98d107070
Author: Michał Górny <mgorny <AT> gentoo <DOT> org>
AuthorDate: Sun Aug 18 23:22:59 2013 +0000
Commit: Zac Medico <zmedico <AT> gentoo <DOT> org>
CommitDate: Sun Aug 18 23:31:01 2013 +0000
URL: http://git.overlays.gentoo.org/gitweb/?p=proj/portage.git;a=commit;h=f0711200
Add FEATURES=ipc-sandbox to isolate IPC from host.
This way, only privileged phases (pkg_*) can use *nix IPC to communicate
with host applications. src_* use private IPC namespace.
---
man/make.conf.5 | 4 +++
pym/portage/const.py | 3 +-
pym/portage/package/ebuild/doebuild.py | 27 +++++++++++-----
pym/portage/process.py | 56 +++++++++++++++++++++-------------
4 files changed, 60 insertions(+), 30 deletions(-)
diff --git a/man/make.conf.5 b/man/make.conf.5
index 461172c..91817ae 100644
--- a/man/make.conf.5
+++ b/man/make.conf.5
@@ -385,6 +385,10 @@ would otherwise be useless with prefix configurations. This brings
compatibility with the prefix branch of portage, which also supports EPREFIX
for all EAPIs (for obvious reasons).
.TP
+.B ipc\-sandbox
+Isolate the ebuild phase functions from host IPC namespace. Supported
+only on Linux. Requires network namespace support in kernel.
+.TP
.B lmirror
When \fImirror\fR is enabled in \fBFEATURES\fR, fetch files even
when \fImirror\fR is also in the \fBebuild\fR(5) \fBRESTRICT\fR variable.
diff --git a/pym/portage/const.py b/pym/portage/const.py
index cde0079..88c199b 100644
--- a/pym/portage/const.py
+++ b/pym/portage/const.py
@@ -102,7 +102,8 @@ SUPPORTED_FEATURES = frozenset([
"digest", "distcc", "distcc-pump", "distlocks",
"downgrade-backup", "ebuild-locks", "fakeroot",
"fail-clean", "force-mirror", "force-prefix", "getbinpkg",
- "installsources", "keeptemp", "keepwork", "fixlafiles", "lmirror",
+ "installsources", "ipc-sandbox",
+ "keeptemp", "keepwork", "fixlafiles", "lmirror",
"merge-sync",
"metadata-transfer", "mirror", "multilib-strict",
"network-sandbox", "news",
diff --git a/pym/portage/package/ebuild/doebuild.py b/pym/portage/package/ebuild/doebuild.py
index a35e717..2d26d2c 100644
--- a/pym/portage/package/ebuild/doebuild.py
+++ b/pym/portage/package/ebuild/doebuild.py
@@ -82,14 +82,18 @@ _unsandboxed_phases = frozenset([
"prerm", "setup"
])
+# phases in which IPC with host is allowed
+_ipc_phases = frozenset([
+ "setup", "pretend",
+ "preinst", "postinst", "prerm", "postrm",
+])
+
# phases in which networking access is allowed
_networked_phases = frozenset([
# for VCS fetching
"unpack",
- # for IPC
- "setup", "pretend",
- "preinst", "postinst", "prerm", "postrm",
-])
+ # + for network-bound IPC
+] + list(_ipc_phases))
_phase_func_map = {
"config": "pkg_config",
@@ -120,6 +124,8 @@ def _doebuild_spawn(phase, settings, actionmap=None, **kwargs):
if phase in _unsandboxed_phases:
kwargs['free'] = True
+ if phase in _ipc_phases:
+ kwargs['ipc'] = True
if phase in _networked_phases:
kwargs['networked'] = True
@@ -1399,7 +1405,7 @@ def _validate_deps(mysettings, myroot, mydo, mydbapi):
# XXX This would be to replace getstatusoutput completely.
# XXX Issue: cannot block execution. Deadlock condition.
-def spawn(mystring, mysettings, debug=0, free=0, droppriv=0, sesandbox=0, fakeroot=0, networked=0, **keywords):
+def spawn(mystring, mysettings, debug=0, free=0, droppriv=0, sesandbox=0, fakeroot=0, networked=0, ipc=0, **keywords):
"""
Spawn a subprocess with extra portage-specific options.
Optiosn include:
@@ -1431,6 +1437,8 @@ def spawn(mystring, mysettings, debug=0, free=0, droppriv=0, sesandbox=0, fakero
@type fakeroot: Boolean
@param networked: Run this command with networking access enabled
@type networked: Boolean
+ @param ipc: Run this command with host IPC access enabled
+ @type ipc: Boolean
@param keywords: Extra options encoded as a dict, to be passed to spawn
@type keywords: Dictionary
@rtype: Integer
@@ -1459,9 +1467,12 @@ def spawn(mystring, mysettings, debug=0, free=0, droppriv=0, sesandbox=0, fakero
features = mysettings.features
- # Unshare network namespace to keep ebuilds sanitized
- if not networked and uid == 0 and platform.system() == 'Linux' and "network-sandbox" in features:
- keywords['unshare_net'] = True
+ # Use Linux namespaces if available
+ if uid == 0 and platform.system() == 'Linux':
+ if not networked and "network-sandbox" in features:
+ keywords['unshare_net'] = True
+ if not ipc and "ipc-sandbox" in features:
+ keywords['unshare_ipc'] = True
# TODO: Enable fakeroot to be used together with droppriv. The
# fake ownership/permissions will have to be converted to real
diff --git a/pym/portage/process.py b/pym/portage/process.py
index 6a60dec..22c6a88 100644
--- a/pym/portage/process.py
+++ b/pym/portage/process.py
@@ -184,7 +184,8 @@ def cleanup():
def spawn(mycommand, env={}, opt_name=None, fd_pipes=None, returnpid=False,
uid=None, gid=None, groups=None, umask=None, logfile=None,
- path_lookup=True, pre_exec=None, close_fds=True, unshare_net=False):
+ path_lookup=True, pre_exec=None, close_fds=True, unshare_net=False,
+ unshare_ipc=False):
"""
Spawns a given command.
@@ -219,6 +220,8 @@ def spawn(mycommand, env={}, opt_name=None, fd_pipes=None, returnpid=False,
@type close_fds: Boolean
@param unshare_net: If True, networking will be unshared from the spawned process
@type unshare_net: Boolean
+ @param unshare_ipc: If True, IPC will be unshared from the spawned process
+ @type unshare_ipc: Boolean
logfile requires stdout and stderr to be assigned to this process (ie not pointed
somewhere else.)
@@ -285,7 +288,7 @@ def spawn(mycommand, env={}, opt_name=None, fd_pipes=None, returnpid=False,
# This caches the libc library lookup in the current
# process, so that it's only done once rather than
# for each child process.
- if unshare_net:
+ if unshare_net or unshare_ipc:
find_library("c")
parent_pid = os.getpid()
@@ -297,7 +300,7 @@ def spawn(mycommand, env={}, opt_name=None, fd_pipes=None, returnpid=False,
try:
_exec(binary, mycommand, opt_name, fd_pipes,
env, gid, groups, uid, umask, pre_exec, close_fds,
- unshare_net)
+ unshare_net, unshare_ipc)
except SystemExit:
raise
except Exception as e:
@@ -367,7 +370,7 @@ def spawn(mycommand, env={}, opt_name=None, fd_pipes=None, returnpid=False,
return 0
def _exec(binary, mycommand, opt_name, fd_pipes, env, gid, groups, uid, umask,
- pre_exec, close_fds, unshare_net):
+ pre_exec, close_fds, unshare_net, unshare_ipc):
"""
Execute a given binary with options
@@ -394,6 +397,8 @@ def _exec(binary, mycommand, opt_name, fd_pipes, env, gid, groups, uid, umask,
@type pre_exec: callable
@param unshare_net: If True, networking will be unshared from the spawned process
@type unshare_net: Boolean
+ @param unshare_ipc: If True, IPC will be unshared from the spawned process
+ @type unshare_ipc: Boolean
@rtype: None
@return: Never returns (calls os.execve)
"""
@@ -430,32 +435,41 @@ def _exec(binary, mycommand, opt_name, fd_pipes, env, gid, groups, uid, umask,
_setup_pipes(fd_pipes, close_fds=close_fds)
- # Unshare network (while still uid==0)
- if unshare_net:
+ # Unshare (while still uid==0)
+ if unshare_net or unshare_ipc:
filename = find_library("c")
if filename is not None:
libc = LoadLibrary(filename)
if libc is not None:
+ CLONE_NEWIPC = 0x08000000
CLONE_NEWNET = 0x40000000
+
+ flags = 0
+ if unshare_net:
+ flags |= CLONE_NEWNET
+ if unshare_ipc:
+ flags |= CLONE_NEWIPC
+
try:
- if libc.unshare(CLONE_NEWNET) != 0:
- writemsg("Unable to unshare network: %s\n" % (
+ if libc.unshare(flags) != 0:
+ writemsg("Unable to unshare: %s\n" % (
errno.errorcode.get(ctypes.get_errno(), '?')),
noiselevel=-1)
else:
- # 'up' the loopback
- IFF_UP = 0x1
- ifreq = struct.pack('16sh', b'lo', IFF_UP)
- SIOCSIFFLAGS = 0x8914
-
- sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM, 0)
- try:
- fcntl.ioctl(sock, SIOCSIFFLAGS, ifreq)
- except IOError as e:
- writemsg("Unable to enable loopback interface: %s\n" % (
- errno.errorcode.get(e.errno, '?')),
- noiselevel=-1)
- sock.close()
+ if unshare_net:
+ # 'up' the loopback
+ IFF_UP = 0x1
+ ifreq = struct.pack('16sh', b'lo', IFF_UP)
+ SIOCSIFFLAGS = 0x8914
+
+ sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM, 0)
+ try:
+ fcntl.ioctl(sock, SIOCSIFFLAGS, ifreq)
+ except IOError as e:
+ writemsg("Unable to enable loopback interface: %s\n" % (
+ errno.errorcode.get(e.errno, '?')),
+ noiselevel=-1)
+ sock.close()
except AttributeError:
# unshare() not supported by libc
pass
^ permalink raw reply related [flat|nested] 5+ messages in thread
* [gentoo-commits] proj/portage:master commit in: man/, pym/portage/package/ebuild/, pym/portage/
@ 2015-05-06 17:26 Brian Dolbec
0 siblings, 0 replies; 5+ messages in thread
From: Brian Dolbec @ 2015-05-06 17:26 UTC (permalink / raw
To: gentoo-commits
commit: 1f94508e9adeffd7170cb23852ae40fc1f8b6c98
Author: Nikoli <nikoli <AT> gmx <DOT> us>
AuthorDate: Wed May 6 14:02:28 2015 +0000
Commit: Brian Dolbec <dolsen <AT> gentoo <DOT> org>
CommitDate: Wed May 6 17:26:13 2015 +0000
URL: https://gitweb.gentoo.org/proj/portage.git/commit/?id=1f94508e
Disable SOCKSv5-over-UNIX-socket proxy by default, bug #548710
man/make.conf.5 | 4 ++++
pym/portage/const.py | 1 +
pym/portage/package/ebuild/doebuild.py | 3 ++-
3 files changed, 7 insertions(+), 1 deletion(-)
diff --git a/man/make.conf.5 b/man/make.conf.5
index 1b71b97..298eb80 100644
--- a/man/make.conf.5
+++ b/man/make.conf.5
@@ -463,6 +463,10 @@ from putting 64bit libraries into anything other than (/usr)/lib64.
.B network\-sandbox
Isolate the ebuild phase functions from host network interfaces.
Supported only on Linux. Requires network namespace support in kernel.
+.TP
+.B network\-sandbox\-proxy
+Enable escaping network-sandbox through SOCKSv5 proxy. Enabling distcc
+feature also enables the proxy.
If asyncio Python module is available (requires Python 3.3, built-in
since Python 3.4) Portage will additionally spawn an isolated SOCKSv5
diff --git a/pym/portage/const.py b/pym/portage/const.py
index 6c1201d..617cd96 100644
--- a/pym/portage/const.py
+++ b/pym/portage/const.py
@@ -158,6 +158,7 @@ SUPPORTED_FEATURES = frozenset([
"mirror",
"multilib-strict",
"network-sandbox",
+ "network-sandbox-proxy",
"news",
"noauto",
"noclean",
diff --git a/pym/portage/package/ebuild/doebuild.py b/pym/portage/package/ebuild/doebuild.py
index 4d926c7..5e4d7b1 100644
--- a/pym/portage/package/ebuild/doebuild.py
+++ b/pym/portage/package/ebuild/doebuild.py
@@ -1505,7 +1505,8 @@ def spawn(mystring, mysettings, debug=False, free=False, droppriv=False,
keywords['unshare_net'] = not networked
keywords['unshare_ipc'] = not ipc
- if not networked and mysettings.get("EBUILD_PHASE") != "nofetch":
+ if not networked and mysettings.get("EBUILD_PHASE") != "nofetch" and \
+ ("network-sandbox-proxy" in features or "distcc" in features):
# Provide a SOCKS5-over-UNIX-socket proxy to escape sandbox
# Don't do this for pkg_nofetch, since the spawn_nofetch
# function creates a private PORTAGE_TMPDIR.
^ permalink raw reply related [flat|nested] 5+ messages in thread
end of thread, other threads:[~2015-05-06 17:26 UTC | newest]
Thread overview: 5+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2011-04-05 22:23 [gentoo-commits] proj/portage:master commit in: man/, pym/portage/package/ebuild/, pym/portage/ Zac Medico
-- strict thread matches above, loose matches on Subject: below --
2011-04-07 23:50 Zac Medico
2013-08-17 20:45 Zac Medico
2013-08-18 23:33 Zac Medico
2015-05-06 17:26 Brian Dolbec
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox