pkg/ns: introduce error types indicate NS verification
This commit is contained in:
parent
131ecc4055
commit
35f3a090b2
38
pkg/ns/ns.go
38
pkg/ns/ns.go
@ -81,11 +81,23 @@ const (
|
|||||||
PROCFS_MAGIC = 0x9fa0
|
PROCFS_MAGIC = 0x9fa0
|
||||||
)
|
)
|
||||||
|
|
||||||
func IsNS(nspath string) (isNS bool, msg string, err error) {
|
type NSPathNotExistErr struct{ msg string }
|
||||||
|
|
||||||
|
func (e NSPathNotExistErr) Error() string { return e.msg }
|
||||||
|
|
||||||
|
type NSPathNotNSErr struct{ msg string }
|
||||||
|
|
||||||
|
func (e NSPathNotNSErr) Error() string { return e.msg }
|
||||||
|
|
||||||
|
func IsNSorErr(nspath string) error {
|
||||||
stat := syscall.Statfs_t{}
|
stat := syscall.Statfs_t{}
|
||||||
if err = syscall.Statfs(nspath, &stat); err != nil {
|
if err := syscall.Statfs(nspath, &stat); err != nil {
|
||||||
err = fmt.Errorf("failed to Statfs %s: %v", nspath, err)
|
if os.IsNotExist(err) {
|
||||||
return
|
err = NSPathNotExistErr{msg: fmt.Sprintf("failed to Statfs %q: %v", nspath, err)}
|
||||||
|
} else {
|
||||||
|
err = fmt.Errorf("failed to Statfs %q: %v", nspath, err)
|
||||||
|
}
|
||||||
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
switch stat.Type {
|
switch stat.Type {
|
||||||
@ -95,33 +107,29 @@ func IsNS(nspath string) (isNS bool, msg string, err error) {
|
|||||||
validPathContent := "ns/"
|
validPathContent := "ns/"
|
||||||
validName := strings.Contains(nspath, validPathContent)
|
validName := strings.Contains(nspath, validPathContent)
|
||||||
if !validName {
|
if !validName {
|
||||||
msg = fmt.Sprintf("path doesn't contain %q", validPathContent)
|
return NSPathNotNSErr{msg: fmt.Sprintf("path %q doesn't contain %q", nspath, validPathContent)}
|
||||||
return
|
|
||||||
}
|
}
|
||||||
isNS = true
|
|
||||||
|
return nil
|
||||||
case NSFS_MAGIC:
|
case NSFS_MAGIC:
|
||||||
// Kernel >= 3.19
|
// Kernel >= 3.19
|
||||||
|
|
||||||
isNS = true
|
return nil
|
||||||
default:
|
default:
|
||||||
msg = fmt.Sprintf("unknown FS magic: %x", stat.Type)
|
return NSPathNotNSErr{msg: fmt.Sprintf("unknown FS magic on %q: %x", nspath, stat.Type)}
|
||||||
}
|
}
|
||||||
return
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Returns an object representing the namespace referred to by @path
|
// Returns an object representing the namespace referred to by @path
|
||||||
func GetNS(nspath string) (NetNS, error) {
|
func GetNS(nspath string) (NetNS, error) {
|
||||||
isNS, msg, err := IsNS(nspath)
|
err := IsNSorErr(nspath)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
if !isNS {
|
|
||||||
return nil, fmt.Errorf("no network namespace detected on %s: %s", nspath, msg)
|
|
||||||
}
|
|
||||||
|
|
||||||
fd, err := os.Open(nspath)
|
fd, err := os.Open(nspath)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, fmt.Errorf("Failed to open %v: %v", nspath, err)
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return &netNS{file: fd}, nil
|
return &netNS{file: fd}, nil
|
||||||
|
@ -181,8 +181,8 @@ var _ = Describe("Linux namespace operations", func() {
|
|||||||
|
|
||||||
_, err = ns.GetNS(nspath)
|
_, err = ns.GetNS(nspath)
|
||||||
Expect(err).To(HaveOccurred())
|
Expect(err).To(HaveOccurred())
|
||||||
errString := fmt.Sprintf("%v", err)
|
Expect(err).To(BeAssignableToTypeOf(ns.NSPathNotNSErr{}))
|
||||||
Expect(errString).To(HavePrefix("no network namespace detected on %s", nspath))
|
Expect(err).NotTo(BeAssignableToTypeOf(ns.NSPathNotExistErr{}))
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
|
||||||
@ -214,13 +214,11 @@ var _ = Describe("Linux namespace operations", func() {
|
|||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
|
||||||
Describe("IsNS", func() {
|
Describe("IsNSorErr", func() {
|
||||||
It("should detect a namespace", func() {
|
It("should detect a namespace", func() {
|
||||||
createdNetNS, err := ns.NewNS()
|
createdNetNS, err := ns.NewNS()
|
||||||
isNSFS, msg, err := ns.IsNS(createdNetNS.Path())
|
err = ns.IsNSorErr(createdNetNS.Path())
|
||||||
Expect(err).NotTo(HaveOccurred())
|
Expect(err).NotTo(HaveOccurred())
|
||||||
Expect(msg).To(Equal(""))
|
|
||||||
Expect(isNSFS).To(Equal(true))
|
|
||||||
})
|
})
|
||||||
|
|
||||||
It("should refuse other paths", func() {
|
It("should refuse other paths", func() {
|
||||||
@ -231,9 +229,17 @@ var _ = Describe("Linux namespace operations", func() {
|
|||||||
nspath := tempFile.Name()
|
nspath := tempFile.Name()
|
||||||
defer os.Remove(nspath)
|
defer os.Remove(nspath)
|
||||||
|
|
||||||
isNSFS, _, err := ns.IsNS(nspath)
|
err = ns.IsNSorErr(nspath)
|
||||||
Expect(err).NotTo(HaveOccurred())
|
Expect(err).To(HaveOccurred())
|
||||||
Expect(isNSFS).To(Equal(false))
|
Expect(err).To(BeAssignableToTypeOf(ns.NSPathNotNSErr{}))
|
||||||
|
Expect(err).NotTo(BeAssignableToTypeOf(ns.NSPathNotExistErr{}))
|
||||||
|
})
|
||||||
|
|
||||||
|
It("should error on non-existing paths", func() {
|
||||||
|
err := ns.IsNSorErr("/tmp/IDoNotExist")
|
||||||
|
Expect(err).To(HaveOccurred())
|
||||||
|
Expect(err).To(BeAssignableToTypeOf(ns.NSPathNotExistErr{}))
|
||||||
|
Expect(err).NotTo(BeAssignableToTypeOf(ns.NSPathNotNSErr{}))
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
Loading…
x
Reference in New Issue
Block a user