aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorYonghong Song <yhs@fb.com>2019-01-10 14:14:02 -0500
committerDaniel Borkmann <daniel@iogearbox.net>2019-01-11 04:40:54 -0500
commit298e59d322954e89ed2a556c601a04a4c007d1b3 (patch)
tree8702529ada7e857caa223af4c4523d5c2e58cb59
parente43207fa2e6130e39e3aca4c55e2ee21cfb46828 (diff)
tools/bpf: fix bpftool map dump with bitfields
Commit 8772c8bc093b ("tools: bpftool: support pretty print with kind_flag set") added bpftool map dump with kind_flag support. When bitfield_size can be retrieved directly from btf_member, function btf_dumper_bitfield() is called to dump the bitfield. The implementation passed the wrong parameter "bit_offset" to the function. The excepted value is the bit_offset within a byte while the passed-in value is the struct member offset. This commit fixed the bug with passing correct "bit_offset" with adjusted data pointer. Fixes: 8772c8bc093b ("tools: bpftool: support pretty print with kind_flag set") Acked-by: Martin KaFai Lau <kafai@fb.com> Signed-off-by: Yonghong Song <yhs@fb.com> Signed-off-by: Daniel Borkmann <daniel@iogearbox.net>
-rw-r--r--tools/bpf/bpftool/btf_dumper.c13
1 files changed, 7 insertions, 6 deletions
diff --git a/tools/bpf/bpftool/btf_dumper.c b/tools/bpf/bpftool/btf_dumper.c
index 3f0629edbca5..6ba5f567a9d8 100644
--- a/tools/bpf/bpftool/btf_dumper.c
+++ b/tools/bpf/bpftool/btf_dumper.c
@@ -82,8 +82,6 @@ static void btf_dumper_bitfield(__u32 nr_bits, __u8 bit_offset,
82 int bits_to_copy; 82 int bits_to_copy;
83 __u64 print_num; 83 __u64 print_num;
84 84
85 data += BITS_ROUNDDOWN_BYTES(bit_offset);
86 bit_offset = BITS_PER_BYTE_MASKED(bit_offset);
87 bits_to_copy = bit_offset + nr_bits; 85 bits_to_copy = bit_offset + nr_bits;
88 bytes_to_copy = BITS_ROUNDUP_BYTES(bits_to_copy); 86 bytes_to_copy = BITS_ROUNDUP_BYTES(bits_to_copy);
89 87
@@ -118,7 +116,9 @@ static void btf_dumper_int_bits(__u32 int_type, __u8 bit_offset,
118 * BTF_INT_OFFSET() cannot exceed 64 bits. 116 * BTF_INT_OFFSET() cannot exceed 64 bits.
119 */ 117 */
120 total_bits_offset = bit_offset + BTF_INT_OFFSET(int_type); 118 total_bits_offset = bit_offset + BTF_INT_OFFSET(int_type);
121 btf_dumper_bitfield(nr_bits, total_bits_offset, data, jw, 119 data += BITS_ROUNDDOWN_BYTES(total_bits_offset);
120 bit_offset = BITS_PER_BYTE_MASKED(total_bits_offset);
121 btf_dumper_bitfield(nr_bits, bit_offset, data, jw,
122 is_plain_text); 122 is_plain_text);
123} 123}
124 124
@@ -216,11 +216,12 @@ static int btf_dumper_struct(const struct btf_dumper *d, __u32 type_id,
216 } 216 }
217 217
218 jsonw_name(d->jw, btf__name_by_offset(d->btf, m[i].name_off)); 218 jsonw_name(d->jw, btf__name_by_offset(d->btf, m[i].name_off));
219 data_off = data + BITS_ROUNDDOWN_BYTES(bit_offset);
219 if (bitfield_size) { 220 if (bitfield_size) {
220 btf_dumper_bitfield(bitfield_size, bit_offset, 221 btf_dumper_bitfield(bitfield_size,
221 data, d->jw, d->is_plain_text); 222 BITS_PER_BYTE_MASKED(bit_offset),
223 data_off, d->jw, d->is_plain_text);
222 } else { 224 } else {
223 data_off = data + BITS_ROUNDDOWN_BYTES(bit_offset);
224 ret = btf_dumper_do_type(d, m[i].type, 225 ret = btf_dumper_do_type(d, m[i].type,
225 BITS_PER_BYTE_MASKED(bit_offset), 226 BITS_PER_BYTE_MASKED(bit_offset),
226 data_off); 227 data_off);