From 442b01d2e2573c73cd866ef83fc2571d5c6fe119 Mon Sep 17 00:00:00 2001 From: apostasie Date: Sun, 1 Dec 2024 20:38:08 -0800 Subject: [PATCH] Fix permissions for resolv.conf and hosts WriteFile uses syscall.Open, so permissions are modified by umask, if set. For people using agressive umasks (0077), /etc/resolv.conf will end-up unreadable for non root processes. See https://github.com/containerd/nerdctl/issues/3704 Signed-off-by: apostasie --- pkg/dnsutil/hostsstore/hostsstore.go | 17 +++++++++++++++++ pkg/resolvconf/resolvconf.go | 11 ++++++++++- 2 files changed, 27 insertions(+), 1 deletion(-) diff --git a/pkg/dnsutil/hostsstore/hostsstore.go b/pkg/dnsutil/hostsstore/hostsstore.go index 507f93ec708..1980e4f934b 100644 --- a/pkg/dnsutil/hostsstore/hostsstore.go +++ b/pkg/dnsutil/hostsstore/hostsstore.go @@ -115,6 +115,14 @@ func (x *hostsStore) Acquire(meta Meta) (err error) { return errors.Join(store.ErrSystemFailure, err) } + // os.WriteFile relies on syscall.Open. Unless there are ACLs, the effective mode of the file will be matched + // against the current process umask. + // See https://www.man7.org/linux/man-pages/man2/open.2.html for details. + // Since we must make sure that these files are world readable, explicitly chmod them here. + if err = os.Chmod(loc, 0o644); err != nil { + err = errors.Join(store.ErrSystemFailure, err) + } + var content []byte content, err = json.Marshal(meta) if err != nil { @@ -176,6 +184,14 @@ func (x *hostsStore) AllocHostsFile(id string, content []byte) (location string, err = errors.Join(store.ErrSystemFailure, err) } + // os.WriteFile relies on syscall.Open. Unless there are ACLs, the effective mode of the file will be matched + // against the current process umask. + // See https://www.man7.org/linux/man-pages/man2/open.2.html for details. + // Since we must make sure that these files are world readable, explicitly chmod them here. + if err = os.Chmod(loc, 0o644); err != nil { + err = errors.Join(store.ErrSystemFailure, err) + } + return err }) if err != nil { @@ -333,6 +349,7 @@ func (x *hostsStore) updateAllHosts() (err error) { if err != nil { log.L.WithError(err).Errorf("failed to write hosts file for %q", entry) } + _ = os.Chmod(loc, 0o644) } return nil } diff --git a/pkg/resolvconf/resolvconf.go b/pkg/resolvconf/resolvconf.go index 676fc9fe366..79bec3ecd9e 100644 --- a/pkg/resolvconf/resolvconf.go +++ b/pkg/resolvconf/resolvconf.go @@ -317,7 +317,16 @@ func Build(path string, dns, dnsSearch, dnsOptions []string) (*File, error) { return nil, err } - return &File{Content: content.Bytes(), Hash: hash}, os.WriteFile(path, content.Bytes(), 0644) + err = os.WriteFile(path, content.Bytes(), 0o644) + if err != nil { + return nil, err + } + + // os.WriteFile relies on syscall.Open. Unless there are ACLs, the effective mode of the file will be matched + // against the current process umask. + // See https://www.man7.org/linux/man-pages/man2/open.2.html for details. + // Since we must make sure that these files are world readable, explicitly chmod them here. + return &File{Content: content.Bytes(), Hash: hash}, os.Chmod(path, 0o644) } func hashData(src io.Reader) (string, error) {