[lxc-devel] [lxd/master] shared/idmap: Fix handling of hardlinks

stgraber on Github lxc-bot at linuxcontainers.org
Mon Nov 20 05:20:47 UTC 2017


A non-text attachment was scrubbed...
Name: not available
Type: text/x-mailbox
Size: 354 bytes
Desc: not available
URL: <http://lists.linuxcontainers.org/pipermail/lxc-devel/attachments/20171120/141ec65d/attachment.bin>
-------------- next part --------------
From 4887b70b692f5b15a728b3a6e80d1d9319152e54 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?St=C3=A9phane=20Graber?= <stgraber at ubuntu.com>
Date: Mon, 20 Nov 2017 00:20:22 -0500
Subject: [PATCH] shared/idmap: Fix handling of hardlinks
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Signed-off-by: Stéphane Graber <stgraber at ubuntu.com>
---
 shared/idmap/idmapset_linux.go | 18 +++++++++++++++---
 1 file changed, 15 insertions(+), 3 deletions(-)

diff --git a/shared/idmap/idmapset_linux.go b/shared/idmap/idmapset_linux.go
index 3b68d0872..a85a74714 100644
--- a/shared/idmap/idmapset_linux.go
+++ b/shared/idmap/idmapset_linux.go
@@ -477,16 +477,28 @@ func (set *IdmapSet) doUidshiftIntoContainer(dir string, testmode bool, how stri
 	dir = filepath.Join(tmp, filepath.Base(dir))
 	dir = strings.TrimRight(dir, "/")
 
+	hardLinks := []uint64{}
 	convert := func(path string, fi os.FileInfo, err error) (e error) {
 		if err != nil {
 			return err
 		}
 
-		intUid, intGid, _, _, _, _, err := shared.GetFileStat(path)
+		intUid, intGid, _, _, inode, nlink, err := shared.GetFileStat(path)
 		if err != nil {
 			return err
 		}
 
+		if nlink >= 2 {
+			for _, linkInode := range hardLinks {
+				// File was already shifted through hardlink
+				if linkInode == inode {
+					return nil
+				}
+			}
+
+			hardLinks = append(hardLinks, inode)
+		}
+
 		uid := int64(intUid)
 		gid := int64(intGid)
 
@@ -505,8 +517,8 @@ func (set *IdmapSet) doUidshiftIntoContainer(dir string, testmode bool, how stri
 			if err != nil {
 				return err
 			}
-			err = ShiftACL(
-				path, func(uid int64, gid int64) (int64, int64) { return set.doShiftIntoNs(uid, gid, how) })
+
+			err = ShiftACL(path, func(uid int64, gid int64) (int64, int64) { return set.doShiftIntoNs(uid, gid, how) })
 			if err != nil {
 				return err
 			}


More information about the lxc-devel mailing list