selftests/bpf: Adjust veristat stack depth parsing

The verifier now reports instruction and stack depth statistics using
uniform "subprog <id> (<name>) <kind>" records. Subprogram 0 is classified
as main, while other records are global or static. Each record carries
insns_self, insns_total, and stack depth.

Teach veristat to parse the new records while retaining support for the
legacy one-line stack depth format used by older kernels. Skip both
instruction counts and match only through the stack value so fields can
still be appended without breaking parsing.

Increase the bounded backward scan so it can include all 256 per-subprogram
records.

Zero-initialize the legacy stack buffer because logs using the new format do
not populate it before the trailing tokenizer loop. This makes the loop see
an empty string instead of reading uninitialized data.

Signed-off-by: Kumar Kartikeya Dwivedi <memxor@gmail.com>
Acked-by: Eduard Zingerman <eddyz87@gmail.com>
Link: https://patch.msgid.link/20260812221925.3358041-5-memxor@gmail.com
Signed-off-by: Eduard Zingerman <eddyz87@gmail.com>
This commit is contained in:
Kumar Kartikeya Dwivedi
2026-08-13 00:19:21 +02:00
committed by Eduard Zingerman
parent c2e6c7de88
commit 5026862334

View File

@@ -993,13 +993,15 @@ static void free_verif_stats(struct verif_stats *stats, size_t stat_cnt)
static char verif_log_buf[64 * 1024];
#define MAX_PARSED_LOG_LINES 100
/* Keep room for all 256 subprogram records and trailing statistics. */
#define MAX_PARSED_LOG_LINES 300
static int parse_verif_log(char * const buf, size_t buf_sz, struct verif_stats *s)
{
const char *cur;
int pos, lines, sub_stack, cnt = 0;
char *state = NULL, *token, stack[512];
long sub_stack;
int pos, lines, cnt = 0;
char *state = NULL, *token, stack[512] = {};
buf[buf_sz - 1] = '\0';
@@ -1025,11 +1027,24 @@ static int parse_verif_log(char * const buf, size_t buf_sz, struct verif_stats *
&s->stats[MARK_READ_MAX_LEN]))
continue;
/*
* New kernels emit one "subprog <id> (<name>) <kind>" record
* per subprogram with the stack depth at the end, while old
* kernels emit a single "stack depth <a+...+n> max <max>"
* line. Match both formats so veristat works against either
* kernel.
*/
if (sscanf(cur, "stack depth max %ld", &s->stats[MAX_STACK]) == 1)
continue;
if (sscanf(cur, "subprog %*d %*s %*s insns_self %*d insns_total %*d stack %ld", &sub_stack) == 1) {
s->stats[STACK] += sub_stack;
continue;
}
if (2 == sscanf(cur, "stack depth %511s max %ld", stack, &s->stats[MAX_STACK]))
continue;
}
while ((token = strtok_r(cnt++ ? NULL : stack, "+", &state))) {
if (sscanf(token, "%d", &sub_stack) == 0)
if (sscanf(token, "%ld", &sub_stack) == 0)
break;
s->stats[STACK] += sub_stack;
}