From patchwork Fri Nov 17 14:55:04 2017 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Florian Weimer X-Patchwork-Id: 839025 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=pass (mailfrom) smtp.mailfrom=sourceware.org (client-ip=209.132.180.131; helo=sourceware.org; envelope-from=libc-alpha-return-87223-incoming=patchwork.ozlabs.org@sourceware.org; receiver=) Authentication-Results: ozlabs.org; dkim=pass (1024-bit key; secure) header.d=sourceware.org header.i=@sourceware.org header.b="H9I+fKEE"; dkim-atps=neutral Received: from sourceware.org (server1.sourceware.org [209.132.180.131]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id 3ydh491l41z9s71 for ; Sat, 18 Nov 2017 01:55:20 +1100 (AEDT) DomainKey-Signature: a=rsa-sha1; c=nofws; d=sourceware.org; h=list-id :list-unsubscribe:list-subscribe:list-archive:list-post :list-help:sender:date:to:subject:mime-version:content-type :content-transfer-encoding:message-id:from; q=dns; s=default; b= qWLGsG5XUlrq/6/A20VgUIsHCPRn4lsk2cKL14EQlm575EEd5+FhpfbAK4RyeyQr sPzojQtALTbwOAwlFz+TMLUvklfBmwX+caY+jrZd/+cQsQTerat4sTRgXvoG8V5v TCeGPdVX4lByTzWF652fUPiujzf/B8S2Dr77nH4NAXY= DKIM-Signature: v=1; a=rsa-sha1; c=relaxed; d=sourceware.org; h=list-id :list-unsubscribe:list-subscribe:list-archive:list-post :list-help:sender:date:to:subject:mime-version:content-type :content-transfer-encoding:message-id:from; s=default; bh=Y2cvOD JttMKU/w7scrGgySfnz7I=; b=H9I+fKEEa6VTknATl3oQn7aoECWmehxUgltI3l q/NutQUvApSOsRcsaG6ownEQ1l6JbSXiVdj9UCJ7CIkAahk6x1RQgGk9TJfLw8cb jGcwTnQwInl1XZRHW+9yHzEV4L+FIWNiEnnPxnYQFLfxzN0xdJ6y10DrZ4xtbEtB 9NJ+E= Received: (qmail 115829 invoked by alias); 17 Nov 2017 14:55:13 -0000 Mailing-List: contact libc-alpha-help@sourceware.org; run by ezmlm Precedence: bulk List-Id: List-Unsubscribe: List-Subscribe: List-Archive: List-Post: List-Help: , Sender: libc-alpha-owner@sourceware.org Delivered-To: mailing list libc-alpha@sourceware.org Received: (qmail 115817 invoked by uid 89); 17 Nov 2017 14:55:13 -0000 Authentication-Results: sourceware.org; auth=none X-Virus-Found: No X-Spam-SWARE-Status: No, score=-26.7 required=5.0 tests=BAYES_00, GIT_PATCH_0, GIT_PATCH_1, GIT_PATCH_2, GIT_PATCH_3, KB_WAM_FROM_NAME_SINGLEWORD, RP_MATCHES_RCVD, SPF_HELO_PASS autolearn=ham version=3.3.2 spammy=sic, our X-HELO: mx1.redhat.com Date: Fri, 17 Nov 2017 15:55:04 +0100 To: libc-alpha@sourceware.org Subject: [PATCH] support_become_root: Enable file creation in user namespaces User-Agent: Heirloom mailx 12.5 7/5/10 MIME-Version: 1.0 Message-Id: <20171117145504.D28A3446EB324@oldenburg.str.redhat.com> From: fweimer@redhat.com (Florian Weimer) Without UID/GID maps, file creation will file with EOVERFLOW. This patch is based on DJ Delorie's work on container testing. 2017-11-17 Florian Weimer support_become_root: Enable file creation in namespaces. * support/support_become_root.c (setup_mapping): New function. (support_become_root): Call it. Reviewed-by: Jonathan Nieder diff --git a/support/support_become_root.c b/support/support_become_root.c index 3fa0bd4ac0..5086570251 100644 --- a/support/support_become_root.c +++ b/support/support_become_root.c @@ -18,18 +18,69 @@ #include +#include #include #include +#include +#include +#include #include +#ifdef CLONE_NEWUSER +/* The necessary steps to allow file creation in user namespaces. */ +static void +setup_uid_gid_mapping (uid_t original_uid, gid_t original_gid) +{ + int fd = open64 ("/proc/self/uid_map", O_WRONLY); + if (fd < 0) + { + printf ("warning: could not open /proc/self/uid_map: %m\n" + "warning: file creation may not be possible\n"); + return; + } + + /* We map our original UID to the same UID in the container so we + own our own files normally. Without that, file creation could + fail with EOVERFLOW (sic!). */ + char buf[100]; + int ret = snprintf (buf, sizeof (buf), "%llu %llu 1\n", + (unsigned long long) original_uid, + (unsigned long long) original_uid); + TEST_VERIFY_EXIT (ret < sizeof (buf)); + xwrite (fd, buf, ret); + xclose (fd); + + /* Disable setgroups before mapping groups, otherwise that would + fail with EPERM. */ + fd = xopen ("/proc/self/setgroups", O_WRONLY, 0); + xwrite (fd, "deny\n", strlen ("deny\n")); + xclose (fd); + + /* Now map our own GID, like we did for the user ID. */ + fd = xopen ("/proc/self/gid_map", O_WRONLY, 0); + ret = snprintf (buf, sizeof (buf), "%llu %llu 1\n", + (unsigned long long) original_gid, + (unsigned long long) original_gid); + TEST_VERIFY_EXIT (ret < sizeof (buf)); + xwrite (fd, buf, ret); + xclose (fd); +} +#endif /* CLONE_NEWUSER */ + bool support_become_root (void) { #ifdef CLONE_NEWUSER + uid_t original_uid = getuid (); + gid_t original_gid = getgid (); + if (unshare (CLONE_NEWUSER | CLONE_NEWNS) == 0) - /* Even if we do not have UID zero, we have extended privileges at - this point. */ - return true; + { + setup_uid_gid_mapping (original_uid, original_gid); + /* Even if we do not have UID zero, we have extended privileges at + this point. */ + return true; + } #endif if (setuid (0) != 0) {