Make utils_daemon and volumes cross-platform compileable.

Signed-off-by: Rik Nijessen <riknijessen@gmail.com>
This commit is contained in:
Rik Nijessen 2015-03-11 16:42:49 +01:00
parent 1a5e46ce89
commit 1ec2eac50d
10 changed files with 64 additions and 25 deletions

View File

@ -8,12 +8,12 @@ import (
"path/filepath" "path/filepath"
"sort" "sort"
"strings" "strings"
"syscall"
log "github.com/Sirupsen/logrus" log "github.com/Sirupsen/logrus"
"github.com/docker/docker/daemon/execdriver" "github.com/docker/docker/daemon/execdriver"
"github.com/docker/docker/pkg/chrootarchive" "github.com/docker/docker/pkg/chrootarchive"
"github.com/docker/docker/pkg/symlink" "github.com/docker/docker/pkg/symlink"
"github.com/docker/docker/pkg/system"
"github.com/docker/docker/volumes" "github.com/docker/docker/volumes"
) )
@ -385,15 +385,14 @@ func copyExistingContents(source, destination string) error {
// copyOwnership copies the permissions and uid:gid of the source file // copyOwnership copies the permissions and uid:gid of the source file
// into the destination file // into the destination file
func copyOwnership(source, destination string) error { func copyOwnership(source, destination string) error {
var stat syscall.Stat_t stat, err := system.Stat(source)
if err != nil {
if err := syscall.Stat(source, &stat); err != nil {
return err return err
} }
if err := os.Chown(destination, int(stat.Uid), int(stat.Gid)); err != nil { if err := os.Chown(destination, int(stat.Uid()), int(stat.Gid())); err != nil {
return err return err
} }
return os.Chmod(destination, os.FileMode(stat.Mode)) return os.Chmod(destination, os.FileMode(stat.Mode()))
} }

View File

@ -143,7 +143,7 @@ func Changes(layers []string, rw string) ([]Change, error) {
type FileInfo struct { type FileInfo struct {
parent *FileInfo parent *FileInfo
name string name string
stat *system.Stat stat *system.Stat_t
children map[string]*FileInfo children map[string]*FileInfo
capability []byte capability []byte
added bool added bool

View File

@ -6,7 +6,7 @@ import (
"syscall" "syscall"
) )
func Lstat(path string) (*Stat, error) { func Lstat(path string) (*Stat_t, error) {
s := &syscall.Stat_t{} s := &syscall.Stat_t{}
err := syscall.Lstat(path, s) err := syscall.Lstat(path, s)
if err != nil { if err != nil {

View File

@ -2,7 +2,7 @@
package system package system
func Lstat(path string) (*Stat, error) { func Lstat(path string) (*Stat_t, error) {
// should not be called on cli code path // should not be called on cli code path
return nil, ErrNotSupportedPlatform return nil, ErrNotSupportedPlatform
} }

View File

@ -4,7 +4,7 @@ import (
"syscall" "syscall"
) )
type Stat struct { type Stat_t struct {
mode uint32 mode uint32
uid uint32 uid uint32
gid uint32 gid uint32
@ -13,30 +13,30 @@ type Stat struct {
mtim syscall.Timespec mtim syscall.Timespec
} }
func (s Stat) Mode() uint32 { func (s Stat_t) Mode() uint32 {
return s.mode return s.mode
} }
func (s Stat) Uid() uint32 { func (s Stat_t) Uid() uint32 {
return s.uid return s.uid
} }
func (s Stat) Gid() uint32 { func (s Stat_t) Gid() uint32 {
return s.gid return s.gid
} }
func (s Stat) Rdev() uint64 { func (s Stat_t) Rdev() uint64 {
return s.rdev return s.rdev
} }
func (s Stat) Size() int64 { func (s Stat_t) Size() int64 {
return s.size return s.size
} }
func (s Stat) Mtim() syscall.Timespec { func (s Stat_t) Mtim() syscall.Timespec {
return s.mtim return s.mtim
} }
func (s Stat) GetLastModification() syscall.Timespec { func (s Stat_t) GetLastModification() syscall.Timespec {
return s.Mtim() return s.Mtim()
} }

View File

@ -4,11 +4,20 @@ import (
"syscall" "syscall"
) )
func fromStatT(s *syscall.Stat_t) (*Stat, error) { func fromStatT(s *syscall.Stat_t) (*Stat_t, error) {
return &Stat{size: s.Size, return &Stat_t{size: s.Size,
mode: s.Mode, mode: s.Mode,
uid: s.Uid, uid: s.Uid,
gid: s.Gid, gid: s.Gid,
rdev: s.Rdev, rdev: s.Rdev,
mtim: s.Mtim}, nil mtim: s.Mtim}, nil
} }
func Stat(path string) (*Stat_t, error) {
s := &syscall.Stat_t{}
err := syscall.Stat(path, s)
if err != nil {
return nil, err
}
return fromStatT(s)
}

View File

@ -6,8 +6,8 @@ import (
"syscall" "syscall"
) )
func fromStatT(s *syscall.Stat_t) (*Stat, error) { func fromStatT(s *syscall.Stat_t) (*Stat_t, error) {
return &Stat{size: s.Size, return &Stat_t{size: s.Size,
mode: uint32(s.Mode), mode: uint32(s.Mode),
uid: s.Uid, uid: s.Uid,
gid: s.Gid, gid: s.Gid,

View File

@ -7,6 +7,11 @@ import (
"syscall" "syscall"
) )
func fromStatT(s *syscall.Win32FileAttributeData) (*Stat, error) { func fromStatT(s *syscall.Win32FileAttributeData) (*Stat_t, error) {
return nil, errors.New("fromStatT should not be called on windows path") return nil, errors.New("fromStatT should not be called on windows path")
} }
func Stat(path string) (*Stat_t, error) {
// should not be called on cli code path
return nil, ErrNotSupportedPlatform
}

View File

@ -3,14 +3,14 @@
package utils package utils
import ( import (
"github.com/docker/docker/pkg/system"
"os" "os"
"syscall"
) )
// IsFileOwner checks whether the current user is the owner of the given file. // IsFileOwner checks whether the current user is the owner of the given file.
func IsFileOwner(f string) bool { func IsFileOwner(f string) bool {
if fileInfo, err := os.Stat(f); err == nil && fileInfo != nil { if fileInfo, err := system.Stat(f); err == nil && fileInfo != nil {
if stat, ok := fileInfo.Sys().(*syscall.Stat_t); ok && int(stat.Uid) == os.Getuid() { if int(fileInfo.Uid()) == os.Getuid() {
return true return true
} }
} }

View File

@ -0,0 +1,26 @@
package utils
import (
"os"
"path"
"testing"
)
func TestIsFileOwner(t *testing.T) {
var err error
var file *os.File
if file, err = os.Create(path.Join(os.TempDir(), "testIsFileOwner")); err != nil {
t.Fatalf("failed to create file: %s", err)
}
file.Close()
if ok := IsFileOwner(path.Join(os.TempDir(), "testIsFileOwner")); !ok {
t.Fatalf("User should be owner of file")
}
if err = os.Remove(path.Join(os.TempDir(), "testIsFileOwner")); err != nil {
t.Fatalf("failed to remove file: %s", err)
}
}