1. 11 3月, 2021 1 次提交
  2. 05 3月, 2021 1 次提交
  3. 04 2月, 2021 1 次提交
  4. 20 11月, 2020 1 次提交
  5. 30 9月, 2020 2 次提交
  6. 09 9月, 2020 1 次提交
    • T
      tools/libbpf: Avoid counting local symbols in ABI check · 746f534a
      Tony Ambardar 提交于
      Encountered the following failure building libbpf from kernel 5.8.5 sources
      with GCC 8.4.0 and binutils 2.34: (long paths shortened)
      
        Warning: Num of global symbols in sharedobjs/libbpf-in.o (234) does NOT
        match with num of versioned symbols in libbpf.so (236). Please make sure
        all LIBBPF_API symbols are versioned in libbpf.map.
        --- libbpf_global_syms.tmp    2020-09-02 07:30:58.920084380 +0000
        +++ libbpf_versioned_syms.tmp 2020-09-02 07:30:58.924084388 +0000
        @@ -1,3 +1,5 @@
        +_fini
        +_init
         bpf_btf_get_fd_by_id
         bpf_btf_get_next_id
         bpf_create_map
        make[4]: *** [Makefile:210: check_abi] Error 1
      
      Investigation shows _fini and _init are actually local symbols counted
      amongst global ones:
      
        $ readelf --dyn-syms --wide libbpf.so|head -10
      
        Symbol table '.dynsym' contains 343 entries:
           Num:    Value  Size Type    Bind   Vis      Ndx Name
             0: 00000000     0 NOTYPE  LOCAL  DEFAULT  UND
             1: 00004098     0 SECTION LOCAL  DEFAULT   11
             2: 00004098     8 FUNC    LOCAL  DEFAULT   11 _init@@LIBBPF_0.0.1
             3: 00023040     8 FUNC    LOCAL  DEFAULT   14 _fini@@LIBBPF_0.0.1
             4: 00000000     0 OBJECT  GLOBAL DEFAULT  ABS LIBBPF_0.0.4
             5: 00000000     0 OBJECT  GLOBAL DEFAULT  ABS LIBBPF_0.0.1
             6: 0000ffa4     8 FUNC    GLOBAL DEFAULT   12 bpf_object__find_map_by_offset@@LIBBPF_0.0.1
      
      A previous commit filtered global symbols in sharedobjs/libbpf-in.o. Do the
      same with the libbpf.so DSO for consistent comparison.
      
      Fixes: 306b267c ("libbpf: Verify versioned symbols")
      Signed-off-by: NTony Ambardar <Tony.Ambardar@gmail.com>
      Signed-off-by: NAlexei Starovoitov <ast@kernel.org>
      Acked-by: NAndrii Nakryiko <andriin@fb.com>
      Link: https://lore.kernel.org/bpf/20200905214831.1565465-1-Tony.Ambardar@gmail.com
      746f534a
  7. 03 9月, 2020 1 次提交
  8. 28 8月, 2020 1 次提交
  9. 20 8月, 2020 1 次提交
    • A
      bpf: Add kernel module with user mode driver that populates bpffs. · d71fa5c9
      Alexei Starovoitov 提交于
      Add kernel module with user mode driver that populates bpffs with
      BPF iterators.
      
      $ mount bpffs /my/bpffs/ -t bpf
      $ ls -la /my/bpffs/
      total 4
      drwxrwxrwt  2 root root    0 Jul  2 00:27 .
      drwxr-xr-x 19 root root 4096 Jul  2 00:09 ..
      -rw-------  1 root root    0 Jul  2 00:27 maps.debug
      -rw-------  1 root root    0 Jul  2 00:27 progs.debug
      
      The user mode driver will load BPF Type Formats, create BPF maps, populate BPF
      maps, load two BPF programs, attach them to BPF iterators, and finally send two
      bpf_link IDs back to the kernel.
      The kernel will pin two bpf_links into newly mounted bpffs instance under
      names "progs.debug" and "maps.debug". These two files become human readable.
      
      $ cat /my/bpffs/progs.debug
        id name            attached
        11 dump_bpf_map    bpf_iter_bpf_map
        12 dump_bpf_prog   bpf_iter_bpf_prog
        27 test_pkt_access
        32 test_main       test_pkt_access test_pkt_access
        33 test_subprog1   test_pkt_access_subprog1 test_pkt_access
        34 test_subprog2   test_pkt_access_subprog2 test_pkt_access
        35 test_subprog3   test_pkt_access_subprog3 test_pkt_access
        36 new_get_skb_len get_skb_len test_pkt_access
        37 new_get_skb_ifindex get_skb_ifindex test_pkt_access
        38 new_get_constant get_constant test_pkt_access
      
      The BPF program dump_bpf_prog() in iterators.bpf.c is printing this data about
      all BPF programs currently loaded in the system. This information is unstable
      and will change from kernel to kernel as ".debug" suffix conveys.
      Signed-off-by: NAlexei Starovoitov <ast@kernel.org>
      Signed-off-by: NDaniel Borkmann <daniel@iogearbox.net>
      Link: https://lore.kernel.org/bpf/20200819042759.51280-4-alexei.starovoitov@gmail.com
      d71fa5c9
  10. 19 8月, 2020 3 次提交
  11. 02 6月, 2020 2 次提交
  12. 14 1月, 2020 1 次提交
  13. 10 1月, 2020 1 次提交
  14. 23 12月, 2019 1 次提交
  15. 18 12月, 2019 1 次提交
  16. 16 12月, 2019 2 次提交
    • A
      libbpf: Support libbpf-provided extern variables · 166750bc
      Andrii Nakryiko 提交于
      Add support for extern variables, provided to BPF program by libbpf. Currently
      the following extern variables are supported:
        - LINUX_KERNEL_VERSION; version of a kernel in which BPF program is
          executing, follows KERNEL_VERSION() macro convention, can be 4- and 8-byte
          long;
        - CONFIG_xxx values; a set of values of actual kernel config. Tristate,
          boolean, strings, and integer values are supported.
      
      Set of possible values is determined by declared type of extern variable.
      Supported types of variables are:
      - Tristate values. Are represented as `enum libbpf_tristate`. Accepted values
        are **strictly** 'y', 'n', or 'm', which are represented as TRI_YES, TRI_NO,
        or TRI_MODULE, respectively.
      - Boolean values. Are represented as bool (_Bool) types. Accepted values are
        'y' and 'n' only, turning into true/false values, respectively.
      - Single-character values. Can be used both as a substritute for
        bool/tristate, or as a small-range integer:
        - 'y'/'n'/'m' are represented as is, as characters 'y', 'n', or 'm';
        - integers in a range [-128, 127] or [0, 255] (depending on signedness of
          char in target architecture) are recognized and represented with
          respective values of char type.
      - Strings. String values are declared as fixed-length char arrays. String of
        up to that length will be accepted and put in first N bytes of char array,
        with the rest of bytes zeroed out. If config string value is longer than
        space alloted, it will be truncated and warning message emitted. Char array
        is always zero terminated. String literals in config have to be enclosed in
        double quotes, just like C-style string literals.
      - Integers. 8-, 16-, 32-, and 64-bit integers are supported, both signed and
        unsigned variants. Libbpf enforces parsed config value to be in the
        supported range of corresponding integer type. Integers values in config can
        be:
        - decimal integers, with optional + and - signs;
        - hexadecimal integers, prefixed with 0x or 0X;
        - octal integers, starting with 0.
      
      Config file itself is searched in /boot/config-$(uname -r) location with
      fallback to /proc/config.gz, unless config path is specified explicitly
      through bpf_object_open_opts' kernel_config_path option. Both gzipped and
      plain text formats are supported. Libbpf adds explicit dependency on zlib
      because of this, but this shouldn't be a problem, given libelf already depends
      on zlib.
      
      All detected extern variables, are put into a separate .extern internal map.
      It, similarly to .rodata map, is marked as read-only from BPF program side, as
      well as is frozen on load. This allows BPF verifier to track extern values as
      constants and perform enhanced branch prediction and dead code elimination.
      This can be relied upon for doing kernel version/feature detection and using
      potentially unsupported field relocations or BPF helpers in a CO-RE-based BPF
      program, while still having a single version of BPF program running on old and
      new kernels. Selftests are validating this explicitly for unexisting BPF
      helper.
      Signed-off-by: NAndrii Nakryiko <andriin@fb.com>
      Signed-off-by: NAlexei Starovoitov <ast@kernel.org>
      Link: https://lore.kernel.org/bpf/20191214014710.3449601-3-andriin@fb.com
      166750bc
    • T
      libbpf: Fix readelf output parsing for Fedora · aa915931
      Thadeu Lima de Souza Cascardo 提交于
      Fedora binutils has been patched to show "other info" for a symbol at the
      end of the line. This was done in order to support unmaintained scripts
      that would break with the extra info. [1]
      
      [1] https://src.fedoraproject.org/rpms/binutils/c/b8265c46f7ddae23a792ee8306fbaaeacba83bf8
      
      This in turn has been done to fix the build of ruby, because of checksec.
      [2] Thanks Michael Ellerman for the pointer.
      
      [2] https://bugzilla.redhat.com/show_bug.cgi?id=1479302
      
      As libbpf Makefile is not unmaintained, we can simply deal with either
      output format, by just removing the "other info" field, as it always comes
      inside brackets.
      
      Fixes: 3464afdf (libbpf: Fix readelf output parsing on powerpc with recent binutils)
      Reported-by: NJustin Forbes <jmforbes@linuxtx.org>
      Signed-off-by: NThadeu Lima de Souza Cascardo <cascardo@canonical.com>
      Signed-off-by: NAlexei Starovoitov <ast@kernel.org>
      Acked-by: NAndrii Nakryiko <andriin@fb.com>
      Cc: Aurelien Jarno <aurelien@aurel32.net>
      Link: https://lore.kernel.org/bpf/20191213101114.GA3986@calabresa
      aa915931
  17. 05 12月, 2019 1 次提交
  18. 02 12月, 2019 1 次提交
  19. 28 11月, 2019 2 次提交
  20. 21 10月, 2019 1 次提交
  21. 13 10月, 2019 2 次提交
  22. 09 10月, 2019 2 次提交
  23. 06 10月, 2019 1 次提交
  24. 01 10月, 2019 1 次提交
    • Y
      libbpf: handle symbol versioning properly for libbpf.a · 1bd63524
      Yonghong Song 提交于
      bcc uses libbpf repo as a submodule. It brings in libbpf source
      code and builds everything together to produce shared libraries.
      With latest libbpf, I got the following errors:
        /bin/ld: libbcc_bpf.so.0.10.0: version node not found for symbol xsk_umem__create@LIBBPF_0.0.2
        /bin/ld: failed to set dynamic section sizes: Bad value
        collect2: error: ld returned 1 exit status
        make[2]: *** [src/cc/libbcc_bpf.so.0.10.0] Error 1
      
      In xsk.c, we have
        asm(".symver xsk_umem__create_v0_0_2, xsk_umem__create@LIBBPF_0.0.2");
        asm(".symver xsk_umem__create_v0_0_4, xsk_umem__create@@LIBBPF_0.0.4");
      The linker thinks the built is for LIBBPF but cannot find proper version
      LIBBPF_0.0.2/4, so emit errors.
      
      I also confirmed that using libbpf.a to produce a shared library also
      has issues:
        -bash-4.4$ cat t.c
        extern void *xsk_umem__create;
        void * test() { return xsk_umem__create; }
        -bash-4.4$ gcc -c -fPIC t.c
        -bash-4.4$ gcc -shared t.o libbpf.a -o t.so
        /bin/ld: t.so: version node not found for symbol xsk_umem__create@LIBBPF_0.0.2
        /bin/ld: failed to set dynamic section sizes: Bad value
        collect2: error: ld returned 1 exit status
        -bash-4.4$
      
      Symbol versioning does happens in commonly used libraries, e.g., elfutils
      and glibc. For static libraries, for a versioned symbol, the old definitions
      will be ignored, and the symbol will be an alias to the latest definition.
      For example, glibc sched_setaffinity is versioned.
        -bash-4.4$ readelf -s /usr/lib64/libc.so.6 | grep sched_setaffinity
           756: 000000000013d3d0    13 FUNC    GLOBAL DEFAULT   13 sched_setaffinity@GLIBC_2.3.3
           757: 00000000000e2e70   455 FUNC    GLOBAL DEFAULT   13 sched_setaffinity@@GLIBC_2.3.4
          1800: 0000000000000000     0 FILE    LOCAL  DEFAULT  ABS sched_setaffinity.c
          4228: 00000000000e2e70   455 FUNC    LOCAL  DEFAULT   13 __sched_setaffinity_new
          4648: 000000000013d3d0    13 FUNC    LOCAL  DEFAULT   13 __sched_setaffinity_old
          7338: 000000000013d3d0    13 FUNC    GLOBAL DEFAULT   13 sched_setaffinity@GLIBC_2
          7380: 00000000000e2e70   455 FUNC    GLOBAL DEFAULT   13 sched_setaffinity@@GLIBC_
        -bash-4.4$
      For static library, the definition of sched_setaffinity aliases to the new definition.
        -bash-4.4$ readelf -s /usr/lib64/libc.a | grep sched_setaffinity
        File: /usr/lib64/libc.a(sched_setaffinity.o)
           8: 0000000000000000   455 FUNC    GLOBAL DEFAULT    1 __sched_setaffinity_new
          12: 0000000000000000   455 FUNC    WEAK   DEFAULT    1 sched_setaffinity
      
      For both elfutils and glibc, additional macros are used to control different handling
      of symbol versioning w.r.t static and shared libraries.
      For elfutils, the macro is SYMBOL_VERSIONING
      (https://sourceware.org/git/?p=elfutils.git;a=blob;f=lib/eu-config.h).
      For glibc, the macro is SHARED
      (https://sourceware.org/git/?p=glibc.git;a=blob;f=include/shlib-compat.h;hb=refs/heads/master)
      
      This patch used SHARED as the macro name. After this patch, the libbpf.a has
        -bash-4.4$ readelf -s libbpf.a | grep xsk_umem__create
           372: 0000000000017145  1190 FUNC    GLOBAL DEFAULT    1 xsk_umem__create_v0_0_4
           405: 0000000000017145  1190 FUNC    GLOBAL DEFAULT    1 xsk_umem__create
           499: 00000000000175eb   103 FUNC    GLOBAL DEFAULT    1 xsk_umem__create_v0_0_2
        -bash-4.4$
      No versioned symbols for xsk_umem__create.
      The libbpf.a can be used to build a shared library succesfully.
        -bash-4.4$ cat t.c
        extern void *xsk_umem__create;
        void * test() { return xsk_umem__create; }
        -bash-4.4$ gcc -c -fPIC t.c
        -bash-4.4$ gcc -shared t.o libbpf.a -o t.so
        -bash-4.4$
      
      Fixes: 10d30e30 ("libbpf: add flags to umem config")
      Cc: Kevin Laatz <kevin.laatz@intel.com>
      Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
      Cc: Andrii Nakryiko <andriin@fb.com>
      Acked-by: NAndrii Nakryiko <andriin@fb.com>
      Signed-off-by: NYonghong Song <yhs@fb.com>
      Signed-off-by: NAlexei Starovoitov <ast@kernel.org>
      1bd63524
  25. 30 9月, 2019 1 次提交
  26. 31 8月, 2019 1 次提交
  27. 21 8月, 2019 1 次提交
  28. 16 8月, 2019 1 次提交
    • A
      libbpf: make libbpf.map source of truth for libbpf version · dadb81d0
      Andrii Nakryiko 提交于
      Currently libbpf version is specified in 2 places: libbpf.map and
      Makefile. They easily get out of sync and it's very easy to update one,
      but forget to update another one. In addition, Github projection of
      libbpf has to maintain its own version which has to be remembered to be
      kept in sync manually, which is very error-prone approach.
      
      This patch makes libbpf.map a source of truth for libbpf version and
      uses shell invocation to parse out correct full and major libbpf version
      to use during build. Now we need to make sure that once new release
      cycle starts, we need to add (initially) empty section to libbpf.map
      with correct latest version.
      
      This also will make it possible to keep Github projection consistent
      with kernel sources version of libbpf by adopting similar parsing of
      version from libbpf.map.
      
      v2->v3:
      - grep -o + sort -rV (Andrey);
      
      v1->v2:
      - eager version vars evaluation (Jakub);
      - simplified version regex (Andrey);
      
      Cc: Andrey Ignatov <rdna@fb.com>
      Signed-off-by: NAndrii Nakryiko <andriin@fb.com>
      Acked-by: NAndrey Ignatov <rdna@fb.com>
      Signed-off-by: NAlexei Starovoitov <ast@kernel.org>
      dadb81d0
  29. 28 5月, 2019 1 次提交
  30. 23 5月, 2019 1 次提交
  31. 05 5月, 2019 1 次提交
  32. 10 4月, 2019 1 次提交
    • D
      bpf, libbpf: support global data/bss/rodata sections · d859900c
      Daniel Borkmann 提交于
      This work adds BPF loader support for global data sections
      to libbpf. This allows to write BPF programs in more natural
      C-like way by being able to define global variables and const
      data.
      
      Back at LPC 2018 [0] we presented a first prototype which
      implemented support for global data sections by extending BPF
      syscall where union bpf_attr would get additional memory/size
      pair for each section passed during prog load in order to later
      add this base address into the ldimm64 instruction along with
      the user provided offset when accessing a variable. Consensus
      from LPC was that for proper upstream support, it would be
      more desirable to use maps instead of bpf_attr extension as
      this would allow for introspection of these sections as well
      as potential live updates of their content. This work follows
      this path by taking the following steps from loader side:
      
       1) In bpf_object__elf_collect() step we pick up ".data",
          ".rodata", and ".bss" section information.
      
       2) If present, in bpf_object__init_internal_map() we add
          maps to the obj's map array that corresponds to each
          of the present sections. Given section size and access
          properties can differ, a single entry array map is
          created with value size that is corresponding to the
          ELF section size of .data, .bss or .rodata. These
          internal maps are integrated into the normal map
          handling of libbpf such that when user traverses all
          obj maps, they can be differentiated from user-created
          ones via bpf_map__is_internal(). In later steps when
          we actually create these maps in the kernel via
          bpf_object__create_maps(), then for .data and .rodata
          sections their content is copied into the map through
          bpf_map_update_elem(). For .bss this is not necessary
          since array map is already zero-initialized by default.
          Additionally, for .rodata the map is frozen as read-only
          after setup, such that neither from program nor syscall
          side writes would be possible.
      
       3) In bpf_program__collect_reloc() step, we record the
          corresponding map, insn index, and relocation type for
          the global data.
      
       4) And last but not least in the actual relocation step in
          bpf_program__relocate(), we mark the ldimm64 instruction
          with src_reg = BPF_PSEUDO_MAP_VALUE where in the first
          imm field the map's file descriptor is stored as similarly
          done as in BPF_PSEUDO_MAP_FD, and in the second imm field
          (as ldimm64 is 2-insn wide) we store the access offset
          into the section. Given these maps have only single element
          ldimm64's off remains zero in both parts.
      
       5) On kernel side, this special marked BPF_PSEUDO_MAP_VALUE
          load will then store the actual target address in order
          to have a 'map-lookup'-free access. That is, the actual
          map value base address + offset. The destination register
          in the verifier will then be marked as PTR_TO_MAP_VALUE,
          containing the fixed offset as reg->off and backing BPF
          map as reg->map_ptr. Meaning, it's treated as any other
          normal map value from verification side, only with
          efficient, direct value access instead of actual call to
          map lookup helper as in the typical case.
      
      Currently, only support for static global variables has been
      added, and libbpf rejects non-static global variables from
      loading. This can be lifted until we have proper semantics
      for how BPF will treat multi-object BPF loads. From BTF side,
      libbpf will set the value type id of the types corresponding
      to the ".bss", ".data" and ".rodata" names which LLVM will
      emit without the object name prefix. The key type will be
      left as zero, thus making use of the key-less BTF option in
      array maps.
      
      Simple example dump of program using globals vars in each
      section:
      
        # bpftool prog
        [...]
        6784: sched_cls  name load_static_dat  tag a7e1291567277844  gpl
              loaded_at 2019-03-11T15:39:34+0000  uid 0
              xlated 1776B  jited 993B  memlock 4096B  map_ids 2238,2237,2235,2236,2239,2240
      
        # bpftool map show id 2237
        2237: array  name test_glo.bss  flags 0x0
              key 4B  value 64B  max_entries 1  memlock 4096B
        # bpftool map show id 2235
        2235: array  name test_glo.data  flags 0x0
              key 4B  value 64B  max_entries 1  memlock 4096B
        # bpftool map show id 2236
        2236: array  name test_glo.rodata  flags 0x80
              key 4B  value 96B  max_entries 1  memlock 4096B
      
        # bpftool prog dump xlated id 6784
        int load_static_data(struct __sk_buff * skb):
        ; int load_static_data(struct __sk_buff *skb)
           0: (b7) r6 = 0
        ; test_reloc(number, 0, &num0);
           1: (63) *(u32 *)(r10 -4) = r6
           2: (bf) r2 = r10
        ; int load_static_data(struct __sk_buff *skb)
           3: (07) r2 += -4
        ; test_reloc(number, 0, &num0);
           4: (18) r1 = map[id:2238]
           6: (18) r3 = map[id:2237][0]+0    <-- direct addr in .bss area
           8: (b7) r4 = 0
           9: (85) call array_map_update_elem#100464
          10: (b7) r1 = 1
        ; test_reloc(number, 1, &num1);
        [...]
        ; test_reloc(string, 2, str2);
         120: (18) r8 = map[id:2237][0]+16   <-- same here at offset +16
         122: (18) r1 = map[id:2239]
         124: (18) r3 = map[id:2237][0]+16
         126: (b7) r4 = 0
         127: (85) call array_map_update_elem#100464
         128: (b7) r1 = 120
        ; str1[5] = 'x';
         129: (73) *(u8 *)(r9 +5) = r1
        ; test_reloc(string, 3, str1);
         130: (b7) r1 = 3
         131: (63) *(u32 *)(r10 -4) = r1
         132: (b7) r9 = 3
         133: (bf) r2 = r10
        ; int load_static_data(struct __sk_buff *skb)
         134: (07) r2 += -4
        ; test_reloc(string, 3, str1);
         135: (18) r1 = map[id:2239]
         137: (18) r3 = map[id:2235][0]+16   <-- direct addr in .data area
         139: (b7) r4 = 0
         140: (85) call array_map_update_elem#100464
         141: (b7) r1 = 111
        ; __builtin_memcpy(&str2[2], "hello", sizeof("hello"));
         142: (73) *(u8 *)(r8 +6) = r1       <-- further access based on .bss data
         143: (b7) r1 = 108
         144: (73) *(u8 *)(r8 +5) = r1
        [...]
      
      For Cilium use-case in particular, this enables migrating configuration
      constants from Cilium daemon's generated header defines into global
      data sections such that expensive runtime recompilations with LLVM can
      be avoided altogether. Instead, the ELF file becomes effectively a
      "template", meaning, it is compiled only once (!) and the Cilium daemon
      will then rewrite relevant configuration data from the ELF's .data or
      .rodata sections directly instead of recompiling the program. The
      updated ELF is then loaded into the kernel and atomically replaces
      the existing program in the networking datapath. More info in [0].
      
      Based upon recent fix in LLVM, commit c0db6b6bd444 ("[BPF] Don't fail
      for static variables").
      
        [0] LPC 2018, BPF track, "ELF relocation for static data in BPF",
            http://vger.kernel.org/lpc-bpf2018.html#session-3Signed-off-by: NDaniel Borkmann <daniel@iogearbox.net>
      Acked-by: NAndrii Nakryiko <andriin@fb.com>
      Acked-by: NMartin KaFai Lau <kafai@fb.com>
      Signed-off-by: NAlexei Starovoitov <ast@kernel.org>
      d859900c