From bd42769f8755216a5c6aa4e95286dcf2258f76d4 Mon Sep 17 00:00:00 2001 From: Dylan Myers Date: Wed, 15 May 2024 22:12:03 -0400 Subject: [PATCH] Add a working implementation of host.Users() for AIX --- host/host_aix.go | 52 ++++++++++++++++++++++++++++++---------------------- 1 file changed, 30 insertions(+), 22 deletions(-) diff --git a/host/host_aix.go b/host/host_aix.go index b0cdb0f..a0922ee 100644 --- a/host/host_aix.go +++ b/host/host_aix.go @@ -4,9 +4,7 @@ package host import ( - "bytes" "context" - "encoding/binary" "errors" "strconv" "strings" @@ -81,30 +79,40 @@ func UptimeWithContext(ctx context.Context) (uint64, error) { return uint64(total_time), nil } -// This is probably broken, it doesn't seem to work even with CGO +// This is a weak implementation due to the limitations on retrieving this data in AIX func UsersWithContext(ctx context.Context) ([]UserStat, error) { var ret []UserStat - ut, err := invoke.CommandWithContext(ctx, "w").Output() - - for i := 0; i < count; i++ { - b := buf[i*sizeOfUtmp : (i+1)*sizeOfUtmp] + out, err := invoke.CommandWithContext(ctx, "w").Output() + if err != nil { + return nil, err + } + lines := strings.Split(string(out), "\n") + if len(lines) < 3 { + return []UserStat{}, common.ErrNotImplementedError + } - var u utmp - br := bytes.NewReader(b) - err := binary.Read(br, binary.LittleEndian, &u) - if err != nil { - continue + hf := strings.Fields(lines[1]) // headers + for l := 2; l < len(lines)-1; l++ { + v := strings.Fields(lines[l]) // values + us := &UserStat{} + for i, header := range hf { + // We're done in any of these use cases + if i >= len(v) || v[0] == "-" { + break + } + + if t, err := strconv.ParseFloat(v[i], 64); err == nil { + switch header { + case `User`: + us.User = t + case `tty`: + us.Terminal = t + } + } } - if u.Type != user_PROCESS { - continue - } - user := UserStat{ - User: common.IntToString(u.User[:]), - Terminal: common.IntToString(u.Line[:]), - Host: common.IntToString(u.Host[:]), - Started: int(u.Tv.Sec), - } - ret = append(ret, user) + + // Valid User data, so append it + ret = append(ret, *us) } return ret, nil