Skip to content
  • Andrey Ignatov's avatar
    selftests/bpf: Selftest for sys_connect hooks · 622adafb
    Andrey Ignatov authored
    
    
    Add selftest for BPF_CGROUP_INET4_CONNECT and BPF_CGROUP_INET6_CONNECT
    attach types.
    
    Try to connect(2) to specified IP:port and test that:
    * remote IP:port pair is overridden;
    * local end of connection is bound to specified IP.
    
    All combinations of IPv4/IPv6 and TCP/UDP are tested.
    
    Example:
      # tcpdump -pn -i lo -w connect.pcap 2>/dev/null &
      [1] 478
      # strace -qqf -e connect -o connect.trace ./test_sock_addr.sh
      Wait for testing IPv4/IPv6 to become available ... OK
      Load bind4 with invalid type (can pollute stderr) ... REJECTED
      Load bind4 with valid type ... OK
      Attach bind4 with invalid type ... REJECTED
      Attach bind4 with valid type ... OK
      Load connect4 with invalid type (can pollute stderr) libbpf: load bpf \
        program failed: Permission denied
      libbpf: -- BEGIN DUMP LOG ---
      libbpf:
      0: (b7) r2 = 23569
      1: (63) *(u32 *)(r1 +24) = r2
      2: (b7) r2 = 16777343
      3: (63) *(u32 *)(r1 +4) = r2
      invalid bpf_context access off=4 size=4
      [ 1518.404609] random: crng init done
    
      libbpf: -- END LOG --
      libbpf: failed to load program 'cgroup/connect4'
      libbpf: failed to load object './connect4_prog.o'
      ... REJECTED
      Load connect4 with valid type ... OK
      Attach connect4 with invalid type ... REJECTED
      Attach connect4 with valid type ... OK
      Test case #1 (IPv4/TCP):
              Requested: bind(192.168.1.254, 4040) ..
                 Actual: bind(127.0.0.1, 4444)
              Requested: connect(192.168.1.254, 4040) from (*, *) ..
                 Actual: connect(127.0.0.1, 4444) from (127.0.0.4, 56068)
      Test case #2 (IPv4/UDP):
              Requested: bind(192.168.1.254, 4040) ..
                 Actual: bind(127.0.0.1, 4444)
              Requested: connect(192.168.1.254, 4040) from (*, *) ..
                 Actual: connect(127.0.0.1, 4444) from (127.0.0.4, 56447)
      Load bind6 with invalid type (can pollute stderr) ... REJECTED
      Load bind6 with valid type ... OK
      Attach bind6 with invalid type ... REJECTED
      Attach bind6 with valid type ... OK
      Load connect6 with invalid type (can pollute stderr) libbpf: load bpf \
        program failed: Permission denied
      libbpf: -- BEGIN DUMP LOG ---
      libbpf:
      0: (b7) r6 = 0
      1: (63) *(u32 *)(r1 +12) = r6
      invalid bpf_context access off=12 size=4
    
      libbpf: -- END LOG --
      libbpf: failed to load program 'cgroup/connect6'
      libbpf: failed to load object './connect6_prog.o'
      ... REJECTED
      Load connect6 with valid type ... OK
      Attach connect6 with invalid type ... REJECTED
      Attach connect6 with valid type ... OK
      Test case #3 (IPv6/TCP):
              Requested: bind(face:b00c:1234:5678::abcd, 6060) ..
                 Actual: bind(::1, 6666)
              Requested: connect(face:b00c:1234:5678::abcd, 6060) from (*, *)
                 Actual: connect(::1, 6666) from (::6, 37458)
      Test case #4 (IPv6/UDP):
              Requested: bind(face:b00c:1234:5678::abcd, 6060) ..
                 Actual: bind(::1, 6666)
              Requested: connect(face:b00c:1234:5678::abcd, 6060) from (*, *)
                 Actual: connect(::1, 6666) from (::6, 39315)
      ### SUCCESS
      # egrep 'connect\(.*AF_INET' connect.trace | \
      > egrep -vw 'htons\(1025\)' | fold -b -s -w 72
      502   connect(7, {sa_family=AF_INET, sin_port=htons(4040),
      sin_addr=inet_addr("192.168.1.254")}, 128) = 0
      502   connect(8, {sa_family=AF_INET, sin_port=htons(4040),
      sin_addr=inet_addr("192.168.1.254")}, 128) = 0
      502   connect(9, {sa_family=AF_INET6, sin6_port=htons(6060),
      inet_pton(AF_INET6, "face:b00c:1234:5678::abcd", &sin6_addr),
      sin6_flowinfo=0, sin6_scope_id=0}, 128) = 0
      502   connect(10, {sa_family=AF_INET6, sin6_port=htons(6060),
      inet_pton(AF_INET6, "face:b00c:1234:5678::abcd", &sin6_addr),
      sin6_flowinfo=0, sin6_scope_id=0}, 128) = 0
      # fg
      tcpdump -pn -i lo -w connect.pcap 2> /dev/null
      # tcpdump -r connect.pcap -n tcp | cut -c 1-72
      reading from file connect.pcap, link-type EN10MB (Ethernet)
      17:57:40.383533 IP 127.0.0.4.56068 > 127.0.0.1.4444: Flags [S], seq 1333
      17:57:40.383566 IP 127.0.0.1.4444 > 127.0.0.4.56068: Flags [S.], seq 112
      17:57:40.383589 IP 127.0.0.4.56068 > 127.0.0.1.4444: Flags [.], ack 1, w
      17:57:40.384578 IP 127.0.0.1.4444 > 127.0.0.4.56068: Flags [R.], seq 1,
      17:57:40.403327 IP6 ::6.37458 > ::1.6666: Flags [S], seq 406513443, win
      17:57:40.403357 IP6 ::1.6666 > ::6.37458: Flags [S.], seq 2448389240, ac
      17:57:40.403376 IP6 ::6.37458 > ::1.6666: Flags [.], ack 1, win 342, opt
      17:57:40.404263 IP6 ::1.6666 > ::6.37458: Flags [R.], seq 1, ack 1, win
    
    Signed-off-by: default avatarAndrey Ignatov <rdna@fb.com>
    Signed-off-by: default avatarAlexei Starovoitov <ast@kernel.org>
    Signed-off-by: default avatarDaniel Borkmann <daniel@iogearbox.net>
    622adafb