|
@@ -12,7 +12,6 @@ import (
|
|
"path"
|
|
"path"
|
|
"path/filepath"
|
|
"path/filepath"
|
|
"runtime"
|
|
"runtime"
|
|
- "strconv"
|
|
|
|
"strings"
|
|
"strings"
|
|
|
|
|
|
"github.com/docker/docker/api/types"
|
|
"github.com/docker/docker/api/types"
|
|
@@ -24,10 +23,8 @@ import (
|
|
"github.com/docker/docker/pkg/containerfs"
|
|
"github.com/docker/docker/pkg/containerfs"
|
|
"github.com/docker/docker/pkg/idtools"
|
|
"github.com/docker/docker/pkg/idtools"
|
|
"github.com/docker/docker/pkg/stringid"
|
|
"github.com/docker/docker/pkg/stringid"
|
|
- "github.com/docker/docker/pkg/symlink"
|
|
|
|
"github.com/docker/docker/pkg/system"
|
|
"github.com/docker/docker/pkg/system"
|
|
"github.com/docker/go-connections/nat"
|
|
"github.com/docker/go-connections/nat"
|
|
- lcUser "github.com/opencontainers/runc/libcontainer/user"
|
|
|
|
"github.com/pkg/errors"
|
|
"github.com/pkg/errors"
|
|
)
|
|
)
|
|
|
|
|
|
@@ -216,82 +213,6 @@ func (b *Builder) performCopy(state *dispatchState, inst copyInstruction) error
|
|
return b.exportImage(state, imageMount, runConfigWithCommentCmd)
|
|
return b.exportImage(state, imageMount, runConfigWithCommentCmd)
|
|
}
|
|
}
|
|
|
|
|
|
-func parseChownFlag(chown, ctrRootPath string, idMappings *idtools.IDMappings) (idtools.IDPair, error) {
|
|
|
|
- var userStr, grpStr string
|
|
|
|
- parts := strings.Split(chown, ":")
|
|
|
|
- if len(parts) > 2 {
|
|
|
|
- return idtools.IDPair{}, errors.New("invalid chown string format: " + chown)
|
|
|
|
- }
|
|
|
|
- if len(parts) == 1 {
|
|
|
|
- // if no group specified, use the user spec as group as well
|
|
|
|
- userStr, grpStr = parts[0], parts[0]
|
|
|
|
- } else {
|
|
|
|
- userStr, grpStr = parts[0], parts[1]
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- passwdPath, err := symlink.FollowSymlinkInScope(filepath.Join(ctrRootPath, "etc", "passwd"), ctrRootPath)
|
|
|
|
- if err != nil {
|
|
|
|
- return idtools.IDPair{}, errors.Wrapf(err, "can't resolve /etc/passwd path in container rootfs")
|
|
|
|
- }
|
|
|
|
- groupPath, err := symlink.FollowSymlinkInScope(filepath.Join(ctrRootPath, "etc", "group"), ctrRootPath)
|
|
|
|
- if err != nil {
|
|
|
|
- return idtools.IDPair{}, errors.Wrapf(err, "can't resolve /etc/group path in container rootfs")
|
|
|
|
- }
|
|
|
|
- uid, err := lookupUser(userStr, passwdPath)
|
|
|
|
- if err != nil {
|
|
|
|
- return idtools.IDPair{}, errors.Wrapf(err, "can't find uid for user "+userStr)
|
|
|
|
- }
|
|
|
|
- gid, err := lookupGroup(grpStr, groupPath)
|
|
|
|
- if err != nil {
|
|
|
|
- return idtools.IDPair{}, errors.Wrapf(err, "can't find gid for group "+grpStr)
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- // convert as necessary because of user namespaces
|
|
|
|
- chownPair, err := idMappings.ToHost(idtools.IDPair{UID: uid, GID: gid})
|
|
|
|
- if err != nil {
|
|
|
|
- return idtools.IDPair{}, errors.Wrapf(err, "unable to convert uid/gid to host mapping")
|
|
|
|
- }
|
|
|
|
- return chownPair, nil
|
|
|
|
-}
|
|
|
|
-
|
|
|
|
-func lookupUser(userStr, filepath string) (int, error) {
|
|
|
|
- // if the string is actually a uid integer, parse to int and return
|
|
|
|
- // as we don't need to translate with the help of files
|
|
|
|
- uid, err := strconv.Atoi(userStr)
|
|
|
|
- if err == nil {
|
|
|
|
- return uid, nil
|
|
|
|
- }
|
|
|
|
- users, err := lcUser.ParsePasswdFileFilter(filepath, func(u lcUser.User) bool {
|
|
|
|
- return u.Name == userStr
|
|
|
|
- })
|
|
|
|
- if err != nil {
|
|
|
|
- return 0, err
|
|
|
|
- }
|
|
|
|
- if len(users) == 0 {
|
|
|
|
- return 0, errors.New("no such user: " + userStr)
|
|
|
|
- }
|
|
|
|
- return users[0].Uid, nil
|
|
|
|
-}
|
|
|
|
-
|
|
|
|
-func lookupGroup(groupStr, filepath string) (int, error) {
|
|
|
|
- // if the string is actually a gid integer, parse to int and return
|
|
|
|
- // as we don't need to translate with the help of files
|
|
|
|
- gid, err := strconv.Atoi(groupStr)
|
|
|
|
- if err == nil {
|
|
|
|
- return gid, nil
|
|
|
|
- }
|
|
|
|
- groups, err := lcUser.ParseGroupFileFilter(filepath, func(g lcUser.Group) bool {
|
|
|
|
- return g.Name == groupStr
|
|
|
|
- })
|
|
|
|
- if err != nil {
|
|
|
|
- return 0, err
|
|
|
|
- }
|
|
|
|
- if len(groups) == 0 {
|
|
|
|
- return 0, errors.New("no such group: " + groupStr)
|
|
|
|
- }
|
|
|
|
- return groups[0].Gid, nil
|
|
|
|
-}
|
|
|
|
-
|
|
|
|
func createDestInfo(workingDir string, inst copyInstruction, imageMount *imageMount, platform string) (copyInfo, error) {
|
|
func createDestInfo(workingDir string, inst copyInstruction, imageMount *imageMount, platform string) (copyInfo, error) {
|
|
// Twiddle the destination when it's a relative path - meaning, make it
|
|
// Twiddle the destination when it's a relative path - meaning, make it
|
|
// relative to the WORKINGDIR
|
|
// relative to the WORKINGDIR
|