Merge branch 'bpftool-fixes'

Quentin Monnet says:

====================
Hi,
Several items for bpftool are included in this set: the first three patches
are fixes for bpftool itself and bash completion, while the last two
slightly improve the information obtained when dumping programs or maps, on
Daniel's suggestion. Please refer to individual commit logs for more
details.
====================

Signed-off-by: Alexei Starovoitov <ast@kernel.org>
This commit is contained in:
Alexei Starovoitov 2018-11-30 14:06:07 -08:00
commit 779a459719
6 changed files with 129 additions and 65 deletions

View file

@ -243,16 +243,20 @@ _bpftool()
# Completion depends on object and command in use # Completion depends on object and command in use
case $object in case $object in
prog) prog)
if [[ $command != "load" && $command != "loadall" ]]; then # Complete id, only for subcommands that use prog (but no map) ids
case $prev in case $command in
id) show|list|dump|pin)
_bpftool_get_prog_ids case $prev in
return 0 id)
;; _bpftool_get_prog_ids
esac return 0
fi ;;
esac
;;
esac
local PROG_TYPE='id pinned tag' local PROG_TYPE='id pinned tag'
local MAP_TYPE='id pinned'
case $command in case $command in
show|list) show|list)
[[ $prev != "$command" ]] && return 0 [[ $prev != "$command" ]] && return 0
@ -293,22 +297,43 @@ _bpftool()
return 0 return 0
;; ;;
attach|detach) attach|detach)
if [[ ${#words[@]} == 7 ]]; then case $cword in
COMPREPLY=( $( compgen -W "id pinned" -- "$cur" ) ) 3)
return 0 COMPREPLY=( $( compgen -W "$PROG_TYPE" -- "$cur" ) )
fi return 0
;;
if [[ ${#words[@]} == 6 ]]; then 4)
COMPREPLY=( $( compgen -W "msg_verdict skb_verdict \ case $prev in
skb_parse flow_dissector" -- "$cur" ) ) id)
return 0 _bpftool_get_prog_ids
fi ;;
pinned)
if [[ $prev == "$command" ]]; then _filedir
COMPREPLY=( $( compgen -W "id pinned" -- "$cur" ) ) ;;
return 0 esac
fi return 0
return 0 ;;
5)
COMPREPLY=( $( compgen -W 'msg_verdict skb_verdict \
skb_parse flow_dissector' -- "$cur" ) )
return 0
;;
6)
COMPREPLY=( $( compgen -W "$MAP_TYPE" -- "$cur" ) )
return 0
;;
7)
case $prev in
id)
_bpftool_get_map_ids
;;
pinned)
_filedir
;;
esac
return 0
;;
esac
;; ;;
load|loadall) load|loadall)
local obj local obj
@ -411,7 +436,7 @@ _bpftool()
lru_percpu_hash lpm_trie array_of_maps \ lru_percpu_hash lpm_trie array_of_maps \
hash_of_maps devmap sockmap cpumap xskmap \ hash_of_maps devmap sockmap cpumap xskmap \
sockhash cgroup_storage reuseport_sockarray \ sockhash cgroup_storage reuseport_sockarray \
percpu_cgroup_storage' -- \ percpu_cgroup_storage queue stack' -- \
"$cur" ) ) "$cur" ) )
return 0 return 0
;; ;;

View file

@ -48,7 +48,6 @@
#include <sys/mount.h> #include <sys/mount.h>
#include <sys/resource.h> #include <sys/resource.h>
#include <sys/stat.h> #include <sys/stat.h>
#include <sys/types.h>
#include <sys/vfs.h> #include <sys/vfs.h>
#include <bpf.h> #include <bpf.h>
@ -276,7 +275,7 @@ int get_fd_type(int fd)
char buf[512]; char buf[512];
ssize_t n; ssize_t n;
snprintf(path, sizeof(path), "/proc/%d/fd/%d", getpid(), fd); snprintf(path, sizeof(path), "/proc/self/fd/%d", fd);
n = readlink(path, buf, sizeof(buf)); n = readlink(path, buf, sizeof(buf));
if (n < 0) { if (n < 0) {
@ -304,7 +303,7 @@ char *get_fdinfo(int fd, const char *key)
ssize_t n; ssize_t n;
FILE *fdi; FILE *fdi;
snprintf(path, sizeof(path), "/proc/%d/fdinfo/%d", getpid(), fd); snprintf(path, sizeof(path), "/proc/self/fdinfo/%d", fd);
fdi = fopen(path, "r"); fdi = fopen(path, "r");
if (!fdi) { if (!fdi) {
@ -605,7 +604,7 @@ void print_dev_plain(__u32 ifindex, __u64 ns_dev, __u64 ns_inode)
if (!ifindex) if (!ifindex)
return; return;
printf(" dev "); printf(" offloaded_to ");
if (ifindex_to_name_ns(ifindex, ns_dev, ns_inode, name)) if (ifindex_to_name_ns(ifindex, ns_dev, ns_inode, name))
printf("%s", name); printf("%s", name);
else else

View file

@ -19,7 +19,6 @@
#include <string.h> #include <string.h>
#include <bfd.h> #include <bfd.h>
#include <dis-asm.h> #include <dis-asm.h>
#include <sys/types.h>
#include <sys/stat.h> #include <sys/stat.h>
#include <limits.h> #include <limits.h>
@ -28,20 +27,12 @@
static void get_exec_path(char *tpath, size_t size) static void get_exec_path(char *tpath, size_t size)
{ {
const char *path = "/proc/self/exe";
ssize_t len; ssize_t len;
char *path;
snprintf(tpath, size, "/proc/%d/exe", (int) getpid());
tpath[size - 1] = 0;
path = strdup(tpath);
assert(path);
len = readlink(path, tpath, size - 1); len = readlink(path, tpath, size - 1);
assert(len > 0); assert(len > 0);
tpath[len] = 0; tpath[len] = 0;
free(path);
} }
static int oper_count; static int oper_count;

View file

@ -78,6 +78,32 @@
#define HELP_SPEC_MAP \ #define HELP_SPEC_MAP \
"MAP := { id MAP_ID | pinned FILE }" "MAP := { id MAP_ID | pinned FILE }"
static const char * const prog_type_name[] = {
[BPF_PROG_TYPE_UNSPEC] = "unspec",
[BPF_PROG_TYPE_SOCKET_FILTER] = "socket_filter",
[BPF_PROG_TYPE_KPROBE] = "kprobe",
[BPF_PROG_TYPE_SCHED_CLS] = "sched_cls",
[BPF_PROG_TYPE_SCHED_ACT] = "sched_act",
[BPF_PROG_TYPE_TRACEPOINT] = "tracepoint",
[BPF_PROG_TYPE_XDP] = "xdp",
[BPF_PROG_TYPE_PERF_EVENT] = "perf_event",
[BPF_PROG_TYPE_CGROUP_SKB] = "cgroup_skb",
[BPF_PROG_TYPE_CGROUP_SOCK] = "cgroup_sock",
[BPF_PROG_TYPE_LWT_IN] = "lwt_in",
[BPF_PROG_TYPE_LWT_OUT] = "lwt_out",
[BPF_PROG_TYPE_LWT_XMIT] = "lwt_xmit",
[BPF_PROG_TYPE_SOCK_OPS] = "sock_ops",
[BPF_PROG_TYPE_SK_SKB] = "sk_skb",
[BPF_PROG_TYPE_CGROUP_DEVICE] = "cgroup_device",
[BPF_PROG_TYPE_SK_MSG] = "sk_msg",
[BPF_PROG_TYPE_RAW_TRACEPOINT] = "raw_tracepoint",
[BPF_PROG_TYPE_CGROUP_SOCK_ADDR] = "cgroup_sock_addr",
[BPF_PROG_TYPE_LWT_SEG6LOCAL] = "lwt_seg6local",
[BPF_PROG_TYPE_LIRC_MODE2] = "lirc_mode2",
[BPF_PROG_TYPE_SK_REUSEPORT] = "sk_reuseport",
[BPF_PROG_TYPE_FLOW_DISSECTOR] = "flow_dissector",
};
enum bpf_obj_type { enum bpf_obj_type {
BPF_OBJ_UNKNOWN, BPF_OBJ_UNKNOWN,
BPF_OBJ_PROG, BPF_OBJ_PROG,

View file

@ -487,7 +487,6 @@ static int show_map_close_json(int fd, struct bpf_map_info *info)
char *memlock; char *memlock;
memlock = get_fdinfo(fd, "memlock"); memlock = get_fdinfo(fd, "memlock");
close(fd);
jsonw_start_object(json_wtr); jsonw_start_object(json_wtr);
@ -514,6 +513,30 @@ static int show_map_close_json(int fd, struct bpf_map_info *info)
jsonw_int_field(json_wtr, "bytes_memlock", atoi(memlock)); jsonw_int_field(json_wtr, "bytes_memlock", atoi(memlock));
free(memlock); free(memlock);
if (info->type == BPF_MAP_TYPE_PROG_ARRAY) {
char *owner_prog_type = get_fdinfo(fd, "owner_prog_type");
char *owner_jited = get_fdinfo(fd, "owner_jited");
if (owner_prog_type) {
unsigned int prog_type = atoi(owner_prog_type);
if (prog_type < ARRAY_SIZE(prog_type_name))
jsonw_string_field(json_wtr, "owner_prog_type",
prog_type_name[prog_type]);
else
jsonw_uint_field(json_wtr, "owner_prog_type",
prog_type);
}
if (atoi(owner_jited))
jsonw_bool_field(json_wtr, "owner_jited", true);
else
jsonw_bool_field(json_wtr, "owner_jited", false);
free(owner_prog_type);
free(owner_jited);
}
close(fd);
if (!hash_empty(map_table.table)) { if (!hash_empty(map_table.table)) {
struct pinned_obj *obj; struct pinned_obj *obj;
@ -536,7 +559,6 @@ static int show_map_close_plain(int fd, struct bpf_map_info *info)
char *memlock; char *memlock;
memlock = get_fdinfo(fd, "memlock"); memlock = get_fdinfo(fd, "memlock");
close(fd);
printf("%u: ", info->id); printf("%u: ", info->id);
if (info->type < ARRAY_SIZE(map_type_name)) if (info->type < ARRAY_SIZE(map_type_name))
@ -557,6 +579,30 @@ static int show_map_close_plain(int fd, struct bpf_map_info *info)
printf(" memlock %sB", memlock); printf(" memlock %sB", memlock);
free(memlock); free(memlock);
if (info->type == BPF_MAP_TYPE_PROG_ARRAY) {
char *owner_prog_type = get_fdinfo(fd, "owner_prog_type");
char *owner_jited = get_fdinfo(fd, "owner_jited");
printf("\n\t");
if (owner_prog_type) {
unsigned int prog_type = atoi(owner_prog_type);
if (prog_type < ARRAY_SIZE(prog_type_name))
printf("owner_prog_type %s ",
prog_type_name[prog_type]);
else
printf("owner_prog_type %d ", prog_type);
}
if (atoi(owner_jited))
printf("owner jited");
else
printf("owner not jited");
free(owner_prog_type);
free(owner_jited);
}
close(fd);
printf("\n"); printf("\n");
if (!hash_empty(map_table.table)) { if (!hash_empty(map_table.table)) {
struct pinned_obj *obj; struct pinned_obj *obj;

View file

@ -54,30 +54,6 @@
#include "main.h" #include "main.h"
#include "xlated_dumper.h" #include "xlated_dumper.h"
static const char * const prog_type_name[] = {
[BPF_PROG_TYPE_UNSPEC] = "unspec",
[BPF_PROG_TYPE_SOCKET_FILTER] = "socket_filter",
[BPF_PROG_TYPE_KPROBE] = "kprobe",
[BPF_PROG_TYPE_SCHED_CLS] = "sched_cls",
[BPF_PROG_TYPE_SCHED_ACT] = "sched_act",
[BPF_PROG_TYPE_TRACEPOINT] = "tracepoint",
[BPF_PROG_TYPE_XDP] = "xdp",
[BPF_PROG_TYPE_PERF_EVENT] = "perf_event",
[BPF_PROG_TYPE_CGROUP_SKB] = "cgroup_skb",
[BPF_PROG_TYPE_CGROUP_SOCK] = "cgroup_sock",
[BPF_PROG_TYPE_LWT_IN] = "lwt_in",
[BPF_PROG_TYPE_LWT_OUT] = "lwt_out",
[BPF_PROG_TYPE_LWT_XMIT] = "lwt_xmit",
[BPF_PROG_TYPE_SOCK_OPS] = "sock_ops",
[BPF_PROG_TYPE_SK_SKB] = "sk_skb",
[BPF_PROG_TYPE_CGROUP_DEVICE] = "cgroup_device",
[BPF_PROG_TYPE_SK_MSG] = "sk_msg",
[BPF_PROG_TYPE_RAW_TRACEPOINT] = "raw_tracepoint",
[BPF_PROG_TYPE_CGROUP_SOCK_ADDR] = "cgroup_sock_addr",
[BPF_PROG_TYPE_LIRC_MODE2] = "lirc_mode2",
[BPF_PROG_TYPE_FLOW_DISSECTOR] = "flow_dissector",
};
static const char * const attach_type_strings[] = { static const char * const attach_type_strings[] = {
[BPF_SK_SKB_STREAM_PARSER] = "stream_parser", [BPF_SK_SKB_STREAM_PARSER] = "stream_parser",
[BPF_SK_SKB_STREAM_VERDICT] = "stream_verdict", [BPF_SK_SKB_STREAM_VERDICT] = "stream_verdict",
@ -1172,6 +1148,7 @@ static int do_help(int argc, char **argv)
" tracepoint | raw_tracepoint | xdp | perf_event | cgroup/skb |\n" " tracepoint | raw_tracepoint | xdp | perf_event | cgroup/skb |\n"
" cgroup/sock | cgroup/dev | lwt_in | lwt_out | lwt_xmit |\n" " cgroup/sock | cgroup/dev | lwt_in | lwt_out | lwt_xmit |\n"
" lwt_seg6local | sockops | sk_skb | sk_msg | lirc_mode2 |\n" " lwt_seg6local | sockops | sk_skb | sk_msg | lirc_mode2 |\n"
" sk_reuseport | flow_dissector |\n"
" cgroup/bind4 | cgroup/bind6 | cgroup/post_bind4 |\n" " cgroup/bind4 | cgroup/bind6 | cgroup/post_bind4 |\n"
" cgroup/post_bind6 | cgroup/connect4 | cgroup/connect6 |\n" " cgroup/post_bind6 | cgroup/connect4 | cgroup/connect6 |\n"
" cgroup/sendmsg4 | cgroup/sendmsg6 }\n" " cgroup/sendmsg4 | cgroup/sendmsg6 }\n"