Skip to content

Commit

Permalink
Improved process of swap info collecting
Browse files Browse the repository at this point in the history
  • Loading branch information
andyone committed May 16, 2018
1 parent 8c3f9dc commit 3dc895b
Show file tree
Hide file tree
Showing 2 changed files with 80 additions and 61 deletions.
7 changes: 4 additions & 3 deletions common/swptop.spec
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@

Summary: Utility for viewing swap consumption of processes
Name: swptop
Version: 0.4.1
Version: 0.5.0
Release: 0%{?dist}
Group: Applications/System
License: EKOL
Expand All @@ -20,7 +20,7 @@ Source0: https://source.kaos.st/%{name}/%{name}-%{version}.tar.bz2

BuildRoot: %{_tmppath}/%{name}-%{version}-%{release}-root-%(%{__id_u} -n)

BuildRequires: golang >= 1.9
BuildRequires: golang >= 1.10

Provides: %{name} = %{version}-%{release}

Expand Down Expand Up @@ -57,7 +57,8 @@ rm -rf %{buildroot}
################################################################################

%changelog
* Tue May 15 2018 Anton Novojilov <andy@essentialkaos.com> - 0.4.1-0
* Wed May 16 2018 Anton Novojilov <andy@essentialkaos.com> - 0.5.0-0
- Improved process of swap info collecting
- Fixed bug with output info if swap disabled on system

* Wed Jan 31 2018 Anton Novojilov <andy@essentialkaos.com> - 0.4.0-0
Expand Down
134 changes: 76 additions & 58 deletions swptop.go
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@ import (

const (
APP = "swptop"
VER = "0.4.1"
VER = "0.5.0"
DESC = "Utility for viewing swap consumption of processes"
)

Expand Down Expand Up @@ -81,6 +81,9 @@ var useRawOutput bool
// winWidth is current window width
var winWidth int

// cmdEllipsis command ellipsis size
var cmdEllipsis = 64

// ////////////////////////////////////////////////////////////////////////////////// //

func main() {
Expand Down Expand Up @@ -142,71 +145,82 @@ func configureUI() {
fmtutil.SeparatorFullscreen = true
winWidth = window.GetWidth()
}

if winWidth > 110 {
cmdEllipsis = winWidth - 40
}
}

// printPrettyTop print info with separators and headers
func printPrettyTop() {
info, err := collectInfo()
procInfo, memInfo, err := collectInfo()

if err != nil {
printErrorAndExit(err.Error())
}

if len(info) == 0 {
if len(procInfo) == 0 && memInfo.SwapUsed == 0 {
fmtc.Println("{g}Can't find any process with swap usage{!}")
return
}

cmdEllipsis := 64
fmtc.NewLine()

if winWidth > 110 {
cmdEllipsis = winWidth - 40
if len(procInfo) != 0 {
printPrettyProcessList(procInfo)
}

fmtutil.Separator(true)
fmtc.NewLine()

printOverallInfo(procInfo, memInfo)

fmtc.NewLine()
fmtutil.Separator(true)

fmtc.NewLine()
}

// printPrettyProcessList print info about swap usage by processes
func printPrettyProcessList(procInfo ProcessInfoSlice) {
fmtutil.Separator(true)

fmtc.Printf(
" {*}%5s{!} {s}|{!} {*}%16s{!} {s}|{!} {*}%8s{!} {s}|{!} {*}%-s{!}\n",
"PID", "USERNAME", "SWAP", "COMMAND",
)

fmtutil.Separator(true)

for _, pi := range info {
for _, pi := range procInfo {
fmtc.Printf(
" %5d {s}|{!} %16s {s}|{!} %8s {s}|{!} %-s\n",
pi.PID, pi.User, fmtutil.PrettySize(pi.VmSwap),
strutil.Ellipsis(pi.Command, cmdEllipsis),
)
}

fmtutil.Separator(true)

printOverallInfo(info)

fmtc.NewLine()
}

// printOverallInfo print overall swap usage info
func printOverallInfo(info ProcessInfoSlice) {
overall := getOverallSwapUsage()
func printOverallInfo(procInfo ProcessInfoSlice, memInfo *system.MemInfo) {
var procUsed uint64
var procUsedPerc float64

if overall == nil {
return
if len(procInfo) != 0 {
procUsed = calculateUsage(procInfo)
procUsedPerc = (float64(procUsed) / float64(memInfo.SwapTotal)) * 100.0
}

procUsed := calculateUsage(info)
procUsedPerc := (float64(procUsed) / float64(overall.SwapTotal)) * 100.0
overallUsed := overall.SwapUsed
overallUsed := memInfo.SwapUsed

// Procfs cannot show values less than 1kb, so we have use calculated processes usage
if procUsed > overallUsed {
if procUsed > memInfo.SwapUsed {
overallUsed = procUsed
}

overallUsedPerc := (float64(overallUsed) / float64(overall.SwapTotal)) * 100.0
overallUsedPerc := (float64(overallUsed) / float64(memInfo.SwapTotal)) * 100.0

if math.IsNaN(procUsedPerc) {
if len(procInfo) == 0 || math.IsNaN(procUsedPerc) {
fmtc.Println(" {*}Processes:{!} n/a")
} else {
fmtc.Printf(
Expand All @@ -226,30 +240,62 @@ func printOverallInfo(info ProcessInfoSlice) {
)
}

fmtc.Printf(" {*}Total:{!} %s\n", fmtutil.PrettySize(overall.SwapTotal))

fmtutil.Separator(true)
fmtc.Printf(" {*}Total:{!} %s\n", fmtutil.PrettySize(memInfo.SwapTotal))
}

// printRawTop just print raw info
func printRawTop() {
info, err := collectInfo()
procInfo, _, err := collectInfo()

if err != nil {
printErrorAndExit(err.Error())
}

if len(info) == 0 {
if len(procInfo) == 0 {
return
}

for _, pi := range info {
for _, pi := range procInfo {
fmt.Printf("%d %s %d %s\n", pi.PID, pi.User, pi.VmSwap, pi.Command)
}
}

// collectInfo collect info about processes and sort result slice
func collectInfo() (ProcessInfoSlice, error) {
func collectInfo() (ProcessInfoSlice, *system.MemInfo, error) {
memInfo, err := system.GetMemInfo()

if err != nil {
return nil, nil, err
}

procInfo, err := getProcessesSwapUsage()

if err != nil {
return nil, nil, err
}

return procInfo, memInfo, err
}

// ignoreInfo return true if we must ignore this info
func ignoreInfo(info ProcessInfo) bool {
if options.Has(OPT_USER) {
if info.User != options.GetS(OPT_USER) {
return true
}
}

if options.Has(OPT_FILTER) {
if !strings.Contains(info.Command, options.GetS(OPT_FILTER)) {
return true
}
}

return false
}

// getProcessesSwapUsage return slice with info about swap usage by processes
func getProcessesSwapUsage() (ProcessInfoSlice, error) {
processes, err := process.GetList()

if err != nil {
Expand Down Expand Up @@ -286,34 +332,6 @@ func collectInfo() (ProcessInfoSlice, error) {
return result, nil
}

// ignoreInfo return true if we must ignore this info
func ignoreInfo(info ProcessInfo) bool {
if options.Has(OPT_USER) {
if info.User != options.GetS(OPT_USER) {
return true
}
}

if options.Has(OPT_FILTER) {
if !strings.Contains(info.Command, options.GetS(OPT_FILTER)) {
return true
}
}

return false
}

// getOverallSwapUsage get overall memory info
func getOverallSwapUsage() *system.MemInfo {
info, err := system.GetMemInfo()

if err != nil {
return nil
}

return info
}

// calculateUsage calculate total swap usage
func calculateUsage(info ProcessInfoSlice) uint64 {
var result uint64
Expand Down

0 comments on commit 3dc895b

Please sign in to comment.