1 // SPDX-License-Identifier: GPL-2.0-only 2 /* Copyright (c) 2022 Meta Platforms, Inc. and affiliates. */ 3 #include <linux/capability.h> 4 #include <stdlib.h> 5 #include <regex.h> 6 #include <test_progs.h> 7 #include <bpf/btf.h> 8 9 #include "autoconf_helper.h" 10 #include "disasm_helpers.h" 11 #include "unpriv_helpers.h" 12 #include "cap_helpers.h" 13 14 #define str_has_pfx(str, pfx) \ 15 (strncmp(str, pfx, __builtin_constant_p(pfx) ? sizeof(pfx) - 1 : strlen(pfx)) == 0) 16 17 #define TEST_LOADER_LOG_BUF_SZ 2097152 18 19 #define TEST_TAG_EXPECT_FAILURE "comment:test_expect_failure" 20 #define TEST_TAG_EXPECT_SUCCESS "comment:test_expect_success" 21 #define TEST_TAG_EXPECT_MSG_PFX "comment:test_expect_msg=" 22 #define TEST_TAG_EXPECT_REGEX_PFX "comment:test_expect_regex=" 23 #define TEST_TAG_EXPECT_XLATED_PFX "comment:test_expect_xlated=" 24 #define TEST_TAG_EXPECT_FAILURE_UNPRIV "comment:test_expect_failure_unpriv" 25 #define TEST_TAG_EXPECT_SUCCESS_UNPRIV "comment:test_expect_success_unpriv" 26 #define TEST_TAG_EXPECT_MSG_PFX_UNPRIV "comment:test_expect_msg_unpriv=" 27 #define TEST_TAG_EXPECT_REGEX_PFX_UNPRIV "comment:test_expect_regex_unpriv=" 28 #define TEST_TAG_EXPECT_XLATED_PFX_UNPRIV "comment:test_expect_xlated_unpriv=" 29 #define TEST_TAG_LOG_LEVEL_PFX "comment:test_log_level=" 30 #define TEST_TAG_PROG_FLAGS_PFX "comment:test_prog_flags=" 31 #define TEST_TAG_DESCRIPTION_PFX "comment:test_description=" 32 #define TEST_TAG_RETVAL_PFX "comment:test_retval=" 33 #define TEST_TAG_RETVAL_PFX_UNPRIV "comment:test_retval_unpriv=" 34 #define TEST_TAG_AUXILIARY "comment:test_auxiliary" 35 #define TEST_TAG_AUXILIARY_UNPRIV "comment:test_auxiliary_unpriv" 36 #define TEST_BTF_PATH "comment:test_btf_path=" 37 #define TEST_TAG_ARCH "comment:test_arch=" 38 39 /* Warning: duplicated in bpf_misc.h */ 40 #define POINTER_VALUE 0xcafe4all 41 #define TEST_DATA_LEN 64 42 43 #ifdef CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS 44 #define EFFICIENT_UNALIGNED_ACCESS 1 45 #else 46 #define EFFICIENT_UNALIGNED_ACCESS 0 47 #endif 48 49 static int sysctl_unpriv_disabled = -1; 50 51 enum mode { 52 PRIV = 1, 53 UNPRIV = 2 54 }; 55 56 struct expect_msg { 57 const char *substr; /* substring match */ 58 const char *regex_str; /* regex-based match */ 59 regex_t regex; 60 }; 61 62 struct expected_msgs { 63 struct expect_msg *patterns; 64 size_t cnt; 65 }; 66 67 struct test_subspec { 68 char *name; 69 bool expect_failure; 70 struct expected_msgs expect_msgs; 71 struct expected_msgs expect_xlated; 72 int retval; 73 bool execute; 74 }; 75 76 struct test_spec { 77 const char *prog_name; 78 struct test_subspec priv; 79 struct test_subspec unpriv; 80 const char *btf_custom_path; 81 int log_level; 82 int prog_flags; 83 int mode_mask; 84 int arch_mask; 85 bool auxiliary; 86 bool valid; 87 }; 88 89 static int tester_init(struct test_loader *tester) 90 { 91 if (!tester->log_buf) { 92 tester->log_buf_sz = TEST_LOADER_LOG_BUF_SZ; 93 tester->log_buf = calloc(tester->log_buf_sz, 1); 94 if (!ASSERT_OK_PTR(tester->log_buf, "tester_log_buf")) 95 return -ENOMEM; 96 } 97 98 return 0; 99 } 100 101 void test_loader_fini(struct test_loader *tester) 102 { 103 if (!tester) 104 return; 105 106 free(tester->log_buf); 107 } 108 109 static void free_msgs(struct expected_msgs *msgs) 110 { 111 int i; 112 113 for (i = 0; i < msgs->cnt; i++) 114 if (msgs->patterns[i].regex_str) 115 regfree(&msgs->patterns[i].regex); 116 free(msgs->patterns); 117 msgs->patterns = NULL; 118 msgs->cnt = 0; 119 } 120 121 static void free_test_spec(struct test_spec *spec) 122 { 123 /* Deallocate expect_msgs arrays. */ 124 free_msgs(&spec->priv.expect_msgs); 125 free_msgs(&spec->unpriv.expect_msgs); 126 free_msgs(&spec->priv.expect_xlated); 127 free_msgs(&spec->unpriv.expect_xlated); 128 129 free(spec->priv.name); 130 free(spec->unpriv.name); 131 spec->priv.name = NULL; 132 spec->unpriv.name = NULL; 133 } 134 135 static int push_msg(const char *substr, const char *regex_str, struct expected_msgs *msgs) 136 { 137 void *tmp; 138 int regcomp_res; 139 char error_msg[100]; 140 struct expect_msg *msg; 141 142 tmp = realloc(msgs->patterns, 143 (1 + msgs->cnt) * sizeof(struct expect_msg)); 144 if (!tmp) { 145 ASSERT_FAIL("failed to realloc memory for messages\n"); 146 return -ENOMEM; 147 } 148 msgs->patterns = tmp; 149 msg = &msgs->patterns[msgs->cnt]; 150 151 if (substr) { 152 msg->substr = substr; 153 msg->regex_str = NULL; 154 } else { 155 msg->regex_str = regex_str; 156 msg->substr = NULL; 157 regcomp_res = regcomp(&msg->regex, regex_str, REG_EXTENDED|REG_NEWLINE); 158 if (regcomp_res != 0) { 159 regerror(regcomp_res, &msg->regex, error_msg, sizeof(error_msg)); 160 PRINT_FAIL("Regexp compilation error in '%s': '%s'\n", 161 regex_str, error_msg); 162 return -EINVAL; 163 } 164 } 165 166 msgs->cnt += 1; 167 return 0; 168 } 169 170 static int parse_int(const char *str, int *val, const char *name) 171 { 172 char *end; 173 long tmp; 174 175 errno = 0; 176 if (str_has_pfx(str, "0x")) 177 tmp = strtol(str + 2, &end, 16); 178 else 179 tmp = strtol(str, &end, 10); 180 if (errno || end[0] != '\0') { 181 PRINT_FAIL("failed to parse %s from '%s'\n", name, str); 182 return -EINVAL; 183 } 184 *val = tmp; 185 return 0; 186 } 187 188 static int parse_retval(const char *str, int *val, const char *name) 189 { 190 struct { 191 char *name; 192 int val; 193 } named_values[] = { 194 { "INT_MIN" , INT_MIN }, 195 { "POINTER_VALUE", POINTER_VALUE }, 196 { "TEST_DATA_LEN", TEST_DATA_LEN }, 197 }; 198 int i; 199 200 for (i = 0; i < ARRAY_SIZE(named_values); ++i) { 201 if (strcmp(str, named_values[i].name) != 0) 202 continue; 203 *val = named_values[i].val; 204 return 0; 205 } 206 207 return parse_int(str, val, name); 208 } 209 210 static void update_flags(int *flags, int flag, bool clear) 211 { 212 if (clear) 213 *flags &= ~flag; 214 else 215 *flags |= flag; 216 } 217 218 /* Matches a string of form '<pfx>[^=]=.*' and returns it's suffix. 219 * Used to parse btf_decl_tag values. 220 * Such values require unique prefix because compiler does not add 221 * same __attribute__((btf_decl_tag(...))) twice. 222 * Test suite uses two-component tags for such cases: 223 * 224 * <pfx> __COUNTER__ '=' 225 * 226 * For example, two consecutive __msg tags '__msg("foo") __msg("foo")' 227 * would be encoded as: 228 * 229 * [18] DECL_TAG 'comment:test_expect_msg=0=foo' type_id=15 component_idx=-1 230 * [19] DECL_TAG 'comment:test_expect_msg=1=foo' type_id=15 component_idx=-1 231 * 232 * And the purpose of this function is to extract 'foo' from the above. 233 */ 234 static const char *skip_dynamic_pfx(const char *s, const char *pfx) 235 { 236 const char *msg; 237 238 if (strncmp(s, pfx, strlen(pfx)) != 0) 239 return NULL; 240 msg = s + strlen(pfx); 241 msg = strchr(msg, '='); 242 if (!msg) 243 return NULL; 244 return msg + 1; 245 } 246 247 enum arch { 248 ARCH_X86_64 = 0x1, 249 ARCH_ARM64 = 0x2, 250 ARCH_RISCV64 = 0x4, 251 }; 252 253 /* Uses btf_decl_tag attributes to describe the expected test 254 * behavior, see bpf_misc.h for detailed description of each attribute 255 * and attribute combinations. 256 */ 257 static int parse_test_spec(struct test_loader *tester, 258 struct bpf_object *obj, 259 struct bpf_program *prog, 260 struct test_spec *spec) 261 { 262 const char *description = NULL; 263 bool has_unpriv_result = false; 264 bool has_unpriv_retval = false; 265 int func_id, i, err = 0; 266 u32 arch_mask = 0; 267 struct btf *btf; 268 269 memset(spec, 0, sizeof(*spec)); 270 271 spec->prog_name = bpf_program__name(prog); 272 spec->prog_flags = testing_prog_flags(); 273 274 btf = bpf_object__btf(obj); 275 if (!btf) { 276 ASSERT_FAIL("BPF object has no BTF"); 277 return -EINVAL; 278 } 279 280 func_id = btf__find_by_name_kind(btf, spec->prog_name, BTF_KIND_FUNC); 281 if (func_id < 0) { 282 ASSERT_FAIL("failed to find FUNC BTF type for '%s'", spec->prog_name); 283 return -EINVAL; 284 } 285 286 for (i = 1; i < btf__type_cnt(btf); i++) { 287 const char *s, *val, *msg; 288 const struct btf_type *t; 289 bool clear; 290 int flags; 291 292 t = btf__type_by_id(btf, i); 293 if (!btf_is_decl_tag(t)) 294 continue; 295 296 if (t->type != func_id || btf_decl_tag(t)->component_idx != -1) 297 continue; 298 299 s = btf__str_by_offset(btf, t->name_off); 300 if (str_has_pfx(s, TEST_TAG_DESCRIPTION_PFX)) { 301 description = s + sizeof(TEST_TAG_DESCRIPTION_PFX) - 1; 302 } else if (strcmp(s, TEST_TAG_EXPECT_FAILURE) == 0) { 303 spec->priv.expect_failure = true; 304 spec->mode_mask |= PRIV; 305 } else if (strcmp(s, TEST_TAG_EXPECT_SUCCESS) == 0) { 306 spec->priv.expect_failure = false; 307 spec->mode_mask |= PRIV; 308 } else if (strcmp(s, TEST_TAG_EXPECT_FAILURE_UNPRIV) == 0) { 309 spec->unpriv.expect_failure = true; 310 spec->mode_mask |= UNPRIV; 311 has_unpriv_result = true; 312 } else if (strcmp(s, TEST_TAG_EXPECT_SUCCESS_UNPRIV) == 0) { 313 spec->unpriv.expect_failure = false; 314 spec->mode_mask |= UNPRIV; 315 has_unpriv_result = true; 316 } else if (strcmp(s, TEST_TAG_AUXILIARY) == 0) { 317 spec->auxiliary = true; 318 spec->mode_mask |= PRIV; 319 } else if (strcmp(s, TEST_TAG_AUXILIARY_UNPRIV) == 0) { 320 spec->auxiliary = true; 321 spec->mode_mask |= UNPRIV; 322 } else if ((msg = skip_dynamic_pfx(s, TEST_TAG_EXPECT_MSG_PFX))) { 323 err = push_msg(msg, NULL, &spec->priv.expect_msgs); 324 if (err) 325 goto cleanup; 326 spec->mode_mask |= PRIV; 327 } else if ((msg = skip_dynamic_pfx(s, TEST_TAG_EXPECT_MSG_PFX_UNPRIV))) { 328 err = push_msg(msg, NULL, &spec->unpriv.expect_msgs); 329 if (err) 330 goto cleanup; 331 spec->mode_mask |= UNPRIV; 332 } else if ((msg = skip_dynamic_pfx(s, TEST_TAG_EXPECT_REGEX_PFX))) { 333 err = push_msg(NULL, msg, &spec->priv.expect_msgs); 334 if (err) 335 goto cleanup; 336 spec->mode_mask |= PRIV; 337 } else if ((msg = skip_dynamic_pfx(s, TEST_TAG_EXPECT_REGEX_PFX_UNPRIV))) { 338 err = push_msg(NULL, msg, &spec->unpriv.expect_msgs); 339 if (err) 340 goto cleanup; 341 spec->mode_mask |= UNPRIV; 342 } else if ((msg = skip_dynamic_pfx(s, TEST_TAG_EXPECT_XLATED_PFX))) { 343 err = push_msg(msg, NULL, &spec->priv.expect_xlated); 344 if (err) 345 goto cleanup; 346 spec->mode_mask |= PRIV; 347 } else if ((msg = skip_dynamic_pfx(s, TEST_TAG_EXPECT_XLATED_PFX_UNPRIV))) { 348 err = push_msg(msg, NULL, &spec->unpriv.expect_xlated); 349 if (err) 350 goto cleanup; 351 spec->mode_mask |= UNPRIV; 352 } else if (str_has_pfx(s, TEST_TAG_RETVAL_PFX)) { 353 val = s + sizeof(TEST_TAG_RETVAL_PFX) - 1; 354 err = parse_retval(val, &spec->priv.retval, "__retval"); 355 if (err) 356 goto cleanup; 357 spec->priv.execute = true; 358 spec->mode_mask |= PRIV; 359 } else if (str_has_pfx(s, TEST_TAG_RETVAL_PFX_UNPRIV)) { 360 val = s + sizeof(TEST_TAG_RETVAL_PFX_UNPRIV) - 1; 361 err = parse_retval(val, &spec->unpriv.retval, "__retval_unpriv"); 362 if (err) 363 goto cleanup; 364 spec->mode_mask |= UNPRIV; 365 spec->unpriv.execute = true; 366 has_unpriv_retval = true; 367 } else if (str_has_pfx(s, TEST_TAG_LOG_LEVEL_PFX)) { 368 val = s + sizeof(TEST_TAG_LOG_LEVEL_PFX) - 1; 369 err = parse_int(val, &spec->log_level, "test log level"); 370 if (err) 371 goto cleanup; 372 } else if (str_has_pfx(s, TEST_TAG_PROG_FLAGS_PFX)) { 373 val = s + sizeof(TEST_TAG_PROG_FLAGS_PFX) - 1; 374 375 clear = val[0] == '!'; 376 if (clear) 377 val++; 378 379 if (strcmp(val, "BPF_F_STRICT_ALIGNMENT") == 0) { 380 update_flags(&spec->prog_flags, BPF_F_STRICT_ALIGNMENT, clear); 381 } else if (strcmp(val, "BPF_F_ANY_ALIGNMENT") == 0) { 382 update_flags(&spec->prog_flags, BPF_F_ANY_ALIGNMENT, clear); 383 } else if (strcmp(val, "BPF_F_TEST_RND_HI32") == 0) { 384 update_flags(&spec->prog_flags, BPF_F_TEST_RND_HI32, clear); 385 } else if (strcmp(val, "BPF_F_TEST_STATE_FREQ") == 0) { 386 update_flags(&spec->prog_flags, BPF_F_TEST_STATE_FREQ, clear); 387 } else if (strcmp(val, "BPF_F_SLEEPABLE") == 0) { 388 update_flags(&spec->prog_flags, BPF_F_SLEEPABLE, clear); 389 } else if (strcmp(val, "BPF_F_XDP_HAS_FRAGS") == 0) { 390 update_flags(&spec->prog_flags, BPF_F_XDP_HAS_FRAGS, clear); 391 } else if (strcmp(val, "BPF_F_TEST_REG_INVARIANTS") == 0) { 392 update_flags(&spec->prog_flags, BPF_F_TEST_REG_INVARIANTS, clear); 393 } else /* assume numeric value */ { 394 err = parse_int(val, &flags, "test prog flags"); 395 if (err) 396 goto cleanup; 397 update_flags(&spec->prog_flags, flags, clear); 398 } 399 } else if (str_has_pfx(s, TEST_TAG_ARCH)) { 400 val = s + sizeof(TEST_TAG_ARCH) - 1; 401 if (strcmp(val, "X86_64") == 0) { 402 arch_mask |= ARCH_X86_64; 403 } else if (strcmp(val, "ARM64") == 0) { 404 arch_mask |= ARCH_ARM64; 405 } else if (strcmp(val, "RISCV64") == 0) { 406 arch_mask |= ARCH_RISCV64; 407 } else { 408 PRINT_FAIL("bad arch spec: '%s'", val); 409 err = -EINVAL; 410 goto cleanup; 411 } 412 } else if (str_has_pfx(s, TEST_BTF_PATH)) { 413 spec->btf_custom_path = s + sizeof(TEST_BTF_PATH) - 1; 414 } 415 } 416 417 spec->arch_mask = arch_mask; 418 419 if (spec->mode_mask == 0) 420 spec->mode_mask = PRIV; 421 422 if (!description) 423 description = spec->prog_name; 424 425 if (spec->mode_mask & PRIV) { 426 spec->priv.name = strdup(description); 427 if (!spec->priv.name) { 428 PRINT_FAIL("failed to allocate memory for priv.name\n"); 429 err = -ENOMEM; 430 goto cleanup; 431 } 432 } 433 434 if (spec->mode_mask & UNPRIV) { 435 int descr_len = strlen(description); 436 const char *suffix = " @unpriv"; 437 char *name; 438 439 name = malloc(descr_len + strlen(suffix) + 1); 440 if (!name) { 441 PRINT_FAIL("failed to allocate memory for unpriv.name\n"); 442 err = -ENOMEM; 443 goto cleanup; 444 } 445 446 strcpy(name, description); 447 strcpy(&name[descr_len], suffix); 448 spec->unpriv.name = name; 449 } 450 451 if (spec->mode_mask & (PRIV | UNPRIV)) { 452 if (!has_unpriv_result) 453 spec->unpriv.expect_failure = spec->priv.expect_failure; 454 455 if (!has_unpriv_retval) { 456 spec->unpriv.retval = spec->priv.retval; 457 spec->unpriv.execute = spec->priv.execute; 458 } 459 460 if (spec->unpriv.expect_msgs.cnt == 0) { 461 for (i = 0; i < spec->priv.expect_msgs.cnt; i++) { 462 struct expect_msg *msg = &spec->priv.expect_msgs.patterns[i]; 463 464 err = push_msg(msg->substr, msg->regex_str, 465 &spec->unpriv.expect_msgs); 466 if (err) 467 goto cleanup; 468 } 469 } 470 if (spec->unpriv.expect_xlated.cnt == 0) { 471 for (i = 0; i < spec->priv.expect_xlated.cnt; i++) { 472 struct expect_msg *msg = &spec->priv.expect_xlated.patterns[i]; 473 474 err = push_msg(msg->substr, msg->regex_str, 475 &spec->unpriv.expect_xlated); 476 if (err) 477 goto cleanup; 478 } 479 } 480 } 481 482 spec->valid = true; 483 484 return 0; 485 486 cleanup: 487 free_test_spec(spec); 488 return err; 489 } 490 491 static void prepare_case(struct test_loader *tester, 492 struct test_spec *spec, 493 struct bpf_object *obj, 494 struct bpf_program *prog) 495 { 496 int min_log_level = 0, prog_flags; 497 498 if (env.verbosity > VERBOSE_NONE) 499 min_log_level = 1; 500 if (env.verbosity > VERBOSE_VERY) 501 min_log_level = 2; 502 503 bpf_program__set_log_buf(prog, tester->log_buf, tester->log_buf_sz); 504 505 /* Make sure we set at least minimal log level, unless test requires 506 * even higher level already. Make sure to preserve independent log 507 * level 4 (verifier stats), though. 508 */ 509 if ((spec->log_level & 3) < min_log_level) 510 bpf_program__set_log_level(prog, (spec->log_level & 4) | min_log_level); 511 else 512 bpf_program__set_log_level(prog, spec->log_level); 513 514 prog_flags = bpf_program__flags(prog); 515 bpf_program__set_flags(prog, prog_flags | spec->prog_flags); 516 517 tester->log_buf[0] = '\0'; 518 } 519 520 static void emit_verifier_log(const char *log_buf, bool force) 521 { 522 if (!force && env.verbosity == VERBOSE_NONE) 523 return; 524 fprintf(stdout, "VERIFIER LOG:\n=============\n%s=============\n", log_buf); 525 } 526 527 static void emit_xlated(const char *xlated, bool force) 528 { 529 if (!force && env.verbosity == VERBOSE_NONE) 530 return; 531 fprintf(stdout, "XLATED:\n=============\n%s=============\n", xlated); 532 } 533 534 static void validate_msgs(char *log_buf, struct expected_msgs *msgs, 535 void (*emit_fn)(const char *buf, bool force)) 536 { 537 regmatch_t reg_match[1]; 538 const char *log = log_buf; 539 int i, j, err; 540 541 for (i = 0; i < msgs->cnt; i++) { 542 struct expect_msg *msg = &msgs->patterns[i]; 543 const char *match = NULL; 544 545 if (msg->substr) { 546 match = strstr(log, msg->substr); 547 if (match) 548 log = match + strlen(msg->substr); 549 } else { 550 err = regexec(&msg->regex, log, 1, reg_match, 0); 551 if (err == 0) { 552 match = log + reg_match[0].rm_so; 553 log += reg_match[0].rm_eo; 554 } 555 } 556 557 if (!ASSERT_OK_PTR(match, "expect_msg")) { 558 if (env.verbosity == VERBOSE_NONE) 559 emit_fn(log_buf, true /*force*/); 560 for (j = 0; j <= i; j++) { 561 msg = &msgs->patterns[j]; 562 fprintf(stderr, "%s %s: '%s'\n", 563 j < i ? "MATCHED " : "EXPECTED", 564 msg->substr ? "SUBSTR" : " REGEX", 565 msg->substr ?: msg->regex_str); 566 } 567 return; 568 } 569 } 570 } 571 572 struct cap_state { 573 __u64 old_caps; 574 bool initialized; 575 }; 576 577 static int drop_capabilities(struct cap_state *caps) 578 { 579 const __u64 caps_to_drop = (1ULL << CAP_SYS_ADMIN | 1ULL << CAP_NET_ADMIN | 580 1ULL << CAP_PERFMON | 1ULL << CAP_BPF); 581 int err; 582 583 err = cap_disable_effective(caps_to_drop, &caps->old_caps); 584 if (err) { 585 PRINT_FAIL("failed to drop capabilities: %i, %s\n", err, strerror(err)); 586 return err; 587 } 588 589 caps->initialized = true; 590 return 0; 591 } 592 593 static int restore_capabilities(struct cap_state *caps) 594 { 595 int err; 596 597 if (!caps->initialized) 598 return 0; 599 600 err = cap_enable_effective(caps->old_caps, NULL); 601 if (err) 602 PRINT_FAIL("failed to restore capabilities: %i, %s\n", err, strerror(err)); 603 caps->initialized = false; 604 return err; 605 } 606 607 static bool can_execute_unpriv(struct test_loader *tester, struct test_spec *spec) 608 { 609 if (sysctl_unpriv_disabled < 0) 610 sysctl_unpriv_disabled = get_unpriv_disabled() ? 1 : 0; 611 if (sysctl_unpriv_disabled) 612 return false; 613 if ((spec->prog_flags & BPF_F_ANY_ALIGNMENT) && !EFFICIENT_UNALIGNED_ACCESS) 614 return false; 615 return true; 616 } 617 618 static bool is_unpriv_capable_map(struct bpf_map *map) 619 { 620 enum bpf_map_type type; 621 __u32 flags; 622 623 type = bpf_map__type(map); 624 625 switch (type) { 626 case BPF_MAP_TYPE_HASH: 627 case BPF_MAP_TYPE_PERCPU_HASH: 628 case BPF_MAP_TYPE_HASH_OF_MAPS: 629 flags = bpf_map__map_flags(map); 630 return !(flags & BPF_F_ZERO_SEED); 631 case BPF_MAP_TYPE_PERCPU_CGROUP_STORAGE: 632 case BPF_MAP_TYPE_ARRAY: 633 case BPF_MAP_TYPE_RINGBUF: 634 case BPF_MAP_TYPE_PROG_ARRAY: 635 case BPF_MAP_TYPE_CGROUP_ARRAY: 636 case BPF_MAP_TYPE_PERCPU_ARRAY: 637 case BPF_MAP_TYPE_USER_RINGBUF: 638 case BPF_MAP_TYPE_ARRAY_OF_MAPS: 639 case BPF_MAP_TYPE_CGROUP_STORAGE: 640 case BPF_MAP_TYPE_PERF_EVENT_ARRAY: 641 return true; 642 default: 643 return false; 644 } 645 } 646 647 static int do_prog_test_run(int fd_prog, int *retval, bool empty_opts) 648 { 649 __u8 tmp_out[TEST_DATA_LEN << 2] = {}; 650 __u8 tmp_in[TEST_DATA_LEN] = {}; 651 int err, saved_errno; 652 LIBBPF_OPTS(bpf_test_run_opts, topts, 653 .data_in = tmp_in, 654 .data_size_in = sizeof(tmp_in), 655 .data_out = tmp_out, 656 .data_size_out = sizeof(tmp_out), 657 .repeat = 1, 658 ); 659 660 if (empty_opts) { 661 memset(&topts, 0, sizeof(struct bpf_test_run_opts)); 662 topts.sz = sizeof(struct bpf_test_run_opts); 663 } 664 err = bpf_prog_test_run_opts(fd_prog, &topts); 665 saved_errno = errno; 666 667 if (err) { 668 PRINT_FAIL("FAIL: Unexpected bpf_prog_test_run error: %d (%s) ", 669 saved_errno, strerror(saved_errno)); 670 return err; 671 } 672 673 ASSERT_OK(0, "bpf_prog_test_run"); 674 *retval = topts.retval; 675 676 return 0; 677 } 678 679 static bool should_do_test_run(struct test_spec *spec, struct test_subspec *subspec) 680 { 681 if (!subspec->execute) 682 return false; 683 684 if (subspec->expect_failure) 685 return false; 686 687 if ((spec->prog_flags & BPF_F_ANY_ALIGNMENT) && !EFFICIENT_UNALIGNED_ACCESS) { 688 if (env.verbosity != VERBOSE_NONE) 689 printf("alignment prevents execution\n"); 690 return false; 691 } 692 693 return true; 694 } 695 696 /* Get a disassembly of BPF program after verifier applies all rewrites */ 697 static int get_xlated_program_text(int prog_fd, char *text, size_t text_sz) 698 { 699 struct bpf_insn *insn_start = NULL, *insn, *insn_end; 700 __u32 insns_cnt = 0, i; 701 char buf[64]; 702 FILE *out = NULL; 703 int err; 704 705 err = get_xlated_program(prog_fd, &insn_start, &insns_cnt); 706 if (!ASSERT_OK(err, "get_xlated_program")) 707 goto out; 708 out = fmemopen(text, text_sz, "w"); 709 if (!ASSERT_OK_PTR(out, "open_memstream")) 710 goto out; 711 insn_end = insn_start + insns_cnt; 712 insn = insn_start; 713 while (insn < insn_end) { 714 i = insn - insn_start; 715 insn = disasm_insn(insn, buf, sizeof(buf)); 716 fprintf(out, "%d: %s\n", i, buf); 717 } 718 fflush(out); 719 720 out: 721 free(insn_start); 722 if (out) 723 fclose(out); 724 return err; 725 } 726 727 static bool run_on_current_arch(int arch_mask) 728 { 729 if (arch_mask == 0) 730 return true; 731 #if defined(__x86_64__) 732 return arch_mask & ARCH_X86_64; 733 #elif defined(__aarch64__) 734 return arch_mask & ARCH_ARM64; 735 #elif defined(__riscv) && __riscv_xlen == 64 736 return arch_mask & ARCH_RISCV64; 737 #endif 738 return false; 739 } 740 741 /* this function is forced noinline and has short generic name to look better 742 * in test_progs output (in case of a failure) 743 */ 744 static noinline 745 void run_subtest(struct test_loader *tester, 746 struct bpf_object_open_opts *open_opts, 747 const void *obj_bytes, 748 size_t obj_byte_cnt, 749 struct test_spec *specs, 750 struct test_spec *spec, 751 bool unpriv) 752 { 753 struct test_subspec *subspec = unpriv ? &spec->unpriv : &spec->priv; 754 struct bpf_program *tprog = NULL, *tprog_iter; 755 struct test_spec *spec_iter; 756 struct cap_state caps = {}; 757 struct bpf_object *tobj; 758 struct bpf_map *map; 759 int retval, err, i; 760 bool should_load; 761 762 if (!test__start_subtest(subspec->name)) 763 return; 764 765 if (!run_on_current_arch(spec->arch_mask)) { 766 test__skip(); 767 return; 768 } 769 770 if (unpriv) { 771 if (!can_execute_unpriv(tester, spec)) { 772 test__skip(); 773 test__end_subtest(); 774 return; 775 } 776 if (drop_capabilities(&caps)) { 777 test__end_subtest(); 778 return; 779 } 780 } 781 782 /* Implicitly reset to NULL if next test case doesn't specify */ 783 open_opts->btf_custom_path = spec->btf_custom_path; 784 785 tobj = bpf_object__open_mem(obj_bytes, obj_byte_cnt, open_opts); 786 if (!ASSERT_OK_PTR(tobj, "obj_open_mem")) /* shouldn't happen */ 787 goto subtest_cleanup; 788 789 i = 0; 790 bpf_object__for_each_program(tprog_iter, tobj) { 791 spec_iter = &specs[i++]; 792 should_load = false; 793 794 if (spec_iter->valid) { 795 if (strcmp(bpf_program__name(tprog_iter), spec->prog_name) == 0) { 796 tprog = tprog_iter; 797 should_load = true; 798 } 799 800 if (spec_iter->auxiliary && 801 spec_iter->mode_mask & (unpriv ? UNPRIV : PRIV)) 802 should_load = true; 803 } 804 805 bpf_program__set_autoload(tprog_iter, should_load); 806 } 807 808 prepare_case(tester, spec, tobj, tprog); 809 810 /* By default bpf_object__load() automatically creates all 811 * maps declared in the skeleton. Some map types are only 812 * allowed in priv mode. Disable autoload for such maps in 813 * unpriv mode. 814 */ 815 bpf_object__for_each_map(map, tobj) 816 bpf_map__set_autocreate(map, !unpriv || is_unpriv_capable_map(map)); 817 818 err = bpf_object__load(tobj); 819 if (subspec->expect_failure) { 820 if (!ASSERT_ERR(err, "unexpected_load_success")) { 821 emit_verifier_log(tester->log_buf, false /*force*/); 822 goto tobj_cleanup; 823 } 824 } else { 825 if (!ASSERT_OK(err, "unexpected_load_failure")) { 826 emit_verifier_log(tester->log_buf, true /*force*/); 827 goto tobj_cleanup; 828 } 829 } 830 emit_verifier_log(tester->log_buf, false /*force*/); 831 validate_msgs(tester->log_buf, &subspec->expect_msgs, emit_verifier_log); 832 833 if (subspec->expect_xlated.cnt) { 834 err = get_xlated_program_text(bpf_program__fd(tprog), 835 tester->log_buf, tester->log_buf_sz); 836 if (err) 837 goto tobj_cleanup; 838 emit_xlated(tester->log_buf, false /*force*/); 839 validate_msgs(tester->log_buf, &subspec->expect_xlated, emit_xlated); 840 } 841 842 if (should_do_test_run(spec, subspec)) { 843 /* For some reason test_verifier executes programs 844 * with all capabilities restored. Do the same here. 845 */ 846 if (restore_capabilities(&caps)) 847 goto tobj_cleanup; 848 849 if (tester->pre_execution_cb) { 850 err = tester->pre_execution_cb(tobj); 851 if (err) { 852 PRINT_FAIL("pre_execution_cb failed: %d\n", err); 853 goto tobj_cleanup; 854 } 855 } 856 857 do_prog_test_run(bpf_program__fd(tprog), &retval, 858 bpf_program__type(tprog) == BPF_PROG_TYPE_SYSCALL ? true : false); 859 if (retval != subspec->retval && subspec->retval != POINTER_VALUE) { 860 PRINT_FAIL("Unexpected retval: %d != %d\n", retval, subspec->retval); 861 goto tobj_cleanup; 862 } 863 } 864 865 tobj_cleanup: 866 bpf_object__close(tobj); 867 subtest_cleanup: 868 test__end_subtest(); 869 restore_capabilities(&caps); 870 } 871 872 static void process_subtest(struct test_loader *tester, 873 const char *skel_name, 874 skel_elf_bytes_fn elf_bytes_factory) 875 { 876 LIBBPF_OPTS(bpf_object_open_opts, open_opts, .object_name = skel_name); 877 struct test_spec *specs = NULL; 878 struct bpf_object *obj = NULL; 879 struct bpf_program *prog; 880 const void *obj_bytes; 881 int err, i, nr_progs; 882 size_t obj_byte_cnt; 883 884 if (tester_init(tester) < 0) 885 return; /* failed to initialize tester */ 886 887 obj_bytes = elf_bytes_factory(&obj_byte_cnt); 888 obj = bpf_object__open_mem(obj_bytes, obj_byte_cnt, &open_opts); 889 if (!ASSERT_OK_PTR(obj, "obj_open_mem")) 890 return; 891 892 nr_progs = 0; 893 bpf_object__for_each_program(prog, obj) 894 ++nr_progs; 895 896 specs = calloc(nr_progs, sizeof(struct test_spec)); 897 if (!ASSERT_OK_PTR(specs, "specs_alloc")) 898 return; 899 900 i = 0; 901 bpf_object__for_each_program(prog, obj) { 902 /* ignore tests for which we can't derive test specification */ 903 err = parse_test_spec(tester, obj, prog, &specs[i++]); 904 if (err) 905 PRINT_FAIL("Can't parse test spec for program '%s'\n", 906 bpf_program__name(prog)); 907 } 908 909 i = 0; 910 bpf_object__for_each_program(prog, obj) { 911 struct test_spec *spec = &specs[i++]; 912 913 if (!spec->valid || spec->auxiliary) 914 continue; 915 916 if (spec->mode_mask & PRIV) 917 run_subtest(tester, &open_opts, obj_bytes, obj_byte_cnt, 918 specs, spec, false); 919 if (spec->mode_mask & UNPRIV) 920 run_subtest(tester, &open_opts, obj_bytes, obj_byte_cnt, 921 specs, spec, true); 922 923 } 924 925 for (i = 0; i < nr_progs; ++i) 926 free_test_spec(&specs[i]); 927 free(specs); 928 bpf_object__close(obj); 929 } 930 931 void test_loader__run_subtests(struct test_loader *tester, 932 const char *skel_name, 933 skel_elf_bytes_fn elf_bytes_factory) 934 { 935 /* see comment in run_subtest() for why we do this function nesting */ 936 process_subtest(tester, skel_name, elf_bytes_factory); 937 } 938
Linux® is a registered trademark of Linus Torvalds in the United States and other countries.
TOMOYO® is a registered trademark of NTT DATA CORPORATION.