// pacmanIgnore checks to see whether a given package is in /etc/pacman.conf's // IgnorePkg setting func pacmanIgnore(parameters []string) (exitCode int, exitMessage string) { pkg := parameters[0] path := "/etc/pacman.conf" data := wrkutils.FileToString(path) re := regexp.MustCompile(`[^#]IgnorePkg\s+=\s+.+`) find := re.FindString(data) var packages []string if find != "" { spl := strings.Split(find, " ") wrkutils.IndexError("Not enough lines in "+path, 2, spl) packages = spl[2:] // first two are "IgnorePkg" and "=" if tabular.StrIn(pkg, packages) { return 0, "" } } msg := "Couldn't find package in IgnorePkg" return wrkutils.GenericError(msg, pkg, packages) }
// getGroups returns a list of Group structs, as parsed from /etc/group func getGroups() (groups []Group) { path := "/etc/group" data := wrkutils.FileToString(path) rowSep := regexp.MustCompile(`\n`) colSep := regexp.MustCompile(`:`) lines := tabular.SeparateString(rowSep, colSep, data) commaRegexp := regexp.MustCompile(`,`) for _, line := range lines { if len(line) > 3 { // only lines that have all fields (non-empty) gid, err := strconv.ParseInt(line[2], 10, 64) if err != nil { log.WithFields(log.Fields{ "group": line[0], "path": path, }).Fatal("Could not parse ID for group") } userSlice := commaRegexp.Split(line[3], -1) group := Group{Name: line[0], ID: int(gid), Users: userSlice} groups = append(groups, group) } } return groups }
// getAptrepos constructs repos from the sources.list file at path. Gives // non-zero URLs func getAptRepos() (repos []repo) { // getAptSources returns all the urls of all apt sources (including source // code repositories getAptSources := func() (urls []string) { otherLists := wrkutils.GetFilesWithExtension("/etc/apt/sources.list.d", ".list") sourceLists := append([]string{"/etc/apt/sources.list"}, otherLists...) for _, f := range sourceLists { split := tabular.ProbabalisticSplit(wrkutils.FileToString(f)) // filter out comments commentRegex := regexp.MustCompile(`^\s*#`) for _, line := range split { if len(line) > 1 && !(commentRegex.MatchString(line[0])) { urls = append(urls, line[1]) } } } return urls } for _, src := range getAptSources() { repos = append(repos, repo{URL: src}) } return repos }
// port parses /proc/net/tcp to determine if a given port is in an open state // and returns an error if it is not. func port(parameters []string) (exitCode int, exitMessage string) { // getHexPorts gets all open ports as hex strings from /proc/net/tcp getHexPorts := func() (ports []string) { paths := [2]string{"/proc/net/tcp", "/proc/net/udp"} for _, path := range paths { data := wrkutils.FileToString(path) table := tabular.ProbabalisticSplit(data) // TODO by header isn't working //localAddresses := tabular.GetColumnByHeader("local_address", table) localAddresses := tabular.GetAllNoHeader(table) portRe := regexp.MustCompile(`([0-9A-F]{8}):([0-9A-F]{4})`) for _, address := range localAddresses { port := portRe.FindString(address) if port != "" { if len(port) < 10 { log.WithFields(log.Fields{ "port": port, "length": len(port), }).Fatal("Couldn't parse port number in " + path) } portString := string(port[9:]) ports = append(ports, portString) } } } return ports } // strHexToDecimal converts from string containing hex number to int strHexToDecimal := func(hex string) int { portInt, err := strconv.ParseInt(hex, 16, 64) if err != nil { log.WithFields(log.Fields{ "number": hex, "error": err.Error(), }).Fatal("Couldn't parse hex number") } return int(portInt) } // getOpenPorts gets a list of open/listening ports as integers getOpenPorts := func() (ports []int) { for _, port := range getHexPorts() { ports = append(ports, strHexToDecimal(port)) } return ports } // TODO check if it is in a valid range port := wrkutils.ParseMyInt(parameters[0]) open := getOpenPorts() for _, p := range open { if p == port { return 0, "" } } // convert ports to string to send to wrkutils.GenericError var strPorts []string for _, port := range open { strPorts = append(strPorts, fmt.Sprint(port)) } return wrkutils.GenericError("Port not open", fmt.Sprint(port), strPorts) }