Allocate COMMAND (cmdline) and comm buffers dynamically#1865
Allocate COMMAND (cmdline) and comm buffers dynamically#1865fasterit wants to merge 1 commit intohtop-dev:mainfrom
Conversation
Fixes htop-dev#1860 This PR was developed by DLange/Faster IT with Microsoft Copilot
|
I left the initial buffer at 4096 +1 bytes so we can compare performance. I suggest we ramp up from 512 bytes if/when we commit this to main as we can save memory this way and it comes rather "for free" with the dynamic allocation. |
|
@fasterit This thing is very similar to the dynamic buffer code I've done in #1821. My code snippet (generic/Demangle.c): char* Generic_Demangle(const char* mangled) {
// The cplus_demangle() API from libdemangle is flawed. It does not
// provide us the required size of the buffer to store the demangled
// name, and it leaves the buffer content undefined if the specified
// buffer size is not big enough.
static size_t bufSize = 128;
static char* buf;
while (true) {
if (!buf) {
buf = malloc(bufSize);
if (!buf)
return NULL;
}
int res = cplus_demangle(mangled, buf, bufSize);
if (res == 0)
break;
if (res != DEMANGLE_ESPACE || bufSize > SIZE_MAX / 2)
return NULL;
bufSize *= 2;
free(buf);
buf = NULL;
}
return strdup(buf);
}Notice that I keep the buffer and not deallocate it after use. I think this can save some time when there are lots of strings needed to fetch (and all of them need a dynamically-sized temporary buffer). I don't know if it is a good idea. |
| #endif | ||
|
|
||
| /* Maximum buffer size for reading COMMAND / comm */ | ||
| #define MAX_CMDLINE_BUFFER_SIZE (2 * 1024 * 1024 + 1) |
There was a problem hiding this comment.
Given the 4K+1 is multiplied a bunch of times, by the time we reach this size, it's more like 2M+512.
There was a problem hiding this comment.
Yes, see my comment on suggesting to start with 512 bytes in production
|
I have a question: How does this solve the original bug (#1860) when the new proposed solution still has a length limit? |
|
@Explorer09 Because the length limit is 2 MB now, not 4096 Bytes. As much as I know currently, 2MB seems to be the practical limit of cmdlines in the Linux kernel these days. At least |
I am uncomfortable when the whole 2 MB long command line is kept in htop's memory. If we keep that line in memory only to let the filter function work, I think an alternative approach is to read and "grep" from the file in procfs on demand. |
Having 2MiB in memory is much better from a performance PoV than having to grep 2000+ files just in case one of the processes matches something. It's a trade-of between memory vs. repeatedly doing several syscalls just to safe a few kB of memory. You can still do "keep the buffer for next read and strdup for internal storage". |
Fixes #1860
This PR was developed by DLange/Faster IT with Microsoft Copilot