ports/157195: [PATCH] sysutils/htop miscalculates available memory

Bartosz Fabianowski freebsd at chillt.de
Fri May 20 00:10:10 UTC 2011


>Number:         157195
>Category:       ports
>Synopsis:       [PATCH] sysutils/htop miscalculates available memory
>Confidential:   no
>Severity:       non-critical
>Priority:       low
>Responsible:    freebsd-ports-bugs
>State:          open
>Quarter:        
>Keywords:       
>Date-Required:
>Class:          sw-bug
>Submitter-Id:   current-users
>Arrival-Date:   Fri May 20 00:10:09 UTC 2011
>Closed-Date:
>Last-Modified:
>Originator:     Bartosz Fabianowski
>Release:        8.2-STABLE
>Organization:
>Environment:
>Description:
The sysutils/htop port reads /compat/linux/proc/meminfo to calculate the amount of memory used.

The code that generates this file resides in sys/compat/linprocfs/linprocfs.c. Here, the amount of available memory is intentionally misreported:

/*
 * The correct thing here would be:
 *
memfree = cnt.v_free_count * PAGE_SIZE;
memused = memtotal - memfree;
 *
 * but it might mislead linux binaries into thinking there
 * is very little memory left, so we cheat and tell them that
 * all memory that isn't wired down is free.
 */
memused = cnt.v_wire_count * PAGE_SIZE;
memfree = memtotal - memused;

>How-To-Repeat:
Run top and htop simultaneously. Notice that htop reports very low memory usage while top reports the correct value.
>Fix:
The attached patch uses sysctl to read the actual amount of available memory, just as top does.

Patch attached with submission follows:

--- ProcessList.c.orig	2009-03-11 14:03:42.000000000 +0100
+++ ProcessList.c	2011-05-20 01:48:22.000000000 +0200
@@ -31,6 +31,11 @@
 #include "debug.h"
 #include <assert.h>
 
+#ifdef __FreeBSD__
+#include <sys/types.h>
+#include <sys/sysctl.h>
+#endif
+
 /*{
 #ifndef PROCDIR
 #define PROCDIR "/proc"
@@ -313,7 +318,7 @@
    unsigned int pid = p->pid;
    int index = Vector_indexOf(this->processes, p, Process_pidCompare);
    assert(index != -1);
-   Vector_remove(this->processes, index);
+   if (index >= 0) Vector_remove(this->processes, index);
    assert(Hashtable_get(this->processTable, pid) == NULL); (void)pid;
    assert(Hashtable_count(this->processTable) == Vector_count(this->processes));
 }
@@ -730,7 +735,7 @@
 
 void ProcessList_scan(ProcessList* this) {
    unsigned long long int usertime, nicetime, systemtime, systemalltime, idlealltime, idletime, totaltime;
-   unsigned long long int swapFree;
+   unsigned long long int swapFree = 0;
 
    FILE* status;
    char buffer[128];
@@ -766,6 +771,12 @@
       }
    }
 
+   #ifdef __FreeBSD__
+   size_t len = sizeof(this->freeMem);
+   if (!sysctlbyname("vm.stats.vm.v_free_count", &this->freeMem, &len, NULL, 0))
+      this->freeMem *= getpagesize() / 1024;
+   #endif
+
    this->usedMem = this->totalMem - this->freeMem;
    this->usedSwap = this->totalSwap - swapFree;
    fclose(status);


>Release-Note:
>Audit-Trail:
>Unformatted:



More information about the freebsd-ports-bugs mailing list