/* Ensure that the field->offset has been correctly advanced from one * nested struct or array sub-tree to another. In the case of * kptr_nested_deep, it comprises two sub-trees: ktpr_1 and kptr_2. By * calling bpf_kptr_xchg() on every single kptr in both nested sub-trees, * the verifier should reject the program if the field->offset of any kptr * is incorrect. * * For instance, if we have 10 kptrs in a nested struct and a program that * accesses each kptr individually with bpf_kptr_xchg(), the compiler * should emit instructions to access 10 different offsets if it works * correctly. If the field->offset values of any pair of them are * incorrectly the same, the number of unique offsets in btf_record for * this nested struct should be less than 10. The verifier should fail to * discover some of the offsets emitted by the compiler. * * Even if the field->offset values of kptrs are not duplicated, the * verifier should fail to find a btf_field for the instruction accessing a * kptr if the corresponding field->offset is pointing to a random * incorrect offset.
*/
SEC("tp_btf/task_newtask") int BPF_PROG(test_global_mask_nested_deep_rcu, struct task_struct *task, u64 clone_flags)
{ int r, i;
r = _global_mask_array_rcu(&global_mask_nested_deep.ptrs[0].m.mask,
&global_mask_nested_deep.ptrs[1].m.mask); if (r) return r;
for (i = 0; i < 3; i++) {
r = _global_mask_array_rcu(&global_mask_nested_deep.ptr_pairs[i].mask_1,
&global_mask_nested_deep.ptr_pairs[i].mask_2); if (r) return r;
} return 0;
}
SEC("tp_btf/task_newtask") int BPF_PROG(test_global_mask_nested_deep_array_rcu, struct task_struct *task, u64 clone_flags)
{ int i;
for (i = 0; i < CPUMASK_KPTR_FIELDS_MAX; i++)
_global_mask_array_rcu(&global_mask_nested_deep_array_1.d_1.d_2.mask[i], NULL);
for (i = 0; i < CPUMASK_KPTR_FIELDS_MAX; i++)
_global_mask_array_rcu(&global_mask_nested_deep_array_2.d_1.d_2[i].mask, NULL);
for (i = 0; i < CPUMASK_KPTR_FIELDS_MAX; i++)
_global_mask_array_rcu(&global_mask_nested_deep_array_3.d_1[i].d_2.mask, NULL);
/* * Make sure that adding additional CPUs changes the weight. Test to * see whether the CPU was set to account for running on UP machines.
*/
bpf_cpumask_set_cpu(1, local); if (bpf_cpumask_test_cpu(1, cast(local)) && bpf_cpumask_weight(cast(local)) != 2) {
err = 5; goto out;
}
free_masks_return: if (mask1)
bpf_cpumask_release(mask1); if (mask2)
bpf_cpumask_release(mask2); return 0;
}
SEC("tp_btf/task_newtask") int BPF_PROG(test_populate_reject_small_mask, struct task_struct *task, u64 clone_flags)
{ struct bpf_cpumask *local;
u8 toofewbits; int ret;
if (!is_test_task()) return 0;
local = create_cpumask(); if (!local) return 0;
/* The kfunc should prevent this operation */
ret = bpf_cpumask_populate((struct cpumask *)local, &toofewbits, sizeof(toofewbits)); if (ret != -EACCES)
err = 2;
bpf_cpumask_release(local);
return 0;
}
/* Mask is guaranteed to be large enough for bpf_cpumask_t. */ #define CPUMASK_TEST_MASKLEN (sizeof(cpumask_t))
/* Add an extra word for the test_populate_reject_unaligned test. */
u64 bits[CPUMASK_TEST_MASKLEN / 8 + 1]; externbool CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS __kconfig __weak;
SEC("tp_btf/task_newtask") int BPF_PROG(test_populate_reject_unaligned, struct task_struct *task, u64 clone_flags)
{ struct bpf_cpumask *mask; char *src; int ret;
if (!is_test_task()) return 0;
/* Skip if unaligned accesses are fine for this arch. */ if (CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS) return 0;
/* Pass the entire bits array, the kfunc will only copy the valid bits. */
ret = bpf_cpumask_populate((struct cpumask *)mask, bits, CPUMASK_TEST_MASKLEN); if (ret) {
err = 2; goto out;
}
/* * Test is there to appease the verifier. We cannot directly * access NR_CPUS, the upper bound for nr_cpus, so we infer * it from the size of cpumask_t.
*/ if (nr_cpus < 0 || nr_cpus >= CPUMASK_TEST_MASKLEN * 8) {
err = 3; goto out;
}
bpf_for(i, 0, nr_cpus) { /* Odd-numbered bits should be set, even ones unset. */
bit = bpf_cpumask_test_cpu(i, (conststruct cpumask *)mask); if (bit == (i % 2 != 0)) continue;
err = 4; break;
}
out:
bpf_cpumask_release(mask);
return 0;
}
#undef CPUMASK_TEST_MASKLEN
Messung V0.5
¤ Dauer der Verarbeitung: 0.1 Sekunden
(vorverarbeitet)
¤
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.