* IDState cleaned up. Should work on all *NIXes now. * Can now get IDState of arbitrary PID. * Shuffled some env stuff around.
161 lines
3.0 KiB
Go
161 lines
3.0 KiB
Go
package internal
|
|
|
|
import (
|
|
`bytes`
|
|
`errors`
|
|
`fmt`
|
|
`os`
|
|
"runtime"
|
|
"strconv"
|
|
"strings"
|
|
|
|
`r00t2.io/sysutils/paths`
|
|
)
|
|
|
|
// EnvListToMap splits a []string of env var keypairs to a map.
|
|
func EnvListToMap(envs []string) (envMap map[string]string) {
|
|
|
|
var kv []string
|
|
var k, v string
|
|
|
|
envMap = make(map[string]string)
|
|
|
|
for _, ev := range envs {
|
|
kv = strings.SplitN(ev, "=", 2)
|
|
// I *think* SplitN does this for me, but...
|
|
if len(kv) == 1 {
|
|
kv = append(kv, "")
|
|
}
|
|
k = kv[0]
|
|
v = kv[1]
|
|
envMap[k] = v
|
|
}
|
|
|
|
return
|
|
}
|
|
|
|
// GetPathEnv returns a slice of the PATH variable's items.
|
|
func GetPathEnv() (pathList []string, err error) {
|
|
|
|
var pathVar string = GetPathEnvName()
|
|
|
|
pathList = make([]string, 0)
|
|
|
|
for _, p := range strings.Split(os.Getenv(pathVar), string(os.PathListSeparator)) {
|
|
if err = paths.RealPath(&p); err != nil {
|
|
return
|
|
}
|
|
pathList = append(pathList, p)
|
|
}
|
|
return
|
|
}
|
|
|
|
/*
|
|
GetPidEnvMap will only work on *NIX-like systems with procfs.
|
|
It gets the environment variables of a given process' PID.
|
|
*/
|
|
func GetPidEnvMap(pid uint32) (envMap map[string]string, err error) {
|
|
|
|
var envBytes []byte
|
|
var envList []string
|
|
var envArr [][]byte
|
|
var procPath string
|
|
var exists bool
|
|
|
|
envMap = make(map[string]string)
|
|
|
|
procPath = fmt.Sprintf("/proc/%v/environ", pid)
|
|
|
|
if exists, err = paths.RealPathExists(&procPath); err != nil {
|
|
return
|
|
}
|
|
if !exists {
|
|
err = errors.New(fmt.Sprintf("information for pid %v does not exist", pid))
|
|
return
|
|
}
|
|
|
|
if envBytes, err = os.ReadFile(procPath); err != nil {
|
|
return
|
|
}
|
|
|
|
envArr = bytes.Split(envBytes, []byte{0x0})
|
|
envList = make([]string, len(envArr))
|
|
for idx, b := range envArr {
|
|
envList[idx] = string(b)
|
|
}
|
|
|
|
envMap = EnvListToMap(envList)
|
|
|
|
return
|
|
}
|
|
|
|
// GetPathEnvName gets the OS-specific path environment variable name.
|
|
func GetPathEnvName() (envVarName string) {
|
|
|
|
var ok bool
|
|
|
|
if envVarName, ok = pathEnvVarName[runtime.GOOS]; !ok {
|
|
// *NIX/the default.
|
|
envVarName = "PATH"
|
|
}
|
|
|
|
return
|
|
}
|
|
|
|
// NativizeEnvMap returns a native-typed env map from a string version.
|
|
func NativizeEnvMap(stringMap map[string]string) (envMap map[string]interface{}) {
|
|
|
|
var pathVar string = GetPathEnvName()
|
|
var err error
|
|
|
|
envMap = make(map[string]interface{})
|
|
|
|
for k, v := range stringMap {
|
|
|
|
// Check for PATH/Path - we handle this uniquely.
|
|
if k == pathVar {
|
|
if envMap[k], err = GetPathEnv(); err != nil {
|
|
envMap[k] = v
|
|
err = nil
|
|
}
|
|
continue
|
|
}
|
|
|
|
// It might be...
|
|
// a float
|
|
if reMaybeFloat.MatchString(v) {
|
|
if envMap[k], err = strconv.ParseFloat(v, 64); err == nil {
|
|
continue
|
|
}
|
|
err = nil
|
|
}
|
|
|
|
// an int
|
|
if reMaybeInt.MatchString(v) {
|
|
if envMap[k], err = strconv.Atoi(v); err == nil {
|
|
continue
|
|
}
|
|
err = nil
|
|
}
|
|
|
|
// a uint
|
|
if envMap[k], err = strconv.ParseUint(v, 10, 64); err == nil {
|
|
continue
|
|
} else {
|
|
err = nil
|
|
}
|
|
|
|
// a boolean
|
|
if envMap[k], err = strconv.ParseBool(v); err == nil {
|
|
continue
|
|
} else {
|
|
err = nil
|
|
}
|
|
|
|
// ok so... guess it's a string, then.
|
|
envMap[k] = v
|
|
}
|
|
|
|
return
|
|
}
|