diff options
author | Benoît Dejean <benoit@placenet.org> | 2009-05-03 16:25:31 +0200 |
---|---|---|
committer | Benoît Dejean <benoit@placenet.org> | 2009-05-03 16:25:31 +0200 |
commit | 62bafe804e2841786d0084454bc649f964991b7e (patch) | |
tree | 2a8a93becc5a66e96fc0174ef8ef36ec0df0e78b /sysdeps/linux | |
parent | 9f051c9569466b3d08e20a32e6f51df80453a6d3 (diff) | |
download | libgtop-62bafe804e2841786d0084454bc649f964991b7e.tar.gz |
Don't use sscanf anymore when parsins smaps.
That's more code but it brings a 20% speed improvement.
Diffstat (limited to 'sysdeps/linux')
-rw-r--r-- | sysdeps/linux/procmap.c | 71 |
1 files changed, 70 insertions, 1 deletions
diff --git a/sysdeps/linux/procmap.c b/sysdeps/linux/procmap.c index 5762e9f1..40efafca 100644 --- a/sysdeps/linux/procmap.c +++ b/sysdeps/linux/procmap.c @@ -141,6 +141,68 @@ parse_smaps(glibtop_map_entry *entry, const char* line) } +/* + sscanf is too slow + and system-monitor calls procmap for each pid every second + + manual parsing is faster + + error checking is weaker +*/ + +static gboolean +parse_line(char* line, + guint64* start, guint64* end, char flags[4], guint64* offset, + gushort* dev_major, gushort* dev_minor, guint64* inode, + char** filename) +{ + /* %16llx-%16llx %4c %16llx %02hx:%02hx %llu%*[ ]%n */ + + char *p, *next; + + p = line; + + *start = strtoull(p, &p, 16); + + if (G_UNLIKELY(*p != '-')) + return FALSE; + p++; + + *end = strtoull(p, &p, 16); + + p = next_token(p); + + memcpy(flags, p, 4); + p += 4; + + *offset = strtoull(p, &p, 16); + + *dev_major = strtoul(p, &p, 16); + + if (G_UNLIKELY(*p != ':')) + return FALSE; + p++; + + *dev_minor = strtoul(p, &p, 16); + + *inode = strtoull(p, &p, 10); + + p = next_token(p); + + *filename = p; + + for ( ; *p; p++) { + if (*p == '\n') { + *p = '\0'; + break; + } + } + + return TRUE; +} + + + glibtop_map_entry * @@ -181,7 +243,7 @@ glibtop_get_proc_map_s (glibtop *server, glibtop_proc_map *buf, pid_t pid) { unsigned long perm; guint len; - int line_end; + /* int line_end; */ unsigned short dev_major, dev_minor; guint64 start, end, offset, inode; @@ -195,6 +257,12 @@ glibtop_get_proc_map_s (glibtop *server, glibtop_proc_map *buf, pid_t pid) new_entry_line: + if (!parse_line(line, + &start, &end, flags, &offset, + &dev_major, &dev_minor, &inode, &filename)) + continue; + + /* if (sscanf(line, PROC_MAPS_FORMAT, &start, &end, flags, &offset, &dev_major, &dev_minor, &inode, &line_end) != 7) @@ -202,6 +270,7 @@ glibtop_get_proc_map_s (glibtop *server, glibtop_proc_map *buf, pid_t pid) filename = line + line_end; g_strstrip(filename); + */ /* Compute access permissions. */ perm = 0; |