Open sofardware opened 4 years ago
sofardware notifications@github.com writes:
[root@localhost packet03-redirecting]# make ... [root@localhost packet03-redirecting]# t exec -n left -- ./xdp_loader -d veth0 -F --progsec xdp_pass libbpf: Error in bpf_objectprobe_name():Operation not permitted(1). Couldn't load basic 'r0 = 0' BPF program. libbpf: Error in bpf_objectprobe_global_data():Operation not permitted(1). Couldn't create simple array map. libbpf: failed to create map (name: 'xdp_stats_map'): Operation not permitted(-1) libbpf: failed to load object 'xdp_prog_kern.o' ERR: loading BPF-OBJ file(xdp_prog_kern.o) (-22): Invalid argument ERR: loading file: xdp_prog_kern.o
Hmm, this seems like another ulimit error; I fear the raising of the limit we are currently doing is not sufficient.
Could you try the following, please:
In place of your 't exec' line, do t his:
t enter -n left ulimit -l unlimited ./xdp_loader -d veth0 -F --progsec xdp_pass
Does this work?
Yes,it does. Thank you very much. [root@localhost packet03-redirecting]# t enter -n left [root@localhost packet03-redirecting]# ulimit -l unlimited [root@localhost packet03-redirecting]# ./xdp_loader -d veth0 -F --progsec xdp_pass Success: Loaded BPF-object(xdp_prog_kern.o) and used section(xdp_pass)
sofardware notifications@github.com writes:
Yes,it does. Thank you very much.
Great, thanks for confirming!
when I added memcpy(eth->h_dest, dst, ETH_ALEN); in xdp_redirect_func, and the follow commd failed. why?
[root@localhost packet03-redirecting]# ./xdp_loader -d veth0 -F --progsec xdp_pass Success: Loaded BPF-object(xdp_prog_kern.o) and used section(xdp_pass)
int xdp_redirect_func(struct xdp_md ctx) { void data_end = (void )(long)ctx->data_end; void data = (void )(long)ctx->data; struct hdr_cursor nh; struct ethhdr eth; int eth_type; int action = XDP_PASS;
**unsigned char dst[ETH_ALEN] = {0x2e,0x7d,0xf6,0x80,0xf9,0x26}; /* Assignment 2: fill in with the MAC address of the left inner interface */**
unsigned ifindex = 9;//6; /* Assignment 2: fill in with the ifindex of the left interface */
/* These keep track of the next header type and iterator pointer */
nh.pos = data;
/* Parse Ethernet and IP/IPv6 headers */
eth_type = parse_ethhdr(&nh, data_end, ð);
if (eth_type == -1)
goto out;
/* Assignment 2: set a proper destination address and call the
* bpf_redirect() with proper parameters, action = bpf_redirect(...) */
memcpy(eth->h_dest, dst, ETH_ALEN);
action = bpf_redirect(ifindex, 0);
out: return xdp_stats_record_action(ctx, action); }
sofardware notifications@github.com writes:
when I added memcpy(eth->h_dest, dst, ETH_ALEN); in xdp_redirect_func, and the follow commd failed. why?
Hmm, I think maybe because the pinned file is already there? Could you try manually removing the pinned files in /sys/fs/bpf/veth0 before loading the program?
I met the same problem. My system kernel is 5.4.2, but it working in kernel 4.18.16.
And I change the code unsigned char dst[ETH_ALEN] = {...};
to unsigned char dst[ETH_ALEN + 1] = {...};
or unsigned char dst[] = {... ,'\0'};
both working in kernel 5.4.2.
But I dont know why...
I ran into this exact same issue Pagbit reported.
As soon as I add the memcpy to xdp_redirect_func
unsigned char dst[ETH_ALEN] = {0x66, 0x6d, 0xc3, 0x44, 0x30, 0x9c}; memcpy(eth->h_dest, dst, ETH_ALEN);
I get this error xdp/xdp-tutorial/packet03-redirecting# t exec -n left -- ./xdp_loader -d veth0 -F --progsec xdp_pass Success: Loaded BPF-object(xdp_prog_kern.o) and used section(xdp_pass)
However, if I change the Mac addr to
unsigned char dst[ETH_ALEN+1] = {0x66, 0x6d, 0xc3, 0x44, 0x30, 0x9c, '\0'};
it starts to work
t exec -n left -- ./xdp_loader -d veth0 -F --progsec xdp_pass Success: Loaded BPF-object(xdp_prog_kern.o) and used section(xdp_pass)
Does anyone know why?
Thanks pagbit for the workaround/fix.
I also hit this bug. From my debugging (using ftrace), the _builtinmemcpy didn't pollute the target memory without '\0'. Is there any side effect of using _builtinmemcpy ?!
Instead I just copy the MAC bytes manually
#pragma unroll
for (i = 0; i < ETH_ALEN; i++) {
eth->h_dest[i] = dest[i];
}
Hitting the same problem as described above in assignment packet02-03:
libbpf: failed to pin map: Operation not permitted
ERR: pinning maps
The following change does indeed help:
unsigned char dst[ETH_ALEN] = {0xda, 0xa6, 0xad, 0xd4, 0x27, 0xb7};
-->
unsigned char dst[ETH_ALEN+1] = {0xda, 0xa6, 0xad, 0xd4, 0x27, 0xb7};
Okay, this was a fun one to track down :)
What happens is this:
When you add a constant ({0xda, 0xa6, 0xad, 0xd4, 0x27, 0xb7}
) to copy the MAC addr from, that gets stored in the .rodata section of the object file. When libbpf sees an .rodata section, it transparently creates a map to store the contents of that section. When pinning the maps, this map will also be pinned, but since its name contains a period, this fails, leading to the error you observe.
The reason making the array larger helps is that this makes the compiler think the constant is a zero-delimited string, and put it into a section called .rodata.str.1 instead, which libbpf will not create a map for (but you will notice output like libbpf: elf: skipping unrecognized data section(13) .rodata.str1.1
when loading).
So the real fix here is to fix libbpf; I'll send a patch for that. In the meantime, feel free to use the workaround of enlarging the array, but I'm going to close the pull request to include it... :)
[root@localhost packet03-redirecting]# make ... [root@localhost packet03-redirecting]# t exec -n left -- ./xdp_loader -d veth0 -F --progsec xdp_pass libbpf: Error in bpf_objectprobe_name():Operation not permitted(1). Couldn't load basic 'r0 = 0' BPF program. libbpf: Error in bpf_objectprobe_global_data():Operation not permitted(1). Couldn't create simple array map. libbpf: failed to create map (name: 'xdp_stats_map'): Operation not permitted(-1) libbpf: failed to load object 'xdp_prog_kern.o' ERR: loading BPF-OBJ file(xdp_prog_kern.o) (-22): Invalid argument ERR: loading file: xdp_prog_kern.o