File: os.go

package info (click to toggle)
acmetool 0.2.2-3
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid, trixie
  • size: 792 kB
  • sloc: sh: 349; makefile: 105
file content (55 lines) | stat: -rw-r--r-- 1,076 bytes parent folder | download | duplicates (6)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
package hooks

import (
	deos "github.com/hlandau/goutils/os"
	"os"
	"os/exec"
)

func runningAsRoot() bool {
	return os.Getuid() == 0
}

func fileIsScript(fn string) bool {
	f, err := os.Open(fn)
	if err != nil {
		return false
	}
	defer f.Close()
	var b [2]byte
	n, _ := f.Read(b[:])
	if n < 2 {
		return false
	}

	return string(b[:]) == "#!"
}

// Vulnerable to race conditions, but this is just a check. sudo enforces all
// security properties.
func shouldSudoFile(fn string, fi os.FileInfo) bool {
	if runningAsRoot() {
		return false
	}

	_, err := exec.LookPath("sudo")
	if err != nil {
		return false
	}

	// Only setuid files if the setuid bit is set.
	if (fi.Mode() & os.ModeSetuid) == 0 {
		return false
	}

	// Don't sudo anything which appears to be setuid'd for a non-root user.
	// This doesn't really buy us anything security-wise, but it's not what
	// we're expecting.
	uid, err := deos.GetFileUID(fi)
	if err != nil || uid != 0 {
		return false
	}

	// Make sure the file is a script, otherwise we can just execute it directly.
	return fileIsScript(fn)
}